Integration guide
From model and MCP calls to customer margin.
Ganivra stays outside your model and tool request paths. Send both through one telemetry API, attach customer and plan context to the shared execution, then report revenue later when approval, payment, or credit redemption happens.
Your first useful insight
Start with one call. Build toward customer margin.
First, get a trustworthy cost breakdown for one real execution. Then connect one customer and their revenue. Cohorts and trends become useful as your history grows.
- 01
Connect one AI feature
Add the SDK to your existing app or send an API event. Start with one workflow; you can expand later.
See SDK & API setup → - 02
See what a call costs
Inspect model usage, tokens, latency, and the cost breakdown. Add a private rate if the model is unpriced.
Check your dashboard → - 03
Identify the customer
Send customer_id, application, and feature with usage. Find which customers and features drive your spend.
Add customer context → - 04
Connect what they pay
Configure one customer pricing plan or import confirmed revenue. Compare it with AI cost to understand contribution margin.
Set up customer pricing →
From cost to value
Answer a question your provider bill cannot.
“Which customer or feature costs more to serve than it earns?” You do not need every integration to begin. Follow one execution from usage to customer revenue.
1. Confirm the connection
Run a supported call in your existing app, then check the dashboard. Open its execution to verify the model, tokens, latency, and cost. An accepted event confirms delivery; a priced event gives you your first cost insight.
The Python SDK captures supported calls made after initialization. REST clients send actual usage. Neither path imports historical provider usage automatically.
2. Add the customer context
Read a stable customer ID from your app. Add application and feature so spend has an owner. Customer IDs appear automatically; no separate customer registration is required.
# Python: wrap your existing AI call
with ganivra.trace(
application="support-app",
customer_id=account.id,
feature="support_assistant",
):
# Your existing supported AI call runs here
...REST: send these same fields inside attributes. Replace account.id with the customer ID from your own request context.
3. Connect customer revenue
In Profile & setup, define what the customer pays. Send the configured plan_key with each execution or assign the customer to that plan. You can also import confirmed revenue.
Your customer's pricing plan is separate from your Ganivra subscription. Profit requires revenue and complete cost data; unknown revenue is not a confirmed loss.
Configure customer pricing →4. Choose one improvement
Illustrative example: $50 of customer revenue and $80 of AI cost means a $30 contribution loss. Inspect the model and MCP steps to locate the spend before changing anything.
Test a cheaper model, reduce unnecessary calls, or review your customer pricing in your own app. Compare equivalent periods and check output quality as well as cost. Ganivra does not automatically change your routing or prices.
Read the coverage indicators before acting. Contribution margin here uses the costs and revenue you supplied; it is not total company profit. With only a few calls, prioritize execution details over cohort or trend conclusions.
Why MCP visibility matters
A tool can cost almost nothing and still trigger an expensive execution.
Agents do not stop spending when tools/call returns. They may reason over the result, fetch more context, validate an action, retry, or call another paid service. Provider dashboards show the model spend; tool logs show the invocation. Ganivra joins both sides.
- 01Model decidesPlanning cost
- 02MCP tool runsDirect tool or paid API cost
- 03Model continuesResult processing and generation
- 04Agent retriesHidden fan-out and margin risk
SDK & REST API
Integration instructions.
Return here whenever you need to connect another service, review the event contract, or update your instrumentation.
Technical cost signals
Model and provider · input, output, and cached tokens · latency · status and errors · execution IDs
Business context
Your product or site · current tenant/customer ID · workflow · feature · prompt version · optional revenue
No customer registration required.
Read the signed-in tenant or account ID from your own request context and send it as customer_id. Every new value appears automatically in customer economics and cohorts.
- Your Ganivra workspace
- Your company
application- Product, site, or domain
customer_id- Current B2B tenant/account
plan_key- Current configured pricing plan
Configure price once. Send usage facts per execution.
Send the stable plan_key configured in Ganivra. Your application never sends the plan's rate or calculates revenue during a model call; manual customer assignment remains an optional fallback.
| Pricing model | Configure in Ganivra | Send with each execution | Ganivra calculates |
|---|---|---|---|
| Monthly subscription | Monthly amount + plan key | customer_id + plan_key; add feature for feature margin | Monthly revenue allocated across that customer's executions |
| Per execution | Revenue rate + plan key | customer_id + plan_key; recommended feature | Execution rate minus the execution's AI cost |
| Token based | Revenue rate per 1M tokens + plan key | customer_id + plan_key; SDK captures tokens automatically | Captured tokens × the plan rate |
| Credits or units | Revenue per unit + plan key + exact usage attribute | customer_id, plan_key, and attributes.credits | Credits consumed × the plan's unit rate |
| Hybrid | Monthly amount plus execution and/or token rates | customer_id; SDK captures executions and tokens | Allocated base revenue plus captured usage revenue |
customer_id="account_northstar" · plan_key="growth" · credits=25Send the credits actually deducted by your system—not their monetary value. Use the exact attribute name configured on the plan. Treat one billable customer action as one execution_id; if that execution produces multiple model steps, repeat the same transaction-level credit value and Ganivra counts it once.
python -m pip install ganivraimport ganivra
ganivra.init(api_key="your_key")This alone captures cost telemetry. No prompt or response content is collected.
def run_ai(account, credits_debited):
with ganivra.trace(
application="customer-operations-platform",
customer_id=account.id,
plan_key=account.plan_key,
workflow="inbound_support_call",
feature="voice_agent",
metadata={"credits": credits_debited},
):
client.responses.create(...)Use a stable pseudonymous tenant ID—not a person’s name. For a credit plan, pass the units your system already deducted; do not send their price. Omit credits for subscription, execution, token, and hybrid plans because Ganivra derives their usage from the trace. Metadata accepts additional bounded JSON dimensions.
with ganivra.mcp_call(
server="crm-server",
tool="search_accounts",
transport="streamable_http",
auth_type="oauth",
metadata={"result_count": 3, "cache_hit": False},
provider_reported_cost_usd=0.002,
):
result = mcp_client.call_tool(...)Requires Ganivra Python SDK 0.4 or newer. The helper measures latency and outcome, inherits the active trace, and never receives arguments or results. For Node.js and other runtimes, send the equivalent MCP event to the same REST endpoint.
Usage and revenue · two different inputs
Which API does your app need?
Start with usage events. Add confirmed payment data when you want reported transactions alongside calculated customer economics. Both ingestion endpoints use the same server-side Ganivra workspace API key.
Events API: what your AI did
POST /v1/eventsSend model or MCP usage after the call. Include stable event, execution, and step IDs plus the usage facts needed to calculate cost.
Add attributes.customer_id and a configured attributes.plan_key for plan-rated revenue. This is your customer's pricing plan, not your Ganivra subscription.
Transactions API: what the customer paid
POST /v1/economics/transactionsSend a confirmed purchase, subscription payment, credit purchase, or refund from your backend or verified payment webhook. This reports a payment; it does not charge the customer.
Use the same customer_id. Include execution_id when the payment belongs to one particular result. Omit it for a general subscription or credit pack.
Why revenue can exist with zero transactions
Customer pricing plans and event-supplied revenue can populate the economics overview without creating a revenue ledger record. The Reported transactions table shows ledger records from the Transactions API, revenue imports, or manual revenue entry.
An empty table means no matching records in the selected period and customer filter. It does not mean your integration failed or your customers generated no revenue.
Keep the two flows connected
- Send usage with your own stable customer and execution IDs.
- Confirm payment in your system before reporting it.
- Send the same customer ID and, for a paid result, the original execution ID.
- Check Reported transactions, then inspect the linked execution.
Without an execution link, do not expect a subscription or credit-pack purchase to appear as revenue on one specific execution.
Retries, refunds, imports, and expected responses
Retry safely
Events return HTTP 202 with accepted and duplicate counts. Transactions return HTTP 201 with an ID and created: true; repeating the same external_id returns created: false. Reuse the ID for retries of the same transaction, not for different purchases. An existing record is not updated by resending its ID.
A 401 means the key is invalid or missing. A 422 means the payload failed validation. Retry temporary failures with backoff.
Report refunds separately
Use a new external ID, transaction_type: "refund", and a positive refund amount. Ganivra records it with refunded status and treats it as negative revenue in economics. Link the same customer and execution where applicable.
Import billing records
Use POST /v1/economics/revenue for one revenue entry, or POST /v1/economics/revenue/import with an entries array for a batch. Profile & setup also supports manual entry. These write to the same ledger.
Reuse the same external ID across ingestion paths for the same financial record. Do not send one payment with different IDs through multiple endpoints.
Understand revenue precedence
Recognized or refunded ledger records linked to an execution take precedence over its event-supplied or plan-rated revenue. Customer-month billing actuals can also replace estimated plan allocation. Import complete, correctly linked records and check the resulting coverage.
For non-USD transactions, provide exactly one reporting value: amount_usd or exchange_rate_to_usd. Amounts use major currency units.
API 02 · Optional · Confirmed purchases
Keep actual payment data current when you need it.
You do not need both APIs to start. API 01 already provides AI cost and plan-rated execution profitability from customer_id, plan_key, and usage. Add this purchase API when you also want actual credit purchases, subscription payments, renewals, discounts, and refunds reflected in Ganivra.
- 1Verify paymentValidate the Stripe signature and handle a successful webhook such as
payment_intent.succeeded. - 2Fulfil the purchaseUpdate credits, subscription access, or the purchased result in your own database. Ganivra never changes entitlements.
- 3Post to GanivraSend the confirmed transaction with your server-side Ganivra workspace key.
Stripe example
Example: your customer buys 1,000 credits for $49.
Use Stripe's PaymentIntent ID as external_id. It stays stable when Stripe retries the webhook, so Ganivra records the purchase once.
external_id- Payment provider's unique transaction ID
customer_id- Your internal customer or tenant ID
plan_key- Plan key configured in Ganivra
amount- Major currency units—Stripe's cents divided by 100
units_purchased- Credits granted by your application
https://api.ganivra.com/v1/economics/transactionsAuthorization: Bearer gv_live_...
Content-Type: application/json
{
"external_id": "pi_3QxExample",
"customer_id": "customer_123",
"plan_key": "growth",
"transaction_type": "credit_purchase",
"amount": 49,
"currency": "USD",
"units_purchased": 1000,
"source": "stripe",
"occurred_at": "2026-08-12T16:30:00Z"
}Include execution_id only when relevant.
For a paid resume, image, or report, send the original execution ID. Ganivra assigns the purchase revenue to that execution and recalculates profit. Omit it for a general credit pack or subscription purchase.
Send native currency plus reporting value.
USD needs only amount. For INR, EUR, and other currencies, also send exactly one of amount_usd or exchange_rate_to_usd from your payment or accounting data.
History remains effective-dated.
Send the new plan_key on future executions. Ganivra keeps the plan stored on earlier events, so upgrades and downgrades never reprice old usage. Refunds are appended as new transactions.
What your team owns
A small, explicit contract.
Ganivra needs operational facts from the call and stable business identifiers from your application. Everything else can be added incrementally.
Execution telemetry
Model calls send provider, model, operation, and tokens. MCP calls send event_type, server, and tool. Both send latency, status, and stable event/execution/step IDs.
Business attribution
application, dynamic customer_id, workflow, and feature connect spend and plan-derived revenue to the exact product action that caused them.
Revenue usage facts
Subscription, execution, token, and hybrid plans use captured trace facts. Credit/unit plans additionally require the units actually deducted, such as attributes.credits. Ganivra applies the assigned rate.
Metadata, never tool content
Send server, tool, transport, auth category, counts, categories, and flags. Never send arguments, results, scopes, credentials, workspace IDs, prompts, or responses.