Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Deep Link Conflict with AppLinks and Delegate Swizzling on iOS #30

Open
ctykaya opened this issue Mar 12, 2025 · 3 comments
Open

Deep Link Conflict with AppLinks and Delegate Swizzling on iOS #30

ctykaya opened this issue Mar 12, 2025 · 3 comments

Comments

@ctykaya
Copy link

ctykaya commented Mar 12, 2025

Issue Summary:

Deep links processed by the app_links Flutter package are not being received by the Flutter application when the Infobip Mobile Messaging SDK is initialized on iOS. This issue appears to be related to the SDK's delegate swizzling and potential timing conflicts.

Detailed Description:

We are experiencing a problem with deep links not being captured by our Flutter application when using the Infobip Mobile Messaging SDK on iOS. We are using the app_links Flutter package to handle deep links.

The problem manifests as follows:

Deep Link Processing:

Deep links are correctly received by the native iOS side of the application, as confirmed by logging within the AppDelegate's didFinishLaunchingWithOptions method.
However, the uriLinkStream listener in our Flutter code, which should capture these deep links, is not being triggered.
Suspected Cause:

We believe the issue is related to the Infobip Mobile Messaging SDK's delegate swizzling, which occurs during its initialization via MobileMessagingPluginApplicationDelegate.install().
Even when we ensure the app_links logic runs before the SDK's initialization in didFinishLaunchingWithOptions, the deep link is not propagated to Flutter.
It is suspected that the delegate swizzling is causing timing issues, or that the applinks package is losing the original application delegate, before the flutter side can read the deep link.
Environment:

Steps to Reproduce:

Setup:

Create a Flutter project with the Infobip Mobile Messaging SDK and the app_links package.
Configure deep linking for your app.
Add the following code to your AppDelegate.swift:


import UIKit
import Flutter
import MobileMessaging
import app_links

@main
@objc class AppDelegate: FlutterAppDelegate {

    override func application(
        _ application: UIApplication,
        didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?
    ) -> Bool {
        GeneratedPluginRegistrant.register(with: self)
        print("AppDelegate: didFinishLaunchingWithOptions called")
        if let url = AppLinks.shared.getLink(launchOptions: launchOptions) {
            print("AppDelegate: AppLinks link found: \(url)")
            AppLinks.shared.handleLink(url: url)
            print("AppDelegate: AppLinks link handled")
        } else {
            print("AppDelegate: AppLinks no link found")
        }

        MobileMessagingPluginApplicationDelegate.install()
        print("AppDelegate: Mobile Messaging installed")

        return super.application(application, didFinishLaunchingWithOptions: launchOptions)
    }
}

main.dart


import 'package:app_links/app_links.dart';
import 'package:flutter/material.dart';
import 'package:infobip_mobilemessaging/infobip_mobilemessaging.dart';
import 'package:infobip_mobilemessaging/models/configurations/configuration.dart';
import 'dart:async';

void main() async {
  WidgetsFlutterBinding.ensureInitialized();
  await InfobipMobilemessaging.init(
    Configuration(
      applicationCode: '[Your App Code]',
      iosSettings: IOSSettings(notificationTypes: ['alert', 'badge', 'sound'], logging: true),
    ),
  );

  StreamSubscription<Uri>? _linkSubscription = AppLinks().uriLinkStream.listen((uri) {
    print('onAppLink (main): $uri');
    print("Applinks listener triggered");
  });

  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        body: Center(
          child: Text("App Initialized"),
        ),
      ),
    );
  }
}

We would greatly appreciate your assistance in resolving this issue. Please let us know if you require any further information.

@riskpp
Copy link
Collaborator

riskpp commented Mar 19, 2025

Hello @ctykaya,

Could you please try instead of the "MobileMessagingPluginApplicationDelegate.install()" call the MobileMesssaging SDK methods similar to this:

import MobileMessaging

@UIApplicationMain
@objc class AppDelegate: FlutterAppDelegate {
  override func application(
    _ application: UIApplication,
    didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?
  ) -> Bool {
    GeneratedPluginRegistrant.register(with: self)
    return super.application(application, didFinishLaunchingWithOptions: launchOptions)
  }
    
    override func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
        MobileMessaging.didRegisterForRemoteNotificationsWithDeviceToken(deviceToken)
    }
    
    override func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable : Any], fetchCompletionHandler completionHandler: @escaping (UIBackgroundFetchResult) -> Void) {
        if MM_MTMessage.isCorrectPayload(userInfo) {
            MobileMessaging.didReceiveRemoteNotification(userInfo, fetchCompletionHandler: completionHandler)
        } else {
            completionHandler(.noData)
        }
    }
}

@ctykaya
Copy link
Author

ctykaya commented Apr 7, 2025

Hello @riskpp
Thanks for your response.
I'm experiencing an issue with Infobip push notifications and deep linking on iOS. I’m using the infobip_mobilemessaging: ^7.2.4 in a Flutter app.

Issue: When a push notification contains a deeplink field and the user taps the notification when app is killed, the app does not receive or handle the deep link on iOS . However, on iOS 15, the exact same implementation works as expected — the app launches or resumes and correctly navigates to the deep link destination.

Additionally, certain events (such as notification tap callbacks) are not triggered on iOS 18, while they work as expected on iOS 15.

Could you please look into this issue or provide guidance on handling deep links, notification events properly on iOS 18?

Thank you in advance!

 InfobipMobilemessaging.on(LibraryEvent.actionTapped, (Message event) {
      if (event.deeplink != null) {
        Uri uri = Uri.parse(event.deeplink.toString());
        print('Action tapped with link: $uri');
        link = uri;
        // _deepLinkStreamController.add(uri); // Send to listener
      } else {
        print("No Deep Link detected ");
      }
    });

    InfobipMobilemessaging.on(LibraryEvent.notificationTapped, (Message event) {
      if (event.deeplink != null) {
        Uri uri = Uri.parse(event.deeplink.toString());
        print('Action tapped with link: $uri');

        link = uri;
        // _deepLinkStreamController.add(uri); // Send to listener
      } else {
        print("No Deep Link detected ");
      }
    });

Here is the delegate file:

import UIKit
import Flutter

import MobileMessaging
import FBSDKCoreKit
import app_links

@main
@objc class AppDelegate: FlutterAppDelegate {

    override func application(
        _ application: UIApplication,
        didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?
    ) -> Bool {
        
        GeneratedPluginRegistrant.register(with: self)
        print("AppDelegate: didFinishLaunchingWithOptions called")
          if let url = AppLinks.shared.getLink(launchOptions: launchOptions) {
              print("AppDelegate: AppLinks link found: \(url)")
              AppLinks.shared.handleLink(url: url)
              print("AppDelegate: AppLinks link handled")
          } else {
              print("AppDelegate: AppLinks no link found")
          }

    
//         MobileMessagingPluginApplicationDelegate.install()
//         print("AppDelegate: Mobile Messaging installed")


        // Initialize Facebook SDK
        ApplicationDelegate.shared.application(
            application,
            didFinishLaunchingWithOptions: launchOptions
        )


        return super.application(application, didFinishLaunchingWithOptions: launchOptions)
    }

    override func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
        MobileMessaging.didRegisterForRemoteNotificationsWithDeviceToken(deviceToken)
    }

    override func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable : Any], fetchCompletionHandler completionHandler: @escaping (UIBackgroundFetchResult) -> Void) {
        if MM_MTMessage.isCorrectPayload(userInfo) {
            MobileMessaging.didReceiveRemoteNotification(userInfo, fetchCompletionHandler: completionHandler)
        } else {
            completionHandler(.noData)
        }
    }

    override func application(
              _ app: UIApplication,
              open url: URL,
              options: [UIApplication.OpenURLOptionsKey : Any] = [:]
          ) -> Bool {
              return ApplicationDelegate.shared.application(
                  app,
                  open: url,
                  sourceApplication: options[UIApplication.OpenURLOptionsKey.sourceApplication] as? String,
                  annotation: options[UIApplication.OpenURLOptionsKey.annotation]
              )
          }

    
}

@mkbilgic
Copy link

@riskpp Hello, could we kindly ask for your assistance? We are waiting to resolve this issue in order to go live. Thanks in advance.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants