Enable push notifications in a Cordova app (iOS)

This guide walks you through enabling push notifications in your Cordova app on iOS using the Acoustic Connect SDK.

Language: JavaScript, with TypeScript definitions. The Notification Service Extension and Notification Content Extension are implemented in Swift and ship with the plugin — you don't write or maintain this Swift code yourself.

Availability: Pro, Premium, and Ultimate

Scope: Test setup — building, running on the simulator or a connected iPhone, and verifying push delivery. Covers both automatic and manual push mode.

Sample app: See our GitHub repository for a reference implementation to compare your configuration against.


Prerequisites

  • Apple Developer Program membership — push notifications require a paid account. Required role: Account Holder or Admin.
  • The Connect Cordova plugin, integrated in your project with a Connect app key from a Mobile app integration created after April 2026 — earlier integrations don't support push. See Integrate the Connect SDK into a Cordova app to install the plugin first.

Overview

  1. Get an APNs authentication key.
  2. Share your push notification credentials with your Connect administrator.
  3. Register an App Group and enable capabilities in the Apple Developer portal.
  4. Configure push notifications in ConnectConfig.json.
  5. Build — the plugin wires up Xcode automatically.
  6. Add code to request notification permission from your users.
  7. Forward native delegate callbacks to the SDK (only if using manual push mode).

Step 1: Get an APNs authentication key

Connect uses token-based APNs authentication. A single .p8 key works across all apps in your team.

  1. In your Apple Developer account, go to Certificates, Identifiers & Profiles > Keys > +.
  2. Enter a name and enable Apple Push Notifications service (APNs).
  3. Click Configure, set Environment to Sandbox & Production unless your security team requires tighter scoping — this can't be changed later.
  4. Save > Continue > Register.
  5. Download the .p8 file — Apple only allows this once.
  6. Note the Key ID and your Team ID (10-character string, top-right of the portal).

Step 2: Share push notification credentials with your Connect administrator

CredentialWhere to find it
Encryption keyThe .p8 file from Step 1
Key IDThe confirmation page, or the file name
Team IDTop-right of the Apple Developer portal, or under Membership
Bundle IDYour Cordova project's config.xml — the id attribute on the <widget> element
EnvironmentSandbox — this guide covers test setup
📘

Note

Your Connect administrator needs to upload these credentials before push notifications will be delivered. See Connect mobile apps in the Connect user guide. Steps 3–5 can be completed while you wait.


Step 3: Configure the Apple Developer portal

Push notifications in Connect require three components sharing an App Group — a container that lets them exchange push data. The identifier must be identical across all three or delivery tracking and rich media silently fail.

ComponentPurpose
Main appInitializes the SDK and requests notification permission
Notification Service Extension (NSE)Downloads rich media and records delivery, including dismissed notifications
Notification Content Extension (NCE)Renders the expanded notification view on long-press

Do the following in the portal:

Register or update your App ID

If you are registering a new App ID:

  1. In your Apple Developer account, go to Identifiers > +.
  2. Select App IDs > App and click Continue.
  3. Enter a description and your bundle ID.
  4. Under Capabilities, enable Push Notifications and App Groups.
  5. Click Continue > Register.

If your App ID already exists:

  1. Click the App ID in the list to open it.
  2. Under Capabilities, enable Push Notifications and App Groups.
  3. Click Save.

Register App IDs for the extensions

This step is automated — you don't do it in the portal. The plugin creates the ConnectNSE and ConnectNCE extension targets in Xcode for you on every build (see Step 5).

Create an App Group

  1. Go to Identifiers > + and select App Groups.
  2. Enter a description and an identifier using the group. prefix (for example, group.com.yourcompany.yourapp).
  3. Click Continue > Register.
  4. Go back to your main App ID and assign the App Group you just created.

You'll assign this same App Group to the NSE and NCE extension App IDs later, in Step 5, after the plugin creates the extension targets.


Step 4: Configure push in ConnectConfig.json

Back in your project root (outside Xcode), open ConnectConfig.json and add the following keys inside the Connect object.

{
  "Connect": {
    "AppKey": "...",
    "PostMessageUrl": "...",
    "iOSPushMode": "automatic",
    "iOSAppGroupIdentifier": "group.com.yourcompany.yourapp",
    "iOSDevelopmentTeam": "YOUR_TEAM_ID"
  }
}
KeyValue
iOSPushMode'automatic' (default) — the SDK installs its own notification delegate and handles APNs registration, delivery, and tap actions. 'manual' — your app owns UNUserNotificationCenter.delegate and forwards events via AcousticConnect.push.didReceiveNotification() / didReceiveResponse().
iOSAppGroupIdentifierThe App Group identifier from Step 3. Substituted automatically into the NSE/NCE Swift source and into the host app's and both extensions' entitlements files — you don't edit any .entitlements file by hand.
iOSDevelopmentTeamRequired. Your 10-character Apple Team ID. Stamped onto the main app target and both extension targets automatically on every prepare.

Step 5: Build — the plugin wires up Xcode

Build for iOS.

npx cordova build ios

Every build wires up Xcode for you automatically — you do not need to manually create extension targets, edit a Podfile, or hand-edit an entitlements file.

What happens automatically on every build
  • Copies the NSE (NotificationService.swift) and NCE (NotificationViewController.swift) source into platforms/ios/, with your App Group identifier substituted in.
  • Creates the ConnectNSE and ConnectNCE app-extension targets in your .xcodeproj (idempotently — safe to run every prepare), links the required system frameworks (UserNotifications, and UserNotificationsUI + UIKit for the NCE), and adds an "Embed Foundation Extensions" build phase on the main app target.
  • Adds ConnectNSE and ConnectNCE as CocoaPods targets in your Podfile and runs pod install — only when the Podfile actually changed, to avoid an unnecessary reinstall on every build.
  • Adds the App Group and aps-environment entitlement to the main app's entitlements file (and both extensions').
  • Adds UIBackgroundModesremote-notification to Info.plist.

What you still do manually, once:

In Xcode:

  1. Open platforms/ios/App.xcworkspace (never the .xcodeproj — CocoaPods generates the workspace).
  2. Select the main app target → Signing & Capabilities → confirm a Team is set. This is automatic — you already set iOSDevelopmentTeam in ConnectConfig.json in Step 4.
  3. Add the Push Notifications capability to the main app target. This is the one capability the plugin doesn't add for you — UIBackgroundModes is added automatically, but the capability entry itself is not.

In the Apple Developer portal:

  1. Assign the App Group from Step 3 to the two extension App IDs the plugin just created for ConnectNSE and ConnectNCE.
🚧

Warning

If Xcode doesn't offer App Groups as a capability, or your App Group isn't selectable, Xcode hasn't picked up your portal changes yet. Go to Xcode > Settings > Apple Accounts, select your account and team, click Download Manual Profiles, then try again.


Step 6: Request notification permission

const result = await AcousticConnect.push.requestPermission();

if (result.granted) {
  console.log('Notification permission granted');
} else {
  console.log('Notification permission denied:', result.error);
}

push.requestPermission() presents the system permission dialog when the state is undetermined. Call it at an appropriate moment in your UX rather than on first launch.

🚧

Warning

iOS only shows the system permission dialog once. If the user denies it, the only way to re-enable notifications is through the Settings app.

Check the current state without prompting:

const granted = await AcousticConnect.push.getPermissionState();
// true = granted, false = denied, null = not yet determined

Step 7: Handle manual push mode

If iOSPushMode is 'manual', your app's own native delegate handles APNs callbacks and forwards them:

await AcousticConnect.push.didReceiveAuthorization(granted, error);
await AcousticConnect.push.didReceiveNotification(userInfo);
await AcousticConnect.push.didReceiveResponse(actionIdentifier, userInfo);

These three methods reject with ACOUSTIC_PUSH_MODE_NOT_MANUAL if called while the SDK is running in automatic mode.


Testing

Enable debug logging

With "useRelease": false in ConnectConfig.json (the default), the plugin sets CONNECT_DEBUG, TLF_DEBUG, and EODebug at runtime, and verbose native logging appears in the Xcode console.

On the simulator — instant verification

You can test push delivery in the simulator using .apns payload files — drag them onto the running simulator. This confirms basic delivery and NCE invocation, but rich-media images may not have time to load; use a real iPhone to validate images.

{
    "Simulator Target Bundle": "com.yourcompany.yourapp",
    "aps": {
        "alert": { "title": "New arrivals", "body": "Fresh styles just landed." },
        "sound": "default"
    }
}
{
    "Simulator Target Bundle": "com.yourcompany.yourapp",
    "aps": {
        "alert": { "title": "New arrivals", "body": "Fresh styles just landed." },
        "sound": "default",
        "mutable-content": 1
    }
}

On an iPhone — real APNs delivery

  1. Build and run on a physical iPhone.
  2. Grant notification permission when prompted. A new mobile contact is created in Connect.
  3. Coordinate with your marketing team to send a test push, or do it yourself — see Test your push notification setup.
  4. Verify the notification appears, images load, and push signals appear in the contact's activity feed in Connect.

Troubleshooting

Push notifications not being delivered

  • If you're testing on a device, check your debug log for an APNs token. If none appears, confirm the Push Notifications capability is added to the main app target and that the device has network access. (On the simulator, no token is ever generated.)
  • Confirm the user granted notification permission.
  • Confirm remote-notification is in UIBackgroundModes in Info.plist (added automatically — check if you've overridden Info.plist manually).
  • Confirm the bundle ID matches the App ID with Push Notifications enabled in the portal.

Rich push images not showing

  • Confirm the image URL is accessible over HTTPS.
  • Confirm iOSAppGroupIdentifier in ConnectConfig.json matches the App Group assigned to all three App IDs in the portal.
  • Confirm pod install ran after any App Group change — check the after_prepare console output for Podfile changed — running pod install.

Extension targets missing or stale after a fresh clone / plugin re-add

Run npx cordova prepare ios (or npx cordova build ios) again — the extension targets, embed phase, and entitlements are rebuilt idempotently by the after_prepare hook each time. If signing looks stale specifically, re-open Xcode, confirm Signing & Capabilities shows a Team on all three targets, and re-download provisioning profiles if App Groups isn't selectable.

[after_prepare] pod install failed

CocoaPods isn't installed, or your local spec repo is stale. Run sudo gem install cocoapods && pod repo update, then npx cordova build ios again.

Unable to find host target(s) for ConnectNSE, ConnectNCE during pod install

This can happen on a fresh platform add, when the Podfile still references extension targets from a previous prepare but the .xcodeproj was reset. The plugin's before_prepare hook detects and strips stale references automatically, and after_prepare re-adds them once the project is consistent again — if you still see this error, re-run npx cordova prepare ios once more before investigating further.


Next step: Identify app users

Push setup is now complete. To make the most of push notifications, identify the people receiving them — see Identify users at sign-in.