LevelUpWith

Explore / Cloud Pro: Azure Databases: Choose, Compare and Launch / Lesson 2

Lesson 2: The Standard Workload Profile

Learners build a reusable workload profile covering data model, read/write mix, QPS and latency, transactions and consistency, size and growth, scaling and sharding, availability with RPO and RTO, multi-region, engine compatibility and licensing, OLTP versus analytics, team skills and cost model. Every later lesson tests services against it.

Free to read, no account needed. Part of Cloud Pro: Azure Databases: Choose, Compare and Launch.

By the end of this level you'll be able to

  • Fill in the profile for a real workload, using measured numbers instead of adjectives
  • Pick out the two or three profile items that rule services out straight away, such as engine lock-in, RPO or multi-region writes
  • Turn a vague business request into concrete targets for latency, throughput, availability and budget

Why you need a profile before you need a service

In L1 you saw the whole Azure database map: relational, distributed SQL, key-value and document, wide-column, in-memory, graph and time series, and migration. That map is a menu. A menu doesn't help until you know what you're hungry for.

The usual mistake is to start with a product ("we're a Postgres shop", "Cosmos DB scales") and then justify it. Experienced engineers turn it around. They describe the workload first, in numbers, and then test each service against that description. This lesson builds that description: a standard workload profile. Every service lesson after this one checks the service against the same twelve items.

Think of it as a tenancy application for your data. A landlord won't accept "I earn quite a lot." They want a figure.

The twelve items

# Item The question it answers Measured as
1 Data model Tables with joins? Documents? Key lookups? Wide rows? Graph? Entity list, access patterns
2 Read/write mix Mostly reads, mostly writes, or balanced? % reads vs % writes
3 QPS and latency How busy at peak, and how fast must it answer? Peak queries/sec, p95/p99 ms
4 Transactions and consistency Multi-row ACID? Must every read see the latest write? Yes/no per flow, consistency level
5 Size and growth How big now, how big in 3 years? GB today, GB/month
6 Scaling and sharding Scale up one box, or spread across nodes? Natural shard key? Max single-node need, candidate key
7 Availability, RPO, RTO How much downtime and data loss are acceptable? %, seconds/minutes
8 Multi-region Read locally only, or write in several regions? Regions, single or multi-writer
9 Engine compatibility and licensing Tied to T-SQL, PL/pgSQL, Oracle, Cassandra CQL, Redis commands? Existing licences? Feature list, licence count
10 OLTP vs analytics Many small transactions, big scans, or both? Query shapes, report frequency
11 Team skills What can the team run at 3 a.m.? Named skills, on-call depth
12 Cost model Budget, and do you want fixed or usage-based billing? Money per month, ceiling

Walkthrough: from adjectives to numbers

Here's a realistic request from a product owner for an order-tracking service:

"It needs to be fast, always up, work globally, and not cost a fortune."

Every word in that sentence is an adjective, so none of it can be tested. Convert each one, starting with measured data. If the system already runs on PostgreSQL, pg_stat_statements tells you what the database actually does:

-- Top statements by call count since the stats were last reset
SELECT left(query, 60)              AS query,
       calls,                         -- how often it ran
       round(mean_exec_time::numeric, 2) AS mean_ms,  -- average, NOT p99
       rows
FROM   pg_stat_statements
ORDER  BY calls DESC
LIMIT  5;

Then turn daily volumes into a peak rate. Averages hide peaks, so apply a peak factor taken from your own traffic graphs:

orders_per_day   = 2_000_000      # from the business
reads_per_order  = 12             # status checks, from app logs
writes_per_order = 4              # create, pay, ship, deliver

secs = 86_400
avg_reads  = orders_per_day * reads_per_order  / secs   # ~278/s
avg_writes = orders_per_day * writes_per_order / secs   # ~93/s
peak_factor = 4                   # measured: busiest hour vs daily average

print(round(avg_reads * peak_factor), round(avg_writes * peak_factor))
# 1111 370  -> design for ~1,100 reads/s and ~370 writes/s, a 75/25 mix

Availability percentages also become concrete once you turn them into minutes:

for sla in (99.9, 99.95, 99.99, 99.999):
    mins = (1 - sla/100) * 365 * 24 * 60
    print(f"{sla}% -> {mins:.1f} min/year")
# 99.9%   -> 525.6 min/year (~8.8 h)
# 99.95%  -> 262.8 min/year (~4.4 h)
# 99.99%  -> 52.6 min/year
# 99.999% -> 5.3 min/year

Now write the profile down as a file you keep in the repo and reuse:

# workload-profile.yaml : order tracking, v1, 2026-10-25
data_model: relational; orders, lines, shipments; joins on order_id
read_write_mix: 75/25
peak_qps: { reads: 1100, writes: 370 }
latency: { p99_read_ms: 50, p99_write_ms: 100 }   # "fast" made testable
transactions: multi-row ACID on payment; read-your-own-writes on status
size: { today_gb: 180, growth_gb_month: 12 }       # ~610 GB in 3 years
scaling: single writer fine today; shard key candidate = customer_id
availability: 99.95%                                # "always up", agreed
rpo: 5 min            # data loss we can tolerate
rto: 1 h              # time to be serving again
multi_region: reads in EU + US; writes EU only      # "global", clarified
engine: PostgreSQL 16, uses PostGIS extension
workload_type: OLTP; nightly report could move to a replica
team: strong Postgres, no SQL Server DBA
cost: ceiling 4,000/month, steady load -> reserved capacity OK

Gotcha: average vs p99. mean_exec_time is an average. Users feel the slow tail, so set targets at p95 or p99 and measure them at the application, where network time is included.

Gotcha: "global". Ask whether users need to write in several regions or only read close to home. Local reads are cheap and common. Writes in several regions are a different architecture.

Knockout items: rule services out first

Most profile items only affect the score. A few are knockouts: a single answer removes whole services before you compare anything else. Check these first.

  1. Engine lock-in. If the app depends on T-SQL stored procedures, PostgreSQL extensions such as PostGIS, Oracle PL/SQL or Cassandra CQL, any service that doesn't speak that engine is either out or needs a rewrite project.
  2. RPO and RTO across regions. Cross-region replication is usually asynchronous. Microsoft's Azure SQL Database documentation, for example, puts geo-replication RPO at "equal to or greater than 0". The real figure depends on changes not yet replicated when the region fails. Restoring from geo-replicated backups can take minutes to hours. A hard "zero data loss if a whole region fails" requirement rules out many configurations straight away.
  3. Multi-region writes. Most managed relational setups have one writable primary and readable secondaries. If the business truly needs writes accepted in several regions at once, the shortlist shrinks quickly. Cosmos DB, for example, offers multi-region writes, with a 99.999% read and write availability SLA in that configuration.

In our profile, PostGIS and the 5-minute RPO matter most. Multi-region writes are not needed, and confirming that with the business keeps a lot of options open.

Best practice: For each knockout, record who agreed to the number and when. "RPO 5 min, agreed by Head of Ops, 2026-10-25" carries weight. "RPO low" carries none.

Trade-offs to keep honest

  • Each extra nine of availability, or each step down in RPO, usually adds a replica, a region or a higher tier. Put a price next to each one.
  • Stronger consistency costs latency and availability in distributed systems. Cosmos DB, for instance, offers five levels: Strong, Bounded staleness, Session, Consistent prefix and Eventual. Decide what each user flow actually needs.
  • Team skills are a real constraint. A technically better engine the team can't operate is a risk.

Key takeaways

  • Describe the workload before picking a service, using the same twelve items every time.
  • Use measurements: peak QPS from logs, p99 latency, GB and growth per month, RPO and RTO in minutes, budget per month.
  • Convert SLA percentages into minutes per year (99.99% ≈ 52.6 min) so stakeholders know what they're asking for.
  • Check knockouts first: engine lock-in, cross-region RPO/RTO and multi-region writes.
  • Keep the profile as a versioned file. Every later lesson tests a service against it.

A 6-question knowledge check follows this lesson in the app, free and without an account.

Keep going: levels 3 and 4 are free

Create a free account to open the next two levels, save your progress and pick up where you left off. No card needed.

Next: Level 3, Azure SQL Database: vCore, DTU and Service Tiers.

Create a free account →See the whole course

More like this

  • Cloud Pro: Azure Networking: Choose, Compare and Launch

    Map every Azure networking service to a standard connectivity profile, and learn each one's limits, cost levers and trade-offs. You will launch each service wi…

    Course · Microsoft · Cloud Pro: Choose and Use · Expert · 36 levels · 4 free · Professionally curated by levelupwith.com

  • Cloud Pro: Azure Storage: Choose, Compare and Launch

    Turn any workload into a standard data profile, then choose the right Azure storage service with evidence. For each service you will learn its limits, costs an…

    Course · Microsoft · Cloud Pro: Choose and Use · Expert · 30 levels · 4 free · Professionally curated by levelupwith.com

  • Microsoft Azure Fundamentals (AZ-900) Exam Prep

    Learn to pick the cloud model, service type or Azure service that fits a scenario and explain why the alternatives do not, across every skill in the 20 July 20…

    Exam prep · AZ-900 · Cloud & Compute · Capable · 17 levels · 4 free · Professionally curated by levelupwith.com

  • Microsoft Azure Administrator (AZ-104) Exam Prep

    Work through every bullet of the AZ-104 skills measured as of April 17, 2026, learning each task in the Azure portal, Azure CLI, PowerShell, and ARM templates…

    Exam prep · AZ-104 · Cloud & Compute · Expert · 60 levels · 4 free · Professionally curated by levelupwith.com

  • Support Pro: Helping Users Move to Microsoft 365

    Help users get through a move from Google Workspace to Microsoft 365, from the week before cutover to the first tickets afterwards. You will learn what moves a…

    Course · Microsoft · Suite Support Pro: Configure and Fix · Expert · 40 levels · 4 free · Professionally curated by levelupwith.com

  • Microsoft 365 Support Pro: Copilot for End Users

    Learn to work out which Copilot a user actually has, and to fix the everyday Copilot tickets: missing buttons, licence and sign-in problems, files Copilot can'…

    Course · Microsoft · Suite Support Pro: Configure and Fix · Expert · 36 levels · 4 free · Professionally curated by levelupwith.com