BBizOS Docs

API keys, webhooks & external events

Everything the BizOS app does goes through one API, and an API key lets another system use it on your business's behalf: a school's admin portal messaging parents, a website creating leads, an ERP raising invoices. You choose exactly what the key may do, BizOS pushes replies and delivery status back to your system as signed webhooks, and a named event from your system can start a BizOS workflow.

Creating a key

  1. 1

    Settings → Connections & AI → API & webhooks → Create key

    Name it after the system that will hold it ("School portal"). Tick only the permissions it needs, for example chats.send and settings.whatsapp_manage for a messaging integration, or leads.manage for a website form.

  2. 2

    Copy the key once

    It looks like bzk_live_… and is never shown again. Store it as a server-side secret in the other system; never in a web page or a mobile app.

  3. 3

    Call the API

    Send it as Authorization: Bearer bzk_live_… to the same /v1 routes the app uses. Each route accepts the key only if the key holds one of the permissions the route checks.

  4. 4

    Watch the activity

    The key row shows when it was last used and from where; Activity lists every change it made. Revoke takes effect within seconds; Rotate keeps the old secret working for an hour so you can swap without downtime.

A business can hold up to 20 active keys. A key can also be given an expiry date and its own per-minute budget.

Keys for one branch

If your business uses Branches, pick a Branch when you create the key. The key then behaves like a teammate who works only at that branch: lists return that branch's records, another branch's record is “not found”, new records land at that branch, and whole-business routes (GSTR-1, accounting exports, campaigns) refuse it. Leaving the branch empty gives the key the whole business. Widening a key later is an explicit, audited choice by the Owner or an Admin.

Idempotency

Send an Idempotency-Key header on writes. If your system retries, BizOS returns the original response instead of creating a second lead or sending a second message.

How do I create and send an invoice through the API?

Issue it, then send it — two calls, two permissions:

PATCH /v1/invoices/:id/status   {"status":"SENT"}   # issues the draft; needs invoices.manage
POST  /v1/invoices/:id/send                         # sends the issued invoice; needs invoices.send

send on a draft returns 400 “Issue this invoice before sending it.” and on a cancelled invoice 400 as well; it never changes the invoice’s status. A key with invoices.send but not invoices.manage can re-send and chase issued invoices only. GST follows your business’s GST registration: the gst_enabled field is still accepted on invoices and quotations but has no effect — read it on the response to see what was applied.

Sending WhatsApp from another system

Contacts in the other system are usually not BizOS customers (parents, students, vendors), so sends are addressed to a phone:

POST /v1/messages
{ "to": "+919876543210",
  "contact": { "name": "Priya (parent of Arjun)", "external_ref": "student:4021" },
  "template_key": "…", "params": ["Arjun", "Term 2", "1,500", "30 Sep"] }

to takes any international number with its +<country code>; a bare 10-digit number starting 6–9 is read as Indian. BizOS finds or creates the conversation, shows the contact's name in Chats, and sends through the same path the inbox uses. A contact who replies STOP is refused thereafter, even though they are not a customer. POST /v1/messages/batch accepts up to 1 000 recipients, refuses bad numbers up front, paces the rest at about two a second and reports each recipient as sent, failed or skipped (opted out, plan cap). Templates are listed, created and submitted to Meta through the API too, so the other system can offer its own template screen; connecting the WhatsApp number itself stays a one-time step inside BizOS.

Webhooks

Add an HTTPS endpoint (up to 10 per business) under Settings → Connections & AI → API & webhooks → Add endpoint, choose the events, and store the signing secret it shows once. Every delivery carries X-BizOS-Event, X-BizOS-Event-Id (dedupe on it), X-BizOS-Timestamp and X-BizOS-Signature: v1=<hex>, the HMAC-SHA256 of <timestamp>.<raw body> with that secret. Answer 2xx within ten seconds; otherwise BizOS retries at 1 minute, 5 minutes, 30 minutes, 2 hours and 8 hours, and switches the endpoint off after twenty dead deliveries in a row (you are notified). Test, pause, rotate the secret, and replay any delivery from the same screen.

Payloads carry ids and the minimum fields, never full records; your system fetches more with its key if it needs to.

Starting a workflow from outside

POST /v1/events
{ "name": "fee_overdue", "payload": { "student_name": "Arjun", "amount": 1500, "parent_phone": "+919876543210" } }

One trigger, Event from another system, fires for every event; each workflow's conditions pick the events it wants (event.name is fee_overdue, event.payload.amount above zero). Actions can notify the owner or send a WhatsApp template to the phone carried in the payload. The automation.trigger permission lets a key fire events without being able to read or edit the workflows. See Workflows.

Plans and limits

ControlBehaviour
API access (the API & Webhooks module, ₹5,999 a year before GST)Off on the free platform and on for trials; not in any bundle, added on top of Billing or a bundle. When off, keys cannot be created and existing keys stop with an upgrade prompt — nothing is revoked.
API calls per month (plan limit)Metered per business; the meter is on Plan & billing. At the cap, calls get the same upgrade response as any other cap.
Requests per minutePer key (default 600, sends 60), plus a per-business ceiling from the plan. Over budget returns 429 with a Retry-After header.
SupportBizOS support can suspend a business's API access with a reason; nothing is revoked.

For developers

  • The full reference is an OpenAPI 3.1 document, openapi.json, generated from the API source: every route a key can reach, the permissions per operation, request schemas for the common writes, and the webhook payloads. Ask your BizOS contact for the current file, or find it in the repository under docs/integrations/.
  • A step-by-step integration guide for a third-party portal (setup, calls, webhook verification, data model, screens, acceptance criteria) accompanies it.

Common questions

Can an API key read or change my team, roles or plan?
No. Team, roles, business settings, billing, data export and import, and the Assistant are never available to keys, whatever permissions are ticked. The permission editor hides those options.
Does a message sent through the API count against my WhatsApp allowance?
Yes. It goes through the same send path as the inbox, so the monthly WhatsApp cap, opt-outs and the 24-hour free-text window all apply.
Can I send WhatsApp to people who are not customers in BizOS?
Yes. POST /v1/messages takes a phone number and an optional contact name and reference; the conversation appears in Chats under that name. STOP replies from such contacts are honoured too.
What if I lose the key?
Rotate it from Settings → Connections & AI → API & webhooks. You get a new secret immediately and the old one keeps working for an hour so the other system can be updated without a gap. If it may have leaked, Revoke it instead; that takes effect within seconds.
Which plan do I need?
API access is the BizOS API & Webhooks module, ₹5,999 a year before GST, added on top of Billing or any bundle; no bundle includes it. It is on during the 30-day trial, and the monthly call allowance is shown on Plan & billing.
Why does sending an invoice through the BizOS API return 400?
The invoice is still a draft. BizOS sends only issued invoices: first issue it with PATCH /v1/invoices/:id/status and status SENT (needs invoices.manage), then call POST /v1/invoices/:id/send (needs invoices.send).
Can a BizOS API key be limited to one branch?
Yes. Pick a branch when you create the key. It then reads and creates only that branch’s records, and whole-business routes such as GSTR-1 and accounting exports refuse it.