DEV Community

Felix Jumason for AWS Community Builders

Posted on Fully Autonomous

A $0 AWS Bill Doesn’t Mean Free Infrastructure: Lessons from My Tailscale EC2 Server

My AWS console showed $5.18 in October usage and a $35.90 forecast for the end of the month. Then I opened Bills and saw an estimated total of $0.00.

Both views were telling me something useful. My resources were generating charges, and my AWS Community Builders credits were covering them.

That distinction sent me through the bill line by line. The result was a small cost investigation, a lesson about burstable EC2 instances, and the cleanup of a Tailscale server I chose to retire.

If you use AWS credits for experiments or a home lab, this is a practical way to understand what your account is consuming before the credits run out.

Usage and the amount payable

I started the investigation on October 6, 2026. At that point, the dashboard showed $5.18 in usage. When I captured the billing screenshots on October 7, the accumulated usage shown for Stockholm had reached $6.06. The estimated payable bill remained $0.00.

These are dated snapshots of a pending monthly bill. They are not a final invoice or evidence that every billing update had completed after cleanup.

October 2026 pending bill with a zero estimated grand total

Figure 1. The October bill still showed an estimated grand total of USD 0.00 on October 7. The account number has been redacted.

The distinction I needed was simple:

  • Usage charges: what the resources consumed before promotional credits.
  • Applied credits: the amounts AWS deducted from eligible charges.
  • Estimated bill: the resulting amount shown for the pending billing period.
  • Forecast: an estimate of future cost, rather than an invoice or spending limit.

A zero estimated bill did not tell me that the infrastructure was free to run indefinitely. It told me that the charges currently shown were covered.

Following the bill to Stockholm

The console had initially been set to N. Virginia. The charging resources were in EU Stockholm, or eu-north-1.

Opening EC2 in the current region would have been the wrong starting point. I used the bill to identify the region, then switched the resource console to Stockholm.

Under Bills, I expanded the service entries. Here is the comparison between the initial investigation and the later screenshot:

Usage category October 6 snapshot October 7 screenshot
Linux t3.micro instance time $1.34 $1.51
T3 surplus CPU credits $3.10 $3.71
EBS gp3 storage $0.11 $0.13
In-use public IPv4 address $0.63 $0.71
Total of displayed amounts $5.18 $6.06

The service labels initially made the account look busier than it was. Compute, CPU credits, and storage appeared under EC2, while the public IPv4 charge appeared under Virtual Private Cloud.

The resource inspection identified one running t3.micro instance named Tailscale, with an 8 GiB root volume and an auto-assigned public IPv4 address. No Auto Scaling group was listed for it.

CPU credits cost more than base compute

The largest line item was not the instance’s hourly price. It was T3 CPU credits.

In the October 7 screenshot, base compute was $1.51 and surplus CPU credits were $3.71. The billed CPU-credit usage was 74.274 vCPU-hours at $0.05 per vCPU-hour. Multiplying those values gives $3.7137, displayed as $3.71.

EC2 compute CPU credit and EBS charges with an offsetting promotional credit

Figure 2. Stockholm EC2 usage totaled $5.35. A matching Community Builders credit offset it. CPU credits accounted for $3.71 of the usage.

The instance’s credit specification was Unlimited. Burstable instances earn CPU credits and spend them when they burst. In Unlimited mode, they can use surplus credits after exhausting their earned balance. Surplus usage that is not paid down can produce additional charges. AWS explains the conditions in its Unlimited mode documentation.

That explains the billing mechanism. It does not identify which process used the CPU. The server’s name was Tailscale, but I did not inspect its workload or CPU history, so I cannot attribute the charge to Tailscale itself.

For a server I wanted to keep, the next investigation would be its processes and CloudWatch metrics, especially CPUUtilization, CPUCreditBalance, and CPUSurplusCreditsCharged. Switching to Standard mode would require considering performance limits, rather than treating it as a cost fix with no tradeoff.

The public IP had its own charge

The public IPv4 address generated another $0.71 in the later screenshot: 142 hours at $0.005 per hour.

Public IPv4 usage charge and matching Community Builders credit

Figure 3. The IPv4 charge appeared under VPC and was also covered by promotional credits.

The address was auto-assigned, rather than an Elastic IP allocation. That distinction mattered during cleanup because an allocated Elastic IP would need a separate check.

Retiring the instance and checking the disk

I chose to retire this server. Before termination, I checked its storage settings: the 8 GiB root volume had Delete on termination set to Yes.

Termination is irreversible. An attached volume configured for deletion is deleted with the instance, so this is a decision to make only after identifying any data you need to retain. See AWS’s termination guidance.

I terminated the instance using the normal shutdown path, leaving Skip OS shutdown unchecked. Then I verified the final state instead of relying only on the success banner.

Tailscale EC2 instance in the Terminated state

Figure 4. The instance reached Terminated. Its identifier has been redacted.

Next, I refreshed the Volumes page. It showed no volumes remaining in Stockholm.

Empty EBS volume list after termination

Figure 5. The refreshed volume list confirmed that the root disk was gone.

I also checked Elastic IPs, which showed no allocations in the region. These checks confirmed removal of the resources behind the identified charges; they were not an audit of every service in every AWS region.

Stopping an instance would have left its EBS storage in place. For my goal of retiring this server, verifying disk deletion was part of completing the cleanup.

What I will check on future experiments

For each AWS experiment, I now want to know the usage cost as well as the amount payable. Credits are useful, but I still need to understand what consumes them.

My review starts with the bill’s service, region, and usage type. For EC2, it continues through compute, CPU-credit configuration, attached disks, snapshots, and public IPs. Cleanup ends with a refreshed resource listing.

One final detail matters: AWS can charge an outstanding surplus CPU-credit balance when an Unlimited instance is stopped or terminated. Existing usage and billing updates can therefore still appear after shutdown. Deleting the server does not erase its history.

The outcome here was specific: I removed the Tailscale instance, confirmed its root volume was gone, and found no Elastic IP allocation left in Stockholm. The estimated bill was already zero because credits covered usage. The cleanup removed the infrastructure that had been consuming those credits.

Top comments (0)