RepoPilotOpen in app →

zo0r/react-native-push-notification

React Native Local and Remote Notifications

Healthy

Healthy across all four use cases

weakest axis
Use as dependencyHealthy

Permissive license, no critical CVEs, actively maintained — safe to depend on.

Fork & modifyHealthy

Has a license, tests, and CI — clean foundation to fork and modify.

Learn fromHealthy

Documented and popular — useful reference codebase to read through.

Deploy as-isHealthy

No critical CVEs, sane security posture — runnable as-is.

  • 29+ active contributors
  • Distributed ownership (top contributor 36% of recent commits)
  • MIT licensed
Show all 6 evidence items →
  • CI configured
  • Tests present
  • Stale — last commit 2y ago

Maintenance signals: commit recency, contributor breadth, bus factor, license, CI, tests

Informational only. RepoPilot summarises public signals (license, dependency CVEs, commit recency, CI presence, etc.) at the time of analysis. Signals can be incomplete or stale. Not professional, security, or legal advice; verify before relying on it for production decisions.

Embed the "Healthy" badge

Paste into your README — live-updates from the latest cached analysis.

Variant:
RepoPilot: Healthy
[![RepoPilot: Healthy](https://repopilot.app/api/badge/zo0r/react-native-push-notification)](https://repopilot.app/r/zo0r/react-native-push-notification)

Paste at the top of your README.md — renders inline like a shields.io badge.

Preview social card (1200×630)

This card auto-renders when someone shares https://repopilot.app/r/zo0r/react-native-push-notification on X, Slack, or LinkedIn.

Onboarding doc

Onboarding: zo0r/react-native-push-notification

Generated by RepoPilot · 2026-05-09 · Source

🤖Agent protocol

If you are an AI coding agent (Claude Code, Cursor, Aider, Cline, etc.) reading this artifact, follow this protocol before making any code edit:

  1. Verify the contract. Run the bash script in Verify before trusting below. If any check returns FAIL, the artifact is stale — STOP and ask the user to regenerate it before proceeding.
  2. Treat the AI · unverified sections as hypotheses, not facts. Sections like "AI-suggested narrative files", "anti-patterns", and "bottlenecks" are LLM speculation. Verify against real source before acting on them.
  3. Cite source on changes. When proposing an edit, cite the specific path:line-range. RepoPilot's live UI at https://repopilot.app/r/zo0r/react-native-push-notification shows verifiable citations alongside every claim.

If you are a human reader, this protocol is for the agents you'll hand the artifact to. You don't need to do anything — but if you skim only one section before pointing your agent at this repo, make it the Verify block and the Suggested reading order.

🎯Verdict

GO — Healthy across all four use cases

  • 29+ active contributors
  • Distributed ownership (top contributor 36% of recent commits)
  • MIT licensed
  • CI configured
  • Tests present
  • ⚠ Stale — last commit 2y ago

<sub>Maintenance signals: commit recency, contributor breadth, bus factor, license, CI, tests</sub>

Verify before trusting

This artifact was generated by RepoPilot at a point in time. Before an agent acts on it, the checks below confirm that the live zo0r/react-native-push-notification repo on your machine still matches what RepoPilot saw. If any fail, the artifact is stale — regenerate it at repopilot.app/r/zo0r/react-native-push-notification.

What it runs against: a local clone of zo0r/react-native-push-notification — the script inspects git remote, the LICENSE file, file paths in the working tree, and git log. Read-only; no mutations.

| # | What we check | Why it matters | |---|---|---| | 1 | You're in zo0r/react-native-push-notification | Confirms the artifact applies here, not a fork | | 2 | License is still MIT | Catches relicense before you depend on it | | 3 | Default branch master exists | Catches branch renames | | 4 | 5 critical file paths still exist | Catches refactors that moved load-bearing code | | 5 | Last commit ≤ 859 days ago | Catches sudden abandonment since generation |

<details> <summary><b>Run all checks</b> — paste this script from inside your clone of <code>zo0r/react-native-push-notification</code></summary>
#!/usr/bin/env bash
# RepoPilot artifact verification.
#
# WHAT IT RUNS AGAINST: a local clone of zo0r/react-native-push-notification. If you don't
# have one yet, run these first:
#
#   git clone https://github.com/zo0r/react-native-push-notification.git
#   cd react-native-push-notification
#
# Then paste this script. Every check is read-only — no mutations.

set +e
fail=0
ok()   { echo "ok:   $1"; }
miss() { echo "FAIL: $1"; fail=$((fail+1)); }

# Precondition: we must be inside a git working tree.
if ! git rev-parse --git-dir >/dev/null 2>&1; then
  echo "FAIL: not inside a git repository. cd into your clone of zo0r/react-native-push-notification and re-run."
  exit 2
fi

# 1. Repo identity
git remote get-url origin 2>/dev/null | grep -qE "zo0r/react-native-push-notification(\\.git)?\\b" \\
  && ok "origin remote is zo0r/react-native-push-notification" \\
  || miss "origin remote is not zo0r/react-native-push-notification (artifact may be from a fork)"

# 2. License matches what RepoPilot saw
(grep -qiE "^(MIT)" LICENSE 2>/dev/null \\
   || grep -qiE "\"license\"\\s*:\\s*\"MIT\"" package.json 2>/dev/null) \\
  && ok "license is MIT" \\
  || miss "license drift — was MIT at generation time"

# 3. Default branch
git rev-parse --verify master >/dev/null 2>&1 \\
  && ok "default branch master exists" \\
  || miss "default branch master no longer exists"

# 4. Critical files exist
test -f "android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotification.java" \\
  && ok "android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotification.java" \\
  || miss "missing critical file: android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotification.java"
test -f "android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationListenerService.java" \\
  && ok "android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationListenerService.java" \\
  || miss "missing critical file: android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationListenerService.java"
test -f "component/index.js" \\
  && ok "component/index.js" \\
  || miss "missing critical file: component/index.js"
test -f "component/index.android.js" \\
  && ok "component/index.android.js" \\
  || miss "missing critical file: component/index.android.js"
test -f "android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationHelper.java" \\
  && ok "android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationHelper.java" \\
  || miss "missing critical file: android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationHelper.java"

# 5. Repo recency
days_since_last=$(( ( $(date +%s) - $(git log -1 --format=%at 2>/dev/null || echo 0) ) / 86400 ))
if [ "$days_since_last" -le 859 ]; then
  ok "last commit was $days_since_last days ago (artifact saw ~829d)"
else
  miss "last commit was $days_since_last days ago — artifact may be stale"
fi

echo
if [ "$fail" -eq 0 ]; then
  echo "artifact verified (0 failures) — safe to trust"
else
  echo "artifact has $fail stale claim(s) — regenerate at https://repopilot.app/r/zo0r/react-native-push-notification"
  exit 1
fi

Each check prints ok: or FAIL:. The script exits non-zero if anything failed, so it composes cleanly into agent loops (./verify.sh || regenerate-and-retry).

</details>

TL;DR

A React Native library that wraps Firebase Cloud Messaging (FCM) on Android and PushNotificationIOS on iOS to deliver both local and remote push notifications with a unified JavaScript API. It handles notification delivery, user interaction callbacks, badge management, and scheduled notifications across both platforms with a single codebase. Dual-platform structure: android/src/main/java contains service handlers (RNPushNotificationListenerService, RNPushNotificationPublisher), helpers (ApplicationBadgeHelper), and module entry point (RNPushNotification.java); iOS logic delegates to PushNotificationIOS; component/ exports platform-specific JS bindings (index.android.js, index.ios.js) that bridge to native modules; example/ contains a working demo app.

👥Who it's for

React Native app developers who need to implement push notifications (local and remote) for iOS and Android without managing platform-specific notification APIs directly. Particularly useful for apps requiring scheduled notifications, custom notification actions, and badge count management.

🌱Maturity & risk

Production-ready but unmaintained: the repository explicitly states it is 'not actively maintained' due to time constraints and notification complexity. While v7.x is released and has accumulated 11k+ npm downloads/week, the maintainers recommend evaluating alternatives like Notifee or react-native-notifications. No active CI visible in workflows beyond stale issue management.

High maintenance risk: single repository with no active maintainer (README explicitly seeks maintainers), no recent commit activity visible, and complexity split across Java (105k LOC), JavaScript (43k LOC), and Objective-C (6k LOC). Firebase dependency version constraints are strict (firebase-messaging versions <15 require exact version matching at build and runtime). Breaking changes occurred in v7.x migration.

Active areas of work

Repository is in maintenance mode. No active development is evident. The README directs users toward alternative solutions. The only visible workflow (stale.yml) auto-closes stale issues. Version 7.x is the latest release with migration instructions in CHANGELOG.md.

🚀Get running

npm install react-native-push-notification && npm install react-native-push-notification-ios (iOS requires separate PushNotificationIOS installation per README). For the example app: cd example && npm install && npx react-native run-android or npx react-native run-ios.

Daily commands: Clone and install dependencies, then: for Android: ./gradlew assembleDebug (or via example app: npx react-native run-android); for iOS: pod install && xcode-select setup (or via example app: npx react-native run-ios). Example app includes NotifService.js and NotificationHandler.js for reference implementation.

🗺️Map of the codebase

  • android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotification.java — Core Android module exposing push notification APIs to React Native; entry point for all notification operations
  • android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationListenerService.java — FCM message listener that receives incoming push notifications and dispatches them to handlers
  • component/index.js — JavaScript bridge layer routing to platform-specific implementations (iOS/Android)
  • component/index.android.js — Android-specific JavaScript API surface binding native RNPushNotification module
  • android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationHelper.java — Utility methods for notification creation, scheduling, and platform-specific configuration handling
  • android/build.gradle — Android library build configuration defining dependencies and SDK version constraints
  • README.md — Project documentation revealing unmaintained status and recommending migration paths for users

🛠️How to make changes

Add a new notification configuration option

  1. Define configuration field in RNPushNotificationConfig.java (android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationConfig.java)
  2. Parse the option in RNPushNotificationHelper.java during notification creation (android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationHelper.java)
  3. Apply setting to NotificationCompat.Builder instance (android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationHelper.java)
  4. Document option in README.md and example usage in example/NotifService.js (example/NotifService.js)

Add handling for a new notification action/button

  1. Define action handling in RNPushNotificationActions.java (android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationActions.java)
  2. Add broadcast receiver or intent filter in AndroidManifest.xml (android/src/main/AndroidManifest.xml)
  3. Dispatch action result to JavaScript via RNPushNotificationJsDelivery.java (android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationJsDelivery.java)
  4. Add example usage in component/index.android.js (component/index.android.js)

Add remote (FCM) notification feature

  1. Implement new handler logic in RNPushNotificationListenerService.java (android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationListenerService.java)
  2. Route processed message through RNReceivedMessageHandler.java (android/src/main/java/com/dieam/reactnativepushnotification/modules/RNReceivedMessageHandler.java)
  3. Ensure notification display by RNPushNotificationHelper.java (android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationHelper.java)
  4. Add corresponding JS API in component/index.android.js (component/index.android.js)

🔧Why these technologies

  • React Native Bridge (JNI) — Enables JavaScript code to invoke native Android notification APIs (NotificationManager, AlarmManager) with callback delivery
  • Firebase Cloud Messaging (FCM) — Standard Android push notification service for receiving remote notifications with high reliability and Android system integration
  • AlarmManager — Enables scheduled/delayed local notifications across app lifecycle and device reboots via RNPushNotificationBootEventReceiver
  • AndroidX NotificationCompat — Backward-compatible notification API supporting SDK 16+ with consistent UX across Android versions
  • BroadcastReceiver — Decouples notification actions and boot events from main app lifecycle, allowing async processing and persistence

⚖️Trade-offs already made

  • Single RNPushNotification.java module handling both local and remote notifications

    • Why: Simplifies API surface and code organization, single entry point for JS
    • Consequence: Mixed concerns in one module make it harder to test and maintain independently; harder to support platform-specific features
  • Event delivery via RNPushNotificationJsDelivery using sendEvent callbacks

    • Why: Decouples notification receipt from JS initialization, supports background delivery
    • Consequence: Loss of events if app is not running; requires careful lifecycle management in JS to avoid memory leaks
  • No built-in TypeScript support or strict typing in JS layer

    • Why: Legacy codebase predating TS adoption in React Native ecosystem
    • Consequence: Requires external type definitions or manual TypeScript integration; higher risk of config errors at runtime
  • Repository marked as unmaintained with recommendation to use Notifee or react-native-notifications

    • Why: Time constraints and complexity of notification behavior across Android/iOS versions
    • Consequence: Users face uncertainty about bug fixes and feature backports; community forks may diverge

🚫Non-goals (don't propose these)

  • Does not provide iOS implementation (Swift/Objective-C) as a primary focus — iOS layer exists but is less frequently updated
  • Does not handle in-app notification UI rendering — delegates all display to Android NotificationManager and system UI
  • Does not provide real-time bidirectional messaging or chat features — notifications are one-way delivery only
  • Does not manage authentication or FCM token registration — assumes external registration via Firebase SDK
  • Does not support notification encryption or end-to-

🪤Traps & gotchas

Firebase dependency version pinning: firebase-messaging <15 requires exact version match between build-time and runtime, enforced in android/build.gradle via safeExtGet(). AndroidManifest.xml must be manually updated by the consuming app to include RNPushNotificationBootEventReceiver for scheduled notifications to survive device reboot. iOS requires separate installation of react-native-push-notification-ios. PushNotificationIOS on iOS does not support all features (e.g., custom actions) on older iOS versions. No automatic linking: manual AndroidManifest.xml changes are required. The example app (example/) is not auto-linked, requiring manual setup.

🏗️Architecture

💡Concepts to learn

  • Firebase Cloud Messaging (FCM) — This library is built entirely around FCM as the Android remote notification transport; understanding FCM topics, message types, and registration tokens is essential to debugging delivery issues
  • BroadcastReceiver (Android) — RNPushNotificationBootEventReceiver extends BroadcastReceiver to listen for BOOT_COMPLETED, required to reschedule notifications after device reboot; critical for scheduled notification persistence
  • AlarmManager (Android) — Used by RNPushNotificationPublisher to schedule local notifications at specified times; understanding PendingIntent and alarm scheduling is needed to modify scheduled notification behavior
  • NotificationManager & NotificationChannel (Android) — Android 8.0+ requires NotificationChannel for all notifications; this library abstracts channel creation in RNPushNotificationConfig and publishes via NotificationManager
  • React Native Native Modules Bridge — Core pattern used to invoke native Java/Objective-C code from JavaScript via NativeModules; RNPushNotification is a native module exposing methods like requestPermissions() and localNotification()
  • App Badge Count (Android Launcher Integration) — ApplicationBadgeHelper abstracts different launcher badge APIs (Samsung, LG, Sony, HTC) since Android has no standard API; required to show notification count badges
  • Silent Notifications & Data-Only Messages — FCM supports data-only messages that trigger app logic without visible notification; RNPushNotificationListenerService routes these to JS callbacks for custom handling

🪄PR ideas

To work on one of these in Claude Code or Cursor, paste: Implement the "<title>" PR idea from CLAUDE.md, working through the checklist as the task list.

Add Firebase Cloud Messaging (FCM) integration tests for android/src/main/java/com/dieam/reactnativepushnotification/modules/RNPushNotificationListenerService.java

The RNPushNotificationListenerService.java handles incoming FCM messages but lacks unit tests. Given that firebase-messaging:21.1.0 is a critical dependency and this service is the entry point for remote notifications on Android, adding comprehensive tests would catch regressions in message handling, token refresh, and notification delivery logic.

  • [ ] Create android/src/test/java/com/dieam/reactnativepushnotification/modules/ directory structure
  • [ ] Write unit tests for RNPushNotificationListenerService covering: onMessageReceived(), token refresh callbacks, and message payload parsing
  • [ ] Add Robolectric or Mockito dependencies to android/build.gradle for Android unit testing
  • [ ] Test edge cases like null payloads, missing required fields, and concurrent message handling

Create GitHub Actions workflow to validate Android and iOS builds for each PR

The repo has stale.yml in .github/workflows but lacks actual build validation. With Android (Gradle) and iOS (CocoaPods) setup present, a CI workflow would catch breaking changes early. This is especially critical given the repository note states it's not actively maintained—CI helps new maintainers catch issues.

  • [ ] Create .github/workflows/build.yml with separate Android and iOS build jobs
  • [ ] Android job: Set up JDK, run ./gradlew build in android/ directory, validate firebase-messaging compatibility
  • [ ] iOS job: Set up Node.js, install dependencies, validate pod install against component/index.ios.js integration
  • [ ] Add build status badge to README.md and fail PRs on build errors

Add integration tests for the example app (example/App.js, example/NotifService.js, example/NotificationHandler.js)

The example app demonstrates the library's usage but has only tests/App-test.js which appears minimal. Adding E2E or integration tests would ensure the notification lifecycle (local scheduling, remote delivery, user interaction) works end-to-end. This helps contributors verify their changes don't break the public API.

  • [ ] Expand example/tests/App-test.js to test NotifService.js notification scheduling API (configure, localNotification, cancelNotification)
  • [ ] Add tests for NotificationHandler.js callback chains (onNotification, onRegister) using Jest mocks
  • [ ] Test the component integration at example/component/ to ensure platform-specific behavior matches between android/ios
  • [ ] Document test execution in example/README or add to CI workflow from idea #2

🌿Good first issues

  • Add unit tests for android/src/main/java/com/dieam/reactnativepushnotification/helpers/ApplicationBadgeHelper.java (currently untested), including edge cases for devices without badge support
  • Document the exact AndroidManifest.xml changes required for scheduled notifications in a separate troubleshooting guide with code snippets (currently mentioned only in README, not detailed)
  • Create TypeScript definitions (src/index.d.ts) for the JavaScript API exported from component/index.js to help TypeScript users and IDEs provide autocomplete for methods like localNotification(), requestPermissions(), etc.

Top contributors

Click to expand

📝Recent commits

Click to expand
  • fcf40a0 — Update stale.yml (Boris Tacyniak)
  • e1a0716 — Update README.md (Boris Tacyniak)
  • da7dde7 — Bump version. (Dallas62)
  • f525fff — Merge pull request #2151 from mmmoussa/ios-notif-version (Boris Tacyniak)
  • cce3e49 — Merge pull request #2150 from mmmoussa/patch-1 (Boris Tacyniak)
  • 16b4842 — Raise @react-native-community/push-notification-ios version (mmmoussa)
  • 3dd30ef — Fix iOS repeated notification timing (mmmoussa)
  • f986f55 — Missing change in CHANGELOG. (Dallas62)
  • 2b2c69e — Merge pull request #2096 from Abhishek12345679/master (Boris Tacyniak)
  • fcc229d — Upgrade to 8.1.0. (Dallas62)

🔒Security observations

  • High · Outdated Gradle Build Tools — android/build.gradle. The build.gradle file specifies Gradle 3.2.0 (from 2018), which contains known security vulnerabilities and has reached end-of-life. This version lacks security patches and modern protections. Fix: Update com.android.tools.build:gradle to version 7.x or higher. Current stable version is 8.x. Run gradle wrapper --gradle-version 8.x to update.
  • High · Insecure Dependencies - Firebase Messaging — android/build.gradle (firebase-messaging dependency). The firebase-messaging dependency uses a dynamic version constraint (21.1.0). If not pinned, future versions could introduce breaking changes or vulnerabilities. The version specified is from 2021 and is outdated. Fix: Update to the latest Firebase Messaging version (currently 23.x+) and use an exact version constraint instead of dynamic constraints. Review release notes for security fixes.
  • High · Outdated Support Library — android/build.gradle (supportLibVersion variable). The default support library version is 27.1.1 (from 2018). This is deprecated and no longer receives security updates. AndroidX should be used instead. Fix: Migrate to AndroidX by updating the support library to version 1.x+ or use AndroidX directly. Set minSdkVersion to 21 or higher to support AndroidX.
  • High · Deprecated minSdkVersion — android/build.gradle (minSdkVersion: 16). The default minSdkVersion is 16, which reached end-of-life in 2017. This includes many unpatched vulnerabilities in older Android versions. Current Google Play Store minimum is API level 31+. Fix: Increase minSdkVersion to at least 24 (API level 24 from 2016 or higher, preferably 26+). Update the default to align with modern Android security standards.
  • High · Outdated Compile SDK Version — android/build.gradle (compileSdkVersion: 28). compileSdkVersion is set to 28 (Android 9, released 2018). Current stable is 34 (Android 14). Older SDK versions lack modern security features and API protections. Fix: Update compileSdkVersion to 34 (or latest available). This enables modern Android security features and API deprecations.
  • High · Inactive Repository Maintenance — README.md. The README explicitly states the repository is not actively maintained. This means security vulnerabilities and issues will not be patched. Users are at risk of using unmaintained code in production. Fix: Consider forking and maintaining the codebase, or migrate to actively maintained alternatives like Notifee or react-native-notifications as suggested in the README.
  • Medium · ShortcutBadger Dependency Outdated — android/build.gradle (ShortcutBadger:1.1.22). The ShortcutBadger library version 1.1.22 is from 2016 and is outdated. It may have unpatched vulnerabilities and compatibility issues with modern Android versions. Fix: Update to the latest available version of ShortcutBadger or evaluate if the dependency is still necessary for modern Android versions.
  • Medium · No Proguard Configuration Enabled — android/build.gradle (buildTypes.release.minifyEnabled: false). minifyEnabled is set to false in release builds, meaning the code is not obfuscated. This exposes the codebase to reverse engineering and makes it easier to identify and exploit vulnerabilities. Fix: Enable minification: set minifyEnabled to true and properly configure proguard-rules.pro to obfuscate sensitive code while maintaining functionality.
  • Medium · Deprecated JCenter Repository — android/build.gradle (repositories). The build.gradle includes jcenter() as a repository. JCenter was sunset on May 1, 2021 and no longer receives updates. Dependencies from this source are stale. Fix: Remove jcenter()

LLM-derived; treat as a starting point, not a security audit.


Generated by RepoPilot. Verdict based on maintenance signals — see the live page for receipts. Re-run on a new commit to refresh.

Healthy signals · zo0r/react-native-push-notification — RepoPilot