23. Hands-On Lab: Design Indexes for an Order API

Assume an order API supports these operations:

  • Fetch the newest orders for one customer.
  • Fetch delivered orders newest first.
  • Find an order by its unique order number.
  • Find all orders within a date interval.
  • Expire temporary sessions after a retention period.

Propose indexes for each operation, but do not blindly create every candidate. Some query patterns may share a compound index; others may need separate indexes. The order number may require a unique index if the business rule says it is unique.

After creating candidate indexes, run explain with realistic parameters and compare keys examined, documents examined, returned count, and latency. Then consider write overhead and whether every index is justified.

Check constraints before running

The unique index requires existing orderNumber values to be unique and present according to your intended policy. The TTL index requires a suitable date field. Treat these as candidate designs, not universal recommendations.

Code Example
db.orders.createIndex({ customerId: 1, createdAt: -1 });
db.orders.createIndex({ status: 1, createdAt: -1 });
db.orders.createIndex({ orderNumber: 1 }, { unique: true });
db.sessions.createIndex({ expiresAt: 1 }, { expireAfterSeconds: 0 });

// Validate a key query.
db.orders.find({ customerId: 501 })
  .sort({ createdAt: -1 })
  .limit(20)
  .explain("executionStats");
Key Takeaways
  • Map each index to a specific API query.
  • Reuse compound prefixes when the query shape aligns.
  • Unique and TTL indexes enforce special behaviors.
  • Validate existing data and measure every candidate.
Knowledge Check

What must be checked before creating a unique index on orderNumber?