Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Behavior Actors template-law audit (engineering record)

Historical evidence snapshot: the retained campaign verdicts were last committed at 1f20cc4. They describe that revision. The current repository quality audit tracks later verification and unresolved work.

This is the working record of a proof-driven audit of every reusable Behavior implementation exported by bombay-behavior-actors. It replaces the earlier routing-only review, which incorrectly accepted creator-local delivery from a standalone MessageAdapter and did not test BehaviorBase at the runtime resolution boundary.

This file is not a completion certificate. A verdict is final only after its negative cases have an independent oracle and the full repository gates pass on the recorded revision. Earlier versions of this file incorrectly declared the catalogue complete while several action-loss and hard-coded-path cases were still untested; those declarations are not evidence.

Active owner-contract follow-up ledger

This checkpoint records the four independently reported gaps before any production edit. It is not evidence that any gap is closed.

  • Exact blockers and smallest regressions:
    1. A generic framework can declare and finish shutdown phases through associated outputs, but cannot begin the one existing inferred builder without naming its hidden initial proof. A compile-only external-consumer regression must call a generic begin operation, declare two roles, and finish without spelling builder states.
    2. RelayChildReports forwards nested ingress but drops root ShutdownRequested ingress. Pure-fold regressions must cover the relay, FIFO pool, keyed pool, and relay under another transparent composition; the report lane must remain exactly once.
    3. Supervise retains worker installation and replacement facts but exposes no typed evidence to its inner application. An independent lifecycle trace must observe initial readiness with the exact worker nonce, replacement start/unavailability, replacement readiness, and permanent retirement or restart denial without guessing elapsed time.
    4. WorkerPool::new and KeyedWorkerPool::new cannot infer the customer route because no input mentions it. External-user compile tests must compare an associated construction operation, a route witness, and an extension operation, rejecting any dummy value that the pool does not semantically retain.
  • Source classification: serialized actor turns, fresh creation, and the absence of a cross-producer arrival-order guarantee are actor-model laws. Root-ingress preservation and the associated-output builder entry are derived static compositions. Lifecycle evidence after a committed ownership transition, its exact fact vocabulary, and restart timing are explicit Bombay policy rather than Agha guarantees.
  • Expected files: shutdown builder/re-exports and its interpretation test; report relay plus relay/pool composition tests; supervision protocol, ownership fold, adapter and model/fuzz tests; pool constructors and one external construction test; this audit record. Expected cumulative ceiling: 15 changed files.
  • Expected production delta: at most +260 / -40 / net +220. Tests and documentation are measured separately at each checkpoint.
  • Expected public API: add at most three public items: one begin operation, one exhaustive lifecycle fact sum (with data carried in its variants), and one owner-defined pool construction operation only if existing inherent syntax cannot express the inference law. Add no wrapper, alias, builder, route marker, registry, or erased envelope. Remove any superseded public machinery discovered in the same semantic path rather than retaining a compatibility layer.
  • Existing machinery to reuse: shutdown_after_children and its sole ChildShutdownPhases typestate; InjectEvent/ComposedEvent and the relay's named SendLayer; FixedFleetOwnership, OwnershipFold, and SupervisionEvent; DeliveryRoute, Recipient, BehaviorLayer, and the existing FIFO/keyed pool folds. No parallel planner, lifecycle wrapper, or pool factory object is permitted.
  • Toolchain finding: the repository pins Rust 1.95. General type-position ! remains unavailable on that toolchain and on stable 1.98; stabilizing it remains an active Rust 2026 project goal. The existing uninhabited Never remains the MSRV-compatible representation. Neither Never nor ! can constrain a customer route generic that occurs in no constructor input.

Supervision lifecycle design checkpoint

The application-facing lifecycle is one exhaustive event sum, not a wrapper, callback, query API, or second supervisor. One authoritative runtime fact may produce at most one inner lifecycle event. Multi-slot restart policy is carried as one named batch variant so the inner application performs at most one fold per outer turn.

Lifecycle eventData owned by the variantLegal source transition
Readystable proxy nonce, exact worker-incarnation nonce, explicit CreationKindthe join becomes complete after either a successful proxy creation or a successful worker creation; a replacement kind identifies replacement readiness
ReplacementStartedcomplete triggering WorkerStopped, exact running-worker creation facts selected by one-for-all/rest-for-one, and stable nonces selected while still awaiting initial creationone atomic restart admission succeeds; delayed admission is still unavailable and cannot become ready before its matching replacement creation commits
RetiredAfterStopcomplete WorkerStoppedrestart policy deliberately declines replacement
Retiredcomplete existing SupervisionFailurerestart admission, worker factory, worker creation, proxy creation, or stable-proxy continuity fails permanently
ShuttingDownall stable slot nonces whose availability is endingthe first accepted shutdown request; duplicate shutdown requests produce no second lifecycle event

The Ready join is symmetric: worker-first retains the worker fact without notifying, proxy-first retains the proxy fact without notifying, and the matching second success emits exactly one event. Duplicate, stale, wrong-kind, wrong-nonce, and contradictory facts remain the existing typed errors and emit no lifecycle event.

Lifecycle delivery must be an ordinary variant in the inner application's named exhaustive domain/system event sum. That sum owns EventIngress<Here, SupervisionLifecycle<A>>; existing structural EventLayer compositions lift the source-indexed ingress to it without a caller naming or recounting wrapper depth. Supervise must not make the lane optional, silently discard it, invoke a callback, or queue an interpreter-private self-message. Applications needing no lifecycle evidence use the standalone Supervisor topology owner instead.

Controlled-error atomicity requires a prepare/commit transition:

  1. validate the authoritative fact against the current ownership sum;
  2. prepare the next ownership state, effects, and one lifecycle event without mutating ownership (restart admission is calculated on a staged budget and newly built workers remain owned by the plan);
  3. fold the lifecycle event through the inner application;
  4. only after that fold succeeds, commit the prepared ownership state and combine the complete inner and ownership Actions products once.

If the inner fold rejects the lifecycle event, the prepared workers are dropped and neither the restart budget nor ownership state commits. This preserves B7 rather than relying on actor termination to hide partial mutation. For lifecycle-free authoritative facts, the existing ownership transition is unchanged.

Making this lane truthful is intentionally source-breaking: every current Supervise inner event that lacks the lane must be migrated explicitly. A scan finds 20 source/test/fuzz call-site files in addition to the supervision protocol, ownership fold, and adapter. With the nine files already changed in this follow-up, the complete migration necessarily exceeds the 15-file review checkpoint; compatibility modes would only evade that checkpoint while preserving the broken contract.

The audit question is not merely whether a template's fold compiles. For every capability or lifecycle fact, the review traces:

  1. who produced or supplied it;
  2. which concrete type retains it;
  3. which actor namespace owns its interpretation;
  4. which Actions lane emits it;
  5. which static interpreter authority realizes it; and
  6. how rejection or stale input remains typed and observable.

Laws and policies used

The source classification matters. Framework convention is not presented as actor-model law.

Actor-model laws

  • A1 — serialized turns: one actor processes one communication at a time; the transition determines communications, fresh creation, and the next behavior.
  • A2 — finite acquaintance: a transition may communicate with prior acquaintances, acquaintances in the current communication, and freshly created actors.
  • A3 — fresh creation: allocation is fresh; replacing behavior with become is distinct from actor creation.
  • A4 — no primitive effect ordering: the actor model does not require a general order among send, create, and become effects.

The primary-source classification and the exact boundary between these laws and Bombay constructions are summarized in the canonical actor-transition algebra and established-capabilities contracts.

Behavior Core laws

  • B1 — explicit effects: a successful pure fold returns complete Actions; it does not deliver, allocate, schedule, observe, or stop actors through an ambient side channel.
  • B2 — concrete protocols: protocol, event sum, send product, phase, error, and birth algebra remain statically visible.
  • B3 — capability distinctions: Recipient, ChildRoute, and EstablishedRecipient mean logical name, creator-local occurrence, and exact installed incarnation respectively. They are not interchangeable.
  • B4 — structural child authority: a local child effect resolves only when the running emitter's direct Birth algebra proves the named occurrence.
  • B5 — transparent projection: nominal roles cross BehaviorBase only while both canonical protocol and complete direct-birth algebra are equal.
  • B6 — compositional initialization: wrappers initialize their inner fold once, preserve its full result, and define how wrapper effects accumulate.
  • B7 — typed rejection: rejected creation carries no established capability; controlled transition failures do not partially commit a new behavior state.

Declared Bombay policy

  • P1 — staged child routes: a creator-local nonce may name a requested child before interpretation but is neither an address nor freshness proof.
  • P2 — commit before dependency: interpreters commit same-action creation before dependent local sends and observation requests.
  • P3 — explicit provenance: birth, replacement incarnation, observation relationship, timer generation, and shutdown request provenance travel as typed data.
  • P4 — structural return paths: interpreter facts return through the exact typed path selected by the owning composition.
  • P5 — explicit root shutdown: the root is composed directly as StopOnShutdown, FinalizeOnShutdown, or a shutdown coordinator; it does not discover a nested shutdown handler.
  • P6 — stable logical domains: discovery membership, configured downstream destinations, stable proxy identity, and transport names deliberately remain logical recipients.
  • P7 — truthful customer routes: a template that accepts an arbitrary customer capability retains its logical or exact form and emits the matching concrete effect without conversion.
  • P8 — creation-dependent shutdown plans: a coordinator may begin before its committed children are known. The topology owner reports its validated plan through Actions to an explicit parent return path; installation is one typed event, happens at most once, and retains any earlier shutdown request.

Hypotheses and verdicts

Failed → fixed means the hypothesis was false in the audited revision and this change repairs it. A pass means both the public type surface and the relevant fold/interpreter seam support the statement.

IDSourceFalsifiable hypothesisVerdict and evidence
H01A1, B1Every template transition is a deterministic fold returning all effects in Actions.Failed → fixed. Machine committed a prefix of a failed drain, Stash could replay a fallible inner fold after earlier actions became unreturnable, and Supervise could reject child adoption after the application fold succeeded. Machine now stages the complete drain, Stash statically requires an infallible inner fold, and adoption is an explicit reported outcome that preserves the rest of the application's Actions. Independent models compare state and complete outputs after every generated step.
H02B2Every exported behavior has concrete event, send, phase, error, and birth types.Pass. All Behavior implementations use associated concrete types; no catch-all envelope or registry exists.
H03B2No template uses dyn, Any, TypeId, downcasting, unsafe, serialization, or type-name dispatch for protocol composition.Pass. Static source scan is clean; the only type_name use is a test assertion.
H04B5, B6A topology-transparent wrapper preserves its inner BehaviorBase, protocol, birth algebra, initialization effects, and order.Pass. Stash, timing wrappers, watch/monitor, shutdown wrappers, and termination propagation project the inner base; equality constraints guard nominal role resolution. Composition and initialization tests exercise nested orders.
H05B4, B5Each standalone behavior that authors a direct topology exposes itself as BehaviorBase<Base = Self>.Failed → fixed. Proxy, WorkerPool, and KeyedWorkerPool lacked the projection. runtime_contracts::every_topology_owner_exposes_itself_as_its_behavior_base now proves proxy, fixed, dynamic, FIFO, and keyed owners.
H06B4, B5A topology-changing composition cannot inherit an inner nominal child role whose birth algebra it replaced.Pass. ResolveChildOccurrence requires exact protocol and birth equality. Supervise may expose its application base for inspection, but its proxy birth rewrite prevents stale role resolution; raw structural positions resolve against the running wrapper.
H07B4, P1Every production ChildDelivery, ObserveChild, ObserveCreation, ShutdownChild, or ChildTermination emitter owns the matching direct occurrence in its Birth.Pass after H05. All such emissions are confined to proxy/supervision/pool/lifecycle owners with the corresponding child leaf; occurrence propagation is tested through nested wrappers.
H08B3, B4A standalone MessageAdapter with NoBirths cannot emit creator-local child delivery.Failed → fixed. DeliveryRoute no longer accepts ChildRoute; a compile-fail example rejects the foreign route before runtime. The adapter retains logical, established, and closed mixed delivery modes only.
H09A2, B3, P6, P7Every delivery destination is supplied by configuration, a received message, discovery membership, or stable-proxy policy—not fabricated from child correlation.Pass. Customer-bearing routing, workflow, operations, persistence, pool, supervision, and discovery messages retain their supplied DeliveryRoute; stable internal logical destinations remain explicit Recipient values. A committed dynamic proxy is returned as the exact EstablishedRecipient issued by the creation interpreter; no logical destination is reconstructed from its child correlation nonce or allocation address.
H10B3, P7A received or configured exact endpoint is never weakened to a logical recipient before delivery, observation, or shutdown.Pass. Exact modes retain EstablishedRecipient/EstablishedActor and emit EstablishedDelivery, ObserveEstablished, or ShutdownEstablished; ReplyRoute retains mixed alternatives and its interpreter visits them in original order. No exact-to-logical conversion exists.
H11B7, P3A rejected EstablishedCreation cannot produce a recipient, actor, child route, birth, or restart-success fact.Pass. The rejected variant owns only nonce, kind, and CreationRejection; independent established-creation models cover allocation through binding failure.
H12B3, B4, P1After a named child commits, callers can retain both its exact incarnation and its creator-local role/nonce without reconstructing either.Failed → fixed. established_child now returns EstablishedChild<C, Role>, a named product of ChildRoute and EstablishedActor; rejection yields neither. Its shutdown_target method selects a heterogeneous plan branch from the retained role.
H13B4, P3Child observation and shutdown preserve the declared occurrence when equal child protocols appear more than once.Pass. All local lifecycle request types carry Occurrence; compile-fail tests reject head/tail or nominal-role substitution.
H14B2, B4A shutdown plan accepts only child behaviors whose exact event algebra owns ShutdownRequested.Pass. Homogeneous and heterogeneous coordinator compile-fail tests reject non-shutdown-capable children; request interpretation uses the resolved concrete child.
H15B4, P4Proxy reports retain the final parent event path through an outer shutdown transformation for every proxy-owning template.Failed → fixed. The reporting path is generic. Action-interpreted outer-StopOnShutdown tests execute creation and stop reports for application-owned supervision, standalone fixed supervision, both delayed forms, dynamic supervision, FIFO pools, and keyed pools. None supplies a structural path at the composition call.
H16B2, P4Every timer, observation, creation, shutdown, and parent-report request names the exact structural return path accepted by the enclosing event sum.Pass. runtime_contracts proves request/fact duals and nested path injection; send-product interpretation tests exercise each lane at the same path exactly once.
H17B6, P5Root shutdown can reach a FinalizeOnShutdown, retaining its final sends, creations, and stop result.Pass. The finalizer or coordinator is placed directly at the root; algebra tests prove delivery to the finalizer and full action preservation. No guardian alias selects that policy indirectly.
H18B3, P3Recurring logical watch and exact-once correlated monitoring remain distinct laws.Historical selected Watch evidence remains separate: it emits ObservePeer and accepts matching logical stop facts, including later incarnations. The new established-target affine-scope correlation, exact protocol-indexed accepted identity and cancellation authority are proposed and unexecuted here; they do not inherit that historical Pass. The candidate TerminationMonitor owns the single requested/observing/terminal control sum and emits one whole ObserveEstablished. Full new owning/consumer evidence and independent review are still required.
H19B3, B7, P3Termination monitoring represents requested, observing, rejected/cancelled, observed, and already-consumed relationships without correlated flags.The public TerminationObservation view derives from one target-owned control sum. Rejected cancellation remains nonterminal and consumingly recoverable alongside Stopped; startup rejection remains distinct. Candidate ownership, replay, both-order and full-report tests must pass before acceptance is recorded.
H20B3, B4Termination propagation chooses either an occurrence-aware local child or an explicitly late-bound logical peer, never an inferred destination.Pass. ChildTermination<A, O> and PeerTermination<A> are distinct target types with distinct request effects.
H21A3, B7, P3Supervision distinguishes replacement request, installation attempt, committed incarnation, rejection, stale result, and retirement.Pass. Incarnation and ownership folds use exhaustive phase enums and explicit creation kinds; independent supervision models and exhaustive/property suites compare the full sequence behavior.
H22A3, P3Restarted or replacement success is reported only after a replacement-designated creation commits.Pass. Proxy reports a request separately, checks CreationKind::Replacement, and emits committed resolution only after installation success; failure remains typed.
H23B7, P3Stale and duplicate lifecycle/timer facts cannot be reinterpreted as fresh success or consume another relationship.Failed → fixed. Timer reactions are now statically infallible, so a matching generation has one total consume-and-react transition. A later audit found consumption hidden inside debug_assert!, which made deadline, one-shot, periodic, and receive-timeout accept duplicates in optimized builds. Acceptance now validates and consumes in the production guard; the redundant preflight helpers were removed. Duplicate lifecycle facts are returned through exact typed errors; stale timer facts remain inert. Debug and optimized regressions, wrapper-order properties, and stack fuzzing exercise these cases.
H24B1, B2Named multi-lane send products preserve every lane exactly once and in their documented structural order.Pass. Each product has explicit SendEffects, SendsFor, and InterpretSends; runtime-contract and cross-lane tests record complete traces.
H25A2, B3, P6A dynamic supervisor exposes the exact committed stable proxy, never a reconstructed logical destination or the replaceable worker incarnation.Failed → fixed. Proxy and worker creation facts are retained and joined in either arrival order. Exactly one Started is produced only after both have committed. It returns the EstablishedRecipient<C::Protocol> issued by the proxy-creation commit; later worker replacement stays local to that proxy.
H26B1, P3Time is always a typed input or schedule request; no fold reads wall-clock time or sleeps.Pass. Production transitions consume Instant carried by lifecycle facts or TimerElapsed, and emit ScheduleAt/ScheduleAfter; Instant::now occurrences are test setup.
H27B2Semantic alternatives entering transition logic are sums, not booleans.Failed → fixed. Circuit-breaker Succeeded/Failed messages were collapsed into succeeded: bool; the private Completion::{Succeeded, Failed} sum now preserves the domain through the helper boundary. Query predicates remain ordinary booleans.
H28B2, B7Option<T> denotes one value or absence, not overlapping lifecycle phases or correlated capabilities.Pass after targeted inspection. Dynamic child, proxy incarnation, pool slot, breaker, lease, workflow, watch, and monitor phases use enums. Remaining options are exact absence queries, optional independent metadata, or optional one-effect outputs.
H29B1, B6Wrapper reactions cannot drop inner sends or creations when selecting Goto or Stop.Pass. Wrappers transform the complete action product with map_sends/named reconstruction; terminal and initialization tests assert retained creates, sends, and verdicts.
H30A3, P1No actor address or exact endpoint is derived from nonce arithmetic, sequence position, timing, or address reuse.Pass. From<u64> in fleet code creates configured local nonces only; exact addresses enter exclusively through interpreter facts.
H31B7Invalid configuration, overlap, exhaustion, unknown targets, and interpreter rejection remain typed results rather than production panics.Failed → fixed. The conservation pass found errors that named only a key, nonce, or reason while consuming the remaining owned input. Machine, router policies, circuit breaker, rate limiter, priority queue, sequencer, lease, acknowledgements, correlation, task, barrier, workflow, health, readiness, presence, registry, pub-sub, supervision, and pools now return the complete rejected command or lifecycle fact. The only production expect is the proved positive capacity + full buffer => oldest value exists invariant.
H32A4, B6, P2Any ordering relied upon beyond actor-model law is declared as Bombay policy and tested at the interpreter boundary.Pass. Create-before-dependent-send/request and wrapper initialization order are documented as policy; send products define their own deterministic interpretation order without claiming it as an Agha guarantee.
H33B2, B3, P7Every genuine customer-passing template accepts logical, exact, or deliberately mixed reply capabilities without allowing the route protocol to disagree with the reply message.Failed → fixed. Customer, payload, and membership fields now carry one Route: DeliveryRoute that projects its exact protocol and send product; the duplicate protocol marker and repeated reply protocol parameters are removed. A catalogue compile/fold matrix instantiates every affected family with EstablishedRecipient and ReplyRoute, protocol mismatch is compile-fail, and logical recursive protocol tests remain finite.
H34B1–B3, B7, P4, P8Homogeneous and heterogeneous shutdown coordinators can receive their validated plans after committed child creation without out-of-band mutation, flags, plan substitution, lost early shutdown, or repeated installation.Failed → fixed. ShutdownState is the complete lifecycle sum. A topology owner emits ReportShutdownPlan through Actions; the interpreter constructs the exact outer InstallShutdownPlan<P> event from the carried typed return path. Unit, independent model/property, fuzz, and compile-fail coverage exercise both plan families, duplicate installation, early shutdown, stale stops, ordered phases, and empty-plan termination.
H35B2–B4, B7, P1, P3A standalone fixed supervisor owns only supervision, while application command selection is expressed by ordinary typed actor composition.Failed → fixed. The former SupervisedWorkers policy engine combined fixed ownership with a selector but owned no distinct lifecycle law. It and its availability-policy surface were removed. Supervisor now implements the concrete fixed-fleet fold directly; an application behavior or routing actor owns command selection and its own typed rejection law.
H36B1–B4, B6–B7, P1–P4, P8Creation-dependent shutdown planning retains a single typed implementation that both direct applications and generic frameworks can carry.Failed → fixed. ChildShutdownPlan owns the distinct join from committed direct-child creation facts to one reported heterogeneous plan. Its direct builder remains the semantic implementation. DeclareShutdownPhase and FinishShutdownPhases expose only associated output types, so a framework neither names nor copies the hidden availability and phase proofs.
H37B1–B2, B6–B7A reusable actor template is retained only when it owns a distinct state-transition or typed event/effect transformation law.Failed → fixed. Guardian aliases, established-watch policy aliases, feature aliases, selector-policy supervisors, backoff parameterization wrappers, and recipe functions were removed. The child shutdown planner remains because it owns creation-fact correlation and plan reporting. Watch and exact-once monitoring, application and standalone backoff, FIFO and keyed pools, and homogeneous and heterogeneous coordinators remain separate because their recurrence, input, assignment, or typed effect transitions differ.
H38B1–B4, B6–B7, P3Expected supervised-command unavailability is observable after mailbox admission and never collapses into an opaque actor crash.Failed → fixed. Proxy returns the complete sender, phase, and command through its established parent-report lane in every unavailable phase. FIFO pools join that return with worker-stop in both orders, including restart exhaustion and shutdown. DynamicSupervisor returns it through the retained Start outcome route, while Supervise routes it into an explicitly authored application-domain event only when that application owns a stable-child route. All three owner paths are interpreted through an outer shutdown composition; the pool join, dynamic customer route, application event, duplicate replay, restart exhaustion, and shutdown cases pass in debug and optimized builds.
H39B1–B2, P1–P4A generic consumer can carry the child-shutdown builder without naming hidden typestate or implementing a second planner.Failed → fixed. Generic full-interpreter tests declare and finish phases using only the two associated-output operation traits; direct syntax, reverse order, early shutdown, and all existing typed failures retain the same builder implementation.
H40B1–B2, P1–P3A composition owner exposes every transitive intentional logical protocol host statically, preserving duplicate occurrences and excluding exact-only endpoints.Failed → fixed. LogicalHostRequirements is blanket-derived from the concrete root sends product and every transitive birth node. LogicalDeliveryProtocols follows each real send-product interpretation order: logical deliveries and interpreter requests with logical recipients contribute their protocols, while established and creator-local routes contribute none. The structural regression derives P, Q, Q without owner metadata; focused request regressions distinguish customer, logical diagnostic, and exact diagnostic routes. No registry, erased envelope, normalization, or runtime lookup was added.

The repairs require no new Behavior Core algebra, runtime registry, dynamic type, forwarding actor, or address reconstruction. The verification record below is authoritative only when every listed gate is green on the same tree.

Complete template coverage

The hypotheses above were applied to every exported behavior family, not just the templates implicated by the initial blockers.

FamilyBehavior templates auditedPrincipal hypotheses
Base compositionMachine, MessageAdapter, MessageAdapterWithRouteH01–H03, H08–H10, H24, H27–H31
Transparent state/lifecycle wrappersStash, StopOnShutdown, FinalizeOnShutdown, Watch, TerminationMonitorWith, PropagateTerminationH04, H06, H13, H16–H20, H23–H24, H29
Shutdown ownershipShutdownCoordinator, HeterogeneousShutdownCoordinatorH07, H12–H17, H23–H24, H29–H32, H34, H36–H37
Lifecycle taskTaskH01–H03, H09–H10, H24, H27–H31, H33
SupervisionProxy, application-composed Supervise, standalone Supervisor, and DynamicSupervisor; delayed replacement is the shared RestartTiming policy inside fixed ownershipH05–H07, H10, H13, H15–H16, H21–H25, H28–H33, H35, H37
Worker poolsWorkerPool and the affinity-owning KeyedWorkerPool, both using the same fixed-ownership and stable-child layersH05, H07, H09–H10, H13, H15–H16, H21–H24, H28–H31, H33
TimingDeadline, OneShot, Periodic, ReceiveTimeout, LeaseH01–H04, H10, H16, H23–H24, H26, H28–H33
RoutingRouter with all strategies, WorkQueue, Buffer, PriorityQueue, OrderGate, Sequencer, Deduplicator, RateLimiter, CircuitBreaker, Correlator, AcknowledgementsH01–H03, H09–H10, H23–H24, H27–H31, H33
DiscoveryRegistry, Resolver, Topic, PubSub, PresenceH01–H03, H09–H10, H16, H23–H24, H26–H31, H33
WorkflowLatch, Barrier, WorkflowH01–H03, H09–H10, H23–H24, H27–H31, H33
Operations/persistenceConfiguration<FeatureSet<_>>, Health, Readiness, CacheH01–H03, H09–H10, H23–H24, H27–H31, H33, H37

Routing strategies are policy values owned by Router, not actors with their own effect boundary. Redundant aliases for the same observation and shutdown state machines were removed rather than counted as separate templates.

Adversarial law coverage

The audit does not count a constructor smoke test as proof of a state-machine law. The following independent suites model state after every generated step:

SurfaceIndependent or adversarial evidence
Creation and exact capabilitiescreation, custody, child_creation_actor, creation_settlement_custody
Machine and replayfsm_properties, exhaustive, fsm_sequences
Stash and wrapper lane isolationstash_properties, two_buffer, cross_lane, stack_sequences
Watch, monitoring, and terminal propagationexact_termination_model, terminal_outcome_sequences, catalogue_sequences
Stable proxy, fixed supervision, and dynamic supervisionstable_proxy_shutdown_model, fixed_supervisor_initialization, dynamic
FIFO and keyed worker poolsfifo_pool, keyed_pool, direct_pool_customer, direct_worker_shutdown, fifo_pool_sequences
Homogeneous and heterogeneous shutdownshutdown_model, heterogeneous_shutdown, shutdown_plan_sequences, plus coordinator compile-fail and ordering tests
Versioned operations and cachecatalogue_invariants models configuration, feature-set normalization, readiness, health tombstones, and LRU ownership
Routing and correlationcatalogue_models, routing_invariants, and correlation_invariants model stable priority, bounded ownership, token arithmetic, round robin, FIFO worker availability, sequencing, deduplication, ordering, correlation, and acknowledgements
Timereceive_timeout, timing_invariants, receive_timeout_sequences; timer-wrapper composition and initialization are attacked by init_contract, cross_lane, and stack_sequences
Workflowworkflow_invariants models barrier generations, latch single release, dependency activation, and terminal rejection; catalogue_sequences fuzzes workflow inputs
Discoveryregistry and topic generated models live in catalogue_invariants; presence is generation-fuzzed by catalogue_sequences; resolver and keyed publication retain focused atomic owner tests because their immutable/snapshot state spaces are already exhaustively covered there

Each model uses different vocabulary and ordinary collections. It compares observable state and complete owned outputs after every operation, including rejection and stale input. Fuzz targets are retained as a separate layer; they do not replace the reference models.

Verification checkpoint — 2026-08-27 working tree

  • cargo nextest run --workspace --no-fail-fast: 542 passed, none skipped.
  • cargo clippy --workspace --all-targets: pass without Rust warnings.
  • The nominal-protocol, pool named-product, keyed/FIFO model, and corrected supervision regressions pass in both debug and optimized profiles.
  • The pool state-machine fuzz target completed 5,000 executions after keyed delegation.

This is an intermediate checkpoint, not the final repository gate. The final record must be updated only after cargo nextest run --workspace and nix flake check pass on the same committed tree.

Capability conclusions

The three recipient forms have non-overlapping authority:

CapabilityMeaningLawful use in templates
Recipient<P>Logical protocol namecaller reply, discovery membership, transport name, or stable proxy identity
ChildRoute<C, O>One role and nonce in the current creator's namespaceonly a topology owner whose direct Birth proves O
EstablishedRecipient<P> / EstablishedActor<C>One exact installed incarnationexact delivery, observation, shutdown, or retained post-creation capability
ReplyRoute<P>Closed logical-or-exact customer capabilityone running template intentionally accepts both forms without conversion

EstablishedChild<C, O> intentionally retains the latter two facts together. It is an Actors-level named product over existing capabilities. It neither allocates an actor nor extends the Behavior algebra.

Future changes must repeat the six-step provenance trace above. A test that only inspects the emitted value is insufficient for creator-local effects: the running emitter must also prove that its interpreter can lawfully resolve the same occurrence.