Nuria Peña, Contoso Airlines' finance lead, has spent months asking the same question in the steering committee and getting the same vague answer. When the migration was approved, somebody put "around €8,500 a month" on a slide. The average bill for the first real quarter was €17,500 a month: exactly double. Nobody lied. The estimate was simply built by adding up virtual machines and databases, which is what everybody estimates, and it left out everything else: the firewall, the bastion, the global entry point, log ingestion, data transfer out and a Kubernetes cluster whose nodes somebody believed were "part of AKS".

This lesson teaches you to estimate before you deploy. You will see how Azure really bills — which unit of measure each service family uses — the three types of cost almost nobody estimates, full use of the pricing calculator, Contoso's entire platform estimate rebuilt line by line, the total cost of ownership calculator for comparing against the Barcelona datacenter, why the same machine costs different amounts in two regions, how to automate estimates with the Retail Prices API and, above all, how you document the margin of error, because an estimate with no written assumptions is not an estimate: it is a number.

A warning about the prices in this lesson and across the whole module: every euro figure that appears here is illustrative and fictitious, chosen so that the orders of magnitude and the proportions teach something. Real Azure prices change frequently, and they vary by region, by currency, by offer type and by negotiated discounts. No figure in this module should be used to decide anything: always check the official Azure pricing calculator and your own commercial agreement.

Contents

  1. Why you estimate before you deploy
  2. How Azure really bills: units of measure
  3. The three costs almost nobody estimates
  4. The Azure pricing calculator, step by step
  5. The complete Contoso Airlines estimate
  6. The total cost of ownership calculator
  7. Pricing by region: the same VM at two prices
  8. The Retail Prices API
  9. The margin of error and the written assumptions
  10. Estimation as part of the design
  11. Common Mistakes and Tips
  12. Exercises
  13. Conclusion

  1. Why you estimate before you deploy

In your own datacenter, spending money takes a purchase order, a signature and several weeks. In Azure it takes three clicks. That is the whole difference, and it is enormous: control of spending has moved from the purchasing department to the engineer's keyboard, and nobody told the engineer.

The consequence is a pattern that repeats in every organization that migrates:

Moment What happens Cost of correcting it
Design The architecture and its service tiers are chosen Almost nil: it is changing a decision in a document
Deployment The resources are created with Bicep Low: change a parameter and redeploy
First month The bill arrives and surprises everybody Medium: resources have to change in production
Sixth month Spending has normalized and there is data on top of it High: migrations, windows, risk

Estimation is the only lever that acts on the first row. Put another way: the hardest bill to correct is the one you have already caused. A redundancy level chosen carelessly on day one turns into a data migration the following year.

And there is a second reason, less obvious and more important: estimating forces you to understand the architecture. When Marta Ríos redid Contoso's estimate with the calculator, she discovered three things that had been sitting there for months without anybody seeing them — a geo-replica of the database that cost almost as much as the primary, an AKS node pool sized for a load test that finished in March, and a VPN gateway with no active connections. Estimating is auditing the design with a calculator in your hand.

  1. How Azure really bills: units of measure

The underlying error in Contoso's failed estimate was a mental one: Azure was pictured as a catalog of machines with a monthly price. Azure bills units of consumption, and each service family uses its own. Until you have internalized the following table, you cannot estimate anything.

Family Main unit of measure Other units that also bill Example at Contoso
Compute (VM, VMSS) Instance hour while running (deallocated does not bill) Managed disks (GB-month, IOPS), public IP, OS license vmss-api-disponibilidad-pro
App Service Plan hour, not application hour Certificates, domains, extra slots depending on tier plan-contoso-reservas-pro
Containers (AKS) Hour of each node (VM) + disks Standard control plane, load balancer, egress aks-contoso-operaciones
Container Apps / Functions consumption vCPU-second and GiB-second + executions Minimum replicas always running ca-motor-disponibilidad
Storage GB-month per access tier Transactions, data retrieval, tier change sttarjetascontosopro
SQL Database (vCore) vCore-hour provisioned or vCore-second serverless Storage GB-month, LTR backups, secondary replica db-reservas
Cosmos DB Request units per second (RU/s) hour Storage GB-month, backups, each additional region cosmos-contoso-tarifas-pro
Synapse serverless TB of data read per query Lake storage, pipelines per activity syn-contoso-analitica-pro
Log Analytics GB ingested GB-month retained, table plan, queries over the archive log-contoso-pro
Networking GB of data transfer out (egress) Firewall hour + GB processed, bastion hour, gateway hour fw-contoso-hub-pro
Messaging Operations or messaging/throughput units per hour Extra entities, extended retention sb-contoso-pro
Logic Apps Action execution Enterprise connectors with their own rate logic-contoso-retrasos-pro
AI / Azure OpenAI Token in and out Provisioned throughput units, if contracted oai-contoso-pro
Backup Protected instance + GB stored Geo-redundancy, cross-region restore rsv-contoso-pro

Three readings of this table that change how you estimate:

  • The unit is not always the resource you can see. You do not pay for app-contoso-reservas-pro; you pay for plan-contoso-reservas-pro, and it makes no difference whether you host one application or five.
  • Almost everything has a second unit. Storage has GB and transactions. The firewall has hours and gigabytes processed. The database has compute and storage and backups. Estimating only the main unit systematically produces low estimates.
  • Some units are not proportional to the usage you perceive. A badly written query in Synapse serverless reads 2 TB and costs more than a whole day of virtual machines, even though the user only clicked "refresh".

  1. The three costs almost nobody estimates

Of Contoso's failed estimate, nearly half the deviation came from three items that did not even appear in the original spreadsheet.

Data transfer out (egress). Traffic into Azure is free; traffic out of Azure to the internet is not. Nor is traffic between regions free, and in many cases neither is traffic between availability zones. As module 2 anticipated, this is the usual surprise on the bill, because it does not show up as a resource: there is no object called "data transfer out" in the portal for you to look at. At Contoso it is produced by all of this at once: every boarding pass downloaded by a passenger, every response from the Availability API to the external aggregators, the replication of db-reservas to North Europe, the geo-replication of acrcontosopro and the nightly exports to the local billing system. You estimate it with a simple rule: how many objects leave per month × average size, and you write the assumption down.

Transactions and operations. The GB of a storage account get estimated properly; the transactions almost never do. And on workloads with many small objects — which is exactly the boarding pass case — transactions can exceed storage. Worse still: cold tiers make the GB-month cheaper and the transaction more expensive, so a badly tuned lifecycle rule that moves data still being read frequently to Cool can actually raise the bill. The same applies to Key Vault operations, Cosmos DB requests and Defender for Cloud operations over Storage.

The "free" features that drag a paid resource behind them. This is the most treacherous one, because the service advertises zero cost and delivers it:

"Free" service What you do pay for
Azure Policy Nothing for the policy, but a DeployIfNotExists effect creates paid resources
Diagnostic settings The setting is free; the ingestion into log-contoso-pro is not
Microsoft Entra ID (base tier) Conditional Access and Identity Protection require paid tiers
Defender for Cloud (basic CSPM) The per-workload plans do cost (module 4)
Azure Advisor Genuinely free, with no small print (08-04)
Azure Monitor alerts Resource health alerts are free; metric and log alerts are billed per rule and per series
Resource groups, tags, ARM Really free
Automation account The account costs nothing; the execution minutes above the free allowance do

The rule to burn into your memory: whenever you switch something free on, always ask what consumption it generates downstream. The diagnostic settings from module 7 are free and produced the third most expensive item on the platform.

  1. The Azure pricing calculator, step by step

The Azure pricing calculator (azure.microsoft.com/pricing/calculator) is a public tool, no account required, that lets you build a complete estimate. It is deceptively simple, and using it well takes method.

flowchart LR
  A["Search for and add<br/>the services"] --> B["Configure each one:<br/>region, tier, quantity,<br/>hours and units"]
  B --> C["Group by<br/>component or environment"]
  C --> D["Apply currency,<br/>offer and discounts"]
  D --> E["Save, share<br/>and export to Excel"]
  E --> F["Review with the team<br/>and with Nuria"]
  F -->|"assumptions missing"| B

The procedure Marta follows:

  1. Search for the service and add it. The calculator has a catalog by category and a search box. Add every service in the architecture, including the ones that "cost nothing" — so there is a record that they were considered.
  2. Configure region, tier and quantity. This is 90% of the work. For a VM: region, operating system, instance type, number of instances, hours per month (730 for 24x7, around 176 for business hours only), disk type and number of disks, and the savings option (pay-as-you-go, one-year or three-year reservation, savings plan, spot). That selector is what connects this lesson to 08-03.
  3. Group by component. The calculator lets you create groups and rename them. Contoso uses one group per architecture block: Web front end, Availability API, Data, Networking and security, Observability, Integration and AI, Development. Without groups, a forty-line estimate is unreadable and nobody reviews it.
  4. Set currency, billing region and licensing program. The calculator applies the offer type (pay-as-you-go, Enterprise, CSP) and lets you enter a negotiated discount percentage.
  5. Save and share. With a Microsoft account the estimate is saved and you get a link. That is what gets attached to the architecture review.
  6. Export to a spreadsheet. The export button produces an .xlsx with one row per line, which is the format Nuria can work with and compare month to month.

Two usage warnings. The first: the calculator does not know your workload; it only multiplies whatever you tell it. If you put 730 hours for a machine that will actually be running for 200, that is not the tool's fault. The second: there are services whose cost cannot be estimated without prior data — data transfer out, transactions, tokens, GB ingested — and for those, the calculator forces you to enter a quantity, and that quantity is an assumption you have to document (section 9).

  1. The complete Contoso Airlines estimate

Marta rebuilt the estimate of the platform exactly as it stands today. The result, in illustrative and fictitious euros per month:

Group Line Assumed configuration € / month
Web front end plan-contoso-reservas-pro + plan-contoso-api-pro Premium v3, 3 and 2 instances, zone redundancy, 730 h 1,930
Availability API vmss-api-disponibilidad-pro Average of 6 instances out of the autoscale range of 2-20 1,320
Availability API cae-contoso-pro + ca-motor-disponibilidad Environment + 1 minimum replica always running 240
Containers aks-contoso-operaciones sistema (3) + aplicaciones (4) nodes + lotes on spot 1,980
Containers acrcontosopro Premium with geo-replication 90
Development Development plans and VM Dev App Service + vm-motor-disponibilidad-dev switched off at night 285
Storage sttarjetascontosopro GZRS, 4 TB, lifecycle to Cool after 30 days, transactions 420
Storage stlagocontosopro Data Lake, 12 TB, mixed tiers 280
Storage stoperacionescontosopro + sttarjetascontosodev ZRS 1 TB + LRS 300 GB 75
Data db-reservas (primary) General Purpose vCore, 8 vCores, zone redundancy, 500 GB 1,480
Data fg-contoso-reservas replica in North Europe Readable secondary of the failover group 1,180
Data sql-contoso-reservas-dev + cosmos-contoso-tarifas-pro Serverless with auto-pause + autoscale, average 1,400 RU/s 255
Data mysql-contoso-portal-pro + psql-contoso-tripulaciones-pro Flexible, 2 vCores each 345
Data syn-contoso-analitica-pro Serverless SQL per TB read + occasional sqlpool-contoso 400
Networking and security fw-contoso-hub-pro Azure Firewall: hours + GB processed 1,010
Networking and security fd-contoso-global + wafcontosoglobal Front Door Premium + WAF rules 385
Networking and security bastion-contoso-pro Standard tier, 730 h 205
Networking and security vgw-contoso-pro + private endpoints VPN + 14 private endpoints 235
Networking and security Data transfer out ~4.5 TB/month to the internet + cross-region replication 700
Observability log-contoso-pro + ai-insights-contoso-pro ~42 GB/day ingested + per-table retention 1,500
Observability Defender for Cloud SQL, Storage and Key Vault plans 310
Observability rsv-contoso-pro + bv-contoso-pro Protected instances + GB, 30 days, GRS 465
Integration sb-contoso-pro + evhns-contoso-telemetria-pro + evgt-contoso-reservas-pro Service Bus Premium 1 unit, Event Hubs 2 TU 780
Integration func-contoso-tarjetas-pro + logic-contoso-retrasos-pro Premium EP1 plan + Logic Apps actions 335
AI oai-contoso-pro + ai-contoso-pro Cost per token + AI services 730
Cross-cutting kv-contoso-pro, aa-contoso-operaciones, Azure DevOps and other minor items Operations, minutes, licenses, contoso-paquetes, IPs, DNS 515
Estimated total €17,450/month

Where each block comes from deserves comment, because that is where the learning is:

  • The five lines that surprise people are, in this order: log-contoso-pro (€1,500, more than half the entire web platform), fw-contoso-hub-pro (€1,010, which bills per hour and per gigabyte processed whether traffic flows or not), the aks-contoso-operaciones cluster (€1,980, because the nodes are virtual machines you pay for in full), bastion-contoso-pro (€205 for a service used fifteen minutes a day) and fd-contoso-global (€385 for the Premium tier the WAF requires).
  • The db-reservas replica costs €1,180, 80% of the primary. That is the explicit price of the recovery decision from module 7, and now it can be seen in euros: exactly the kind of data that makes an honest conversation with the business possible.
  • Data transfer out (€700) does not correspond to any resource. Nobody would have estimated it without the table in section 2.
  • The whole development environment is €285 thanks to the Detener-IniciarEntornosDev runbook and the serverless tier with auto-pause. Without those two decisions it would be around €1,100.

Compared with the €8,500 on the original slide, the difference is explained almost entirely by five lines: AKS, Log Analytics, the firewall, the database replica and data transfer out. None of them is a resource the team ever "asked for"; they are all consequences of correct architecture decisions that nobody translated into money.

  1. The total cost of ownership calculator

Nuria asked the inevitable question: "wasn't the Barcelona datacenter cheaper?". To answer it there is the total cost of ownership (TCO) calculator, a different tool from the pricing one: you describe the on-premises infrastructure — servers, cores, memory, storage, bandwidth, licenses — and it returns a multi-year comparison against the Azure equivalent.

The value of the tool is not in the number it produces, but in the fact that it forces you to include the costs local accounting never charges to the project:

On-premises cost Is it usually included? Comment
Hardware (servers, storage array, network) Yes The only thing almost everybody counts
Virtualization and OS licenses Sometimes And their annual maintenance
Electricity and cooling Rarely Typically 10-20% of the hardware cost per year
Space, raised floor and UPS Almost never Even if the building is your own, it has an opportunity cost
Operations staff Almost never On-call rotas, patching, replacing disks
Refresh every 4-5 years and overcapacity Badly You buy for the peak and pay all year, every cycle
The cost of downtime Never Without geo-redundancy, the risk is a deferred cost

With the TCO calculator and those adjustments, Contoso's comparison came out like this (illustrative and fictitious annual figures):

Scenario Annual cost Comment
Barcelona datacenter, visible cost €190,000 What appeared in the IT budget
Barcelona datacenter, real adjusted cost €340,000 With power, staff, space, refresh and overcapacity
Azure, current platform without optimization €209,400 €17,450 × 12
Azure, after the optimization in module 8 ~€150,600 A preview of 08-05

The conclusion Contoso wrote down, and one worth copying verbatim into any report: the comparison is not "Azure is cheaper", it is "Azure is cheaper than an honestly accounted-for datacenter, and on top of that it turns capital investment into operating expense, eliminates overcapacity and provides capabilities — geo-redundancy, scaling in minutes, managed services — that the datacenter did not have at any price". Comparing hardware alone against Azure invoices is the most common way of lying to yourself.

  1. Pricing by region: the same VM at two prices

The same instance size costs different amounts in West Europe, in North Europe, in Sweden Central or in the United States. The causes are real: the cost of energy and land, taxes, datacenter maturity, exchange rates and local demand.

An illustrative and fictitious index taking West Europe as 100 for the same VM:

Region Price index Comment
West Europe 100 Contoso's primary region
North Europe 96 Secondary region of the pair
Sweden Central 89 Cheaper, plentiful energy
East US 87 Usually among the most economical
Brazil South 128 Taxation and infrastructure

The temptation is obvious: move workloads to the cheapest region. Before doing so, four brakes Contoso applied:

  • Latency. The bookings website serves European passengers. A 13% saving on compute does not make up for 120 ms extra on every purchase.
  • Data residency. Personal data about passengers and crews does not leave the EU. That is a legal constraint, not a preference, and it is enforced by the allowed-regions policy from module 4.
  • Cross-region data transfer out. Splitting components that talk to each other a lot across two regions turns free internal traffic into billed cross-region traffic.
  • Service availability. Not every service and not every size exists in every region, and neither do availability zones.

The practical rule: the region is chosen on latency, data residency and service availability, and price is used only as a tie-breaker, or for workloads that have none of those constraints — a nightly batch process with no personal data, for example.

  1. The Retail Prices API

To automate estimates — or to compare regions without opening the calculator forty times — Azure publishes the Retail Prices API, which is public, requires no authentication and costs nothing. It returns official list prices, without your negotiated discounts.

# Hourly price of a VM size in West Europe, in euros
curl -s "https://prices.azure.com/api/retail/prices?currencyCode='EUR'&\$filter=\
serviceName eq 'Virtual Machines' and armRegionName eq 'westeurope' and \
armSkuName eq 'Standard_D4s_v5' and priceType eq 'Consumption'" \
  | jq -r '.Items[] | select(.productName | contains("Windows") | not)
           | "\(.armRegionName)\t\(.meterName)\t\(.retailPrice) \(.currencyCode)"'

The $filter parameter uses OData syntax and accepts serviceName, armRegionName, armSkuName, meterName, priceType (Consumption, Reservation, DevTestConsumption) and reservationTerm. The select clause in jq discards the Windows-licensed variants, which come mixed in with the Linux ones and are the most common misreading.

An equivalent loop over several regions — the use that pays off most — substitutes armRegionName eq '$REGION' inside a for REGION in westeurope northeurope swedencentral eastus, takes [.Items[].retailPrice] | min and multiplies by 730 hours to get the average month. The response is paginated through the NextPageLink field, so broad queries have to iterate. A very practical use: keep a script in contoso-infra that, on every pull request that modifies a .bicep file, looks up the prices of the declared SKUs and posts the estimate as an automatic comment on the pull request itself (section 10).

{
  "currencyCode": "EUR",
  "retailPrice": 0.2048,
  "unitOfMeasure": "1 Hour",
  "armRegionName": "westeurope",
  "armSkuName": "Standard_D4s_v5",
  "serviceName": "Virtual Machines",
  "priceType": "Consumption",
  "meterName": "D4s v5"
}

Every item returned has this shape. Look at unitOfMeasure: it is the key to not being wrong by three orders of magnitude. Some meters are expressed in "1 Hour", others in "1 GB/Month", others in "10K" operations and others in "1M" tokens. Multiplying without reading that column is the classic mistake of anybody automating estimates for the first time.

  1. The margin of error and the written assumptions

An estimate is a model, and every model has error. The difference between a professional estimate and an improvised number is that the first one declares its error and its assumptions.

The components of Contoso's estimate are classified by predictability:

Type of cost Examples Predictability Recommended margin
Fixed App Service plans, firewall, bastion, gateway Very high ±5%
Semi-fixed AKS base nodes, provisioned database High ±10%
Bounded variable VMSS with autoscale 2-20, Cosmos with autoscale Medium ±25%
Open variable Data transfer out, transactions, GB ingested, tokens Low ±50%

And this is how you estimate the variable part, which is where everybody gives up:

  • Autoscale: you do not estimate the maximum or the minimum, but the expected hourly profile. Contoso documented: 2 instances from 00:00 to 07:00, 6 from 07:00 to 22:00, and an apertura-temporada-verano profile averaging 14 for three weeks. The weighted monthly average came out at 6, and that is why the line says 6 and not 20.
  • Transactions and data transfer out: these are estimated from the business, not from the infrastructure. "92,000 bookings a month × 1.4 boarding passes per booking × 180 KB" gives the gigabytes of boarding pass egress; the rest is bounded with a factor.
  • Tokens: consumption per interaction × expected interactions, with a hard limit configured on the service so that the error is not unbounded.

Contoso's buffer: on top of the €17,450 base, a 15% contingency gives €20,070/month, and that is the figure that went to the committee. It is deliberately conservative, and it answers a real asymmetry: falling short on an estimate costs credibility with finance; overshooting slightly produces good news. The written rule was: "you budget the estimate with the buffer; you chase the base estimate".

The assumptions go in the document, not in somebody's head:

{
  "estimate": "contoso-platform-2026-08",
  "currency": "EUR",
  "primary_region": "westeurope",
  "prices_valid_as_of": "2026-08-01",
  "monthly_base_total": 17450,
  "buffer_pct": 15,
  "budgeted_total": 20070,
  "assumptions": [
    "Monthly bookings: 92,000, peaking at 148,000 in August",
    "vmss-api-disponibilidad-pro: average of 6 instances (hourly profile documented)",
    "Data transfer out to internet: 4.5 TB/month, cross-region replication included",
    "log-contoso-pro: 42 GB/day ingested, current per-table retention",
    "oai-contoso-pro: 40 million tokens/month, hard limit configured",
    "No reservations or savings plans purchased (see 08-03)",
    "Official list prices, no commercial agreement discount"
  ],
  "risks": ["Summer may double egress and VMSS", "sqlpool-contoso not paused"]
}

That file lives next to the templates in contoso-infra. Its value shows up three months later, when the bill does not add up: you compare the assumption with reality and you know what failed, not just how much.

  1. Estimation as part of the design

For cost to stop being a surprise, it has to be built into two moments of the process, not into an annual review.

In the architecture review. No proposal is approved at Contoso without an attached estimate with its assumptions and, when there are alternatives, without a comparison table. A real example from the design of the Availability API:

Alternative Illustrative € / month Latency Operations Decision
VMSS with autoscale 1,320 Low and stable Medium: patches, images Chosen: sustained, predictable load
Container Apps 890 Low, with occasional cold start Low Ruled out because of cold start at season opening
Functions on a consumption plan 410 Variable Very low Ruled out: the API is sustained, not sporadic

Notice that the cheapest option did not win, and that is the point: the estimate does not decide, it informs. What is unacceptable is deciding without one.

In the infrastructure pull request. Every change to a .bicep file in contoso-infra (05-06) goes through an automated check that compares the declared SKUs against the main branch and comments on the impact:

# Simplified: extract SKUs from the templates and ask the Retail Prices API
grep -rhoP "(?<=sku:\s')[A-Za-z0-9_]+" ./infra/*.bicep | sort -u | while read -r SKU; do
  P=$(curl -s "https://prices.azure.com/api/retail/prices?currencyCode='EUR'&\$filter=\
armSkuName eq '$SKU' and armRegionName eq 'westeurope' and priceType eq 'Consumption'" \
    | jq -r '[.Items[].retailPrice] | min // empty')
  [ -n "$P" ] && echo "| \`$SKU\` | €$P/h | €$(echo "$P * 730" | bc)/month |"
done

The output is posted as a comment on the pull request, with the markdown table already formatted. The cultural effect is bigger than the technical one: whoever proposes a change sees its price before anybody asks, and the conversation about cost happens at the moment when correcting it is free.

Common Mistakes and Tips

  • Estimating only compute and databases. That is exactly the mistake that doubled Contoso's bill. Walk through the units table in section 2 service by service.
  • Forgetting data transfer out. It has no resource of its own, it does not appear in the portal as an object and it is usually one of the top ten items.
  • Confusing the resource with the billed unit. You pay for the plan, not the application; the nodes, not the cluster; the vCore-hour, not the database.
  • Putting 730 hours against everything, or estimating the autoscale maximum. The first inflates environments that are switched off at night; the second produces figures nobody believes and discredits the entire estimate. Estimate the profile, and declare the maximum as a risk.
  • Misreading unitOfMeasure in the API. "1M tokens" and "1K operations" live side by side in the same response.
  • Switching something free on without looking downstream. Diagnostic settings are free; the ingestion they cause is not.
  • Tip: group the estimate by architecture component, not by Azure service. Nobody argues about "Storage"; everybody argues about "how much the Availability API costs".
  • Tip: save the estimate with a link and export it to a spreadsheet the day you make it, and revisit it when the architecture changes, not when the bill arrives.

Exercises

Exercise 1. Using the official calculator — with your region and your currency — estimate a development environment equivalent to Contoso's: a basic App Service plan, a serverless SQL database with auto-pause, a 200 GB LRS storage account and a 2 vCPU VM running during business hours only. Group by component, export it and note which three assumptions you had to invent.

Exercise 2. Contoso Miles (centro-coste=CC-2077) is about to launch: a website on App Service, PostgreSQL flexible, receipt blobs, a Function that calculates points, an Event Grid and a Log Analytics dashboard. Build the list of all the units of measure that will have to be estimated, marking which are fixed, bounded variable and open variable, and what margin you would apply to each group.

Exercise 3. A colleague proposes moving vmss-api-disponibilidad-pro from West Europe to East US because "it costs 13% less". Write the technical and economic response: which new costs appear, which constraints rule it out, and which Contoso workloads would be legitimate candidates for that move.

Solutions

Solution 1: the exercise matters for the assumptions, not for the total. The three you inevitably have to invent are: (1) VM hours — 176 hours a month with the business-hours pattern of 8 h × 22 days, against the 730 the calculator proposes by default; (2) compute seconds for the serverless database, which depend on how many hours a day the team works and on the auto-pause window configured, and which in development usually land at 15-25% of the month; and (3) storage transactions, which the calculator asks for as write, read and list operations and which in development nobody has ever measured. There are also two costs almost certainly omitted that have to be added: the VM's managed disk, which is billed even when the machine is deallocated, and its public IP if it has one. Sanity check: in an environment like this, the disk and the database usually weigh more than the compute, precisely because the compute gets switched off and the storage does not.

Solution 2: units by service and their classification. Fixed (±5%): App Service plan hour; vCore-hour and GB-month of PostgreSQL flexible if provisioned; the high-availability replica if enabled. Bounded variable (±25%): executions and GB-seconds of the Function if on a consumption plan — bounded because the number of redemptions has a known ceiling; Event Grid operations; GB-month of the blobs, which grow predictably at the pace of redemptions. Open variable (±50%): storage transactions, which with small receipts can exceed the GB-month; GB ingested into log-contoso-pro by the project's diagnostic settings, which is the most underestimated item; and data transfer out from receipt downloads. Free services with downstream consumption that have to be declared even at zero: Event Grid has a generous free allowance, tags and policies cost nothing, but the diagnostico-app-service assignment inherited from the "Base de gobernanza de Contoso" initiative will generate ingestion from day one. Recommended overall margin: 15% on the total, with the assumptions about monthly redemptions and average receipt size written into the document.

Solution 3: the 13% saving applies only to the compute line (€1,320 → around €1,150, roughly €170 a month), and against that come new costs: cross-region data transfer out for every availability query the VMSS makes to db-reservas and cosmos-contoso-tarifas-pro, which stay in West Europe — traffic that is internal and free today would start being billed and, at the API's volume, would comfortably eat the saving; latency of a transatlantic round trip on every request, degrading the availability shown to the passenger; and double operations, because you would have to replicate the network, NSGs, private endpoints, bastion, fw-contoso-hub-pro rules and diagnostic settings in a second region. The constraint that closes the discussion is compliance: passenger data does not leave the EU, and the allowed-regions policy from module 4 will deny the deployment. Workloads that would be legitimate candidates: nightly batch processes over already anonymized data, self-hosted build agents for contoso-reservas-ci — which can also run on spot instances (08-03) — and one-off training runs or load tests with no personal data. General rule: you move on price whatever has no critical latency, no regulated data and no chatty conversation with resources in another region.

Conclusion

You now know why estimation is the only lever that acts while correcting is still free, and why Contoso's error — doubling the forecast — was not one of arithmetic but of mental model: Azure is not a catalog of machines with a monthly price, but a set of units of consumption. You have the table of those units by service family — instance hour, plan hour, GB-month, transaction, request unit, TB read, GB ingested, GB of data transfer out, execution, token, protected instance — the warning that almost everything has a second unit nobody estimates, and the three costs that always get forgotten: data transfer out, which has no resource to look at; transactions, which on small objects exceed storage; and the "free" features that drag consumption along downstream, with diagnostic settings as the perfect example.

You can use the pricing calculator with method — search, configure region, tier, quantity and hours, group by component, set currency and offer, save, share and export — and you have seen Contoso's complete estimate: an illustrative €17,450/month, with the five surprising lines identified — Log Analytics, the firewall, the AKS nodes, the bastion and Front Door — plus the db-reservas replica, which costs 80% of the primary and puts an explicit price on the recovery decision from module 7. You know how to use the total cost of ownership calculator and which hidden datacenter costs have to be added for the comparison to be honest: power, staff, space, refresh, overcapacity and risk. You understand why the same VM costs different amounts in each region and why the region is chosen on latency, data residency and availability, with price only as a tie-breaker; and you can automate it with the Retail Prices API, always watching unitOfMeasure. Above the tooling you carry what turns a number into an estimate: the declared margin of error, the way to estimate the variable part from the hourly profile and from the business instead of from the theoretical maximum, the 15% buffer that took €17,450 to the €20,070 budgeted, and the file of assumptions and risks versioned alongside the templates.

But an estimate, however good, is still a hypothesis. Nuria's question — "why does the bill go up every month?" — can only be answered with real data: what was spent, on which resource, by which team, on which day and why. That is Azure Cost Management, and it is the next lesson: the billing hierarchy and how it differs from the resource one, cost analysis grouped by service, location, resource group and tag — where the discipline of centro-coste=CC-1042 sown in module 1 and enforced by the hereda-centro-coste policy from module 4 finally pays off — budgets with their automated alerts, allocation between teams, exports to stlagocontosopro and anomaly detection. We move from estimating cost to measuring it.

Azure Course

Module 1: Introduction to Azure

Module 2: Core Azure Services

Module 3: Azure Databases

Module 4: Security in Azure

Module 5: Azure DevOps

Module 6: Advanced Azure Services

Module 7: Monitoring and Management

Module 8: Cost Management and Optimization

Module 9: Case Studies and Best Practices

© Copyright 2026. All rights reserved