Apphud SDK requires minimum iOS 11.2 and Xcode 10 and Swift version 5.0.
Apphud SDK can be installed via CocoaPods, Carthage, Swift Package Manager or manually.
Add the following line to your Podfile
:
pod 'ApphudSDK'
In Objective-C project make sure use_frameworks!
is added in your Podfile
.
Add the following line to your Cartfile
:
github "apphud/ApphudSDK"
And then run in the Terminal:
carthage update
Add package dependency with the following URL:
https://github.com/apphud/ApphudSDK
Copy all files from ApphudSDK
folder to your project from this link.
Integration process consists of following parts:
To initialize Apphud SDK you will need SDK Token. It is a unique identifier of your Apphud application. You can get it in your Apphud application settings under General
tab.
Basic initialization looks like this:
import ApphudSDKfunc application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {Apphud.start(apiKey: "YOUR_API_KEY")// the rest of your codereturn true}
#import <ApphudSDK-Swift.h>- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {// set observerMode to YES if you are running SDK in Observer (Analytics) mode.// set your custom userID or nil to let Apphud automatically generate User ID (recommended)[Apphud startWithApiKey:@"YOUR_API_KEY" userID:@"CUSTOM_USER_ID_OR_NIL" observerMode:NO];// the rest of your codereturn YES;}
There are additional parameters, like setting your custom unique User ID or running the SDK in observer mode:
Apphud.start(apiKey: "API_KEY", userID: "CUSTOM_USER_ID", observerMode: true)
[Apphud startWithApiKey:@"API_KEY" userID:@"CUSTOM_USER_ID" observerMode:NO];
When observerMode
is true
, Apphud SDK will not finish transactions automatically and will only listen for purchases. If you handle payments by your own code, then set true
. Otherwise, if you purchase products using Apphud.purchase(product){}
method, then you should set observerMode
parameter to false
. Default value is false
.
You can also initialize SDK with custom Device ID. This should be used if you plan to use logout / login features. You can pass the same identifier to Device ID and User ID:
Apphud.startManually(apiKey: "YOUR_API_KEY", userID: "SOME_USER_ID", deviceID: "SOME_USER_ID")
Log out method will clear all saved data and reset SDK to uninitialised state:
// log out:Apphud.logout()// then start Apphud SDK again:Apphud.startManually(apiKey: "YOUR_API_KEY", userID: "ANOTHER_USER_ID", deviceID: "ANOTHER_USER_ID")
Configuring push notifications is highly recommended in order to use Rules – a powerful feature that lets you increase your app revenue by automatically offering a discount to a user at the specified moment.
If you have a live app and already implemented purchasing logic, it's not necessary to rewrite your purchase code with Apphud methods. Apphud SDK will still automatically track all purchases in your app.
Apphud SDK provides a set of methods to manage subscriptions and non-renewing purchases. All these methods can be used regardless of how you purchased the product (via Apphud SDK or your existing code).
Apphud automatically fetches SKProduct
objects upon launch. Make sure products identifiers are added in Apphud products. To get your products call:
Apphud.products()
[Apphud products];
When products are fetched from the App Store you will also receive a notification from Notification Center along with Apphud delegate method call and a callback block, if set. So use whatever you want.
You can also force refresh products by calling refreshStoreKitProducts
method. See Apphud.swift
file for details. Use this method only as a fallback.
To make a purchase call:
Apphud.purchase(product) { result inif let subscription = result.subscription, subscription.isActive(){// has active subscription} else if let purchase = result.nonRenewingPurchase, purchase.isActive(){// has active non-renewing purchase} else {// handle error or check transaction status.}}
[Apphud purchase:product callback:^(ApphudPurchaseResult * result) {if (result.subcription.isActive){// has active subscription} else if (result.nonRenewingPurchase.isActive){// has active non-renewing purchase} else {// handle error or check transaction status}}];
This method will return an ApphudPurchaseResult
object, which contains subscription model with all info about your subscription. ApphudPurchaseResult
may also contain transaction
, error
and nonRenewingPurchase
objects in case user purchased non-renewing purchase. See ApphudPurchaseResult.swift
and ApphudSubscription.swift
files for details.
You can also read In-App Purchase Testing Tips.
Apphud.hasActiveSubscription()
[Apphud hasActiveSubscription];
Returns true
if user has active subscription. Use this method to determine whether to unlock premium functionality to the user.
To get subscription object (which contains expiration date, autorenewal status, etc.) use the following method:
Apphud.subscription()
[Apphud subscription];
See ApphudSubscription.swift
file for details.
Use this method to check whether the user has purchased in-app purchase and it's not refunded. Returns false
if was never purchased or is refunded.
Apphud.isNonRenewingPurchaseActive(productIdentifier: "productID")
[Apphud isNonRenewingPurchaseActiveWithProductIdentifier:@"producID"];
To get non-renewing purchases, which contain purchase date, product identifier and cancellation date, use the following method:
Apphud.nonRenewingPurchases()
[Apphud nonRenewingPurchases];
It will return array of all non-renewing in-app purchases user has ever purchased. In-app purchases are sorted by purchase date.
If your app doesn't have a login system, which identifies a premium user by his credentials, then you need a "restore" mechanism. If you already have a "restore purchases" mechanism by calling SKPaymentQueue.default().restoreCompletedTransactions()
, then you have nothing to worry about: Apphud SDK will automatically intercept and send the latest App Store Receipt to Apphud servers when your restoration is completed. However, better to call our restore method from SDK:
Apphud.restorePurchases{ subscriptions, purchases, error inif Apphud.hasActiveSubscription(){// has active subscription} else {// no active subscription found, check non-renewing purchases or error}}
[Apphud restorePurchasesWithCallback:^(NSArray<ApphudSubscription *> * _Nullable subscriptions, NSArray *purchases, NSError * _Nullable error) {if (Apphud.hasActiveSubscription){// has active subscription} else {// no active subscription found, check non-renewing purchases or error}}];
Basically it just sends App Store Receipt to Apphud and returns subscriptions (or nil
, if subscriptions are never purchased), non-renewing purchases (or nil
, if there are no any) and an optional error.
Do not get confused with Promotional Offers! Promoted in-app purchases are the ones that appear in the App Store page.
If you have in-app purchases that can be purchased directly from the App Store, you should implement a logic to continue a payment in the app.
To continue an in-app purchase transaction initiated from the App Store page, please implement the following ApphudDelegate
method:
func apphudShouldStartAppStoreDirectPurchase(_ product: SKProduct) -> ((ApphudPurchaseResult) -> Void) {// manage your UI here, show a progress hud, etc.let callback : ((ApphudPurchaseResult) -> Void) = { result in// check the result, hide a progress hud, etc.}return callback}
- (void (^)(ApphudPurchaseResult * _Nonnull))apphudShouldStartAppStoreDirectPurchase:(SKProduct *)product {// manage your UI here, show a progress hud, etc.return ^(ApphudPurchaseResult * _Nonnull result) {// check the result, hide a progress hud, etc.};}
You must return a callback block which will be called when a payment is finished. If you don't implement this method or return nil
then a payment will not start; you can also save the product and return nil to initiate a payment later by yourself. You can also read Apple documentation for details.
If you already have a live app with paying users and you want Apphud to track their subscriptions and non-renewing purchases, you should import their App Store receipts into Apphud. Apphud SDK doesn't automatically submit App Store receipts of your existing paying users. Run this code at launch of your app:
// hasPurchases - is your own boolean value indicating that current user is paying user.if hasPurchases {Apphud.migratePurchasesIfNeeded {_, _, _ in}}
Some integrations require you to match user ids between Apphud and corresponding integration. Please see documentation for your integration for details.
To test integrations, ensure that test credentials are provided and make a sandbox in-app purchase.
Starting iOS 14 you can reset your trial eligibility in iOS Settings > App Store
Apphud will send all subscription events of current user to your test analytics, if test credentials are set in integration settings.
Sandbox events will never be sent to your production integrations. If test credentials are not provided, sandbox events will not be sent anywhere.
You can also click on "Send Test Event" near the integration's "..." button. This feature is available only for some Integrations.
Set custom User Properties (or User Attributes) through iOS SDK. These attributes will be displayed in Apphud User Page and can be segmented in charts and filters. For example, you can view revenue or MRR chart segmented by your own user attribute.
You can increment existing user attributes (with integer or floating values) or set attribute just once, so it will not be overwritten.
Here are some usage examples:
Apphud.setUserProperty(key: .email, value: "user4@example.com", setOnce: true)Apphud.setUserProperty(key: .age, value: 31)Apphud.setUserProperty(key: .init("custom_test_property_1"), value: true)Apphud.setUserProperty(key: .gender, value: "gay")Apphud.setUserProperty(key: .init("custom_email"), value: "user2@example.com", setOnce: true)Apphud.incrementUserProperty(key: .age, by: 1)Apphud.incrementUserProperty(key: .init("progress"), by: 0.5)
[Apphud setUserPropertyWithKey:[ApphudUserPropertyKey email] value:@"user@example.com" setOnce:YES];[Apphud setUserPropertyWithKey:[ApphudUserPropertyKey age] value:@25 setOnce:false];[Apphud setUserPropertyWithKey:[[ApphudUserPropertyKey alloc] init:@"custom_property"] value:@"test" setOnce:false];[Apphud incrementUserPropertyWithKey:[[ApphudUserPropertyKey alloc] init:@"coins_count"] by:@5];
Value must be one of: Int
, Float
, Double
, Bool
, String
, NSNumber
, NSString
, NSNull
, nil
.
Key must be 30 characters maximum.
Each user may have maximum 50 attributes.
You can read more about eligibility testing here.
You can use Apphud to determine if user is eligible for introductory offer:
// Check eligibility for introductory offerApphud.checkEligibilityForIntroductoryOffer(product: myProduct) { result in// handle result}// Check eligibility for multiple products at one callApphud.checkEligibilitiesForIntroductoryOffers(products: products) { resultDict in// handle result}
// Check eligibility for introductory offer[Apphud checkEligibilityForIntroductoryOfferWithProduct:myProduct callback:^(BOOL eligible) {// handle result}];// Check eligibility for multiple products at one call[Apphud checkEligibilitiesForIntroductoryOffersWithProducts:productsArray callback:^(NSDictionary * resultDict) {// handle result}];
You can read more about eligibility testing here.
You can also use Apphud to determine if user is eligible for promotional offer:
// Check eligibility for promotional offerApphud.checkEligibilityForPromotionalOffer(product: myProduct) { result in// handle result}// Check eligibility for multiple products at one callApphud.checkEligibilitiesForPromotionalOffers(products: products) { resultDict in// handle result}