SDKs

Three official clients, one mental model: same method names, same batching, same error families, same replay guarantees — each written in the naming conventions of its language. None of them has a runtime package dependency — the PHP client only needs the curl and json extensions.

Official libraries

Node.js

@sinio/sdk — Node 18+, no runtime dependency, ESM and CommonJS, typed end to end.

Read more

Python

sinio — Python 3.10+, standard library only, clean under mypy --strict.

Read more

PHP

sinio/sinio-php — PHP 8.1+, ext-curl and ext-json only, PHPStan level 8 clean.

Read more

What they do for you

  • Name
    Chunking
    Type
    automatic
    Description

    Pass 50 000 events; the client issues calls of 500 — the API limit — and merges the counters and rejections into a single result.

  • Name
    Retries
    Type
    automatic
    Description

    429, 5xx and dropped connections are retried with exponential backoff and full jitter, honouring Retry-After. Safe by construction: ingestion is idempotent, so a replay is counted in duplicates.

  • Name
    Local validation
    Type
    before the call
    Description

    A timestamp without a UTC offset is refused locally, before any call, instead of coming back as an invalid_occurred_at rejection.

  • Name
    Typed errors
    Type
    per failure family
    Description

    Auth, request, rate limit, server, connection and validation errors are distinct types, so "fix this" and "retry this" never look alike.

Installing

npm install @sinio/sdk

Creating a client

Client

import { SinioClient } from '@sinio/sdk'

const sinio = new SinioClient({
  apiKey: process.env.SINIO_API_KEY,
  baseUrl: 'https://api.sinio.ai',
})

The key names the project and the source: nothing else is needed to start sending.

The surface

EndpointMethod
POST /v1/eventssendEvents / backfillEvents
POST /v1/webhooks/{key}sendEvents / backfillEvents, in webhook-key mode
POST /v1/entitiesupsertEntities
POST /v1/locationsupsertLocations
POST /v1/assignmentscreateAssignments

Python and PHP use their own conventions — send_events, upsert_entities in Python; the same camelCase as Node in PHP.

Webhook-key mode

For a system that can only be pointed at a URL:

const sinio = new SinioClient({ webhookKey: process.env.SINIO_WEBHOOK_KEY })

await sinio.sendEvents(events) // POST /v1/webhooks/<key>

In this mode only event ingestion is available — live or backfill, the webhook URL honours mode like POST /v1/events. The reference endpoints require an API key, and calling one raises immediately rather than failing over the network.

Handling the result

Always read rejections. A 200 confirms reception, not derivation, and valid events are accepted even when others in the batch are not.

Result

const result = await sinio.sendEvents(events)

console.log(result.accepted, result.duplicates, result.revisions)
for (const rejection of result.rejections) {
  console.warn(rejection.sourceEventId, rejection.code, rejection.message)
}

Because a large batch is split across several HTTP calls, the result carries batchIds (batch_ids in Python) — one server-side id per call the client made.

Was this page helpful?