Home
service:
name: payments-api
version: 2.1.0
owner: { team: payments, dri: alice }
interfaces:
- name: rest-api
type: http
port: 8080
dependencies:
- ref: oci://ghcr.io/acme/auth
compatibility: "^2.0.0"
runtime:
state: { type: stateful }
health: { path: /health }
One file, checked and shipped
Everything above is validated (structure, cross-references, semantics and policy), versioned with semver, and distributed as an OCI artifact.
What is Pacto?¶
Pacto (/ˈpak.to/ — Spanish for pact) captures everything a platform needs to know about a service — interfaces, runtime behavior, dependencies, configuration, and scaling — in one YAML file that machines can validate and tooling can consume.
Pacto doesn't invent a new configuration language. An interface is a JSON Schema, OpenAPI spec or protobuf definition you already maintain — Pacto composes the interfaces you already have instead of redefining them. On top of that it adds what no single schema can express: how interfaces relate, what they depend on and how they change over time. JSON Schema describes an interface; Pacto describes the relationships between interfaces and how they change over time.
Pacto is a runtime contract system made of three complementary pieces:
- CLI — author, validate, diff, explain, and publish contracts
- Dashboard — explore contracts, dependency graphs, versions, readiness and diffs visually
- Kubernetes Operator — verify that live runtime remains faithful to the contract
No runtime agents. No sidecars. No new infrastructure. The CLI runs at build time and CI time. The dashboard and operator extend the same contracts into exploration and runtime verification.
AI-native contracts¶
Pacto contracts are machine-readable by design. Beyond platforms and CI pipelines, they can be consumed directly by AI assistants through the Model Context Protocol. Running pacto mcp starts an MCP server that exposes contract-aware tools — allowing assistants like Claude, Cursor, and GitHub Copilot to generate, edit and validate contracts and surface improvement suggestions. See the MCP Integration guide.
The problem¶
Today, a cloud service is described across six different places — none of which talk to each other:
OpenAPI spec → describes the API, but not the runtime
Helm values → describes deployment, but not the service
env vars → documented in a wiki (maybe), validated never
K8s manifests → hardcoded ports, guessed health checks
Dependencies → tribal knowledge in Slack threads
README.md → outdated the day it was written
The consequences:
- Platforms guess service behavior. Is it stateful? What port? Does it need persistent storage?
- Dev ↔ Platform friction. Developers ship code; platform engineers reverse-engineer how to run it.
- Breaking changes detected too late. A port change or removed dependency breaks production, not CI.
- No dependency visibility. No one knows what depends on what until something breaks.
The solution: one operational contract¶
Pacto replaces those six fragmented sources with the single file shown at the top of this page — interfaces, dependencies, runtime behavior, configuration and scaling — validated by tooling and versioned in a registry. Only pactoVersion and service are required; every other section is opt-in, so a contract stays as small as the service needs.
See the contract reference for every field, including the readiness section (requires pactoVersion: "1.2").
When should I use Pacto?¶
Pacto earns its keep when operational knowledge is scattered, implicit, or outdated:
- You manage many services and discover their runtime needs in production — Pacto makes every service self-describing up front, not reverse-engineered from Helm charts.
- Runtime assumptions live in deployment configs — Pacto separates what a service is from how it's deployed.
- Dependencies are undocumented — declare them once;
pacto diffshows the full blast radius (every service transitively affected) before a change ships. - CI can't catch operational breaking changes — a changed port or a removed health endpoint is caught when contracts are validated and diffed in the pipeline.
- Onboarding is slow — a developer runs
pacto init, fills in the contract, and pushes; the platform has everything it needs to provision the service.
How it works — 30 seconds¶
1. Developer writes a pacto.yaml alongside their code
2. pacto validate checks it (structure, cross-references, semantics, policy)
3. pacto push ships the contract to an OCI registry as a versioned artifact
4. pacto dashboard explores contracts, graphs, versions, and diffs visually
5. The Kubernetes operator verifies runtime stays faithful to the contract
The real value of Pacto appears across the full loop: author → validate → publish → explore → verify at runtime.
What's inside a Pacto bundle¶
graph LR
subgraph Bundle["Pacto Bundle"]
direction TB
YAML["pacto.yaml<br/><i>required</i>"]
subgraph Sections["Contract Sections <i>(all optional)</i>"]
direction TB
Interfaces["Interfaces<br/>HTTP · gRPC · ports · visibility"]
Dependencies["Dependencies<br/>oci://auth:2.0.0 · oci://db:1.0.0"]
Runtime["Runtime<br/>state · health · lifecycle · scaling"]
Config["Configuration<br/>schema.json"]
Policy["Policy<br/>schema.json"]
end
subgraph Extras["Metadata <i>(optional)</i>"]
direction TB
Docs["docs/<br/>README · runbooks · guides"]
SBOM["sbom/<br/>SPDX · CycloneDX"]
Skills["skills/<br/>agent domain knowledge"]
end
YAML --> Sections
end
Bundle -- "pacto push" --> Registry["OCI Registry<br/>GHCR · ECR · ACR<br/>Docker Hub"]
A bundle is a self-contained directory (or OCI artifact): pacto.yaml (required) plus optional interfaces/, configuration/, policy/, docs/, sbom/ and skills/ directories. These are schemas you already maintain — an OpenAPI spec, a JSON Schema for your config — composed into the bundle rather than rewritten in a Pacto-specific format; pacto.yaml adds the relational layer around them (dependencies, compatibility, runtime semantics). Validation enforces that every referenced file exists within the bundle. See the contract reference for the full bundle layout.
Key capabilities¶
- 4-layer validation — structural (JSON Schema), cross-field (port references, interface names), semantic (state vs. persistence consistency), and policy enforcement
- Breaking change detection —
pacto diffcompares two contract versions field-by-field and resolves both dependency trees to show the full blast radius - Dependency graph resolution — recursively resolve transitive dependencies from OCI registries; sibling deps are fetched in parallel
- OCI distribution — push/pull contracts to any OCI registry (GHCR, ECR, ACR, Docker Hub, Harbor); bundles are cached locally for fast repeated operations
- Plugin-based generation —
pacto generateinvokes out-of-process plugins to produce deployment artifacts from a contract - Rich documentation —
pacto docgenerates Markdown with architecture diagrams, interface tables, and configuration details - SBOM diffing — optional SPDX or CycloneDX SBOM inclusion with automatic package-level change detection on
pacto diff - Contract exploration dashboard —
pacto dashboardlaunches a web UI for navigating contracts, dependency graphs, version history, interface details, configuration schemas, readiness and diffs across local, OCI, and Kubernetes sources - Runtime fidelity verification — the optional Kubernetes Operator continuously checks that deployed services match their contracts — port alignment, workload existence, health endpoint reachability, and more
- AI assistant integration —
pacto mcpexposes contract create, edit, validate and schema operations as MCP tools for Claude, Cursor and GitHub Copilot
See it in action¶
Detect breaking changes — with full dependency graph diff¶
$ pacto diff oci://ghcr.io/acme/payments-api-pacto:1.0.0 \
oci://ghcr.io/acme/payments-api-pacto:2.0.0
Classification: BREAKING
Changes (4):
[BREAKING] runtime.state.type (modified): runtime.state.type modified [stateless -> stateful]
[BREAKING] runtime.state.persistence.durability (modified): ... [ephemeral -> persistent]
[BREAKING] interfaces (removed): interfaces removed [- metrics]
[BREAKING] dependencies (removed): dependencies removed [- redis]
Dependency graph changes:
payments-api
├─ auth-service 1.5.0 → 2.3.0
└─ postgres -16.0.0
Version upgrades, added services, removed dependencies — all visible in one command, with the exit code gating deployments in CI. pacto graph renders the full resolved dependency tree the same way.
Who is Pacto for?¶
Developers¶
Define your service's operational interface alongside your code. Declare interfaces, configuration schema, health checks, and dependencies. Validate locally before pushing. Learn more
Platform engineers¶
Consume contracts to generate deployment manifests, enforce policies, detect breaking changes, and build dependency graphs — deterministically and automatically. Learn more
Building a platform on Pacto?¶
These primitives compose into reusable platform patterns — root + component contracts for monorepos, infrastructure contracts with provisioner metadata, configurations as composable claims, platform-published policy + schema bundles, progressive policy versioning, and per-environment override files. See Composition Patterns.
What Pacto is not¶
- Not a deployment tool — it describes what to deploy, not how
- Not another configuration language — an interface is a JSON Schema, OpenAPI or protobuf definition you already own; Pacto composes those rather than replacing them
- Not a registry — it uses existing OCI registries (GHCR, ECR, ACR, Docker Hub)
- Not a service catalog — it produces the structured data that a catalog (Backstage, Port, Cortex) could consume
See the Manifesto for the full positioning and rationale.
Pacto is a runtime contract system that tells platforms, pipelines and AI agents what a service is — and whether it still matches what was declared.