Skip to main content

Data Contract Specification

A data contract formalizes what producers promise consumers about a data asset: its structure, business rules, quality, service levels, security, and terms of use. OpenMetadata stores each contract as a Data Contract entity attached to one data asset, and checks the parts it can check each time the contract runs. This page describes every section of a contract, which assets support it, and what OpenMetadata actually checks. The JSON Schema for the Data Contract entity is in the OpenMetadata repository.

Supported Assets

Each asset has at most one contract of its own. Schema and quality sections depend on the asset type. Every supported asset type accepts semantics, security, SLA, and terms of use. A contract that sets a section its asset type doesn’t support is rejected with a 400 error that names the section. A second contract for an asset that already has one is also rejected.

Contract Sections

The following table summarizes what each section holds and whether a contract run checks it: Sections that aren’t checked document an expectation for consumers. OpenMetadata shows them on the contract, exports them, and passes them down from data products, but doesn’t evaluate them.

Contract Details

Terms of Use

The terms of use are Markdown text, shown as Terms of Service in the UI. Use them for allowed and disallowed uses, and for compliance requirements such as GDPR or HIPAA. The create API takes a Markdown string, and the stored contract returns it as termsOfUse.content.

Schema

The schema lists the columns (for tables and dashboard data models) or fields (for topics and API endpoints) the asset must have. Each entry uses the column format: name, dataType, and optionally dataLength, constraint, and description. A contract usually lists a subset of the asset’s columns. OpenMetadata checks the schema in two places:
  • When you save the contract: A column the asset doesn’t have, or a column listed twice, rejects the save. If the asset later drops a column, remove it from the contract schema before saving other changes.
  • When the contract runs: Each missing or duplicate column counts as a failure. A type that differs from the asset’s is reported but doesn’t fail the run.
Types match when they’re in the same family: What the check compares depends on the asset: Only top-level contract entries are checked. A contract entry matches a nested column or field by its name alone. The UI lets you select top-level columns only.

Semantics

Semantics rules check the asset’s metadata, such as whether it has an owner, a description, or a tier. Each rule has these fields: The UI rule builder offers these fields: Owners, Display Name, Description, Domain, Data Product, Tags, Glossary Term, Tier, Updated on, Updated by, Version, and Status. For Updated by, the Is Owner and Is Reviewer operators compare the last editor with the asset’s owners or reviewers. A rule passes only when its expression returns true. Rules are evaluated only when the contract runs. They don’t block edits to the asset. A skipped rule counts as passed.

Security

The security section records who should access the data and how: OpenMetadata doesn’t enforce the security section or check it against its own policies. It documents the agreement between producer and consumer.

Quality

The quality section links data quality test cases to the contract. It’s available only for tables. Select existing test cases on the table, or add a test from the contract form. When you save a contract with test cases, OpenMetadata creates a test suite for the contract and a pipeline that runs it. Each contract run triggers that pipeline. The run shows Running until the tests finish, then records how many passed. A test whose latest result is Failed or Aborted counts as a failure. To define quality rules in an ODCS file and have OpenMetadata create the test cases, see ODCS Import and Export.

SLA

A contract run doesn’t check SLA values. The run result has a slaValidation field, but OpenMetadata doesn’t fill it in. To check freshness or volume on a table, add test cases to the contract’s quality section, such as a tableCustomSQLQuery test that compares the latest update time with the current time, or a tableRowInsertedCountToBeBetween test.

Status and Approval

A contract’s entityStatus is one of Draft, In Review, Approved, Rejected, Deprecated, or Archived. The status is separate from the result of each run.
  • Creating in the UI: The Contract Details tab has a Status field with Draft, In Review, and Approved. New contracts default to Draft.
  • Changing the status: Edit the contract, or update entityStatus through the API. OpenMetadata has no built-in approval workflow for data contracts.
  • Reviewers: When a contract has reviewers, only a reviewer (or a member of a reviewer team) can move it from In Review to Approved or Rejected, or delete it while it’s In Review.
  • Data products: An asset inherits a data product’s contract only when that contract is Approved. See Data Product Inheritance.

Running a Contract

A contract run checks the schema, semantics, and quality sections and stores the result. Runs start in three ways:
  • Run now: On the asset’s Contract tab, open the actions menu and select Run now.
  • API: POST /v1/dataContracts/{id}/validate, or POST /v1/dataContracts/entity/validate for an asset’s effective contract. See Validate & Results.
  • Schedule: The Data Contract Validation application runs every contract daily at midnight by default. Change its schedule under Settings > Applications.
A run ends with one of these statuses: The Contract tab shows each section’s result and an Execution History chart of past runs, 30 days by default. When the latest run is Failed, Aborted, or Running, the asset’s header shows a button that opens the contract.

Data Product Inheritance

A data product can have its own contract with semantics, security, SLA, and terms of use. Its assets inherit that contract when both of these are true:
  • The asset belongs to exactly one data product. An asset in several data products inherits nothing.
  • The data product’s contract is Approved.
What an asset gets depends on whether it has its own contract: Schema and quality are never inherited. Inherited sections and rules are marked Inherited in the UI, and aren’t editable from the asset. Selecting Edit on an inherited contract creates a new contract for the asset. An inherited contract can’t be deleted from the asset. Running an inherited contract creates a contract for the asset to store its results. The run uses the data product’s rules.

Import and Export

Contracts can move in and out of OpenMetadata in two formats:
  • OpenMetadata YAML: The contract’s own format, shown in the contract’s YAML view. Use Export and Import in the actions menu, or Import OM when the asset has no contract.
  • ODCS: The Open Data Contract Standard. Use Export as ODCS and Import ODCS. See ODCS Import and Export for what carries over.

Data Contract YAML Example

This example is a contract for a table in the OpenMetadata YAML format. It’s the format Import accepts and the POST /v1/dataContracts API takes as JSON.

Creating Data Contracts

Create data contracts in the OpenMetadata UI.

ODCS Import and Export

Import and export contracts in the Open Data Contract Standard format.