Deleting an S3 Bucket Costs Money
AWS is complex. Start learning what's important now.
Sign up to get some heard-earned knowledge, starting with my top 10 AWS mistakes.
Yep! Deleting an S3 bucket (with files in it) isn't free.
If you ever tried to delete a bucket with files, you'll get an error. You have to delete all of the files first!
However, if your feeling brave and check the AWS pricing docs for S3, you'll note that DELETE requests are actually free!
What's incurring a cost?
It turns out you have to know what files to delete in order to delete them.
If you check out the API, this is a bit more obvious. The only methods for deleting objects are:
DeleteObject- Delete one file (You need to know the exact file name)
DeleteObjects- Delete up to 1000 (You need to know the exact file names)
So, while DELETE operations are free, LIST operations (to get a list of objects) are not free (~$.005 per 1000 requests, varying a bit by region).
The cost is cheap enough where emptying a bucket is often cheap, but it depends on how many objects are in the bucket!
Furthermore, LIST operations can only grab 1000 objects at a time. So, to get a list of objects, you need to paginate through all of them, 1000 at a time.
So you want to delete a bucket...
This really only matters for buckets with many objects, but I see the question about the quickest and cheapest ways to delete a bucket often enough that I thought it would be useful to show how.
Side note: The strategy to delete a bucket with many files quickly vs cheaply are not the same.
Here's a collection of fun ways to empty out a bucket before deleting it. Note that I'm mostly talking about objects in Standard storage tiers.
Within the last year, AWS added a handy Empty button to the S3 console when viewing a bucket. You can click that button and watch the S3 console make API calls on your behalf.
Here's what it does: It calls a LIST on the bucket, pagination through the objects in the bucket 1000 at a time. It calls a DeleteObjects API method, deleting 1000 at a time.
The cost is 1 API LIST call per 1000 objects in the bucket. Delete operations are free, so there's no extra cost there.
The AWS API doesn't directly support what we're after here, but the AWS CLI has some extra features to help us here (especially for the oldest AWS service - S3). Here are a few commands to help with emptying a bucket:
1# rm (remove) command deletes specific objects2aws s3 rm s3://some-bucket --recursive
Adding the recursive flag here is the key. This acts the same as the web console - paginate through objects 1000 at a time and delete them.
1# rb "remove bucket" command deletes a bucket2aws s3 rb s3://some-bucket --force
Adding the force flag deletes all the objects before finally deleting the bucket. It deletes files the same way as above.
The Web Console and CLI methods aren't necessarily slow, but they can be both slow and expensive for buckets with many objects.
This is the preferred method. If you can wait, emptying a bucket with S3 Lifecycles is the cheapest (probably, see below) and most efficient way.
- Lifecycle rules are ran once a day at midnight UTC (you'll have to wait to see results!)
- Lifecycles actions incur Transition costs, rather than API call costs. Marking an object as Expired (aka "ready to delete") is a "transition" for each object. Review the S3 pricing here.
- Objects in standard storage are free to transition. Objects in other storage types (Infrequent Access, Glacier, Intelligent Tiering, etc) have a cost to transition objects. That's why this person almost incurred a $20,000 bill.
If you're using standard storage, this is the cheaper way to do this. As a bonus, it will also clean up (abort) failed multi-part uploads.
If you like to do things the hard way, you can also get an export of all objects in a bucket using S3 Inventory and run the output through AWS Batch in order to delete those objects. I'm actually not sure how this is priced exactly, but I believe it might be a good option if you're not using standard storage.
Another potential idea is to list out all the objects and then use Step Functions to delete the objects.
Maybe Don't Delete Buckets
Don't delete a bucket you want to re-create ASAP.
AWS is "eventually consistent" within most services, and S3 is no exception. Deleting a bucket won't let you re-create that bucket immediately.
The wait is often hours until AWS released a bucket name (since bucket names are globally unique, not just within your account). You might be better off emptying a bucket but not deleting it.