deeplinking 1.0.1 copy "deeplinking: ^1.0.1" to clipboard
deeplinking: ^1.0.1 copied to clipboard

PlatformAndroid

A lightweight developer-first mobile attribution and deep linking SDK for Link Traker (FDL alternative) with multi-screen and multi-permission support.

deeplinking Flutter SDK #

A lightweight, developer-first, self-hosted Mobile Measurement Partner (MMP) and attribution package for Flutter. Connects app clicks to app installs, captures P2P referrals, supports multi-screen routing, and enforces granular per-screen permissions.

Features #

  • Deferred Deep Linking: 100% deterministic attribution via clipboard matching + probabilistic fingerprinting fallback.
  • Multiple Target Screens: Direct users to multiple accessible screens (screens / allowedScreens).
  • Granular Permissions: Global permissions (permissions) and per-screen capability scoping (screenPermissions).
  • P2P Referral Engine: Built-in reward crediting and FCM push sync for referrers and invitees.
  • Native Direct Intent Routing: Seamless handling for cold-start and warm-start deep link intents.

Installation #

Add deeplinking to your Flutter project's pubspec.yaml:

dependencies:
  deeplinking: ^1.0.1

And run:

flutter pub get

Getting Started #

1. Initialize the SDK #

Configure the SDK when your app starts (typically in lib/main.dart):

import 'package:flutter/material.dart';
import 'package:deeplinking/deeplinking.dart';

void main() {
  WidgetsFlutterBinding.ensureInitialized();
  
  // Configure with your server base URL, registered App ID, and Workspace SDK Key
  DeepLinking.configure(
    baseUrl: 'https://deeplinking.in',
    appId: 'com.example.store_room',
    sdkKey: 'dlk_live_xxxxxxxxxxxxxxxxxxxxxxxx',
  );

  runApp(const MyApp());
}

Usage Guide #

2. Auto-Attributing Installs (Deferred Deep Linking) #

When the app launches for the first time, check if the install originated from a tracking link. This will automatically read the click ID from the clipboard or fall back to IP-based fingerprinting.

void checkAttribution(BuildContext context) async {
  try {
    final result = await DeepLinking.trackInstall(
      linkId: 'FALLBACK_LINK_ID', // Used for fingerprint matching
      installerFcmToken: 'USER_FCM_TOKEN', // Send to enable push notifications
      installerUserId: 'USER_123', // User ID inside your system
    );

    if (result != null && result.success) {
      print('Successfully attributed install!');
      print('Method: ${result.method}'); // 'direct' or 'fingerprint'
      print('Referral Code: ${result.referralCode}');
      print('Target Screens: ${result.screens}');
      print('Granted Permissions: ${result.permissions}');
      print('Per-Screen Permissions: ${result.screenPermissions}');
      
      // Check if user is allowed to access a specific screen:
      if (result.allowsScreen('PromoScreen')) {
        Navigator.of(context).pushNamed('/promo');
      }

      // Check if user has a global or screen-specific permission:
      if (result.hasScreenPermission('ProductDetail', 'buy')) {
        // Enable direct purchase button
      }
    } else {
      print('Organic install / No attribution matches.');
    }
  } on SdkLimitExceededException catch (e) {
    ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(e.message)));
  } on InvalidSdkKeyException catch (e) {
    ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(e.message)));
  }
}

Generate personalized share links with multiple accessible screens and granular per-screen permissions:

void generateMultiScreenShare() async {
  try {
    final response = await DeepLinking.registerShare(
      linkId: 'PROMO_LINK_ID',
      screens: ['Catalog', 'ProductDetail', 'Cart'],
      permissions: ['read', 'comment', 'vip_access'],
      screenPermissions: {
        'ProductDetail': ['view_price', 'add_to_cart'],
        'Cart': ['apply_coupon'],
      },
      senderReferralCode: 'ALICE100',
      senderUserId: 'user_alice',
      productId: 'shoe_123',
    );

    final shareUrl = response['shareUrl'];
    print('Generated Share Link: $shareUrl');
  } catch (e) {
    print('Error registering share: $e');
  }
}

4. Branded URL Shortener & P2P Sharing #

Generate clean, branded short URLs (https://yourdomain.com/s/:code) instead of sharing long URLs with query parameters:

When registering a share with user referral codes, target screens, or permissions, registerShare automatically provisions a branded short link:

void shareReferralInvite() async {
  try {
    final response = await DeepLinking.registerShare(
      linkId: 'LINK_ID',
      senderReferralCode: 'ALICE100',
      senderUserId: 'user_123',
      senderFcmToken: 'USER_FCM_TOKEN',
      screen: 'ProductDetail',
    );

    // Clean, compact short link ready for WhatsApp / SMS:
    final shortUrl = response['shortUrl']; // e.g. https://deeplinking.in/s/7vNkoGn
    print('Share via WhatsApp: $shortUrl');
  } catch (e) {
    print('Error registering share: $e');
  }
}

Generate a branded short URL for any master tracking link, with an optional custom vanity alias or custom domain:

void generateShortLink() async {
  try {
    final response = await DeepLinking.shortenLink(
      linkId: 'YOUR_LINK_ID',
      customCode: 'summer-sale', // Optional vanity slug: /s/summer-sale
      customDomain: 'links.example.com', // Optional custom domain
    );

    final shortUrl = response['shortUrl']; // e.g. https://links.example.com/s/summer-sale
    print('Short URL: $shortUrl');
  } catch (e) {
    print('Error shortening link: $e');
  }
}

Listen for deep link open events when the app is already installed:

@override
void initState() {
  super.initState();

  DeepLinking.onDeepLinkOpen((params) {
    print('Deep link opened natively: $params');
    final screen = params['screen'];
    final screens = params['screens'];
    final permissions = params['permissions'];
    // Route user accordingly...
  });
}

6. Redeeming Referrals & Granting Rewards #

When a referred user completes onboarding or registers, call this method to trigger referral rewards. This fires FCM notifications to the referrer and returns the dynamic reward settings:

void redeemUserReferral(BuildContext context, String referralCode) async {
  try {
    final response = await DeepLinking.redeemReferral(
      referralCode: referralCode,
      newUserId: 'NEW_USER_456', // The new user who just signed up
      rewardDays: 15, // Dynamic reward overwrite (optional)
    );

    if (response['success'] == true) {
      final rewardDays = response['rewardDays'];
      print('Referral redeemed! Credited $rewardDays days of premium.');
    }
  } on SdkLimitExceededException catch (e) {
    ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(e.message)));
  } on InvalidSdkKeyException catch (e) {
    ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(e.message)));
  }
}

7. Tracking Shares & CTA Actions #

Log sharing activity immediately before opening the OS Share Sheet. This contributes to your analytics for most-shared screens and products:

void onShareProductClicked(BuildContext context) async {
  try {
    await DeepLinking.trackShare(
      linkId: 'TRACKING_LINK_ID',
      referralCode: 'SENDER_REF_CODE',
      screens: ['ProductDetail', 'Checkout'],
      permissions: ['view', 'buy'],
      eventId: 'share_evt_123',
      params: {
        'productId': 'prod_999',
        'price': 49.99
      }
    );
  } on SdkLimitExceededException catch (e) {
    ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(e.message)));
  } on InvalidSdkKeyException catch (e) {
    ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(e.message)));
  }
}

Exception Handling #

All gated SDK methods throw dedicated typed exceptions on failure:

  • SdkLimitExceededException: Thrown when monthly plan quota is exhausted (HTTP 429).
  • InvalidSdkKeyException: Thrown when SDK key is invalid, missing, or app ID is not registered (HTTP 401/403).

License #

MIT

9
likes
150
points
91
downloads

Documentation

API reference

Publisher

verified publisherdeeplinking.in

Weekly Downloads

A lightweight developer-first mobile attribution and deep linking SDK for Link Traker (FDL alternative) with multi-screen and multi-permission support.

Homepage
Repository (GitHub)
View/report issues

License

MIT (license)

Dependencies

device_info_plus, flutter, http

More

Packages that depend on deeplinking

Packages that implement deeplinking