{"id":908,"date":"2026-04-25T17:00:00","date_gmt":"2026-04-25T22:00:00","guid":{"rendered":"https:\/\/tolinku.com\/blog\/?p=908"},"modified":"2026-03-07T03:48:35","modified_gmt":"2026-03-07T08:48:35","slug":"cross-platform-sdk-integration","status":"publish","type":"post","link":"https:\/\/tolinku.com\/blog\/cross-platform-sdk-integration\/","title":{"rendered":"Cross-Platform SDK Integration for Deep Linking"},"content":{"rendered":"\n<p>Cross-platform frameworks add a layer between your app code and the native platform. Deep linking SDKs need to bridge this gap: the native OS delivers the URL, the SDK processes it, and the result reaches your JavaScript, Dart, or TypeScript code. This guide covers SDK integration patterns for the major cross-platform frameworks.<\/p>\n\n\n\n<p>For framework-specific deep linking setup (without an SDK), see <a href=\"https:\/\/tolinku.com\/blog\/react-native-deep-linking-setup\/\">React Native Deep Linking<\/a> and <a href=\"https:\/\/tolinku.com\/blog\/flutter-deep-linking-setup\/\">Flutter Deep Linking<\/a>. For the SDK feature comparison, see <a href=\"https:\/\/tolinku.com\/blog\/deferred-deep-linking-sdks-comparison\/\">Deferred Deep Linking SDKs: Feature Comparison<\/a>.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Why Use an SDK<\/h2>\n\n\n\n<p>You can implement basic deep linking without any SDK. The OS delivers the URL, and your router handles it. An SDK adds value when you need:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>Deferred deep linking<\/strong>: Matching a link click to an app install that happens later. This requires server-side fingerprinting that you can&#39;t build into a URL alone.<\/li>\n<li><strong>Attribution<\/strong>: Knowing which link, campaign, or channel led to an install or conversion.<\/li>\n<li><strong>Link creation<\/strong>: Generating short links programmatically from within the app.<\/li>\n<li><strong>Analytics<\/strong>: Click counts, conversion rates, and device breakdown for your links.<\/li>\n<\/ul>\n\n\n\n<p>If you only need direct deep linking (app is installed, user taps link, app opens to the right screen), the platform&#39;s built-in linking APIs are sufficient. No SDK required.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">React Native Integration<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\">Installation<\/h3>\n\n\n\n<pre><code class=\"language-bash\">npm install @tolinku\/react-native-sdk\n# or\nyarn add @tolinku\/react-native-sdk\n\ncd ios &amp;&amp; pod install\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Initialization<\/h3>\n\n\n\n<pre><code class=\"language-javascript\">import { Tolinku } from &#39;@tolinku\/react-native-sdk&#39;;\n\n\/\/ Initialize early in your app&#39;s entry point\nTolinku.init({\n  apiKey: &#39;tolk_pub_your_publishable_key&#39;,\n});\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Deferred Deep Link Handling<\/h3>\n\n\n\n<pre><code class=\"language-javascript\">import { Tolinku } from &#39;@tolinku\/react-native-sdk&#39;;\n\nuseEffect(() =&gt; {\n  \/\/ Check for deferred deep link on first launch\n  Tolinku.checkDeferredLink().then((result) =&gt; {\n    if (result) {\n      navigation.navigate(result.screen, result.params);\n    }\n  });\n}, []);\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Link Creation<\/h3>\n\n\n\n<pre><code class=\"language-javascript\">const link = await Tolinku.createLink({\n  path: &#39;\/invite\/&#39; + userId,\n  campaign: &#39;referral&#39;,\n  ogTitle: &#39;Join me on the app&#39;,\n  ogDescription: &#39;Use my referral link to get started&#39;,\n});\n\/\/ link.url = &quot;https:\/\/go.yourapp.com\/abc123&quot;\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Native Setup<\/h3>\n\n\n\n<p>The React Native SDK still requires the same native configuration as manual deep linking:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>iOS<\/strong>: Associated Domains entitlement, AppDelegate <code>continueUserActivity<\/code> handler<\/li>\n<li><strong>Android<\/strong>: Intent filters with <code>autoVerify<\/code>, Digital Asset Links file<\/li>\n<\/ul>\n\n\n\n<p>The SDK doesn&#39;t replace this configuration; it adds deferred linking and analytics on top of it.<\/p>\n\n\n\n<p>See the <a href=\"https:\/\/tolinku.com\/docs\/developer\/sdks\/react-native\/\">React Native SDK docs<\/a> for the full API reference.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Flutter Integration<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\">Installation<\/h3>\n\n\n\n<pre><code class=\"language-yaml\"># pubspec.yaml\ndependencies:\n  tolinku: ^1.0.0\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Initialization<\/h3>\n\n\n\n<pre><code class=\"language-dart\">import &#39;package:tolinku\/tolinku.dart&#39;;\n\nvoid main() {\n  Tolinku.init(apiKey: &#39;tolk_pub_your_publishable_key&#39;);\n  runApp(MyApp());\n}\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Deferred Deep Link Handling<\/h3>\n\n\n\n<pre><code class=\"language-dart\">import &#39;package:tolinku\/tolinku.dart&#39;;\n\nclass _MyAppState extends State&lt;MyApp&gt; {\n  @override\n  void initState() {\n    super.initState();\n    _checkDeferredLink();\n  }\n\n  Future&lt;void&gt; _checkDeferredLink() async {\n    final result = await Tolinku.checkDeferredLink();\n    if (result != null) {\n      router.go(result.path);\n    }\n  }\n}\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Link Creation<\/h3>\n\n\n\n<pre><code class=\"language-dart\">final link = await Tolinku.createLink(\n  path: &#39;\/invite\/$userId&#39;,\n  campaign: &#39;referral&#39;,\n  ogTitle: &#39;Join me on the app&#39;,\n  ogDescription: &#39;Use my referral link to get started&#39;,\n);\n\/\/ link.url = &quot;https:\/\/go.yourapp.com\/abc123&quot;\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Native Setup<\/h3>\n\n\n\n<p>Same as React Native: the Flutter SDK requires Associated Domains (iOS) and intent filters (Android) to be configured in the native project.<\/p>\n\n\n\n<p>See the <a href=\"https:\/\/tolinku.com\/docs\/developer\/sdks\/flutter\/\">Flutter SDK docs<\/a> for the full API reference.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Capacitor \/ Ionic Integration<\/h2>\n\n\n\n<p>Capacitor apps use the <code>@capacitor\/app<\/code> plugin to receive deep links, similar to React Native&#39;s Linking module.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Configuration<\/h3>\n\n\n\n<pre><code class=\"language-typescript\">\/\/ capacitor.config.ts\nconst config: CapacitorConfig = {\n  appId: &#39;com.yourapp&#39;,\n  plugins: {\n    App: {\n      \/\/ Deep linking configuration\n    },\n  },\n};\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">iOS Setup<\/h3>\n\n\n\n<p>Add Associated Domains in Xcode (same as native iOS or React Native).<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Android Setup<\/h3>\n\n\n\n<p>Add intent filters to <code>AndroidManifest.xml<\/code> (same as native Android).<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Link Handling<\/h3>\n\n\n\n<pre><code class=\"language-typescript\">import { App } from &#39;@capacitor\/app&#39;;\n\nApp.addListener(&#39;appUrlOpen&#39;, (event) =&gt; {\n  const url = new URL(event.url);\n  const path = url.pathname;\n  const params = Object.fromEntries(url.searchParams);\n\n  \/\/ Route to the correct page\n  router.navigateByUrl(path);\n});\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Using Tolinku Web SDK in Capacitor<\/h3>\n\n\n\n<p>Since Capacitor runs a web view, you can use the Tolinku Web SDK for analytics and link creation:<\/p>\n\n\n\n<pre><code class=\"language-typescript\">import { Tolinku } from &#39;@tolinku\/web-sdk&#39;;\n\nTolinku.init({ apiKey: &#39;tolk_pub_your_publishable_key&#39; });\n\n\/\/ Create a link\nconst link = await Tolinku.createLink({\n  path: &#39;\/invite\/&#39; + userId,\n});\n<\/code><\/pre>\n\n\n\n<p>For deferred deep linking in Capacitor, combine the native deep link listener with a server-side check:<\/p>\n\n\n\n<pre><code class=\"language-typescript\">App.addListener(&#39;appUrlOpen&#39;, async (event) =&gt; {\n  \/\/ Handle direct deep links\n  handleDeepLink(event.url);\n});\n\n\/\/ On first launch, check for deferred link\nconst deferred = await fetch(&#39;https:\/\/api.tolinku.com\/v1\/deferred-link&#39;, {\n  method: &#39;POST&#39;,\n  headers: { &#39;x-api-key&#39;: &#39;tolk_pub_your_key&#39; },\n  body: JSON.stringify({ fingerprint: getDeviceFingerprint() }),\n});\n<\/code><\/pre>\n\n\n\n<h2 class=\"wp-block-heading\">Integration Architecture<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\">Where the SDK Fits<\/h3>\n\n\n\n<pre><code>User taps link\n    \u2502\n    \u25bc\nOS receives URL \u2192 checks App Links \/ Universal Links\n    \u2502\n    \u25bc\nApp launches (or comes to foreground)\n    \u2502\n    \u25bc\nNative layer receives URL\n    \u2502\n    \u25bc\nSDK processes URL:\n  - Records click event\n  - Extracts parameters\n  - Checks for deferred link (first launch only)\n    \u2502\n    \u25bc\nCross-platform bridge (React Native bridge \/ Flutter platform channel)\n    \u2502\n    \u25bc\nYour JavaScript\/Dart code receives parsed result\n    \u2502\n    \u25bc\nRouter navigates to the correct screen\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">What the SDK Handles<\/h3>\n\n\n\n<figure class=\"wp-block-table\"><table>\n<thead>\n<tr>\n<th>Capability<\/th>\n<th>Without SDK<\/th>\n<th>With SDK<\/th>\n<\/tr>\n<\/thead>\n<tbody><tr>\n<td>Direct deep links<\/td>\n<td>Yes (built-in)<\/td>\n<td>Yes<\/td>\n<\/tr>\n<tr>\n<td>URL parsing<\/td>\n<td>Manual<\/td>\n<td>Automatic<\/td>\n<\/tr>\n<tr>\n<td>Deferred deep links<\/td>\n<td>No<\/td>\n<td>Yes<\/td>\n<\/tr>\n<tr>\n<td>Link creation<\/td>\n<td>Manual API calls<\/td>\n<td>SDK method<\/td>\n<\/tr>\n<tr>\n<td>Click analytics<\/td>\n<td>No<\/td>\n<td>Automatic<\/td>\n<\/tr>\n<tr>\n<td>Attribution<\/td>\n<td>No<\/td>\n<td>Automatic<\/td>\n<\/tr>\n<tr>\n<td>Fingerprinting<\/td>\n<td>No<\/td>\n<td>Built-in<\/td>\n<\/tr>\n<\/tbody><\/table><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\">Best Practices<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\">Initialize Early<\/h3>\n\n\n\n<p>Initialize the SDK before your app&#39;s navigation is ready. The deferred deep link check should happen before the user sees the home screen, so they&#39;re routed directly to the intended content.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Don&#39;t Block the UI<\/h3>\n\n\n\n<p>The deferred deep link check makes a network request. Show a splash or loading screen while the check runs, but set a timeout (2-3 seconds) to ensure the app isn&#39;t stuck waiting.<\/p>\n\n\n\n<pre><code class=\"language-javascript\">\/\/ React Native example with timeout\nconst result = await Promise.race([\n  Tolinku.checkDeferredLink(),\n  new Promise(resolve =&gt; setTimeout(() =&gt; resolve(null), 3000)),\n]);\n<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Test on Physical Devices<\/h3>\n\n\n\n<p>SDK features like deferred deep linking rely on device fingerprinting (IP address, user agent, device model). These signals are different in simulators and emulators. Always test on physical devices.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Handle Both Direct and Deferred<\/h3>\n\n\n\n<p>Your routing code should handle links from both sources:<\/p>\n\n\n\n<pre><code class=\"language-javascript\">function handleLink(result) {\n  if (result.path.startsWith(&#39;\/product\/&#39;)) {\n    navigation.navigate(&#39;Product&#39;, { id: result.params.id });\n  } else if (result.path.startsWith(&#39;\/invite\/&#39;)) {\n    navigation.navigate(&#39;Invite&#39;, { code: result.params.code });\n  }\n}\n\n\/\/ Direct deep links\nLinking.addEventListener(&#39;url&#39;, ({ url }) =&gt; {\n  handleLink(parseUrl(url));\n});\n\n\/\/ Deferred deep links\nTolinku.checkDeferredLink().then((result) =&gt; {\n  if (result) handleLink(result);\n});\n<\/code><\/pre>\n\n\n\n<p>The same routing function handles both cases. This keeps your code DRY and ensures consistent behavior.<\/p>\n\n\n\n<p>For the SDK swap process, see <a href=\"https:\/\/tolinku.com\/blog\/sdk-swap-guide\/\">SDK Swap Guide<\/a>. For all SDK documentation, see <a href=\"https:\/\/tolinku.com\/docs\/developer\/sdks\/\">Tolinku SDK docs<\/a>. For deep linking features, see <a href=\"https:\/\/tolinku.com\/features\/deep-linking\">Tolinku deep linking<\/a>.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Integrate the Tolinku SDK in cross-platform apps. Setup guides for React Native, Flutter, Capacitor, and other hybrid frameworks.<\/p>\n","protected":false},"author":2,"featured_media":907,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"rank_math_title":"Cross-Platform SDK Integration for Deep Linking","rank_math_description":"Integrate the Tolinku SDK in cross-platform apps. Setup guides for React Native, Flutter, Capacitor, and other hybrid frameworks.","rank_math_focus_keyword":"cross-platform SDK integration","rank_math_canonical_url":"","rank_math_facebook_title":"","rank_math_facebook_description":"","rank_math_facebook_image":"https:\/\/tolinku.com\/blog\/wp-content\/uploads\/2026\/03\/og-cross-platform-sdk-integration.png","rank_math_facebook_image_id":"","rank_math_twitter_title":"","rank_math_twitter_description":"","rank_math_twitter_image":"https:\/\/tolinku.com\/blog\/wp-content\/uploads\/2026\/03\/og-cross-platform-sdk-integration.png","footnotes":""},"categories":[15],"tags":[187,156,20,57,188,69,56,186],"class_list":["post-908","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-engineering","tag-capacitor","tag-cross-platform","tag-deep-linking","tag-flutter","tag-integration","tag-mobile-development","tag-react-native","tag-sdk"],"_links":{"self":[{"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/posts\/908","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/comments?post=908"}],"version-history":[{"count":1,"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/posts\/908\/revisions"}],"predecessor-version":[{"id":909,"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/posts\/908\/revisions\/909"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/media\/907"}],"wp:attachment":[{"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/media?parent=908"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/categories?post=908"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/tolinku.com\/blog\/wp-json\/wp\/v2\/tags?post=908"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}