On this page
- 01What you'll set up
- 02How a budget works
- 03Choose how a budget is enforced
- 04Set the budget
- 05A worked example
- 06One budget for everything on the policy
- 07What callers see at the limit
- 08Choose what happens if the budget check cannot run
- 09Test it before you rely on it
- 10Pick starting values
- 11Keep it as code
- 12Roll out in three steps
- 13If something goes wrong
01
What you'll set up
In about eleven minutes you will give a policy a monthly and a daily budget, choose how it is enforced, prove it works with a test key, and decide what happens if the budget check itself cannot run.
- A monthly and a daily budget on a policy
- An enforcement style that fits how much control you want
- A test that shows the limit working before real traffic depends on it
- A clear, readable response when a limit is reached
- A rollout that never surprises a team
You need an owner or admin role and a policy bound to the traffic you want to cap. If you do not have a policy yet, start with the guide on creating your first policy.
02
How a budget works
A budget is checked before a request reaches the provider. If there is room, the call runs and its real cost is counted. If there is not, the call never leaves, so a blocked request adds no spend.
1Request arrives
Key, team, app
2Policy found
Most specific binding
3Budget checked
Daily and monthly room left
4Room left
The call runs and its cost is counted
5No room
HTTP 402, nothing sent to the provider
The same budget applies to requests on your own provider keys and to requests paid with Cloptima credits.
03
Choose how a budget is enforced
Every budget has an enforcement style. It decides what happens when spend reaches the limit.
| Enforcement | What it does | Use it when |
|---|---|---|
| Alert only (never blocks) | Tracks spend against the budget and never stops traffic | You are learning what normal spend looks like |
| Block immediately (fast counter) | Stops requests once the budget is reached, with a fast check before each call | You want a firm limit on interactive traffic |
| Precise block (atomic DB check) | Checks each request against the budget before it runs | You need exact accounting at the limit |
Block immediately
- The console default, and the right choice for most apps
- Adds almost no time to a request
- Needs at least one allowed provider and model on the policy (All qualifies)
Precise block
- Exact accounting right at the limit
- Adds a small check to each request
- A fit for finance automation and batch jobs
04
Set the budget
Budgets live on the policy form. The monthly budget is on the first step. The daily budget and the enforcement style are on the Advanced step.
- 1
Open the policy
Go to AI → Policies. Create a policy, or open the one you want to cap.
- 2
Set the Monthly budget
On Basics, enter the most this policy may spend in a calendar month, in US dollars. The presets are a quick start.
- 3
Choose the enforcement style
On Advanced, choose Budget enforcement.
- 4
Set the Daily budget
Still on Advanced, enter the daily limit. It cannot be higher than the monthly budget.
- 5
Review and save
The Review step lists every limit. The budget applies to new requests at once.
Basics
- 2Monthly budget
- 2000$500$2000$5000
Advanced
- 3Budget enforcement
- Block immediately (fast counter)
- 4Daily budget
- 100
05
A worked example
Take a support assistant on one policy with a monthly budget of $3,000, a daily budget of $150, and Block immediately. The numbers below are an illustration.
| Time (UTC) | What happens | Result |
|---|---|---|
| Most days | Traffic costs about $60 a day | Well inside both budgets |
| Tuesday 14:00 | A retry bug in a new release doubles the calls | Spend climbs fast |
| Tuesday 17:40 | Today's spend reaches $150 | New requests return HTTP 402 with the daily budget named |
| Tuesday 17:45 | The team sees the 402s and ships a fix | The monthly budget still has most of its room |
| Wednesday 00:00 | The daily budget resets | Traffic resumes under the same limits |
Without a limit, the same bug would have run until someone noticed the invoice. With one, the cost of the mistake is capped at the daily budget.
06
One budget for everything on the policy
A budget belongs to the policy. Every app, team, and key bound to the policy spends from the same daily and monthly allowance, so one limit covers a whole group.
| Goal | How |
|---|---|
| Give each team its own allowance | Create one policy per team and bind each to its team |
| Put one ceiling over everything in production | Bind a single policy to the production environment |
| Keep a company ceiling even when a team sets its own | Nothing extra. When several enforcing policies match, the lower budget applies |
Two policies, one request
The company policy caps production at $10,000 a month. The research team's own policy allows $15,000. A research request matches both. The lower limit applies, so the company ceiling holds.
07
What callers see at the limit
At the limit the request stops before it reaches the provider. The response is HTTP 402 and names the budget that was reached, so a developer knows what happened without opening a ticket.
{
"error": "Your AI request was blocked because the daily AI spend limit has been reached.",
"reason": "gateway_daily_budget_exceeded",
"violations": ["gateway_daily_budget_exceeded"],
"details": { "daily_budget_usd": "500", "estimated_cost_usd": "0.0123" }
}| Reason | Meaning |
|---|---|
| gateway_daily_budget_exceeded | The daily budget was reached. Requests resume after the UTC reset or when you raise it. |
| gateway_monthly_budget_exceeded | The monthly budget was reached. Requests resume next month or when you raise it. |
from openai import OpenAI, APIStatusError
client = OpenAI(base_url="https://api.cloptima.ai/v1/ai", api_key="clop_vk_...")
try:
reply = client.chat.completions.create(
model="gpt-4o-mini",
messages=[{"role": "user", "content": "Summarize this ticket"}],
)
except APIStatusError as error:
body = error.response.json()
if error.status_code == 402:
# Budget reached: queue the work or tell the user, do not retry in a loop
print(body["reason"], body.get("details"))
else:
raise08
Choose what happens if the budget check cannot run
Budget checks depend on Cloptima's own services. On the rare occasion one is unavailable, the policy's Fail mode decides what a request does.
Block on error (the default)
- The request waits for a budget decision, and stops if there is none
- No request is admitted without a budget decision
- The right choice for customer-facing and costly workloads
Allow on error
- The request continues without a budget decision
- The app stays available through an incident
- A fit for low-cost internal tools
Fail mode is on the Advanced step of the policy form, next to Budget enforcement.
09
Test it before you rely on it
Prove the limit with a throwaway policy. It takes a few minutes and removes any doubt.
- 1
Create a test policy
Set a Monthly budget of a few dollars and a Daily budget of a few cents. Choose Block immediately.
- 2
Bind it to a test key
Create a virtual key for the test and bind the policy to that key.
- 3
Send test calls
Open AI → Credentials & Keys, open Test Virtual Key, select the key, and choose Send Test Call. Repeat until the daily budget is used.
- 4
Read the 402
You should see the reason and the budget that was reached.
- 5
Clean up
Delete the test policy and key, or raise the budget to a real value.
10
Pick starting values
Start from how the app behaves today, then tighten after a week of real usage.
| Setting | A good start |
|---|---|
| Daily budget | About twice a typical day, so normal growth never trips it |
| Monthly budget | The AI budget your finance team has approved |
| Maximum output size | Set one on the policy. It keeps the cost of each request predictable |
Use AI → Explorer to find a typical day. Group by App for the last 7 days and read the spend column.
11
Keep it as code
Teams that manage infrastructure in Terraform can keep budgets in a pull request.
resource "cloptima_llm_gateway_policy" "support_production" {
name = "support-production"
mode = "enforce"
budget_mode = "hard_fast"
allowed_providers = ["openai"]
allowed_models = ["openai/gpt-4o-mini"]
daily_budget_usd = 150
monthly_budget_usd = 3000
fail_mode = "fail_closed"
}In Terraform, budget_mode accepts observe, soft, hard_fast, or hard_strict. They correspond to Alert only, Block immediately, and Precise block in the console. Block immediately (hard_fast) needs at least one allowed provider and model, so list them as above.
12
Roll out in three steps
You do not need to switch on blocking everywhere at once.
- 1
Start with Alert only
Set the budgets and watch spend in the Explorer for a week.
- 2
Block on one app
Switch to Block immediately on a policy bound to a single app.
- 3
Widen the binding
Bind the policy to more apps and teams as confidence grows.
13
If something goes wrong
Most surprises come from the enforcement style or from which policy applies.
| What you see | Likely cause | Fix |
|---|---|---|
| 402 gateway_daily_budget_exceeded | The daily budget was reached | Wait for the UTC reset, or raise the daily budget |
| 402 gateway_monthly_budget_exceeded | The monthly budget was reached | Raise the monthly budget, or wait for the new month |
| Traffic is never stopped | Enforcement is Alert only | Switch to Block immediately or Precise block |
| A different budget applies than you expect | Another bound policy has a lower budget | Check the bindings for the key, app, or team |
| The policy will not save with Block immediately | No provider or model is allowed on the policy | Allow at least one provider and model, or leave the lists on All |