Skip to content
Sendora Cloud
Create account
Get started — React Native

First 5 minutes with React Native.

This page covers the React-Native–specific gotchas that the generic quickstart doesn't surface — Hermes CSPRNG polyfill, anonymous-first identity, push token receipts, and the loop-closing demo send.

1. Install

Two npm packages — the SDK plus a CSPRNG polyfill that Hermes doesn't ship out of the box.

npm install @sendoracloud/sdk-react-native react-native-get-random-values

react-native-get-random-values is required for both Expo and bare React Native. Sendora refuses to mint anonymous IDs from Math.random — predictable IDs are a security floor regression, not a tradeoff.

2. Wire the CSPRNG polyfill (line 1 of your entry file)

Edit your app's entry file (index.js or index.tsx at the project root) so the polyfill loads before any other import:

// index.tsx — must be the FIRST import
import "react-native-get-random-values";

import { AppRegistry } from "react-native";
import App from "./App";
import { name as appName } from "./app.json";

AppRegistry.registerComponent(appName, () => App);

If you forget this, SendoraCloud.init() throws with a paste-ready remediation block — it won't fail silently. After adding the import, do a full JS bundle reload (not Fast Refresh) so the runtime picks up the new global.

3. Initialise the SDK

Call init() once on app startup. The public key belongs in SENDORA_PUBLIC_KEY (or your env-var of choice — Sendora doesn't require a specific name). Mint one in Dashboard → Settings → API Keys → Create key → Public.

import SendoraCloud from "@sendoracloud/sdk-react-native";

await SendoraCloud.init({
  apiKey: process.env.EXPO_PUBLIC_SENDORA_PUBLIC_KEY!,
});

// Anonymous user is now created. Track immediately.
await SendoraCloud.track("app.opened");

4. Anonymous-first identity

Sendora creates an anonymous user the first time init() runs. Every subsequent track() + identify() attaches to the same user_id until you upgrade.

Critical: when an anonymous user later signs up with email + password, call signUp() on the existing session. Sendora detects the anonymous session via the refresh cookie and upgrades the same user_id in place — your analytics + funnels stay continuous across the anon-to-known boundary.

// Anonymous user — works immediately after init()
await SendoraCloud.track("paywall.shown");
await SendoraCloud.track("paywall.dismissed");

// User decides to sign up. SAME user_id is preserved.
const { user } = await SendoraCloud.auth.signUp({
  email: "alice@example.com",
  password: "correct-horse-battery-staple",
});
// user.id === the anonymous user_id from before. No funnel break.

await SendoraCloud.track("signup.completed");

Calling signUp() on a brand-new install (no anonymous session yet) creates a fresh user. Either way, the SDK reads the refresh-token cookie as the authoritative signal — never falls back to a stale isAnonymous flag.

5. Register a push token

Pair Sendora's registerPushToken() with your push provider (Firebase Messaging on Android, APNs on iOS). The call returns a PushTokenReceipt so you can log a confirmation:

import messaging from "@react-native-firebase/messaging";

const fcmToken = await messaging().getToken();

const receipt = await SendoraCloud.registerPushToken({
  token: fcmToken,
  platform: Platform.OS === "ios" ? "ios" : "android",
  bundleId: "com.yourapp.production",
  // bundleId is optional but strongly recommended for multi-env apps
  // so dev / staging tokens never get a prod APNs / FCM push.
});

console.log("Sendora token id:", receipt.tokenId, "new?", receipt.created);

6. Send a test push (close the loop)

Tokens registered? Confirm end-to-end by sending one to your own device from the dashboard or directly via the API:

curl -X POST https://api.sendoracloud.com/api/v1/orgs/$ORG_ID/push/send \
  -H "x-api-key: $SENDORA_SECRET_KEY" \
  -d '{
    "userIds": ["<the user_id you signed up above>"],
    "title": "Hello from Sendora",
    "body": "Push works ✅",
    "data": { "kind": "test" }
  }'

From the dashboard: Messaging → Push → Send. The recipient picker accepts a single user id for one-off testing without setting up an audience.

Env-var naming

Sendora's SDKs accept any string in apiKey, but the canonical convention across docs + examples is:

  • SENDORA_PUBLIC_KEY — public key (pk_…), ships in browser / mobile bundles. Safe to commit to a public repo only when project-scoped.
  • SENDORA_SECRET_KEY — secret key (sk_…), server-side only. Never include in any client bundle.
  • In Next.js, the browser-side public key needs the NEXT_PUBLIC_ prefix: NEXT_PUBLIC_SENDORA_PUBLIC_KEY.
  • Older docs referenced NEXT_PUBLIC_SENDORA_KEY / SENDORA_API_KEY. Both still work — the SDK only cares about the value, not the env-var name — but new code should use the canonical names above.

SDK stability commitment

@sendoracloud/sdk-react-native is currently on the 0.10.x line. Pre-1.0 minor bumps may include breaking changes; patch bumps (0.10.x → 0.10.y) are backwards-compatible. The next major (1.0) is targeted once the HttpOnly-cookie SSR auth + auto-trait extraction features have soaked in production for two consecutive months without a schema-shape change. Once 1.0 ships, semver is strict — no breaking changes outside major bumps.

Next steps