Flurry Push for iOS

Flurry Push enables app developers to send targeted messages to re-engage and retain users. To start using Flurry Push on iOS:

  1. Integrate the latest Flurry SDK for iOS
  2. If using Cocoapods, include “pod ‘Flurry-iOS-SDK/FlurryMessaging’” in your podfile
  3. Follow the integration steps below
  4. Provide Flurry your authorization credentials
  5. Test your integration via test push

Push Setup

  1. Enable Push Notifications

IMG1

  1. Enable Background Modes (Background Fetch and Remote Notifications turned on)

IMG2

Info.Plist

IMG3

  1. Include FlurryMessaging.h

Integration Types

  1. Auto Integration - With Auto Integration, Flurry handles everything for you. We’ll receive the notification, convert it to a FlurryMessage, show the notification, handle the notification click, handle the dismissed notification, and handle all the Flurry logging associated with it. Want some customized functionality? You have the option of passing us a delegate to handle any of these steps yourself.
  2. Manual Integration - The app is responsible for handling the notification receivers and logging events like “Opened” to Flurry.

Auto Integration

Flurry will receive the push notification (from APNs) and convert it to a Flurry Message. You may optionally set a listener to get notified when a push is received and opened. This allows you to handle and customize each event as you wish.

  • Setup for receiving push Notifications - Flurry will register with UNUserNotificationCenter (>= iOS 10) or UIUserNotification. Also, setup the delegate to receive the below notifications
  • Notification Received - Flurry will LOG and SHOW the notification if the app is in the background. If the app is in foreground Flurry will LOG but NOT show the notification.
  • Flurry will also return a callback , if the delegate is set.
  • Notification Clicked - Flurry will LOG notification when user clicks on it. By default Flurry would launch the app.
  • Flurry will also return a callback , if the delegate is set. This would be the place to use the deeplink to load the appropriate View.

Integration Steps

In your AppDelegate class, place the following code in application:willFinishLaunchingWithOptions:

  1. Registration & Setup
  • (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {

    //Step1 : Call the Integration API

    [FlurryMessaging setAutoIntegrationForMessaging];

    //Step2 (Optional): Get a callback

    [FlurryMessaging setMessagingDelegate:self];

    FlurrySessionBuilder* builder = [[[FlurrySessionBuilder alloc] withIncludeBackgroundSessionsInMetrics:YES];

    [Flurry startSession:@”API_KEY” withOptions:launchOptions withSessionBuilder:builder];

    return YES;

}

  1. Implement the Delegate method for Received

-(void) didReceiveMessage:(nonnull FlurryMessage*)message

{

NSLog(@”didReceiveMessage = %@”, [message description]);

//App specific implementation

}

  1. Implement the Delegate method for Clicked

-(void) didReceiveActionWithIdentifier:(nullable NSString*)identifier message:(nonnull FlurryMessage*)message

{

NSLog(@”didReceiveAction %@ , Message = %@”,identifier, [message description]);

//Any app specific logic goes here.

//Ex: Deeplink logic (loading of viewControllers (nibs or storboards),

//additional logging, etc

}

Manual Integration

Manual integration helps you handle it all. Flurry provides a few helper methods for you to determine if a notification is from Flurry, and if so, convert the notification into a FlurryMessage. In manual integration, you must log the following events as described:

  • Set token - If you receive a callback that the token has been set, provide Flurry with the token via the setDeviceToken: api.
  • Notification Received - When a notification from Flurry is received log it to Flurry via

receivedRemoteNotification:withCompletionHandler: api

  • Notification Clicked - When a notification from Flurry is clicked, log this event to Flurry via the receivedNotificationResponse:withCompletionHandler: api.

Integration Steps

In your AppDelegate class, implement as follows:

  1. Setup and Registration
  • (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions

{

// Step1: Register

if(SYSTEM_VERSION_GRATERTHAN_OR_EQUALTO(@”10.0”))

{

UNUserNotificationCenter* center = [UNUserNotificationCenter currentNotificationCenter];

center.delegate = self;

//Note : UNAuthorizationOptionBadge not supported in v1

[[UNUserNotificationCenter currentNotificationCenter] requestAuthorizationWithOptions:(UNAuthorizationOptionSound | UNAuthorizationOptionAlert)

completionHandler:^(BOOL granted, NSError * _Nullable error)

{

if( !error && granted)

{

[application registerForRemoteNotifications]; // required to get the app to do anything at all about push notifications

NSLog(@”Push registration success.”);

}

else

{

NSLog(@”Push registration Failed. ERROR: %@ - %@”, error.localizedFailureReason, error.localizedDescription );

}

}];

}

else

{

UIApplication* application = [UIApplication sharedApplication];

//Note:UIUserNotificationTypeBadge not supported in v1

if ([application respondsToSelector:@selector(isRegisteredForRemoteNotifications)])

{

// iOS 8 Notifications registration

[application registerUserNotificationSettings:[UIUserNotificationSettings settingsForTypes:(UIUserNotificationTypeSound |UIUserNotificationTypeAlert ) categories:nil]];

[application registerForRemoteNotifications];

}

}

FlurrySessionBuilder* builder = [[[FlurrySessionBuilder alloc] withLogLevel:FlurryLogLevelDebug] withIncludeBackgroundSessionsInMetrics:YES];

[Flurry startSession:@”API_KEY” withOptions:launchOptions withSessionBuilder:builder];

//Step2 (Optional): Get a callback

[FlurryMessaging setMessagingDelegate:self];

return YES;

}

  1. Set the device token

-(void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken

{

[FlurryMessaging setDeviceToken:deviceToken];

}

  1. Log Notification Received & Clicked

#pragma iOS7+ (prior to UNUserNotificationCenter)

-(void) application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo fetchCompletionHandler:(void (^)(UIBackgroundFetchResult))completionHandler

{

if ([FlurryMessaging isFlurryMsg:userInfo]) {

//Step4: Notify msg received callback

[FlurryMessaging receivedRemoteNotification:userInfo withCompletionHandler:^{

//Load and Nibs or storyboard from here

completionHandler(UIBackgroundFetchResultNewData);

}];

}

}

#pragma iOS10+ (UNUserNotificationCenter only)

  • (void)userNotificationCenter:(UNUserNotificationCenter *)center didReceiveNotificationResponse:(UNNotificationResponse *)response

    withCompletionHandler:(void (^)())completionHandler

{

if ([FlurryMessaging isFlurryMsg:response.notification.request.content.userInfo]) {

//Step5: Notify response received callback

[FlurryMessaging receivedNotificationResponse:response withCompletionHandler:^{

completionHandler();

}];

}

}

  • (void)userNotificationCenter:(UNUserNotificationCenter *)center willPresentNotification:(UNNotification *)notification withCompletionHandler:(void (^)(UNNotificationPresentationOptions options))completionHandler

{

if ([FlurryMessaging isFlurryMsg:notification.request.content.userInfo]) {

//Step4: Notify msg received callback

[FlurryMessaging presentNotification:notification withCompletionHandler:^{

completionHandler(UNNotificationPresentationOptionSound);

}];

}

}

Background Sessions

When pushes are received or tapped, a Flurry background session occurs to allow Flurry to measure push metrics. Flurry exposes a method to allow you to determine whether such sessions are counted in the same way that foreground sessions are counted: withIncludeBackgroundSessionsInMetrics. Make sure to set withIncludeBackgroundSessionsInMetrics according to your app measurement needs.

Setting this method to YES/true:

  • Background sessions initiated by push notifications, as well as session data for other background sessions, will be included in overall session metrics. This will impact time spent, uniques and other metrics.

Setting this method to NO/false

  • Background sessions including sessions initiated by push notifications will not be included in overall session metrics. Push events such as PushOpened will be reported even if set to NO/false.
  • You must set to NO/false to exclude push-initiated background sessions from being counted as sessions for your app.

This is set in the Builder:

FlurrySessionBuilder* builder = [[[FlurrySessionBuilder alloc] withIncludeBackgroundSessionsInMetrics:NO];

[Flurry startSession:@”API_KEY” withOptions:launchOptions withSessionBuilder:builder];

Deep Linking

Overview

Deep linking is the ability for an app to direct a user to a specified location in the app. When setting up a campaign, users may input a deep link.

IMG4

Flurry has reserved the “deeplink” keyword in the app data payload. You may leverage the deeplink string the user enters during campaign set up via the appData property (message.appData). By setting up the proper handling of this string during integration, you will ensure that the user lands on the deep link location after tapping on the notification.

While Flurry can’t define the deep linking experience for an app, here is an example on how to use our suite to implement it.

Deep Linking Example

Imagine you are building an app which contains a series of news articles. Each news article is identified by a unique integer identifier. Let’s say the local sports team drafts a top prospect, and you want to send a push notification with the breaking news article. On the Flurry portal, you can create a new push campaign, set the title to “Breaking News!”, set the body to “49ers pick up top prospect”, and set the reserved “deeplink” field to “appproject://main/article?number=149”. Note: this a sample deeplink, you should format your deeplinks in accordance with your app’s deep link schema.

Now, when the FlurryMessage is received by the application, you may use appData property (message.appData) to retrieve your custom deeplink String. Be sure to do your null checks, and use the deep link string retrieved to instrument the tap action.

Note: There is another way to implement deep linking using key-value pairs. On the flurry portal, you can add a custom key value pair as: key=article and value=149. On the app side, fetch this key value pair by message.appData[@”article”]. Now the app can download the article with unique identifier “149”, and display that to the user. Code for this use case is shown in the Sample Code section.

Deep Linking Sample Code

Option 1: Using the AppDelegate callbacks

  • (void)userNotificationCenter:(UNUserNotificationCenter *)center didReceiveNotificationResponse:(UNNotificationResponse *)response withCompletionHandler:(void (^)(void))completionHandler {

    [FlurryMessaging receivedNotificationResponse:response withCompletionHandler:^{

    NSLog(@”Article to open = %@”,message.appData[@”article”])

    completionHandler();

    }];

}

Option 2: Using the FlurryMessaging delegate method (Optional Delegate)

  • (void)didReceiveActionWithIdentifier:(nullable NSString *)identifier message:(nonnull FlurryMessage *)message {

    NSLog(@”Article to open = %@”, message.appData[@”article”])

}