ZOREAL

Documentation

The ZOREAL API over HTTPS and JSON: create meetings, manage their schedule, read what happened, and run a live room.

Make your first request

Create an API key in the dashboard, send it as a Bearer header, and a meeting is one request away. This call returns the room code people join at and the host token that runs the room.

CREATE A MEETING · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant \
  -H "Authorization: Bearer private_XXXXXXXXXXXXXXXXXXXXXXXX" \
  -H "Content-Type: application/json" \
  -d '{ "title": "Weekly sync" }'

Introduction

The API speaks JSON over HTTPS from one base address. Every path in this reference is shown in full, so a sample can be pasted as it stands, and every request sample carries its credential header.

Requests to the meetings surface are limited to 30 a minute per address; the presenter endpoints allow 12.

https://api.bynn.com

Authentication

API keys are created and managed in the dashboard. A key begins with private_ or public_, with sandbox_ added on test keys, and authenticates your organization. Send it as a Bearer header on every request.

Rotating a key issues a new one and keeps the old one working for 12 hours, so a deploy can catch up; rotation can also expire the old key immediately. A key is readable back in the dashboard after creation.

Two credential kinds appear in this reference: your API key, for account operations such as creating meetings, listing them and reading notes, and the per-meeting tokens returned when a meeting is created or joined, which authorize actions inside that one room. Host controls explains them once, at the top of the group.

AUTHENTICATED REQUEST · CURL
curl "https://api.bynn.com/v1/zoreal/meet/instant/meetings" \
  -H "Authorization: Bearer private_XXXXXXXXXXXXXXXXXXXXXXXX"
Keys belong on your server. Keep them out of browser code, mobile apps and public repositories, and if one may have been exposed, rotate it from the dashboard: the replacement is immediate and the old key can be expired on the spot.

Meetings

The lifecycle of a meeting: create it, schedule it, change it, end it, and read what happened.

Create an instant meeting

POST/v1/zoreal/meet/instant

AuthAPI key (Bearer)

Creates a meeting and returns its code, the address people join at, together with a host token that authorizes the host controls for this room. With no schedule fields the meeting is ready as soon as the host joins.

To create a scheduled meeting, add the schedule fields described in Schedule a meeting.

Request body

  • titlestringOptional
    Shown to everyone who opens the link. Up to 80 characters.
  • e2eebooleanOptional
    End-to-end encryption. It can be turned on later from inside the room, but only while the host is alone, and never off.

    Default: false

Returns

The room and its host_token. The token appears in this response and nowhere else - only a digest is stored - so keep it if the meeting will be managed later.

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant \
  -H "Authorization: Bearer private_XXXXXXXXXXXXXXXXXXXXXXXX" \
  -H "Content-Type: application/json" \
  -d '{ "title": "Weekly sync" }'
RESPONSE
{
  "room": {
    "code": "kfm-qhtz-pgd",
    "created_at": "2026-09-01T10:14:22Z",
    "began_at": null,
    "title": "Weekly sync",
    "e2ee": false
  },
  "host_token": "<HOST_TOKEN>"
}

The code is ten letters in xxx-xxxx-xxx, drawn from a to z without the letter l, which is misread when a code is spoken aloud.

A meeting holds up to 25 people, and a call runs up to 90 minutes, measured from when the host first joins; the link itself survives the cap and can carry a fresh call.

When no media node can take a new room, the request answers 503 no_capacity.

Schedule a meeting

POST/v1/zoreal/meet/instant

AuthAPI key (Bearer)

A scheduled meeting is the same call as create with the schedule fields; there is no separate endpoint. Set scheduled_at and the link becomes a calendar object that opens 30 minutes before its start, for the host too.

Request body (in addition to title and e2ee)

  • scheduled_atdatetimeOptional
    When the meeting starts, ISO 8601.
  • scheduled_minutesintegerOptional
    Planned length, 1 to 600.
  • scheduled_tzstringOptional
    An IANA zone name. An unknown zone is refused with 422 rather than silently dropped. A zone rather than an offset, so a series set for 09:00 in Stockholm keeps 09:00 across the daylight-saving change.

    Europe/StockholmAmerica/New_York

  • recurrencestringOptional
    An RRULE body. Three components are honored: FREQ (DAILY, WEEKLY or MONTHLY), INTERVAL (a positive integer, 1 when absent) and UNTIL (a date, inclusive). Anything else is accepted syntactically and silently ignored: FREQ=WEEKLY;BYDAY=MO,WE means every week from the anchor, not Mondays and Wednesdays.

    FREQ=DAILYFREQ=WEEKLY;INTERVAL=2FREQ=MONTHLY;UNTIL=20261231

Returns

The same room and host_token shape as create; the schedule is not echoed back. Read it with Get a meeting, which returns scheduled_at, scheduled_minutes, scheduled_tz and opens_at.

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant \
  -H "Authorization: Bearer private_XXXXXXXXXXXXXXXXXXXXXXXX" \
  -H "Content-Type: application/json" \
  -d '{
    "title": "Design review",
    "scheduled_at": "2026-09-08T09:00:00Z",
    "scheduled_minutes": 45,
    "scheduled_tz": "Europe/Stockholm",
    "recurrence": "FREQ=WEEKLY;INTERVAL=1"
  }'
RESPONSE
{
  "room": {
    "code": "npg-wkfd-tmc",
    "created_at": "2026-09-01T10:21:07Z",
    "began_at": null,
    "title": "Design review",
    "e2ee": false
  },
  "host_token": "<HOST_TOKEN>"
}

Once created, recurrence and scheduled_tz cannot be changed. The time can be moved with Reschedule a meeting; a single occurrence can be closed but not moved.

An occurrence admits late arrivals within its planned length, and at least 30 minutes. A series with no dates left answers 409 series_over.

Rename a meeting

POST/v1/zoreal/meet/instant/:code/host/title

AuthHost token

Sets or clears the meeting's title. This is the one host control that also works on an ended meeting: a past meeting's name stays editable, its time does not.

Request body

  • host_tokenstringOptional
    From the create response. The meeting owner may omit it and authenticate with their API key instead.
  • titlestringOptional
    Up to 80 characters. Sending an empty string clears the title, which is why the field is optional.
  • session_idintegerOptional
    Renames one past session instead of the room, so a recurring series keeps its name.
REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/title \
  -H "Content-Type: application/json" \
  -d '{ "host_token": "<HOST_TOKEN>", "title": "Budget review" }'
RESPONSE
{ "title": "Budget review" }

A rename reaches people who join after it; participants already connected keep the name they joined under.

A rejected title answers 400 with the reason. Anything else - an unknown code, a wrong credential - answers 404, so the endpoint confirms nothing about which codes exist.

Reschedule a meeting

POST/v1/zoreal/meet/instant/:code/host/schedule

AuthHost token

Moves a scheduled meeting's time. A recurring meeting moves as a whole series; a single occurrence cannot be moved, only closed.

Request body

  • host_tokenstringOptional
    From the create response. The meeting owner may omit it and authenticate with their API key instead.
  • scheduled_atstringRequired
    The new start, ISO 8601. A string that does not parse answers 422.
  • scheduled_minutesintegerOptional
    The new planned length. Must be positive.
  • notifybooleanOptional
    Re-sends the calendar invitation to everyone already invited.

    Default: false

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/npg-wkfd-tmc/host/schedule \
  -H "Content-Type: application/json" \
  -d '{
    "host_token": "<HOST_TOKEN>",
    "scheduled_at": "2026-09-15T09:00:00Z",
    "notify": true
  }'
RESPONSE
{
  "scheduled_at": "2026-09-15T09:00:00Z",
  "scheduled_minutes": 45,
  "notified": 4
}

A meeting that was never scheduled answers 409: only a scheduled meeting has a time to move.

Calendar clients move the event because its sequence number grows with each reschedule.

Cancel or end a meeting

POST/v1/zoreal/meet/instant/:code/host/end

AuthHost token

Ends the current call, and with scope: "series" retires the link itself. A meeting is ended, never deleted: the record and its history survive.

Request body

  • host_tokenstringOptional
    From the create response. The meeting owner may omit it and authenticate with their API key instead.
  • scopestringOptional
    occurrence closes this date and the next occurrence opens on schedule; series ends the call and retires the link. A one-off meeting is always treated as series, because it has no other date to protect.

    occurrenceseries

    Default: occurrence

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/end \
  -H "Content-Type: application/json" \
  -d '{ "host_token": "<HOST_TOKEN>", "scope": "series" }'
RESPONSE
{ "ended": true, "scope": "series" }

The response's scope reports what the server resolved, not what was asked: a one-off answers "series" even when the caller sent occurrence.

Everyone is disconnected at the media node first. If the node refuses, the request answers 502 and the meeting keeps running; nothing is left half-ended.

Ending a scheduled series emails a calendar cancellation to everyone invited; closing one occurrence emails nothing.

A closed occurrence reopens if the creator walks back in; guests stay gated. The 90-minute cap ends a call the same way this endpoint does, measured from the host's first join.

List meetings

GET/v1/zoreal/meet/instant/meetings

AuthAPI key (Bearer)

The meetings your account owns: upcoming, live and past, newest first. This is also where attendee data lives - each row carries who was in the room.

Query parameters

  • limitintegerOptional
    Rows per page, 1 to 100.

    Default: 50

  • beforestringOptional
    The opaque cursor from a previous page's last row. An unreadable cursor returns the first page.
  • qstringOptional
    Search. Every whitespace-separated term must match the title, the code, an attendee's name or a tag name; up to 6 terms.
  • fromdateOptional
    Earliest day to include.
  • todateOptional
    Latest day to include.
  • tags[]array of stringsOptional
    Tag tokens, repeated once per tag. A meeting must carry all of them; up to 10.
  • horizon_daysintegerOptional
    How far forward to unroll a recurring series into its upcoming dates, 1 to 90.

Returns

{ "meetings": [...] }, at most 500 rows. Past rows additionally carry session_id, actual_minutes and capture, whose transcription reports recording, processing, ready or failed.

REQUEST · CURL
curl "https://api.bynn.com/v1/zoreal/meet/instant/meetings?limit=2&q=sync" \
  -H "Authorization: Bearer private_XXXXXXXXXXXXXXXXXXXXXXXX"
RESPONSE
{
  "meetings": [
    {
      "code": "kfm-qhtz-pgd",
      "cursor": "MjAyNi0wOS0wMVQxMDo0MToxNi4wMDAwMDB8OTQx",
      "title": "Weekly sync",
      "status": "ended",
      "began_at": "2026-09-01T10:14:22Z",
      "created_at": "2026-09-01T10:02:51Z",
      "last_used_at": "2026-09-01T10:41:16Z",
      "scheduled_at": null,
      "series_start_at": null,
      "scheduled_minutes": null,
      "scheduled_tz": null,
      "recurrence": null,
      "ended_at": "2026-09-01T10:41:16Z",
      "e2ee": false,
      "presence_on_join": null,
      "attendees": [
        { "name": "Anna Lindqvist", "role": "owner", "email": null },
        { "name": "Jonas Vikander", "role": "participant", "email": null }
      ],
      "invited": [],
      "tags": []
    }
  ]
}

Pagination is a cursor, not an offset: pass the last row's cursor back as before. While paging, horizon_days expansion is skipped.

A tag token that resolves to nothing returns an empty list, not an unfiltered one.

status is computed server-side: live, ended or not_started. email on an attendee is only ever a guest's self-typed address; accounts expose none.

Get a meeting

GET/v1/zoreal/meet/instant/:code

AuthNone (public)

Resolves a meeting code to its public state: what a client needs before joining. No credential is required, because an invitation link has to work for someone without an account; a signed-in owner is recognized and gets host: true.

Query parameters

  • invitestringOptional
    An invitation token. When it is valid for this room, the response includes the invitee's name and email; an unknown token is silently absent, because it authorizes nothing and there is nothing to refuse loudly.
REQUEST · CURL
curl https://api.bynn.com/v1/zoreal/meet/instant/npg-wkfd-tmc
RESPONSE
{
  "room": {
    "code": "npg-wkfd-tmc",
    "created_at": "2026-09-01T10:21:07Z",
    "started_at": "2026-09-01T10:21:07Z",
    "began_at": null,
    "e2ee": false,
    "host": false,
    "title": "Design review",
    "scheduled_at": "2026-09-08T09:00:00Z",
    "scheduled_minutes": 45,
    "scheduled_tz": "Europe/Stockholm",
    "opens_at": "2026-09-08T08:30:00Z",
    "policy": {
      "screen_share": true,
      "microphone": true,
      "camera": true,
      "messages": true,
      "reactions": true,
      "knock": true
    }
  },
  "invite": null
}

began_at is when the current call started, null when none is running; started_at is when the link was minted. scheduled_at is the next occurrence of a series, never the anchor, and opens_at is 30 minutes before it.

This endpoint returns no attendees; attendee data lives on List meetings rows.

An unknown or ended code answers 404.

Meeting notes

GET/v1/zoreal/meet/instant/:code/sessions/:session_id/notes

AuthAPI key (Bearer), owner only

The transcript of one past session, speaker by speaker. Transcription runs on ZOREAL's own deployment, not a third-party service, and only when it was started in the call - see Transcription.

Path parameters

  • :codestringRequired
    The meeting code.
  • :session_idintegerRequired
    From a past row on List meetings.

Returns

status is one of: processing, still transcribing; ready, segments available; empty, everything settled and nobody spoke; failed, every track failed; none, nothing was captured, and the other fields are omitted.

REQUEST · CURL
curl "https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/sessions/941/notes" \
  -H "Authorization: Bearer private_XXXXXXXXXXXXXXXXXXXXXXXX"
RESPONSE
{
  "notes": {
    "status": "ready",
    "turns": [
      {
        "speaker": "Anna Lindqvist",
        "start": 12.4,
        "end": 18.9,
        "text": "Let us start with the budget."
      },
      {
        "speaker": "Jonas Vikander",
        "start": 19.2,
        "end": 24.1,
        "text": "The numbers are in the shared sheet."
      }
    ],
    "pending_tracks": 0,
    "began_at": "2026-09-01T10:14:22Z"
  }
}

Owner-scoped: only the meeting's owner may read notes. Anyone else gets the same 404 an unknown meeting gets.

As a PDF

GET/v1/zoreal/meet/instant/:code/sessions/:session_id/notes/pdf

The same transcript as a document. Answers application/pdf as an attachment named zoreal-meet-notes-<code>-<date>.pdf.

Host controls

Actions on a live room. Every control below takes the room's host_token, returned once by create, in the request body; the meeting's owner may omit it and authenticate with their API key, and a promoted co-host uses their participant_token in the same slot. A wrong or missing credential answers 404, never 403: these endpoints do not confirm that a code exists.

Controls name their target by identity, the per-join identifier every participant carries. Identities are minted per join, so someone who leaves and returns is a new identity.

Presenter control

POST/v1/zoreal/meet/instant/:code/present

AuthParticipant token

One person presents at a time, and the stage is a server-side lock: no join grant carries the screen-share source, so a client that publishes without claiming the stage is refused by the media node.

Request body

  • identitystringRequired
    From the join response.
  • participant_tokenstringRequired
    From the join response.
  • host_tokenstringOptional
    Permits taking the stage from the current presenter.

Returns

displaced names the identity taken off the stage, and is null when the stage was free.

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/present \
  -H "Content-Type: application/json" \
  -d '{ "identity": "user_ab12cd34", "participant_token": "<PARTICIPANT_TOKEN>" }'
RESPONSE
{ "presenting": true, "displaced": null }

When somebody else is presenting and the caller may not take over, the answer is 409 carrying the holder's identity; the roster turns it into a name.

403 when screen sharing is off in the room policy - hosts are exempt from that one - and 403 when the caller has not satisfied the room's presence rule, from which hosts are not exempt. 404 for a stale credential.

Stop presenting

POST/v1/zoreal/meet/instant/:code/present/stop

Takes identity and participant_token. In the response, released: false means a host had already stopped the share or taken the stage - the browser sees both as a bare unpublish, and this field is how it tells them apart.

RESPONSE
{ "presenting": false, "released": true }

Promote a co-host

POST/v1/zoreal/meet/instant/:code/host/promote

AuthHost token (creator only)

Hands the host controls to someone in the room. This is the one host power a co-host does not inherit: only the meeting's creator may promote, so a room's authority spreads no further than the creator handed it.

Request body

  • host_tokenstringOptional
    The creator's token, or the creator's API key session.
  • identitystringRequired
    The participant to promote.
  • revokebooleanOptional
    Takes a promotion back.

    Default: false

Returns

The current co-host identities.

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/promote \
  -H "Content-Type: application/json" \
  -d '{ "host_token": "<HOST_TOKEN>", "identity": "user_3f9a1c02" }'
RESPONSE
{ "hosts": ["user_3f9a1c02"] }

Hostship is scoped to the live connection: leave and rejoin, and it is gone. The creator cannot be demoted; their identity carries the host_ prefix and is never in this list.

409 when the target is already a host. A co-host calling this gets the same 404 an unknown meeting gets. The roster's host marker renders from room metadata only the server can write.

Mute or remove

POST/v1/zoreal/meet/instant/:code/host/mute

AuthHost token

The moderation pair. Muting is a request the participant can undo; removal is executed by the media node itself.

Request body

  • host_tokenstringOptional
    From the create response. The meeting owner may omit it and authenticate with their API key instead.
  • identitystringRequired
    The participant to act on.
REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/mute \
  -H "Content-Type: application/json" \
  -d '{ "host_token": "<HOST_TOKEN>", "identity": "user_ab12cd34" }'
RESPONSE
{ "muted": true }

A muted participant may unmute again; a hard mute is a remove.

404 when the identity names nobody in the room; 502 when the media node refuses.

Remove

POST/v1/zoreal/meet/instant/:code/host/remove

The same body: host_token and the identity to disconnect.

RESPONSE
{ "removed": true }

Transcription

POST/v1/zoreal/meet/instant/:code/host/transcription

AuthHost token

Starts capturing the call's audio for Meeting notes. Starting is idempotent: asking twice is one recording. Everyone in the room can see that transcription is on; it cannot be switched on quietly.

Request body

  • host_tokenstringOptional
    From the create response. The meeting owner may omit it and authenticate with their API key instead.
REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/transcription \
  -H "Content-Type: application/json" \
  -d '{ "host_token": "<HOST_TOKEN>" }'
RESPONSE
{
  "recording": {
    "id": 118,
    "status": "recording",
    "started_at": "2026-09-01T10:15:03Z"
  }
}

409 in an end-to-end encrypted meeting: the servers cannot read the call, so there is nothing to transcribe. 409 when no call is running.

Stop

DELETE/v1/zoreal/meet/instant/:code/host/transcription

Stops the capture; transcription of what was recorded continues and lands in Meeting notes. 404 when nothing is being transcribed.

RESPONSE
{
  "recording": { "id": 118, "status": "processing" }
}

The door

When a room's knock policy is on, which it is by default, someone without a host credential asks to come in and a host answers. Until a host says yes there is nothing for the guest's browser to connect to: no lobby connection, no muted seat in the call.

Knock

POST/v1/zoreal/meet/instant/:code/knock

AuthNone (public)

Asks to join a knocking room. The answer is a knock_token, the handle the guest polls with and a host answers; it is single use and belongs to this one request to enter.

Request body

  • namestringRequired
    The name shown at the door, 1 to 40 characters; control characters are refused.
REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/knock \
  -H "Content-Type: application/json" \
  -d '{ "name": "Maja Ekberg" }'
RESPONSE
{ "knock_token": "<KNOCK_TOKEN>", "status": "pending" }

422 when the room admits anyone with the link: there is no door to knock on.

429 means the door queue is full, not the room; the meeting itself may have space.

Poll the knock

GET/v1/zoreal/meet/instant/:code/knock/:knock_token

AuthNone (the token is the credential)

Reads the state of a knock. The poll is also the heartbeat: a waiting guest holds no connection, so polling is what keeps them visible at the door, and a knock unseen for ten seconds drops off the host's list. Poll every couple of seconds; the allowance is 120 a minute.

Returns

status is one of: pending, still waiting; admitted, join with this token; denied, a host said no; ended, the meeting is over. There is no waiting deadline - a knock ends when a host answers or the meeting does, never because a clock ran out.

REQUEST · CURL
curl https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/knock/<KNOCK_TOKEN>
RESPONSE
{ "status": "admitted" }

An unknown room answers ended with HTTP 200, not denied: saying a host refused someone when the meeting simply finished would be a lie about a person.

An unknown token reads as denied, so the guest gets an instruction rather than a fault.

Withdraw a knock

POST/v1/zoreal/meet/instant/:code/knock/:knock_token/withdraw

AuthNone (the token is the credential)

Takes a knock back, so the guest leaves the host's door instead of lingering on it until the heartbeat lapses.

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/knock/<KNOCK_TOKEN>/withdraw
RESPONSE
{ "withdrawn": true }

Answer the door

POST/v1/zoreal/meet/instant/:code/host/knocks

AuthHost token

Who is waiting right now. This read is a POST deliberately: a GET would put the host credential in a query string, and from there into access logs, proxies and Referer headers.

Request body

  • host_tokenstringOptional
    From the create response. The meeting owner may omit it and authenticate with their API key instead.
REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/knocks \
  -H "Content-Type: application/json" \
  -d '{ "host_token": "<HOST_TOKEN>" }'
RESPONSE
{
  "knocks": [
    {
      "token": "<KNOCK_TOKEN>",
      "name": "Maja Ekberg",
      "at": "2026-09-02T09:12:40Z"
    }
  ]
}

Admit

POST/v1/zoreal/meet/instant/:code/host/admit

Takes host_token and the knock_token to let in. Admission grants the permissions the room's policy would have given them at the door, in one call; the guest's next poll reads admitted and they join with their token.

Deny

POST/v1/zoreal/meet/instant/:code/host/deny

The same body. Denying removes the guest from the door; there is no third state between the corridor and the room. 404 when nobody is waiting under that handle.

RESPONSE
{ "denied": true }

Room settings

What the room permits, set by a host while the meeting runs. The same host credential as Host controls.

Room policy

POST/v1/zoreal/meet/instant/:code/host/policy

AuthHost token

Turns the room's capabilities on and off. Send any subset; what you do not send is left as it is, and the response returns the whole policy. A change binds people already in the room, not only future joiners.

Request body (any subset, all boolean)

  • screen_sharebooleanOptional
    Whether participants may present. Turning it off also frees the stage if a participant holds it; hosts keep presenting.

    Default: true

  • microphonebooleanOptional
    Whether participants may unmute.

    Default: true

  • camerabooleanOptional
    Whether participants may send video.

    Default: true

  • messagesbooleanOptional
    Whether participants may write in the chat.

    Default: true

  • reactionsbooleanOptional
    Whether participants may send reactions.

    Default: true

  • knockbooleanOptional
    Whether joining requires a host to admit. On by default: a new room has a door.

    Default: true

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/policy \
  -H "Content-Type: application/json" \
  -d '{ "host_token": "<HOST_TOKEN>", "screen_share": false }'
RESPONSE
{
  "policy": {
    "screen_share": false,
    "microphone": true,
    "camera": true,
    "messages": true,
    "reactions": true,
    "knock": true
  }
}

Sending an empty body answers 422: there is nothing to change.

Presence rule

POST/v1/zoreal/meet/instant/:code/host/presence

AuthHost token

What a participant must prove before the room treats them as verified, and what someone who has not proved it may still do.

Request body

  • host_tokenstringOptional
    From the create response. The meeting owner may omit it and authenticate with their API key instead.
  • levelstringRequired
    The bar: poh is proof of a live human, poh_kyc adds a verified identity. Turning the rule off is the literal word off, never a null or an omitted field: a field dropped by a bug must not read as "turn the rule off".

    pohpoh_kycoff

  • unproven_accessstringOptional
    What someone who has not satisfied the rule may do in the meantime.

    fullvideo_onlydenied

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/presence \
  -H "Content-Type: application/json" \
  -d '{
    "host_token": "<HOST_TOKEN>",
    "level": "poh",
    "unproven_access": "video_only"
  }'
RESPONSE
{ "presence_on_join": "poh", "unproven_access": "video_only" }

Raising the bar re-checks everyone: a verification that no longer satisfies the new level is dropped, not grandfathered in.

Uniquely among host controls, a media-node hiccup does not fail this request: the rule is already written, and every future join reads it.

Encryption

POST/v1/zoreal/meet/instant/:code/host/encryption

AuthHost token

Turns end-to-end encryption on for a room created without it. One-way, and only while the host is alone in the room: re-keying a populated call would drop everyone's media to renegotiate.

Request body

  • host_tokenstringOptional
    From the create response. The meeting owner may omit it and authenticate with their API key instead.

Returns

rejoin: true means it worked and the host must reconnect: the encryption key arrives only in a fresh join grant.

REQUEST · CURL
curl -X POST https://api.bynn.com/v1/zoreal/meet/instant/kfm-qhtz-pgd/host/encryption \
  -H "Content-Type: application/json" \
  -d '{ "host_token": "<HOST_TOKEN>" }'
RESPONSE
{ "e2ee": true, "rejoin": true }

409 when the room is already encrypted, and 409 when more than one participant is connected; 502 when the node cannot be reached to count.

In an encrypted room the servers cannot read the call, so Transcription is refused.