Workload access
Workload access gives each Kubernetes workload only the MCP tools and LLM models it needs. You bind the workload's ServiceAccount, register it against a Workload Blueprint in Audit mode, learn from what it does, promote the grants it needs, and then switch it to Enforce. You can contain a workload at any point.
Workload Trust is available only in private, self-managed AIControls installations, on premises or in a cloud cluster that you run. It needs a dedicated cluster that you run, with Kyverno, Kyverno Runtime, and cluster OIDC and RBAC access in place. Nirmata-hosted (SaaS) workspaces don't include it. See Feature availability.
The path to Enforce
Each stage builds on the one before it. A stage never skips the checks of an earlier stage.
- Bind the identity. An administrator ties the workload's Workload Registration to one cluster-qualified ServiceAccount. AIControls authorizes that ServiceAccount and never the workload's name or labels. See Bind a workload identity.
- Attach a Blueprint. The administrator registers the workload against a Workload Blueprint, in Audit mode. The Blueprint's one Access Binding holds the grants, and the workload's own override can add references and blocks. See Register a workload.
- Run in Audit. The Blueprint's Access Binding and the workload's referenced bindings grant access. The workload's own deny entries are evaluated and recorded but don't block calls. See Access modes.
- Review recommendations. AIControls learns candidate grants from the workload's unmatched and gate-denied calls. See Recommendations.
- Promote. The administrator previews and promotes the grants that the workload needs into an Access Binding. The next matching call is granted without a rollout. See Promote a recommendation. To reuse the promoted access for similar workloads, create a Blueprint from the workload. See Reuse learned access.
- Preview. The administrator previews the calls that Enforce would block. See Switch a workload to Enforce.
- Enforce. The administrator switches the registration to Enforce, and its own deny entries block matching calls. With the workload unmatched action set to Deny, the default on a new installation, any call outside the granted access is denied too. See Switch to Enforce.
- Contain. At any stage, an administrator can contain the workload's ServiceAccount to deny its MCP and LLM calls at once.
The AI access tab on the workload detail page brings the mode switch, the effective access, the unmatched calls, the recommendation queue, and containment together. The registration wizard binds the identity and registers the workload against a Blueprint, and Trusted: enforce now starts it in Enforce. A Blueprint has no revisions, and a workload has no pin or admission: Enforce is a mode switch.
What stays enforced in Audit
Audit changes only the workload's own deny entries, the workload unmatched action, and, when you turn it on, the default access policy's restrictive action. Referenced grants, binding gates, the server's tool default, guardrails, ceilings, containment, and the fail-closed rules always apply. See What Audit shadows.
Fail-closed rules
AIControls denies a call, instead of using the default access policy, when a workload's configured access is missing, stale, or ambiguous. The denial is not exemptible: Audit never shadows it, and observe mode, whether configured or turned on automatically when the LLM upstream is unreachable, never downgrades it.
| Situation | Result |
|---|---|
The workload has no pod_uid identity binding. A virtual_key binding is also ineligible for workload access. | The legacy path. The default access policy and the Access Bindings that match the caller decide. |
| The workload has a binding, but its registration doesn't name a Blueprint, or the Blueprint's Access Binding or Runtime Binding no longer exists, or the identity binding moved to a new revision. | Deny, with workload-registration-binding-incoherent. |
| Another registration also uses the ServiceAccount. | Deny, with the same policy. |
| A replica hasn't loaded the policies for the newest access change. | Deny, with workloadaccess:generation-stale, after one reload attempt. See Access policy. |
| An administrator contained the ServiceAccount. | Deny, with workloadaccess:contain:mcp or workloadaccess:contain:llm. |
Findings about shared or multiple ServiceAccounts are warnings only. They never gate Enforce: AIControls doesn't read them when it switches a workload's mode, or authorizes a call. Pods that share one ServiceAccount are one principal and share the same access.
Where to find it
An access decision is unmatched when no access policy covers the call, so the default access policy decides it. The Workloads list shows how often that happens for each workload, so you can find the workloads whose access list needs attention.
Inventory → Workloads has an Access column. For each workload it shows the unmatched rate over the last 7 days: the share of the workload's access decisions that no access policy matched. Hover the tag to see the counts, for example "20 of 100 calls were unmatched in the last 7 days."
The column shows one of three unmatched-rate states:
| State | Meaning |
|---|---|
| Has unmatched calls | At least one call in the last 7 days matched no access policy. The tag shows the rate. |
| All calls matched | The workload made calls, and every one matched an access policy or a known grant. |
| No traffic | The workload made no access decisions in the last 7 days. |
Use the column filter to show only workloads in one state. The filter runs on the server, so it covers the complete inventory and not only the rows on the current page. The filter also appears as the access URL parameter, so you can link to a filtered view. For the full list of parameters, see the Workloads table reference.
The same column filter also offers Audit mode and Enforce mode, which match registrations by their access mode, and Contained, which matches contained workloads. These appear as access=audit, access=enforce, and access=contained, and the workload list API, GET /api/v1/workload-trust, computes their totals and pages on the server.
The AI access tab
Open Inventory → Workloads, select a workload, open its full detail page, and select the AI access tab. The tab is for administrators. Other users see a note that administrators manage workload access, and the page makes no access requests for them. A workload with no cluster in view shows a note that you must open it with a cluster selected. An unregistered workload shows Register this workload.
The tab has five cards, plus a sixth when the workload's own binding grants something:
| Card | What it shows |
|---|---|
| Mode | An Audit or Enforce tag, plus Contained and Audit unmatched override on tags when they apply. Blueprint names the Workload Blueprint, and Access policy shows the workload's access policy ID. An Audit and Enforce switch changes the mode. A workload with a registration but no Blueprint shows a No Blueprint tag. Selecting Enforce opens the Switch to Enforce? dialog, which says how many calls from the last 7 days matched no grant, and you select Switch to Enforce. The switch stays off while the workload has no effective grant, and while the workload is contained. |
| Effective access | The Access Bindings that reach the workload, in three groups: Access Bindings (the Blueprint's Access Binding and any binding added for this workload), Extra access for this workload (the binding that Promote writes), and Team access rules that also match (bindings whose agent or agent label subjects also match the workload's identity). A Broken reference tag marks a reference to a binding that no longer exists, and a Not referenced tag marks an owned binding that the workload's override no longer references. Neither grants anything. Each server, tool, and model grant of a binding that reaches the workload has a Block for this workload action; see Deny a grant for one workload. The Intent block shows the profile and data classification from the Blueprint, the workload's customization (tagged Customized for this workload and, when it widens the Blueprint, Wider than the Blueprint), and the effective intent. The runtime answers are on the Runtime tab. Gate outcomes shows Passes the gate or Denied by gate for each gated MCP server. The card links to the Blueprint and to Manage Access Bindings, where an edit goes through the impact preview. |
| Reuse this workload's access | Shown when the workload's own binding grants something. Create Blueprint from this workload creates a Workload Blueprint from the workload's effective profile, where you select or create its Access Binding and Runtime Binding. See Reuse learned access. |
| Unmatched calls | The unmatched rate for the last 7 days and the Unmatched action that applies. |
| Recommendations | The recommendation queue with the columns Entry, Count, First seen, Last seen, Evidence, and Actions. It lists grant recommendations and intent recommendations, tagged Intent, together. A status selector switches between open, dismissed, promoted, expired, and resolved recommendations, and the table pages on the server with a total. A grant recommendation's actions menu has Promote and Dismiss. Promote opens the Promote recommendation dialog, where you choose the Target binding and review the Before and After selectors. An intent recommendation's menu has Promote to this workload, Promote to the Runtime Binding, and Dismiss. Dismiss closes a recommendation. Promote all promotes every open grant entry, on every page, into Extra access for this workload, stops at the first failure, and stays off while the list is incomplete. |
| Containment | A Contained or Not contained tag, with the administrator, time, and reason when contained. Contain and Release change the state. A note says containment covers MCP tool calls and LLM requests only, and links to the kill switch. |
If the Enforce switch is refused because the workload has no effective grant, the Mode card shows Enforce is not available yet, with the reason. Add a grant to the Blueprint's Access Binding or promote a recommendation, then switch. See Switch a workload to Enforce. A shared or multiple identity finding shows a warning on the Mode card. It never blocks Enforce.
Access modes
A Workload Registration that follows a Workload Blueprint runs in one of two modes. The mode belongs to the registration, so two workloads that use the same Blueprint can be in different modes.
| Mode | What happens |
|---|---|
| Audit | The workload's own deny list and the workload unmatched action are evaluated on every call and recorded, but they do not block the call. Use Audit to see what Enforce would do before you turn it on. |
| Enforce | The workload's own deny list blocks matching calls. With the workload unmatched action set to Deny, a call that none of the workload's grants match is blocked too. |
In both modes, the Access Bindings that the Blueprint or the workload references grant access. A referenced binding is reviewed by an administrator and is not one of the workload's own decisions, so Audit never shadows it.
What Audit shadows
Audit shadows only the workload-owned restrictions: the workloadaccess:<accessPolicy>:deny:mcp and workloadaccess:<accessPolicy>:deny:llm deny policies, and the workload unmatched action's accessdefault:mcp:workload and accessdefault:llm:workload policies. A shadowed deny has these effects:
- AIControls records the would-be decision on the call's audit event, and the call continues.
- The match does not count as a known grant. If nothing else matches the call, the default access policy still decides it. For example, with MCP set to Deny in the default access policy, a call that only a shadowed deny matched is still denied by
accessdefault:mcp.
Audit never shadows guardrail policies, binding gates, the server's tool default (mcptooldefault), Access Binding decision modes, ceilings, containment, or a fail-closed snapshot. These always apply.
Workload unmatched action
The default access policy has one more setting for registered workloads: what happens to an MCP or LLM call that none of the workload's grants match. On a new installation it is Deny, so once you promote a workload's learned access and switch it to Enforce, every other call is blocked with accessdefault:mcp:workload or accessdefault:llm:workload. You don't need to change the plane actions, which still decide unmatched calls from developers, personal access tokens, human users, virtual keys, and other callers that aren't registered workloads.
In Audit mode, the workload unmatched action is shadowed like the workload's deny list, with or without the audit unmatched override, so Learn first still allows the call and turns it into a recommendation. The action can only add a restriction to the plane action, never relax it. An installation upgraded from an earlier release keeps the plane action until an administrator selects Deny. See Workload callers.
Audit unmatched override
By default, a restrictive unmatched action (Hold or Deny, including a Judge-driven one) enforces in Audit too. If you want Audit to show what a workload would do under the default access policy without blocking it, turn on auditUnmatchedOverride in the workload's override.
With the override on, a registration in Audit mode works like this:
- When the default access policy would hold or deny an MCP or LLM call that no access policy matched, AIControls allows the call and records the would-be decision as shadowed. The HTTP egress default always applies.
- The call still counts as unmatched, so the unmatched rate and
aicontrols_access_unmatched_totaldo not change. - The override never affects guardrails, binding gates,
mcptooldefault, binding decision modes, or ceilings, which decide before the default access policy. - The override has no effect in Enforce mode.
Every change to the override records its own workload_access.override_changed configuration audit event. Containing a workload turns the override off.
Switch to Enforce
Enforce is a mode switch. There's no admission and no revision to pin. On the AI access tab, turn on Enforce on the Mode card. AIControls previews the unmatched calls from the last 7 days that Enforce would now block, and you confirm. Both steps are administrator-only API calls:
POST /api/v1/workloads/{namespace}/{kind}/{name}/mode/preview?cluster={cluster}
{"mode": "enforce"}
POST /api/v1/workloads/{namespace}/{kind}/{name}/mode?cluster={cluster}
{"mode": "enforce", "previewHash": "…", "expectedRowVersion": 7, "rowToken": "…"}
Read expectedRowVersion and rowToken from GET /api/v1/workloads/{namespace}/{kind}/{name}/access?cluster={cluster}. AIControls refuses the switch with 409 unless both of these are true. A missing grant returns enforce_no_grant, and an identity binding that isn't current and unambiguous returns enforce_ineligible:
- The workload has an effective grant: an enabled, allow-mode Access Binding, the Blueprint's or one the override references, with at least one server, tool selector, Toolset reference, or model selector.
- The configured identity binding is current and unambiguous: it is the only active binding for the ServiceAccount in its cluster, and no other registration still uses that identity.
A stale previewHash returns 409 preview_stale. PUT .../access can't enter Enforce: it returns 409 mode_switch_required.
Shared or multiple ServiceAccount findings are warnings only. They don't block the switch, and acknowledging one doesn't make an ambiguous configured binding valid. Pods that share one ServiceAccount are one security principal and share the same access.
Each switch records a workload_registration.mode_changed configuration audit event. Switching back to Audit needs no preview.
Because bindings are live, an edit to the workload's Access Binding reaches an Enforce workload at once. The impact preview flags an edit that gives Enforce workloads new access or leaves them with none.
To change what a whole group of workloads can reach, edit their Blueprint's Access Binding instead of each override. See Review and restore a binding change. A Blueprint also has a starting mode, which is only a suggestion for new registrations. See Edit a Blueprint.
Audit evidence
The audit event of every call from a registered workload carries a workloadAccess record:
| Field | Meaning |
|---|---|
mode | audit or enforce |
blueprint, accessPolicy | The Blueprint name and the opaque access policy ID that the call used |
identityBindingRevision | The identity binding revision the decision used |
generation | The workload access generation that AIControls read with the Blueprint and bindings |
auditUnmatchedOverride | Whether the override was on |
shadowed | Each would-be decision that Audit recorded instead of enforcing: its policy, mode, and message. unmatched: true marks the default access action the override shadowed. |
When the default access policy uses the Judge, the Judge decides from the same Blueprint, bindings, and override as authorization. A change to the Blueprint, the mode or override, or a referenced Access Binding or a Toolset it references starts a new Judge assessment. When the identity binding is missing, the Judge returns unknown and the default access policy uses its fallback decision.
Effective access
A workload's effective access is the union of every Access Binding that reaches it. GET /api/v1/workloads/{namespace}/{kind}/{name}/access/summary?cluster={cluster} (administrator-only) groups those bindings by how they reach the workload:
| Source | What it is |
|---|---|
| Blueprint | The Blueprint's one Access Binding. You edit it in the Blueprint's Access section or on the Access Bindings page, with an impact preview. |
| Referenced | Other shared bindings that the workload's override lists in bindingRefs. A reference to a binding that no longer exists shows missing: true; a missing or disabled reference grants nothing. |
| Owned | The workload's own binding, which only Promote writes. When the workload's override no longer references it, it shows notReferenced: true and grants nothing. |
| Legacy | Bindings whose own agent or agentLabel subjects match the workload's identity, such as a broad label binding. Phase 1 doesn't exclude them. To narrow one for this workload only, deny the grant for this workload. |
A model grant names model IDs or patterns, and an upstream only when it must pin one. When you edit a Blueprint's binding, you choose models from the model catalog: every model your enabled upstreams advertise. The editor names an upstream only when the same model ID is on more than one.
The summary also reports each gated MCP server's outcome. A server is gated when any binding names it. The workload passes the gate when its Blueprint's binding, a binding it references, its owned binding, or a legacy binding covers the server. Otherwise the outcome is denied, with the message "Denied by gate: no binding you reference covers <server>."
The summary includes the workload's access mode, the override, its containment state, the open recommendation count, and the same 7-day unmatched rate as the Workloads list. Each section reports its own error, so one unavailable source doesn't hide the others.
Deny a grant for one workload
A legacy binding, the Blueprint's binding, or a shared binding that the workload references often grants more than one workload needs. Blueprints have no deny list, so this is the way to block a grant for one workload. Block for this workload narrows that grant for this workload only, in one step, and leaves the binding as it is for every other subject and workload.
Each server, tool selector, and model selector of an enabled allow binding that reaches the workload offers the action. A whole-server grant becomes the deny entry {"servers": ["<server>"], "tools": ["*"]}; a tool or model selector is copied as it is. A Toolset reference has no action: deny the tools it resolves to instead.
The action previews the change first: the deny entry it adds, the workload's deny list after the change, and the resulting effective access, with each grant marked Granted or Blocked. When you confirm, AIControls writes the deny entry to the workload's override in one transaction. The change is recorded in the configuration audit as workload_access.deny_added, beside the registration update, and the whole write rolls back when the audit write fails. If the registration, its override, or the binding changes after the preview, the write is refused with 409 preview_stale and the dialog shows a fresh preview.
The deny follows the workload's access mode:
- Audit. The next matching call is allowed and the deny is recorded as shadowed in its audit event, so you can confirm what it would block.
- Enforce. The deny applies from the next call. Review the preview first, because there is no admission step to catch a mistake.
When the workload's deny list already covers the grant, the preview says so and the write is refused with 409 already_denied. For the steps and the API calls, see Deny a grant for one workload.
Recommendations
AIControls learns candidate grants from each workload's own audit trail. Every 5 minutes it groups the last 30 days of the workload's calls that no access policy matched, plus MCP calls that a binding gate denied, into recommendations:
- An MCP recommendation names one server and one tool, the same selector shape that Propose from usage produces for a Toolset.
- An LLM recommendation names one exact model. The audit trail doesn't record the resolved provider, so the recommendation is marked
providerUnresolvedand grants the model on every provider. AIControls warns you about the wider scope when you preview it.
Recommendations follow these rules:
- Cluster-qualified. AIControls groups calls by the workload recorded on each audit event, including its cluster. Identical workloads in two clusters never share counts, candidates, or evidence. Calls recorded without a resolved workload are excluded.
- Value-free evidence. A recommendation stores only counts, first and last seen times, the target server and tool or model, the deciding policy, and up to three audit event IDs. It never stores prompts, request bodies, tool arguments, tool results, or responses.
- Intent cleanup. On upgrade, AIControls deletes any
intent.llmandintent.mcprecommendations. - Bounded. A workload keeps at most 100 open recommendations per facet (MCP and LLM), ordered by call count, then by most recent call. When more candidates exist, the list reports
truncated, thedroppedCandidateCount, andoldestIncludedAt. - Retention. An open recommendation that sees no new call for 30 days expires. Any recommendation unseen for 90 days is deleted with its evidence.
- Sticky decisions. A dismissed recommendation stays dismissed. A promoted or expired one reopens only when a newer matching call arrives.
Promoting a recommendation adds exactly the previewed entry to an Access Binding:
- The workload's own binding (default). The first promotion creates a binding owned by the Workload Registration (
owner.kindisworkloadRegistration) and adds it to the workload's override in the same transaction. The first promotion works only while the workload is in Audit. In Enforce, it returns409 audit_required. Later promotions append to the same binding in either mode. - A shared binding that the workload already uses, either its Blueprint's or one its override references. The preview lists every subject, workload, and Blueprint that gains the entry.
Binding contents are live, so the next matching call is granted without a rollout. A workload's own binding changes only through Promote: the Access Bindings page and API refuse to edit or delete it. Only its owner reaches it: a Blueprint, or another workload's override, that references it is refused, and such a reference grants nothing. Every promotion and dismissal is recorded in the configuration audit. For the steps, see Promote a recommendation.
Intent recommendations
The queue also holds intent recommendations for the network, files, exec, and kubernetes sections. Intent has no model or MCP section, so unmatched model and tool calls produce grant recommendations instead. When a workload does more than its effective intent declares, the workload trust reconcile pass recommends the wider tier. It compares the tier that the workload's observed behavior needs, drafted the same way as the registration wizard's suggestion, with the workload's materialized intent, section by section:
| Facet | Observed from | Example |
|---|---|---|
intent.network | Observed egress destinations | network: llm-providers while the workload reaches an uncatalogued internet host |
intent.files | The running pod's volume mounts, or the pod template's | files: none on a workload with its own volumes |
intent.exec | Agent exec findings | exec: none while the workload runs a shell |
intent.kubernetes | The ServiceAccount's RBAC, when the posture reader is on | kubernetes: none on a ServiceAccount that can read the API |
Intent recommendations follow the same rules as grant recommendations, with these differences:
- One row per section and tier. A workload has at most one recommendation for each tier above
none. Each pass updates it in place. A section the effective intent leaves out declares no constraint, so it never gets a recommendation. - Value-free evidence. The evidence is the kind of source (for example, a runtime finding or network egress), a count, and the first and last seen times. It never names the binary, path, host, model, or server that was observed.
- Resolved. When the workload's effective intent covers the tier, for example after a Runtime Binding edit covers the tier, the next pass closes the recommendation with the status
resolved. - Advisory. An intent recommendation never changes a protection status, and it never adds a workload to Needs attention.
- Timing. The pass runs at most every 5 minutes. Gateway calls count only from a Pod that AIControls has bound to the workload. AIControls attributes a new Pod within seconds of scheduling, or on its first gateway call, so a newly deployed workload's first egress shows up in an intent recommendation on the next pass, at most about 5 minutes later. See How new Pods are attributed.
- In-cluster destinations. An egress destination counts as in-cluster when it has a Service domain name, when it's an address the Kubernetes API server reports as a Service ClusterIP or Pod IP, which includes the AIControls gateway, or when it falls in the Runtime Binding's cluster services. Any other address counts as internet.
Promote offers two targets, both administrator-only and recorded in the configuration audit as workload_access_recommendation.promoted:
- This workload. AIControls writes a workload override that sets the section's tier. An override that makes the workload's intent wider than its Runtime Binding needs
acknowledgeWidening. For a workload in Enforce, the override applies live: the preview reportsenforceLiveand warns, and the preview hash covers the mode, so a mode switch after the preview returns409 preview_stale. - The Runtime Binding. AIControls drafts the Runtime Binding change with the wider level and opens the impact preview, which lists every Blueprint and workload that uses the binding and what changes for it. Nothing is written until you confirm, and the save closes the recommendation in the same transaction.
Promotion requires current evidence. If the recommendation or workload changes after review, refresh the preview before confirming. Recommendations unseen for 30 days cannot be promoted, even before the background expiry pass. Shared Runtime Binding drafts carry a review hash alongside the separate fleet impact confirmation.
Promote all covers grant recommendations only. Promote each intent recommendation on its own, so that you review its widening and choose its target.
Reuse learned access
Because only its owner reaches a workload's own binding, a workload's learned access can't be shared as it is. Create Blueprint from this workload, on the AI access tab, creates a Workload Blueprint from the workload's effective profile. You select or create its one Access Binding, which can start from the workload's learned grants, and its one Runtime Binding. In the same audited step, you can move the workload onto the new Blueprint, which clears its override. The preview checks that the workload's effective access doesn't change. Afterward, you can register similar workloads, in the same namespace or with the same image, against the Blueprint in Audit. For the steps, see Turn a workload's learned access into a Blueprint.
Containment
Containment denies every MCP and LLM request from a workload's ServiceAccount, starting with its next call. Use it when you need to stop a workload now, without waiting for a policy reload or a rollout.
- It applies in both Audit and Enforce, and a fail-closed snapshot doesn't lift it. No exception lifts it.
- It is keyed on the cluster and the ServiceAccount. It doesn't change the registration's mode.
- It denies before the default access policy runs, so the default doesn't apply to a contained workload's MCP and LLM calls.
- Containing a workload in Audit also clears the audit unmatched override in its override. The override stays off after you release the workload, so turn it on again if you still want it. In Enforce the override has no effect and is left as it is.
- It denies MCP and LLM requests only. Outbound HTTP egress and everything that doesn't go through the gateway continue. Use the kill switch to stop network, file system, and exec activity.
- It has no expiry. You release it explicitly.
For the steps, see Contain a workload. The Workloads list API filters contained workloads with access=contained.
How the rate is computed
AIControls counts the gateway requests for which the access pass produced an outcome: an enforcing access policy matched, or the default access policy handled the call. The rate is unmatched calls divided by those decided calls over the last 7 days.
- Calls that failed policy evaluation, calls no access outcome applied to, response-phase records, and audit-mode observations are not decided calls and are not counted.
- Calls recorded before you upgraded to this version carry no outcome marker, so a new rate fills in over the following 7 days.
- AIControls records the workload that the calling pod belonged to on each audit event when the call happens. If a shared ServiceAccount moves between workloads, the earlier calls stay with the workload that made them, and neither workload's past rate changes.
- Calls recorded before you upgraded to this version carry no workload. AIControls attributes those calls through the workload that the calling agent identity currently resolves to, so they follow the identity if it moves. They age out of the 7-day window within a week of the upgrade.
- Calls where AIControls could not resolve the pod to a workload at call time also record no workload and use the same fallback.
- A workload whose agents are not attributed to it shows No traffic. That means no calls were attributed to the workload, not that the workload made no calls.
- The rate is evidence for you to act on. It is not a score.
Outlier chip
AIControls compares a workload's unmatched rate with the rate of its peer group in the same cluster. The peer group is the workloads that use the same Workload Blueprint. A workload that is the only one on its Blueprint is compared with the registered workloads that share its image repository. An Outlier chip appears next to the rate when the workload:
- Made at least 20 decided calls in the last 7 days.
- Has an unmatched rate of at least 3%.
- Has a rate at least twice the rate of the other workloads in the group.
An outlier usually has an allow list that is missing entries its peers already have, or it runs a different configuration from the rest of the group.
Metrics
AIControls exposes two counters about access decisions. Both use only bounded labels. Neither has a workload label, because a per-workload label would multiply the number of time series with the size of your fleet. Use the Workloads list for per-workload figures.
| Metric | Labels | Counts |
|---|---|---|
aicontrols_access_unmatched_total | plane, action | Requests that the default access policy handled, by the action it took (allow, hold, or deny). |
aicontrols_workload_access_decided_total | plane, source, mode | Every request-phase access decision. |
The labels of aicontrols_workload_access_decided_total take these values:
| Label | Values |
|---|---|
plane | mcp, llm, or http |
source | access_policy when an enforcing access policy matched, unmatched_default when the default access policy decided, guardrail when only a non-access policy matched, or none when no policy applied |
mode | The caller's registration access mode: audit, enforce, or unregistered for every call without registered workload access |
To estimate the org-wide share of unmatched calls on a plane, divide the rate of source="unmatched_default" by the rate of all decisions on that plane.
Next steps
- Workload Blueprints and Workload Registrations
- Bind a workload identity
- Switch a workload to Enforce
- Review and restore a binding change
- Promote a recommendation
- Turn a workload's learned access into a Blueprint
- Deny a grant for one workload
- Default access policy
- Set the default access policy
- Workloads table reference
- Workload Protection