Embed the AI tutor
Add the InsyteAI voice tutor to your own website or learning platform. You create an API key, paste one line of HTML, and learners can start a session on any topic you choose. Sessions use the credits of the account that owns the key.
1. Create an API key
Sign in and open API keys. Give the key a name.
For anything public, list the websites that may use the key under Allowed domains, for example example.com or *.example.com. The tutor then only loads inside pages on those sites: browsers refuse to show it anywhere else, and opening its address in a tab of its own is refused too. Direct API calls from a browser are limited to the same sites. A key with no allowed domains works on any site.
Treat a key like a password. If one leaks, turn it off on the same page and create a new one.
2. Add the tutor to your page
<iframe src="https://insyte.vercel.app/embed/new?apiKey=YOUR_API_KEY&topic=Fractions" width="100%" height="600" frameborder="0" allow="microphone" ></iframe>
The allow="microphone" attribute is required: without it the browser blocks the learner’s microphone and the tutor cannot hear them.
3. Options
Add these to the address in src. Values must be URL-encoded.
- apiKey (required): your key.
- topic: what the session is about, for example
topic=Photosynthesis. Without it the learner is asked. - theme:
lightordark. The default is light. - accent: your brand colour as a hex value without the #, for example
accent=1d4ed8. Buttons and highlights use it. - getFeedback:
trueasks the learner for a short rating when the session ends.
/embed/new?apiKey=YOUR_API_KEY&topic=Fractions&theme=dark&accent=1d4ed8
4. Sessions from your own code
Your server can list the sessions a key has started. Send the key in the Authorization header.
curl https://insyte.vercel.app/api/embed/sessions?limit=50 \ -H "Authorization: Bearer YOUR_API_KEY"
The answer is a list of sessions with their id, topic, status and start and end times. limit can be from 1 to 200.
5. Webhooks
A webhook tells your server when something happens, so you don’t have to keep asking. Open a key on the API keys page, choose Webhook, and enter an https address on your server. You are shown a signing secret once; keep it on your server.
We send a POST with a JSON body for these events:
- session.started: a learner started a tutor session with the key.
- session.ended: the session finished. Includes
durationSeconds. - webhook.test: you pressed “Send test event”.
{
"id": "evt_3f1c9a...",
"type": "session.ended",
"created": "2026-11-10T09:30:00.000Z",
"data": {
"sessionId": "b6f0...",
"topic": "Fractions",
"startedAt": "2026-11-10T09:18:00.000Z",
"endedAt": "2026-11-10T09:30:00.000Z",
"durationSeconds": 720
}
}Check that an event really came from us before trusting it. The X-Insyte-Signature header has the form t=TIME,v1=SIGNATURE. The signature is the HMAC-SHA256, in hex, of the time, a dot, and the raw body, using your signing secret. Reject events whose time is more than five minutes old.
import { createHmac, timingSafeEqual } from 'node:crypto';
function isFromInsyte(rawBody, header, secret) {
const { t, v1 } = Object.fromEntries(header.split(',').map((part) => part.split('=')));
if (!t || !v1 || Math.abs(Date.now() / 1000 - Number(t)) > 300) return false;
const expected = createHmac('sha256', secret).update(t + '.' + rawBody).digest('hex');
return v1.length === expected.length && timingSafeEqual(Buffer.from(v1), Buffer.from(expected));
}Answer with any 2xx status within five seconds. Each event is sent once and is not retried, redirects are not followed, and the address must be a public https site.
Limits and errors
- Rate limits: each key has an hourly and a daily request limit, shown on the API keys page. Going over returns
429. - Credits: a session needs at least one credit on the owning account. Without it the answer is
402with the codeINSUFFICIENT_CREDITS. - Domains: a key with allowed domains only shows the tutor on those sites, over
https(localhostalso works overhttpfor development). A server-side call that sends noOriginheader needs a key without allowed domains. - Keys: a missing, expired or switched-off key returns
401.
Watching usage
Each key on the API keys page has a “Usage in the last 30 days” panel with requests and sessions per day, so you can see when a site is active and catch a key that is being used more than you expect.