microsoft / microsoft/agent-governance-toolkit
RFC: durable artifacts carry labels across sessions — extending accumulated-context governance past workflow lifetime
- Dominant language
- Python
- Stars
- 6.3k
- Forks
- 1.1k
- Avg merge
- 5d 11h
- Merged PRs (30d)
- 142
Description
### Summary
This RFC proposes host-side requirements for propagating IFC labels through durable artifacts such as long-term memory entries, summaries, notes, and vector-store records. The gap is that ACS’s stateless label flow model can correctly govern a single session, but cannot by itself preserve sensitivity labels when agent-produced data is written during one session and recalled later by a fresh session. The proposal is to require hosts to persist result_labels with durable artifacts by artifact identity, fold those labels back into snapshot.ifc.source_labels on recall, enforce monotonic label joins on rewrite, and treat unlabeled durable artifacts conservatively during migration.
### Motivation
Relates to: #2797 / #2800 accumulated context governance, #3084 / #3199 TypeScript parity, #3245 FIDES-compatible IFC layer
Spec sections: ACS §11 stateless label flow policy model, §13.2 result_labels
Type: specification + design gap, explicitly scoped out of #2797
#2797 introduced ContextEnvelope to stop sensitivity accumulating unnoticed across a multi-agent workflow. Its “What I’m leaving out for now” section names a remaining gap:
Splitting work across sibling agents, sessions, or separate workflows so no single envelope ever sees all the labels. Catching that needs a per-principal accumulation register.
This RFC addresses one specific case inside that gap: labels that reach durable storage and return later.
For example, an agent writes to long-term memory or a vector store during a session carrying high-sensitivity labels. That session ends and its envelope is discarded, correctly. Days later, a fresh session recalls the entry. Nothing in the current model necessarily brings the labels back with it.
ACS cannot catch this by construction: the runtime is stateless, and the write and read are two separate evaluations with no shared runtime state, possibly weeks apart. §13.2 correctly delegates propagation to the host, but it primarily describes the intra-loop case. A host implementing it literally is not clearly told that “later evaluations” may span sessions, nor that labels attach to the artifact rather than the conversation.
The result is a governance gap where sensitive content can be persisted with labels during Session A, recalled without labels during Session B, and then pass §11 clearance checks as if it were unlabeled. This is the default failure mode unless the host independently re-materializes the artifact’s labels.
ADR Review
The ADR index (adr/index.md) was reviewed. No existing ADR directly addresses information-flow control labels, durable memory, artifact-scoped sensitivity, or cross-session propagation.
Two ADRs are relevant:
ADR-0016 (Trust Ceiling Propagation for Delegation) establishes monotonic propagation semantics across live delegation chains, but does not address persistence or restoration across serialization boundaries.
ADR-0013 (Fail Closed on Policy Evaluation Errors) reinforces the project's fail-closed security posture and informs the handling of unlabeled durable artifacts and migration behavior.
This RFC therefore proposes a new architectural decision rather than modifying an already recorded one. If accepted, the topic may warrant a dedicated ADR.
### Detailed Design
Why artifact-scoped rather than per-principal
#2797 suggests a per-principal accumulation register. That is the right shape for sibling-agent and parallel-workflow cases. For the durable-storage case specifically, artifact-scoped labels are a better fit.
Precision. A per-principal register raises the floor for every future action by that principal, whether or not the action touches the sensitive data. Artifact-scoped labels only affect sessions that actually recall the artifact.
Termination. A per-principal register accumulates monotonically and has no natural reset. A principal that once handled sensitive data may become permanently elevated, which in practice risks being disabled. Artifact labels are bounded by the artifact: retire the artifact and the label goes with it.
The two mechanisms compose rather than compete. A per-principal register is still needed for split-across-sibling cases where no artifact is written.
The case, step by step
Session A. Agent retrieves content; the host supplies snapshot.ifc.source_labels accordingly. Every sink in Session A is checked correctly against them.
Agent writes a note, summary, preference, memory entry, or embedding-backed record to long-term storage. The host persists result_labels alongside the produced data, per §13.2.
Session A ends. In-loop state and its envelope are discarded. This is correct; the runtime remains stateless.
Session B, days later, is fresh. Its source_labels start empty.
The agent recalls the durable artifact from step 2 into context.
A later tool call is evaluated. Unless the host re-materialized the artifact’s stored labels into snapshot.ifc.source_labels, the recalled content presents as unlabeled and the §11 clearance check passes.
Step 6 is the default behavior this RFC aims to prevent.
Proposed additions
1. Durable stores are labeled sinks; recall is a labeled source
A host that persists agent-produced data to any store surviving session termination MUST persist the associated result_labels with the artifact, keyed by artifact identity, not by session, turn, workflow, or envelope.
On recall, the host MUST fold the artifact’s stored labels into snapshot.ifc.source_labels for subsequent evaluations in the recalling session.
This may be implied by “persists returned result_labels alongside sink-produced data,” but the keying requirement is what determines whether the cross-session case is protected. A host that keys labels by session discards exactly the labels that matter.
2. Artifact labels are monotonic under rewrite
Where an artifact is rewritten, its persisted label MUST be the join of the existing label and the new result_labels, not a replacement.
This extends the same principle already used by ContextEnvelope within a workflow: max-lattice sensitivity and grow-only restrictions. Without monotonic rewrite, a host can still be bypassed:
Write from a high-sensitivity context.
Rewrite the same artifact from a low-sensitivity context.
The second write lowers or removes the artifact label.
A later recall treats the artifact as less sensitive than its contents require.
Agent memory is routinely updated in place, so this is not an edge path.
Corollary: retiring a mislabeled artifact is a delete, not an update. Under monotonicity, an update cannot lower a label. That is intended and should be documented because it is surprising to implementers.
3. Unlabeled durable artifacts and migration
§11 already says missing, non-array, empty, or unknown labels should be treated as denials unless policy proves lower sensitivity by other means. Applied to durable artifacts, that is the right default.
The explicit migration consequence is important: every artifact predating a host’s IFC rollout is unlabeled, so the first recall against an existing corpus may deny.
Implementers will be tempted to default unlabeled artifacts to the lowest label. That removes information-flow control while leaving the machinery in place and reporting green. The spec should name silent default-to-clean as non-conformant.
A conformant host should either:
Treat unlabeled durable artifacts as maximally sensitive; or
Record an explicit, attributable attestation for a bounded backfill, naming who attested and on what basis, since the claim cannot be verified retroactively.
Related question: resolved escalation and accumulated labels
This may deserve a separate issue, but it interacts with this proposal and with #3126.
§13.2 says the host MUST NOT propagate result_labels for actions that did not proceed, including unresolved escalate. Behavior after a resolved escalation is less clear.
Approvals bind to enforced_identity, a hash of the exact action, implying an approval authorizes one action and nothing further. If that reading is correct, a session carrying a high source label escalates at every subsequent sink, with each sink requiring a separate approval.
Whether that is intended matters. Published containment research reports high approval rates on permission prompts, so one prompt per action may produce habituated approval.
If an approval can instead clear accumulated labels for a session — effectively a break-glass with recorded authorization — that is a meaningful state transition the spec does not currently describe. Either answer is defensible; the current text implies per-action approval without saying so.
### Alternatives Considered
Per-principal accumulation register
A per-principal accumulation register was considered and is already suggested by #2797. It remains appropriate for sibling-agent and parallel-workflow cases where no artifact is written.
It is less precise for durable storage because it raises the sensitivity floor for every future action by that principal, even when the action never recalls or uses the sensitive artifact. It also has no natural termination point: once a principal has handled sensitive data, the register may remain elevated indefinitely.
Session-scoped label persistence
Another approach is to persist labels by session, turn, workflow, or envelope. This does not solve the durable-storage case because the labels that matter must survive the session boundary. If labels are keyed by session, they are discarded at exactly the point where cross-session recall becomes dangerous.
Default unlabeled artifacts to clean
Defaulting unlabeled durable artifacts to the lowest label avoids migration friction but defeats IFC in the most important migration scenario. Existing corpora become implicitly trusted without evidence, while the governance machinery still appears to be working. This should be explicitly non-conformant.
Runtime state
The runtime could theoretically track cross-session accumulation, but that conflicts with the existing stateless invariant. This RFC deliberately keeps the runtime stateless and places the new requirements on the host, storage layer, and recall path.
### Security Implications
This change strengthens the trust model for durable memory, vector stores, long-term notes, summaries, and other persisted agent-produced artifacts.
Without artifact-scoped labels, sensitive information can cross a session boundary and re-enter a fresh session without its original labels. That creates an information-flow laundering path:
Sensitive content enters Session A.
The agent writes a derived artifact to durable storage.
Session A ends and its envelope is discarded.
Session B recalls the artifact without re-materialized labels.
A sink check evaluates the content as unlabeled.
The proposal closes that path by making persisted artifacts labeled sinks and recall operations labeled sources.
Monotonic rewrite prevents label laundering through in-place updates. A later low-sensitivity write cannot lower the label of an artifact that previously carried higher-sensitivity content.
The migration rule prevents silent trust of unlabeled legacy artifacts. Treating unlabeled durable artifacts as maximally sensitive, or requiring explicit attributable attestation for bounded backfill, avoids a false sense of compliance.
This proposal does not add runtime state and does not weaken the ACS stateless invariant. It clarifies host responsibilities at durable storage and recall boundaries.
### Migration / Backward Compatibility
This does not require breaking ACS runtime APIs, but it does impose new conformance requirements on hosts that support durable storage or recall.
Hosts with existing durable artifacts need a migration strategy because pre-existing artifacts may not have persisted labels. A conformant migration should either:
Treat unlabeled durable artifacts as maximally sensitive; or
Perform a bounded, attributable backfill with an explicit attestation recording who labeled the artifact and on what basis.
Silent default-to-clean should be considered non-conformant.
Hosts that already persist result_labels may still need to verify that labels are keyed by artifact identity rather than session, turn, workflow, or envelope. Hosts that support artifact rewrite need to enforce monotonic joins in the storage layer or another concurrency-safe layer so simultaneous writers cannot lower labels.
No existing public API necessarily needs to be removed. The primary migration burden is host-side storage schema, recall propagation behavior, and documentation of legacy unlabeled artifact handling.
### Scope
Cross-package (2-3 packages)
### Target Placement
Core (agent-os, agent-mesh, agent-hypervisor)
### Prior Art
Prior implementation
I have implemented the proposed behavior in a self-hosted agent stack, including an injection evaluation targeting the cross-session case specifically:
Content enters during one session.
It reaches durable memory.
It activates in a later clean session.
Before artifact-scoped labels, it activated on every attempt.
After artifact-scoped labels, it activated on none.
Three design points survived implementation:
Three-valued session state: clean, labeled, and unknown, with unknown denying rather than defaulting either way. The distinction between “no labels” and “no record” mattered more than expected.
Monotonicity enforced in the storage layer: not only in application logic, so concurrent writers cannot produce a lowered label.
Unlabeled-means-maximal: this produced a loud but bounded rollout against an existing corpus. The migration was documented rather than worked around by defaulting artifacts to clean.
I would be happy to contribute a reference host-side propagator if useful. §11 lists label propagation as a host responsibility, and I could not find a reference implementation, though #3245 may be headed in that direction. If this is already covered by work in flight, this RFC can be treated as a documentation request against §13.2: the cross-session durable artifact case deserves an explicit sentence even when the mechanism exists.
### Checklist
- [x] I have searched existing issues and RFCs for duplicates
- [x] I have read the ADR index (adr/index.md) for related decisions
- [x] I am willing to implement this RFC or help review an implementation
Contributor guide
Research direction
Start with ACS §11 and §13.2, then read #2797 and the ADR index, especially ADR-0016 and ADR-0013. Map the proposal's durable-artifact, recall, rewrite, migration, and resolved-escalation questions to the existing specification. Done means the accepted design clearly defines host responsibilities and any required ADR or spec changes.
Written by the indexing model from the issue text.
Assessment
- Domain
- backend-api-design, security
- Issue type
- Feature
- Difficulty
- 5/5
- Estimated time
- Over a week
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 38/100