Welcome to the ultimate guide for setting up deep links, deferred deep links, and user invites in your React Native app using AppsFlyer. Buckle up! This blog will walk you through everything—from SDK setup to sending users on magical journeys inside your app with a single click (or tap—we don't discriminate here).
📦 Step 1: Install the AppsFlyer SDK
Like every React Native adventure, we start in the terminal.
yarn add react-native-appsflyer
Step 2: Login to AppsFlyer Dashboard
Before anything, make sure you're logged into your AppsFlyer account. Don’t remember your password? Welcome to the club. Reset it and move on
Step 3: SDK Initialization
In your App.js
or main screen
(e.g., Home.js), call the initialization:
useEffect(() => {
setupDeepLinkListeners();
initAppflyerSDK();
}, []);
And define the initAppflyerSDK function like this:
import appsFlyer from 'react-native-appsflyer';
import { Platform } from 'react-native';
export const initAppflyerSDK = () => {
try {
appsFlyer.initSdk(
{
devKey: 'K2***********99', // Replace with your dev key
isDebug: false,
appId: '41*****44', // iOS only
onInstallConversionDataListener: true,
onDeepLinkListener: true,
timeToWaitForATTUserAuthorization: 10,
},
(result) => {
console.log('🚀 AppsFlyer SDK initialized successfully:', result);
},
(error) => {
console.error('❌ Error initializing AppsFlyer SDK:', error);
}
);
} catch (error) {
console.error('❌ Error initializing AppFlyer SDK:', error);
}
};
Handle Deep Links (Direct & Deferred)
Now we plug in the listeners:
export const setupDeepLinkListeners = () => {
try {
// Direct Deep Link
appsFlyer.onDeepLink((res) => {
console.log('📩 Direct Deep Link received:', res);
// Navigate your user here!
});
// Deferred Deep Link (First Install)
appsFlyer.onInstallConversionData((res) => {
console.log('🕰 Deferred Deep Link:', res);
// Handle navigation based on your use case
});
} catch (error) {
console.error('❌ Error setting up deep link listeners:', error);
}
};
Custom Domains
If you're fancy and have custom domains, add this:
appsFlyer.setOneLinkCustomDomains(
['YOUR_CUSTOM_DOMAIN1', 'YOUR_CUSTOM_DOMAIN2'],
(success) => {
console.log("Custom domains set successfully!", success);
},
(error) => {
console.error("Failed to set custom domains:", error);
}
);
iOS Setup (Don’t Skip This or Cry Later)
Update your AppDelegate.m (Objective-C):
#import <RNAppsFlyer.h>
// For iOS 9+
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url options:(NSDictionary *) options {
[[AppsFlyerAttribution shared] handleOpenUrl:url options:options];
return YES;
}
// For iOS 8 and below
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString*)sourceApplication annotation:(id)annotation {
[[AppsFlyerAttribution shared] handleOpenUrl:url sourceApplication:sourceApplication annotation:annotation];
return YES;
}
// Universal Links
- (BOOL)application:(UIApplication *)application continueUserActivity:(NSUserActivity *)userActivity restorationHandler:(void (^)(NSArray * _Nullable))restorationHandler {
[[AppsFlyerAttribution shared] continueUserActivity:userActivity restorationHandler:restorationHandler];
return YES;
}
Swift Config
For Swift projects, update your AppDelegate
with the following methods:
import AppsFlyerLib
// MARK: - AppsFlyer Deeplink Handling
// Deep linking - Open URI-scheme for iOS 9 and above
func application(
_ application: UIApplication,
open url: URL,
options: [UIApplication.OpenURLOptionsKey: Any] = [:]
) -> Bool {
AppsFlyerAttribution.shared().handleOpen(url, options: options)
return true
}
// Deep linking - Open URI-scheme for iOS 8 and below
func application(
_ application: UIApplication,
open url: URL,
sourceApplication: String?,
annotation: Any
) -> Bool {
AppsFlyerAttribution.shared().handleOpen(url, sourceApplication: sourceApplication, withAnnotation: annotation)
return true
}
// Open Universal Links
func application(
_ application: UIApplication,
continue userActivity: NSUserActivity,
restorationHandler: @escaping ([UIUserActivityRestoring]?) -> Void
) -> Bool {
AppsFlyerAttribution.shared().continue(userActivity, restorationHandler: { (array: [Any]?) in
restorationHandler(array as? [UIUserActivityRestoring])
})
return true
}
Bridging Header (if using Swift)
Make sure your bridging header imports the AppsFlyer SDK:
// Use this file to import your target's public headers that you would like to expose to Swift.
#import <RNAppsFlyer.h>
Also, add this in your Associated Domains:
applinks:yourdeeplink.com
Android Deeplink Setup
AppsFlyer SDK inspects activity intent object during onResume()
. Because of that, for each activity that may be configured or launched with any non-standard launch mode please make sure to add the following code to MainActivity.java
in android/app/src/main/java/com...:
...
import android.content.Intent;
...
public class MainActivity extends ReactActivity {
...
@Override
public void onNewIntent(Intent intent) {
super.onNewIntent(intent);
setIntent(intent);
}
}
App Links
Update your AndroidManifest.xml:
<intent-filter android:autoVerify="true">
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data
android:host="yourdeeplink.com"
android:scheme="https" />
</intent-filter>
🧪 Testing:
Now let's start testing Because We All Make Mistakes 🧪
👉 If a Deeplink is not hosted (Android Only):
- For dev testing, go to App Info → Open by default → Supported web addresses → Toggle ON
Creating Your First Referral Deep Link: The Fun Part 🎨
Let's create a referral link (because sharing is caring):
- Open AppsFlyer dashboard
- Go to Home → Engage → OneLink Management
- Click "New Link" (it's like magic, but with more clicking)
- Select "referral-to-app" option
- Choose "User_invite" and click next
- Fill in the required fields (this is where you get creative)
- Under "Additional parameters", add your custom data:
- Parameter name: empId
- Parameter value: 123
- Add another for promotion: "ee"
- Click "Create Link" and voilà! You're now a deep link wizard 🧙♂️
Ensure that your referral link includes the query parameters
af_xp=referral
andpid=User_invite
; otherwise, the deferred deep link will not be recognized.If you're generating the link using the
User_Invite
option (Referral-app
), the required parameters will be automatically appended to the deep link, so there's no need to add them manually.
🧪 How to Test Deferred Deep Link
Testing deferred deep links can be tricky. The key thing to remember:
👉 Attribution SDKs only capture install attribution on a fresh install after a link click.
Follow these steps to test properly:
🔹 Step 1: Prepare Your Device
1 Uninstall the app from your device.
2 Click your deep link (e.g., referral/invite link).
3 Don’t install the app from the App/Play Store when redirected.
🔹 Step 2: Register Your Test Device in AppsFlyer
- Go to AppsFlyer Console → Settings → Test Devices.
- Click + Add device.
- Install the My Device ID app to get your unique device ID:
- iOS: My Device ID (App Store)
- Android: My Device ID (Google Play)
4 Fill in the form:
- Name: Unique identifier (use only English letters).
- OS: iOS or Android.
- Device ID type: Select IDFA (iOS) or AID (Android).
- Device ID: Paste the ID from the app.
5 Click Save.
⚠️ Your device appears immediately, but may take a few minutes to activate.
🔗 Ref: AppsFlyer Docs – Register a Test Device
🔹 Step 3: Run the App Manually
- After clicking the link, go back to your IDE (Android Studio or Xcode).
- Run the app manually from there (don’t install via store).
✅ Why This Works
This simulates a deferred deep link install by letting the attribution SDK capture data on first open after link click.
If you install via Play Store/App Store directly, attribution won’t work because debug/test builds aren’t tracked like real store installs.
✨ Done! You’ve now tested deferred deep linking in a dev-friendly way.
Tracking User Engagement
Want to track how many users clicked your link or installed the app because of it?
- Go to AppsFlyer Dashboard
- Click your App Icon
- Navigate to Campaign → Click
- Scroll to see click stats, conversions, and deep link data
You're now officially stalking—err, "analyzing"—your users 👀
Top comments (0)