Skip to main content

Contracts and Data Workshop

Retrieval Prompts

  1. State the database-per-service rule in one sentence.
  2. Name three legitimate alternatives to a shared database.
  3. Name the three contract shapes and one discipline that applies to all of them.
  4. State the consumer-driven contract testing loop in order.
  5. Name three safe and three breaking changes for a sync API.

Compare and Distinguish

Separate these pairs clearly:

  • API composition vs CQRS read model vs event-carried state transfer
  • sync API contract vs event contract
  • producer-owned contract vs consumer-owned contract
  • backward compatibility vs forward compatibility
  • tolerant reader vs strict reader

Common Mistake Check

For each statement, identify the error:

  1. "Different services use different schemas in the same database, so it is not a shared database."
  2. "We have OpenAPI specs so our contracts are enforced."
  3. "The provider writes the contract tests because they own the API."
  4. "Events don't need schemas because they are fire-and-forget."
  5. "We added a required field -- consumers will just start sending it on the next deploy."

Mini Application: End-to-End Contract

Using the decomposition from practice page 01 (or the e-commerce example), pick one cross-service interaction. For example: Orders publishes OrderConfirmed for Inventory and Fulfillment to consume.

Produce all of the following. Budget: 60 minutes.

1. Owned-Data Table

ServiceDatabaseOwned aggregatesConsumes (via events/sync)

Fill at least 4 rows.

2. Sync API Contract (OpenAPI Fragment)

Write a minimal OpenAPI fragment for one endpoint used in the interaction. Include:

  • one path with one method
  • request parameters (path, query)
  • two response codes (success + one failure)
  • at least one reusable components/schemas block with 4+ fields

Example skeleton:

openapi: 3.0.3
info: { title: X API, version: "1.0.0" }
paths:
/orders/{id}:
get:
parameters: [ ... ]
responses:
"200": { content: { application/json: { schema: { $ref: ... } } } }
"404": { description: Not found }
components:
schemas:
Order: { type: object, required: [...], properties: { ... } }

3. Event Schema (JSON Schema)

Write a JSON Schema for the matching async event. Include:

  • event_id, event_version, occurred_at
  • domain payload with at least 4 fields
  • required list
  • a nested object or array for a realistic domain shape

4. Compatibility Rules

List:

  • three safe additions for each contract
  • two breaking changes for each contract
  • one expand-contract plan for renaming a field (phases: expand / migrate / contract)

5. Consumer-Driven Contract Test Specification

For one consumer (say, Inventory reading from Orders), specify:

  • consumer and provider names
  • provider state ("given order 123 is confirmed")
  • request (method, path)
  • expected response (status, representative body)
  • the three expectations that, if broken on the provider, should fail this test

6. Cross-Service Data Pattern Choice

For three cross-service reads in your decomposition, classify each as:

  • API composition
  • CQRS projection
  • Event-carried state transfer

Justify each choice in one sentence.

Evidence Check

This page is complete only if you can:

  • show an OpenAPI fragment that would compile in a linter
  • show a JSON Schema that validates at least one example event
  • state a breaking-vs-safe classification from memory for 5 changes
  • sketch a Pact-style consumer test without looking at the concept page
  • reject any proposed design that has a shared OLTP table

If any of those are missing, redo the relevant section.