Skip to main content
← Back to list
01Issue
FeatureShippedSwamp CLIPublic
Assigneeszack

Relationships

#3628 typed-secrets 3.5: local entry points, validation diagnostics, context.runModel and model.method delivery

Opened by zack · 10/19/2026· Shipped 10/21/2026

Outcome

Complete Phase 3's local behavior path behind the internal typed-secrets option. Behavior evaluation writes reference-safe caches, validation reports static misuse, nested context.runModel invocations evaluate and deliver through their own bags, and model.method safely performs effects while accepting secret-bearing inputs through the synthetic step's delivery boundary.

This is Phase 3.5 of design/enablers/typed-secrets.md, Sections 3.2-3.4, 4.3 item 4, 4.5, 5, 8.1, 10.2 and 11. It depends on Phase 3.2, swamp-club#3625, Phase 3.3, #3626 and Phase 3.4, #3627, and completes the local integration built on Phase 3.1, #3619.

Scope

  • Local evaluation boundaries. Wire the local behavior evaluation passes and swamp behavior evaluate through the CEL boundary conversion. Secret-bearing results leave CEL as registered sentinels; sentinel-bearing bindings re-enter as Secrets. Keep runtime roots deferred according to the existing pass structure. The evaluated definition cache uses toPersistedForm and the run's registry, retaining sensitiveFormat: 1 and writtenReferences. Do not persist Secrets, orphan sentinels or plaintext, and do not turn evaluate into a delivery.
  • Validation diagnostics. Type-check behavior expressions in the typed CEL environment with vault.get returning Secret and the allowed-set overloads in place of runtime refusal overloads. Report statically identifiable misuse, including container comparisons in expressions that call vault.get. Findings include the file, authored expression location and stable code, never a value. Respect the pinned cel-js limits: dyn operands and Secret map keys can escape static checks; record-origin Secrets are dyn; type(Secret) is permitted; has() on a call result has its separate invalid_macro_argument behavior. Dynamic misuse remains a runtime refusal.
  • Validation delivery. When behavior validate invokes trusted pre-flight checks, use the shared load-at-delivery step and Phase 3.4 destination checks. Keep static type checking separate from provider reads and preserve the documented check argument contract.
  • context.runModel. Treat model_invocation_service.ts as both an evaluation entry point and a delivery. Give each nested invocation its own bag registry rather than sharing the parent-child workflow registry. Apply the reference checks, authorization, destination policy and attempt-scoped loading under RunVaultAccess. A nested invocation checks references anew; no Secret escapes into invocation inputs, stored definitions or outputs.
  • model.method effect gate. Before any delegate work, inspect the ambient evaluation fault context. Refuse if a fault is already recorded, or if the expression has a container comparison and a Secret has already been recorded. An error absorbed by ||, &&, exists or all must not allow an effect to start. Routing model/method names refuse Secrets with a recorded secret_destination_refused fault.
  • model.method inputs and results. Replace Phase 3.1's temporary blanket refusal of secret-bearing inputs with boundary conversion into the synthetic step's bag. The step applies destination policy and loads under its own attempt. Pass a plain copy to the delegate; no Secret reaches step creation or persistence. Adapt tagged fields in the latest resource or raw result through Phase 3.3's accessor adapter before returning to CEL, so stored reference text does not re-enter as a comparable string.
  • Rollout and documentation. Thread the existing internal option through testable local entry points without introducing a user-facing flag or enabling it in production. Update the option/encapsulation fitness checks as needed while retaining that constraint. Record 3.5 and the completed Phase 3 scope in the design, including the source map and diagnostic behavior.

Acceptance criteria

  • Behavior evaluate persists reference-safe caches through the existing format, with correct reference paths/occurrences and no plaintext or orphan sentinel text. Optional, nested and composed values cross the boundary correctly. Evaluation alone makes no delivery load.
  • Behavior validate reports static Secret misuse and the specified container-comparison cases with file/location/code and no value. Allowed operations and the pinned dyn, map-key, type() and has() cases behave as documented. Static checking does not execute methods or read providers.
  • Pre-flight validation checks use the shared delivery path and receive the documented resolved global arguments, sentinel-bearing method arguments and loaded bag. Refusing destinations prevent delivery.
  • context.runModel uses an independent registry, rechecks access/existence under the nested invocation, and delivers each reference once per attempt. Retry creates a new load attempt. Values never become persistent plaintext.
  • model.method's delegate is never called after an absorbed fault or an already-recorded Secret/container-comparison conflict. Secret routing names refuse before work. Allowed secret-bearing inputs reach the synthetic step as sentinels and arrive at the trusted method exactly once per reference per attempt.
  • Tagged fields returned by model.method behave as Secrets within the calling expression. Subsequent equality/string misuse refuses, while allowed passing/composition and null comparisons work. No Secret object crosses the delegate or persistence boundary.
  • Integrated local execution meets the Phase 3 exit criteria: exact trusted delivery for every canary class, clean Phase 3 sink inventory entries, destination refusals before delivery loads, value-free diagnostics, and unchanged non-secret behavior in log and JSON modes.
  • The internal option remains test-only and option-off behavior passes the existing characterization suites.

Use in-process unit and integration tests for evaluator/service/repository boundaries, real temporary persistence, authorization and load counts. Reuse the existing canary classes and refusal-coverage tests. Compiled-binary local behavior journeys and prohibited-sink scans belong in swamp-uat. Follow the repository verification workflow conventions when implementing the change.

Later slices

Phase 4 owns workflow evaluation/validation, guards/asserts, forEach and step identities, query predicates/projections, live/reconstructed/child outputs, resume/retry reconstruction, --last-evaluated, webhook bindings and global enablement. Keep the legacy paths until Phase 4 removes them. Phase 5 owns remote reference transport and its protected delivery protocol.

02Bog Flow
✓OPEN✓TRIAGED✓IN PROGRESS✓SHIPPED+ 1 MOREASSIGNED+ 6 MOREFINDINGS+ 29 MOREPR_LINKED+ 2 MORESESSION_SUMMARIZED

Shipped

10/21/2026, 5:23:27 PM

Click a lifecycle step above to view its details.

03Sludge Pulse
zack assigned zack10/21/2026, 12:23:59 PM

Sign in to post a ripple.