Skip to main content

Source contract

Hephaestus may review work against a practice only from evidence with explicit semantics. Contract 3.0.0 defines the logical source catalog, its capture states, and how well each source must be captured. A folder index records what was supplied to one run. It does not prove that a practice is empirically observable.

If any required evidence clause is unsatisfied, refuse the review and create no result. A source failure is never DOES_NOT_APPLY, a strength, or evidence that desired behavior is absent.

One frozen job folder​

The worker renders permitted database records in one read-only repeatable-read transaction. Integration-owned projections and history visibility checks remain the authorization boundary. The folder index records capture facts separately from practice readiness and typed source refusals. Another repository's records cannot make a missing primary source ready. The workspace ABI owns paths, quote coordinates, transfer budget and retention.

Contract boundary​

The contract separates three identities:

  1. Source catalog: logical source kinds and their authority, identity anchoring, completeness, required capture quality, privacy, and absence-state semantics.
  2. Practice definition: the events a review selects and the evidence that review requires before it may run at all. A source declares the item kinds it applies to, so the catalog constrains which sources a practice may name.
  3. Folder index: the state, provenance facts, and captured files for one invocation.

A practice's reads.sources decide readiness, not staging. Every source permitted for the workspace and purpose is rendered for every review, whether or not a practice named it. Practice criteria and the reviewing model decide relevance. Relevance is not a reason to withhold data from the model. A required source that did not arrive withholds the selected practice.

A COMPLETE need bounds what a result can assert is absent. Neither cuts the sandbox down.

Paths are materializations, not source identities. Prompts, practice files, task envelopes, runner code, model settings, and executables are invocation inputs and require separate evaluation provenance.

Runtime components must reference the exact contract version and catalog digest they implement. Inputs outside the catalog cannot satisfy a practice requirement.

This contract governs automated-review evidence, not every file used by the separate Mentor conversation runtime. Mentor inputs remain subject to Mentor consent and integration controls and cannot support an automated practice review. Reusing one for review requires registering it as a source kind first.

Source vocabulary​

Authority and identity​

AuthorityMeaning
UPSTREAM_SNAPSHOTContent captured from an upstream object.
SYNCHRONIZED_MIRRORA local projection whose currentness depends on upstream synchronization.
DETERMINISTIC_DERIVATIONA deterministic transform of declared dependencies.
LOSSY_DERIVATIONA sample, excerpt, aggregation, heuristic, or other information-losing transform.

A source's authority constrains what it may claim. Only a capture anchored to an immutable upstream identity can declare PINNED_IDENTITY. A SYNCHRONIZED_MIRROR reflects state that moves independently of the capture. A LOSSY_DERIVATION can never claim completeness. Both rules are enforced in SourceContract's constructor, so a catalog that breaks either one fails at startup.

A database row is not automatically authoritative for the current state of GitHub, GitLab, Slack, or Outline.

Required capture quality​

Required capture quality is a fact about the source, recorded once in the catalog as requiredQuality. Each practice that names the source does not restate it.

ValueMeaning
ANY_CAPTUREThe capture must have succeeded. Whatever it holds, including nothing, is reviewable.
COMPLETEThe capture must cover the whole selected scope. A fragment cannot ground a judgment about the whole.
COMPLETE_AND_NON_EMPTYComplete, and containing something.

The three values form a ladder, not two independent booleans. The fourth cell of the cross-product, non-empty but possibly partial, asserts something no source can support. A partial capture that contains something cannot rule out that the omitted part mattered.

A source that cannot report COMPLETE may not demand it, and a source that can never be validly empty may not demand non-emptiness. Both are rejected when the catalog is read, so a requirement that would refuse every review permanently cannot be stated.

Privacy classes​

Privacy class describes risk. It does not authorize collection, disclosure, or model egress.

ClassScopeMinimum treatment
INTERNALNon-public project or workspace content without person-level review resultsWorkspace authorization and purpose-bound retention
PERSONALUser-linked project content, authorship, reviews, comments, or activityPersonal-data access, export, and erasure coverage
SENSITIVE_PERSONALPrivate conversations or derived person-level review resultsRestricted audience and stricter disclosure and retention controls

Each catalog source references separate source-use decisions whose purposes are machine-enforced. Capture requires AUTOMATED_PRACTICE_REVIEW. Result persistence, delivery, and contributor evidence APIs require PRACTICE_FEEDBACK_DELIVERY. Mentor reuse requires CONVERSATIONAL_MENTORING.

And workspace-admin evidence review requires OPERATOR_EVIDENCE_REVIEW. Processor, region, transfer, and model-egress controls remain separate deployment obligations. A source allowed in an internal mirror is not thereby allowed in an external model request.

Source catalog​

The machine-readable catalog, its adjacent JSON Schemas, and the checks in gate:contracts jointly define conformance. Schema validation alone is insufficient. Standard JSON Schema uniqueItems compares whole values, not a selected identity property. The validation checks separate resource validation and digest checks from the server's catalog and governance checks.

Prose does not maintain a second field-by-field catalog. Authoring tools resolve source kinds through the catalog and reject unknown kinds. A source declares the item kinds it applies to, so a practice on one kind of work can only name sources that suit it.

The constraints with direct authoring consequences are:

  • Only sources anchored to an immutable upstream identity — the pull-request diff and the repository tree — declare PINNED_IDENTITY. Every mirrored source, including the pull-request and issue records themselves, has identity policy NOT_APPLICABLE. A source's authority decides whether it can anchor at all. A SYNCHRONIZED_MIRROR reflects upstream state that moves independently of the capture. Calling it pinned would describe a copy that has drifted as demonstrably current.
  • A LOSSY_DERIVATION cannot satisfy COMPLETE. It is a bounded summary of its subject, not the subject itself. It cannot answer "is all of it here?". An author who asserts an absence asks exactly this question. Linked-work number extraction cannot establish that it found every relationship. Outline renders every permitted mirrored document and can report COMPLETE for that mirror scope, not upstream currentness.
  • Three sources cannot be logically empty — the pull-request, issue, and document core records. Every other source may be validly empty.
  • The checks source (scm.pull-request.checks) carries head_checks, head_check_runs, and merge_state_status in checks.json. The core record carries none of these fields. It carries head_check_runs only when a read listed them for that head. An absent field means that the runs are unknown, not that the head has no runs. A practice that needs the runs and cannot read them returns Could not determine, never Not met. A run with finished: false has no result. A claim that depends on its outcome is Could not determine, and admission refuses a citation of it (unfinished_run_cited). A run list never proves that a run is absent, because a provider can add runs after the read. complete: true says only that the read listed every run the provider knew at observed_at. limitation: AWAITING_APPROVAL says that the CI waits for a maintainer to approve it, so it has not run. Then head_checks is PENDING, whatever the provider's rollup says. A result can cite only the listed runs, with the state that they show at observed_at. GitHub supplies check runs and commit statuses. GitLab supplies none yet, because its pipeline hooks cannot show which runs finished. Slack threads and Outline documents have no check runs. The sync lifecycle owns how the runs are read.
  • The review discussion source (scm.review-threads) carries review_decision in review_threads.json. The core record carries no aggregate review decision.
  • Two cannot be partial: the pull-request diff and the document core record. An available diff is also pinned. Its requiredQuality is COMPLETE: a verified empty range is available evidence. Each practice still needs its own review selection and supported result. Capture readiness assigns neither applicability nor an outcome. Missing, failed or incomplete required captures remain unready.

ENGINEERING_BASELINE with ENGINEERING_APPROVED records maintainer approval of the shipped, minimized product scope. Contract 1.3.0 records explicit maintainer engineering approval of the wider permitted workspace scope in #1732. It is not controller or DPO approval. A later expansion of source, purpose, audience, processor, retention policy or collection scope needs its own decision.

It is also the only basis and outcome the contract can express. A use nobody approved carries no decision, not a recorded refusal. Thus, no entry here can read as a controller sign-off. The controller's own record remains separate. Approval is the gate that runtime configuration cannot waive: a source whose decision is missing or expired is never read, whatever the deployment sets.

Within that boundary, a connected workspace integration and an enabled practice authorize the everyday code sources that the product reads. Thus, a default deployment reviews pull requests, issues, and conversations without further configuration.

Privacy class does not gate collection — it records what treatment a source needs.

Changing a source's meaning, selection scope, limit, mapping, identity policy, required capture quality, dependency, or normalization requires a new contract version. Contract 1.2.0 introduced a checkout with Git history reachable from the reviewed commit, plus mirrored branches and tags. The source's governance and retention policies apply. The reviewed commit and tree identify the checkout. The folder index also digests the repos/reviewed/.git/HEAD and captured-refs witnesses, which pin the exported refs — those can change between two captures of the same commit.

Capture state​

Source absence is separate from quality so the folder index does not collapse unavailable, partial, and empty evidence into one state.

Availability​

  • AVAILABLE: capture facts and logical content state are present.
  • NOT_COLLECTED: no unexpired use decision permits the source for this purpose, or collection is switched off for it in this deployment. Never "no practice wanted it". Every source that applies to the item kind is staged for every review. Relevance is not a reason a source can be missing.
  • UNAVAILABLE: the source could not be retrieved for a non-error reason.
  • REDACTED: the entire source was withheld for privacy or security.
  • COLLECTION_ERROR: an attempted collection failed.

A non-available source contains no captured files or source identifiers, and carries a typed SourceAbsenceReason saying why — GOVERNANCE_NOT_EFFECTIVE, NO_PROVIDER, NO_WORKING_COPY, CONSENT_NOT_ACTIVE, and the rest. Safe, typed reason codes may be role-filtered. Free-form exception text must not enter the folder index.

Available-source dimensions​

Only AVAILABLE has:

  • logical content: EMPTY or NON_EMPTY.
  • completeness: COMPLETE, PARTIAL, or UNKNOWN.
  • capture facts: capturedAt — the only required one — plus an optional observedAt, an optional sourceEffectiveAt watermark, and an optional pinned identity.
  • captured files.

Capture facts hold only what could not be known before the capture ran. The folder index pins the catalog by digest. Everything derivable from that catalog is read from it, never copied into the capture. This includes selection scope, limits, required capture quality, and states a source can report.

Logical content is independent of serialized bytes: a JSON file containing [] represents an EMPTY source. Field-level redaction remains an available, usually partial source. Whole-source redaction uses REDACTED.

Source age alone cannot prove currentness. An age threshold needs a watermark recording when a copy was last verified against upstream. The mirror records only when a row was last written. An age derived from it measures time since the last upstream change. It reports a correctly mirrored quiet record as stale and a record modified moments ago as current. Adding one therefore has a prerequisite: a reconciliation pass that advances a verified-as-of watermark after confirming a record is unchanged.

Until that watermark exists, the system cannot substantiate a currentness guarantee on a mirrored source. IdentityPolicy records only whether a capture can be anchored to something immutable at all.

A readiness report names the contract version and the catalog digest used to interpret it. It names the item kind, the folder index's capture time, and one decision per practice. A folder index captured under a contract version the runtime no longer ships is unreplayable, not invalid. The recorded result stands. Only the ability to re-derive it is unavailable.

Practice definition and source requirements​

A practice version owns one authored definition. Reads contains the source contract and declared source needs. Reviewed by controls automated, human or guidance-only behavior and retains its reason and limits. Review on selects automatic events and state. Applies when checks every review origin.

The review pipeline owns applicability checks and capture refusal behavior.

SCM capture retains the pinned base, head, changed paths and unified diff in the captured change record of the job context. Changed paths include both names of a rename. Applicability reads these captured facts without access to the repository mirror. The practice's item kind is explicit and need not have an event.

NeedMeaning
REQUIREDThe review needs this source at its declared capture quality. Failure withholds the result.
COMPLETEThe claim needs complete source capture. A fragment cannot establish bounded absence.
OPTIONALThe review uses the source when available and records its absence as a limitation.

Scope and consent determine whether the material can be collected. The selected About role must resolve to one eligible account, unless About is explicitly null. Feedback mode Off stops delivery at every destination, not result recording. A request bypasses event selection but never authorization or readiness. The pipeline owns those boundaries.

Conservative examples​

Required evidence is insufficient​

scope-one-reviewable-change is bound to scm.pull_request.opened and scm.pull_request.ready, and requires scm.pull-request.core and scm.pull-request.diff, with scm.repository.tree as an optional source. The diff's contract demands a complete capture, including a verified empty range. If the diff cannot be read, or the pinned commit is gone from the mirror, readiness refuses the practice and no result is created. The runtime makes no claim that the change is focused, sprawling, or DOES_NOT_APPLY.

No source need can demand currentness that the pull-request record cannot show. Nothing available could substantiate one.

Empty evidence is valid​

A complete pull-request comment query may materialize as []. Its state is AVAILABLE + EMPTY + COMPLETE, and scm.pull-request.comments sits at ANY_CAPTURE, so that is valid evidence rather than UNAVAILABLE. A redacted or failed query cannot support the same practice claim, and a practice with a COMPLETE need is withheld on a partial capture.

Runtime behavior​

The runtime resolves exact practice versions before capture. It then stages every governed source the purpose permits in the workspace, on every review. There is no per-run source selection. Practice review configuration decides which practices can run, never which sources are captured. A source listed as anything other than AVAILABLE always gives a typed reason code. That reason is never that no practice asked for it.

Readiness is checked for each selected practice. An OPTIONAL source failure does not withhold an otherwise eligible practice. A REQUIRED or COMPLETE source failure does. If no practice is eligible, no model request is made.

One invocation can contain the governed union needed by several practices. A script can use only its declared sources to support a result. A scan also restricts reads and searches to its assigned file and declared context. Evaluations that require process isolation must use separate evidence views.

Citations must name a declared, available source and an exact quote from captured text. Core checks the captured bytes and their digest. Domain verifiers check source-specific side, version and claim-basis meaning. A failed check withholds the candidate at admission. Feedback composition cannot admit it as a result. This proves traceable grounding, not model causality.

The workspace ABI owns manifest fields, read receipts and coordinate verification. The script runner owns the candidate citation shape. Shell output alone is not an authorized source.

Readiness decisions remain server-side. The folder index carries safe capture reason codes to the sandbox. Do not put raw exceptions or private policy detail in a model-visible reason.

Change and staleness​

Historical records keep their original contract and practice version. Currentness is derived:

  • source resources are immutable within a published contract version. Any semantic change creates a new version. The item record schemas under contracts/items/ are not source resources. An optional field added to a record keeps the contract version.
  • an explicit practice upgrade controls when a practice moves to another source-contract version.
  • changing a practice's review configuration or automated-review policy stales that practice's claims.
  • adding a source cannot silently alter existing requirements because each practice names its sources explicitly.
  • governance withdrawal disables its exact future use without rewriting historical semantics. This includes collection, result persistence and delivery, mentoring reuse, or evidence disclosure.
  • erasure or expiry may make a claim unreplayable without making the historical result false.

Semantic currentness, automated-review-validation status, governance eligibility, and replayability remain separate. Result and review APIs expose currentness as CURRENT, STALE, or UNVERIFIABLE. They compare the review digest of the evaluated practice version with the review digest of the current practice version. A result with an end time is STALE.

Presentation-only edits retain semantic currentness. Rows without comparable versioned fingerprints are UNVERIFIABLE.

Neither value says whether a later review ran, and pull request work is never compared.

Whether a result still concerns the stored work is a separate fact. A result records the item version that its review read in item_version. A pull request version identifies the base, the head, and a digest of the title and description. review_job.capture keeps the folder index manifest with its capture time.

Two server paths end a result with WORK_CHANGED:

  • For an issue or a pull request, ResultCurrentness compares the synchronized source's version with the result's item_version. It ends the result when they differ. It checks when an SCM event for the item is recorded. It also checks when the item's source is observed or a result is recorded. Thus, a new result can end when it is recorded.
  • A recorded scm.pull_request_review.* event ends current results of its item without a version comparison. It ends only results whose source reviews were ordered no later than the event.

A result of a later-ordered review for the same practice, item and developer ends the earlier one with REPLACED. The mentor's result history shows endedAt and endReason of an ended result, beside its recorded outcome. It does not name a replacing result, and its bounded sample can omit one.

The history states two more facts of a result whose words it may copy:

  • capturedAt is the capture time in the retained manifest of the job that produced the result. Only the assignment of the result's own review, practice and item that records this result names that job. The custody's sourceJobIds also list copied dependencies, so they do not name it. When that job is missing, belongs to another review, or has no valid manifest, the capture time is unknown. recordedAt, the job's submission time and the provider's edit times are not capture times.
  • storedWorkVersion compares the exact recorded item_version with the version of the work that Hephaestus stores now. ProductItemQuery.currentWorkVersion reads that version, for an issue or a pull request only. ResultCurrentness reads the same version. SAME means that the two stored versions are equal. It is not a live provider read. The version does not cover every field of the work. A matching version does not show that a review is current or that a problem was repaired. DIFFERENT includes an edit of only the title or the description. UNKNOWN applies to other kinds and to a source that is unavailable or withheld. It also applies to a result whose words the history may not copy.

A history read ends no result. The results of a removed item stay out of the history.

A result without an end time is not proof that it concerns the current work. The version comparison ends no result when its source is unavailable. An end reason records why the claim stopped. It does not say which fields changed, when they changed, or what a later review found.

Adding or changing a source​

Complete the source governance decision before enabling a new or expanded source use. Accuracy or product benefit alone does not authorize collection.

Cut a contract version​

The source-contract version is separate from the application release version. Use this procedure when source semantics change, after the governance decision above. Run commands from the repository root.

  1. Copy the current directory under server/application/src/main/resources/contracts/source-use/ to an unused version directory. Keep its catalog, source-use decisions, and all four schemas together. Leave every published version unchanged.

  2. Set the new catalog.json version and source-use-decisions.json contract version. Update every schema version constant and each schema's $id to the new version. Use the schema identifier format of the current contract resources. Update version-specific references to other schemas if the change introduces them.

  3. Apply the intended source and governance changes only in the new directory. Finalize catalog.json, including formatting, before calculating its SHA-256 digest. Replace NEXT_VERSION below with the new version:

    node --input-type=module -e '
    import { createHash } from "node:crypto";
    import { readFileSync } from "node:fs";
    console.log(createHash("sha256").update(readFileSync(process.argv[1])).digest("hex"));
    ' server/application/src/main/resources/contracts/source-use/NEXT_VERSION/catalog.json

    Set automated-review-readiness-report.schema.json → properties.catalogDigest.const to that digest. Hash the exact file bytes, not parsed or normalized JSON. Recalculate the digest after any subsequent catalog edit.

  4. Set ClasspathSourceCatalogRegistry.CURRENT_VERSION_VALUE to the new version. The registry derives current resource paths and the runtime digest from this value. It accepts only the current contract. Keep published resources unchanged for verification.

  5. Update current-version documentation and fixtures without changing historical contract resources. Cover the new catalog, its pinned digest, and rejection of unsupported versions in the registry tests. Cover an explicit practice upgrade in the practice-version and review-digest tests.

  6. Run vp run gate:contracts and vp run test:server:unit. Check both the resource-validation results and the runtime validation below. Follow the local verification procedure for the remaining checks.

A practice definition pins its source contract in reads.contract. A version cut does not change existing practice versions. A definition update creates a practice version with a new review digest.

The stopped 1.0 upgrade creates current versions for practices that pin 2.0.0, including custom practices. It also updates their catalog comparison bases. Historical versions stay unchanged. The currentness rules apply after the update. The catalog update path owns workspace proposal and acceptance behavior.

Validation​

The rules are enforced mechanically, in two places:

  • gate:contracts validates every contract resource and the bundled practice catalog against their schemas. It holds the readiness schema's pinned catalog digest to the catalog's actual hash. It exercises the policy schema against deliberately broken fixtures. These include a retired evidence profile and evidence requirements written onto a policy instead of the definition. A guard whose failure path never runs is indistinguishable from one that cannot fail. The gate also checks published-resource immutability against the branch's merge base and tests that guard. Changed or deleted published files fail that check.
  • When it reads the catalog at startup, the server rejects duplicate source kinds. It rejects a mirror that pins an identity. It rejects a lossy derivation that claims completeness. It rejects required capture quality that the source can never report. It rejects a source whose use decisions do not cover every product purpose. It rejects a decision whose retention or erasure policy disagrees with its source.

Prior art​

  • Gebru et al., "Datasheets for Datasets" — the source catalog is a datasheet. It records composition, selection scope, uses, and limitations alongside the data.
  • GDPR Article 5 — purpose limitation, minimization, accuracy, and storage limitation, which the source-use decisions record per source and purpose.