Assumes you're comfortable with EC2/Auto Scaling and Spot instances (Part 3), S3 storage classes (Part 5), and Compute Optimizer (Part 15) — this part is where those individual cost levers get tied into an actual, account-wide financial management practice, not just a list of discount mechanisms.
Table of Contents#
- Why This Part Exists
- FinOps as a Discipline, Not a Tool
- The Well-Architected Cost Optimization Pillar, Revisited
- Cost Explorer — Understanding Where Money Actually Goes
- Cost Allocation Tags — The Prerequisite for Everything Else
- Cost Categories — Grouping Spend Beyond Tags
- AWS Budgets — Enforcing Limits, Not Just Observing Them
- Budget Actions — Automated Response, Not Just Alerts
- Cost Anomaly Detection
- Cost Anomaly Investigation, Visually
- AI-Powered Cost Investigation
- The Cost and Usage Report (CUR) — The Ground Truth
- Querying CUR With Athena
- Trusted Advisor's Cost Optimization Checks, Revisited
- Reserved Instances — Mechanics and Types
- Savings Plans — Mechanics and Types
- Reserved Instances vs Savings Plans — The Full Comparison
- Layering Commitments: The Real 2026 Practice
- Choosing a Commitment Term Length: 1-Year vs 3-Year
- Reserved Capacity Beyond EC2
- The Reserved Instance Marketplace
- Spot Instances, Revisited
- Compute Optimizer, Revisited: From Recommendation to Action
- Architecture-Level Cost Optimization: Graviton
- License and Software Costs: BYOL vs License-Included
- Support Plan Costs, Revisited
- Per-Service Cost Levers: Storage
- S3 Intelligent-Tiering — Automating the Lifecycle Decision
- Idle and Orphaned Resource Cleanup
- Cost Optimization for CI/CD and Build Infrastructure
- Per-Service Cost Levers: Data Transfer
- A Brief Note on API Gateway and AppSync Costs
- Per-Service Cost Levers: Serverless and Containers
- Per-Service Cost Levers: Databases
- Networking Cost Levers Beyond Data Transfer
- Where AWS-Native Tooling Stops: Third-Party FinOps Platforms
- Cost Guardrails as Code
- Observability and Logging Cost, Revisited
- The AWS Free Tier and Its Limits
- Multi-Account Cost Visibility: Consolidated Billing and RI/SP Sharing
- Unit Economics: The Metric That Actually Matters to the Business
- Showback and Chargeback
- Scheduling: Turning Off What Doesn't Need to Run Continuously
- The FinOps Framework's Three Phases
- A Cost Retrospective on This Series' Own Architectural Choices
- A Full Worked Example: A FinOps Review Cycle
- Bringing It Together: A Simple Cost-Optimization Priority Order
- Cost Optimization Best Practices — The Consolidated Checklist
- A Closing Distinction: Cost Optimization vs Cost Cutting
- Part 16 CLI Cheat Sheet
- Common Mistakes and Interview Traps
- Worked Practice Problems
- A Note on Region Selection and Cost
- Summary and What's Next
Why This Part Exists#
Every part of this series so far has occasionally mentioned cost as a side consideration — Spot instances
in Part 3, S3 storage classes in Part 5, HTTP APIs' cheaper pricing in Part 13. This part pulls cost into
its own first-class discipline, which is exactly how SAA-C03 (20% of the exam), SOA-C02, and SAP-C02 all
treat it, and it's this site's own currently-empty finops-cost content area filled in properly for the
first time. The center of gravity here is Cost Explorer, Budgets, and the Reserved Instance/Savings Plan
commitment decision — the tools that turn "our AWS bill went up" from a mystery into an answerable,
attributable question.
FinOps as a Discipline, Not a Tool#
FinOps (Cloud Financial Management, in AWS's own terminology) is the practice of making cost a shared responsibility across engineering, finance, and business teams — not a monthly finance-only bill review after the spend has already happened. The mental model worth internalizing: cost is a first-class architectural property, exactly like availability or latency, and it should be visible and actionable to the engineers making the decisions that drive it, not discovered after the fact by someone with no context on why a given service exists. Every tool in this part exists to make that visibility real rather than aspirational.
The Well-Architected Cost Optimization Pillar, Revisited#
Part 1 introduced the Well-Architected Framework's six pillars in passing. Cost Optimization's own design principles map directly onto this part's tooling: adopt a consumption model (pay for what's used — On-Demand, Spot, serverless), measure overall efficiency (Cost Explorer, CUR), stop spending on undifferentiated heavy lifting (managed services over self-hosted, the theme underlying most of this series' service choices), and analyze and attribute expenditure (cost allocation tags, showback/ chargeback). None of these principles are new information at this point in the series — this part is where they finally get concrete tooling attached to each one.
Cost Explorer — Understanding Where Money Actually Goes#
Cost Explorer is the primary analysis surface: a visual interface over 13 months of historical billing
data (daily granularity, hourly for the current and prior 14 days), filterable and groupable by service,
account, region, usage type, or tag, with built-in forecasting for future spend based on historical
trends. The core skill it enables is decomposition — "AWS spend went up 15% this month" becomes, after a
few clicks, "specifically EC2 On-Demand usage in us-east-1, specifically the production environment
tag, specifically driven by a doubled instance count since the 12th" — the same root-cause-two-levels-deep
discipline this series applies to technical incidents, applied here to a cost incident instead.
Cost Allocation Tags — The Prerequisite for Everything Else#
None of Cost Explorer's grouping, Budgets' scoping, or CUR's attribution works without cost allocation
tags activated first — a tag (Part 1's tagging discipline) has to be explicitly activated in the Billing
console before it becomes a queryable cost dimension at all; simply tagging a resource isn't sufficient on
its own. AWS-generated tags (aws:createdBy, tracking which principal created a resource) activate
automatically; user-defined tags (Environment, Team, CostCenter) require deliberate activation. This
is, in practice, the single most common reason a team's cost-attribution effort stalls: the tags exist on
every resource, but nobody activated them as cost allocation tags, so Cost Explorer simply can't group by
them yet.
Cost Categories — Grouping Spend Beyond Tags#
Cost Categories solve a gap tags alone can't: rule-based grouping of costs into named categories using criteria beyond simple tag matching — a specific linked account, a range of usage types, or a combination of tags with AND/OR logic — producing a single, stable category (say, "Platform Team") that spans resources tagged inconsistently across different eras of a project's history, or that don't share a common tag at all but should still roll up together for reporting purposes. Where a tag has to exist on the resource itself, a Cost Category is defined centrally and applied retroactively to historical data too — useful when tagging discipline was inconsistent early on and a clean report is still needed covering that earlier period.
AWS Budgets — Enforcing Limits, Not Just Observing Them#
Where Cost Explorer looks backward and sideways, AWS Budgets looks forward: a budget defines a threshold (cost, usage, RI/Savings Plan coverage, or RI/SP utilization) over a period, with configurable alert thresholds fired via SNS before the threshold is even reached, based on either actual or forecasted spend — the forecasted-spend alert is what lets a team catch a runaway trend on day 10 of a 30-day billing cycle instead of discovering it only after the month closes and the damage is already done.
Budget Actions — Automated Response, Not Just Alerts#
Budget Actions go one step further than notification: a budget can automatically apply an IAM policy that denies further spend-driving actions, stop specific EC2/RDS instances, or apply a Service Control Policy across an OU (Part 1) once a threshold is breached — genuinely automated cost circuit-breaking, not just an alert someone might miss. This is a real, deliberate tradeoff (an availability risk in exchange for a cost guarantee) worth using selectively — appropriate for a sandbox or dev account where runaway spend is a bigger risk than a forced stop, and a poor fit for anything production-facing where an automatic stop action would itself be an outage.
Cost Anomaly Detection#
Cost Anomaly Detection applies machine learning to an account's own historical spend pattern, learning what "normal" looks like per service/account/cost-category and alerting on genuine deviations — catching the specific failure mode a fixed-threshold budget alarm structurally can't: a sudden spike that's still comfortably under the monthly budget total but wildly abnormal for that particular day or service. As of 2026, detection runs on rolling 24-hour windows, comparing current cost against the equivalent period from previous days each time updated billing data arrives, rather than waiting for a full daily/monthly cycle to complete before flagging anything.
Cost Anomaly Investigation, Visually#
This is the concrete shape of the "attribute the change to specific API calls and IAM principals" step mentioned above — worth diagramming since it's the single biggest time-to-resolution improvement this part covers: a process that used to take a platform engineer 30-60 minutes of manual Cost Explorer/ CloudTrail cross-referencing now runs as one automated investigation.
AI-Powered Cost Investigation#
A 2026 enhancement worth knowing specifically: Cost Anomaly Detection now offers AI-powered
investigation via Amazon Q, which automatically determines whether a detected anomaly is usage-driven
or rate-driven, identifies the specific contributing services/accounts/regions, and — for usage-driven
anomalies — correlates against CloudTrail (Part 9) to attribute the spike to specific API calls and IAM
principals. This closes a real gap that used to require a manual, often multi-hour investigation: instead
of just "spend went up in EC2," the investigation surfaces "a specific IAM role launched 40 additional
m5.4xlarge instances at 2 AM via the CLI" — enough to go straight to root cause rather than starting one.
The Cost and Usage Report (CUR) — The Ground Truth#
Cost Explorer's UI is built for exploration; the Cost and Usage Report (CUR) is the actual ground-truth dataset underneath it — the most granular billing data AWS produces, with a line item per resource per hour (or day), every discount applied, every RI/Savings Plan amortization, delivered on a schedule to an S3 bucket. CUR 2.0, delivered via AWS Data Exports, is the current recommended version: a fixed, stable schema that doesn't silently change shape when AWS adds a new service, and a flat column structure replacing the older nested-JSON format — meaningfully easier to query reliably with standard SQL tooling than the legacy CUR format it replaces.
Querying CUR With Athena#
CUR data in S3, combined with Athena (introduced briefly in Part 6, covered in depth in Part 18), lets
a team run arbitrary SQL directly against raw billing data — "total spend by tag CostCenter for Q3,
broken down by service" as an actual query rather than a manual export-and-pivot exercise in a
spreadsheet. This is the mechanism behind any genuinely custom cost dashboard or chargeback report that
Cost Explorer's fixed UI doesn't directly support — the same "S3 + Athena for anything the built-in tool
doesn't do out of the box" pattern already familiar from Part 6's data-lake discussion, applied here to
billing data specifically.
Trusted Advisor's Cost Optimization Checks, Revisited#
Part 1 introduced Trusted Advisor as a general first-pass account health check. Its Cost Optimization category specifically flags idle load balancers, low-utilization EC2 instances, unassociated Elastic IPs (billed once no longer attached to a running instance), underutilized EBS volumes, and RI/Savings Plan purchase opportunities based on recent usage — genuinely the fastest, lowest-effort first pass before reaching for Cost Explorer's deeper analysis, though (as Part 1 noted) the full check catalog requires a Business or Enterprise support plan. For an account still on Basic/Developer support, Compute Optimizer (Part 15, free regardless of support tier) covers a meaningful chunk of the same right-sizing ground.
Reserved Instances — Mechanics and Types#
A Reserved Instance (RI) commits to a specific instance configuration (family, size, region, and optionally AZ and OS) for a 1- or 3-year term, in exchange for a discount of up to roughly 72% off On-Demand pricing for Standard RIs. Standard RIs offer the deepest discount but cannot be exchanged for a different instance family; Convertible RIs offer a smaller discount but can be exchanged for a different instance family/OS during the term, trading some discount depth for flexibility as workload needs change. Payment options — All Upfront, Partial Upfront, No Upfront — trade a larger upfront cash outlay for progressively smaller total savings.
Savings Plans — Mechanics and Types#
A Savings Plan commits to a dollar-per-hour spend over 1 or 3 years, rather than a specific instance configuration — the discount then applies automatically to whatever eligible usage occurs, up to that committed spend rate. Compute Savings Plans apply broadly across EC2 (any family/size/region/OS), Fargate, and Lambda, at a slightly lower maximum discount (~66%) than the more restrictive alternative. EC2 Instance Savings Plans apply only within a specific instance family and region but reach a higher maximum discount (~72%) closer to a Standard RI's, while still floating freely across instance size and OS within that family — a middle ground between Compute Savings Plans' full flexibility and an RI's full specificity.
Reserved Instances vs Savings Plans — The Full Comparison#
| Standard RI | Convertible RI | EC2 Instance SP | Compute SP | |
|---|---|---|---|---|
| Commitment unit | Specific instance config | Specific instance family (exchangeable) | Instance family + region | Dollar/hour spend |
| Max discount | ~72% (highest) | Slightly less than Standard | ~72% | ~66% |
| Applies across services | EC2 only | EC2 only | EC2 only | EC2, Fargate, Lambda |
| Can shift with architecture change | No | Yes (exchange) | Yes (within family) | Yes (fully) |
| Marketplace resale | Yes | Yes | No | No |
| Best fit | Truly static, predictable workloads | Predictable spend, evolving instance needs | Predictable EC2 spend, family known | Mixed/evolving compute across EC2/Fargate/Lambda |
Layering Commitments: The Real 2026 Practice#
Current AWS guidance, confirmed across multiple sources, is explicit: the effective 2026 approach isn't choosing one commitment type exclusively — it's layering them. A baseline of steady-state, well- understood compute gets covered by Standard RIs or EC2 Instance Savings Plans for the deepest discount; the more variable, evolving portion of a fleet gets covered by a Compute Savings Plan for flexibility across EC2/Fargate/Lambda; and anything genuinely unpredictable or interruption-tolerant stays uncommitted and either runs On-Demand or opportunistically on Spot (Part 3). This mirrors the same layered-defense instinct from Part 9's security material, applied to cost commitment instead of security controls — no single mechanism has to cover every case. A useful mental sizing exercise: plot 90 days of Cost Explorer usage data per compute category, identify the line that represents the lowest point the fleet ever dips to — that floor is the genuinely safe amount to commit to a 1- or 3-year term against, since committing above it risks paying for capacity that occasionally simply isn't there to use.
Choosing a Commitment Term Length: 1-Year vs 3-Year#
Both RIs and Savings Plans offer 1-year and 3-year terms, and the choice is a genuine forecasting exercise, not a default. A 3-year term unlocks a meaningfully deeper discount than the equivalent 1-year commitment, but locks in that spend rate against a workload's needs three years out — a real risk for a team whose architecture, instance family preferences, or business trajectory might shift meaningfully in that window (a planned migration to Graviton, for instance, or a product line being sunset). The practical heuristic: commit to 3-year terms only for capacity a team is confident will look essentially the same shape in three years (a core database tier, say), and default to 1-year for anything less certain — the deeper discount isn't worth the lock-in risk on capacity that's likely to change shape before the term is up.
Reserved Capacity Beyond EC2#
Reservation-style discounts aren't unique to EC2. RDS Reserved Instances (Part 6) apply the identical mechanics — a 1/3-year commitment to a specific DB instance class/engine for a steep discount — and ElastiCache Reserved Nodes work the same way for Redis/Memcached capacity. The decision framework is identical to EC2's: commit for genuinely steady-state, predictable database/cache capacity; stay On-Demand for anything still evolving or seasonal.
The Reserved Instance Marketplace#
A genuinely underused escape hatch worth knowing: Standard and Convertible RIs (though not Savings Plans, which have no resale mechanism at all) can be sold on the AWS Reserved Instance Marketplace if a workload's needs shift and the commitment no longer fits — recovering some of the remaining term's value rather than simply eating the cost of an unused commitment for its full remaining duration. This is a real practical safety valve for the risk RIs otherwise carry over Savings Plans' full flexibility, though it's worth treating as a last resort rather than a planning assumption — the marketplace has its own listing fees and no guarantee of a buyer at a favorable price, so getting the initial commitment sizing right still matters far more than counting on resale to fix a bad purchase.
Spot Instances, Revisited#
Part 3 covered Spot instances' interruption mechanics in depth. Worth restating here specifically as a cost lever alongside RIs/Savings Plans: Spot is the deepest possible discount (70-90% off On-Demand) but carries interruption risk RIs/Savings Plans don't — the three mechanisms aren't competing choices, they're complementary layers of the same cost strategy, each covering a different slice of a workload's actual predictability profile (steady-state → RI/SP, variable-but-guaranteed → On-Demand, interruption- tolerant → Spot).
Compute Optimizer, Revisited: From Recommendation to Action#
Part 15 introduced Compute Optimizer's right-sizing recommendations. The FinOps-specific point worth adding here: a recommendation only produces real savings once someone actually acts on it and, critically, once any existing RI/Savings Plan commitment tied to the old instance size is accounted for — downsizing an instance already covered by a Standard RI locked to that exact instance type doesn't automatically save money; it can leave the RI underutilized and paying for capacity nobody's using anymore. This is exactly why right-sizing and commitment-purchasing decisions need to happen together, in the same review cycle, not as two disconnected processes run by different people.
Architecture-Level Cost Optimization: Graviton#
Beyond right-sizing an instance's family/size, the underlying processor architecture is itself a real
cost lever. AWS's own Graviton (ARM-based) processors typically offer a meaningfully better price/
performance ratio than equivalent x86 instances — commonly cited around 20-40% better price/performance
for compatible workloads — across EC2, RDS, ElastiCache, and Lambda (arm64 architecture). The catch,
worth stating plainly: this isn't a free, drop-in switch for every workload — it requires the application
(and every dependency, including any compiled native extensions) to actually support ARM, which for a
container-based or Lambda workload is often a straightforward rebuild, but for a fleet running
architecture-specific compiled binaries or legacy dependencies can be genuinely nontrivial migration work.
Compute Optimizer (Part 15) surfaces Graviton-eligible migration opportunities directly alongside its
regular right-sizing recommendations.
License and Software Costs: BYOL vs License-Included#
For commercial software (Windows Server, SQL Server, various commercial database/monitoring products), AWS offers two licensing models on the same underlying compute: License-Included, where the license cost is bundled into the hourly instance rate, and Bring Your Own License (BYOL), where an organization applies an existing license it already owns (subject to the vendor's own licensing terms, sometimes requiring AWS's License Manager to track compliance) against AWS compute at the lower license-excluded rate. An organization with existing, unused enterprise license capacity (common after a migration, Part 17) can realize meaningful savings via BYOL; one without existing licenses is almost always better off with License-Included's simpler, pay-as-you-go model rather than purchasing new licenses outright.
Support Plan Costs, Revisited#
Part 1 introduced AWS Support plans as a scope-of-help decision. Worth a brief cost-specific note here: Business and Enterprise support plans are priced as a percentage of monthly AWS spend (with tiered rates that decrease at higher spend bands), not a flat fee — meaning the support plan's own cost scales with the exact usage this whole part is trying to optimize. A team right-sizing aggressively and reducing overall spend also, as a direct side effect, reduces its support plan bill — one more reason cost optimization work compounds rather than being a one-time, isolated saving.
Per-Service Cost Levers: Storage#
Building directly on Part 5: S3 lifecycle policies transitioning cold data to Glacier/Deep Archive, EBS volumes right-sized and unattached volumes cleaned up (Compute Optimizer flags both), and gp3 chosen over gp2 by default (gp3 decouples IOPS/throughput from volume size, avoiding the common gp2 anti-pattern of over-provisioning capacity purely to buy more baseline IOPS) are the highest-leverage, lowest-risk storage cost actions — genuinely close to free money, since they change no application behavior at all.
S3 Intelligent-Tiering — Automating the Lifecycle Decision#
Part 5 covered S3 lifecycle policies as a manual, rule-based way to transition objects between storage classes on a schedule. S3 Intelligent-Tiering automates that decision entirely: it monitors each object's actual access pattern and moves it automatically between frequent-access and infrequent-access tiers (and, optionally, further into archive tiers for objects unaccessed for 90+/180+ days), with no retrieval fee for the infrequent tier and only a small monthly per-object monitoring charge. This is the right default whenever access patterns are genuinely unpredictable — a manual lifecycle policy requires knowing the access pattern in advance to set sensible transition timings, which Intelligent-Tiering simply doesn't need.
Idle and Orphaned Resource Cleanup#
The single highest-leverage, lowest-risk cost action in most accounts is also the least glamorous: finding and removing resources that are simply no longer used, but still billing. The recurring offenders, all directly flagged by Trusted Advisor or Compute Optimizer: unattached EBS volumes (created for an instance that was later terminated, the volume itself often forgotten), unassociated Elastic IPs (billed once no longer attached to a running instance — a genuinely easy-to-miss line item), idle load balancers (an ALB/NLB with zero or near-zero request volume, often left behind after a service migration), old, unreferenced EBS snapshots and AMIs (accumulating storage cost indefinitely with no retention policy), and stopped-but-not-terminated EC2 instances still holding EBS volumes. None of these require deep architectural change to fix — they require a recurring cleanup habit, ideally automated via a scheduled Lambda function or Systems Manager Automation runbook (Part 15) rather than a manual quarterly sweep someone has to remember to run.
Tip
A genuinely simple automation worth standing up early: a weekly Lambda function (triggered by EventBridge, Part 13) that lists unattached EBS volumes and unassociated Elastic IPs older than a configurable grace period (say, 7 days, to avoid flagging a volume mid-migration) and posts them to a Slack channel or creates an OpsItem (Part 15) rather than deleting anything automatically — visibility first, automatic deletion only once the team trusts the signal enough to act on it without a human double-check in the loop.
Cost Optimization for CI/CD and Build Infrastructure#
Build infrastructure is an easy category to overlook in a cost review because it doesn't serve customer traffic directly. CodeBuild (Part 11) bills per build-minute at a rate scaled to the chosen compute size — over-provisioning build compute "just to be safe" wastes money on every single build, multiplied across however many builds run per day. Build caching (dependencies, Docker layers) cached in S3 between runs cuts both build duration and the compute-minutes billed for it — a build that reuses a warm dependency cache can be meaningfully faster and cheaper than one that reinstalls everything from scratch every time. CodePipeline's own per-pipeline monthly charge is typically a rounding error compared to the compute-minute cost of the CodeBuild stages it orchestrates, so optimization effort here is almost always better spent on build compute sizing and caching than on pipeline structure itself.
Per-Service Cost Levers: Data Transfer#
Data transfer is a persistently underestimated cost category: transfer between AZs within the same region is billed (a real, non-obvious surprise the first time a team sees it on a bill), transfer out to the internet is billed per GB and is usually the single largest data-transfer line item, while transfer into AWS is free. VPC endpoints (Part 4) for S3/DynamoDB and other AWS services avoid NAT Gateway data processing charges entirely for traffic that would otherwise route through one, and CloudFront (Part 8) both improves latency and is frequently cheaper per GB than serving the same content directly from an origin for internet-bound traffic at scale.
A Brief Note on API Gateway and AppSync Costs#
Part 13's API Gateway and AppSync depth is also directly relevant here: HTTP APIs' roughly 70% lower per- request cost than REST APIs (already covered in Part 13 as an architectural default) is as much a Part 16 cost lever as it is a Part 13 architecture choice — reviewing an existing REST API for whether it actually uses any REST-exclusive feature, and migrating it to an HTTP API if not, is a genuine, low-risk cost- reduction action worth including in any API-heavy account's cost review.
Per-Service Cost Levers: Serverless and Containers#
Lambda's pay-per-invocation model means idle cost is already zero (Part 7) — the remaining lever is right-sizing memory allocation, since Lambda's CPU scales with memory and an under-provisioned function can paradoxically cost more by running longer at a lower memory tier than a correctly-sized one running faster at a higher tier; AWS's open-source Lambda Power Tuning tool empirically finds the cost-optimal memory setting per function. For containers, Fargate Spot (the Fargate-specific equivalent of EC2 Spot) and right-sized task CPU/memory requests (an over-provisioned ECS task definition wastes capacity the same way an over-provisioned EC2 instance does) are the primary levers, alongside Compute Optimizer's now-extended coverage of ECS services running on Fargate (Part 15).
Per-Service Cost Levers: Databases#
Aurora Serverless v2 (Part 6) scales capacity down to near-zero for genuinely intermittent workloads, avoiding a fixed-size instance's cost during idle periods; DynamoDB On-Demand capacity mode trades a per-request premium for zero capacity-planning overhead on unpredictable workloads, while Provisioned capacity (with auto scaling) is cheaper at steady, predictable throughput — the exact same predictability-driven decision framework as RIs vs On-Demand, just expressed through DynamoDB's own capacity model instead.
Networking Cost Levers Beyond Data Transfer#
Beyond the transfer-direction pricing already covered, a handful of networking choices from Parts 4 and 8 carry real, easy-to-underweight cost implications: a NAT Gateway bills both an hourly charge and a per-GB data-processing charge, meaning a chatty, high-volume workload routed through a single NAT Gateway can accumulate meaningful cost purely from that processing fee — a VPC endpoint (free of NAT processing charges entirely) is the correct fix whenever the destination is an AWS service, not a NAT Gateway sizing exercise. Transit Gateway similarly bills per-attachment-hour and per-GB processed, worth factoring into a multi-VPC connectivity design rather than treating as a free architectural convenience. And Global Accelerator, while it improves latency, is a genuinely separate line item on top of the resources it accelerates — worth confirming the latency improvement is actually needed before adding it by default to every public-facing architecture.
Where AWS-Native Tooling Stops: Third-Party FinOps Platforms#
Cost Explorer, Budgets, and CUR/Athena cover most of what a single organization needs, but a genuinely large or multi-cloud organization commonly layers a third-party FinOps platform (CloudZero, Vantage, Cloudability, and similar) on top — typically for cross-cloud normalization (a single view spanning AWS, Azure, GCP), more opinionated out-of-the-box unit-economics reporting (cost per customer, cost per API call), or a more polished chargeback workflow than a hand-built Athena-query-plus-spreadsheet pipeline provides. Worth stating honestly: for a single-cloud AWS organization, the native tooling this part covers is usually sufficient on its own, and reaching for a third-party platform is worth doing deliberately once a specific native-tooling gap is actually felt, not as a default first step.
Cost Guardrails as Code#
The most durable version of cost governance isn't a person manually checking a dashboard — it's a guardrail enforced automatically, the same "prevent, don't just detect" philosophy already familiar from Part 9's security material. Concretely: an SCP (Part 1) restricting which instance types or regions an account can launch resources into at all, a CloudFormation/Terraform policy-as-code check (Part 11) that fails a pull request if a new resource is missing a required cost allocation tag, and a Service Catalog (a governance tool not otherwise covered in this series) constraining which pre-approved, cost-reviewed resource configurations a team is even allowed to provision through self-service. Each of these turns a cost policy from "documented and hoped for" into "structurally impossible to violate by accident" — the same distinction Part 9 draws between a security policy that's merely written down and one that's technically enforced.
Observability and Logging Cost, Revisited#
Part 10's observability stack is itself a real, growing cost category worth revisiting through a FinOps lens: CloudWatch Logs ingestion and storage bill by volume, and a verbose debug-level log left enabled in production indefinitely is a surprisingly common, entirely avoidable cost — log level and retention period (Part 10) are cost decisions as much as operational ones. X-Ray's per-trace pricing means 100% sampling across a very high-traffic service can itself become a meaningful line item, which is precisely why Part 10 already recommends sampling rules rather than tracing every single request. The broader point: an observability stack sized for "capture everything, forever, just in case" is itself a cost-optimization target, not exempt from this part's discipline just because it's monitoring infrastructure rather than customer-facing infrastructure.
The AWS Free Tier and Its Limits#
Part 1 introduced the Free Tier briefly. Worth a specific currency note here: accounts created on or
after July 15, 2025 no longer receive the legacy per-service free tier (750 hours of a t2.micro, 5 GB
of S3, and so on) — instead, new accounts receive a $200 credit consumable across any service, valid
for a limited period. This is a genuine, recent shift in how a new account's early cost planning should
work, and any guidance still describing the old always-free per-service tier as universally available is
describing a since-changed policy for newer accounts specifically — existing pre-July-2025 accounts keep
their legacy free tier terms.
Multi-Account Cost Visibility: Consolidated Billing and RI/SP Sharing#
Part 1's AWS Organizations enables consolidated billing: every member account's usage rolls up to one management-account bill, and, critically, RI and Savings Plan discounts are shared automatically across every account in the Organization by default — an RI purchased in one account can apply to matching usage in a completely different account, meaning commitment purchasing decisions should generally happen at the Organization level, not duplicated per-account, to avoid one account under-buying while a sibling account over-buys the same coverage. This sharing behavior can be disabled per account if a specific billing-isolation requirement demands it, but it's on by default and is the right default for most Organizations.
Unit Economics: The Metric That Actually Matters to the Business#
Total spend alone is a poor signal on its own — a growing company should expect growing AWS spend; the question that actually matters to the business is whether spend is growing faster or slower than the value it produces. Unit economics reframes cost around a business-meaningful denominator: cost per customer, cost per API request, cost per transaction processed. A team whose total spend doubled while its customer base tripled is actually improving its unit cost, even though the raw total looks alarming in isolation — exactly the kind of nuance a raw Cost Explorer total obscures and a CUR-plus-Athena query (joining billing data against a business metric like active users) can surface directly. Mature FinOps practices report unit economics alongside raw spend specifically to avoid the "spend went up, therefore something is wrong" reflex that a total-dollars-only view invites.
Showback and Chargeback#
Two distinct maturity levels for turning cost-allocation-tag data into organizational accountability: showback simply reports each team's/product's actual cost back to them (visibility, no financial consequence) — the natural first step once cost allocation tags are activated; chargeback actually bills that cost against the team's own budget as a real financial transaction, a more mature (and more organizationally sensitive) practice requiring accurate, complete tagging coverage before it's fair to implement, since any untagged/mistagged spend either falls through the cracks or gets misattributed. Most organizations deliberately start with showback and only move to chargeback once tagging discipline is genuinely reliable.
Scheduling: Turning Off What Doesn't Need to Run Continuously#
A cost lever simple enough to overlook entirely: non-production environments (dev, staging, a QA fleet) rarely need to run 24/7 — a scheduled Systems Manager Automation runbook (Part 15) or a Lambda function triggered by EventBridge on a cron schedule (Part 13) stopping EC2 instances and scaling Auto Scaling Groups to zero outside business hours can realistically cut a non-production environment's compute cost by 60-70% (roughly the fraction of a week outside a standard working schedule), with zero architectural change and zero risk to anything customer-facing. This is deliberately the simplest lever in this entire part, and precisely because it's so simple, it's also one of the most commonly still-missed ones — teams reach for RIs and Savings Plans on environments that arguably shouldn't be running most of the time at all.
The FinOps Framework's Three Phases#
The (vendor-neutral, widely referenced) FinOps Foundation's own framework describes three iterative phases, worth knowing by name for interview purposes: Inform (visibility — cost allocation, showback, the Cost Explorer/CUR tooling this part covers), Optimize (the actual cost-reduction levers — RIs, Savings Plans, right-sizing, the mechanisms covered above), and Operate (making the first two phases a continuous, governed practice rather than a one-time project — regular review cadences, Budget alerts, Cost Anomaly Detection running continuously). The phases repeat as a cycle, not a one-time linear sequence — an organization's FinOps maturity is really a measure of how tight and automatic that cycle has become.
A Cost Retrospective on This Series' Own Architectural Choices#
Worth pausing to connect this part back to decisions already made across earlier parts, since cost was often a background factor in choices framed primarily around architecture: Part 7's choice between HTTP APIs and REST APIs, revisited in Part 13, was explicitly a cost-driven default; Part 7's Fargate vs EC2 choice trades Fargate's per-task pricing (no idle capacity waste, but a per-vCPU/GB premium over equivalent EC2) against EC2's lower unit cost at high, steady utilization — exactly the same predictability-driven tradeoff RIs vs On-Demand makes at the compute-commitment layer; Part 5's S3 storage class selection is itself a cost-optimization decision dressed as a storage-architecture one. None of this means those earlier chapters were incomplete — it means cost optimization was never actually a separate concern from the architecture decisions already covered, only formalized with its own dedicated tooling here.
A Full Worked Example: A FinOps Review Cycle#
A platform team running a monthly cost review:
- Inform: Cost allocation tags (
Team,Environment,CostCenter) are activated and enforced via a Tag Policy (Part 1); Cost Explorer's monthly report, grouped by those tags, goes to each team's own lead as a showback report. - A Cost Anomaly Detection alert fires mid-month for an unexpected spike in a
stagingaccount; AI- powered investigation attributes it to a forgotten load-test script left running overnight, cross- referenced via CloudTrail to the specific IAM role that launched it. - Optimize: Compute Optimizer's monthly recommendations (Part 15) are reviewed alongside current RI/Savings Plan coverage — a downsizing recommendation for an instance type already covered by a Standard RI is deferred until that RI's term expires, to avoid stranding an existing commitment.
- A new Compute Savings Plan is purchased sized to the team's now-stable baseline compute spend, layered on top of existing Standard RIs covering the truly static core fleet.
- Operate: A Budget with a forecasted-spend alert is set per major account, feeding the same CloudWatch/SNS alerting infrastructure Part 15 already wired up for operational alerts — cost alerts reach the same on-call rotation as any other operational signal, not a separate, easily-ignored channel.
- The full cycle repeats the following month, with the prior month's CUR data (queried via Athena) feeding a trend analysis of whether the changes actually reduced spend as predicted.
- A quarterly idle-resource sweep (Trusted Advisor plus a scheduled Systems Manager Automation runbook) catches an EBS volume left behind from a terminated instance three months earlier, closing a small but real recurring leak.
- The finance team's unit-economics report (cost per active customer, sourced from a CUR-plus-Athena query joined against the product team's own usage metrics) shows unit cost actually declining despite total spend rising 12% quarter over quarter — the growth is healthy, and the raw dollar increase alone would have told a misleadingly alarming story on its own.
- A CloudFormation guardrail, added to the shared IaC module every team's stack inherits from (Part 11),
now fails any deployment missing a required
CostCentertag — the next quarter's tagging coverage gap this cycle would otherwise have needed to chase down manually simply can't happen anymore.
Bringing It Together: A Simple Cost-Optimization Priority Order#
For a team new to this discipline and unsure where to start, a rough, real-world priority order by effort-to-savings ratio: scheduling non-production environments off-hours and idle-resource cleanup first (near-zero risk, immediate savings, no architectural change); activating cost allocation tags and setting Budget alerts next (pure visibility work, prerequisite for everything downstream); Compute Optimizer right-sizing third (low risk once performance-risk scores are reviewed); and RI/Savings Plan commitment purchasing last, only once usage patterns are stable enough to forecast confidently — committing to a discount before understanding the actual steady-state usage it should cover is how a team ends up with the stranded-commitment problems this part has repeatedly warned about.
Cost Optimization Best Practices — The Consolidated Checklist#
- Activate cost allocation tags in the Billing console — a tag existing on a resource doesn't make it a cost dimension until explicitly activated.
- Set Budget alerts on forecasted spend, not just actual spend, to catch a runaway trend mid-cycle.
- Layer commitment types (Standard RI/EC2 Instance SP for static baseline, Compute SP for the flexible remainder, Spot for interruption-tolerant burst) rather than relying on one exclusively.
- Review right-sizing recommendations and commitment coverage together, in the same cycle — acting on one without the other can strand an existing commitment.
- Purchase RIs/Savings Plans at the Organization level to take advantage of automatic cross-account sharing, rather than duplicating purchases per account.
- Use VPC endpoints for S3/DynamoDB traffic to avoid unnecessary NAT Gateway data processing charges.
- Start with showback before chargeback — chargeback only works fairly once tagging coverage is reliable.
- Query CUR via Athena for anything Cost Explorer's fixed UI doesn't directly support.
- Evaluate Graviton for compatible workloads before assuming the current x86 instance family is the cheapest available option.
- Run a recurring (not one-time) idle-resource sweep for unattached EBS volumes, unassociated Elastic IPs, idle load balancers, and stale snapshots/AMIs.
- Report unit economics (cost per customer/transaction) alongside raw spend so a healthy, growth-driven increase isn't mistaken for a problem.
- Enforce cost-relevant guardrails (required tags, approved instance types) as code wherever possible, rather than relying on a person remembering to check.
- Choose 1-year vs 3-year commitment terms based on genuine confidence in a workload's shape staying stable, not purely by chasing the deeper 3-year discount.
- Review log retention periods and trace sampling rates as real cost decisions, not purely operational ones left at whatever default was convenient at setup time.
- Confirm networking cost levers (NAT Gateway data processing, Transit Gateway per-GB charges) are factored into a multi-VPC design, not just its latency/throughput characteristics.
A Closing Distinction: Cost Optimization vs Cost Cutting#
Worth ending on explicitly, since it's easy to conflate: cost optimization is about eliminating waste and choosing the right-priced mechanism for a given requirement — a downsized instance, an activated lifecycle policy, a layered commitment strategy. Cost cutting is reducing capability or reliability to save money — fewer AZs, smaller backups retained for less time, a downgraded support plan on a production-critical account. The tools in this part are built for the former; reaching for the latter as a first response to a budget problem tends to trade a visible dollar saving for an invisible reliability or security risk that only surfaces during the next incident, at a moment when reconstructing anything already reduced is far more expensive than the original savings ever were.
Part 16 CLI Cheat Sheet#
| Task | Command |
|---|---|
| Get cost and usage for a period | aws ce get-cost-and-usage --time-period Start=2026-08-01,End=2026-08-31 --granularity MONTHLY --metrics BlendedCost |
| Get a cost forecast | aws ce get-cost-forecast --time-period Start=2026-09-01,End=2026-09-30 --metric BLENDED_COST --granularity MONTHLY |
| Create a budget | aws budgets create-budget --account-id <id> --budget <budget-json> |
| Get Reserved Instance recommendations | aws ce get-reservation-purchase-recommendation --service "Amazon Elastic Compute Cloud - Compute" |
| Get Savings Plans recommendations | aws ce get-savings-plans-purchase-recommendation --savings-plans-type COMPUTE_SP --term-in-years ONE_YEAR --payment-option NO_UPFRONT --lookback-period-in-days SIXTY_DAYS |
| List active anomaly monitors | aws ce get-anomaly-monitors |
| Get detected cost anomalies | aws ce get-anomalies --date-interval StartDate=2026-08-01,EndDate=2026-08-31 |
| Enable a cost allocation tag | aws ce update-cost-allocation-tags-status --cost-allocation-tags-status TagKey=Environment,Status=Active |
| Get Compute Optimizer EC2 recommendations | aws compute-optimizer get-ec2-instance-recommendations |
| Describe current Reserved Instances | aws ec2 describe-reserved-instances |
Common Mistakes and Interview Traps#
| Mistake | Why it's wrong | Correct approach |
|---|---|---|
| Assuming a resource tag is automatically a cost dimension | Tags must be explicitly activated as cost allocation tags in Billing before Cost Explorer/CUR can group by them | Activate every relevant tag key in the Billing console |
| Downsizing an instance already covered by a Standard RI without checking coverage first | Can strand the existing RI, paying for capacity nobody uses anymore | Review right-sizing and commitment coverage together |
| Buying RIs/Savings Plans separately per account in an Organization | Duplicates coverage and misses automatic cross-account sharing | Purchase at the Organization level (management account or a designated linked account) |
| Setting Budget alerts only on actual (not forecasted) spend | Catches an overrun only after the month has already closed | Use forecasted-spend alert thresholds to catch a trend mid-cycle |
| Assuming every new AWS account gets the classic always-free per-service tier | Accounts created after July 15, 2025 get a one-time credit instead, not the legacy per-service free tier | Confirm which free-tier model applies before relying on it in a cost estimate |
| Enabling Budget Actions' automatic stop/deny on a production account without careful scoping | Turns a cost guardrail into a self-inflicted availability incident | Reserve automatic Budget Actions for sandbox/dev accounts; alert-only for production |
| Judging cost health purely by total spend | Growth-driven spend increases look identical to genuine waste on a raw-dollars chart | Report unit economics (cost per customer/transaction) alongside the total |
| Treating idle-resource cleanup as a one-time project | Orphaned resources accumulate continuously as teams launch and forget resources | Schedule a recurring automated sweep, not a single quarterly manual pass |
| Committing to a 3-year term purely for the deeper discount, without confidence in the workload's stability | A workload that changes shape mid-term leaves a stranded, wasted commitment | Reserve 3-year terms for genuinely stable capacity; default to 1-year for anything less certain |
| Leaving debug-level logging or 100% X-Ray sampling on indefinitely in production | Log/trace ingestion cost scales directly with volume, with no corresponding operational benefit past a point | Treat log retention and sampling rate as deliberate cost decisions, revisited periodically |
Worked Practice Problems#
Problem 1: A team's EC2 fleet runs a mix of a stable, predictable core (about 60% of capacity) and a highly variable remainder that shifts between EC2, Fargate, and Lambda depending on the week. What commitment strategy fits, and why not a single Standard RI covering everything?
Answer: Layer commitments: Standard RIs or EC2 Instance Savings Plans for the stable 60% core (deepest discount, appropriate for genuinely predictable capacity), and a Compute Savings Plan for the variable remainder, since it floats freely across EC2/Fargate/Lambda as the workload shifts service. A single Standard RI covering everything would either under-cover the variable portion (RIs don't apply across services at all) or force rigid instance-type commitments onto capacity that's specifically not rigid.
Problem 2: A cost anomaly alert fires for a 3x spend spike in one account, still well under the account's overall monthly budget. Why did Cost Anomaly Detection catch this when the Budget alert didn't, and what's the fastest path to root cause?
Answer: Cost Anomaly Detection compares against the account's own learned historical pattern on a rolling basis, catching an abnormal spike regardless of whether it breaches an absolute budget threshold; a Budget alert only fires once total spend crosses its configured limit, which a spike well under the monthly total never does. The fastest path to root cause is the AI-powered investigation feature, which correlates the anomaly against CloudTrail to attribute it to specific API calls and IAM principals automatically, rather than manually cross-referencing Cost Explorer against CloudTrail by hand.
Problem 3: A team wants to build a custom chargeback report broken down by a tag Cost Explorer's UI doesn't offer as a built-in grouping dimension. What's the actual path to building this?
Answer: Enable CUR 2.0 delivery via AWS Data Exports to an S3 bucket, then query it with Athena using standard SQL, grouping by whatever tag column is needed — Cost Explorer's UI covers common groupings, but CUR plus Athena is the ground-truth dataset for anything genuinely custom, the same "S3 + Athena for anything the built-in tool doesn't directly support" pattern used elsewhere in this series for data lakes.
Problem 4: An Organization's member accounts each independently purchased Reserved Instances covering roughly the same EC2 instance family, and a review reveals meaningful RI capacity going unused in some accounts while others are still paying On-Demand rates for matching usage. What's the root cause, and what should the purchasing process change to?
Answer: The root cause is purchasing RIs per-account instead of taking advantage of AWS Organizations' default automatic cross-account RI/Savings Plan sharing — each account bought coverage in isolation, producing exactly the mismatch (over-coverage in one account, under-coverage in a sibling) that sharing is designed to prevent. The fix is centralizing commitment purchasing decisions at the Organization level (the management account or a designated linked account), sized against Organization-wide usage data rather than any single account's own view of its needs.
A Note on Region Selection and Cost#
Part 1 covered region selection primarily through latency and compliance. Pricing genuinely varies by
region for identical resources — us-east-1 is typically among the cheapest regions for most services,
while newer or more geographically remote regions often carry a real premium. This is rarely worth letting
override latency or compliance requirements on its own, but it's a legitimate tiebreaker when two
candidate regions are otherwise equivalent, and worth factoring explicitly into a multi-region DR
architecture's cost estimate (Part 12) — a warm-standby region chosen purely for its proximity to a primary
region, without checking its pricing, can end up materially more expensive than a slightly more distant
alternative offering the same latency characteristics for the DR use case specifically.
Summary and What's Next#
Cost is a first-class architectural property, not an afterthought discovered on the monthly bill. Cost Explorer and CUR provide the visibility layer; cost allocation tags are the prerequisite that makes any of that visibility attributable; Budgets and Cost Anomaly Detection provide forward-looking and anomaly- driven alerting rather than pure hindsight; and Reserved Instances, Savings Plans, and Spot — layered together rather than chosen exclusively — are the actual discount mechanisms, working alongside the per-service right-sizing levers Compute Optimizer (Part 15) and this part's storage/data-transfer/ serverless/database-specific guidance surface. The FinOps Inform-Optimize-Operate cycle ties all of it into a continuous practice rather than a one-time cost-cutting project.
Part 17 shifts from optimizing what's already running in AWS to getting workloads there in the first place: the 6 R's in real depth, Application Discovery Service, Application Migration Service (MGN), the Snow Family, DataSync, and Migration Hub — SAP-C02's heaviest-weighted domain (20%) and the thinnest- covered part of this series until now. Every cost-optimization instinct built in this part applies from day one of a migration too — sizing the destination correctly the first time avoids re-learning these same lessons the hard way, after the workload has already landed.