Core API
•7 min read
Types Reference
Complete type definitions for Directive.
Core Types
ModuleDef
interface ModuleDef<M extends ModuleSchema> {
name: string; // unique module identifier
schema: M; // type definitions for facts, events, requirements
init?: (facts: Facts<M>) => void; // set default fact values
derive?: Derivations<M>; // computed values (auto-tracked)
effects?: Effects<M>; // fire-and-forget side effects
constraints?: Constraints<M>; // declarative rules that emit requirements
resolvers?: Resolvers<M>; // handlers that fulfill requirements
}
System
interface System<M extends ModuleSchema> {
// State access
readonly facts: Facts<M["facts"]>; // read/write proxy for facts
readonly derive: InferDerivations<M>; // read-only computed values
readonly events: EventsAccessor<M>; // typed event definitions
readonly constraints: ConstraintsControl; // enable/disable constraints
readonly effects: EffectsControl; // enable/disable effects
readonly history: HistoryAPI | null; // time-travel (null if disabled)
// Lifecycle
start(): void;
stop(): void;
destroy(): void;
// Status flags
readonly isRunning: boolean;
readonly isSettled: boolean;
readonly isInitialized: boolean;
readonly isReady: boolean;
whenReady(): Promise<void>;
// Mutations and events
dispatch(event: SystemEvent): void;
batch(fn: () => void): void;
// Subscriptions
read(derivationId: string): unknown;
subscribe(ids: Array<ObservableKeys<M>>, listener: () => void): () => void;
watch(id: ObservableKeys<M>, callback: (newValue, previousValue) => void, options?: { equalityFn?: (a, b) => boolean }): () => void;
when(predicate: (facts: Facts<M>) => boolean, options?: { timeout?: number }): Promise<void>;
// Debugging and persistence
inspect(): SystemInspection;
settle(maxWait?: number): Promise<void>;
explain(requirementId: string): string | null;
getSnapshot(): SystemSnapshot;
restore(snapshot: SystemSnapshot): void;
getDistributableSnapshot(options?: DistributableSnapshotOptions): DistributableSnapshot;
watchDistributableSnapshot(options: DistributableSnapshotOptions, callback: (snapshot) => void): () => void;
}
ConstraintsControl
interface ConstraintsControl {
disable(id: string): void;
enable(id: string): void;
}
EffectsControl
interface EffectsControl {
disable(id: string): void;
enable(id: string): void;
isEnabled(id: string): boolean;
}
HistoryAPI
interface HistoryAPI {
readonly snapshots: Snapshot[]; // all captured state snapshots
readonly currentIndex: number; // position in the snapshot timeline
goBack(steps?: number): void; // undo state changes
goForward(steps?: number): void; // redo state changes
goTo(snapshotId: number): void; // jump to a specific snapshot
replay(): void; // replay all snapshots from the beginning
export(): string; // serialize timeline to JSON
import(json: string): void; // restore a previously exported timeline
}
Schema Types
ModuleSchema
interface ModuleSchema {
facts: Record<string, SchemaType>; // mutable state
derivations?: Record<string, SchemaType>; // computed values
events?: Record<string, Record<string, SchemaType>>; // event payloads
requirements?: Record<string, Record<string, SchemaType>>; // requirement payloads
}
TypeBuilder
// Fluent API for defining schema types with modifiers
interface TypeBuilder<T> {
nullable(): TypeBuilder<T | null>; // allow null values
optional(): TypeBuilder<T | undefined>; // allow undefined values
default(value: T): TypeBuilder<T>; // set a default when omitted
}
Utility Types
Type helpers for extracting keys and return types from a module schema.
FactKeys
// Extract fact key names from a module schema
type FactKeys<M extends ModuleSchema> = keyof M["facts"] & string;
FactReturnType
// Get the return type of a specific fact from a module schema
type FactReturnType<M extends ModuleSchema, K extends FactKeys<M>> = InferFacts<M>[K];
DerivationKeys
// Extract derivation key names from a module schema
type DerivationKeys<M extends ModuleSchema> = keyof M["derivations"] & string;
DerivationReturnType
// Get the return type of a specific derivation from a module schema
type DerivationReturnType<M extends ModuleSchema, K extends DerivationKeys<M>> = InferDerivations<M>[K];
ObservableKeys
// Union of all fact and derivation keys – used in subscribe() and watch()
type ObservableKeys<M extends ModuleSchema> = FactKeys<M> | DerivationKeys<M>;
Constraint Types
ConstraintDef
interface ConstraintDef<S, R extends Requirement> {
priority?: number; // higher = evaluated first (for conflict resolution)
async?: boolean; // enable async precondition evaluation
timeout?: number; // max time for async constraints (ms)
after?: string[]; // constraint IDs that must evaluate before this one
deps?: string[]; // explicit fact dependencies (recommended for async constraints)
meta?: DefinitionMeta; // optional metadata for debugging and devtools
// Precondition: when should this constraint fire?
when: (facts: Facts<S>) => boolean | Promise<boolean>;
// What requirement does it emit when the condition is met?
require: RequirementOutput<R> | ((facts: Facts<S>) => RequirementOutput<R>);
}
Requirement
// The unit of work passed from constraints to resolvers
interface Requirement {
type: string; // matches a resolver's requirement field
[key: string]: unknown; // arbitrary payload for the resolver
}
Resolver Types
ResolverDef
interface ResolverDef<S, R extends Requirement> {
// Which requirement type this resolver handles
requirement: string | ((req: Requirement) => req is R);
// Dedupe key: identical keys share a single in-flight resolution
key?: (req: R) => string;
// Resilience
retry?: RetryPolicy;
timeout?: number;
// Batching: group multiple requirements into one call
batch?: BatchConfig;
// Resolution strategies (provide one)
resolve?: (req: R, context: ResolverContext<S>) => Promise<void>;
resolveBatch?: (reqs: R[], context: ResolverContext<S>) => Promise<void>;
resolveBatchWithResults?: (reqs: R[], context: ResolverContext<S>) => Promise<BatchItemResult[]>;
meta?: DefinitionMeta; // optional metadata for debugging and devtools
}
ResolverContext
// Provided to every resolver during execution
interface ResolverContext<S> {
readonly facts: Facts<S>; // read/write access to module state
readonly signal: AbortSignal; // cancelled when resolver times out or system stops
readonly snapshot: () => FactsSnapshot<S>; // capture a point-in-time copy of facts
}
RetryPolicy
interface RetryPolicy {
attempts: number; // max number of retries
backoff: "none" | "linear" | "exponential"; // delay strategy between attempts
initialDelay?: number; // base delay in ms
maxDelay?: number; // cap on backoff growth
// Return false to stop retrying early (e.g., for non-transient errors)
shouldRetry?: (error: Error, attempt: number) => boolean;
}
Effect Types
Effect
interface EffectDef<S extends ModuleSchema> {
// Optional: only run when these specific facts change
deps?: Array<keyof InferFacts<S> & string>;
// Side effect function (receives current and previous fact values)
run: (facts: InferFacts<S>, prev: InferFacts<S> | null) => void;
meta?: DefinitionMeta; // optional metadata for debugging and devtools
}
Meta Types
DefinitionMeta
Optional metadata for constraint, resolver, effect, and derivation definitions. Purely informational – never read during reconciliation. Surfaces in inspect(), explain(), and devtools.
interface DefinitionMeta {
label?: string; // Human-readable name
description?: string; // Longer explanation
category?: string; // Grouping key for devtools filtering
color?: string; // CSS hex color for visualization
tags?: string[]; // Multi-dimensional labels for filtering
[key: string]: unknown; // Extensible for plugins
}
MetaAccessor
// O(1) metadata queries — available as system.meta
interface MetaAccessor {
module(id: string): DefinitionMeta | undefined;
fact(key: string): DefinitionMeta | undefined;
event(name: string): DefinitionMeta | undefined;
constraint(id: string): DefinitionMeta | undefined;
resolver(id: string): DefinitionMeta | undefined;
effect(id: string): DefinitionMeta | undefined;
derivation(id: string): DefinitionMeta | undefined;
byCategory(category: string): MetaMatch[];
byTag(tag: string): MetaMatch[];
}
MetaMatch
// Result from bulk meta queries (byCategory, byTag)
interface MetaMatch {
type: "module" | "fact" | "event" | "constraint" | "resolver" | "effect" | "derivation";
id: string;
meta: DefinitionMeta;
}
See Definition Meta for usage examples.
Error Types
ErrorBoundaryConfig
interface ErrorBoundaryConfig {
// Per-component error handlers (use a string strategy or custom function)
onConstraintError?: RecoveryStrategy | ((error: Error, constraint: string) => void);
onResolverError?: RecoveryStrategy | ((error: Error, resolver: string) => void);
onEffectError?: RecoveryStrategy | ((error: Error, effect: string) => void);
onDerivationError?: RecoveryStrategy | ((error: Error, derivation: string) => void);
// Catch-all for any error in the system
onError?: (error: DirectiveError) => void;
// Automatic retry and circuit breaker for transient failures
retryLater?: RetryLaterConfig;
circuitBreaker?: CircuitBreakerConfig;
}
Snapshot Types
SystemSnapshot
// Serializable state for persistence, hydration, or time-travel
interface SystemSnapshot {
facts: Record<string, unknown>; // all current fact values
version?: number; // schema version for migration support
}
DistributableSnapshotOptions
interface DistributableSnapshotOptions {
includeDerivations?: string[]; // which derivations to include (default: all)
excludeDerivations?: string[]; // derivations to exclude
includeFacts?: string[]; // which facts to include (default: none)
ttlSeconds?: number; // snapshot TTL in seconds
metadata?: Record<string, unknown>; // custom metadata attached to snapshot
includeVersion?: boolean; // include a version hash for cache diffing
}
Derivations are included by default – they're computed read-only values safe to distribute. Facts are opt-in to avoid distributing mutable source-of-truth state that could become stale.
DistributableSnapshot
interface DistributableSnapshot<T = Record<string, unknown>> {
data: T; // the selected derivations and/or facts
createdAt: number; // timestamp when snapshot was created
expiresAt?: number; // timestamp when snapshot expires (if ttlSeconds set)
version?: string; // version hash (if includeVersion set)
metadata?: Record<string, unknown>; // custom metadata (if provided)
}
SystemInspection
// Returned by system.inspect() for debugging the current runtime state
interface SystemInspection {
unmet: RequirementWithId[];
inflight: Array<{ id: string; resolverId: string; startedAt: number }>;
constraints: Array<{
id: string;
active: boolean;
disabled: boolean;
priority: number;
hitCount: number;
lastActiveAt: number | null;
meta?: DefinitionMeta;
}>;
resolvers: Record<string, ResolverStatus>;
resolverDefs: Array<{ id: string; requirement: string; meta?: DefinitionMeta }>;
effects: Array<{ id: string; meta?: DefinitionMeta }>;
derivations: Array<{ id: string; meta?: DefinitionMeta }>;
modules: Array<{ id: string; meta?: DefinitionMeta }>;
traceEnabled: boolean;
trace?: TraceEntry[];
}
Next Steps
- Core API – Function reference
- React Hooks – React API
- Schema & Types – Schema types

