Skip to content

Contracts: detect breaking producer-schema changes across downstream pipelines before deployment #302

Description

@LouisDeconinck

Current state

Duckle already has:

  • per-pipeline schema/contracts and drift checks;
  • Git diffs/review;
  • a cross-pipeline asset catalog and downstream impact graph;
  • inferred schemas and lineage.

The remaining gap is using those together to determine whether a producer change will break downstream consumers.

Problem

A pipeline can validate in isolation while still breaking another pipeline.

Examples:

remove or rename a column
change VARCHAR to INTEGER
make a previously non-null field nullable
change decimal precision/scale
change a nested JSON shape
change the semantic meaning while retaining the name

For a large country/source portfolio, manually opening every downstream pipeline is not reliable.

Proposed solution

Add a Git/release-time compatibility check.

Example:

duckle contracts check --base main --head HEAD --json

For each changed produced asset:

  1. compare prior and candidate output contracts/inferred schemas;
  2. find direct and transitive downstream consumers;
  3. determine which consumers reference affected columns/types;
  4. report breaking, potentially breaking, and additive changes.

Suggested compatibility rules

Configurable defaults:

add nullable column                 compatible
remove referenced column           breaking
rename referenced column           breaking
type widening                      usually compatible
type narrowing                     breaking
non-null -> nullable               potentially breaking
nullable -> non-null               breaking for historical data unless validated
decimal precision/scale change     rule-based

Output

Example:

{
  "producer": "source.company",
  "change": "column_removed",
  "column": "legal_form_code",
  "consumers": [
    {
      "pipeline": "normalize.company",
      "node": "map_legal_form",
      "reference": "legal_form_code"
    }
  ]
}

Waivers

Allow a reviewed waiver with:

reason
owner
expiry
affected contract/change hash

A generic permanent “ignore all” switch would be unsafe.

Runtime use

The first implementation can be CI/release-only.

Optional runtime enforcement can later block publishing an incompatible asset.

Relationship to release promotion

Release activation should run this check against the currently active release and show the affected downstream graph.

Scope

This does not require a central hosted schema registry. Git + Duckle’s catalog/contracts are sufficient.

Acceptance criteria

  1. removing a consumed column identifies the exact downstream node;
  2. additive safe changes do not block by default;
  3. results are machine-readable;
  4. waivers are explicit, scoped, and auditable;
  5. the check can run without executing full production data.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

enhancementNew feature or request

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions