2026-08-23 22:07:38 -03:00
{
"$schema" : "https://json-schema.org/draft/2020-12/schema" ,
"$id" : "https://hermes.bstein.dev/contracts/hux/v1/permission.schema.json" ,
"title" : "HUX autonomy, grants, approvals, cancellation" ,
"description" : "Policy engine records (HUX-05). A policy fixes the autonomy level and explicit capability grants for a scope; approvals are queued items answered with the existing gateway choices (once|session|always|deny); a cancellation receipt proves what a stop actually did." ,
"$defs" : {
"capability" : {
"type" : "string" ,
2026-08-24 00:04:37 -03:00
"enum" : [
"read_files" ,
"write_files" ,
"shell" ,
"network" ,
"web_search" ,
"send_message" ,
"memory_write" ,
"artifact_write" ,
"spend_tokens" ,
"delegate" ,
"deploy" ,
"external_side_effect"
]
} ,
"decision" : {
"type" : "string" ,
"enum" : [
"allow" ,
"ask" ,
"deny"
]
2026-08-23 22:07:38 -03:00
} ,
"policy" : {
"type" : "object" ,
"additionalProperties" : false ,
2026-08-24 00:04:37 -03:00
"required" : [
"schema" ,
"id" ,
"owner" ,
"scope" ,
"autonomy" ,
"grants" ,
"budgets" ,
"provenance" ,
"updated_at" ,
"revision"
] ,
2026-08-23 22:07:38 -03:00
"properties" : {
2026-08-24 00:04:37 -03:00
"schema" : {
"const" : "hux.policy.v1"
} ,
"id" : {
"$ref" : "common.schema.json#/$defs/id"
} ,
"owner" : {
"$ref" : "common.schema.json#/$defs/user_ref"
} ,
2026-08-23 22:07:38 -03:00
"scope" : {
"type" : "object" ,
"additionalProperties" : false ,
2026-08-24 00:04:37 -03:00
"required" : [
"level"
] ,
2026-08-23 22:07:38 -03:00
"properties" : {
2026-08-24 00:04:37 -03:00
"level" : {
"type" : "string" ,
"enum" : [
"global" ,
"project" ,
"conversation"
]
} ,
"scope_id" : {
"$ref" : "common.schema.json#/$defs/id"
}
2026-08-23 22:07:38 -03:00
}
} ,
2026-08-24 00:04:37 -03:00
"autonomy" : {
"type" : "string" ,
"enum" : [
"ask_first" ,
"safe" ,
"autonomous"
]
} ,
2026-08-23 22:07:38 -03:00
"grants" : {
"type" : "array" ,
"maxItems" : 64 ,
"items" : {
"type" : "object" ,
"additionalProperties" : false ,
2026-08-24 00:04:37 -03:00
"required" : [
"capability" ,
"decision"
] ,
2026-08-23 22:07:38 -03:00
"properties" : {
2026-08-24 00:04:37 -03:00
"capability" : {
"$ref" : "#/$defs/capability"
} ,
"decision" : {
"$ref" : "#/$defs/decision"
} ,
"expires_at" : {
"$ref" : "common.schema.json#/$defs/timestamp"
} ,
"granted_by" : {
"$ref" : "common.schema.json#/$defs/actor"
}
2026-08-23 22:07:38 -03:00
}
}
} ,
"budgets" : {
"type" : "object" ,
"additionalProperties" : false ,
"properties" : {
2026-08-24 00:04:37 -03:00
"tokens_per_run" : {
"type" : "integer" ,
"minimum" : 0
} ,
"tool_calls_per_run" : {
"type" : "integer" ,
"minimum" : 0
} ,
"wall_clock_seconds" : {
"type" : "integer" ,
"minimum" : 0
} ,
"delegations_per_run" : {
"type" : "integer" ,
"minimum" : 0
} ,
"spend_units" : {
"type" : "integer" ,
"minimum" : 0
} ,
"subagents_per_run" : {
"type" : "integer" ,
"minimum" : 0
} ,
"scope" : {
"type" : "object" ,
"additionalProperties" : false ,
"properties" : {
"conversations" : {
"type" : "array" ,
"maxItems" : 64 ,
"items" : {
"$ref" : "common.schema.json#/$defs/id"
}
} ,
"paths" : {
"type" : "array" ,
"maxItems" : 64 ,
"items" : {
"type" : "string" ,
"maxLength" : 300
}
}
}
}
2026-08-23 22:07:38 -03:00
}
} ,
2026-08-24 00:04:37 -03:00
"provenance" : {
"$ref" : "common.schema.json#/$defs/provenance"
} ,
"updated_at" : {
"$ref" : "common.schema.json#/$defs/timestamp"
} ,
"revision" : {
"$ref" : "common.schema.json#/$defs/revision"
}
2026-08-23 22:07:38 -03:00
}
} ,
"approval" : {
"type" : "object" ,
"additionalProperties" : false ,
2026-08-24 00:04:37 -03:00
"required" : [
"schema" ,
"id" ,
"run_id" ,
"conversation_id" ,
"capability" ,
"request" ,
"status" ,
"requested_at" ,
"expires_at"
] ,
2026-08-23 22:07:38 -03:00
"properties" : {
2026-08-24 00:04:37 -03:00
"schema" : {
"const" : "hux.approval.v1"
} ,
"id" : {
"$ref" : "common.schema.json#/$defs/id"
} ,
"run_id" : {
"type" : "string" ,
"minLength" : 1 ,
"maxLength" : 120
} ,
"conversation_id" : {
"$ref" : "common.schema.json#/$defs/id"
} ,
"capability" : {
"$ref" : "#/$defs/capability"
} ,
2026-08-23 22:07:38 -03:00
"request" : {
"type" : "object" ,
"additionalProperties" : false ,
2026-08-24 00:04:37 -03:00
"required" : [
"summary" ,
"risk" ,
"external"
] ,
2026-08-23 22:07:38 -03:00
"properties" : {
2026-08-24 00:04:37 -03:00
"summary" : {
"type" : "string" ,
"minLength" : 1 ,
"maxLength" : 280
} ,
"detail" : {
"type" : "string" ,
"maxLength" : 4000
} ,
"risk" : {
"type" : "string" ,
"enum" : [
"low" ,
"medium" ,
"high"
]
} ,
"evidence" : {
"type" : "array" ,
"maxItems" : 16 ,
"items" : {
"$ref" : "common.schema.json#/$defs/evidence_ref"
}
} ,
"external" : {
"type" : "boolean" ,
"description" : "True when the action leaves the tenant (message, network call, deploy). External side effects always need an approval record regardless of autonomy level."
}
2026-08-23 22:07:38 -03:00
}
} ,
2026-08-24 00:04:37 -03:00
"status" : {
"type" : "string" ,
"enum" : [
"pending" ,
"approved" ,
"denied" ,
"expired" ,
"cancelled"
]
} ,
2026-08-23 22:07:38 -03:00
"decision" : {
"type" : "object" ,
"additionalProperties" : false ,
2026-08-24 00:04:37 -03:00
"required" : [
"choice" ,
"by" ,
"at"
] ,
2026-08-23 22:07:38 -03:00
"properties" : {
2026-08-24 00:04:37 -03:00
"choice" : {
"type" : "string" ,
"enum" : [
"once" ,
"session" ,
"always" ,
"deny"
]
} ,
"by" : {
"$ref" : "common.schema.json#/$defs/actor"
} ,
"at" : {
"$ref" : "common.schema.json#/$defs/timestamp"
}
2026-08-23 22:07:38 -03:00
}
} ,
2026-08-24 00:04:37 -03:00
"requested_at" : {
"$ref" : "common.schema.json#/$defs/timestamp"
} ,
"expires_at" : {
"$ref" : "common.schema.json#/$defs/timestamp"
} ,
"idempotency_key" : {
"$ref" : "common.schema.json#/$defs/idempotency_key"
}
2026-08-23 22:07:38 -03:00
}
} ,
"cancellation_receipt" : {
"type" : "object" ,
"additionalProperties" : false ,
2026-08-24 00:04:37 -03:00
"required" : [
"schema" ,
"id" ,
"run_id" ,
"requested_by" ,
"requested_at" ,
"outcome" ,
"side_effects"
] ,
2026-08-23 22:07:38 -03:00
"properties" : {
2026-08-24 00:04:37 -03:00
"schema" : {
"const" : "hux.cancel_receipt.v1"
} ,
"id" : {
"$ref" : "common.schema.json#/$defs/id"
} ,
"run_id" : {
"type" : "string" ,
"minLength" : 1 ,
"maxLength" : 120
} ,
"requested_by" : {
"$ref" : "common.schema.json#/$defs/actor"
} ,
"requested_at" : {
"$ref" : "common.schema.json#/$defs/timestamp"
} ,
"acknowledged_at" : {
"$ref" : "common.schema.json#/$defs/timestamp"
} ,
"completed_at" : {
"$ref" : "common.schema.json#/$defs/timestamp"
} ,
"outcome" : {
"type" : "string" ,
"enum" : [
"cancelled" ,
"already_complete" ,
"failed_to_cancel"
]
} ,
2026-08-23 22:07:38 -03:00
"side_effects" : {
"type" : "array" ,
"maxItems" : 64 ,
"items" : {
"type" : "object" ,
"additionalProperties" : false ,
2026-08-24 00:04:37 -03:00
"required" : [
"description" ,
"reverted"
] ,
2026-08-23 22:07:38 -03:00
"properties" : {
2026-08-24 00:04:37 -03:00
"description" : {
"type" : "string" ,
"minLength" : 1 ,
"maxLength" : 280
} ,
"reverted" : {
"type" : "boolean"
} ,
"evidence" : {
"$ref" : "common.schema.json#/$defs/evidence_ref"
}
}
}
} ,
"conversation_id" : {
"$ref" : "common.schema.json#/$defs/id"
2026-08-24 00:45:13 -03:00
} ,
"revision" : {
"type" : "integer" ,
"minimum" : 1 ,
"description" : "Store revision; bumps when a failed_to_cancel receipt is superseded by a later stop."
2026-08-24 00:04:37 -03:00
}
}
} ,
"budget_state" : {
"type" : "object" ,
"additionalProperties" : false ,
"required" : [
"schema" ,
"run_id" ,
"spent" ,
"limits" ,
"exhausted"
] ,
"properties" : {
"schema" : {
"const" : "hux.budget_state.v1"
} ,
"run_id" : {
"type" : "string" ,
"maxLength" : 120
} ,
"spent" : {
"type" : "object" ,
"additionalProperties" : false ,
"properties" : {
"tokens" : {
"type" : "integer" ,
"minimum" : 0
} ,
"tool_calls" : {
"type" : "integer" ,
"minimum" : 0
} ,
"wall_clock_seconds" : {
"type" : "integer" ,
"minimum" : 0
} ,
"delegations" : {
"type" : "integer" ,
"minimum" : 0
} ,
"spend_units" : {
"type" : "integer" ,
"minimum" : 0
} ,
"subagents" : {
"type" : "integer" ,
"minimum" : 0
2026-08-23 22:07:38 -03:00
}
}
2026-08-24 00:04:37 -03:00
} ,
"limits" : {
"$ref" : "#/$defs/policy/properties/budgets"
} ,
"exhausted" : {
"type" : "array" ,
"uniqueItems" : true ,
"items" : {
"type" : "string" ,
"enum" : [
"tokens_per_run" ,
"tool_calls_per_run" ,
"wall_clock_seconds" ,
"delegations_per_run" ,
"spend_units" ,
"subagents_per_run"
]
}
2026-08-23 22:07:38 -03:00
}
}
}
} ,
"oneOf" : [
2026-08-24 00:04:37 -03:00
{
"$ref" : "#/$defs/policy"
} ,
{
"$ref" : "#/$defs/approval"
} ,
{
"$ref" : "#/$defs/cancellation_receipt"
} ,
{
"$ref" : "#/$defs/budget_state"
}
2026-08-23 22:07:38 -03:00
]
}