Skip to content
Back to skills

Pushengage React Native

ASecurity

Use ONLY when the active repo is a React Native app (`package.json` with `react-native` dep, typically alongside `ios/` and `android/` folders, Turbo Modules / New Architecture). Handles full PushEngage integration end-to-end (JS init + Android native config + iOS native config + NSE) plus debugging existing integrations. Do not use for native iOS, native Android, or Flutter apps even if PushEngage is mentioned.

  • 3 stars
  • 0 votes
  • 0 copies
  • 3 views
  • Added September 30, 2026
developmentgoswiftc++shellreactdebuggingapidocumentation

Works with

  • claude code
  • cli
  • api

Security analysis

A92/100
  • mediumInstalls packages at runtime which could introduce malicious dependencies

Pro scans all 13 files and shows the line behind each finding

Scanned September 30, 2026

npx -y skills add awesomemotive/pushengage-skills --skill pushengage-react-native --agent claude-code

Installs into .claude/skills of the current project.

Are you the author of Pushengage React Native?

Add the live security badge to your README. It updates with every re-scan.

Security grade badge for Pushengage React Native
[![Security: A — Skills Directory](https://www.skillsdirectory.com/api/skills/awesomemotive-pushengage-react-native/badge)](https://www.skillsdirectory.com/skills/awesomemotive-pushengage-react-native)

More formats (shields.io, HTML) on the badges page. Keep it an A: scan every change in CI with Pro.

Download with Pro
SKILL.md
---
name: pushengage-react-native
description: Use ONLY when the active repo is a React Native app (`package.json` with `react-native` dep, typically alongside `ios/` and `android/` folders, Turbo Modules / New Architecture). Handles full PushEngage integration end-to-end (JS init + Android native config + iOS native config + NSE) plus debugging existing integrations. Do not use for native iOS, native Android, or Flutter apps even if PushEngage is mentioned.
license: MIT
compatibility: Works with any agent that supports the Agent Skills (SKILL.md) standard, including Claude Code and Cowork. Needs filesystem read access and a shell to detect the project type; some steps fetch allowlisted documentation URLs.
metadata:
  author: PushEngage
  version: "1.0.0"
---

# PushEngage — React Native Spoke

You're working in a React Native app. This skill walks the customer through integrating PushEngage from zero to verified test push, or debugs a broken integration.

> **Trigger gating.** This spoke fires only when `package.json` has `react-native` (or `expo`) as a dependency. The presence of `ios/Podfile` or `android/build.gradle` alone (without `package.json`) does NOT route here — that's the native iOS or Android spoke. The presence of `pubspec.yaml` routes to Flutter, not here. The hub's detection logic puts both Flutter and React Native AHEAD of native iOS/Android checks because RN/Flutter projects also contain `ios/` and `android/` folders.

## Routing

| Customer intent | Read this file next |
|---|---|
| "Integrate PushEngage" / "Set up PushEngage" (greenfield or partial) | This file's "Integration flow" section below. |
| "PushEngage isn't working" / specific symptom | Run static audit (`audit-checks.md`) first, then escalate to `../pushengage-debug/SKILL.md` for Phase 2/3 (skill: `pushengage-debug`). |
| "Audit my PushEngage setup" | Read `audit-checks.md` and run the checks. |
| Concept / terminology question | Read `../pushengage/concepts.md`. |
| Best practices / rule lookup | Read `best-practices.md` (RN-specific) or `../pushengage/best-practices.md` (cross-platform). |
| API surface / "does method X exist" | Read `version-matrix.md` first; if not listed, fetch only URLs from `references.md`. |

## Integration flow (greenfield)

Five parts in order. Earlier artifacts feed later steps.

### Part 1 — Discovery & prereqs

Before touching anything, gather:

1. **Target platforms** — does the customer ship to both stores, or just one? Look for `ios/` and `android/` folders.
2. **React Native version** — read from `package.json`'s `dependencies."react-native"`. **Critical compatibility check:**
   - RN `>= 0.78` → install latest SDK (`^1.0.0`).
   - RN `< 0.78` → upgrade RN to 0.78+ (required — no supported SDK build for older RN; the Turbo Modules API requires it). See `version-matrix.md`.
3. **Existing SDK pin** — does `package.json` already have `@pushengage/pushengage-react-native`? If so, what version?
4. **`applicationId` (Android)** — read from `android/app/build.gradle`'s `defaultConfig.applicationId`.
5. **iOS Bundle Identifier** — confirm from Xcode (Signing & Capabilities → Bundle Identifier on the main target).
6. **PushEngage account state** — ask:
   - Have you already created PushEngage sites for this app? (One per platform.)
   - Do you have a Firebase project (Android)?
   - Do you have an Apple Developer account with Push Notifications enabled (iOS)?
7. **Expo vs Bare:** if `package.json` has `expo` as a dep, flag: **Expo Go does not support custom native modules.** Customer must use Expo Dev Client (`expo-dev-client`) and run `expo prebuild` once to expose `ios/` and `android/`.

Output a one-paragraph integration plan in chat. Wait for the customer to confirm before any edits.

### Part 2 — Provider setup (out-of-code, before any code edits)

Do these BEFORE editing code. The dashboard's App ID UUIDs are needed for `setAppId(...)`; Firebase + APNs have real-world setup steps that block code progress.

- **Android target → `firebase-setup.md`.** Defers to `../pushengage-android/firebase-setup.md` for the click-path. Captures Sender ID, Service Account JSON, `google-services.json`, `applicationId`.
- **iOS target → `apns-setup.md`.** Defers to `../pushengage-ios/provider-setup.md` for the click-path. Captures `.p12`, password, Bundle Identifier.

### Part 3 — Dashboard setup

Read `dashboard-setup.md`. A cross-platform RN app needs TWO PushEngage sites (one Android, one iOS) — each generates its own App ID UUID. Capture BOTH UUIDs and confirm them back to the customer.

### Part 4 — In-code edits

#### 4a — Install + native config

Read `install.md`. Apply:

- `package.json` — install via `npm install @pushengage/pushengage-react-native` (or yarn). **If RN < 0.78, upgrade RN to 0.78+ first — no supported SDK build for older RN.**
- Android: `android/gradle.properties` (`newArchEnabled=true`), `android/build.gradle` (google-services classpath + jitpack repo), `android/app/build.gradle` (**MUST `apply plugin: "com.google.gms.google-services"`** in the app module — the buildscript classpath alone is not enough), `AndroidManifest.xml` (`POST_NOTIFICATIONS`), `google-services.json` placement.
- iOS: `ios/Podfile` (`ENV['RCT_NEW_ARCH_ENABLED'] = '1'`, NSE/NCE target blocks with `pod 'PushEngageExtension', '1.0.0'` — the 1.0.0 two-pod split, no `APPLICATION_EXTENSION_API_ONLY` override needed), `Info.plist` (`PushEngage_App_Group_Key`, background modes), `cd ios && pod install`.

**Auto-edit + announce posture** for config files. Show the diff, then apply.

#### 4b — JS + ObjC init code

Read `init-code.md`. Apply:

- `index.js` / `index.tsx` — import from `@pushengage/pushengage-react-native` (NOT `pushengage-react-native`), `PushEngage.setAppId(...)` with `Platform.OS === 'ios' ? ... : ...` BEFORE `AppRegistry.registerComponent`, `if (__DEV__) PushEngage.enableLogging(true);`.
- iOS AppDelegate — swizzling enabled in the delegate's `init`, `setInitialInfo` in `didFinishLaunchingWithOptions` before React Native boots. RN ≥ 0.77 templates generate `AppDelegate.swift` (use the Swift deltas in `init-code.md` Section 2); upgraded apps may still have `AppDelegate.mm` (use the ObjC++ template).
- `onValueChanged` listener in root component's `useEffect` with `() => subscription.remove()` cleanup.
- Register `getInitialNotification()` alongside `onValueChanged` in the root effect for iOS cold-boot tap recovery (RN-BP-13). New in 1.0.0; resolves `null` on Android.
- **No Android `MainApplication.kt` PushEngage init needed** — RN plugin handles native init.

**Diff + confirm posture** for `index.js`, the AppDelegate (`.swift` or `.mm`), and the root `App.tsx` (when adding the listener).

Insert the App ID UUID(s) captured in Part 3.

#### 4c — Runtime permission flow

Read `permission-flow.md`. Set up `requestNotificationPermission()` behind a user action (button, end-of-onboarding) — NOT in `index.js` or root `useEffect`. SDK auto-calls `subscribe()` on grant; don't double-call.

For Android: confirm `POST_NOTIFICATIONS` is in Manifest (Step 4a).

#### 4d — NSE setup (iOS, required for rich notifications)

If iOS target: read `nse-setup.md`. Walk through Xcode NSE target creation, deployment target iOS 15.1, Podfile target block with `pod 'PushEngageExtension', '1.0.0'` (the extension-safe pod from the 1.0.0 two-pod split, NOT `pod 'PushEngage', '~>0.0.5'`), App Groups capability on BOTH main and NSE targets, matching `PushEngage_App_Group_Key`.

**Skip entirely if Android-only.**

#### 4e — NCE setup (optional)

Default: SKIP. Read `nce-setup.md` if customer asks for custom in-notification UI.

### Part 5 — Verification

Per target platform:

1. Real device:
   - **Android:** must have Google Play Services. NOT a Play-Services-less emulator.
   - **iOS:** must be a physical device. APNs does NOT work on simulator.
2. Install + run + trigger permission request → grant.
3. PushEngage dashboard → corresponding site → Push Broadcasts → send test → confirm arrival.

If verification fails: run static audit (`audit-checks.md`), then escalate to `pushengage-debug/SKILL.md`.

### Part 6 — Post-integration best-practices nudge

Short message. Pick 2–3 rules applicable to what you integrated:

- XP-BP-01 — move App ID UUID(s) out of source (`react-native-config`, `--env`).
- RN-BP-04 — defer `requestNotificationPermission()` to a meaningful moment.
- RN-BP-05 — wrap `enableLogging(true)` in `__DEV__`.
- RN-BP-02 — confirm `onValueChanged` is in the root component's `useEffect`, won't drift to a downstream screen during future refactors.
- RN-BP-13 — register `getInitialNotification()` alongside `onValueChanged` for iOS cold-boot tap recovery.
- ANDROID-BP-13 (if Android target) — document OEM battery optimization in customer's FAQ.

## Debugging entry points

Escalate to `pushengage-debug/SKILL.md` when:

- "Module 'pushengage-react-native' could not be resolved" → RN-AUDIT-01 / KI-RN001 (stale import name).
- "iOS build fails with 'Application extensions cannot use PushEngage'" → RN-AUDIT-03 (extension target links `pod 'PushEngage'` instead of `pod 'PushEngageExtension', '1.0.0'`). The old `APPLICATION_EXTENSION_API_ONLY` override / KI-RN002 path is obsolete in 1.0.0 (two-pod split).
- "iOS build fails with '@import' / c++ modules disabled" → KI-RN008. Note: the `CLANG_ALLOW_NON_MODULAR_INCLUDES_IN_FRAMEWORK_MODULES` override this depended on is obsolete in 1.0.0 (two-pod split); the app target's `@import PushEngage` resolves without it.
- "Rich-push image doesn't load" → RN-AUDIT-03 (stale pod pin) and RN-AUDIT-09 (App Groups).
- "Cold-boot deep link is lost" → RN-AUDIT-12 (listener registered too late) / RN-AUDIT-17 (missing `getInitialNotification`) / KI-RN003. 1.0.0 provides the `getInitialNotification()` recovery API for iOS.
- "Works on Android but not iOS" (or vice versa) → RN-AUDIT-07 / KI-RN006.
- "Permission dialog never shows on Android" → RN-AUDIT-05 / KI-RN004.
- "Android push never arrives, FCM token never registers" → RN-AUDIT-15 / KI-RN010 (missing google-services plugin apply).
- "iOS build crashes with Turbo Module error after `npm install`" → RN-AUDIT-14 / KI-RN009 (RN/SDK version mismatch).

## Edit posture per file class

- **Auto-edit + announce:** `package.json`, `ios/Podfile`, `android/build.gradle`, `android/settings.gradle`, `android/app/build.gradle`, `android/gradle.properties`, `AndroidManifest.xml`, `Info.plist`, NSE `Info.plist`, `google-services.json` placement.
- **Diff + confirm:** `index.js` / `index.tsx`, `ios/<App>/AppDelegate.mm`, root `App.tsx` (when adding listener). Entry-point code.
- **Customer-driven (you instruct):** Xcode UI — NSE/NCE target creation, App Groups capability, Push Notifications + Background Modes capabilities. Don't `.pbxproj`-edit.
- **Never touch:** anything outside integration scope. No formatting passes, no RN version bumps, no Gradle bumps beyond required.

## Where the RN spoke borrows from other spokes

The RN spoke references content files from the iOS and Android spokes to avoid duplication. **By file path only** — you read the referenced content file but does NOT load the other spoke's `SKILL.md`.

| What | Where |
|---|---|
| Firebase Console click-path | `../pushengage-android/firebase-setup.md` |
| Apple Developer + Keychain click-path | `../pushengage-ios/provider-setup.md` |
| Long-form NCE template + category consistency rules | `../pushengage-ios/nce-setup.md` |
| Manual (non-swizzling) iOS forwards template | `../pushengage-ios/init-code.md` |

**Never** read the other spokes' `SKILL.md`s. Only their content files.

## What you must not do

- **Don't import from `'pushengage-react-native'`** (missing scope). Always `'@pushengage/pushengage-react-native'`. RN-AUDIT-01.
- **Don't invent PushEngage method names.** Check `version-matrix.md`. If unsure, fetch an allowlisted URL from `references.md`. If still unsure, say so.
- **Use `version-matrix.md` as the source of truth for the package name and pod pins** — scoped import, and `PushEngageExtension 1.0.0` for NSE/NCE targets.
- **Don't copy the SDK's example app verbatim.** It has two known gaps: missing `POST_NOTIFICATIONS` in Manifest, unconditional `enableLogging(true)`. (It DOES apply `com.google.gms.google-services` — that step is still required in customer apps.) The skill's `install.md` and `init-code.md` cover the correct patterns.
- **Don't auto-edit `index.js` or `AppDelegate.mm` without showing the diff and getting confirmation.** Entry-point code is diff + confirm.
- **Don't touch files outside integration scope.**
- **Don't fetch URLs not in `references.md`.**
- **Don't ask the customer for Service Account JSON or `.p12` contents in chat.** Both are secrets — they upload directly to the dashboard.
- **Don't add `pod 'PushEngage'` to the main app target in Podfile.** Pulled transitively. NSE / NCE target blocks get `pod 'PushEngageExtension', '1.0.0'` (the extension-safe pod from the 1.0.0 two-pod split), not `pod 'PushEngage'`. RN-BP-06.
- **Don't add a `MainApplication.kt` PushEngage init block** — the plugin handles it.
- **Don't follow the SDK example app's unconditional `enableLogging(true)` pattern** — gate behind `__DEV__`.

Files in this skill

  • SKILL.md13 KB
  • apns-setup.md2.2 KB
  • audit-checks.md13.3 KB
  • best-practices.md10 KB
  • dashboard-setup.md2.5 KB
  • firebase-setup.md3.8 KB
  • init-code.md10.2 KB
  • install.md9.4 KB
  • nce-setup.md3.1 KB
  • nse-setup.md5.6 KB
  • permission-flow.md5.4 KB
  • references.md2.4 KB
  • version-matrix.md15.4 KB

Attribution

Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.

Comments

Loading comments…

Newsletter

Get the weekly list of safe new skills, and the ones we pulled.