Skip to main content

Module lifecycle

Module lifecycle 

Source
Expand description

Task 20 — capability-driven extension lifecycle (spec §7.5).

Typed inventory/classification of extension manifests plus OPTIONAL, ADDITIVE passive deferred declarations. Absent declarations keep the documented legacy EAGER lifecycle byte-for-byte (no protocol version bump); present declarations are trusted local manifest expectations: they enable spawn deferral and MUST match the runtime’s initialize declarations exactly (names, schemas, digests) before any registration or grant — a mismatch shuts the child down and fails closed.

Nothing in this module spawns a process or touches the network: it reads bounded local manifest data and mints dormant descriptor tools.

Structs§

DeclaredExtensionContextProvider
Passive MEMORY/CONTEXT contribution provider declaration (continuous-memory spec §7.1) — e.g. Axel’s extension:axel-memory-manager:project-memory. DISTINCT from DeclaredExtensionProvider (model/LLM provider metadata): this declares a dormant context-contribution capability. Discovery, schema export, status inspection, and normal first prompts never spawn the owning extension; activation is exclusively a future exact memory-context lease (task A6).
DeclaredExtensionProvider
Passive provider declaration, field-compatible with the runtime’s RegisteredProviderSpec so a validated declaration can later back metadata-only registration.
DeclaredExtensionProviderModel
Field-compatible with RegisteredProviderModelSpec.
DeclaredExtensionTool
One passively declared tool: exactly the fields the runtime will register at initialize, pinned locally so activation can validate the live declaration against operator-known expectations.
DeferredDeclarations
OPTIONAL additive manifest block. Absent => legacy eager lifecycle.
DeferredExtensionTool
A dormant, manifest-declared extension tool. Registered like any live tool (stable ext:<plugin>:<name> identity, schema, digest — so wire resolution, discovery, exact grants, and the execution gate all work unchanged), but its implementation is DEFERRED: executing it requires the session extension-runtime lease capability (lease lifecycle commit), which starts only the OWNING extension after the execution gate has already authorized the call. Without that capability it fails typed and spawns nothing.

Enums§

ActivationTrigger
The earliest legitimately required activation trigger for a manifest (spec 7.5). Mixed extensions use the EARLIEST of their components — hook events fire passively during any turn, provider selection is an explicit routing choice, exact tool activation comes last; tool SEARCH alone never triggers a start.
DeferredLifecycle
ExtensionClass
Typed extension lifecycle classes (spec §7.5).

Constants§

DECLARED_DESCRIPTION_MAX_BYTES
DECLARED_DISPLAY_MAX_BYTES
DECLARED_MAX_CONTEXT_PROVIDERS
Bound on passive memory/context contribution provider declarations (continuous-memory spec §7.1). Deliberately small: one extension has no legitimate reason to contribute many distinct context surfaces.
DECLARED_MAX_PROVIDERS
DECLARED_MAX_PROVIDER_MODELS
Bounds for provider declarations.
DECLARED_MAX_TOOLS
Bounds for passive tool declarations (parity with the MCP descriptor cache budgets).
DECLARED_NAME_MAX_BYTES
DECLARED_SCHEMA_MAX_BYTES

Functions§

classify
Classify a manifest from its passive declarations. Pure and local.
dormant_extension_tools
Build the dormant deferred tools for one manifest. Deterministic (declaration order); returns nothing for manifests without validated declarations — descriptors are never invented. Never spawns.
earliest_trigger
has_context_provider
Whether a deferred block declares at least one memory/context contribution provider (continuous-memory spec §7.1).
validate_deferred
Bounded validation of a deferred block. Static reasons only; any violation fails the WHOLE manifest closed (validated before any spawn).
validate_manifest_deferred
Manifest-level coupling checks for a deferred block (review fix A1/ A2). Passive declarations are CAPABILITY claims: cataloging a dormant tool descriptor (or provider metadata) grants the extension future runtime reach, so it MUST be backed by the exact permission the live registration would require — otherwise a manifest could obtain discoverable/activatable surface it was never authorized to register. Likewise lifecycle = "hook" without a real manifest hook subscription has NO authorized trigger and can never legitimately start: it fails closed here instead of lingering as unreachable-but-cataloged state.
validate_runtime_provider_declarations
Strict initialize-time PROVIDER declaration check (Task 20 Commit B): the runtime’s registered provider specs must match the manifest’s passive declarations EXACTLY — same id set, display names, descriptions, model id sets, per-model display/context-window/ capability values, and config schemas as declared. A manifest that declares NO providers must see NO registered providers (a tool-only runtime sneaking provider metadata in is an undeclared capability). Static reasons only; callers shut the child down and fail closed.
validate_runtime_tool_declarations
Strict initialize-time declaration check: the runtime’s registered tool specs must match the manifest’s passive declarations EXACTLY — same name set (no missing, no undeclared extras) and identical canonical schema digests. Static reasons only; callers shut the child down and fail closed on any mismatch, before any registration or grant.