once: true hooks
Per-invocation scope; good for one-shot setup.
A once: true hook fires exactly once per runtime invocation, making it ideal for one-shot setup operations that must not repeat.
How It Works
Once-true hooks are an instance of Event Interposition, meaning they intercede in the runtime's event dispatch path. Rather than fire on every event occurrence, a hook marked once: true registers a scoped listener that executes at first event arrival within a single invocation, then deregisters itself for that invocation's remainder. This per-invocation scoping differs fundamentally from permanent registration: the hook re-enables automatically on the next invocation without manual teardown.
The mechanism works by checking an invocation-local flag before dispatch. On first event match, the hook runs and marks itself consumed. Subsequent matching events within the same invocation skip the handler. When invocation context ends, the flag resets, restoring the hook to eligible state.
What the Test Found
Runtime testing confirmed that once-true hooks enforce per-invocation scope reliably. A hook registered with once: true fires exactly once when its triggering event arrives, then silently skips all further matching events in that invocation. The behaviour is deterministic regardless of event volume or timing. Across multiple invocations of the same runtime, the hook re-fires on first match in each new invocation as expected, proving the flag resets correctly at invocation boundaries.
Why It Matters
One-shot setup operations—context initialization, resource pooling, state cache priming—often need to run exactly once per request/execution lifecycle without guard clauses or manual deregistration. A once: true hook eliminates boilerplate: declare the hook once in configuration and let runtime scope enforce the firing rule. This prevents accidental re-execution of idempotent-only operations and avoids the coupling cost of state-checking guards sprinkled through handler code.
Caveats
Per-invocation scope means the hook is not global-permanent. It will re-fire on the next runtime invocation. For truly single-firing hooks across all invocations, use explicit deregistration or a separate guard layer. Once-true semantics are most useful in request-scoped runtimes where invocation boundaries align with application semantics (HTTP request, agent turn, worker lifecycle).
- commit6844c14 ↗
primitive_feb040ccabd490409a77b114ed255199b87705613b1e2fd064d57fa75a6b679d2856ceafad6b1daa8f982493871b6ddc73ad7ea75cf7a661f38c2c1021f24649b304dc0903a75e91918b3a92bbf1b15d42541f8323a0bc3f8a3c209f2a8a6ad8956ab6545b429234eb5f3f5af0a0601Signed with an ed25519 key held off the repo. Anyone can verify against the published public key; nobody without the secret key can forge it. Click verify: it recomputes the signature in your browser. The signature proves integrity and authorship of this exact content — not a third-party timestamp or that the underlying claim is objectively true. signedAt is when the @f3/attest pipeline ran, not when the work happened; the evidence refs carry the source dates.
- instance-of Event Interposition Class
- introduces (in) Claude Code 2.1.0 (Night Zero) Release