Zingle iOS SDK
Overview
Zingle is a multi-channel communications platform that allows the sending, receiving and automating of conversations between a Business and a Customer. Zingle is typically interacted with by Businesses via a web browser to manage these conversations with their customers. The Zingle API provides functionality to developers to act on behalf of either the Business or the Customer. The Zingle iOS SDK provides mobile application developers an easy-to-use layer on top of the Zingle API.
To view the latest API documentation, please refer to: https://github.com/Zingle/rest-api/
Contact vs. Account class sessions
Contact session
A contact session represents someone such as a hotel guest. This session is used by user of a third party application that uses the Zingle API to communicate with a service, such as a hotel front desk, on behalf of the user.
All usage examples in this README will address contact class usage.
Account session
An account session represents a Zingle customer using the API to communicate with their own guests or customers.
For further information regarding account class usage, see Using the SDK as an Account Class User.
Installation with CocoaPods
CocoaPods is a dependency manager for Objective-C, which automates and simplifies the process of using 3rd-party libraries like the ZingleSDK in your projects. You can install it with the following command:
$ gem install cocoapods
Podfile
To integrate the ZingleSDK into your Xcode project using CocoaPods, specify it in your Podfile
:
source 'https://github.com/CocoaPods/Specs.git'
platform :ios, '8.0'
pod 'ZingleSDK'
Then, run the following command:
$ pod install
Import the SDK header file where needed:
#import <ZingleSDK/ZingleSDK.h>
Session creation
Several pieces of data will be required to initialize a contact class session.
- The Zingle API user's token (this is your Zingle dashboard username)
- The Zingle API user's security key (this is your Zingle dashboard password)
- The channel type UUID representing the chat channel being used by the API user
- The channel value, such as the user name of the current third party app user within the custom chat type
Initialization
Using contact selection and error handling blocks
// Initialize the session object.
session = [ZingleSDK contactSessionWithToken:myToken
key:myKey
channelTypeId:channelId
channelValue:username];
// Optionally set an error-handling block.
// (You may alternatively use the completion block with its error property if you only wish to explicitly handle connection errors.)
session.error = ^(ZNGError * _Nonnull error) {
// Do something with the error
};
// Connect, optionally providing a block to be called once all available contact services have been found
[session connectWithContactServiceChooser:^ZNGContactService * _Nullable(NSArray<ZNGContactService *> * _Nonnull availableContactServices) {
// Choose a contact service and return it immediately or present the user with a choice and return nil
//
[self presentContactServiceChoiceToUser];
return nil;
} completion:nil];
// ... Wait for user input ...
void userDidSelectContactService:(ZNGContactService *)selectedContactService
{
// Choose a contact service if it was not done in the block above, optionally providing a completion block
[session setContactService:selectedContactService completion:^(ZNGContactService * _Nullable contactService, ZNGService * _Nullable service, ZNGError * _Nullable error) {
if (error != nil) {
// Something went wrong
} else {
// You did it!
// If you would like to access the data directly, you may grab a conversation object.
ZNGConversation * conversation = session.conversation;
// You may also grab a view controller that will handle message displaying and sending messages.
ZNGConversationViewController * conversationViewController = session.conversationViewController;
[self presentViewController:conversationViewController animated:YES completion:nil];
}
}];
}
Using KVO
You may instead wish to use KVO to determine when the availableContactServices array has been populated and to handle any errors.
session = [ZingleSDK contactSessionWithToken:myToken
key:myKey
channelTypeId:channelId
channelValue:username];
[session addObserver:self forKeyPath:@"availableContactServices" options:0 context:NULL];
[session addObserver:self forKeyPath:@"mostRecentError" options:0 context:NULL];
[session connect];
- (void) observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSString *,id> *)change context:(void *)context
{
if ([keyPath isEqualToString:@"availableContactServices"]) {
// Present UI to the user to select a contact service
} else if ([keyPath isEqualToString:@"mostRecentError"]) {
// Handle an error
}
}
void userDidSelectContactService:(ZNGContactService *)selectedContactService
{
[session setContactService:selectedContactService completion:^(ZNGContactService * _Nullable contactService, ZNGService * _Nullable service, ZNGError * _Nullable error) {
if (error != nil) {
NSLog(@"Something went wrong")
} else {
// You did it!
// If you would like to access the data directly, you may grab a conversation object.
ZNGConversation * conversation = session.conversation;
// You may also grab a view controller that will handle message displaying and sending messages.
ZNGConversationViewController * conversationViewController = session.conversationViewController;
[self presentViewController:conversationViewController animated:YES completion:nil];
}
}];
}
Using a pre-selected contact service
You may wish to immediately select a contact service on login.
// Initialize the session object. This will send off a request for all available contact services.
session = [ZingleSDK contactSessionWithToken:myToken
key:myKey
channelTypeId:channelId
channelValue:username];
[session connectWithContactServiceChooser:^ZNGContactService * _Nullable(NSArray<ZNGContactService *> * _Nonnull availableContactServices) {
if ([availableContactServices containsObject:preselectedContactService]) {
return preselectedContactService;
} else {
// The preselected contact service is not available. Where did it all go wrong?
[self manuallySelectContactService];
return nil;
}
} completion: ^(ZNGContactService * _Nullable contactService, ZNGService * _Nullable service, ZNGError * _Nullable error) {
if (error == nil) {
// You did it!
}
}];
Push Notifications
Conversation objects and Conversation View Controller objects will refresh data whenever a push notification is received and sent to the SDK via NSNotification (see Receiving push notifications below)
Preparing to receive push notifications
Certificates and registration
The user of the SDK must have a valid push notification entitlement/certificate in the app. He is also responsible for registering the application's push notification capabilities on launch. See Apple's Local and Remote Notification Programming Guide and Ray Wenderlich's Push Notifications Tutorial.
Setting the token
Once the application has successfully registered for push notifications, the device token needs to be set within the ZingleSDK before a ZingleSession is created.
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
// ...
application.registerForRemoteNotifications()
// ...
}
func application(application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: NSData) {
ZingleSDK.setPushNotificationDeviceToken(deviceToken)
}
Receiving push notifications
Once a ZingleSession with a valid push notification entitlement and a set device token has connected through the SDK, push notifications will be sent to the device whenever new data is received. It is up to the SDK user to post an NSNotification so that the SDK elements can accept and react to the notification.
All ZingleSDK push notifications should include the Category value of ZingleSDK. A push notification regarding a message will also include the contact service ID of the sender of the message as 'feedId.' Following is a sample push notification dictionary and the Swift code to post an NSNotificationCenter notification to allow ZingleSDK elements to react to the new data.
{
aps = {
alert = {
body = " Jason Nobody \nThis is the message body.";
};
sound = default;
};
feedId = "28e02b1d-a38e-4e6b-85d1-95fe29983a7d";
category = "ZingleSDK";
}
func handleRemoteNotificationDictionary(userInfo: [NSObject : AnyObject], fromApplicationState state: UIApplicationState) {
NSNotificationCenter.defaultCenter().postNotificationName(ZNGPushNotificationReceived, object: nil, userInfo: userInfo)
}
Logging
The ZingleSDK uses the CocoaLumberjack logging framework with a specific logging context.
#define ZINGLE_LOG_CONTEXT 889
Zingle Object Model
Model | Description |
---|---|
ZingleSDK | Static class that provides convenience constructors for Zingle session objects |
ZingleSession | Abstract class that represents a connection to the Zingle API |
ZingleContactSession | Concrete subclass of ZingleSession that represents a connection to the Zingle API as a contact class user (e.g. a Hotel guest communicating with the front desk) |
ZingleAccountSession | Concrete subclass of ZingleSession that represents a connection to the Zingle API as an account class user (e.g. a hotel employee) |
ZNGAccount | See Zingle Resource Overview - Account |
ZNGService | See Zingle Resource Overview - Service |
ZNGPlan | See Zingle Resource Overview - Plan |
ZNGContact | See Zingle Resource Overview - Contact |
ZNGAvailablePhoneNumber | See Zingle Resource Overview - Available Phone Number |
ZNGLabel | See Zingle Resource Overview - Label |
ZNGCustomField | See Zingle Resource Overview - Custom Field |
ZNGCustomFieldOption | See Zingle Resource Overview Custom Field Option |
ZNGCustomFieldValue | See Zingle Resource Overview - Custom Field Value |
ZNGChannelType | See Zingle Resource Overview - Channel Type |
ZNGServiceChannel | See Zingle Resource Overview - Service Channel |
ZNGContactChannel | See Zingle Resource Overview - Contact Channel |
ZNGMessageCorrespondent | Message Correspondents are the abstract representation of either the Sender or Recipient on a Message. |
ZNGMessageAttachment | Message Attachments provide the ability to add binary data, such as images, to messages. |
ZNGConversation | Model responsible for maintaining the state of a conversation between a Contact and a Service. |
ZNGConversationViewController | UI that manages the conversation between a Contact and a Service. |
ZNGAutomation | See Zingle Resource Overview - Automation |