Skip to main content

Crate prov

Crate prov 

Source
Expand description

§prov

A self-describing plaintext workspace: a set of documents whose structure lives in the documents’ own embedded metadata (frontmatter), not in the filesystem layout or an app-private sidecar folder.

The name is the point. A prov is the note in which a book describes its own making — the type, the paper, the press. A prov workspace is one you can hand to any tool and it explains itself: follow the links in the metadata and the whole structure unfolds, with a distinguished root that describes the whole.

§The shape of the abstraction

  • Documents are plaintext files with an embedded metadata block (document::Document).
  • Relations are named links declared in that metadata (relation::RelationSet). Which fields are links is configurable (contents/part_of, links, or your own vocabulary); the mechanism is not. Exactly one relation may be marked spanning — the single-parent tree that gives the workspace its self-describing discovery spine. Every other relation may be many-to-many, so the tree is a backbone, never a ceiling.
  • Identity is a strictly-additive layer (identity, index). The graph, traversal, and (eventually) mutation operate on paths and never require an ID. Turn identity off and it compiles out; turn it on and IDs are minted only when something durably refers to a document.

§Status

Early extraction from diaryx_core. The pure layers — embedded-metadata parsing (meta), document splitting, and relation extraction — are real and tested. The filesystem-driven scan/traversal/mutation engine ports next; its seams (workspace::Workspace, identity::IdentityPolicy, index::IndexStore) are staked out here so nothing diaryx-specific leaks into the eventual public API.

Re-exports§

pub use about::AboutContext;
pub use discovery::Discovered;
pub use discovery::Discovery;
pub use discovery::discover;
pub use intake::Adoption;
pub use intake::PlanOutcome;
pub use intake::StructurePlan;
pub use intake::SynthNode;
pub use manifest::ManifestStatus;
pub use manifest::ManifestUpdate;
pub use mutate::ContentState;
pub use mutate::Created;
pub use mutate::Diagnosis;
pub use mutate::Reparented;
pub use remedy::Fix;
pub use remedy::Remedy;
pub use remedy::RemedyKind;
pub use remedy::Warrant;
pub use route::Layout;
pub use route::RoutePlan;
pub use validate::CheckDiff;
pub use validate::Finding;
pub use workspace::Settings;
pub use workspace::Workspace;
pub use workspace::WorkspaceBuilder;
pub use prov_config as config;
pub use prov_fixity as fixity;
pub use prov_graph;

Modules§

about
The about.md generator — a workspace’s own reading instructions, written for a person who has the directory and nothing else.
attach
Attachments — giving an arbitrary file its own workspace-linked metadata.
change
Transaction primitives, retained at their original paths for compatibility.
content
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. Body-prose parsing via twig — prov’s answer to the content_format knob deferred in docs/next-steps.md, and the ingredient that makes body-link findings code-aware (DESIGN §8’s principle: a [[…]] that is really code, e.g. [[inf] * n for _ in range(m)]] inside backticks, must never be treated as a link).
discovery
Root discovery — finding the workspace a directory belongs to.
document
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. Documents — a plaintext file with an embedded metadata block and a body, or a config file whose entire content is the metadata.
edit
Metadata editing, at the path it had before the write surface moved out of the read core into prov-store. Format-preserving edits to a document’s metadata, whatever carries it.
error
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. Error and result types.
exec
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. A dependency-free executor for backends whose futures are already ready.
exports
Named, closed-by-default document sets that may leave the workspace — the exports: config axis, and the plan that composes a gate with a view.
fs
The filesystem port — both halves.
graph
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. Plain text → walkable graph — the crate’s read core.
history
History — what prov contributes to a workspace recorded by historica.
identity
Compatibility re-exports for the extracted prov-identity crate.
index
The ID index — both halves, split across two crates for the same reason fs is.
intake
Directory-tree import — folding a folder hierarchy into the containment tree.
journal
Journal recovery, retained at its original path for compatibility.
link
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. Link text — the raw strings a relation field holds, the wikilinks embedded in body prose, and the path arithmetic around them.
manifest
Manifests — one node standing for a directory of files, instead of one sidecar per file.
memo
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. A read memo with the lifetime of one operation — the cheap half of not reading the same file twice.
meta
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. Embedded-metadata values — a dynamic, order-preserving value tree over fig.
mutate
Mutation with link maintenance — the crate’s hard, valuable half.
peer
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. prov’s peer port — where the other workspaces are.
relation
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. Relations — the configurable vocabulary of links declared in metadata.
remedy
Remedies — what prov offers to do about a Finding.
route
Routes — addressing a node by its path through the containment tree, and materializing the segments that do not exist yet.
title
The read core’s modules, re-exported at their original paths so prov’s public API is exactly what it was before the split. Title index — the derived name → document map that resolves nominal (“alias”) references like [[My File]].
validate
Validation — integrity findings over the workspace graph, from a root.
views
Declarative views over the workspace — the views: config axis, the traversal that selects the documents one covers, and the pure grouping over what it selected.
vocabulary
Controlled vocabularies — the term sets that make fields references (tags, audiences, statuses) resolvable and therefore consistent.
workspace
The workspace handle — where the filesystem, relation vocabulary, identity policy, and index store are composed.

Structs§

Backlink
An inbound reference to a document, as discovered by the census: which document links here (source), where in it (site), and whether the link is by stable id (survives moves) or by path (rewritten on a move). The inverse of a forward CensusEntry — the marquee payoff of the identity layer (DESIGN §6).
BodyLink
One link found in body prose: the parsed Link (target, label, and whether it was an Obsidian [[…]] wikilink or a markdown/djot [label](target) link) together with the byte span of the whole construct — exactly what a rewrite replaces. The unifying body-link currency: census, check, and the rename machinery all consume this, blind to which syntax the link was written in.
Capabilities
The durability guarantees a Storage backend can make — declared by the backend through Storage::capabilities, honored by prov’s crash-safety machinery.
CensusEntry
One forward link as found in a document: where it is written and how it resolves. The unit of the census.
ChangeSet
A set of writes staged as one unit, applied all-or-nothing by apply.
ConfigIssue
A key in a config surface that WorkspaceConfig::apply would silently ignore — surfaced so a setting that never takes effect becomes visible rather than staying invisible. apply keeps the current value whenever a key is unrecognized or its value fails to parse; that robustness is what makes a typo (notaton) or a bad value (fixity: alll) vanish without a word.
DirEntry
One entry returned by ReadStorage::read_dir.
Document
A parsed document: its path, its embedded metadata, and its body text.
Edge
A resolved link found in a document’s metadata: which relation declared it and the raw (unresolved) target string.
ExportSpec
One export a workspace declares for itself: a gate that bounds what leaves, optionally arranged by a view.
FieldSpec
A field declaration — an entry in the fields block. It promotes a frontmatter field (tags, audience, created) that prov would otherwise merely carry (DESIGN §2, tier 3) into something prov and its frontends know the shape of. Two independent things can be declared, and a field needs at least one of them to be worth an entry:
FileIndex
The persistent registry: a snapshot with tombstones, living under the registry key of a workspace document — the document the root’s registry-pointer relation targets.
FileType
The type of a filesystem entry.
Graph
A readable workspace: a root, a filesystem to read it through, an id index to resolve id: references against, and the ReadSettings that say how its links are spelled.
Id
A stable, opaque document identifier.
InMemoryFs
An in-memory, clone-shared Storage backend.
InMemoryIndex
A simple in-memory registry — for tests and ephemeral workspaces. No tombstones: an unregistered ID is forgotten entirely.
Link
A parsed link string: an optional human label and the target it points at.
Manifest
A parsed manifest document: the directory it claims, and the files it says are in it.
ManifestEntry
One row: a covered file and, when the manifest carries a fixity baseline, the digest of its bytes.
Metadata
Metadata about a filesystem entry — the subset prov needs.
Minter
The bundled minting policy: NOID xdigit + check IDs from a seeded PRNG.
NoIdentity
Identity disabled — the default. Paths only; no ID is ever minted or written.
NoIndex
No index — identity-off workspaces. Registers nothing, resolves nothing.
NoPeers
No peers — every workspace is somewhere this host cannot see.
Node
One node of the materialized spanning tree.
ReadScope
An open read scope. Hold it for the operation; dropping it leaves the scope, and dropping the outermost one drops everything the operation remembered.
ReadSettings
The settings a read of a workspace depends on — the whole of what traversal needs to be told about the workspace it is traversing.
ReferenceStyle
How a durable reference is spelled: a Wrapper, an Addressing, whether an id link carries a title label, and the path rendering used when addressing by path. This is the per-workspace default and the per-relation override (see crate::relation::Relation::style).
Registration
Which events cause a document to be assigned (registered) an ID.
Relation
A single named relation: the frontmatter key it reads, its inverse (if the pair is maintained bidirectionally), and its cardinality.
RelationDef
A relation definition declared in a config’s relations block — the structural half of an entry, parallel to the reference-style half (RelationStyleConfig). This is what makes a workspace’s vocabulary self-describing (DESIGN §1, the prov/1 spec): a foreign reader learns the graph — which fields are relations, their inverse, their cardinality — from the document itself rather than assuming prov’s contents/part_of preset. Each field is optional; a relations entry may carry only style, only definition, or both.
RelationSet
The configured set of relations for a workspace, and which one is spanning.
RelationStyleConfig
A per-relation reference-style override, as declared in a config’s relations block. Each axis is optional and inherits the workspace default (WorkspaceConfig::reference_style) when absent — so a block need only name the axes it changes. This is the config form of Relation::style, and what lets links going “down” (contents) differ from links going “up” (part_of).
Skip
One rule the skiplist asks for, and why.
Skiplist
What the generated region should say, and how that differs from what stands.
StdFs
ReadStorage over the process filesystem (std::fs).
Term
A single term in a vocabulary. prov reads only the three fields here; any other keys on the term entry are carried, not interpreted.
TitleIndex
A name → document(s) index built by scanning a workspace. Names are the documents’ title fields and their file stems; a document is registered under both so [[My File]] (by title) and [[my-file]] (by stem) both find it.
TreeOptions
Options controlling how Graph::tree_with materializes a spanning target that does not resolve on disk.
ViewSpec
One view a workspace declares for itself.
Vocabulary
A parsed controlled vocabulary — the term set for one field.
Walk
The result of one spanning-tree walk: the forward-link census, the structural facts observed from traversal state, and the prose body files reached through separated nodes’ content pointers (tracked for the orphan check, deliberately absent from the census).
Wikilink
A wikilink embedded in a document’s body: [[target]] or, with an Obsidian pipe label, [[target|label]].
WorkspaceConfig
The workspace-wide policy a config declares.

Enums§

About
Whether the workspace generates about.md — a short prose page, specialized against this workspace’s own configuration, that tells a reader with no prior knowledge how to read this directory.
Addressing
What a reference addresses its target by — the second style axis.
Cardinality
How many targets a relation field may hold.
Collision
A registration that would displace one the index already holds.
ConfigIssueKind
The two ways a config key goes unread. See ConfigIssue.
ContentFormat
Which body-prose grammar a document is written in. Maps to a twig twig::Format one-to-one; kept as prov’s own type so callers can name a format without depending on twig directly, e.g. for the content_format config knob.
Durability
What a caller needs from one Storage::sync call — the weakest guarantee that is still correct at that point, so that a backend able to serve it cheaply is free to.
EmbedStyle
The archetype family a workspace authors embedded metadata in — the “embed type” the CLI’s init prompts for, one level above the concrete EmbedType. A family plus a metadata fig::Format resolves to a carrier through embed_carrier: e.g. (CodeBlock, YAML) is a ```yaml block, (Delimited, TOML) is a +++ block, and (Separate, JSON) is a whole-file .json sidecar. It is what the config document records (via prov’s WorkspaceConfig) so a workspace stays self-describing about how its metadata is embedded, not just which format it is written in.
EmbedType
Which embedded config to open — the flat mirror of fig’s parametric Embed.Type. The three parametric families (markdown ---<lang> frontmatter, ```<lang> fenced blocks, <script type> HTML data islands) are enumerated once per format. The first four names are historical (FrontmatterJson is the ;;; block, FrontmatterFig is the ```fig fenced block); the rest are grouped by container.
Error
Errors produced by prov.
ExtKind
The kind of a format-specific Value::Extended scalar. Mirrors the core’s ExtKind and the C ABI’s FigExtKind; the discriminants match that ABI.
FieldType
The field-type vocabulary a fields.<name>.type declaration is spelled in, re-exported so a consumer can name types without depending on fig-schema (or, for ExtKind, on fig) directly — and so neither can drift to a different version than the one prov resolves against. The type a field expects. Drives type-directed parsing and widget choice.
FileOp
One staged filesystem operation. Paths are workspace-relative — the root is joined on at apply time, so a set is portable between workspaces and prints readably in a dry run.
Fixity
How far content checksums cover a workspace.
Format
A config format. Every variant parses, edits, and serializes.
History
Whether the workspace maintains a historica store’s skiplist — the generated region of history/skipped.txt that scopes what historica record takes to the workspace’s reachable graph.
IdStorage
Where a document’s stable ID is persisted — the identity-storage axis (DESIGN §5). Orthogonal to when an ID is minted (prov’s Registration) and to how references are spelled; this is purely the ID’s home.
LinkSite
Where in a document a forward link is written — a frontmatter relation field or a body wikilink. Carried by every link-resolution finding (prov’s Finding, derived in validate — see StructuralFact) and every CensusEntry so a report can point at the exact site.
LinkStyle
The write style for links a workspace authors — prov’s analogue of diaryx’s LinkFormat, and read from the same place: the link_format key in the root document’s frontmatter (a fact declared in the workspace, not an app-private config). Every link prov writes (autofix today; create/rename in time) uses this, so a repair never introduces a foreign style.
MetaCarrier
Where a document’s metadata physically lives — recorded at parse time so a write can preserve the original carrier exactly (a ```fig block is never rewritten as --- YAML; a bare .yaml file never grows fences).
NodeKind
Why a node appears in the tree the way it does.
Notation
The syntactic form a reference is written in — the config-facing notation axis (references.notation), orthogonal to PathStyle. This is the clean split of what the internal Wrapper + plain_/markdown_ LinkStyle prefix fused: Bare is a path with no brackets, Markdown is [Title](…), Wikilink is [[…]].
OpenClosed
Whether a controlled fields vocabulary is open (folksonomy — unknown values are allowed, only near-misses warn) or closed (every value must be a known term; an unknown value is an error). See the fields block and crate::vocabulary.
PathStyle
The path-resolution a reference uses for a path target — the config-facing references.path_style axis, orthogonal to Notation. Applies to path targets only (id/alias ignore it).
PeerLocation
An address a resolver answers with: somewhere on this device, or somewhere on the network.
PeerLookup
What a host knows about where one workspace is — and how sure it is.
Reason
Why a rule is in the skiplist.
Recovered
The outcome of a recover pass.
Resolution
How a forward link resolves against the workspace. Path and id forms stay distinct on purpose: the registry owns id resolution (location-independent, stable across moves), while a path is checked against the on-disk name — so a caller can tell which links a rename must rewrite (paths) from which it must leave alone (ids).
StructuralFact
A structural observation the walk makes as it traverses — not a verdict, just what it saw: a document that would not load, a self-stored id disagreeing with (or absent from) the registry, a spanning edge that revisits an already-reached node, a spanning child whose inverse field does not point back, or a content pointer that failed to resolve.
SyncGuarantee
How strong a backend’s Storage::sync actually is — the standing answer to a Durability request, declared once in Capabilities rather than discovered per call.
Target
The resolution of one link target against a workspace: a path, an ID the registry does not currently resolve, or an off-workspace reference.
TitleMatch
The outcome of resolving a name against a TitleIndex.
Trigger
The registration event a caller is asking about (for example, a workspace’s register operation).
Unconfirmed
Why a location on record could not be confirmed to be the workspace that was asked for.
Value
A dynamic metadata value. Integers and floats are kept distinct, and mappings preserve key order (frontmatter is order-significant to humans).
Wrapper
The syntactic wrapper a reference is written in — the first of the two style axes (see docs/reference-styles.md).

Constants§

FIELD_TYPES
The config spellings of FieldType, in the order a diagnostic offers them.
WORKSPACE_NAME_LEN
Total length of a minted workspace name: WORKSPACE_NAME_RANDOM_LEN plus the check character every moid blade ends with.

Traits§

IdIndex
The query half of an ID index: the three lookups link resolution needs, and no way to change what is stored.
IdentityPolicy
A policy deciding when to register documents and how their IDs are minted.
IndexStore
Somewhere IDs (and eventually derived graph data) are persisted and queried — IdIndex’s lookups plus everything that changes what is stored.
PeerResolver
A host’s map from a workspace name to where that workspace is.
ReadStorage
The read half of an async filesystem backend: everything the traversal core needs, and nothing that can change a byte on disk.
Rebase
What a pending change set can tell a store about its own persisted home.
Storage
An async filesystem backend prov can drive — ReadStorage plus everything that changes bytes on disk.

Functions§

block_on
Drive future to completion on the current thread by polling in a loop with a no-op waker.
code_spans
The byte ranges in body that twig parses as code (inline code spans, fenced code blocks, raw inline/block escapes) — everything a link scan should treat as opaque; see crate::link::scan_wikilinks. Spans are returned sorted by start offset, and cover code inside a footnote definition as well as code in the document body (see spans_where).
diagnose
Diagnose a config surface (a root’s prov: block or a config document’s top-level mapping): one ConfigIssue per key apply would silently ignore. Recognized keys are checked for a value prov can parse; unrecognized keys are reported only when they closely resemble a real axis at their level (a likely typo). Returns empty for a clean config.
embed_carrier
Resolve an EmbedStyle + metadata format to the carrier a new document should get. Separate maps to a whole-file sidecar in format; every other style maps to the concrete EmbedType for that (style, format) pair. None for a combination that has no archetype — notably Delimited + fig (the dialect has no ----style delimiter) and any fenced style paired with a format fig cannot fence (Zon).
embed_style_of
The EmbedStyle family a concrete EmbedType belongs to — the inverse (on the style axis) of embed_carrier, which resolves a (style, format) pair back to a carrier. Pairing it with a new metadata format is how a format conversion keeps a document’s embedding shape while changing only its frontmatter language: classify the current archetype, then embed_carrier the same style with the target format.
escapes_root
Whether path, resolved against a workspace root, would land outside it.
field_type_as_config_str
The fields.<name>.type spelling of a FieldType, or None for a type with no config spelling (see FIELD_TYPES) — such a type is dropped on serialization rather than written as something that would not read back.
field_type_from_config_str
Parse a fields.<name>.type spelling into a FieldType; unknown → None.
format_link
Format a link to target (a workspace-relative canonical path) as written in the document at from, in style, with title (used only by the Markdown styles). This is what keeps an authored link native to the workspace.
is_opaque_payload
Whether prov can read path as text — a recognized body format (Markdown/Djot/HTML) or a whole-file metadata format (YAML/JSON/…). Its negation is an opaque payload: a file prov treats as bytes (an image, a PDF, a font, any binary) and never parses. An attachment is exactly a whole-file metadata sidecar whose content points at such a payload, which is how an arbitrary file gains workspace-linked metadata without being able to carry frontmatter itself.
is_valid_workspace_id
Whether name is a usable workspace self-name.
metadata_format_from_str
Parse a metadata.format config value (yaml/json/toml/fig) into a metadata fig::Format, honoring the compiled-in formats — the public form of [format_from_str], for callers that name a frontmatter language from outside the config parser (the CLI’s convert … metadata.format …).
metadata_format_str
The metadata.format config spelling for a metadata fig::Format — the public form of [format_str], and the inverse of metadata_format_from_str.
mint_workspace_id
Mint an opaque global name for a workspace, randomizing from seed.
path_to_title
A human title generated from a path’s file stem: _/- become spaces and each word is capitalized (utility_index.mdUtility Index). The fallback when a target document declares no title.
reachable_set
The set of workspace-relative paths a walk from start reaches: start itself, every path a census link resolves to (any relation, a body wikilink, or an id through the registry), and every content target.
recover
Finish any change set a crash left journaled at root, rolling the workspace forward to the fully-applied state, then remove the journal.
render_html
Parse body as format and render it to HTML, via twig’s FFI.
require_whole_file
Enforce that a record store at path (the id registry, the recycle-bin index, a flat vocabulary) is a whole-file config document, returning its format. A MetaCarrier::Fenced carrier — markdown frontmatter — is rejected with Error::MarkdownStore: prov re-lays-out these stores as a sorted record list (DESIGN §5), so human prose has no stable home in them and unambiguous extension→format sniffing depends on the carrier being whole-file. The single choke point every store loader passes through, so the rule cannot be enforced in one place and forgotten in another.
spec_ahead
If meta declares a spec newer than SPEC_VERSION — the version this build understands — the declared version. The signal that prov may be silently ignoring settings a newer prov wrote. None when spec is absent, not an integer, or within range. Shared by check (a Finding::ConfigSpecAhead) and the CLI’s proactive config warning, so the version comparison lives in one place.

Type Aliases§

Mapping
An order-preserving metadata mapping — the shape of a frontmatter block.
Result
Convenience alias for results in this crate.