Skip to content

Check Contract Compatibility

As a contract evolves, its version should reflect the actual scope of change — a breaking removal shouldn’t ship as a patch. ContractCompatibility compares two parsed versions of the same contract (matched by id) and classifies the difference.

import com.invaract.contract.ContractCompatibility
val report = ContractCompatibility.diff(previousContract, nextContract)
report.requiredLevel // Patch | Minor | Breaking
report.isBreaking // true iff any Breaking change is present
report.changes // every detected change, each tagged with a level and a path
ChangeLevel
Dataset removedBreaking
Dataset addedMinor
Dataset location changedBreaking
Field removedBreaking
Optional field addedMinor
Required field added (no default)Breaking
Field type changedBreaking
Field changed optional → requiredBreaking
Field changed nullable → non-nullableBreaking
Contract id changedBreaking
The inputs an output is built from (derivedFrom, or every input when unset) changedBreaking
val problems = ContractCompatibility.verifyVersionBump(previous, next)
// Nil if the bump is consistent with (or more conservative than) the diff;
// otherwise, human-readable messages naming the required bump level.

This is the check a CI pipeline would run on a pull request that modifies a contract file — catching, for example, a breaking schema change released as a PATCH version bump, before it ships.

This is a contract-module concern, independent of Spark — it works on two parsed Contract values, with no transformation or plan involved. It’s the mechanism a contract-driven CI check would call against a diff of a contract file across two commits.