Tracking SDK Standard iOS (Swift)
Tracking SDK Standard is used to track targeted user actions in the mobile app and further analyze this information.
Before you start
You should be aware of the following options required to initialize and use the SDK. Ask the SDK team to give them to you.
- partnerId - Partner ID. For example:
123
. - endpointUrl - API URL of tracking system. For example:
"https://my.server.com/event"
.
SDK version:
Demo: Tracking SDK Example
Stable release: Tracking SDK Standard
Requirements
- Swift 5 and above
- iOS 12 and above
Installation
pod 'SATrackingSDK', '{{ version }}'
or
pod 'SATrackingSDKStandard', :git => 'https://github.com/solutionarchitectstech/ios_tracker_sdk_release.git', :tag => '{{ version }}'
Initialization
The library is initialized by the developer when the application is started or when the user is authorized by the method call TechTracker.initialize()
.
For example, see AppDelegate.swift:
TechTracker.initialize(options: TrackerOptions(
partnerId: "YOUR_PARTNER_ID",
sessionId: "YOUR_SESSION_ID",
endpointUrl: "https://YOUR_END_POINT",
debugMode: true,
httpHeaders: [
"Authorization": "YOUR_AUTHORIZATION_TOKEN"
]
))
TechTracker.initialize(options: TrackerOptions)
public struct TrackerOptions {
public init(
partnerId: String,
endpointUrl: String,
sessionId: String,
debugMode: Bool = false,
httpHeaders: [String: String] = [:]
)
}
partnerId
- Partner ID. For example:123
. Ask the SDK team to give it to you.endpointUrl
- API URL of tracking system. For example:https://my.server.com/event
. Ask the SDK team to give it to you.sessionId
- Unique session id what determines current application session. There are types of mobile apps:- Online app (your application uses your own business backend) - in this case please provide session id, what matched with server side session of your own backend - this is the most preferable way.
- Offline app (your mobile doesn't use own business backend). If your app doesn't use backend, then your mobile app can pass generated
UUID
value here. IMPORTANT: yourUUID
must be generated once on each first application startup. You must never re-generate it during application lifecycle. Only if your app terminated (removed from memory) and re-started again, only this triggers newUUID
value.
debugMode
- Enables or disables debug mode in the SDK. Produces extra debug.false
by default. log output - might be useful while you debug your app.httpHeaders
- Dictionary of HTTP headers what will be injected in to each API call.[:]
empty map by default. if you invokeTechTracker.shared.event(event: TrackerEvent)
function.
WARNING
If you attempt to access any SDK method without initialization, then fatalError("TrackingSDK not initialized yet. Please initialize it first.")
will be thrown. This exception indicates to the host's developers that they can only use SDK once they initialize successfully.
User ID (UID)
Your mobile application might be:
- Anonymous (public - no user based authorization at all). For example: any user can use whole functionality of your app without needs to register own user account. Public (anonymous) usage.
- AuthN/AuthZ based (user based authorization required). For example: Sign-in screen on startup.
- Mixed app (some screens of your app are publicly available for anyone, but other ones are only available for authorized users). For example: Anyone (without user account) can navigate between catalog / products screens. But if user tries to 'Add to cart' or 'To make an order', then application asks user to pass authorization (Sign-in / Sign-up).
IMPORTANT
Tracking SDK provides TechTracker.shared.uid
property. Please, setup this property with 'user id' value of your real authorized user.
You have to set this property on each successful 'Sign-in' attempt.
You have to set this property as nil
if user signed out.
You can skip setup of this property only in one scenario: if your mobile is Anonymous and never uses user authorization.
Here is an example how to set TechTracker.shared.uid
property:
myAuthService.signIn(username, password) { authSession, error in
defer {
TechTracker.shared.uid = authSession.success ? authSession.user.id : nil
}
if let error = error {
print("ERROR: Unable to sign-in due error: \(error.localizedDescription)")
return
}
// Here, you do your own business logic specific for your mobile app
// after user passes authorization.
// Eg: navigate to 'Main' screen, or navigate to 'Cart' screen, etc ...
}
myAuthService.signOut() { error in
defer {
TechTracker.shared.uid = nil
}
if let error = error {
print("WARNING: Error occured while sign-out (skipped): \(error.localizedDescription)")
}
// Here, you do your own business logic specific for 'Sign-out' procedure.
// Eg: navigate to 'Sign-in' (startup) screen, etc ...
}
public class TechTracker {
public var uid: String?
}
uid
- (optional) Unique user ID, authorized in your mobile app. Set this up on each successful attempt of your user authorization. Set this asnil
on each 'Sign-out' attempt. Skip this property if your app is Anonymous (never uses user accounts).
Tracking user activity
The Tracking SDK provides an API to send a specific events. To send an event, you must pass the event object to the method TechTracker.shared.event(event: TrackerEvent)
.
Here is an example:
var event = Click(
value: "start registration",
contentId: "1",
contentName: "Doll",
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param1": "value1",
"custom_param2": "value2"
]
)
TechTracker.shared.event(event: event) { error in
if let error = error {
print("ERROR: Unable to send event due error: \(error.localizedDescription)")
return
}
print("DEBUG: Done - your event has been sent successfully.")
}
public func event(
path: String = "",
event: TrackerEvent,
block: @escaping (Error?) -> Void = { _ in }
)
path
- For example:my_company/tracking
.""
by default. If you add this parameter in your call, then SDK sends an event to the following URL:https://my.server.com/event/my_company/tracking
duehttps://my.server.com/event
has been used in the SDKinitialize()
asendpointUrl
. You can also initialize SDK instance with final URL, like:https://my.server.com/event/my_company/tracking
. In this case, just skippath
argument in theevent()
function.event
- Your tracking event object. See Standard events for more details.block
- Callback block (closure), executed after attempt to send an event. Empty closure by default.
Standard events
You can track the following events:
- AddToCart - the user adding product items to the shopping cart in the application
- Purchase - the user purchases goods in the system
- StartView - the user starts viewing the product card
- StopView - the user ends of viewing content
- Click - the user clicks on a significant element/advertising block in the application (links, buttons, product card in the product list, etc.)
- Search - the user searches some content in application (for example, search for a product)
- AdImp - viewing advertising content by the user
- AdClick - click on advertising content by user
- Scroll - the user scrolled the content page
AddToCart
- Trigger: the user adding product items to the shopping cart in the application.
- Payload: the list of product items that are added to the shopping cart.
let event = AddToCart(
items: [
AddToCartItem(
sku: SKU(
skuId: "1",
skuName: "Lego",
price: 35.0,
currency: "RUB"
),
deltaQuantity: 1.0,
quantity: 2.0,
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param_1_1": "value_1_1",
"custom_param_1_2": "value_1_2"
]
),
AddToCartItem(
sku: SKU(
skuId: "2",
skuName: "Ozone"
),
deltaQuantity: 1.0,
quantity: 2.0,
)
]
)
TechTracker.shared.event(event: event)
public struct AddToCart: TrackerEvent {
public init(items: [AddToCartItem] = [])
}
public struct AddToCartItem: CustomParamsAware {
public init(
sku: SKU,
deltaQuantity: Float,
quantity: Float,
category: [Category]? = nil,
customParams: [String: String]? = nil
)
}
sku
- a group of the fields that describe the product's SKU data (see SKU)quantity
- the quantity of the productdeltaQuantity
- the difference (increment or decrement) between the new and current quantity of the productcategory
- (optional) taxonomy of categories of viewed content or products. (see Category)customParams
- (optional) custom parameters to add to tracking event
Purchase
- Trigger: the user purchases goods in the system.
- Payload: the list of product objects that are purchased by the user
let event = Purchase(
items: [
PurchaseItem(
sku: SKU(
skuId: "1",
skuName: "Lego",
price: 35.0,
currency: "RUB"
),
quantity: 2.0,
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param_1_1": "value_1_1",
"custom_param_1_2": "value_1_2"
]
),
PurchaseItem(
sku: SKU(
skuId: "2",
skuName: "Ozone"
),
quantity: 2.0
)
]
)
TechTracker.shared.event(event: event)
public struct Purchase: TrackerEvent {
public init(items: [PurchaseItem] = [])
}
public struct PurchaseItem: CustomParamsAware {
public init(
sku: SKU,
quantity: Float,
category: [Category]? = nil,
customParams: [String: String]? = nil
)
}
sku
- a group of the fields that describe the product's SKU data (see SKU)quantity
- the quantity of the productcategory
- (optional) taxonomy of categories of viewed content or products. (see Category)customParams
- (optional) custom parameters
StartView
- Trigger: the user starts viewing the product card.
- Payload: the list of content objects that are viewed by the user.
WARNING
If the current content being viewed is a catalog page (for example, a list of product teasers), then DO NOT send a view event for each teaser of other content/product presented in that catalog. The view content event must be sent once and only for the catalog itself.
let event = StartView(
contentId: "1",
contentName: "Lego",
sku: SKU(
skuId: "1",
skuName: "Lego",
price: 35.0,
currency: "RUB"
),
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param1": "value1",
"custom_param2": "value2"
]
)
TechTracker.shared.event(event: event)
public struct StartView: TrackerEvent, CustomParamsAware {
public init(
contentId: String,
contentName: String,
sku: SKU? = nil,
category: [Category]? = nil,
customParams: [String: String]? = nil
)
}
contentId
- the unique identifier of the content being viewed. By default, the content URL is assumed, if such a division into identifiers is not possible, then any other ideograph clearly distinguishes one viewed content from another.contentName
- name of the content being viewedsku
- (optional) a group of the fields that describe the product's SKU data (see SKU)category
- (optional) taxonomy of categories of viewed content or products. (see Category)customParams
- (optional) custom parameters
StopView
- Trigger: the user ends of viewing content.
- Payload: the list of content objects that were viewed by the user.
WARNING
If the current content being viewed is a catalog page (for example, a list of product teasers), then DO NOT send a view event for each teaser of other content/product presented in that catalog. The view content event must be sent once and only for the catalog itself.
let event = StopView(
contentId: "1",
contentName: "Lego",
value: 0.5
sku: SKU(
skuId: "1",
skuName: "Lego",
price: 35.0,
currency: "RUB"
),
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param1": "value1",
"custom_param2": "value2"
]
)
TechTracker.shared.event(event: event)
public struct StopView: TrackerEvent, CustomParamsAware {
public init(
contentId: String,
contentName: String,
value: Float,
sku: SKU? = nil,
category: [Category]? = nil,
customParams: [String: String]? = nil
)
}
contentId
- the unique identifier of the content being viewed. By default, the content URL is assumed, if such a division into identifiers is not possible, then any other ideograph clearly distinguishes one viewed content from another.contentName
- name of the content being viewedvalue
- a value between 0 and 1 that describes how much content was viewed in percentagesku
- (optional) a group of the fields that describe the product's SKU data (see SKU)category
- (optional) taxonomy of categories of viewed content or products. (see Category)customParams
- (optional) custom parameters
Click
- Trigger: the user clicks on a significant element/advertising block in the application (links, buttons, product card in the product list, etc.).
- Payload: the object with a description of which element was clicked (url for external links).
TIP
If clicking an item is similar to any of the specialized events, it is better to use a specialized event. For example, to observe the click on the product cart buttons, you must use the event type Add to cart / Purchase .
let event = Click(
value: "start registration",
contentId: "1",
contentName: "Lego",
sku: SKU(
skuId: "1",
skuName: "Lego",
price: 35.0,
currency: "RUB"
),
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param1": "value1",
"custom_param2": "value2"
]
)
TechTracker.shared.event(event: event)
public struct Click: TrackerEvent, CustomParamsAware {
public init(
value: String,
contentId: String,
contentName: String,
sku: SKU? = nil,
category: [Category]? = nil,
customParams: [String: String]? = nil
)
}
value
- a string with a description of which element was clicked (url for external links).contentId
- the unique identifier of the content being viewed. By default, the content URL is assumed, if such a division into identifiers is not possible, then any other ideograph clearly distinguishes one viewed content from another.contentName
- name of the content being viewedsku
- (optional) a group of the fields that describe the product's SKU data (see SKU)category
- (optional) taxonomy of categories of viewed content or products. (see Category)customParams
- (optional) custom parameters
Search
- Trigger: the user searches some content in application (for example, search for a product).
- Payload: the object with the search phrase value
let event = Search(
value: "Pampers",
filter: [
"age": ["0-1", "1-3"],
"sex": ["m"]
],
customParams: [
"custom_param1": "value1",
"custom_param2": "value2"
]
)
TechTracker.shared.event(event: event)
public struct Search: TrackerEvent, CustomParamsAware {
public init(
value: String,
filter: [String: [String]]? = nil,
customParams: [String: String]? = nil
)
}
value
- search phrasefilter
- (optional) search filterscustomParams
- (optional) custom parameters
AdImp
- Trigger: viewing advertising content by the user.
- Payload: the object with description of the advertising block, which was viewed by the user.
let event = AdImp(
placementId: "1",
width: 240,
height: 300,
clickURL: "https://test.com",
adType: .banner,
contentId: "1",
contentName: "Lego",
sku: SKU(
skuId: "1",
skuName: "Lego",
price: 35.0,
currency: "RUB"
),
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param1": "value1",
"custom_param2": "value2"
]
)
TechTracker.shared.event(event: event)
public struct AdImp: TrackerEvent, CustomParamsAware {
public init(
placementId: String,
width: Int,
height: Int,
clickURL: String,
adType: AdType,
contentId: String? = nil,
contentName: String? = nil,
sku: SKU? = nil,
category: [Category]? = nil,
customParams: [String: String]? = nil
)
}
public enum AdType: String {
case banner
case video
case native
case product
case reach_media
case other
}
placementId
- placement unique identifierwidth
- width of ad placementheight
- height of ad placementclickURL
- URL address that is linked to the the advertising blockadType
- the type of advertising on which the user clicks (see types section)contentId
- (optional) the unique identifier of the content being viewed. By default, the content URL is assumed, if such a division into identifiers is not possible, then any other ideograph clearly distinguishes one viewed content from another.contentName
- (optional) name of the content being viewedsku
- (optional) a group of the fields that describe the product's SKU data (see SKU)category
- (optional) taxonomy of categories of viewed content or products. (see Category)customParams
- (optional) custom parameters
AdClick
- Trigger: click on advertising content by user.
- Payload: the object with the description of the advertising block, which was clicked by the user.
let event = AdClick(
placementId: "1",
width: 240,
height: 300,
clickURL: "https://test.com",
adType: .banner,
contentId: "1",
contentName: "Lego",
sku: SKU(
skuId: "1",
skuName: "Lego",
price: 35.0,
currency: "RUB"
),
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param1": "value1",
"custom_param2": "value2"
]
)
TechTracker.shared.event(event: event)
public struct AdClick: TrackerEvent, CustomParamsAware {
public init(
placementId: String,
width: Int,
height: Int,
clickURL: String,
adType: AdType,
contentId: String? = nil,
contentName: String? = nil,
sku: SKU? = nil,
category: [Category]? = nil,
customParams: [String: String]? = nil
)
}
public enum AdType: String {
case banner
case video
case native
case product
case reach_media
case other
}
placementId
- placement unique identifierwidth
- width of ad placementheight
- height of ad placementclickURL
- URL address that is linked to the the advertising blockadType
- the type of advertising on which the user clicks (see types section)contentId
- (optional) the unique identifier of the content being viewed. By default, the content URL is assumed, if such a division into identifiers is not possible, then any other ideograph clearly distinguishes one viewed content from another.contentName
- (optional) name of the content being viewedsku
- (optional) a group of the fields that describe the product's SKU data (see SKU)category
- (optional) taxonomy of categories of viewed content or products. (see Category)customParams
- (optional) custom parameters
Scroll
- Trigger: the user scrolled the content page.
- Payload: an object with a content scrolling value as a percentage of the total content.
let event = Scroll(
value: 0.6,
contentId: "1",
contentName: "Lego",
sku: SKU(
skuId: "1",
skuName: "Lego",
price: 35.0,
currency: "RUB"
),
category: [
Category(
categoryId: "1",
categoryName: "Category Name",
children: [
Category(
categoryId: "11",
categoryName: "SubCategory Name"
)
]
)
],
customParams: [
"custom_param1": "value1",
"custom_param2": "value2"
]
)
TechTracker.shared.event(event: event)
public struct Scroll: TrackerEvent, CustomParamsAware {
public init(
value: Float,
contentId: String,
contentName: String,
sku: SKU? = nil,
category: [Category]? = nil,
customParams: [String: String]? = nil
)
}
value
- the value of scrolling the page that the user watches from 0 to 1contentId
- the unique identifier of the content being viewed. By default, the content URL is assumed, if such a division into identifiers is not possible, then any other ideograph clearly distinguishes one viewed content from another.contentName
- name of the content being viewedsku
- (optional) a group of the fields that describe the product's SKU data (see SKU)category
- (optional) taxonomy of categories of viewed content or products. (see Category)customParams
- (optional) custom parameters
Helpers
Below is a description of the auxiliary fields and their data types used in standard events.
Category
Taxonomy of categories of viewed content or products.
public struct Category {
public init(
categoryName: String,
categoryId: String? = nil,
children: [Category]? = nil
)
}
name
- category namecategoryId
- (optional) unique identificator of the categorychildren
- (optional) the nested array of child subcategories for this category
SKU
A group of the fields that describe the product's SKU data.
public struct SKU {
public init(
skuId: String,
skuName: String,
price: Float? = nil,
currency: String? = nil,
category: [Category]? = nil
)
}
skuId
- SKU identifier of the productskuName
- name of the productprice
- (optional) price of the productcurrency
- (optional) product currency (USD, EUR, RUB, etc.)category
- (optional) taxonomy of categories of viewed content or products. (see Category)