Skip to content

Instantly share code, notes, and snippets.

@bfinamore
Created January 2, 2019 04:00
Show Gist options
  • Save bfinamore/a5e5c2f94861b7d49ee5f05f91223ae0 to your computer and use it in GitHub Desktop.
Save bfinamore/a5e5c2f94861b7d49ee5f05f91223ae0 to your computer and use it in GitHub Desktop.
AppDelegate.m:
///////////////////////////////
// Reports app open from deep link from apps which do not support Universal Links (Twitter) and for iOS8 and below
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation {
[[AppsFlyerTracker sharedTracker] handleOpenURL:url sourceApplication:sourceApplication withAnnotation:annotation];
[[FBSDKApplicationDelegate sharedInstance] application:application
openURL:url
sourceApplication:sourceApplication
annotation:annotation];
return [RCTLinkingManager application:application openURL:url
sourceApplication:sourceApplication annotation:annotation];
}
// Reports app open from URL Scheme deep link for iOS 10
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url
options:(NSDictionary *) options {
[[AppsFlyerTracker sharedTracker] handleOpenUrl:url options:options];
return [RCTLinkingManager application:application openURL:url options:options];
}
//Universal Links
- (BOOL)application:(UIApplication *)application continueUserActivity:(NSUserActivity *)userActivity restorationHandler:(void (^)(NSArray *restorableObjects))restorationHandler {
[[AppsFlyerTracker sharedTracker] continueUserActivity:userActivity restorationHandler:restorationHandler];
return [RCTLinkingManager application:application
continueUserActivity:userActivity
restorationHandler:restorationHandler];
}
////////////////////////////////////
main.js:
///////////////////////////////////
class AppContainer extends PureComponent {
handleAppStateChange = (nextAppState) => {
if (this.state.appState.match(/inactive|background/) && nextAppState === 'active') {
if (Platform.OS === 'ios') {
AppsFlyer.trackAppLaunch(); //only gets called on bg -> fg, not new launch. initSdk() appears to call it though
}
}
if (this.state.appState.match(/active|foreground/) && nextAppState === 'background') {
// if(this.removeConversionListener){ //removed this because we want to continue listening for deeplinks in bg, right?
// console.log('[AppsFlyer] removing install listener');
// this.removeConversionListener();
// }
}
this.setState({appState: nextAppState});
};
async componentDidMount() {
AppState.addEventListener('change', this.handleAppStateChange);
//AppsFlyer init
console.log('[AppsFlyer] [main] componentDidMount');
this.removeConversionListener = AppsFlyer.onInstallConversionData(
data => {
const oneLink = data.data.link;
const appLink = data.data.af_dp; //AppsFlyer's predefined param for passing deeplink
console.log('[AppsFlyer] [main] onInstallConversionData type: '+data.type);
console.log('[AppsFlyer] [main] onInstallConversionData payload: '+JSON.stringify(data));
console.log('[AppsFlyer] [main] OneLink: '+oneLink);
console.log('[AppsFlyer] [main] [af_dp]: '+appLink); // myapp://foo/bar
if(data.type === 'onAppOpenAttribution'){
if(oneLink){
if(Platform.OS === 'android'){
console.log('[AppsFlyer] [main] sending android deeplink data: '+oneLink);
AppsFlyer.sendDeepLinkData(oneLink);
}
}
if(appLink){
console.log('[AppsFlyer] [main] ***handling app deeplink for onAppOpenAttribution');
handleAppUrl(appLink, store.dispatch, 0); //re-direct user to deeplink destination
}
}
}
);
console.log('[AppsFlyer] [main] calling init');
AppsFlyer.initSdk();
//this gets called back on every deeplink as well, but it's currently not handling anything
Linking.addEventListener('url', ({ url }) => {
console.log('[AppsFlyer] [main] Linking listener callback: '+url);
});
}
componentWillUnmount() {
console.log('[AppsFlyer] [main] componentWillUnmount');
if(this.removeConversionListener){
console.log('[AppsFlyer] [main] removing conversion listener in WillUnmount');
this.removeConversionListener();
}
AppState.removeEventListener('change', this.handleAppStateChange);
}
...
////////////
* Log Outputs *
///////////
Case A:
1. Organic app launch- no deeplink (LOOKS CORRECT)
///////////
[AppsFlyer] [main] calling onInstallConversionData
[AppsFlyer] [main] calling init
[AppsFlyerUtil] init result: Success
[AppsFlyer] state change from: unknown to: unknown
[AppsFlyer] state change from: unknown to: active
[AppsFlyer] [main] onInstallConversionData type: onInstallConversionDataLoaded
[AppsFlyer] [main] onInstallConversionData payload: {"status":"success","type":"onInstallConversionDataLoaded","data":{"click_time":"2018-12-27 02:25:33.728","orig_cost":"0.0","cost_cents_USD":"0","is_first_launch":false,"campaign":"test_install_4","af_click_lookback":"7d","af_dp":"myapp://","shortlink":"12345","media_source":"Test","install_time":"2018-12-27 02:29:20.251","af_status":"Non-organic"}}
///////////
Case B: Fresh app launch from deeplink - app not running (LOOKS BROKEN)
1. Fresh launch from deeplink
2. Only the onInstallConversionDataLoaded type fires
3. Background the app, then foreground
4. Both the onInstallConversionDataLoaded and onAppOpenAttribution fires
///////////
[main] calling onInstallConversionData
[AppsFlyer] [main] calling init
[AppsFlyer] [main] found deeplink: https://myapp.onelink.me/YNmb/1234
[AppsFlyerUtil] init result: Success
[AppsFlyer] state change from: unknown to: unknown
[AppsFlyer] state change from: unknown to: active
[AppsFlyer] [main] onInstallConversionData type: onInstallConversionDataLoaded
[AppsFlyer] [main] onInstallConversionData payload: {"status":"success","type":"onInstallConversionDataLoaded","data":{"click_time":"2018-12-27 02:25:33.728","install_time":"2018-12-27 02:29:20.251","cost_cents_USD":"0","is_first_launch":false,"campaign":"test_install_4","af_click_lookback":"7d","af_dp":"myapp://","af_status":"Non-organic","media_source":"Test","orig_cost":"0.0","shortlink":"1234"}}
[AppsFlyer] state change from: active to: inactive
[AppsFlyer] state change from: inactive to: background //backgrounded app
[AppsFlyer] state change from: background to: active //foregrounded app
[AppsFlyerUtil] calling trackAppLaunch() //called on bg -> fg, not fresh launch
[AppsFlyer] [main] onInstallConversionData type: onInstallConversionDataLoaded
[AppsFlyer] [main] onInstallConversionData payload: {"status":"success","type":"onInstallConversionDataLoaded","data":{"click_time":"2018-12-27 02:25:33.728","install_time":"2018-12-27 02:29:20.251","cost_cents_USD":"0","is_first_launch":false,"campaign":"test_install_4","af_click_lookback":"7d","af_dp":"myapp://","af_status":"Non-organic","media_source":"Test","orig_cost":"0.0","shortlink":"1234"}}
[AppsFlyer] [main] onInstallConversionData type: onAppOpenAttribution
[AppsFlyer] [main] onInstallConversionData payload: {"status":"success","type":"onAppOpenAttribution","data":{"af_dp":"myapp://feature/detail","is_retargeting":"true","c":"test_retarget_4","pid":"Email","link":"https://myapp.onelink.me/YNmb/1234"}}
[AppsFlyer] [main] [af_dp]: myapp://feature/airport
AppsFlyer] [main] ***handling app deeplink for onAppOpenAttribution
...
///////////
Case C: Foreground the (running) app from deeplink (LOOKS CORRECT)
///////////
[AppsFlyer] [main] Linking listener callback: https://myapp.onelink.me/YNmb/1234
[AppsFlyer] state change from: background to: active
[AppsFlyerUtil] calling trackAppLaunch()
[AppsFlyer] [main] onInstallConversionData type: onInstallConversionDataLoaded
[AppsFlyer] [main] onInstallConversionData payload: {"status":"success","type":"onInstallConversionDataLoaded","data":{"click_time":"2018-12-27 02:25:33.728","install_time":"2018-12-27 02:29:20.251","cost_cents_USD":"0","is_first_launch":false,"campaign":"test_install_4","af_click_lookback":"7d","af_dp":"myapp://","af_status":"Non-organic","media_source":"Test","orig_cost":"0.0","shortlink":"1234"}}
[AppsFlyer] [main] onInstallConversionData type: onAppOpenAttribution
[AppsFlyer] [main] onInstallConversionData payload: {"status":"success","type":"onAppOpenAttribution","data":{"af_dp":"myapp://feature/airport","is_retargeting":"true","c":"test_retarget_4","pid":"Email","link":"https://myapp.onelink.me/YNmb/1234"}}
main.js:203 [AppsFlyer] [main] [af_dp]: myapp://feature/detail
main.js:206 [AppsFlyer] [main] ***handling app deeplink for onAppOpenAttribution
...
////////////
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment