# Bare React Native Recipe

Register a bare React Native app's APNs and FCM tokens with Native Notify universal push — using react-native-firebase/messaging or the APNs delegate.

A bare React Native app (no Expo modules) usually already has Firebase wired in for Android and an APNs delegate for iOS. Both tokens register with the same endpoint.

## Tokens

**Android — FCM token** (`@react-native-firebase/messaging`):

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

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

**iOS — APNs token:**

```js
const apnsToken = await messaging().getAPNSToken(); // hex string, null until APNs registers
```

`getAPNSToken()` resolves only after APNs has delivered the token — subscribe to `messaging().onTokenRefresh()` and register again whenever either token changes.

No Firebase on iOS? Keep using the APNs delegate directly: `application(_:didRegisterForRemoteNotificationsWithDeviceToken:)` gives you the hex token (see the [Swift recipe](/docs/universal-push/recipes/swift) for the delegate details).

## Register

```js
import { Platform } from "react-native";

export async function registerUniversalDevice({ appId, appToken, subscriberId, deviceId }) {
  const tokens =
    Platform.OS === "ios"
      ? { apnsToken: await messaging().getAPNSToken() }
      : { fcmToken: await messaging().getToken() };

  const res = await fetch("https://app.nativenotify.com/api/universal/device/register", {
    method: "POST",
    headers: { "Content-Type": "application/json" },
    body: JSON.stringify({
      appId,
      appToken,
      deviceId,      // persisted per install — see Device Registration
      platform: Platform.OS,
      subscriberId,  // omit for a mass device
      tokens,
    }),
  });
  return res.json();
}
```

Call it on launch and from both token-refresh listeners. Re-registering is an upsert: same device, refreshed token.

## Required project setup

- **Android:** the app's `google-services.json` (the Firebase project whose service account is saved as the app's credentials in Native Notify).
- **iOS:** APNs capability + push entitlement, an `aps-environment` profile that matches the build, and the app's `.p8` key saved in Native Notify — Apple sends to the bundle id, so the credential's bundle id must match.
- Notification permission must be granted before any token arrives.

## Next steps

- [Device Registration](/docs/universal-push/registration) and [Push Credentials](/docs/universal-push/credentials).
- [Verify Delivery](/docs/universal-push/verification) — test-send to the device you just registered.
- Want to skip the native wiring? The `native-notify` SDK works in bare React Native too — it adds Expo modules for the push token plumbing (see [Installation](/docs/setup/installation)).
