Dashly for iOS

Version

Table of Contents

Installation

At the moment Dashly for iOS can be installed via CocoaPod. ​

CocoaPods

Add the following string into the pod file:

pod 'DashlySDK'

Initialization

You'll need API Key and User Auth Key to work with Dashly for iOS. Those can be found on Settings - Developers tab: Developers

Swift

Initialization

You should add this code into your app's AppDelegate file in order to initialize Dashly: ​

func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey:Any]?) -> Bool {
    ....
    Dashly.shared.setup(
        withApiKey: key,
        successHandler: {
                print("Dashly SDK connected")
        },
        errorHandler: { error in
            print("Dashly SDK error: " + error)
        })
    ....
}

User authorization

In case your application has user authorization, you might want to send user id to Dashly:

Dashly.shared.auth(
    withUserId: userId, 
    withUserAuthKey: userAuthKey,
        successHandler: {
            print("Dashly SDK user auth successed")
        },
        errorHandler: { error in
            print("Dashly SDK user auth error: " + error)
        })

to realize the logout function:

Dashly.shared.logout(
    successHandler: {
        print("Dashly SDK user logout successed")
    },
    errorHandler: { error in
        print("Dashly SDK user logout error: " + error)
    })

User properties and events

You can set user properties, using this method:

Dashly.shared.setUserProperty(userProperties)

Where userProperties is an object of [UserProperty] type. ​ UserProperty class should be used for user properties description:

UserProperty(key: key, value: value)
UserProperty(key: key, value: value, operation: .updateOrCreate)

More info on Operations can be found in «User properties» section. ​ Important!key field value should not start with $. ​ ​ DashlyUserProperty and EcommerceUProperty classes should be used to set system properties. ​ ​ Use the following method for events tracking:

Dashly.shared.trackEvent(withName: name, withParams: params)

where params is a JSON string with additional set of event parameters ​

Live chat

You can give your users an opportunity to start a live chat (with your operator) from anywhere. This can be done two ways - either by adding a floating button or by directly calling a chat openning method at desired moment.

Floating Button

You can use the following method to add chat button:

Dashly.shared.showButton(in: view)

Use this method to hide chat button:

Dashly.shared.hideButton()

Open chat from anywhere

After initialization you can open chat from any place using thix method:

Dashly.shared.openChat()

Notifications

SDK uses Firebase Cloud Messaging for sending notifications. At the moment you are required to get a key and send it to our support. You can find an input for this key at "Settings" - "Developers" tab of Dashly admin panel. Cloud Messaging setup is described here. ​ fcmToken for Dashly SDK should be set in MessagingDelegate next: ​

import FirebaseMessaging
import DashlySDK
extension AppDelegate: MessagingDelegate {  
    func messaging(_ messaging: Messaging, didReceiveRegistrationToken fcmToken: String) {
        if let fcmToken = fcmToken {
            DashlyNotificationService.shared.setToken(fcmToken)
        } else {
            print("Dashly SDK error: fcmToken not found")
        }
        ...
    }
}

Add this code into UNUserNotificationCenterDelegate to display notifications: ​

import DashlySDK
extension AppDelegate: UNUserNotificationCenterDelegate {
    func userNotificationCenter(
        _ center: UNUserNotificationCenter,
        willPresent notification: UNNotification,
        withCompletionHandler completionHandler: @escaping (UNNotificationPresentationOptions) -> Void) {
        let notificationService = DashlyNotificationService.shared
        if notificationService.canHandle(notification) {
            notificationService.show(notification, completionHandler: completionHandler)
        } else {
            // user notifications logic
        }
    }
}

Use this for handling clicks on notifications: ​

import DashlySDK
extension AppDelegate: UNUserNotificationCenterDelegate {
    func userNotificationCenter(
        _ center: UNUserNotificationCenter,
        didReceive response: UNNotificationResponse,
        withCompletionHandler completionHandler: @escaping () -> Void) {
        let notificationService = DashlyNotificationService.shared
        if notificationService.canHandle(response) {
            notificationService.clickNotification(notificationResponse: response)
        } else {
            // user notifications logic
        }
        completionHandler()
    }
}

Objective-C

Initialization

You should add this code into your app's AppDelegate file in order to initialize Dashly: ​

#import "DashlySDK/DashlySDK.h"

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
    ....
    Dashly *dashly = [Dashly shared];
    [
        dashly
        setupWithApiKey: API-KEY
        successHandler: ^(){
            NSLog(@"Dashly SDK connected");
        }
        errorHandler: ^(NSString *error){
            NSLog(@"Dashly SDK error: %@", error);
    }];
    ....
    return YES;
}

User authorization

In case your application has user authorization, you might want to send user id to Dashly:

Dashly *dashly = [Dashly shared];
[
  dashly
  authWithUserId: userId
  withUserAuthKey: userAuthKey
  successHandler: ^(){
      NSLog(@"Dashly SDK user auth successed");
  }
  errorHandler: ^(NSString *error){
      NSLog(@"Dashly SDK user auth error: %@", error);
}];

to realize the logout function:

Dashly *dashly = [Dashly shared];
[
  dashly
  logoutWithSuccessHandler: ^(){
     NSLog(@"Dashly SDK user logout successed");
  } errorHandler: ^(NSString *error){
     NSLog(@"Dashly SDK user logout error: %@", error);
}];

User properties and events

You can set user properties, using this method:

Dashly *dashly = [Dashly shared];
[
  dashly
  setUserProperty:userProperties
];

Where userProperties is an object of [UserProperty] type. ​ UserProperty class should be used for user properties description:

Dashly *dashly = [Dashly shared];
UserProperty *userProp = [[UserProperty alloc] initWithKey: key value: value];
UserProperty *userProp = [[UserProperty alloc] initWithKey: key value: value operation: @"updateOrCreate"];

More info on Operations can be found in «User properties» section. ​ Important!key field value should not start with $. ​ ​ DashlyUserProperty and EcommerceUProperty classes should be used to set system properties. ​ ​ Use the following method for events tracking:

Dashly *dashly = [Dashly shared];
[
  dashly
  trackEventWithName: name
  withParams: params
];

where params is a JSON string with additional set of event parameters ​

Live chat

You can give your users an opportunity to start a live chat (with your operator) from anywhere. This can be done two ways - either by adding a floating button or by directly calling a chat openning method at desired moment. ​

Floating Button

You can use the following method to add chat button:

Dashly *dashly = [Dashly shared];
[dashly showButtonIn: self.view];

Use this method to hide chat button:

Dashly *dashly = [Dashly shared];
[dashly hideButton];

Open chat from anywhere

After initialization you can open chat from any place using thix method:

Dashly *dashly = [Dashly shared];
[dashly openChat];

Getting the number of unread dialogs and messages

To keep track of the number of unread dialogs:

Dashly *dashly = [Dashly shared];
[
  dashly
  getUnreadConversationsCount:^(NSInteger count){
        NSLog(@"Dashly SDK dialogs count: %ld", (long)count);
}];

and for the number of unread messages:

Dashly *dashly = [Dashly shared];
[
  dashly
  getUnreadMessagesCount:^(NSInteger count){
        NSLog(@"Dashly SDK dialogs count: %ld", (long)count);
}];

Notifications

SDK uses Firebase Cloud Messaging for sending notifications. At the moment you are required to get a key and send it to our support. You can find an input for this key at "Settings" - "Developers" tab of Dashly admin panel. Cloud Messaging setup is described here. ​ fcmToken for Dashly SDK should be set in MessagingDelegate next:

#import "DashlySDK/DashlySDK.h"
#import <Firebase.h>

- (void)messaging:(FIRMessaging *)messaging didReceiveRegistrationToken:(NSString *)fcmToken {
    DashlyNotificationService *service = [DashlyNotificationService shared];
    [service setToken: fcmToken];
}

Add this code into UNUserNotificationCenterDelegate to display notifications:

- (void)userNotificationCenter:(UNUserNotificationCenter *)center
       willPresentNotification:(UNNotification *)notification
         withCompletionHandler:(void (^)(UNNotificationPresentationOptions options))completionHandler {
    DashlyNotificationService *service = [DashlyNotificationService shared];
    if ([service canHandle:notification]) {
        [service show:notification appGroudDomain:nil completionHandler:completionHandler];
    } else {
        // user notifications logic
    }
}

Use this for handling clicks on notifications:

- (void)userNotificationCenter:(UNUserNotificationCenter *)center
didReceiveNotificationResponse:(UNNotificationResponse *)response
         withCompletionHandler:(void(^)(void))completionHandler {
    DashlyNotificationService *service = [DashlyNotificationService shared];
    if ([service canHandleWithResponse:response]) {
        [service clickNotificationWithNotificationResponse:response appGroudDomain:nil];
    } else {
        // user notifications logic
    }
}

Double notifications

We're delivering messagis via 2 channels, thus same notification can be received twice. Examples: when logging out or quickly deleting a notification there is a possibility of getting the same notification. Notification Service Extension should be created to prevent such behaviour. Choose your project in files list of Xcode, then File/New/Target/Notification Service Extension.

After that register in AppGroup Apple Developer Portal. Identifier App Group should be unique and start with "group.", otherwise it would not be accepted by Xcode. ​ Add Identifier into Xcode: ​ AppGroup

1) Choose your project in the files list. ​ 2) Choose your project's name in targets list. ​ 3) Click "+ Capability" in "Singing & Capabitities" tab. ​ 4) Find and choose App Group in droplist. ​ 5) An empty App Group identifiers list will be shown in the tab. Add Identifier previously registered on Apple Developer Portal here. ​ 6) Go back to Targets list. Add App Group into your Notification Service Extension. ​ ​ Add next string to SDK init:

   Dashly.shared.setup(
   ...
       withAppGroup: <group_id>,
   ...
   )

You should now add logic into your Notification Service Extension. A new folder with your Notification Service Extension name should have appeared in the files list. Add code into NotificationService.swift: ​

import UserNotifications
import DashlySDK

class NotificationService: UNNotificationServiceExtension {
    var contentHandler: ((UNNotificationContent) -> Void)?
    var bestAttemptContent: UNMutableNotificationContent?
    override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) {
        self.contentHandler = contentHandler
        guard let bestAttemptContent = (request.content.mutableCopy() as? UNMutableNotificationContent) else {
            return
        }
        self.bestAttemptContent = bestAttemptContent
        let domain = "Identifier previously registered on the Apple Developer Portal"
        DashlyNotificationService.shared.deleteDuplicateNotification(withContent: bestAttemptContent, appGroudDomain: domain)
        contentHandler(bestAttemptContent)
    }

    override func serviceExtensionTimeWillExpire() {
        if let contentHandler = contentHandler, let bestAttemptContent =  bestAttemptContent {
            contentHandler(bestAttemptContent)
        }
    }
}

Refresh your pod file and add this:

   target 'NotificationService' do
     inherit! :search_paths
     pod 'DashlySDK'
   end

Lastly, send Identifier previously registered on Apple Developer Portal into show method in UNUserNotificationCenterDelegate: ​

let domain = "Identifier previously registered on Apple Developer Portal"
notificationService.show(notification, appGroudDomain: domain, completionHandler: completionHandler)

Xcode 15

If you are using Xcode 15 and above, and CocoaPods 1.12.1 and below, you will get a directory error like this:

Xcode

To fix this, add the following code to the end of your podfile:

post_install do |installer|
  installer.pods_project.targets.each do |target|
    target.build_configurations.each do |config|
      if config.base_configuration_reference.is_a? Xcodeproj::Project::Object::PBXFileReference
        xcconfig_path = config.base_configuration_reference.real_path
        IO.write(xcconfig_path, IO.read(xcconfig_path).gsub("DT_TOOLCHAIN_DIR", "TOOLCHAIN_DIR"))
      end
    end
  end
end

Perhaps in the future, CocoaPods will be updated and this code will have to be removed, but for now, it is necessary.