Prev Next

Database / Azure Cosmos DB interview questions

1. What is Azure Cosmos DB and what problems does it solve? 2. What are the different APIs available in Azure Cosmos DB? 3. What is a partition key in Azure Cosmos DB and why is choosing it correctly so important? 4. What are Request Units (RU/s) in Azure Cosmos DB? 5. What are the five consistency levels in Azure Cosmos DB? 6. How does global distribution work in Azure Cosmos DB? 7. What is the Cosmos DB Change Feed and what are its main use cases? 8. What is provisioned throughput vs autoscale vs serverless in Cosmos DB? 9. How does indexing work in Azure Cosmos DB? 10. What is Time to Live (TTL) in Cosmos DB and how do you configure it? 11. What is a stored procedure in Cosmos DB and what are its limitations? 12. What is the difference between a point read and a query in Cosmos DB? 13. What is the Cosmos DB NoSQL query language and how does it differ from standard SQL? 14. What is the Cosmos DB transactional batch API? 15. What is Cosmos DB Integrated Cache and how does it reduce RU consumption? 16. How does optimistic concurrency work in Azure Cosmos DB? 17. What is hierarchical partition keys in Cosmos DB and when do you use it? 18. What is the Cosmos DB Bulk Executor and how do you use bulk operations in the SDK? 19. What are Cosmos DB triggers and user-defined functions (UDFs)? 20. How does Cosmos DB handle conflicts in multi-region write (multi-master) setups? 21. What is the Cosmos DB Emulator and how is it used in development? 22. What is Cosmos DB for MongoDB API and what version compatibility does it provide? 23. What is the Cosmos DB analytical store and Azure Synapse Link? 24. What are Cosmos DB materialized views and how do they differ from containers? 25. How does Cosmos DB pricing work and what are the key cost drivers? 26. What is the Cosmos DB Gremlin API and what is it optimized for? 27. How does Cosmos DB backup and restore work? 28. What is the Cosmos DB Patch API and how does it differ from Replace? 29. What is the Cosmos DB Cassandra API and how does CQL map to Cosmos DB concepts? 30. How do you model one-to-many relationships in Cosmos DB? 31. What is the Cosmos DB free tier and what does it include? 32. What is the Cosmos DB SDK and what are the key client configuration options? 33. What is the Cosmos DB Table API and when would you migrate from Azure Table Storage to it? 34. How does Cosmos DB handle security and access control?
Could not find what you were looking for? send us the question and we would be happy to answer your question.

1. What is Azure Cosmos DB and what problems does it solve?

Azure Cosmos DB is Microsoft's globally distributed, multi-model NoSQL database service built for modern cloud-native applications. It is designed to solve two of the hardest problems in distributed systems: global low-latency reads and writes and horizontal scalability without any schema or infrastructure management burden.

At its core, Cosmos DB stores data as items (JSON documents, key-value pairs, graph nodes, or column-family rows depending on which API you use), organizes them into containers (analogous to collections or tables), and groups containers into databases. All storage is SSD-backed, replicated across multiple fault domains within a region, and optionally replicated across every Azure region worldwide with a single toggle.

The problems it specifically addresses: traditional relational databases require you to choose a single region and manually set up complex read replicas for global reach. With Cosmos DB you declare which regions you want, and replication is automatic. You also no longer need to guess capacity upfront — throughput scales elastically via Request Units (RU/s), and the Serverless tier removes the need to pre-provision capacity entirely for sporadic workloads. Schema enforcement is deliberately absent, so schema evolution is friction-free compared to SQL ALTER TABLE migrations.

It is the right choice when you need single-digit millisecond latency at the 99th percentile, when your data spans multiple regions, or when your workload is too variable to size a fixed database cluster.

What is the fundamental unit of throughput in Azure Cosmos DB?
What Cosmos DB pricing tier eliminates the need to pre-provision throughput for sporadic workloads?
2. What are the different APIs available in Azure Cosmos DB?

Azure Cosmos DB is a multi-model database, meaning a single back-end engine exposes different wire-protocol-compatible APIs so you can interact with data using the client libraries and query syntax you already know. As of 2024, six APIs are available:

Azure Cosmos DB API Overview
APIData ModelBest For
NoSQL (Core)JSON documentsNew applications, native Cosmos SDK, richest feature set
MongoDBBSON documentsMigrating existing MongoDB apps; wire-compatible with MongoDB drivers
CassandraColumn-family / CQLMigrating Apache Cassandra workloads; CQL wire protocol
GremlinProperty graphSocial graphs, recommendation engines, highly connected data
TableKey-value (entities)Migrating Azure Table Storage apps with minimal code changes
PostgreSQL (vCore)Relational / SQLDistributed relational workloads using the Citus extension on PostgreSQL

The NoSQL API is the native API with the fullest feature parity — it supports the richest query language, all five consistency levels, server-side JavaScript (stored procedures, triggers), and change feed. The other APIs are compatibility layers that let you point existing drivers at Cosmos DB. The MongoDB API, for example, implements the MongoDB wire protocol, so a Node.js app using Mongoose can switch from Atlas to Cosmos DB by changing the connection string with no code changes.

An important nuance: each account is bound to one API at creation time. You cannot switch APIs after account creation, so choosing the right API upfront is critical. If you have no legacy migration requirement, the NoSQL API is always the recommended starting point.

Which Cosmos DB API provides the richest feature set including full change feed, all consistency levels, and server-side JavaScript?
Can you switch a Cosmos DB account from the MongoDB API to the NoSQL API after creation?
3. What is a partition key in Azure Cosmos DB and why is choosing it correctly so important?

A partition key is a property you designate on every item in a Cosmos DB container. Its value is hashed to determine which logical partition the item belongs to. Cosmos DB distributes logical partitions across physical partitions (server nodes), and this is how it achieves horizontal scaling — more physical partitions means more throughput and storage capacity distributed across more servers.

The reason choosing it correctly matters so much comes down to two hard limits Cosmos DB enforces:

  • A single logical partition can hold at most 20 GB of data.
  • Throughput and storage cannot be rebalanced across logical partitions — you cannot move an item from one logical partition to another after it is written without deleting and reinserting it.

A poorly chosen partition key creates hot partitions — a small number of logical partitions absorbing the majority of reads and writes while others sit idle. Even if you provision 50,000 RU/s at the container level, a hot partition effectively limits you to a fraction of that because RU/s are distributed evenly across physical partitions.

A good partition key has high cardinality (many distinct values), even distribution of reads and writes across those values, and aligns with your most common query patterns so that queries stay within a single partition (cross-partition queries fan out to all physical partitions and are more expensive). For a social app, userId is typically a better partition key than country, because a small country could easily hold millions of users and hit the 20 GB ceiling.

Cosmos DB also supports a synthetic partition key — concatenating two or more properties to form a higher-cardinality value when no single field is sufficient on its own.

What is the maximum data storage limit for a single logical partition in Cosmos DB?
What is a synthetic partition key in Azure Cosmos DB?
4. What are Request Units (RU/s) in Azure Cosmos DB?

Request Units (RU/s) are the currency of throughput in Azure Cosmos DB. Rather than expressing capacity in CPU cores, memory, or IOPS — which are hard to reason about at the application level — Cosmos DB normalizes all database operations into a single unit. One RU is defined as the cost of reading a 1 KB item by its partition key and ID (a point read). Every operation has an RU cost computed from CPU, memory, and I/O it consumes.

Typical RU costs to internalize:

  • Point read (GET by id + partition key): ~1 RU per 1 KB
  • Write (upsert/insert): ~5 RU per 1 KB (writes cost more because they update indexes)
  • Query with filter on partition key: varies — simple filters may be 2-3 RU; complex cross-partition queries can be 10-100+ RU
  • Cross-partition fan-out query: multiplied by number of physical partitions scanned

Provisioned throughput is set in RU/s at either the container level (dedicated throughput) or the database level (shared throughput distributed across all containers in that database). When your workload exceeds the provisioned RU/s, Cosmos DB returns HTTP 429 (Too Many Requests) responses and includes a x-ms-retry-after-ms header indicating how long to back off before retrying.

The Cosmos DB SDKs handle 429 retries automatically with exponential backoff, but you will see increased latency. To avoid this: provision adequate RU/s, use autoscale to handle peaks automatically, or distribute workload more evenly across time.

You can check the actual RU cost of any operation via the x-ms-request-charge response header or via the SDK's response diagnostics, which is the primary way to identify expensive queries and optimize them.

What HTTP status code does Cosmos DB return when a request exceeds provisioned RU/s?
Approximately how many RU/s does a point read of a 1 KB item cost in Cosmos DB?
5. What are the five consistency levels in Azure Cosmos DB?

Consistency levels in Cosmos DB define the tradeoff between data freshness and system availability/latency when data is replicated across multiple regions or replicas. Azure Cosmos DB offers five levels, from strongest to weakest:

Cosmos DB Consistency Levels
LevelGuaranteeLatency Impact
StrongReads always return the most recent committed version. Linearizability guaranteed.Highest — writes must be acknowledged by all replicas before returning
Bounded StalenessReads lag behind writes by at most K versions or T time interval (you configure both)High — similar to Strong within a region; slower for cross-region reads
SessionMonotonic reads, monotonic writes, read-your-own-writes, and write-follows-reads — within a single client sessionLow — the default and most practical level for most applications
Consistent PrefixReads never see out-of-order writes. If writes are A, B, C you will never read B without A.Low — reads may be stale but always see a causally consistent prefix
EventualNo ordering guarantees. Reads may return stale or out-of-order values temporarily.Lowest — maximum throughput, minimum latency

Session consistency is the default and the most widely used level. It gives strong consistency guarantees within a session token scope (a single user or client connection) while keeping cross-replica latency low. The session token is passed in request headers, and any replica that has caught up to that token can serve reads. This covers the most important correctness requirement for most apps: a user immediately sees their own writes.

Cosmos DB lets you relax consistency per request (weaken it, not strengthen it), so you can request eventual reads for a reporting query while keeping session consistency for writes.

Which Cosmos DB consistency level is the default and guarantees read-your-own-writes within a session?
What does Bounded Staleness consistency allow you to configure?
6. How does global distribution work in Azure Cosmos DB?

Cosmos DB is built from the ground up for global distribution. Every account has a single write region by default (or multiple write regions with multi-master enabled), and you can add any number of read regions at any time. Cosmos DB automatically replicates all data to every configured region using a proprietary replication protocol that targets the configured consistency level.

Adding a region is a portal/CLI toggle, not a manual data migration. Cosmos DB handles all the replication behind the scenes. The 99th-percentile read and write latency is under 10 ms within a region, and under 10 ms for reads from any region (since reads go to the nearest read replica). Writes in single-write-region mode are synchronous to the primary region and asynchronous to read regions.

The replication model depends on consistency level. With Strong consistency, every write must be acknowledged across a quorum of replicas in all regions before returning — this means write latency scales with inter-region round-trip time. With Eventual or Session consistency, writes return after the local quorum acknowledges, and other regions catch up asynchronously.

Automatic failover can be configured so that if the primary write region goes down, Cosmos DB automatically promotes the next region in your priority list to become the new write region. You can test this with manual failover in the portal without data loss (because replicas are always in sync up to the consistency level you chose).

Conflict resolution applies when multi-region writes are enabled and two clients in different regions write to the same item concurrently. Cosmos DB resolves this with Last-Write-Wins (based on a server-side timestamp or custom _ts) or a custom conflict resolution procedure you define.

When adding a new read region to a Cosmos DB account, what does the developer need to do to replicate existing data?
Which conflict resolution strategy does Cosmos DB use by default for multi-region write conflicts?
7. What is the Cosmos DB Change Feed and what are its main use cases?

The Change Feed is a persistent, ordered log of every insert and update that occurs in a Cosmos DB container. It records changes in the order they occur within each logical partition, and this log is available for consumption indefinitely (it is not ephemeral like a message queue). Deletes are not captured by default, but you can enable a soft-delete pattern by marking items with a deleted flag and relying on TTL to purge them.

The Change Feed exposes two primary consumption models:

  • Change Feed Processor (CFP) — A library (available in all Cosmos DB SDKs) that manages distributed consumption across multiple worker instances. It uses a separate lease container to track each worker's read position per logical partition. This is the recommended approach for most applications — it handles partition splits, lease management, and worker scaling automatically.
  • Azure Functions Cosmos DB Trigger — A serverless binding that invokes a function for each batch of changes. Internally it uses the Change Feed Processor library. Zero infrastructure to manage.

Common use cases:

  • Real-time event streaming — Forward Cosmos DB mutations to Azure Event Hubs or Kafka for downstream analytics pipelines.
  • Materialized views — Maintain a denormalized view in another container that is optimized for a different query pattern (e.g., store orders by customerId in the source, maintain a separate container keyed by productId for product-based reporting).
  • Cache invalidation — When an item in Cosmos DB changes, push the updated version to Redis or a CDN edge cache.
  • Auditing — Write every change to an immutable audit log container or Azure Blob storage.
  • Event-driven microservices — Use Cosmos DB as an event store and the Change Feed as the outbox, replacing traditional message broker coupling.
Does the Cosmos DB Change Feed capture delete operations by default?
What is the lease container used for in the Change Feed Processor?

8. What is provisioned throughput vs autoscale vs serverless in Cosmos DB?

Cosmos DB offers three throughput provisioning models, and choosing the right one significantly affects cost and performance:

Provisioned Throughput (Manual) — You pre-set a fixed RU/s number (minimum 400) that is guaranteed and always available. The cost is flat per hour regardless of actual usage. Best when you have a stable, predictable workload and need guaranteed performance. You can change the provisioned value at any time, but scaling down has limits (cannot drop below 10% of the highest RU/s set in the past hour).

Autoscale — You set a maximum RU/s ceiling (e.g., 10,000 RU/s), and Cosmos DB automatically scales between 10% of the max (1,000 RU/s) and the max based on actual workload. You are billed for the highest RU/s reached in any one-hour window. This eliminates over-provisioning during off-peak hours while still providing burst capacity. Best for variable workloads with unpredictable spikes.

Serverless — No pre-provisioning at all. You are billed only for the RU/s actually consumed per operation, plus storage. The per-RU rate is higher than provisioned, but there is no charge for idle time. A serverless account is limited to a single region, 50 GB of storage, and lower burst RU/s compared to provisioned. Best for development, testing, or workloads that are truly sporadic (hours or days between activity).

Throughput Model Comparison
ModelBilled OnMulti-RegionBest For
ProvisionedProvisioned RU/s (always)YesSteady, predictable load
AutoscalePeak RU/s per hourYesVariable with defined maximum
ServerlessRU/s consumed + storageNoDev/test, sporadic workloads
With Autoscale enabled at a max of 10,000 RU/s, what is the minimum RU/s Cosmos DB will scale down to?
Which throughput model is restricted to a single Azure region?
9. How does indexing work in Azure Cosmos DB?

By default, Cosmos DB automatically indexes every property in every JSON item you insert — no schema definition, no CREATE INDEX statement required. This is called the automatic indexing policy. When you write a document, the indexing engine traverses the JSON tree and adds every field path, array element, and nested object to a set of inverted indexes maintained alongside the data. This is why write costs in Cosmos DB are higher than read costs per RU — every write triggers index updates.

The indexing policy is configured per container in JSON and controls three things:

  1. indexingModeconsistent (default, synchronous), lazy (asynchronous, lower write cost, not recommended), or none (disables indexing entirely).
  2. includedPaths — Explicit paths to index (e.g., /address/city/?). Wildcard /* indexes everything.
  3. excludedPaths — Paths to exclude from indexing (e.g., large text fields you never filter on). Excluding high-cardinality or rarely-queried large fields significantly reduces RU cost per write and storage overhead.

Three index types exist:

  • Range index — Default for scalar values. Supports =, <, >, BETWEEN, and ORDER BY.
  • Spatial index — For GeoJSON geometry types. Supports ST_DISTANCE, ST_INTERSECTS, and other geo queries.
  • Composite index — Required when an ORDER BY clause references two or more properties, or when a filter and ORDER BY target different properties. You must explicitly define composite indexes.

A common optimization: exclude the /_etag path and any large blob-like string fields from indexing by default to reduce write RU consumption on write-heavy containers.

What type of Cosmos DB index is required to support ORDER BY on two different properties in the same query?
What is the best way to reduce the RU cost per write on a container with many rarely-queried large text fields?
10. What is Time to Live (TTL) in Cosmos DB and how do you configure it?

Time to Live (TTL) is a built-in expiry mechanism that automatically deletes items after a specified number of seconds from their last modification timestamp. This is useful for session data, temporary tokens, audit logs with retention windows, or any data with a known shelf life. Cosmos DB's TTL deletion is handled by a background process and does not consume your provisioned RU/s — it is essentially free in terms of throughput impact.

TTL is configured at two levels:

  • Container-level TTL (DefaultTimeToLive) — Set this to a positive integer (seconds) to give all items a default TTL. Set to -1 to enable TTL at the container level but make each item's TTL opt-in (items without a ttl property never expire). If this property is absent on the container, TTL is completely disabled.
  • Item-level TTL (ttl property) — Set a ttl field on individual items to override the container default. An item-level ttl: -1 means that item never expires regardless of the container default.

An example showing how container default and item override interact:

// Container: DefaultTimeToLive = 3600 (1 hour)

// This item expires in 1 hour (inherits container default)
{ "id": "session-1", "userId": "u123" }

// This item expires in 5 minutes (item override)
{ "id": "temp-token", "userId": "u456", "ttl": 300 }

// This item never expires (item override = -1)
{ "id": "permanent-record", "userId": "u789", "ttl": -1 }

TTL deletion happens within a few seconds to minutes after the expiry time. It is approximate, not exact — do not rely on it for precision timing like security token enforcement (validate the expiry claim in the token itself instead).

What happens if you set DefaultTimeToLive to -1 on a Cosmos DB container?
Does the background process that deletes TTL-expired items in Cosmos DB consume your provisioned RU/s?
11. What is a stored procedure in Cosmos DB and what are its limitations?

Stored procedures in Cosmos DB are JavaScript functions registered on a container and executed server-side on the Cosmos DB engine itself. They run atomically within a single partition — meaning all operations inside the stored procedure either all commit or all roll back, giving you ACID transaction semantics without distributed coordination overhead.

A stored procedure is registered and then called via the SDK or REST API:

// Register a stored procedure
const sprocBody = function createDocIfAbsent(id, body) {
  var context = getContext();
  var collection = context.getCollection();
  var response = context.getResponse();

  var query = { query: "SELECT * FROM c WHERE c.id = @id", parameters: [{ name: "@id", value: id }] };
  var isAccepted = collection.queryDocuments(collection.getSelfLink(), query, {}, function(err, docs) {
    if (err) throw err;
    if (docs.length > 0) {
      response.setBody(docs[0]);
    } else {
      var accepted = collection.createDocument(collection.getSelfLink(), body, function(err, doc) {
        if (err) throw err;
        response.setBody(doc);
      });
      if (!accepted) throw new Error("createDocument not accepted");
    }
  });
  if (!isAccepted) throw new Error("queryDocuments not accepted");
};

await container.scripts.storedProcedures.create({ id: "createIfAbsent", body: sprocBody });

// Execute it
const result = await container.scripts.storedProcedure("createIfAbsent").execute(partitionKey, [id, body]);

Key limitations to know for interviews:

  • Single partition scope only — A stored procedure cannot touch items across multiple partition key values. All reads and writes must target the same logical partition passed at invocation time.
  • Continuation token required for large result sets — Stored procedures have a time and response size budget. If a bulk operation does not complete in one execution, you must implement pagination using continuation tokens and re-invoke the procedure.
  • No external HTTP calls — Server-side scripts cannot call external APIs or Azure services. Logic must be pure JS within the Cosmos DB context API.
  • JavaScript only — No other language is supported for stored procedures, triggers, or user-defined functions.
Across how many partition key values can a single Cosmos DB stored procedure operate?
What language must Cosmos DB stored procedures and triggers be written in?
12. What is the difference between a point read and a query in Cosmos DB?

A point read is the most efficient read operation in Cosmos DB. It fetches a single item by specifying both the item's id and its partition key value exactly. Cosmos DB can route this operation directly to the specific replica holding that item without scanning any index. The RU cost is approximately 1 RU per 1 KB of document size, regardless of the container size.

A query uses the SQL-like query language to filter items based on conditions. Even a simple query like SELECT * FROM c WHERE c.id = 'abc' is more expensive than a point read because it goes through the query processor, which must parse the query, check indexes, and return a result set. If the query includes the partition key in the filter (WHERE c.userId = 'u123'), it is a single-partition query and stays on one physical partition. If it omits the partition key or queries across multiple partition values, it becomes a cross-partition query that fans out to every physical partition — potentially costing 10x or more depending on the number of partitions.

Point Read vs. Query Comparison
AspectPoint ReadQuery
SDK callcontainer.ReadItemAsync(id, partitionKey)container.GetItemQueryIterator(queryDef)
RoutingDirect to owning replicaVia query processor; may fan out
Typical RU cost~1 RU / 1 KB2 RU+ depending on complexity
Index requiredNo (key-based lookup)Yes for efficient filtering
Use whenYou know both id and partition keyYou need filtered/sorted results

The practical implication: design your application to use point reads wherever possible. If you frequently look up items by a non-id property, consider denormalizing data or creating a separate lookup container so the hot path can use a point read rather than a query.

What two pieces of information are required to perform a point read in Cosmos DB?
What happens when a Cosmos DB query does not include the partition key in its WHERE clause?
13. What is the Cosmos DB NoSQL query language and how does it differ from standard SQL?

The Cosmos DB NoSQL API supports a SQL-like query language (sometimes called Cosmos DB SQL or the NoSQL query language) that is syntactically close to ANSI SQL but adapted for JSON documents. You use familiar keywords — SELECT, FROM, WHERE, ORDER BY, GROUP BY, JOIN — but with several important extensions and differences.

Key differences from standard SQL:

  • FROM clause is the container aliasFROM c makes c an alias for each item in the container, not a table. You navigate JSON fields with dot notation: c.address.city.
  • Array iteration with JOIN — Cosmos DB JOIN is not a relational join between two containers; it is a self-join that flattens arrays. SELECT t FROM c JOIN t IN c.tags produces one row per array element, allowing per-element filtering.
  • Built-in JSON functions — Functions like IS_ARRAY(), IS_NULL(), ARRAY_CONTAINS(), STRINGEQUALS(), and dozens of math/string helpers operate directly on JSON types.
  • No multi-container JOINs — You cannot JOIN two different containers in one query the way you JOIN two SQL tables. Data denormalization is required instead.
  • Undefined vs null — A field that does not exist on a document returns undefined, not null. You must check for both: WHERE IS_DEFINED(c.region).

Example query using Cosmos DB-specific syntax:

-- Flatten tags array and filter by tag value
SELECT c.id, c.title, t AS tag
FROM c
JOIN t IN c.tags
WHERE t = "azure"
  AND c.published = true
ORDER BY c.createdAt DESC
What does a JOIN in Cosmos DB NoSQL query actually do?
In Cosmos DB query, what does accessing a property that does not exist on a document return?
14. What is the Cosmos DB transactional batch API?

The transactional batch API is the way to execute multiple operations (up to 100) atomically on items that share the same partition key. Unlike stored procedures (which also provide ACID atomicity but require JavaScript and have size limits), the transactional batch runs from the client SDK and does not require any server-side registration.

A batch groups read, write, replace, delete, and patch operations together. The entire batch either commits or fails together — no partial success. If any single operation in the batch fails (e.g., a precondition check fails), the entire batch rolls back and the response contains which operation failed and why.

// C# example: atomic batch for same partition key "order-456"
TransactionalBatch batch = container.CreateTransactionalBatch(
    new PartitionKey("order-456"));

batch.CreateItem(new OrderItem { id = "item-1", orderId = "order-456", sku = "ABC" });
batch.ReplaceItem("order-456", new Order { id = "order-456", status = "processing" });
batch.DeleteItem("temp-hold-456");

TransactionalBatchResponse response = await batch.ExecuteAsync();
if (!response.IsSuccessStatusCode)
{
    // Check response[0].StatusCode, response[1].StatusCode, etc. for failure details
}

The batch API is the preferred way to handle multi-document transactions in modern Cosmos DB applications because it is cleaner than stored procedures, supports all SDK languages (no JavaScript constraint), and has a defined 100-operation limit per batch. It is ideal for patterns like: update an order header + insert multiple line items atomically, or implement optimistic concurrency by checking an item's ETag in a batch precondition before updating it.

The one constraint that matches stored procedures: all items in the batch must share the same partition key value. Cross-partition multi-document atomicity is not supported in Cosmos DB.

What is the maximum number of operations allowed in a single Cosmos DB transactional batch?
Can a Cosmos DB transactional batch include operations targeting items with different partition key values?
15. What is Cosmos DB Integrated Cache and how does it reduce RU consumption?

The Cosmos DB Integrated Cache is a server-side in-memory cache built into the dedicated gateway tier. When enabled, it caches the results of point reads and queries at the gateway layer so that repeated identical requests can be served from memory without going to the backend storage partitions — meaning those cached responses consume 0 RU/s.

This is fundamentally different from a client-side cache (like Redis). Client caches are application-managed: you maintain cache keys, TTLs, and invalidation logic in your code, and every new application instance starts with a cold cache. The Integrated Cache is managed by Cosmos DB itself, is shared across all clients connecting through the same gateway, and is warm for the first client that populates it.

How it works:

  1. A client sends a read request through the dedicated gateway.
  2. The gateway checks its in-memory cache for a matching item or query result.
  3. On a cache hit, the response is returned immediately — 0 RU consumed.
  4. On a cache miss, the backend is queried normally, the result is cached, and RU is charged as usual.

Cache invalidation is automatic: when an item is written or modified, its cached entry is invalidated. The cache respects the consistency level — if you use Session or Eventual consistency, the gateway may serve slightly stale responses (by design for those levels), which improves hit rates. Strong consistency is not compatible with the Integrated Cache.

The Integrated Cache requires using the dedicated gateway tier (not the direct connectivity mode) and is best suited for read-heavy workloads where the same data is requested repeatedly — leaderboards, product catalogs, configuration data, or user profiles with hot-spot access patterns.

How many RU/s does a Cosmos DB Integrated Cache hit consume?
Which consistency level is incompatible with the Cosmos DB Integrated Cache?
16. How does optimistic concurrency work in Azure Cosmos DB?

Cosmos DB uses ETags for optimistic concurrency control. Every item in Cosmos DB has a system-generated _etag property that changes on every write. When you read an item, you get its current ETag. When you want to update that item, you include the ETag in the write request using the If-Match HTTP header (or the SDK equivalent ifMatchEtag option). Cosmos DB compares your ETag against the item's current ETag on the server.

  • If they match — no one else has modified the item since you read it — the write succeeds and a new ETag is assigned.
  • If they do not match — someone else modified the item in between — the server returns HTTP 412 Precondition Failed and your write is rejected.

This prevents the lost-update problem in concurrent environments without holding any locks, which would block reads. The calling code is expected to handle the 412 by re-reading the item with its new ETag and re-applying the business logic before retrying the write.

// C# SDK example
ItemResponse<Product> readResponse = await container.ReadItemAsync<Product>(
    "product-42", new PartitionKey("electronics"));

Product product = readResponse.Resource;
string etag = readResponse.ETag;

product.Price = 29.99m;

try
{
    await container.ReplaceItemAsync(
        product, product.Id,
        new PartitionKey("electronics"),
        new ItemRequestOptions { IfMatchEtag = etag });
}
catch (CosmosException ex) when (ex.StatusCode == HttpStatusCode.PreconditionFailed)
{
    // Retry: re-read, re-apply business logic, retry write
}

ETags are also used in Change Feed processing — you can use the ETag to detect whether an item has changed since you last processed it, avoiding redundant processing of unchanged items.

What HTTP status code does Cosmos DB return when an optimistic concurrency ETag check fails?
What property on a Cosmos DB item stores the current ETag value?
17. What is hierarchical partition keys in Cosmos DB and when do you use it?

Hierarchical partition keys (also called sub-partitioning) allow you to define up to three levels of partition key paths on a container, forming a composite key like /tenantId/userId/sessionId. This feature, introduced in GA in 2023, solves the hot partition problem for multi-tenant or hierarchical data without requiring synthetic key concatenation.

With a single-level partition key on /tenantId, all data for one tenant lands in a single logical partition capped at 20 GB. A large enterprise tenant can blow through that limit quickly. With hierarchical partition keys on [tenantId, userId], data is first grouped by tenant then sub-partitioned by user, distributing the tenant's data across multiple logical partitions while still allowing single-partition queries scoped to a tenant.

How queries interact with hierarchical keys:

  • Providing all levels (e.g., tenantId = 'acme' AND userId = 'u123') routes to a single partition — cheapest.
  • Providing only the first level (tenantId = 'acme') does a partial partition key query — scans only partitions belonging to that tenant, not the whole container. Much cheaper than a full cross-partition fan-out.
  • Providing no partition key levels triggers a full cross-partition scan — most expensive.

This is the key difference from a flat synthetic key: with a synthetic key you would have to provide the exact concatenated value or do a full cross-partition query. Hierarchical keys let you efficiently query any prefix of the key hierarchy.

Use hierarchical partition keys when you have multi-tenant data, when a single partition key value risks hitting the 20 GB ceiling, or when you need both tenant-scoped and user-scoped query patterns to be efficient.

How many partition key levels can you define with hierarchical partition keys in Cosmos DB?
When you provide only the first-level value of a hierarchical partition key in a query, what happens?
18. What is the Cosmos DB Bulk Executor and how do you use bulk operations in the SDK?

Bulk operations in Azure Cosmos DB allow you to send multiple create, upsert, replace, delete, or read operations in a single SDK call that the library optimizes internally — batching by partition, retrying 429 throttles automatically, and maximizing throughput by saturating available RU/s concurrently. This is far more efficient than issuing individual operations in a loop because each individual await creates a round-trip overhead and underutilizes provisioned throughput.

In the v3 .NET SDK, bulk execution is enabled by setting AllowBulkExecution = true on the CosmosClientOptions. Once enabled, you can create a list of tasks and await them all together — the SDK transparently groups them into optimized batches per partition:

CosmosClient client = new CosmosClient(endpoint, key,
    new CosmosClientOptions { AllowBulkExecution = true });

Container container = client.GetContainer("mydb", "mycontainer");

List<Task> tasks = new List<Task>();
foreach (var item in itemsToUpsert)
{
    tasks.Add(container.UpsertItemAsync(item, new PartitionKey(item.PartitionKey)));
}

await Task.WhenAll(tasks);

Internally the SDK groups operations by partition key, packs them into micro-batches that fit within the 2 MB request limit and 100-operation transactional batch limit, and dispatches multiple batches concurrently. It handles 429 retries with the retry-after delay automatically so your code does not need to implement backoff logic manually.

For Java and Python SDKs, similar bulk APIs exist. In Java the CosmosBulkOperations builder pattern is used. Bulk mode is best for initial data loads, migrations, large backfills, or any scenario where you need to insert or update tens of thousands of items quickly.

How do you enable bulk execution mode in the Cosmos DB v3 .NET SDK?
What does the Cosmos DB SDK automatically handle in bulk mode that you would otherwise need to code yourself?
19. What are Cosmos DB triggers and user-defined functions (UDFs)?

Cosmos DB supports two additional server-side JavaScript constructs beyond stored procedures: triggers and user-defined functions (UDFs). Both run on the Cosmos DB compute engine but serve different purposes.

Triggers are JavaScript functions attached to a container that fire automatically before or after a write operation (create, replace, delete). There are two kinds:

  • Pre-triggers — Execute before the write is committed. Can modify the request (e.g., auto-populate a createdAt timestamp, validate field formats, generate a composite field). If the pre-trigger throws, the write is rejected.
  • Post-triggers — Execute after the write succeeds. Useful for updating aggregate documents, sending notifications, or maintaining denormalized data. Post-triggers run within the same transaction scope as the write.

Triggers must be explicitly listed in the SDK request options — they do not fire automatically unless you opt in per request. This is a common gotcha: unlike SQL database triggers, Cosmos DB triggers require the client to declare PreTriggerInclude or PostTriggerInclude on each write request:

await container.CreateItemAsync(item, partitionKey, new ItemRequestOptions {
    PreTriggers = new List<string> { "validateTimestamp" },
    PostTriggers = new List<string> { "updateUserAggregate" }
});

User-Defined Functions (UDFs) are JavaScript helper functions callable from within a Cosmos DB query using the udf. prefix. They let you extend the query language with custom computation:

-- Query using a UDF to categorize price ranges
SELECT c.id, udf.getPriceCategory(c.price) AS category
FROM c

UDFs cannot modify data — they are read-only transformations used in SELECT and WHERE clauses. They also have no access to external systems or the Cosmos DB context object (unlike stored procedures).

In Cosmos DB, do triggers fire automatically for every write like in traditional SQL databases?
What can a Cosmos DB User-Defined Function (UDF) do that a query expression alone cannot?
20. How does Cosmos DB handle conflicts in multi-region write (multi-master) setups?

When multi-region writes are enabled in Cosmos DB, any region can accept writes simultaneously. If two clients in different regions write to the same item at the same time, a write conflict occurs. Cosmos DB uses a deterministic conflict resolution policy to handle these without blocking either write.

Three conflict resolution modes are available:

Last-Write-Wins (LWW) — The default mode. Cosmos DB uses a timestamp-based comparison to determine the winner. By default it compares the _ts system property. You can configure a custom numeric property as the tiebreaker (useful if client-side timestamps are more reliable than server-assigned ones). The losing write is discarded.

Custom — Merge Procedure — You register a JavaScript stored procedure as the conflict resolver. When a conflict is detected, Cosmos DB calls the procedure with both conflicting versions. Your code decides the final merged state — useful for counter increments, array merges, or any domain where neither version should simply win over the other.

Custom — Async via Conflicts Feed — Cosmos DB writes all conflicting versions to a special conflicts feed container accessible via the SDK. Your application code processes conflicts asynchronously and uses the API to resolve each one. This is the most flexible mode — you can apply business rules, user notifications, or manual review workflows — but it adds latency between conflict detection and resolution.

In practice, the conflict rate in well-designed multi-region applications is very low if you partition data by region affinity (European users write to the European region, etc.). Conflicts only occur when the same item is written concurrently in two different regions, which is rare if your routing logic is sound.

In Cosmos DB multi-region write mode, which conflict resolution strategy is the default?
Which conflict resolution mode is best when two regions both increment a shared counter and neither value should be silently discarded?
21. What is the Cosmos DB Emulator and how is it used in development?

The Azure Cosmos DB Emulator is a locally running software that faithfully emulates the Cosmos DB NoSQL API on your development machine. It lets you develop and test Cosmos DB applications without an Azure subscription, without incurring costs, and with full offline capability. The emulator runs as a Windows application or as a Docker container (supporting Linux and macOS via Docker).

Starting the emulator via Docker is the most cross-platform approach:

docker pull mcr.microsoft.com/cosmosdb/linux/azure-cosmos-emulator:latest

docker run -p 8081:8081 -p 10251-10255:10251-10255 \
  -e AZURE_COSMOS_EMULATOR_PARTITION_COUNT=10 \
  -e AZURE_COSMOS_EMULATOR_ENABLE_DATA_PERSISTENCE=true \
  mcr.microsoft.com/cosmosdb/linux/azure-cosmos-emulator:latest

The emulator exposes the same REST endpoint as the cloud service at https://localhost:8081 and uses a well-known fixed key for authentication (the same key is documented publicly and is the same for every installation). Connection string:

AccountEndpoint=https://localhost:8081/;AccountKey=C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw==

Key limitations compared to the cloud service:

  • Only supports the NoSQL API — no MongoDB, Cassandra, or Gremlin emulation
  • No global distribution simulation
  • No SLA guarantees (performance is your local machine's)
  • The emulator certificate is self-signed — CI pipelines need to trust it explicitly
  • Supports up to 25 fixed containers with simulated partitioning

For integration tests in CI/CD pipelines, the emulator Docker image is commonly used in GitHub Actions or Azure DevOps pipeline steps, giving every pull request its own isolated Cosmos DB environment at zero cost.

Which Cosmos DB APIs does the local Emulator support?
What is the default HTTPS endpoint of the Cosmos DB Emulator?
22. What is Cosmos DB for MongoDB API and what version compatibility does it provide?

The Cosmos DB for MongoDB API is a compatibility layer that implements the MongoDB wire protocol, allowing applications written for MongoDB to connect to Cosmos DB by changing only the connection string. The application code — queries, aggregation pipelines, driver calls — does not change. Cosmos DB parses MongoDB BSON protocol messages and executes them against its own storage engine.

Version compatibility is important to check: Cosmos DB for MongoDB supports several MongoDB server versions (3.2, 3.6, 4.0, 4.2, 5.0, 6.0 as of recent updates). The supported version affects which operators and commands are available. For example, the $lookup aggregation stage (a join-like operation) was added in 3.6, and transactions became available in 4.0. When you create a Cosmos DB for MongoDB account, you select the server version that matches what your application targets.

Key differences from native MongoDB to be aware of in interviews:

  • Shard key = partition key — In Cosmos DB for MongoDB, the MongoDB shard key maps to the Cosmos DB partition key. All the same partitioning rules apply: high cardinality, even distribution, immutable after creation.
  • Index differences — Cosmos DB for MongoDB creates a wildcard index by default (indexes all fields). In native MongoDB, no indexes are created automatically except for _id. This means writes to Cosmos DB for MongoDB are slightly more expensive but all fields are queryable without explicit index creation.
  • Aggregation pipeline support — Not all pipeline stages are supported. $facet, $graphLookup, and some others have limitations or require specific server version selection.
  • Sharded transactions — Multi-document transactions are supported but are limited to a single shard (partition), consistent with Cosmos DB's single-partition atomicity model.
In Cosmos DB for MongoDB API, what does the MongoDB shard key map to?
How does Cosmos DB for MongoDB API handle indexes by default compared to native MongoDB?
23. What is the Cosmos DB analytical store and Azure Synapse Link?

The Cosmos DB analytical store is a fully isolated, column-oriented copy of your operational data maintained automatically by Cosmos DB, designed for analytical queries. When you enable it on a container, Cosmos DB automatically synchronizes every insert, update, and delete from the row-oriented operational store to the columnar analytical store in near real time — without consuming your provisioned RU/s and without impacting the operational workload.

The columnar format is critical for performance: OLAP queries that aggregate millions of rows but only read 3-4 columns scan far less data in a columnar store than in a row-oriented one. The analytical store is also schema-agnostic — it handles heterogeneous JSON documents by inferring a column-based representation automatically.

Azure Synapse Link is the integration layer that connects the Cosmos DB analytical store to Azure Synapse Analytics. With Synapse Link, you can run Apache Spark notebooks or serverless SQL Pool queries directly against the Cosmos DB analytical store — no ETL pipeline, no data movement, no separate data warehouse copy. The data is always current because the analytical store synchronizes in near real time.

# Synapse Spark reading from Cosmos DB analytical store
df = spark.read.format("cosmos.olap") \
    .option("spark.synapse.linkedService", "CosmosDbLink") \
    .option("spark.cosmos.container", "orders") \
    .load()

df.groupBy("region").agg(sum("amount").alias("total")).show()

Before Synapse Link, teams had to build nightly ETL jobs that exported Cosmos DB data to Azure Blob or Data Lake and then loaded it into Synapse — a pipeline with hours of lag and significant engineering overhead. Synapse Link eliminates this entirely, enabling what Microsoft calls HTAP (Hybrid Transactional/Analytical Processing).

Does enabling the Cosmos DB analytical store consume your container's provisioned RU/s for synchronization?
What problem does Azure Synapse Link solve compared to traditional ETL pipelines for Cosmos DB analytics?
24. What are Cosmos DB materialized views and how do they differ from containers?

Cosmos DB materialized views (in preview as of 2024) are automatically maintained read-only containers that are derived from a source container via a defined query or projection. When data changes in the source container, Cosmos DB updates the materialized view automatically and asynchronously — similar to how the analytical store works but for operational read patterns rather than analytical ones.

The problem they solve: Cosmos DB forces you to choose a single partition key per container. If your source container is partitioned by /userId (efficient for user-centric queries), a query like "find all orders for product X" becomes a cross-partition scan. Without materialized views, you have to either build a Change Feed processor that maintains a second container keyed by /productId, or accept the expensive cross-partition query.

With materialized views, you declare the derived container's partition key and projection, and Cosmos DB handles the Change Feed-based maintenance automatically:

// Source container: partitioned by /userId
// Materialized view: same data partitioned by /productId

{
  "materializedViewDefinition": {
    "sourceCollectionName": "orders",
    "definition": "SELECT c.id, c.productId, c.userId, c.amount FROM orders c",
    "partitionKey": { "paths": ["/productId"] }
  }
}

Key differences from a regular container:

  • Materialized views are read-only — writes go only to the source container.
  • They are automatically maintained — no Change Feed processor code required.
  • They may have a short lag between source write and view update (eventual consistency).
  • Storage and throughput for the view are billed separately.

Compared to manually maintaining a secondary container via the Change Feed, materialized views eliminate significant operational code and failure-handling complexity.

Can you write items directly into a Cosmos DB materialized view container?
What Cosmos DB feature was commonly used before materialized views to maintain a secondary container with a different partition key?
25. How does Cosmos DB pricing work and what are the key cost drivers?

Cosmos DB billing has three main components: provisioned throughput, storage, and additional features. Understanding each is essential for cost-effective application design.

1. Throughput cost — For provisioned throughput, you are billed per 100 RU/s per hour (around $0.008/hour per 100 RU/s in East US as of 2024). For autoscale, you pay for the maximum RU/s reached in any one-hour window. For serverless, you pay per million RU consumed. Throughput is the dominant cost for most workloads, making RU optimization the most impactful cost lever.

2. Storage cost — Charged per GB per month for the data stored in the container (both the document data and index storage). Index size can be significant — excluding unnecessary fields from the indexing policy reduces both write RU cost and storage billing.

3. Multi-region replication — Each additional read region multiplies your throughput cost. Writing to a 3-region account with provisioned 10,000 RU/s is billed as 30,000 RU/s equivalent. This is often the largest surprise in Cosmos DB bills for teams that add regions without considering the cost multiplier.

4. Additional features — The analytical store has separate storage pricing. Dedicated gateway has per-hour pricing per instance. Backup storage beyond the default 7-day point-in-time window incurs additional charges. Continuous backup (30-day or 7-day with point-in-time restore) costs more than periodic backup.

Cost optimization strategies:

  • Use autoscale instead of manual provisioning for variable workloads to avoid idle RU cost.
  • Reduce index size by excluding large text fields and rarely-queried properties.
  • Use TTL to auto-delete expired data rather than accumulating storage.
  • Leverage the Integrated Cache for read-heavy hot data to reduce RU consumption.
  • Keep cross-partition queries to a minimum — they consume RU proportional to the number of partitions.
If you add two additional read regions to a Cosmos DB account provisioned at 10,000 RU/s, what is the effective throughput you are billed for?
Beyond document data, what else contributes to Cosmos DB storage billing?
26. What is the Cosmos DB Gremlin API and what is it optimized for?

The Cosmos DB Gremlin API implements Apache TinkerPop's Gremlin graph traversal language, enabling you to model and query data as a property graph — a network of vertices (nodes) and edges (relationships), each of which can carry arbitrary key-value properties. This API is optimized for workloads where the relationships between data points are as important as the data points themselves.

Graph traversal queries with Gremlin look nothing like SQL. They navigate the graph step by step:

// Find friends of Alice who live in Seattle
g.V().has('person', 'name', 'Alice')
  .out('knows')                    // traverse outgoing 'knows' edges
  .has('city', 'Seattle')          // filter by city property
  .values('name')                  // return only the name property

Cosmos DB stores graph data using the same underlying infrastructure as other APIs — every vertex and edge is stored as a JSON document internally. The Gremlin API translates traversal steps into Cosmos DB read and partition-key-based lookups. The partition key for the Gremlin API is the vertex or edge's partition key property, and graph modeling decisions must account for it: if two frequently-traversed vertices live in different partitions, the traversal crosses partitions, increasing cost.

Common use cases for Cosmos DB Gremlin:

  • Social networks — Friend graphs, followers, mutual connections
  • Recommendation engines — "Customers who bought X also bought Y" modeled as a graph
  • Fraud detection — Detecting rings of related entities (shared phone numbers, addresses, devices)
  • Knowledge graphs — Ontologies, entity relationships for search
  • Network topology — IT infrastructure dependency graphs

If your data is naturally relational but not deeply connected (e.g., order → customer → address), the NoSQL API with embedded documents is usually simpler and cheaper. Use Gremlin when graph traversal is the primary query pattern.

Which query language does the Cosmos DB Gremlin API use?
What happens in Cosmos DB Gremlin when two frequently traversed vertices reside in different logical partitions?
27. How does Cosmos DB backup and restore work?

Cosmos DB offers two backup modes, selected at account creation and switchable in some scenarios: Periodic backup (the legacy default) and Continuous backup (the recommended modern option).

Periodic Backup — Takes full snapshots at a configured interval (default every 4 hours, configurable to 1 or 2 hours). Snapshots are replicated to Azure Blob Storage in at least two regions. Retention is configurable (default 8 hours / 2 backup copies). Restoring from periodic backup creates a new Cosmos DB account — you cannot restore in place. Restore initiation requires contacting Azure Support, which adds time. Periodic backup cannot restore to a specific point in time between snapshots.

Continuous Backup (Point-in-Time Restore) — Continuously captures all changes as they happen, stored in backup storage. You can restore to any point in the last 7 or 30 days (two tiers) with minute-level granularity. Restore is self-service via the Azure portal, CLI, or API — no Support ticket needed. This is the mode for production applications where RTO (Recovery Time Objective) matters.

How to restore using Continuous backup via CLI:

az cosmosdb restore \
  --account-name myRestored \
  --target-resource-group myRG \
  --source-account-name mySource \
  --restore-timestamp "2024-05-10T14:30:00Z" \
  --location eastus

Restore always creates a new account — it is not an in-place operation. After restore, you point your application's connection string at the new account, verify data integrity, and then update DNS or configuration to cut over. Restores can take minutes to hours depending on data size.

Backup storage costs are separate from operational Cosmos DB billing. Continuous backup with 30-day retention costs significantly more than periodic backup, but for production workloads the self-service restore capability justifies the cost difference.

Can you restore a Cosmos DB account in-place, overwriting the current account's data?
What is the key operational advantage of Continuous backup over Periodic backup?
28. What is the Cosmos DB Patch API and how does it differ from Replace?

The Patch API (partial document update) was introduced in Cosmos DB in 2022 to address a common inefficiency in document updates. Before Patch, the only way to modify a field in a Cosmos DB item was to read the full document, change the field in memory, and replace the entire document. For large documents or high-frequency partial updates this was wasteful — full read + full write = ~6x the RU cost of a targeted patch.

The Patch API lets you specify a list of operations to apply directly on the server without reading the document first. Supported patch operations:

  • add — Add a new property or array element at the specified path
  • set — Set a property to a value (creates if absent, overwrites if present)
  • replace — Replace an existing property (fails if the property does not exist)
  • remove — Delete a property
  • increment — Atomically increment a numeric property by a delta value
  • move — Move a property from one path to another
// C# Patch API example: update price and increment stock count atomically
PatchOperation[] patches = new[]
{
    PatchOperation.Set("/price", 24.99),
    PatchOperation.Increment("/stockCount", -1),
    PatchOperation.Add("/lastModified", DateTime.UtcNow)
};

await container.PatchItemAsync<Product>("product-42",
    new PartitionKey("electronics"), patches);

The increment operation is particularly powerful for counters — it is atomic at the document level, so concurrent increments from multiple clients do not race (unlike read-modify-replace which is a classic read-modify-write race condition). Patch also supports a condition parameter (a SQL WHERE-like filter) that makes the patch conditional — apply only if the document matches the filter, otherwise return a 412.

What is the main cost advantage of using the Cosmos DB Patch API over a full Replace operation?
Which Patch operation is best for atomically decrementing a stock counter without a read-modify-write race condition?
29. What is the Cosmos DB Cassandra API and how does CQL map to Cosmos DB concepts?

The Cosmos DB Cassandra API exposes Cosmos DB as a Cassandra-compatible data store using the Cassandra Query Language (CQL) wire protocol. Applications built on Apache Cassandra — using drivers like DataStax Java Driver, Python driver, or the gocql Go driver — can connect to Cosmos DB by changing the endpoint and credentials, without modifying application code.

CQL concepts map to Cosmos DB concepts as follows:

Cassandra API Concept Mapping
Cassandra ConceptCosmos DB Equivalent
KeyspaceDatabase
TableContainer
RowItem (document)
Partition KeyPartition Key
Clustering ColumnPart of the item schema (ordering within a partition)
Secondary IndexGSI / Cosmos DB index

Key behavioral differences from native Cassandra to know for interviews:

  • Consistency model — Cosmos DB applies its own 5-level consistency model. Cassandra consistency levels in CQL (LOCAL_QUORUM, ONE, etc.) are accepted by the API but mapped to the account-level Cosmos DB consistency setting, not enforced as true Cassandra quorum reads.
  • Lightweight Transactions (LWT) — Cassandra's IF NOT EXISTS and IF condition compare-and-swap operations have limited support in Cosmos DB Cassandra API. Full LWT support is not guaranteed.
  • Tunable throughput — Unlike Cassandra where you scale by adding nodes, Cosmos DB Cassandra uses RU/s provisioning. There is no concept of a Cassandra ring or token range management.
  • No compaction or repair — Cosmos DB manages its own storage internally. Cassandra operational tasks like nodetool compact or nodetool repair do not exist.
In Cosmos DB Cassandra API, what does a Cassandra Keyspace map to?
What happens to Cassandra consistency level settings like LOCAL_QUORUM when used with Cosmos DB Cassandra API?
30. How do you model one-to-many relationships in Cosmos DB?

Cosmos DB is a document database with no foreign key enforcement and no JOIN between containers, so one-to-many relationship modeling requires deliberate design decisions based on your access patterns. There are three main strategies, each with different tradeoffs:

1. Embedding (denormalization) — Store the "many" items directly inside the "one" parent document as an array. A blog post with its comments embedded:

{
  "id": "post-101",
  "title": "Cosmos DB tips",
  "comments": [
    { "id": "c1", "text": "Great post!", "author": "alice" },
    { "id": "c2", "text": "Helpful!", "author": "bob" }
  ]
}

This is ideal when the "many" side is small, always accessed with the parent, and not queried independently. One point read fetches everything. Avoid this when the array can grow unboundedly — it could approach the 2 MB per-item limit and degrade write performance as every comment addition rewrites the entire document.

2. Referencing with cross-container lookup — Store comments in a separate container with postId as the partition key. The post document contains only an ID reference. Query comments by WHERE c.postId = 'post-101'. Suitable when comments are numerous, independently paginated, or subject to independent TTL. The tradeoff: two operations to fetch a post with its comments.

3. Denormalized buckets (time-bounded embedding) — A hybrid that bounds the array size by grouping related items into "bucket" documents (e.g., one document per month of comments per post). Each bucket holds up to N comments, new buckets are created as limits are hit. More complex but avoids both the unbounded growth problem and the separate container overhead for read-heavy data.

The right model depends almost entirely on: how often the relationship is read together vs. independently, how large the "many" side can grow, and which side drives the query access pattern.

What is the primary risk of embedding an unbounded array of child items inside a parent document in Cosmos DB?
If comments are stored in a separate container partitioned by postId, what query pattern retrieves all comments for a given post efficiently?
31. What is the Cosmos DB free tier and what does it include?

The Cosmos DB free tier is a permanent (not time-limited) offering where every Azure account can have one Cosmos DB account with a perpetual free allocation, making it suitable for prototyping, side projects, and learning without ongoing costs.

The free tier allocation includes:

  • 1,000 RU/s provisioned throughput — always free, every month, no expiration
  • 25 GB of storage — always free, every month

This is enough for a small application with moderate load. For context: 1,000 RU/s can handle approximately 1,000 point reads per second, or roughly 200 writes per second for 1 KB documents. 25 GB covers millions of typical user profile documents.

Important constraints and conditions:

  • Only one free tier account per Azure subscription. You cannot have multiple free tier accounts in the same subscription.
  • Free tier must be selected at account creation — it cannot be applied to an existing paid account.
  • Resources beyond the free allocation (above 1,000 RU/s or 25 GB) are billed at standard rates. For example, if you provision 4,000 RU/s, you pay for 3,000 RU/s and the first 1,000 are free.
  • All APIs are eligible for the free tier — NoSQL, MongoDB, Cassandra, Gremlin, and Table.
  • Multi-region replication multiplies throughput costs as usual, even for the portion covered by free tier.

The free tier is different from the 30-day Azure free trial credits. Free tier credits are perpetual and apply to the Cosmos DB account specifically, continuing even after the trial period ends — as long as you stay within the 1,000 RU/s and 25 GB allocations, you pay nothing.

How many Cosmos DB free tier accounts can you have per Azure subscription?
What happens if you provision 5,000 RU/s on a free tier Cosmos DB account?
32. What is the Cosmos DB SDK and what are the key client configuration options?

The Azure Cosmos DB SDK is the official client library for interacting with Cosmos DB programmatically. Microsoft provides first-party SDKs for .NET, Java, Python, JavaScript/Node.js, and Go. Each SDK wraps the underlying REST API with connection pooling, retry logic, serialization, and Cosmos-specific patterns like bulk execution and change feed processing.

The root object in each SDK is the CosmosClient (or equivalent), which is expensive to initialize — it opens TCP connections to every data node and fetches the cluster routing table. CosmosClient should be created once per application lifetime and reused (singleton pattern). Creating it per request causes severe performance degradation and connection exhaustion.

Key configuration options on the client:

  • Connection mode: Direct (default for .NET/Java) — SDK opens TCP connections directly to backend data nodes, bypassing the gateway for data operations. Lower latency. Gateway — All requests go through the Cosmos DB HTTPS gateway. Compatible with restrictive firewalls, slightly higher latency.
  • Consistency level: Override the account-level default per client. You can only weaken (not strengthen) consistency per request.
  • MaxRetryAttemptsOnRateLimitedRequests: How many times to retry on 429 before surfacing an error to the caller. Default is 9.
  • RequestTimeout: Total timeout for a single operation attempt.
  • PreferredLocations: For multi-region accounts, the ordered list of regions to prefer for reads (nearest first for lowest latency).
  • AllowBulkExecution: Enables bulk batch optimization.
CosmosClient client = new CosmosClientBuilder(endpoint, key)
    .WithConnectionModeDirect()
    .WithApplicationPreferredRegions(new[] { "East US", "West Europe" })
    .WithBulkExecution(true)
    .WithConsistencyLevel(ConsistencyLevel.Session)
    .Build();
Why should CosmosClient be created once as a singleton rather than instantiated per request?
What is the difference between Direct and Gateway connection modes in the Cosmos DB SDK?
33. What is the Cosmos DB Table API and when would you migrate from Azure Table Storage to it?

The Cosmos DB Table API is a compatibility layer that exposes Cosmos DB as an Azure Table Storage-compatible endpoint. Applications using the Azure Table Storage SDK can point their connection string at a Cosmos DB Table API account and gain Cosmos DB's global distribution, SLA guarantees, and latency improvements without changing application code — only the connection string changes.

Azure Table Storage is Microsoft's original low-cost key-value store. It is cheap, simple, and sufficient for small workloads, but it has significant limitations compared to Cosmos DB:

Azure Table Storage vs. Cosmos DB Table API
AspectAzure Table StorageCosmos DB Table API
Latency SLANo P99 latency guarantee<10 ms P99 for reads and writes
Global distributionSingle region + GRS (read-only secondary)Multi-region active-active writes
ThroughputThrottled at the storage account levelConfigurable RU/s per table
ConsistencyStrong within a regionFive tunable consistency levels
Secondary indexesOnly PartitionKey + RowKeyAutomatic indexing on all fields
PricingLower for cold/rare accessHigher but with more guarantees

When to migrate: if your Table Storage application is experiencing slow P99 latencies, hitting throughput throttles, needing read replicas in multiple regions for global users, or requiring automatic indexing on fields other than PartitionKey and RowKey — Cosmos DB Table API directly solves all of these. The migration is operationally simple (connection string change) but the cost is higher than Table Storage, so evaluate whether the workload justifies the premium.

What do you need to change in an Azure Table Storage application to migrate it to Cosmos DB Table API?
What indexing limitation does Azure Table Storage have that Cosmos DB Table API resolves?
34. How does Cosmos DB handle security and access control?

Cosmos DB provides multiple layers of security: network isolation, authentication, and fine-grained authorization.

Network-level security: By default, Cosmos DB accounts accept connections from all networks. You can restrict access using:

  • IP firewall rules — Allowlist specific IP addresses or ranges
  • Virtual Network (VNet) service endpoints — Restrict to specific Azure VNet subnets
  • Private Endpoints — Use Azure Private Link to expose Cosmos DB on a private IP inside your VNet, blocking all public internet access

Authentication: Two models are available:

  • Primary/secondary account keys — 512-bit HMAC keys that grant full read-write or read-only access to the entire account. Simpler but less granular. Avoid hardcoding in application code; store in Key Vault.
  • Azure Active Directory (AAD) RBAC — Assign built-in or custom roles to AAD identities (users, service principals, managed identities). Preferred for production because keys can be rotated independently, access is granular per container, and there is a full audit trail in Azure Monitor.

Built-in AAD roles:

  • Cosmos DB Built-in Data Reader — Read-only access to data
  • Cosmos DB Built-in Data Contributor — Read-write access to data

Custom roles can be defined with granular permissions at the container level using the Azure RBAC JSON definition.

Encryption: All data is encrypted at rest using AES-256 by default (Microsoft-managed keys). Customer-managed keys (CMK) via Azure Key Vault are supported for compliance scenarios. All data in transit is encrypted with TLS 1.2+.

Managed Identities: The recommended pattern for applications running in Azure (VMs, App Service, Functions) is to use a system-assigned or user-assigned managed identity assigned the Cosmos DB RBAC role — no key management required.

What is the recommended authentication approach for an Azure App Service application connecting to Cosmos DB in production?
What Azure networking feature exposes Cosmos DB on a private IP inside your VNet, completely blocking public internet access?
«
»
MuleESB

Comments & Discussions