Graine AI
Enterprise

Plans and tiers

What an enterprise agreement gives you — higher call concurrency, dedicated and customer-hosted deployment, single-jurisdiction residency, a longer verifiable audit window, a negotiated rate card and a named support tier — each grounded in a per-organization setting the platform enforces.

An enterprise agreement with Graine raises the ceilings that actually constrain a production integration, and opens deployment shapes the shared cloud cannot offer. Concretely, it moves seven things: how many calls you can run at once, how you are deployed, where your data is processed, how long your audit trail is kept and exportable, what you pay per minute, how you are billed, and how you are supported.

Each of those is a stored per-organization value, not a code path — which is why a limit can be raised for your account alone, live, and take effect across every worker within a minute, with no release and no restart.

Commercial values — rates, minimum commitments, payment terms and support terms — are quoted per agreement and appear below as Contact sales.

What enterprise adds

CapabilityShared cloud, standardEnterprise
Simultaneous live calls100 per organization, 100 per agent, under a shared platform ceilingSet to your peak, per organization and per agent
Batch parallelism10 concurrent contacts per batchSet per organization
Reserved capacityShares a platform-wide ceilingYour deployment is the ceiling — with a dedicated instance
Deployment modelMulti-tenant cloud we operateDedicated instance, or your own compute with our control plane
Data residencyFixed platform regions, not per tenantSingle jurisdiction, chosen at deployment
Audit retention400 daysAny window from 30 to 3,650 days, set per organization
Audit export and verificationFull history over the API, filterable, independently verifiableSame, across your longer window
Rate cardPlatform default ratesContact sales — negotiated, stored against your organization
Payment modelPrepaid creditsContact sales — invoicing and committed spend
Support tierstandardContact sales — channels, response targets, escalation path, named contact

Security controls are not a tier dimension

Tenant isolation, scope-based access control on every mutating endpoint, the append-only hash-chained audit log, HMAC-signed webhooks and per-organization rate limiting apply to every organization at every plan level. They are described in Security, not here, because there is no lower setting of them to sell you.

How a plan is applied

There is no plan catalog inside the platform. The organization configuration document has no plan field — a plan name is a label carried on the API key, and the only behaviour attached to it is a privilege ladder: a key may mint a new key on its own plan or a lower one, never a higher one. What governs your account is the set of per-organization values in this page, each independently adjustable.

That is an advantage in a negotiation rather than a gap. The honest answer to "what does Enterprise include?" is "these dimensions, set to what you need," and any one of them can be changed for your organization alone without waiting for a release.

Read your own account's settings at any time:

curl -sS https://api.graine.ai/v2/user/me \
  -H "Authorization: Bearer gat_YOUR_API_KEY"
{
  "organization_id": "organization-live-example",
  "developer": {
    "id": "dev_example",
    "name": "Example Integration",
    "key_id": "key_0f3a9c2b71d45e68",
    "key_preview": "gat_...4e68"
  },
  "plan": "trial",
  "rate_limit_tier": "trial",
  "concurrency": {
    "max": 100,
    "current": 12,
    "agent_max": 100,
    "global_max": 1000,
    "enforced": true
  },
  "wallet": {
    "currency": "USD",
    "balance": 4.35,
    "allocated_total": 5.0,
    "lifetime_allocated": 5.0,
    "total_spent": 0.65
  },
  "rate_limits": {
    "default_per_minute": 1000,
    "calls_per_minute": 500,
    "executions_per_minute": 500
  }
}

That single response is the authoritative statement of your tier.

Concurrency

The most consequential dimension: how many calls your organization may have in flight simultaneously. It is enforced by an atomic governor before every dial, not reconciled afterwards, so the limit is a real ceiling rather than a reporting threshold.

SettingDefaultGoverns
concurrency_limits.total_system100, seeded on organization creationSimultaneous live calls across the whole organization
concurrency_limits.per_agent100, seeded on organization creationSimultaneous live calls for any single agent
concurrency_limits.batch_size10, seeded on organization creationParallelism within one batch
Platform ceiling1,000Shared ceiling above your organization's limit

Your effective limit is the lower of the organization and per-agent values, which is why /v2/user/me reports both. The per-agent level only gates when it sits below the organization limit; above it, the value is tracking-only.

The first three levels are atomic counters in Redis incremented by a single Lua check-and-increment, so two workers cannot both take the last slot. Limits are read from the organization configuration and cached for 60 seconds — which is what makes "raise us to 400 lines for tomorrow's campaign" a configuration change rather than a deployment.

StandardEnterprise
Organization concurrency100, raised on requestContact sales — set to your peak
Per-agent concurrency100Contact sales
Batch parallelism10Contact sales
Time to change a limitUnder a minute, no redeployUnder a minute, no redeploy
Capacity isolated from the shared platform ceilingNot offeredAvailable with a dedicated deployment — Contact sales

Exhausting concurrency is not something you have to infer. The call request is refused with a specific code, and the response carries Retry-After:

{
  "error": 1300,
  "message": "Account concurrency limit reached (25 of 25 lines in use)."
}

When the live counts cannot be read the message degrades to Account concurrency limit reached; all lines are in use. — the code stays 1300 either way, which is what you branch on.

Two behaviours to plan around

Enforcement is itself a per-organization flag (features.concurrency_management_enabled). When it is disabled, counters still increment for observability but nothing blocks — used for controlled scenarios, never as a default.

If the coordination store becomes unreachable, the governor falls back to per-process counters. Calling continues; the limit stops being enforced globally until it recovers. This is monitored, and it is the reason reserved capacity is a contract term backed by a dedicated deployment rather than a configuration value.

Audit retention and export

Every state-changing request on the /v2 API writes one row to an append-only, per-organization audit log, and every row is exportable through the API. The retention window is genuinely adjustable per organization.

SettingDefaultRange
audit_retention_days400 days30 – 3,650 days, per organization

400 days is the default so a full financial year plus a filing month is always available. Rows are removed after the window by a sweep that records what it pruned, so legitimate retention and tampering stay distinguishable — a pruned log still verifies clean.

Export is a normal API read, filterable by action, resource, acting API key and time window:

curl -sS "https://api.graine.ai/v2/audit-logs?action_prefix=api_key.&since=2026-08-01T00:00:00%2B05:30" \
  -H "Authorization: Bearer gat_YOUR_API_KEY"

Each row carries its own hash and the hash of its predecessor, so an exported log can be re-verified independently of us. A live verification endpoint returns the same result:

curl -sS https://api.graine.ai/v2/audit-logs/verify \
  -H "Authorization: Bearer gat_YOUR_API_KEY"

Reading the audit log requires a key holding the audit:read scope. The mechanism, including what verification actually detects, is described in Security.

Deployment model and data residency

Covered in full on Deployment. Its bearing on tiering:

Shared cloudDedicated instanceYour compute, our control plane
Who runs the computeGraineGraineYou
IsolationLogical, per organizationSeparate stack and data storesYour infrastructure
Where call data and transcripts livePlatform regions belowThe region the instance is deployed inYour infrastructure
Region choiceNot per tenantChosen at deploymentYours
Concurrency ceilingShared platform ceiling above your limitYour instance is the ceilingYours
Credit checks, finalization, meteringOursOursStill ours — over the public internet
Egress requirement on your sideNoneNoneTCP/443 to our control plane, allowlisted
Air-gapped operationNot offeredNot offeredNot offered
CommercialsContact salesContact sales

The shared cloud runs in fixed regions:

DataRegion
Compute, agents, call records, organization configurationIndia (Mumbai, ap-south-1)
API credential storeUnited States (N. Virginia, us-east-1)
Call recordings and audio objectsFrance (Paris) — third-party object storage, not the cloud provider above

There is no per-tenant region pinning on the shared cloud — region is a property of the deployment. Single-jurisdiction processing is therefore a dedicated or customer-hosted deployment, scoped before contract rather than toggled in a settings page.

Calling window and feature flags

Six flags are set per organization and govern whole subsystems.

FlagDefaultGoverns
notifications_enabledonOutbound notifications
followups_enabledonAutomatic follow-up call scheduling
webhooks_enabledonWebhook event delivery
monitoring_enabledonMonitoring and metric collection
working_hours_enabledonEnforcement of the calling window
concurrency_management_enabledonWhether concurrency limits block or merely count

Calling-window enforcement is usually a compliance requirement rather than a preference, so it is worth stating separately. Each organization carries a timezone, a weekly schedule (default 09:00–18:00, Monday to Friday), a holiday list, and per-category overrides — follow-up calls, for instance, ship exempt from the window by default. Retry behaviour is configured alongside it, per outcome category, with both fixed-delay and exponential-backoff strategies.

Rates, the wallet and the credit ledger

Usage is metered against a prepaid credit balance. Every rate is stored per organization and is overridable per organization — that is the mechanism behind any negotiated commercial rate.

Rates live in organization_configs.cost_management, in USD, in two layers:

  • A flat default per cost component, used when nothing more specific applies: telephony, transcription, synthesis, language model, and a platform fee.
  • Per-provider and per-model rates, in the natural unit for each: telephony and transcription per minute, speech synthesis per 1,000 characters, language models per 1,000 tokens.

Your effective rates are readable rather than inferred:

curl -sS https://api.graine.ai/api/v1/credits/rates \
  -H "Authorization: Bearer gat_YOUR_API_KEY"
StandardEnterprise
Rate cardPlatform defaultsContact sales — negotiated, stored per organization
CurrencyUSD internallyContact sales
Initial creditsSeeded on organization creationContact sales
Payment modelPrepaid creditsContact sales — invoicing and committed spend
Volume discountsContact salesContact sales
Minimum commitmentContact salesContact sales

Two legacy /api/v1 endpoints

credits/rates and credits/ledger are the only calls on this page that are not /v2. There is no /v2 equivalent yet.

/api/v1 accepts your gat_ key but does not carry the /v2 tenancy guarantees — see Tenant isolation. Call them from your own backend with your own organization's key; do not hand an /api/v1 credential to a principal you would not trust with the whole tenant set, and do not build a customer-facing feature on them.

The credit ledger

Worth understanding because it is what your finance team will audit. Every movement of money is written as a ledger entry first and a balance second. Entries are typed — seed, top-up, grant, refund, correction, charge reversal, charge re-application — and reversing a charge is deliberately not the same operation as granting credit, so the two never blur in a reconciliation.

Entries carry an idempotency key with a uniqueness constraint, and the entry is inserted before any balance moves. A retried or double-submitted payment therefore loses the insert and returns the original entry rather than paying out twice. The remaining balance is always derived from allocated minus spent rather than read from a stored mirror, and adjustments above a fixed ceiling are refused outright rather than silently applied.

Every debit is auditable:

curl -sS "https://api.graine.ai/api/v1/credits/ledger" \
  -H "Authorization: Bearer gat_YOUR_API_KEY"

A call is refused before it dials if the wallet cannot fund it:

{ "error": 1400, "message": "Insufficient credits to place this call." }

Support

The platform stores a support tier per organization with an integer priority; standard and premium are seeded on organization creation. What a tier entitles you to — channels, response targets, escalation path and whether you have a named technical contact — is a contract term rather than a platform behaviour.

StandardPremiumEnterprise
Configured tierstandardpremiumContact sales
ChannelsContact salesContact salesContact sales
Response targetsContact salesContact salesContact sales
Named technical contactNot includedContact salesContact sales
Escalation pathContact salesContact salesContact sales

Response-time and availability commitments are agreed in the contract. Graine does not publish them as marketing figures.

API rate limits

Applied per organization on the /v2 API as a weighted sliding window, executed as a single atomic operation so two concurrent requests cannot both see headroom.

BucketLimitCovers
default1,000 / minuteEverything not listed below
calls.create500 / minuteCreating calls, batches and batch schedules
executions.list500 / minuteListing calls, executions and usage

Limits are keyed per organization, not per key, so minting more keys does not multiply your quota. Every response carries X-RateLimit-Limit, X-RateLimit-Remaining and X-RateLimit-Reset; a rejected request adds Retry-After and returns:

{
  "error": 1300,
  "message": "Rate limit exceeded: 1000 requests per minute for this organization. Retry in 12s."
}

These limits read a platform value rather than a per-organization one, so they are the same for every organization today and a higher request limit is a platform change rather than an account setting. Raise it during scoping if your integration needs it. In practice, spend and calling capacity are bounded by concurrency and the funding gate rather than by request rate; the limiter is a fairness control.

Reconciling usage

Usage aggregates are available directly, for the period and grouping you choose.

curl -sS "https://api.graine.ai/v2/usage?from_date=2026-08-01T00:00:00%2B05:30&to_date=2026-08-26T00:00:00%2B05:30&group_by=day" \
  -H "Authorization: Bearer gat_YOUR_API_KEY"
ParameterValuesNotes
from_date, to_dateISO-8601 with a timezone offsetDefaults to the last 30 days; the window may not exceed 366 days
agent_idAn agent identifierRestricts the aggregate to one agent
group_bynone, agent, dayBreakdown returned alongside the totals

The response reports call counts, connected minutes and spend. Results are cached for 60 seconds per organization and filter set.

One counting rule that will otherwise look like a discrepancy

Voicemail is a dimension, not an outcome. A voicemail pickup is stored as a no-answer plus a flag, so it is counted in both. The outcome fields therefore do not sum to the call total. This is intentional, and it is the correct behaviour when reconciling — but it will look like an error the first time you add up the columns.

Usage aggregates are computed from call records rather than from the credit ledger, so they answer "what did we do" quickly. For "what were we charged", reconcile against the ledger, which is the authoritative financial record.

Scoped before contract

A few things are agreed in a scoping conversation rather than switched on in a settings page. Stated here so they do not surface late in a procurement cycle:

  • Invoicing, purchase orders and tax documents are handled outside the platform.
  • Billing is in USD. Internal accounting uses a single currency.
  • Encryption keys at rest are platform-held. Field-level encryption covers phone numbers, webhook signing secrets and customer authentication headers — see Security.
  • Region is a property of the deployment, not a per-tenant setting on the shared cloud.
  • Committed-spend and annual terms are contractual and reconciled outside the platform.

On this page