Skip to main content
snıff

Field infrastructure / schema

The Sniff schemas.

Sniff's machine-readable artifacts conform to small LinkML schemas that extend Biolink by mapping, never by fork. The load-bearing one is the CoverageFrame: a typed vocabulary for reasoned absence, the thing a knowledge graph's open-world assumption cannot say. Each schema's own id URL resolves to the served YAML, and this page is generated from those same files at build, so what you read here is what a machine fetches.

The frames themselves ship at /data/coverage-frames.json with an Ensembl-keyed cell index at /data/coverage-cell-index.json (the display symbol travels in the value; symbols collide). The KGX bundle for stewards lives at /federation.

Sniff CoverageFrame: reasoned absence over a bounded question space

version
0.2.8
license
CC BY 4.0

A small LinkML extension over Biolink for the one thing Biolink cannot express: a REASONED ABSENCE of assertion. Biolink's Association.negated says "we assert this relationship is false" (the absent cause below). It has no vocabulary for the other five darkness causes, and "nobody has looked" is both the most common state of biomedical knowledge and the most useful thing to know when deciding what to study next. The modeling unit is deliberately NOT an absence edge (the ~447M non-edges of a bipartite space carry no information). It is a CoverageFrame: a bounded question over a defined population, where an empty cell is itself informative because an answer was expected. Kept to one class pair and two enums so it stays a contribution, not a fork: it aligns to Biolink by mapping (see the exact_mappings and meaning: bindings), rather than vendoring the full model.

Classes

CoverageFrame · tree root

A bounded question space over a defined population, where the absence of an assertion is itself informative because an answer was expected. The unit of reasoned absence: it names the question, the populations, the expected cardinality, and how the expected answers resolve into answered vs dark cells.

slots: id, question, subject_population, object_population, predicate, expected_cardinality, answered_count, dark_count, dark_by_cause, cell_source, sources_checked, as_of

FrameCell

One subject in a CoverageFrame. Its status is answered (a cited assertion exists), negated (an assertion that the relationship is false exists), or dark (no assertion exists, with a named cause). A dark cell is the payload: it turns a missing edge into a typed, actionable statement about what is not yet known and why.

slots: frame, subject, symbol, object, status, dark_cause, association, recoverability, n, basis, floor_id, as_of

DarkCauseTally

One cause's share of a frame's dark cells. Serialized in the compact dict form, so a tally reads as {cause: count} keyed by DarkCauseEnum.

Enums

CellStatusEnum

The three resolutions of an expected answer cell.

  • answered · An assertion exists and is cited.
  • negated · An assertion exists that the relationship is false. Corresponds to a Biolink association carrying negated = true; biolink:negated is a slot, not a concept, so it is a see_also rather than a meaning.
  • dark · No assertion exists; see dark_cause.
DarkCauseEnum

The causes of darkness, modeled as they are actually computed. Only absent is expressible in Biolink today (as Association.negated). Prior art verified 2026-08-19 against Biolink v4.4.4, the ECO 2026-07-10 release, GO, and FHIR: the nearest existing vocabularies are single-cause and record-scoped. ECO:0000035 (no evidence data found; GO's ND code is its manual-assertion child ECO:0000307) is the closest cousin of unstudied (a literature or exhaustion search that found nothing) and is bound below as a close mapping. no_disease_anchor is a different claim: no ClinVar P/LP disease-gene anchor to bridge from, not that the gene is unstudied. FHIR data-absent-reason types why one field on one existing record is empty. No vocabulary we could find types the cause of absence per cell over a declared, bounded question space, and below_bar, unreachable, method_limited, and no_disease_anchor have no term in Biolink or any evidence ontology checked. Where no mapping appears below, that absence is verified and load-bearing, not an oversight.

  • absent · Studied, and the entity or relationship does not exist. The one cause Biolink can already express, as an association with negated = true. A cell whose cause is absent has status negated, never dark: absent is an evidenced no, not a darkness, and check-conformance refuses the pairing dark + absent.
  • unstudied · A literature or exhaustion search addressing this question in this species found nothing. Not for "no Mendelian disease-gene anchor in ClinVar"; that is no_disease_anchor.
  • no_disease_anchor · Dog ortholog exists but no human P/LP disease evidence to bridge from (ascertainment darkness). Not a claim that the gene is unstudied in the literature.
  • below_bar · Human evidence exists but sits under our review bar (for example under a 3-star ClinVar threshold); distinct from method_limited. Relates to evidence strength (ECO) but no ECO term names "below a downstream bar".
  • unreachable · No ortholog or entity exists for the assay to observe.
  • method_limited · The method cannot resolve this class of entity even where the underlying data are present.
ClaimBasisEnum

How a present claim was produced. Companion to DarkCauseEnum, which names absence. Strength is n plus basis plus floor. A score float is forbidden.

  • measured · Instrument or lab-backed on this subject.
  • estimated · Inferred or owner-sketched, never dressed as a measurement.
  • cited_cohort · A published or atlas cohort statistic with a cited n.
  • owner_register · An owner-contributed aggregate, cohort-of, never population-of.
  • this_dog_lived · Repeated measures on one dog. Never a breed fact.
Slots (23)
id identifier · uriorcurie

The CoverageFrame identifier. Carries biolink:id semantics.

question

Human-readable statement of what the frame asks.

subject_population

The subject set, for example GenCC or ClinVar human disease genes.

object_population

The object set, for example their canine orthologs.

predicate uriorcurie biolink:predicate

The Biolink predicate the frame asks about.

expected_cardinality integer

How many answers the frame expects if the space were fully covered.

answered_count integer

Cells with a cited assertion.

dark_count integer

Cells with no assertion, each carrying a DarkCauseEnum.

dark_by_cause multivalued · DarkCauseTally

Tally of dark cells keyed by DarkCauseEnum, as inlined DarkCauseTally entries (compact dict: {cause: count}). Until 0.2.4 this slot was declared as multivalued integers, a shape the shipped artifact never had; the correction is recorded rather than hidden.

cell_source uriorcurie

The artifact holding the per-cell FrameCell records.

sources_checked multivalued · uriorcurie

The infores CURIEs of the resources that were queried to build the frame.

as_of date

The date the frame was computed. Renamed locally under the class-level implements binding: an as_of is the creation date of the snapshot object (biolink:creation_date).

frame CoverageFrame

The CoverageFrame this cell belongs to.

subject uriorcurie

The subject entity of the cell.

symbol string

The human-readable label for the subject, beside its identifier. Optional, and never the identity: two sources may label one identifier differently, so a symbol is a convenience for a reader and is never matched on. Declared because the cells we publish have always carried it. It went undeclared while every count reconciled, which is the shape of defect a key-level check cannot see and instance validation catches immediately.

object uriorcurie

The object entity of the cell, when one is expected.

status required · CellStatusEnum

Whether the cell is answered, negated, or dark.

dark_cause DarkCauseEnum

The reason no assertion exists. Required when status is dark, enforced by the FrameCell rule (not only this sentence).

association uriorcurie biolink:Association

The Biolink Association backing the cell when status is answered.

recoverability

Optional note for assay-limited or method-limited cells.

n integer

Denominator that produced a present claim. Distinct from darkness. A cell may carry an n and still fall below its reporting floor.

basis ClaimBasisEnum

How a present value was produced. Absent on a dark cell.

floor_id

Which named reporting floor judged this cell, for example sniff:floor/reportable-n. Not a score. This schema does not carry a float confidence on a health-adjacent row.

Sniff CoverageFrame provenance module (an absence claim carries its search)

version
0.3.14
license
CC BY 4.0

The provenance module for reasoned absence. A presence claim's warrant is a pointer (the citation); an absence claim's warrant is a PROCEDURE. This module makes that procedure a schema citizen: the SearchProtocol that produced a frame (pinned to runnable code, with a declared completeness and cause-precedence funnel), the versioned PopulationDefinitions it enumerated (whose counts double as drift checksums), and the positive controls that calibrate it (held-out known-answerable cells the protocol must find before its darkness counts; a dark cell not shown to LIGHT on a planted positive is worth zero). Importable separately from the core (sniff-coverage-frame), which stays frozen at one class pair and two enums. Conformance to the core alone is conformance; this module is how a producer PROVES the rigor of its dark cells. Two frames are comparable as knowledge flow only when their population DEFINITIONS and protocol are identical; a newer source_version under the same definitions is the world moving, and its membership changes are typed boundary events in the delta module. That rule is what makes world-moved vs frame-moved computable.

Classes

SearchProtocol

The reproducible procedure that resolved a frame's cells. The strongest form of a methods section is a pointer to runnable open code at a pinned version. Determinism is the contract; the specific precedence order is a protocol parameter, so two parties running the same protocol version on the same populations must produce the same cells, and a disagreement is diagnosable rather than a shrug.

slots: id, protocol_version, pipeline, match_criteria, completeness, cause_precedence, dial_references, positive_controls, darkness_controls, executed_at, recall, end_to_end_recall, filter_independence, negative_controls

PopulationDefinition

A versioned, counted population a frame enumerates over. Identity is the INTENSION: the id's version (an integer, as in sniff:population/x@1) bumps only when the selection procedure itself changes, never when a new source release changes the membership. The source_version and count are per-release measurements. The count doubles as a drift checksum: same definition version, same source_version, and a differing count means the pipeline drifted (a bug); a newer source_version under the same definition is the world moving, and the delta module enumerates the membership change as boundary events.

slots: id, source, source_version, selection, count

DarknessControl

One held-out cell known to be DARK FOR A SPECIFIC CAUSE, independently of the pipeline: a primate-only gene for unreachable, a gene whose ClinVar records all sit under the declared bar for below_bar, a gene with a clean ortholog and no disease anchor for no_disease_anchor. The protocol must observe the expected cause on every darkness control before its dark cells may ship, and it must carry at least one for every cause its tallies claim. Positive controls prove the instrument finds what exists; darkness controls prove it names why it does not, which is the product. Added after both dark cells of a demonstration frame turned out to be mistyped while every positive control passed: an instrument calibrated only on the cells that light has proven nothing about the cells that do not.

slots: subject, expected_cause, observed_cause, observed_status, basis, basis_kind, receipt_source, receipt_as_of, outcome

PositiveControl

One held-out cell known to be answerable, independent of the pipeline (for Sniff's reference frame: canine disease genes documented in OMIA before this pipeline existed). The protocol must observe the expected status on every control before its dark cells may ship. Calibration is the difference between measured ignorance and a parsing bug wearing ignorance's clothes.

slots: subject, expected_status, observed_status, basis, basis_kind, receipt_source, receipt_as_of, outcome

ProvenancedCoverageFrame is_a CoverageFrame

A CoverageFrame that carries its warrant: the protocol that resolved it and the versioned populations it enumerated. The core class stays frozen; adopters who cannot yet publish protocols emit plain CoverageFrames and graduate to this class when the procedure is publishable.

slots: search_protocol, subject_population_ref, object_population_ref, release_id, conforms_to, scope, constituents

FrameScope

What this frame measured, and what it deliberately did not. A question that outruns its sources is an overclaim every dark cell inherits. sources_queried must match the frame's sources_checked. sources_not_queried names known authorities left out, with a reason and a named path to close each gap, so an unqueried source is a typed limitation rather than silence.

slots: measures, sources_queried, sources_not_queried

SourceOmission

One authority this frame did not query. The reason is why, for this question. close_path is how the gap becomes queried rather than remaining an implicit hole in sources_checked.

slots: source, reason, close_path

Recall

A measured recall figure bound to the identity of the control set that produced it. A recall number whose denominator can silently change is the failure this class exists to prevent.

slots: value, control_set, control_set_hash, control_set_size, dial, measured_at

FilterIndependence

How much two candidate filters fail on the same items. When the observed shared-miss count materially exceeds the independence expectation, stacking further filters of that family will not recover recall.

slots: filters_compared, shared_miss_jaccard, observed_over_expected, marginal_gain

Enums

CompletenessEnum

How completely the protocol enumerated the population, defined operationally so the term is checkable rather than a vibe.

  • exhaustive · The protocol evaluated every cell in the declared population.
  • sampled · The protocol evaluated a declared fraction under a declared sampling method. Dark tallies extrapolate; absent is not assertable.
  • heuristic · Enumeration is not guaranteed (for example keyword search). The weakest honest claim; absent is not assertable.
BasisKindEnum

The kind of evidence a control's basis is, ranked by independence from the protocol's own source.

  • independent_literature · A published paper. Independent of every database the protocol queries; immutable, so a mismatch is always a pipeline defect.
  • independent_source · A database other than the one the protocol queries for this cell (for example OMIA for a ClinVar-anchored protocol). Independent of the source, not of the world.
  • same_source_hand_verified · The protocol's own source, read by hand outside the pipeline, with a dated receipt. Catches builder bugs, parsing errors and wrong filters; catches no error in the source. A control of this kind on a mutable database is a world-movement tripwire and routes to world_moved, never to a build failure on its own.
ControlOutcomeEnum

What the protocol run did to a control.

  • held · Observed equals expected. The only outcome that counts toward calibration.
  • world_moved · Observed differs from expected and the receipt facts no longer hold in the ingested source. The world moved; re-plant a control for the cause.
  • failed · Observed differs from expected while the receipt facts still hold. The funnel is wrong. Nothing ships.
IntersectionStatusEnum

How a cell resolves across the constituent frames of an intersection. These tokens are scoped to the named stack. They are not claims about sources outside that stack. A third frame must use these values; it must not invent a parallel convention.

  • lit_all · Answered in every constituent frame of this stack.
  • lit_any · Answered in at least one constituent frame of this stack, and not in all of them.
  • dark_in_all_frames · Dark in every constituent frame of this stack. Not a claim that nobody has looked, and not a claim about sources that are not in the stack.
  • unresolved · Not evaluated by this stack. The subject is off the shared axis, or a constituent did not emit a cell.
Slots (47)
protocol_version required

The protocol's own version, bumped on ANY behavior change to the emitting pipeline. Producers should hold this with a mechanism that notices silent drift (Sniff's gate hashes the emitting script and fails the build when the code changes without a version bump).

pipeline required · uriorcurie

Identifies the code that emitted this frame. A URI that resolves to the runnable source where that code is public; otherwise a CURIE naming the pipeline, or a URI resolving to a public description of it. The field says WHAT produced the frame and promises the identifier is stable and resolvable; it does not promise a reader can execute what they find there. Stated this way because the earlier wording ("resolvable to the runnable source") was violated by every value a closed-source pipeline can honestly supply, which makes the contract unmeetable rather than strict.

match_criteria required

Human-readable statement of what counts as "answered" for a cell.

completeness required · CompletenessEnum

Operational completeness of the enumeration. This is a property of the protocol, not the frame. absent cells are only assertable under an exhaustive protocol; a sampled or heuristic search may emit unstudied, never absent.

cause_precedence multivalued · DarkCauseEnum

The declared funnel order for assigning the single binding dark_cause when several causes could apply. Instrument-side blockers before world-side by default (unreachable, method_limited, no_disease_anchor, unstudied, below_bar, absent). The funnel makes cause assignment an algorithm, which keeps dark_by_cause tallies additive and cross-party comparable. Bindings are per-frame: no_disease_anchor is a ClinVar-anchor fact; unstudied is a literature-search fact.

dial_references multivalued · uriorcurie

Named, versioned criteria behind any subjective cause (for example sniff:dial/clinvar-review-floor@1 for below_bar). The enum stays closed and interoperable; every adopter's bar is explicit and diffable. A dial change is a criteria_change transition in the delta module, never a silent redefinition of darkness.

positive_controls multivalued · PositiveControl

The calibration set, lit side. A frame whose protocol fails any positive control cannot ship its dark cells.

darkness_controls multivalued · DarknessControl

The calibration set, dark side. One per cause the frame's tallies claim, each independently known dark for that cause. A frame whose protocol assigns a cause it has never demonstrated on a known case cannot ship.

executed_at date

When the protocol run that produced the frame executed.

reason

Why this source was not queried for this question. Not a hedge on the cells; a statement of the search that was not run.

source required · uriorcurie

The infores CURIE of the resource the population was selected from.

source_version

The release or version of the source the selection ran against.

selection required

The criteria or query that produced the population.

count required · integer

The resulting cardinality; the population's drift checksum.

expected_status required · CellStatusEnum

The status the control cell is independently known to have.

expected_cause required · DarkCauseEnum

The cause a darkness control is independently known to carry.

basis_kind required · BasisKindEnum

How much assurance the basis carries, said out loud so nobody reads more into a row than it holds. A paper is independent of every database the protocol queries. A different database is independent of the protocol's source but not of the world. The protocol's own source, read by hand, catches builder bugs, parsing errors and wrong filters, which is most of the value, and catches no error in the source itself.

receipt_source uriorcurie

Where the basis was read: an infores CURIE for a database, a PMID for a paper. Required when basis_kind is same_source_hand_verified, because that is the receipt the outcome logic re-checks.

receipt_as_of date

The UTC calendar date the receipt was read. Every date in this schema family is a UTC calendar date; a reader in a western timezone may see a receipt dated tomorrow, and that is the convention, not a future-dated read.

outcome required · ControlOutcomeEnum

What happened when the protocol ran against this control. held is the only outcome that counts toward calibration. world_moved is the routing for a control on a mutable source whose receipt facts no longer hold: the day an expert panel reviews a below_bar control's gene, that control fails correctly, the cell should leave below_bar, and the frame still ships if another held control covers the cause; the delta carries the movement. A control that fails while its receipt facts still hold is failed, the funnel is wrong, and nothing ships.

observed_cause required · DarkCauseEnum

The cause the protocol actually assigned to the darkness control's cell.

observed_status required · CellStatusEnum

The status the protocol actually produced for the control cell.

release_id uriorcurie

The release this frame snapshot belongs to. Declared in 0.3.3; the shipped artifact had carried it undeclared, which the reference validation loop now makes impossible to repeat silently.

conforms_to uriorcurie dcterms:conformsTo

The schema class this frame instance claims conformance to.

scope FrameScope

The frame's measurement boundary. Rendered on every cell so a dark answer cannot be read as a census of sources this frame did not search.

measures

One sentence naming what the frame measures, and what a reader must not take it to have measured.

sources_queried multivalued · uriorcurie

The infores CURIEs actually searched. Must equal the parent frame's sources_checked. Repeated here so a cell view can render the boundary without joining.

sources_not_queried multivalued · SourceOmission

Known authorities for this question that were not searched, each with a reason and a named path to close the gap.

close_path

How this omission becomes a queried source rather than remaining a silent hole. A named next protocol, join, or parallel frame, not a vague intention.

constituents multivalued · uriorcurie

When this frame is an intersection, the CoverageFrame ids it stacks. Constituents MUST share one subject axis (same population definition, same cell keys, same expected cardinality). The intersection records only lit or dark per constituent; dark causes stay on those frames. sources_checked on an intersection is the union of the leaves' sources. Recursive: a constituent may itself be an intersection.

search_protocol required · uriorcurie

The SearchProtocol (by id) that resolved this frame's cells.

subject_population_ref required · uriorcurie

The PopulationDefinition (by id) enumerated on the subject side.

object_population_ref uriorcurie

The PopulationDefinition (by id) resolved against on the object side.

recall Recall

Measured sensitivity of this protocol against its positive controls. A protocol may carry passing controls while concealing how blind it was; this slot is what makes that impossible.

end_to_end_recall Recall

Recall measured after EVERY stage, not just retrieval. A multi-stage protocol has more than one recall and they answer different questions: recall is whether the search returned candidate documents for a control, and this is whether the control's cell actually ended up answered. The second is bounded above by the first, and the gap between them is a map of whatever sits in between. Declared 0.3.5 after a producing pipeline emitted it as an undeclared key, which the schema now forbids: a producer may not carry a field the schema never promised.

filter_independence FilterIndependence

Whether candidate filters fail on the same items. Stored as a measurement, not an observation, so the conclusion stays re-derivable.

negative_controls multivalued · PositiveControl

Cells known NOT to be answerable, on which the protocol must stay silent. Positive controls alone cannot detect an inflated instrument: a recall figure rises when automated annotations are counted as literature, and only a negative control detects it.

value required · float

Measured recall as a fraction.

control_set required · uriorcurie

Versioned id of the control set, for example sniff:controls/frame-one-positives@1.

control_set_hash required

SHA-256 over the sorted control member ids. Binds the figure to its denominator's identity.

control_set_size required · integer

Number of controls the figure was measured over.

dial required · uriorcurie

The named versioned dial the measurement was taken under.

measured_at required · date

When the measurement ran.

filters_compared required · multivalued

Names of the filters compared.

shared_miss_jaccard float

Jaccard index of the filters' miss sets.

observed_over_expected float

Observed shared misses divided by the count independence predicts.

marginal_gain integer

Additional controls recovered by adding the second filter to the best single filter.

Sniff CoverageFrame delta module (frames are snapshots, change is typed)

version
0.3.4
license
CC BY 4.0

The delta module for reasoned absence. A frame is a snapshot and stale darkness silently lies, so change is a first-class typed object rather than a regenerated file's diff. A FrameDelta separates the two things that can move: the WORLD (identical populations and protocol, cells flipped, knowledge changed) and the FRAME (populations, protocol, or dials changed, so the question changed). Blending them produces a confident falsehood; the kind field makes the blend inexpressible. Every changed cell is enumerated as a CellTransition with a typed trigger and a reference. The correction trigger is the designed repair path: a dark cell that was our bug becomes a typed, public, cited correction instead of a silent overwrite. Population definitions are intensional (see the provenance module), so a new source release can legitimately change the MEMBERSHIP of an unchanged definition: the world does not only answer questions, it also mints and retires them. Those membership changes are first-class CellBoundaryEvents (entered, left), never silent. For world-moved deltas the conservation identity binds the frame's DECLARED counts to the enumerated flows: answered(t1) = answered(t0) + darkToAnswered - answeredToDark + enteredAnswered - leftAnswered, and cardinality(t1) = cardinality(t0) + entered - left, every cell in exactly one status per release. A regenerated frame that does not reconcile against its predecessor plus the delta is a build failure, and the state machine audits itself.

Classes

FrameDelta

The typed change between two releases of one frame. Comparable only when kind is world_moved; a frame_moved delta documents that the question itself changed and its transitions are annotations, not knowledge flow.

slots: id, previous_frame, current_frame, kind, transitions, entered, left

CellTransition

One cell's move between statuses or causes across a release, with a typed trigger and a citation for what moved it. The dark-to-answered transition is the product's core loop made schema: the record updates itself and the owner is told, with a citation.

slots: subject, symbol, from_status, from_cause, to_status, to_cause, trigger, reference

CellBoundaryEvent

One cell entering or leaving the frame's universe across a release. Under world_moved this is knowledge flow (a new source release minted or retired the question cell itself, for example a gene newly carrying a pathogenic classification); under frame_moved it is an annotation of the changed question. Either way it is enumerated, because a silently appearing or vanishing cell is the delta equivalent of an untyped gap.

slots: subject, symbol, status, dark_cause, trigger, reference

Enums

DeltaKindEnum

What changed between two releases. Never blended. Held two values until a release corrected a source identifier without the world or the method moving: identical definitions over an identical upstream snapshot, and not one cell flipped. That is not the world moving, and world_moved was acting as the residual bucket rather than as a claim about the world.

  • world_moved · Identical populations and protocol; cells flipped because knowledge changed. The conservation identity binds.
  • frame_moved · Populations, protocol, or dials changed; the question changed. Not comparable to the predecessor as knowledge flow.
  • correction · Nothing moved. Identical populations, protocol and dials over an identical upstream snapshot; the release exists to repair our own record. Counts are expected to be unchanged, and any cell that does flip flips because the previous release was wrong about it.
TransitionTriggerEnum

The typed causes of a cell transition.

  • source_release · An upstream source shipped a new release.
  • new_publication · A new primary publication answered or negated the cell.
  • method_change · The protocol or pipeline changed how it resolves cells.
  • criteria_change · A named dial changed (the bar moved, visibly).
  • population_change · The population definition or its source version changed.
  • correction · The previous release was our error. The typed, public, cited repair path; never a silent overwrite.
Slots (12)
previous_frame required · uriorcurie

The prior frame release (by id plus release).

current_frame required · uriorcurie

The new frame release (by id plus release).

kind required · DeltaKindEnum

world_moved, frame_moved, or correction, never blended. Populations and protocol identical AND the upstream snapshot unchanged means the record was corrected, not that anything moved. Identical definitions over a NEW upstream snapshot means the world moved. Anything else means the frame moved.

transitions multivalued · CellTransition

Every changed cell, enumerated.

entered multivalued · CellBoundaryEvent

Every cell that entered the universe, enumerated with its arrival status.

left multivalued · CellBoundaryEvent

Every cell that left the universe, enumerated with its departure status.

from_status required · CellStatusEnum

The cell's status in the previous release.

from_cause DarkCauseEnum

The cell's dark cause in the previous release, when it was dark.

to_status required · CellStatusEnum

The cell's status in the current release.

to_cause DarkCauseEnum

The cell's dark cause in the current release, when it is dark.

trigger required · TransitionTriggerEnum

What moved the cell, typed.

reference uriorcurie

The citation or artifact behind the trigger (the new publication, the source release, the correction notice).

Sniff OwnerFact: per-field privacy born on the living Record

version
0.2.2
license
CC BY 4.0

LinkML root for owner-contributed facts on user dogs (the living-dog layer). Where CoverageFrame models reasoned ABSENCE over the genetics substrate, OwnerFact models privacy-born PRESENCE on the living dog: the same immune grammar, opposite polarity. A fact is born with a FactVisibility intent that is refuse-null (never a database default), and its effective exposure is COMPOSED under the dog's visibility tier and the owner's trust tier, never read from raw intent alone. science here means eligible to COUNT in an anonymized cohort, not safe to RENDER a cohort rate: any aggregate still passes the cohort-frame and apoptosis rules before it can be shown. Instances live in Turso (dog_facts); the pure composition logic lives in web/src/lib/consumer/fact-core.mjs. This schema is the contract those obey.

Classes

OwnerFact · tree root

One owner-contributed fact about a dog, born with a FactVisibility intent (refuse-null). The value is carried under a stable typed key; provenance records whether it was declared, measured, or imported.

slots: id, dog_id, kind, key, value, visibility, provenance, created_at, n, basis, floor_id

FactExposure

The result of composing a fact's visibility intent with the dog's visibility tier and the owner's trust tier. science here is an eligibility gate to count, not a permission to render a cohort rate.

slots: owner, science, showcase

Enums

FactKindEnum

The category of an owner-contributed fact.

  • answer · A response to a dog-questions item.
  • lifestyle · A structured lifestyle seed such as acquisition window or diet class.
  • note · A free-text owner note; born private.
  • vet_doc · A clinical document handle; born private, handling deferred.
FactVisibilityEnum

The owner's per-field visibility intent. The same three-value vocabulary is shared across the record (see INV-116); it is refuse-null and fails closed to private.

  • private · The owner's own lens only.
  • science · Eligible for an anonymized cohort count when trust clears; never shown publicly.
  • public · Eligible for showcase when the dog is public and trust clears.
FactProvenanceEnum

How a value was obtained. ECO evidence-code bindings are a planned Phase 2 extension; they are omitted here rather than asserted unverified.

  • declared · Owner-reported, carried in estimated language.
  • measured · Instrument or lab-backed.
  • imported · Brought in from an external source with a provenance trail.
Slots (14)
id identifier

The fact identifier.

dog_id required

The user_dogs id this fact belongs to; never the Founder dogs table.

kind required · FactKindEnum

The category of fact.

key required

A stable key such as acquisition_window, diet_class, free_note, or a dog-questions id.

value required

A JSON string for structured keys, or raw text for a free note.

visibility required · FactVisibilityEnum

The owner's intent only, never a database default; refused if null at write time. Effective exposure is composed downstream, never read from here alone.

provenance required · FactProvenanceEnum

How the value was obtained.

created_at datetime

When the fact was written.

n integer

Denominator when this fact is later aggregated. A single owner fact is n=1. Cohort renders still pass the cohort-frame floor.

basis

How the value was produced when distinct from provenance. Typical values are declared, measured, owner_register, or this_dog_lived. No score.

floor_id

Which par an aggregate of this fact must clear before it may render.

owner boolean

Visible to the owner in their own record.

science boolean

Eligible to count in an anonymized cohort. The cohort-frame and apoptosis rules still gate any aggregate before it can be rendered.

showcase boolean

Eligible for public showcase when the dog is public and trust clears.

Sniff Sighting: one observed mention of an entity in one document

version
0.2.0
license
CC BY 4.0

A sighting is one observation that a document mentions an entity, recorded before anyone decides what it means. Literature never enters a coverage frame directly: it enters this ledger, and only an adjudicated sighting may support a frame cell. The separation is the point. Recall comes from a precomputed index, precision comes from adjudication, and a sighting records which stage it has reached. Sentence text is deliberately LOCAL-ONLY: it exists for adjudication and is never emitted into a published artifact. Published sightings carry the document id and character offsets instead, so any claim stays checkable against the source without redistributing copyrighted text.

Classes

Sighting · tree root

One entity mention in one document, with the offsets that locate it and the adjudication that judged it.

slots: id, subject, taxon, document, passage_offset, annotation_offset, annotation_length, extractor, extractor_version, retrieved_date, archive_hash, filter_flags, proposal, adjudication, adjudication_basis, adjudication_note, sentence_text

Proposal

A machine's opinion about a sighting, recorded before any human judged it. Held as its own class rather than as fields alongside adjudication on purpose: a proposal and a verdict are different kinds of thing, and a flat proposed sitting beside adjudication is one mis-read away from a compiler typing a cell on a machine's say-so. INV-145 forbids exactly that, so the shape is built to make the mistake awkward rather than merely detectable. Nothing here may promote a cell; only a merged human adjudication may. A proposal is what the adjudication ladder measures. Blind review withholds it from the reviewer, and blind agreement between this and the human verdict is the only agreement figure that means anything.

Enums

AdjudicationStatusEnum

The three states of a sighting.

  • pending · Observed, not yet judged. May not support a frame cell.
  • confirmed · Judged to support a claim about this entity in this taxon.
  • rejected · Judged not to support such a claim.
AdjudicationBasisEnum

Why an adjudication went the way it did. Turns the species-assignment problem from a caveat into a measured quantity.

  • confirmed_canine · The document studies this entity in this taxon.
  • species_ambiguous · Entity and taxon both present, but which species the claim attaches to is not resolvable from the text.
  • wrong_species_context · The entity is studied in another species and this taxon is mentioned incidentally, as in a comparative genomics survey.
  • dog_as_comparator · The taxon appears as a comparison or control group, not the subject.
  • gene_mismatch · The annotation resolves to a different entity, an alias or symbol collision.
  • insufficient_text · Undecidable without full text.
Slots (17)
proposal Proposal

The machine proposal for this sighting, if one has been made. Absent until propose runs. Its presence never advances adjudication.

id identifier

Stable sighting id, a hash of subject, document, offsets, extractor and version.

subject required · uriorcurie

The entity sighted, as a CURIE.

taxon required · uriorcurie

The taxon the sighting is scoped to, for example NCBITaxon:9615.

document required · uriorcurie

The source document, for example PMID:35277861.

passage_offset required · integer

Character offset of the passage within the document.

annotation_offset required · integer

Character offset of the mention within the document. A published receipt.

annotation_length required · integer

Length of the mention. With the offset, this is the checkable span.

extractor required

The tool that produced the annotation, for example pubtator3.

extractor_version required

Pinned version or release date of the extractor.

retrieved_date required · date

When the response that carried this sighting was retrieved.

archive_hash required

SHA-256 of the archived response this sighting was derived from. The corpus-of-record pointer: re-derivation replays the archive, never the live service.

filter_flags multivalued

Which candidate filters fired on this sighting, for example sentence_cooccurrence or dog_gene_id. Annotation only. A filter never types a cell.

adjudication required · AdjudicationStatusEnum

How far this sighting has progressed. A pending sighting cannot support a cell.

adjudication_basis AdjudicationBasisEnum

Why the adjudication went the way it did. Required once adjudicated (see the class rule). The share of species_ambiguous plus insufficient_text is the irreducible-human-judgment fraction.

adjudication_note

One sentence from the adjudicator, citing what was judged.

sentence_text

LOCAL-ONLY. The sentence that was judged, kept for adjudication and never emitted into a published artifact. Published sightings carry offsets.