Skip to main content

License management

AIControls requires a valid license before it will process AI traffic — MCP tool calls and LLM requests. Without one, the Admin UI stays fully accessible, but a banner is shown and AI requests are blocked until a license is loaded.

Need a license or an upgrade?

Contact support@nirmata.com for a new license, or to upgrade an existing one.

License types​

A license names a plan: Free, Team, Business, or Enterprise. See Plans and entitlements for what each plan is for.

  • Free — a free, no-signup tier for self-hosted (Kubernetes) installs, described below.
  • Trial — a time-limited license for evaluation.
  • Enterprise — a full production license, issued for your organization (SaaS) or your cluster (Kubernetes Self-Hosted).

Free tier​

A self-hosted Kubernetes install with no license loaded processes AI traffic immediately, no signup required. The Free plan allows up to 5 identities and 1,000 requests each calendar month (UTC). The request count resets on the first of each month. Identities are counted over the life of the installation: an identity that has made a counted call stays counted. This is meant for evaluation: trying AIControls against real traffic before requesting a trial or enterprise license.

Calls that AIControls blocks because the workload isn't registered don't count toward either limit. When the unregistered workload mode is Enforce, a call denied with workload_not_registered isn't a request, and a workload that only made blocked calls isn't an identity. If that workload makes other counted calls, for example after you register it or when the mode is Audit, those calls and the workload count as usual. Other denied calls count.

Once either limit is reached, AI request processing (MCP tool calls and LLM requests) is blocked with the same "load a license to continue" behavior described below — the Admin UI stays fully accessible throughout, and nothing about your existing setup needs to change once you activate a real license.

The free tier does not apply to Nirmata-managed SaaS deployments, which require a license (trial or enterprise) from the start.

Usage telemetry is part of the Free plan: once telemetry.endpoint is set, a Free install sends a daily usage document and telemetry.enabled: false is ignored. Paid plans send it only when opted in. See Usage telemetry.

Config-file tier (deprecated)​

Older self-hosted installs set ui.tier: team or ui.tier: enterprise (or proxy.mode: team) in the configuration file instead of loading a license. That setting is deprecated, and from v1.22.0 AIControls refuses to start with ui.tier set. Load a license before upgrading to v1.22.0. While an install with no license loaded relies on it, AIControls logs a warning at every start.

Plan-based enforcement is the default. The license's plan decides which features are unlocked (user management, SSO login, full capture, and more than two providers). An unlicensed self-hosted install gets the Free plan, apart from the deprecated ui.tier and proxy.mode grant, which stops working in v1.22.0. The tier the Admin UI shows comes from the license: the license's plan when one is loaded, the config-file tier while it applies to an unlicensed install, and Free otherwise. See Plans and entitlements.

See What plan-based enforcement gates for what each plan and add-on unlocks once it is on.

Plan-based enforcement and the compatibility opt-out​

Plan-based enforcement is the default. Features, limits, locked controls and upgrade prompts follow the loaded license. An Enterprise license keeps every feature. Installs that never selected a mode move to plan-based enforcement when they upgrade to v1.21.1, within two minutes of every running replica supporting it. Compatibility mode, which gates features and limits the way releases before plan-based enforcement did, stays selectable as an opt-out until v1.22.0, when it and the ui.tier setting are removed.

Deployments with storage disabled stay in compatibility mode, because they have no place to keep the setting or a license.

Before you upgrade, confirm that your license carries the plan you expect. Unlicensed self-hosted installs get the Free plan. To keep the previous behavior for now, select Compatibility (steps below, or the admin API with "compat") before or after the upgrade; an explicit selection is kept.

  1. As an admin, go to Setup → System → License.
  2. In the Plan card, set Enforcement to Plan-based or Compatibility.
  3. For Plan-based, select Turn on to confirm.

The new mode applies within two minutes. On a multi-replica install it applies once every running replica supports it; until then the card says how many replicas it is waiting for. Once it has applied, a replica running an older version that does not support it is reported not ready instead of serving under the old rules.

Setting Enforcement to Compatibility applies at once and needs no confirmation. Both changes are recorded in the configuration audit log. Viewers cannot change the mode.

You can also select the mode with the admin API:

curl -X PUT "$YOUR_WORKSPACE_URL/api/v1/admin/entitlements/enforcement" \
-H "Authorization: Bearer $ADMIN_TOKEN" \
-d '{"mode": "catalogue"}'

Use "compat" to opt out. See Enforcement mode.

Plan limits​

With plan-based enforcement, the default, each plan also sets limits. A limit never stops traffic from an identity that already works. It refuses new additions, trims history, or turns off one optional behavior, and the Admin UI says which. In compatibility mode, the limits below that come from the plan catalogue do not refuse anything, but the legacy limit of two upstreams still applies unless the legacy ui.tier is enterprise; see Plan-based enforcement and the compatibility opt-out.

LimitAt the limit
SeatsSeats are counted each calendar month (UTC): every person, service-account session and machine credential (virtual key, PAT, cross-app access or Entra app) with traffic, plus users invited this month who have not sent traffic yet. Kubernetes workloads and registered workloads are not seats. From 90% of the plan, admins see a banner. Past the plan plus a 10% grace, creating a user, approving a developer access request, or a developer registering with an email code returns 402, and a person signing in with SSO for the first time sees a message asking them to contact their administrator. Each refusal is recorded in the configuration audit log. People who already have an account keep signing in. Virtual keys and service-account credentials are always issued; one issued past the grace marks the month as a seat overage, shown on the License page for billing review.
TeamsCreating a team past the plan's number returns 402; the built-in Default team does not count. Adding or changing an identity-provider group binding on an existing team is never limited.
Workload agentsTurning on enforcement for one more workload past the number you bought returns 402. Turning it on again for a workload that already has it never counts, and discovery continues.
UpstreamsSaving a provider configuration that raises the number of enabled upstreams past the plan returns 402.
Raw retentionAudit events, prompt and response snippets, and full-capture blobs are kept for the smaller of your configured retention and the plan's. A configured "keep forever" uses the plan's. The Data settings page shows Set by plan when the plan's value applies.
Trend retentionCost and productivity charts accept any range but show data only inside the plan's window, with the earlier part marked as locked.
Full-capture sessionsEach seat allows a number of fully captured sessions a month. Past that, new sessions are recorded without full capture until the month resets; sessions already captured this month keep capturing. Admins see a banner.

A refused change returns 402 with a body that names the limit:

{
"error": "Teams: your plan allows 3",
"upgrade": true,
"feature": null,
"required": null,
"addon": null,
"limit": { "name": "teams", "value": 3, "current": 3 }
}

Managing your license​

Go to Setup → System → License in the Admin UI to:

  • View your current plan and expiry date
  • Request a trial extension or an enterprise upgrade
  • Start an Advanced Security trial on Business
  • Upload a new .lic file you received from Nirmata
  • See your plan, add-ons, and limits with usage on the Plan card

The Plan card​

Below the license status, the Plan card shows:

  • Plan and Source: the plan name (Free, Team, Business, or Enterprise), a Trial tag for a trial, and where the plan comes from: a license, no license, or the deprecated ui.tier setting. When a paid license has expired, a notice says so and names the plan the install now runs on.
  • Enforcement (admins only): Plan-based (default) or Compatibility, with a note while a selection has not applied yet. See Plan-based enforcement and the compatibility opt-out.
  • Limits (admins only): whether plan limits are Enforced or Shown, not yet enforced. While they are not enforced, the card shows each limit but nothing is refused.
  • Add-ons: each add-on with its end date, or Expired, in grace with the date it ended, or Lasts as long as the license.
  • Limits: each limit with a usage bar. A limit with no cap shows Unlimited. A tenant with no license on a hosted deployment shows Blocked. A limit under billing review shows a Billing review tag, and a monthly limit shows the date it resets.

Admins also see two notices on this page:

  • The ui.tier setting is deprecated. It appears while an install with no license relies on the config-file tier, and names the release that stops honoring it (v1.22.0).
  • Licence not applied. It appears when the last upload was refused, with the reason. Viewers see only a short, general message, because the reason can name tenant or cluster ids.

The Settings page no longer shows a tier row. System → About shows the plan name under Plan & limits.

Locked controls​

A feature your plan or add-on does not include stays visible, but its action is disabled. A lock icon and one line say why, for example "Shadow MCP quarantine is on Business" or "Advanced Security is available with Advanced Security". Admins also get a See link to the License page. Viewers and developers see the line only. Data you could already read, such as incidents and findings, stays readable.

On the Security pages, the incident triage actions and the baseline alert actions (acknowledge, dismiss, accept) lock without Advanced Security. On the Workloads pages, enforcement, contain and release, and the kill switch lock without Workloads. While you have opted out to compatibility mode, nothing locks that was available before.

When a request is refused because of your plan, the message is the same wherever it appears: one line naming the feature or limit, and for admins a See link to the License page.

Upgrade prompts​

Nirmata AIControls tells admins, in counts only, when the install would benefit from a higher plan or the Advanced Security add-on. For example, a prompt can say that you are using all of your plan's teams. A prompt never contains names, emails, policy names, or request content. Developers and viewers never see prompts.

  • Frequency. An admin sees a given prompt at most once every 14 days.
  • Dismissal. Dismissing a prompt hides it from you permanently, even if its trigger fires again. Other admins still see it until they dismiss it. Dismiss with POST /api/v1/upsell/prompts/{id}/dismiss.
  • Plan changes. A prompt shows only while you are on the plan it upgrades from. Changing plans removes it.
  • Delivery. Prompts are delivered in the app. The only other place one appears is the weekly digest email's Plan section, described below. Nothing is sent to Slack, Teams, or webhooks, and no prompt triggers its own email. The day-60 security findings summary is an in-app notification only.
  • Never blocking. A prompt is informational. It never refuses or slows a request.

Upgrade prompts API lists every trigger and the endpoints.

The Plan section of the weekly digest​

The weekly governance digest email has a Plan section for admins, with at most one prompt a week and a Compare plans link to the License page. A prompt shown in the digest counts as seen. The section is omitted when there is nothing to show, and viewers who receive the digest never get it. Daily digests have no Plan section.

Start an add-on trial​

On Business, you can try Advanced Security for 14 days. Each organization gets one trial of each add-on, and your plan does not change.

  1. Go to Setup → System → License.

  2. Click Start Advanced Security trial. The button appears for administrators on Business while the license does not already include the add-on.

  3. Confirm. A hosted organization gets the trial at once, and the License page lists the add-on with its end date. A self-hosted install sends the request to Nirmata, who reply with a license that includes the trial.

When the trial ends, its features lock again and your data stays.

Grace period​

Licenses are normally issued with a grace period after their expiry date — 14 days unless Nirmata set a different length for yours — during which AI traffic keeps flowing normally while you renew. Your license's actual grace period is shown on the License page.

While a trial is inside that window, the License page badge changes to Active (Grace Period) with a countdown to the date service will actually be blocked — hover the badge, or check the Service blocked on row, for the exact date. The expiry date shown on the page is not the date AI traffic stops; the grace period countdown is.

A license issued with a zero-length grace period is blocked as soon as it expires, with no grace window at all.

On Nirmata-hosted AIControls, a paid license that expires past its grace period leaves the tenant read-only for 30 days: you can still sign in, view and export, but changes and AI traffic are refused, and subscribing again restores access. See When a hosted subscription ends.

Kubernetes Self-Hosted​

Self-hosted Kubernetes licenses are bound to your cluster rather than to a Nirmata account — a license issued for one cluster will not activate on another.

1. Get your cluster ID​

kubectl get namespace kube-system -o jsonpath='{.metadata.uid}'

2. Request a license​

Email the ID above to support@nirmata.com with your organization name and whether you'd like a trial or enterprise license. Nirmata will send you a signed .lic file.

3. Activate the license​

Create a Secret from the file in the release namespace, then point the chart at it:

# Replace NAMESPACE with the namespace of your `helm install`
kubectl create secret generic aicontrols-license \
--from-file=license.lic=./path/to/license.lic \
-n NAMESPACE
# values.yaml
license:
existingSecret: aicontrols-license

The chart mounts the Secret read-only at /etc/aicontrols/license and sets proxy.licenseFile to /etc/aicontrols/license/license.lic. To use a different key or directory, set license.secretKey or license.mountPath. An explicit proxy.licenseFile takes precedence over the path the chart derives. The proxy reads the file once on first startup and stores the license in its database, so to replace it later, upload the renewed license in the Admin UI.

An install with the Admin UI turned off (ui.enabled: false) enforces the license the same way: a blocked or expired license, or the free tier limits on an install with no license, refuse AI traffic exactly as they do with the UI on. The proxy reports ready only after it has read the license.

On a kind cluster from the quickstart, pass the file with make kind-quickstart LICENSE_FILE=/path/to/license.lic. See Quickstart on kind.

Once loaded, you can also upload a renewed license directly from Setup → System → License in the Admin UI — no restart or redeploy required.

Rebuilding or migrating your cluster?

Your license stops working if the cluster is rebuilt or you move to a new cluster. Email support@nirmata.com for a reissued license.

Upload rejected: tenant/cluster mismatch​

When you upload a license through the Admin UI, it is validated against your cluster's identity — the kube-system namespace UID from step 1 — before it is accepted. A license whose tenant_id does not match that UID (including a license issued without any cluster binding, or one issued for a different cluster) is rejected with a 422 tenant-binding validation error (for example license rejected: license: issued for tenant "…", this instance is "…") instead of appearing to activate and then reverting to No License.

This check depends on the proxy having discovered the cluster's identity at startup. If that lookup fails — typically missing RBAC (the proxy needs get on the kube-system namespace) or an unreachable API server — the proxy logs a cluster identity warning and skips tenant binding for that run, so a mismatched license may be accepted. If you see that warning, fix the underlying RBAC/connectivity error and restart the proxy before relying on this validation.

If an upload is rejected:

  1. Re-run the command from step 1 and compare the UID with the one you sent to Nirmata when requesting the license.
  2. If they differ (for example, the cluster was rebuilt since the license was issued), email support@nirmata.com with the current UID for a reissued license.
  3. If the upload succeeds but the response reports the license did not activate, check the proxy logs for the revalidation failure reason (expiry, cluster binding, or storage errors).