Skip to main content

Qriib Meet — Python integration guide

qriib-meet is the Python package a backend uses to create and manage Qriib rooms, then hand the returned meeting link to the client application that opens the embedded Qriib meeting.

from qriib_meet import QriibMeetClient

It is the server-side counterpart of the qriib_meet Flutter package. Every resource, method, model, and error keeps the same name in snake_case, so a team that knows one SDK can read the other.

Before you start

qriib-meet runs on Python 3.10 or newer. The API client signs management requests with Qriib credentials, while a meeting is opened on a device with the fresh final_link returned by the Qriib API.

A Python process has no camera, microphone, or screen, so the embedded meeting UI is not part of this package. Create rooms here, then pass the final_link to your Flutter app, which opens it with client.meetings.join.

For a production service, do not hard-code organization or project secret keys in source control. Keep them in a secrets manager or environment configuration, and never log a final_link.

Installation

pip install qriib-meet

Import only the public package entry point:

from qriib_meet import QriibMeetClient

Five-minute integration

  1. Create one QriibMeetClient when your service starts.
  2. Call a room API such as create_quick_video_room or join_room.
  3. Read the server-returned final_link and return it to your client app.
  4. The Flutter qriib_meet package opens the full-screen meeting from it.
from qriib_meet import (
    QriibApiException,
    QriibMeetClient,
    QriibMeetException,
    QriibRoomMetadata,
)

qriib = QriibMeetClient.with_project_credentials(
    api_key="YOUR_PROJECT_API_KEY",
    secret_key="YOUR_PROJECT_SECRET_KEY",
    base_url="https://api.qriib.dev",
    enable_network_logging=False,
)


def start_call(ticket_id: str) -> dict[str, str | None]:
    try:
        response = qriib.rooms.create_quick_video_room(
            project_id="YOUR_PROJECT_ID",
            client_room_id=f"support-call-{ticket_id}",
            metadata=QriibRoomMetadata(room_title="Support call"),
        )
        final_link = qriib.meetings.link_from_response(response)
        return {"room_id": response.get("room_id"), "final_link": final_link}
    except QriibMeetException as error:
        raise RuntimeError(error.message) from error
    except QriibApiException as error:
        raise RuntimeError(error.message) from error

client_room_id must be unique in the selected project. Use an ID from your backend domain, for example an order, appointment, or support-ticket ID, or generate one with new_client_room_id().

What it provides

  • QriibMeetClient — API client that can use project and organization credentials (also aliased as QriibClient and VCloudClient).
  • client.rooms — create, schedule, start, join, inspect, and end rooms.
  • client.meetings — validates the server-issued final_link that the client application opens.
  • client.branding — upload and update project branding logos and icons.
  • client.analytics, client.projects, and client.recordings — management and reporting endpoints.

Credentials and resource access

The client automatically signs the appropriate requests. You do not create your own HTTP client, headers, key, or hash-signature values.

Resource Required credentials Main use
client.rooms Project Create, join, schedule, inspect, and end rooms
client.meetings None; validates a fresh server final_link Hand the meeting link to the client app
client.branding Project Create and update project branding assets
client.analytics Project Read room analytics
client.recordings Project Read recording data and links
client.projects Organization Create and manage projects

Use with_project_credentials for room-only services. Use with_credentials when the same service also calls organization/project-management operations.

Create the client once

Create one client for the selected Qriib project and close it with the service or dependency container that owns it. The client is also a context manager.

from qriib_meet import QriibMeetClient

qriib = QriibMeetClient.with_project_credentials(
    api_key="YOUR_PROJECT_API_KEY",
    secret_key="YOUR_PROJECT_SECRET_KEY",
    base_url="https://api.qriib.dev",
    enable_network_logging=True,
    timeout=30.0,
)

# ... later, on shutdown
qriib.close()

# or
with QriibMeetClient.with_project_credentials(api_key="...", secret_key="...") as qriib:
    ...

enable_network_logging emits request/response summaries on the qriib_meet logger at INFO level. Disable it in production. Never hard-code or log project credentials, final_link values, or decoded meeting tokens.

Create a quick video room and return its link

Quick rooms return a final_link. Pass that complete string unchanged to the client application; do not decode the token yourself.

from qriib_meet import QriibRoomMetadata, new_client_room_id

response = qriib.rooms.create_quick_video_room(
    project_id="YOUR_PROJECT_ID",
    client_room_id=new_client_room_id(),  # Unique inside the project.
    name="Support call",
    moderator_id="moderator-42",
    max_participants=20,
    empty_timeout=1_000,
    metadata=QriibRoomMetadata(
        room_title="Support call",
        welcome_message="Welcome to the call",
        room_duration=60,
    ),
)

final_link = qriib.meetings.link_from_response(response)
room_id = response.get("room_id")

Use create_quick_audio_room in the same way for an immediate audio room.

Join an existing room

join_room returns the participant-specific final_link used to open the meeting. The role is sent as user_metadata.role.

from qriib_meet import QriibUserInfo

response = qriib.rooms.join_room(
    room_id="ROOM_ID",
    user_info=QriibUserInfo(
        name="Karim",
        role="attendee",
        is_admin=False,
        is_hidden=False,
    ),
)

final_link = qriib.meetings.link_from_response(response)

Scheduled rooms

Creating a scheduled room is not the same as starting a meeting:

create scheduled room -> room_id
start scheduled room -> final_link
open Qriib meeting -> client app opens final_link

Create the schedule and store the returned room_id in your own backend:

scheduled = qriib.rooms.create_scheduled_video_room(
    project_id="YOUR_PROJECT_ID",
    client_room_id="order-123-scheduled-video",
    start_at="2026-12-31T18:30",  # Local ISO-8601 minute precision.
    max_participants=20,
    empty_timeout=1_000,
    metadata=QriibRoomMetadata(room_title="Scheduled review"),
)

room_id = scheduled["room_id"]

When the room is started, return its meeting link:

started = qriib.rooms.start_scheduled_room(room_id, name="Scheduled review")
final_link = qriib.meetings.link_from_response(started)

Use create_scheduled_audio_room for scheduled audio rooms. If the server does not return final_link from start_scheduled_room, call join_room with the started room_id and use the link from that join response.

Other room operations

client.rooms currently provides these methods:

Category Methods
Create create_quick_audio_room, create_quick_video_room, create_scheduled_audio_room, create_scheduled_video_room
Enter/share join_room, create_invitation_link
Scheduled start_scheduled_room
Inspect get_room_status, get_active_room_info, get_active_rooms_info, fetch_past_rooms
End end_room

All resource methods return dict[str, Any]. This deliberately preserves the server response while API response schemas remain flexible. Read only the fields your integration needs, such as room_id and final_link.

fetch_past_rooms takes from_ for the API's from field because from is a Python keyword.

Analytics, projects, and recordings

client.analytics.get_analytics(room_id=...) and all client.recordings methods require project credentials. Project management methods require organization credentials, so initialize the client with both scopes when your service uses all resources:

from qriib_meet import (
    QriibMeetClient,
    QriibOrganizationCredentials,
    QriibProjectCredentials,
)

qriib = QriibMeetClient.with_credentials(
    organization=QriibOrganizationCredentials(
        api_key="YOUR_ORGANIZATION_API_KEY",
        secret_key="YOUR_ORGANIZATION_SECRET_KEY",
    ),
    project=QriibProjectCredentials(
        api_key="YOUR_PROJECT_API_KEY",
        secret_key="YOUR_PROJECT_SECRET_KEY",
    ),
)

analytics = qriib.analytics.get_analytics(room_id="ROOM_ID")
recordings = qriib.recordings.get_records(project_id="PROJECT_ID")
project = qriib.projects.get_project(project_id="PROJECT_ID")

Update a project by supplying at least one documented field. Nested settings are passed as JSON-shaped collections because their inner schema is API-owned:

qriib.projects.update_project(
    project_id="PROJECT_ID",
    default_project=True,
    webhook_url="https://example.com/qriib-webhook",
    room_features=[{"chat": True}],
    default_lock_settings={"locked": True},
)

Change a project's status with QriibProjectStatus:

from qriib_meet import QriibProjectStatus

qriib.projects.update_project_status(
    project_id="PROJECT_ID",
    status=QriibProjectStatus.inactive,
)

Meeting behavior

client.meetings cannot open a meeting from a Python process. It offers:

Method Use
validate_final_link(final_link) Returns the trimmed link, or raises QriibMeetException when it has no meeting token.
link_from_response(response) Reads final_link from a room response, direct or inside a data envelope, and validates it.

Return the complete fresh final_link to the participant's device. Never send only a decoded token, a room ID, or an invitation URL to the client's meetings.join: it requires the complete link returned by the server for that participant.

Errors

Handle SDK errors at the call site and show only safe messages to the user:

try:
    final_link = start_call("123")
except QriibMeetException as error:
    show_message(error.message)
except QriibApiException as error:
    show_message(error.message)

QriibMeetException covers local validation, including a missing or malformed meeting link. QriibSessionException and QriibNetworkException are meeting-specific subclasses kept for parity with the Flutter package. QriibApiException represents a failed API request and includes the server response and HTTP status for application-level error handling. Typed subclasses map common statuses:

Status Exception
400, 422 QriibValidationException
401, 403 QriibAuthenticationException
404 QriibNotFoundException
429 QriibRateLimitException
other QriibApiException

For API errors, prefer error.message; it contains a meaningful server message when one is available, for example Client room ID already exists. Do not show or log raw request credentials or meeting links.

Development

pip install -e ".[dev]"
pytest
ruff check .
mypy src

Release files for qriib-meet 1.1.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for qriib-meet 1.1.0
File Size Uploaded
qriib_meet-1.1.0.tar.gz 22.8 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for qriib-meet 1.1.0
File Interpreter ABI Platform
qriib_meet-1.1.0-py3-none-any.whl Python 3 none any Details

Total release size: 47.6 kB

Release files / qriib_meet-1.1.0.tar.gz

Download URL qriib_meet-1.1.0.tar.gz
Size 22.8 kB
Tags Source
SHA-256 checksum
How to use checksums
7821cc5ce9145917eade1eb6ee36534c3d5132ab4a5820455162c2ffca5a7baa
BLAKE2b-256 checksum
How to use checksums
363a01eb80dcf25584bf3843e99256b7ef9223ea42e53725e50e73e45345b263
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.12.1 {"installer":{"name":"uv","version":"0.12.1","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Release files / qriib_meet-1.1.0-py3-none-any.whl

Download URL qriib_meet-1.1.0-py3-none-any.whl
Size 24.8 kB
Tags Python 3
SHA-256 checksum
How to use checksums
f62f3241e8d371c8989741aa5a33350991fd789716d88443b2de389efc1fb2c8
BLAKE2b-256 checksum
How to use checksums
3db7f8163ccc0875eea0d8e733d91ffaf8061f5e2adafb37527aa3d12aea5186
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.12.1 {"installer":{"name":"uv","version":"0.12.1","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Release history Release notifications | RSS feed

This release

1.1.0 This release

2 release files

1.0.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page