You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Enrich policy denials with machine-readable remediation metadata — what would have
to change for the request to succeed (missing role, missing justification, rate
window reset time, TTL/constraint conflict) — so LLM agents can self-correct
instead of retry-looping or giving up.
Why this matters
The kernel's consumers are LLM agents. When an agent receives "denied," its next
action is a prompt-side decision: ask the user for approval, supply a
justification, wait, or pick another tool. Stable reason codes (policy_reasons.py)
identify why; they do not say what would help. A small structured remediation
payload ("provide justification", "retry after 14:32:05Z", "requires role writer") turns denials from dead ends into protocol — directly reducing wasted
agent loops. This complements HITL approvals (#128): remediation hints are how an
agent learns that escalation is the right next step.
Current evidence
policy_reasons.py: stable codes with docstrings exist (e.g., role-missing) — the taxonomy to hang hints on.
errors.py:30: PolicyDenied carries a message; no structured fields for remediation.
policy.pyexplain() produces human-oriented descriptions; nothing is designed for in-loop agent consumption.
Structured, actionable error payloads are an established API-design norm (problem-
details-style responses); agent frameworks increasingly branch on typed tool errors.
Populate from the same unified rule chain as ISSUE 23 (each rule knows its
remediation) — sequence after 23 to avoid triple-maintaining logic.
Render compactly in adapters so the agent sees it in the tool-error message;
keep wording neutral and non-sensitive (never reveal other principals'
permissions).
Carry the remediation kind into denial trace records (ISSUE 7).
Security review the hint content: hints must not become an oracle for probing policy (e.g., do not enumerate which roles exist; only name the role required for this capability, which explain() already reveals).
Summary
Enrich policy denials with machine-readable remediation metadata — what would have
to change for the request to succeed (missing role, missing justification, rate
window reset time, TTL/constraint conflict) — so LLM agents can self-correct
instead of retry-looping or giving up.
Why this matters
The kernel's consumers are LLM agents. When an agent receives "denied," its next
action is a prompt-side decision: ask the user for approval, supply a
justification, wait, or pick another tool. Stable reason codes (
policy_reasons.py)identify why; they do not say what would help. A small structured remediation
payload ("provide
justification", "retry after 14:32:05Z", "requires rolewriter") turns denials from dead ends into protocol — directly reducing wastedagent loops. This complements HITL approvals (#128): remediation hints are how an
agent learns that escalation is the right next step.
Current evidence
policy_reasons.py: stable codes with docstrings exist (e.g., role-missing) — the taxonomy to hang hints on.errors.py:30:PolicyDeniedcarries a message; no structured fields for remediation.policy.pyexplain()produces human-oriented descriptions; nothing is designed for in-loop agent consumption.External context
Structured, actionable error payloads are an established API-design norm (problem-
details-style responses); agent frameworks increasingly branch on typed tool errors.
Proposed implementation
PolicyDenied.remediation: Remediation | None— dataclass withkind(provide_justification | acquire_role | wait | reduce_scope | escalate),optional
detailfields (role name, retry-after timestamp from the ratelimiter, constraint name).
remediation) — sequence after 23 to avoid triple-maintaining logic.
keep wording neutral and non-sensitive (never reveal other principals'
permissions).
AI-agent execution notes
policy_reasons.py,policy.py(deny paths),errors.py,adapters/_base.py(error rendering),tests/test_policy.py.explain()already reveals).Acceptance criteria
explain()output.Test plan
Per-reason-code mapping tests; rate-window retry-after test with injected clock;
adapter rendering test. Run
make ci.Documentation plan
docs/capabilities.mddenial-handling section with an agent-loop example;CHANGELOG
Added.Migration and compatibility notes
Additive field; not expected to require migration.
Risks and tradeoffs
Information-disclosure tradeoff is real but bounded (parity with
explain()).Remediation vocabulary becomes contract — start with ≤6 kinds.
Suggested labels
ai, llm, product, developer-experience