Add the Notification Service Framework to a native iOS project

The AcousticMobilePushNotification.xcframework enables support for media attachments (images, audio, and video) and also enables support for Acoustic dynamic action categories.

A notification extension functions as a second app within your overall app bundle and requires separate provisioning.

Step A: Add a notification service target

  1. In your Xcode project, go to the File menu and select New > Target.

    Target menu item in Xcode
  2. Under iOS, select Notification Service Extension.

    Dialogue box
  3. In the Language list, select Objective-C. Fill out the remaining settings as appropriate.

  1. If a confirmation message appears, click Activate.
  1. Find a new target in your Xcode project.

Step B: Add the Acoustic notification framework to the target

  1. Select the Notification Service target and open the General tab.

  2. In the Signing section, select the same team the main project target belongs to and configure the bundle ID. A typical pattern for the bundle ID is com.company.app.notification if your app bundle ID is com.company.app.

  3. In the  Frameworks and Libraries section, add AcousticMobilePushNotification.xcframework.

  4. On the Build Settings tab, expand the Linking section. Add -ObjC to the Other Linker Flags build options for the Notification Service.

  5. On the Signing & Capabilities tab, add the App Group capability. Enable the same app group that the main application target uses.

  6. On the same tab, add the Keychain Sharing capability. Add the same value for the keychain group that the main application target uses.

To add media attachments to notifications, you must configure the mutable-content flag and media-attachment key in the iOS 10 payload. For more information, refer to the following articles:

Step C: Implementing the framework

Automatic implementation

In the NotificationService.h file, replace the contents with the following.

#import <UserNotifications/UserNotifications.h> #import <AcousticMobilePushNotification/AcousticMobilePushNotification.h> @interface NotificationService : MCENotificationService @end

In the NotificationService file, replace the contents with the following.

import UserNotifications import AcousticMobilePushNotification class NotificationService: MCENotificationService { }

Manual implementation

  1. In the NotificationService.h file, replace the contents with the following.

    #if __has_feature(modules) @import UserNotifications; @import AcousticMobilePushNotification; #else #import <UserNotifications/UserNotifications.h> #import <AcousticMobilePushNotification/AcousticMobilePushNotification.h> #endif @interface NotificationService : UNNotificationServiceExtension @property MCENotificationService * notificationService; @end
  2. In the NotificationService.m file, replace the contents with the following.

    #import "NotificationService.h" #import "MCEManualConfiguration.h" @interface NotificationService () @property (nonatomic, strong) void (^contentHandler)(UNNotificationContent *contentToDeliver); @property (nonatomic, strong) UNMutableNotificationContent *bestAttemptContent; @end @implementation NotificationService -(instancetype)init { if(self = [super init]) { // If using a dictionary based configuration: [MCEConfig sharedInstanceWithDictionary: MCEManualConfiguration.xmlSettings]; // If using the MceConfig.json file, you only need to initialize the object self.notificationService = [[MCENotificationService alloc] init]; } return self; } - (void)didReceiveNotificationRequest:(UNNotificationRequest *)request withContentHandler:(void (^)(UNNotificationContent * _Nonnull))contentHandler { if(request.content.userInfo[@"notification-action"]) { [self.notificationService didReceiveNotificationRequest: request withContentHandler: contentHandler]; return; } } - (void)serviceExtensionTimeWillExpire { // Called just before the extension will be terminated by the system. // Use this as an opportunity to deliver your "best attempt" at modified content, otherwise the original push payload will be used. [self.notificationService serviceExtensionTimeWillExpire]; } @end

In the NotificationService file, replace the contents with the following.

import UserNotifications import AcousticMobilePushNotification class NotificationService: UNNotificationServiceExtension { let mobilePushNotificationService: MCENotificationService override init() { // If using a dictionary based configuration: // MCEConfig.sharedInstance(with: Config.mobilePushConfig) // If using the MceConfig.json file, you only need to initialize the object mobilePushNotificationService = MCENotificationService() super.init() } override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) { if request.content.userInfo["notification-action"] != nil { mobilePushNotificationService.didReceive(request, withContentHandler: contentHandler) return } // Handle other notifications here } override func serviceExtensionTimeWillExpire() { mobilePushNotificationService.serviceExtensionTimeWillExpire() } }

📘

Note

If you are using MCEConfig.json for configuration, you can remove the dictionary-based configuration in the init method.

Add the MceConfig.json file to the Notification Service target. In MceConfig.json, check the notification service target membership in the Target Membership of the File Inspector in the Xcode pane.