← All posts

July 28, 2026 · Nick Krykunov

Your AWS account got hacked and the bill is huge. Do this now.

Your AWS bill jumped to five or six figures overnight and you did not do it. Here is the short version: secure the account first, delete what the attacker spun up across every region second, and ask AWS to review the charges third. Do it in that order. Below is each step in detail, and then the part that actually matters, which is making a bill like this impossible to run up in the first place.

First, breathe. This is common, it is recoverable, and panicking into the wrong order makes it worse. People post some version of “I am panicking pretty hard, how screwed am I?” almost every week. You are less screwed than you feel.

Do this in the next hour

The goal right now is not to understand what happened. It is to cut off the attacker’s ability to keep spending your money. Investigation comes after containment.

Rotate the credentials they are using. If the root account is compromised, reset the root password and enable MFA on it immediately. For IAM users, deactivate the access keys rather than deleting them at first, so you keep the record of what they did. Do not skip this to go look at the bill. Every minute the key stays live is more compute.

Revoke active sessions. Deactivating a key does not kill sessions already running on temporary credentials. In the IAM console, open each affected role, go to the revoke sessions tab, and revoke active sessions. This attaches a policy that denies anything issued before now.

Enable MFA on root if it was not already on. If the attacker changed the root email or you cannot get in, that is a support emergency, and you contact AWS through the account recovery path rather than a normal case.

That is containment. The account can no longer be driven by the credentials that were stolen. Now you can look at the damage.

Find what they spun up, in every region

This is the step people miss, and it is why bills keep climbing after the owner thinks they cleaned up. Attackers deliberately spread across regions, because most people only ever look at the one region their console defaults to.

Open Cost Explorer and group by region and by service. The spike will point you straight at the offending service, usually EC2 or ECS. Then go region by region and delete what does not belong: running and stopped EC2 instances, ECS clusters, EBS volumes and snapshots, Lambda functions, and any IAM users or roles you do not recognize. A recent campaign that AWS caught in late 2025 was creating dozens of ECS clusters and auto-scaling groups configured to grow from 20 to 999 instances, so do not assume one rogue instance is the whole story.

Expect them to have made deletion hard. In that same campaign, attackers used an instance attribute change to disable API termination so the victim could not simply delete the instances. If a resource refuses to terminate, that is why. Re-enable termination first, then kill it. Also check for IAM roles and Lambda functions they left behind for persistence, because a key you rotated does not help if they planted a way back in.

While you are in there, pull the CloudTrail event history and filter by the compromised access key. Look for RunInstances, CreateUser, and AssumeRole. This is both your cleanup checklist and your evidence for the refund conversation.

Will AWS actually refund it?

Usually, and not always. AWS frequently waives charges it confirms were caused by a fraudulent compromise, and your odds go up sharply when you secured the account fast and can show exactly what happened. But it is a discretionary review, not a guaranteed reversal, so go in with evidence and reasonable expectations.

Open a case in the Billing and Cost Management console once the account is secure. Tell them when you noticed, what you shut down and when, and that the resources were not yours. Attach the CloudTrail entries. The more it reads like “I was compromised, here is the timeline, here is what I did about it in the first hour,” the better the outcome tends to be. What you do not want is to ask for a refund while the mining is still running, because that undercuts the whole story.

Plan for the refund as likely. Never build your response around it as certain.

Why your budget alert did not save you

A lot of people set a billing alarm, feel protected, and then get hit anyway. Here is the uncomfortable reason. A budget alert is a notification, not a control. It cannot stop anything. And AWS billing data lags real usage by hours, so by the time the alert fires, the compute has already been running long enough to do the damage. The alert is a smoke detector that goes off after the house has burned.

The deeper problem is upstream of the alert entirely. A single credential had enough standing power to launch expensive compute in every region the moment it was stolen. The alert was never going to fix that. It was only ever going to tell you about it late.

How the key leaked in the first place

Almost always, it is one of a small set of boring causes, and we walk through a real one, a key exposed for ten minutes that cost $14,000, in how AWS account hacks actually happen. A key committed to a public GitHub repo, where automated scanners find and test it in about four minutes. A key in a config file on a laptop that got malware. A key a contractor kept after the engagement ended. A long-lived key that has been sitting in an environment variable for two years and finally got exposed. Notice that none of these are exotic. The common thread is a powerful credential that lived forever and sat somewhere it could eventually be found.

That is the thing to fix. Not the specific leak. The existence of a standing key with that much power.

How to make a huge bill impossible

The bill is a symptom. The disease is standing access, and the cure is to stop handing out permanent, broad credentials that wait around to be abused. Three changes do most of the work, and they help whether the culprit is a stolen key, a careless commit, a departed contractor, or an AI agent that decided to do something destructive.

Stop issuing standing keys. Access should be requested for a task and expire on its own rather than sitting in an account forever. A key that only exists for the twenty minutes someone actually needed it cannot be found and abused six months later. This is the single highest-leverage change most teams have not made, and it is what zero standing privileges means in practice.

Keep no long-lived credentials in code, config, or a contractor’s laptop. If nothing has a permanent key, there is nothing to leak. Short-lived credentials that rotate automatically remove the artifact the attacker was looking for.

Watch live sessions and stop anomalous activity in real time. This is the part billing alerts and deletion protections cannot do. Something has to read what a session is actually doing, notice that a credential just tried to launch a hundred instances across six regions, and cut it off in seconds rather than reporting it in hours.

That last piece is what Korvalis is built for. It installs inside your own AWS account, watches what live sessions are actually doing, and cuts off a session on its own when it turns anomalous or destructive, whether the session belongs to a leaked key, a contractor, an engineer, or an agent. It treats them the same, because your account does not care who holds the credential. Pair that with access that expires on its own, and the scenario in this post stops being possible: there is no standing key to steal, and if one is somehow abused, something is watching the session in real time instead of emailing you a bill.

The takeaway

If you are reading this mid-incident, work the order: secure, then clean, then claim. You will very likely get most or all of the money back, and the account will be fine. If you are reading this before it happens to you, do not stop at a budget alert and call it security. An alert tells you the money is already gone. The only real protection is upstream, where you decide whether a stolen credential runs into a wall or into a wide-open account with your card on file.

Frequently asked questions

My AWS account was hacked and the bill is huge, what do I do first? Secure the account before you investigate. Rotate or deactivate the compromised root and IAM credentials, revoke active sessions, and enable MFA on root. Then delete what the attacker launched across every region. Open the billing case last, once the spending has actually stopped.

Will AWS refund the charges? Often, but not guaranteed. AWS frequently waives charges confirmed to be from a fraudulent compromise, especially when you secured the account fast and can show the timeline in CloudTrail. Open a case in the Billing console with evidence, and treat the refund as likely rather than certain.

How did they spend so much so fast? A leaked key is exploited in minutes, and mining compute can be running within ten. Attackers spread expensive instances across many regions and disable termination so you cannot easily kill them, and the charges surface hours after the damage is done.

If a standing key with your whole account behind it is the thing you would rather not lie awake over, see how Korvalis handles it or join the waitlist.