Setting Up the SDK

Are you starting your iOS app from scratch? You can download our starter Xcode project, which is empty except for the pre-loaded Koupon Media SDK.


The purpose of this section is to explain the components of the Koupon Media SDK and to help you configure it for use with an existing iOS app. We assume that you have already downloaded the Koupon Media SDK (or our starter Xcode project if you do not have an existing app), and if applicable, the Gimbal SDK

Files Included in the SDK

The following framework and header files are included in the Koupon Media SDK archive Koupon.embeddedframework:

File Name Description
KouponResources.bundle Contains all of the resources for Advanced Push.
KouponGimbalManager.h A bridge for linking the KouponMedia SDK to the Gimbal SDK.
Koupon.h The main Koupon object that houses all the functions for interacting with our APIs
KMRequest.h The request object that holds all details for an API request. Details include the signed URL, API body (if necessary), and several shortcut functions for executing the request.
KMLocation.h All the location services for the SDK.
KMProximityEvent.h Returned from any Beacon Proximity events and contains proximity specific information.
KMGeofence.h Returned from any Geofence events and contains geofence specific information.

Note that the SDK archive also contains documentation.

Add the SDK Files to Your Existing App

To add the Koupon Media SDK files to your existing Xcode project, unzip the archive and follow the steps below.

In addition to the SDK files below, the Koupon Media SDK also depends on the following frameworks to function properly:

• Security.framework
• Foundation.framework
• UIKit.framework
• CoreLocation.framework

    1. Drag Koupon.embeddedframework into your Xcode project’s Frameworks folder (be sure to select “Copy the items to your destination’s group folder“).

How to include the Koupon Media SDK in your project

If you are also using the Gimbal SDK, refer to the documentation included in the Gimbal SDK package for instructions on adding frameworks.

  1. Within Xcode, add the dependencies to your project by navigating to the screen Targets > [Your project name] > Build Phases. Here, expand the section entitled “Link Binary with Libraries.” If you are only using the Koupon Media SDK, verify that Koupon.framework is within the dependency list.

How to link the Koupon Media SDK binaries

  1. Expand the section entitled “Copy Bundle Resources” and verify KouponResources.bundle is included

How to verify the Koupon Media SDK was installed

If you are also using the Gimbal SDK, you need to include the following dependencies (in addition to Koupon.embeddedframework):

• Common.embeddedframework
• CoreTelephony.framework
• CoreBluetooth.framework
• libz.dylib
• MapKit.framework
• ContextCore.embeddedframework
• CoreTelephony.embeddedframework
• ContextLocation.embeddedframework
• ContextProfiling.embeddedframework
• FYX.framework
• NetworkServices.embeddedframework


Configure Preferences (.plist file)

To configure the Koupon Media SDK preferences, create a file named KouponConfiguration.plist and add the entries below. If any errors occur, the .plist should be the first place you need to look. Ensure that you have authKey, authSecret, Domain and Channel values correct for the environment that you are trying to perform operations on.

The Koupon Media SDK supports production and sandbox environments. During the integration and testing phases of application development, it is necessary to ensure the proper endpoint URL is used for the intended environment. If the Domain value is not set in your .plist file, then the SDK will default to using the production environment and will produce errors if your client has not been set up on production. If you are just now installing the SDK, then you will want to include your domain value. Your domain value is given by your Account manager.

Koupon Media Entries

Entry Description
authKey Your Koupon Media authKey. This value is generally the same for production and sandbox enviornments, but they can vary. “Signature does not match” error code most likely means that the combination of your authkey/authSecret/Domain is incorrect.
authSecret Your Koupon Media authSecret. This value is generally the same for production and sandbox enviornments, but they can vary. “Signature does not match” error code most likely means that the combination of your authkey/authSecret/Domain is incorrect.
Domain The base URL for Koupon API calls. You should only need to specify this if you are pointing to a sandbox environment. This value is generally the same for production and sandbox enviornments, but they can vary. “Signature does not match” error code most likely means that the combination of your authkey/authSecret/Domain is incorrect.
Channel The value for the channel that you are retrieving offers for. The most likely case is that you are retrieving offers for an app, in which the value of “APP” ensures that your app only pulls in offers that are destined to go inside of the app digital property

How to configure your .plist to include the Koupon Media Offers SDK

The image above shows a representation of a sample KouponConfiguration.plist.

The following entries in “Optional Entries”/”Gimbal .plist”/”Gimbal Optional Entries” are not necessary in order to implement the Koupon Media base SDK. The following options expose more rich analytics and targeting capabilities, but do not directly have to do with the presentation of offers.

Optional Entries

Entry Value
AppEventDomain The URL for AppEvent calls. You should only need to specify this if you are pointing to a sandbox environment.
VisitDepartureInterval The number of seconds that a consumer needs to be away from a beacon in order to register a return.
VisitArrivalStrength The radio signal decibel level that defines when a consumer is near a beacon. A reasonable range is -90 to -25 dB.
VisitDepatureStrength The radio signal decibel level that defines when a consumer is sufficiently away from a beacon. A reasonable range is -90 to -25 dB.
SignalSmoothingLevel Since the radio signal can be erratic, a smoothing function can be applied to eliminate discontinuities in the signal.


Gimbal .plist (if Applicable)

The Gimbal SDK requires another .plist file named UserContext.plist with the following configuration entries:

Entry Description
FEATURE_DESCRIPTION Human readable description of what sort of events you will be tracking
FEATURE_NAME Broad title representing your app
PRODUCTION_API_KEY Your Gimbal Production API Key (provided by Koupon Media)

By default, when you enable Gimbal, a branded dialog containing the end user consent, privacy notice and terms of service will be presented to the end user. However, you have the choice to display your own privacy notice and end user opt-in consent in lieu of the Gimbal branded dialog.You will be bound by the “White Label Mode” terms within the Gimbal Developer Agreement.

To bypass this branded dialog box, simply add the property CUSTOM_OPT_IN_FLOW: YES to UserContext.plist file.

Custom dialog flow in iOs

Gimbal Entries (if Applicable)

Entry Description
GeofenceEnabled YES or NO
BeaconsEnabled YES or NO
GimbalAppId Your Gimbal App Id (provided by Koupon Media)
GimbalAppSecret Your Gimbal App Secret (provided by Koupon Media)


Update the App Delegate

Registering a Consumer

There are several options for registering a consumer. Please refer to the use cases below and add the corresponding code to application didFinishLaunchingWithOptions. Your AppDelegate.m will look similar to the following sample code:

//  AppDelegate.m
//  MyKouponSample

#import "AppDelegate.h"
#import <Koupon/Koupon.h>

@implementation AppDelegate

@synthesize kouponSDK;

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
    //Init the Koupon SDK using the KouponConfiguration.plist file
    kouponSDK = [[Koupon alloc] init];
   [kouponSDK createConsumerIdentity:[NSMutableDictionary dictionary] withOptionalQueryData:nil];

  1. You can register a consumer with an external Consumer ID (CID), such as a CRM identifier from a retailer’s IT system.
// Register a consumer using "CID"
NSMutableDictionary *consumerData = [[NSMutableDictionary alloc ] init];
[consumerData setObject:@"123456" forKey:@"cid"];


  1. You can register a consumer with an email address or mobile number (most likely obtained from a log-in page).
// Register a consumer using “email” or “mobile” 
NSMutableDictionary *consumerData = [[NSMutableDictionary alloc ] init];
[consumerData setObject: @"" forKey:@"email"];


  1. You can register a consumer using all three identifiers (i.e., CID, email address and mobile number).
// Register a consumer using all three: “cid”, “email”,and “mobile” 
NSMutableDictionary *consumerdata = [NSDictionary dictionaryWithObjectsAndKeys:
					@"5555555555", @"mobile",
					@"", @"email"
					@"123456",@"cid", nil];


Registering for Push Notifications

If you would like your application to register with Koupon Media as a Third Party Push Providers, add the following code to the App Delegate, under application:didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken

[[kouponSDK reportAppEvent:@"pushreg" withData:[NSMutableDictionary dictionaryWithObjectsAndKeys:deviceToken, @"device_id", @"ios", @"platform", nil]] 

sendRequestAsyncOnSuccess:^(NSMutableDictionary* response){
    NSLog(@"MySampleApp->Successfully sent Device Token to Koupon Media”);

OnFailure:^(NSMutableDictionary* response){
    NSLog(@"MySampleApp->Failed to send Device Token to Koupon Media");

Note that the example above demonstrates how to asynchronously perform a network request using the Koupon Media SDK. For more information on setting up a third party push provider, please see the official Apple Developer Documentation.


Setting Up Advanced Push

Advanced push is a feature that allows you to send push notifications that direct the user to a seque of a mobile web page.

Make sure to add #import <Koupon/KMAdvancedPush> inside your appdelegate.

- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo
   [[KMAdvancedPush shared] handleAdvancedPush:userInfo];

Somewhere inside your application:didFinishLaunchingWithOptions: method, add the following.

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
   [[KMAdvancedPush shared] handleAdvancedPush:launchOptions];


Adding Gimbal to the App Delegate

Be sure to add the Gimbal SDK files, link the libraries, and prepare the PList entries described above. Also, you must include the following files in your project:

For this example, we will be updating AppDelegate.h to include the following code, but you can include these headers and code anywhere in your project:

#import "Koupon/KouponGimbalManager.h"
#import "Koupon/KMProximityEvent.h"
#import "Koupon/KMGeofenceEvent.h"
@interface KouponAppDelegate : NSObject <UIApplicationDelegate, KouponGimbalManagerDelegate>

Update the App Delegate function of application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions to include the following:

// Inside of ApplicationDidStartWithOptions
[[KouponGimbalManager sharedManager] initGimbalServicesWithDelegate:self KouponSDK:kouponSDK ];

Note that the code above could also be implemented in another class delegate that inherits from the KouponGimbalManger. Your application can now respond to various events by implementing one or more of the following delegate methods:

- (void) beaconServiceStarted {
    [[KouponGimbalManager sharedManager] startListeningForVisits];
- (void) beaconServiceFailedToStart: (NSError *) error {
    NSLog(@"handle error");
- (void) receivedSighting: (KMProximityEvent*) proxEvent {
    NSLog(@"Sighting: %@ ---- RSSI: %@",, proxEvent.RSSI);
- (void) receivedArrival: (KMProximityEvent*) proxEvent {
    NSLog(@"Arrival: %@",;
- (void) receivedDeparture: (KMProximityEvent*) proxEvent {
    NSLog(@"Departure: %@ ---- dwellTime: %f",, proxEvent.visit.dwellTime);
- (void) didEnterGeofence: (KMGeofenceEvent*) geoEvent{
    NSLog(@"You have entered %@.",;
- (void) didExitGeofence:(KMGeofenceEvent *) geoEvent {
    NSLog(@"You have left %@",;


Alternate Gimbal Approach

An alternate approach utilizes a publish/subscribe model in lieu of the delegate functions, which allows multiple parts of your application to have access to your location events.

For this use case, KouponGimbalManager broadcasts/publishes events through the NSNotificationCenter, thereby notifying your app where controllers subscribe to notifications through the Notification Center.

The approach below synchronizes information across many parts of your application, rather than limiting it to a particular delegate for handling the business logic. The following code provides a brief sample of how to do that using several possible notifications.

//First, you need to subscribe to the notification
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didEnterGeofence:) name:KMGimbalManagerDidEnterGeofenceNotification object:nil];

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didExitGeofence:) name:KMGimbalManagerDidExitGeofenceNotification object:nil];
//Now you can pull the geoEvent from the NSNotification object
- (void) didEnterGeofence: (NSNotification*) notification{
    KMGeofenceEvent *geoEvent = [notification object];  
    NSLog(@"You have entered %@.",;
- (void) didExitGeofence:(NSNotification *) notification {
    KMGeofenceEvent *geoEvent = [notification object];
    NSLog(@"You have left %@",;

Other possible notifications include the following:

• KMGimbalManagerBeaconServiceStartedNotification
• KMGimbalManagerDidExitGeofenceNotification
• KMGimbalManagerDidEnterGeofenceNotification
• KMGimbalManagerReceivedDepartureNotification
• KMGimbalManagerReceivedArrivalNotification
• KMGimbalManagerReceivedSightingNotification
• KMGimbalManagerBeaconServiceFailedToStartNotification