Document & ManifestInstance¶
Document is the universal wrapper for every manifest document —
doc.kind, doc.name, doc.spec, doc.metadata, doc.typed,
doc.origin. ManifestInstance is the blessed query surface: the one
documented read API (all, one, root, default_agent, find_agent,
build_prompt, resolve) that the guides and examples teach.
Document¶
dna.kernel.document.Document ¶
Document(
api_version: str,
kind: str,
name: str,
metadata: dict[str, Any] | None = None,
spec: dict[str, Any] | None = None,
raw: dict[str, Any] | None = None,
typed: Any | None = None,
origin: str = "local",
)
Bases: Generic[SpecT]
Universal wrapper. Works for parsed BaseKind AND raw dict.
doc.spec and doc.metadata always return SpecDict at runtime
— a dict subclass with attribute access. When typed via
Document[MySpec], the type checker treats doc.spec as MySpec,
enabling autocomplete + typo detection at edit time without a
runtime cast.
The typed model is still available via doc.typed.
metadata
cached
property
¶
Always returns SpecDict — typed metadata when available, raw dict otherwise.
spec
cached
property
¶
Always returns SpecDict — typed spec when available, raw dict otherwise.
from_raw
classmethod
¶
Create a Document from a raw dict.
Returns Document[Any] because the spec type is determined at
the call site by the consumer's annotation; the factory itself
cannot infer it. Consumers using typed access:
doc: Document[PageIndexSpec] = Document.from_raw(raw)
get the right type via the annotation.
ManifestInstance¶
dna.kernel.instance.ManifestInstance ¶
ManifestInstance(
scope: str,
documents: list[Document],
kinds: dict[tuple[str, str], KindPort],
source: SourcePort | None = None,
resolve_errors: list[str] | None = None,
kernel: Any = None,
profiles: list | None = None,
lazy: bool = False,
)
Facade over a loaded manifest scope.
Marco B (s-lazy-manifest-instance-class, 2026-05-14): supports a LAZY mode where the constructor only receives bootstrap docs (Genome + KindDefinition + LayerPolicy + UA index ~30 docs) instead of the full scope (often 1500+). In lazy mode:
one(kind, name)→ delegates tokernel.get_document(L2 cached, ~5ms).all(kind)→ delegates tokernel.query(~10ms indexed).documents→ triggers_ensure_loaded()which materializes the full scope. Emits a DeprecationWarning when called in lazy mode — callers should use one/all or kernel.query directly.
Bootstrap kinds (always eager) keep mi.root, mi.kind_for,
namespace getters (mi.composition, mi.nav) functional
cheaply. Heavy operations like mi.summary() /
mi.composition.validate() that iterate the full scope still
force the materialization, but that's the explicit ask.
To enable lazy mode: pass lazy=True to the constructor (the
Kernel does this when DNA_LAZY_MI=1). When lazy=False
(default), ManifestInstance behaves exactly as before — full
back-compat for tests, agent paths, and external callers.
documents
property
writable
¶
Materialized list of all docs. In lazy mode, accessing this
triggers a full load (the only way to honor list semantics).
Prefer one(kind, name) or all(kind) which stay lazy.
Emits a DeprecationWarning in lazy mode the first time the full set is materialized.
reports
property
¶
Namespace: mi.reports.eval_summary() / findings_summary().
root
cached
property
¶
The manifest's root document (the Genome), or None when the
scope has no doc whose KindPort is marked is_root.
composition_result
cached
property
¶
Validate cross-kind references. Returns resolved + missing + warnings.
all ¶
Return all docs of kind — DEPRECATED, will be removed in 1.0.
s-blessed-query-surface: the blessed query surface is
mi.documents (in-memory, filter by d.kind) plus
kernel.query(scope, kind) for indexed / record-plane reads.
This method survives as a warning shim until 1.0.
all_async
async
¶
Async-native variant of all() — bridge for callers
migrating to await kernel.query(scope, kind).
f-mi-class-extinction (Story s-mi-async-bridge, 2026-05-14):
new API that callers should target during the MI sweep. Returns
the same list[Document] shape as sync all() but uses
await kernel.query end-to-end — no thread, no asyncio.run,
no loop-mismatch with asyncpg pools.
Bootstrap kinds (Genome, KindDefinition, LayerPolicy) are
served from the in-memory self._documents (no query).
Lazy-cached kinds (already materialized by a previous call)
are served from self._lazy_kind_cache.
Tenant note: does not auto-apply tenant overlay from this
MI's resolved layer context. Callers that need tenant filtering
should pass tenant via kernel.query(..., tenant=...)
directly. The MI overlay-merge is applied at doc content level
and is observable via this method only when the underlying
layer storage already filters by tenant (Postgres adapter does).
all_where ¶
Return all documents whose registered KindPort satisfies a predicate. Forces full materialization in lazy mode (cross-kind walk requires the whole scope).
one_async
async
¶
Async-native variant of one() — bridge for callers
migrating to await kernel.get_document(scope, kind, name).
f-mi-class-extinction (Story s-mi-async-bridge, 2026-05-14):
new API that callers should target during the MI sweep. Same
return shape as sync one(). Bootstrap kinds + lazy-cached
kinds short-circuit; otherwise delegates to
await kernel.get_document (L2 cached).
one ¶
Lookup single doc by (kind, name) — DEPRECATED, will be removed in 1.0.
s-blessed-query-surface: the blessed query surface is
mi.documents (in-memory, search by d.kind/d.name)
plus kernel.get_document(scope, kind, name) for indexed /
record-plane reads. This method survives as a warning shim
until 1.0.
read_spec ¶
Read a single field from document.spec.
read_metadata ¶
Same contract as read_spec but reads from document.metadata.
read_spec_list ¶
Read a list-typed spec field, returning [] when missing or None.
default_agent ¶
The agent Document the root Genome names as its default
(spec.default_agent via the root KindPort), or None when
there is no root or no such agent.
list_kinds ¶
Sorted list of the distinct Kind names present in this manifest's loaded documents.
consumers_of ¶
Walk the manifest and return every doc that references this one.
kind_for ¶
Return the KindPort registered for kind (by kind name), or None.
kind_for_alias ¶
Return the KindPort whose alias matches, or None.
iter_doc_deps ¶
Iterate a document's declared dep_filters dynamically.
get ¶
List documents as light {kind, name, apiVersion} dicts —
all of them, or only those of kind. For full Documents use
documents / all() instead.
describe ¶
Human-readable description of one document (metadata, spec highlights, relationships) — delegates to the Navigator.
summary ¶
Plain-text overview of the manifest (scope + the documents loaded, grouped by kind) — delegates to the Navigator.
inventory ¶
Structured inventory of everything loaded in this manifest.
dependency_tree ¶
Build a dependency tree for every document that has dep_filters.
dependency_tree_mermaid ¶
Mermaid flowchart of the dependency tree (docs → their dep_filter targets), as diagram source text.
er_diagram_mermaid ¶
Mermaid ER diagram of the document instances and their relationships, as diagram source text.
mindmap_mermaid ¶
Mermaid mindmap centered on the root document, fanning out to the manifest's kinds and docs.
quadrant_mermaid ¶
Mermaid quadrant chart of the docs — axes come from the CompositionProfile hints, not hardcoded kind names.
timeline_mermaid ¶
Mermaid timeline of the build_prompt composition phases.
kind_catalog_mermaid ¶
Mermaid classDiagram of every registered Kind (the catalog, not just the kinds instantiated in this scope).
export_diagrams_md ¶
Render every diagram to Markdown with embedded Mermaid blocks.
Returns {diagram_name: markdown}; when path is given the
files are also written to that directory.
matrix ¶
Agent × dependency matrix — which agent uses which docs —
as a structured dict (agents, dependencies, matrix).
impact ¶
Blast-radius analysis for changing/removing one document: which agents depend on it and through which dep_filters.
health ¶
Manifest health report — coverage gaps, orphan documents, missing refs — driven generically by CompositionProfile slots (no kind names hardcoded).
ascii_tree ¶
Terminal-friendly ASCII rendering of the dependency tree — no diagram renderer needed.
ref ¶
Resolve a file reference via source, or return value as-is.
Sync entry-point. Use this from CLI / tests / sync workers
whose top-level entry is asyncio.run. Async callers MUST
use meth:
ref_async — running this from inside an event
loop with a postgres source orphans the asyncpg pool.
ref_async
async
¶
Async variant of meth:
ref.
Use from inside the harness event loop (lifespan, request
handlers, async middleware). Awaits source.resolve_ref
directly on the caller's loop, which is the same loop that
owns the asyncpg pool — no cross-loop dispatch needed.
build_prompt ¶
build_prompt(
agent: str | None = None,
context: dict[str, Any] | None = None,
enabled_skills: list[str] | None = None,
enabled_guardrails: list[str] | None = None,
enabled_slots: dict[str, list[str]] | None = None,
) -> str
Build system prompt via template cascade.
Sync — uses _run_sync_helper to await source ref()
coroutines. Callers inside an async event loop must use
build_prompt_async to avoid the "called from inside a
running loop" guard.
build_prompt_async
async
¶
build_prompt_async(
agent: str | None = None,
context: dict[str, Any] | None = None,
enabled_skills: list[str] | None = None,
enabled_guardrails: list[str] | None = None,
enabled_slots: dict[str, list[str]] | None = None,
) -> str
Async variant of meth:
build_prompt. Use from
inside an async caller (test, middleware, etc.) so the
ref_async path keeps the source pool's loop binding
intact.
find_agent ¶
Find the best prompt-target document matching name.
Considers prompt_target_priority when multiple kinds match. Public API — use this instead of _find_agent().
resolve ¶
Apply layer overlays (sync). Delegates to Kernel.resolve_layers().
Memoizes per-layers so repeated mi.resolve({"tenant": X}) calls
from request handlers reuse the same merged instance instead of
re-reading every doc from disk. Cache lives on the base mi;
MIHolder.reload() swaps the base instance, which discards
this cache transparently.
From inside an event loop, prefer await mi.resolve_async(layers)
— the sync path falls back to a ThreadPool/asyncio.run dance
that orphans pool-based source adapters.
resolve_async
async
¶
Async variant of resolve. Use from inside an event loop
(request handlers, lifespan, EventBus consumer) so the source
pool stays tied to the caller's loop.