Claim families
Tenure’s selective disclosure is signed-variant, not zero-knowledge. When
income is issued, the registrar mints the exact value and its derived band and
threshold variants together as one claim family sharing a family_id. The
worker later chooses which granularity each verifier sees, without re-asking the
employer. The implementation is
crates/tenure-core/src/family.rs.
Why families exist
Two problems motivate them:
- Disclosure should be the worker’s dial. A landlord asking for “income ≥ $3,200/mo” should see a threshold, not an exact salary — and the worker shouldn’t have to ask the employer for a fresh credential each time.
- Stale variants must not linger. If the exact, band, and threshold credentials were independent, a raise could update the band while an old threshold kept verifying. A family prevents that: supersession and revocation are atomic across all variants.
Minting a family
One underlying fact — an exact annual figure with a basis and as_of — produces
three attestations under one family_id:
| Variant | Type | Derived value |
|---|---|---|
| Exact | income_exact | the exact amount |
| Band | income_band | the $25,000-wide band the amount falls in |
| Threshold | income_threshold | the largest $5,000 step at or below the amount |
When income changes, a fresh family is minted that points back at the prior
period’s family via supersedes_family. Families are tracked per underlying fact,
so the income family and the employment-status family supersede on independent
schedules.
Resolving currency
At verification, each family resolves to one of three states by asking whether it is the latest unsuperseded family for its fact:
| State | Effect |
|---|---|
| Current | the latest family for its fact — its members may verify |
| Superseded | a later family or a supersede entry retired it — no member verifies, including a leftover threshold |
| Revoked | every member is revoked |
The key property: when a family is superseded, every variant retires at once. A verifier handed a leftover threshold from an old family resolves that family as superseded and rejects it — a stale threshold can never verify.
Atomic retirement
The atomicity primitive is a single FamilySupersede log entry. It names the
family and the member attestations being retired, optionally points at the
replacement family, and emits one revocation commitment per member — so there is
never a window in which the band has updated but the threshold has not. A
verifier only honours the entry if a registrar in the epoch chain signed it.
Not zero-knowledge
A band or threshold credential is a signed statement of a coarser fact, not a proof that cryptographically hides the exact value. The exact figure still exists as its own variant and the worker holds it; selective disclosure simply lets the worker present only the coarse variant. The product never implies otherwise — ZK-based disclosure is a later research track, not a current promise.