Skip to content

Conversation

@denischilik
Copy link
Contributor

@denischilik denischilik commented Nov 18, 2025

Background

Flutter layer needs to wait for mParticle SDK initialization from iOS native layer before making SDK calls. Implements EventChannel-based signaling mechanism to notify Flutter when mParticleDidFinishInitializing fires.

What Has Changed

  • Added EventChannel in iOS (AppDelegate) to broadcast mParticle initialization events to Flutter
  • Flutter main.dart now listens for initialization signal before using SDK
  • Updated iOS deployment target to 13.0 for mParticle-Rokt compatibility
  • Added comprehensive setup documentation to example README

Checklist

  • I have performed a self-review of my own code.
  • I have made corresponding changes to the documentation.
  • I have added tests that prove my fix is effective or that my feature works.
  • I have tested this locally.

Additional Notes

POC implementation for initialization synchronization pattern between native iOS and Flutter layers.

Integration Guide: iOS-Flutter EventChannel for SDK Initialization

iOS (Native Layer) - AppDelegate.swift

  1. Add FlutterStreamHandler protocol to your AppDelegate

    @objc class AppDelegate: FlutterAppDelegate, FlutterStreamHandler
  2. Create variables for EventSink and initialization flag

    private var eventSink: FlutterEventSink?
    var isInitialized = false
  3. Register EventChannel in didFinishLaunchingWithOptions

    let controller = window?.rootViewController as! FlutterViewController
    let initializationChannel = FlutterEventChannel(
      name: "mparticle_initialization",
      binaryMessenger: controller.binaryMessenger
    )
    initializationChannel.setStreamHandler(self)
  4. Subscribe to SDK initialization notification

    NotificationCenter.default.addObserver(
      self,
      selector: #selector(handleMParticleInitialized),
      name: NSNotification.Name.mParticleSDKDidFinishInitializing,
      object: nil
    )
  5. Implement FlutterStreamHandler methods

    func onListen(withArguments arguments: Any?, eventSink events: @escaping FlutterEventSink) -> FlutterError? {
      self.eventSink = events
      // If SDK already initialized, send event immediately
      if isInitialized {
        events(["initialized": true])
      }
      return nil
    }
    
    func onCancel(withArguments arguments: Any?) -> FlutterError? {
      self.eventSink = nil
      return nil
    }
  6. Handle notification and send event to Flutter

    @objc private func handleMParticleInitialized(notification: Notification) {
      isInitialized = true
      if let eventSink = self.eventSink {
        eventSink(["initialized": true])
      }
    }

Flutter Layer - main.dart

  1. Create EventChannel with the same name

    static const _initializationEventChannel = 
      EventChannel('mparticle_initialization');
  2. Create subscription variable and initialization flag

    StreamSubscription? _initializationSubscription;
    bool _isInitialized = false;
  3. Add platform check and subscribe to events

    Future<void> initMparticle() async {
      if (Platform.isIOS) {
        _initializationSubscription = _initializationEventChannel
          .receiveBroadcastStream()
          .listen((event) async {
            if (event is Map && event['initialized'] == true) {
              print("mParticle initialized from native layer");
              mpInstance = await MparticleFlutterSdk.getInstance();
              setState(() {
                _isInitialized = true;
              });
            }
          });
      } else {
        // For Android, use standard initialization
        mpInstance = await MparticleFlutterSdk.getInstance();
        if (mpInstance != null) {
          setState(() {
            _isInitialized = true;
          });
        }
      }
    }
  4. Unsubscribe from events on dispose

    @override
    void dispose() {
      _initializationSubscription?.cancel();
      super.dispose();
    }
  5. Use _isInitialized flag to block UI or SDK calls until initialization completes

Result

Flutter layer will now wait for actual SDK initialization from native iOS layer before using SDK methods.

Reference Issue (For employees only. Ignore if you are an outside contributor)

- Update minimum iOS version from 12.0 to 13.0
- Required for compatibility with mParticle-Rokt and Rokt-Widget dependencies
- Add EventChannel in iOS (AppDelegate.swift) to notify Flutter when mParticle is initialized
- Subscribe to mParticleDidFinishInitializing notification in native layer
- Listen for initialization events in Flutter (main.dart) before using mParticle SDK
- Add proper cleanup in dispose method

This allows Flutter to wait for mParticle initialization from iOS native layer before making SDK calls.
- Add prerequisites section (Flutter SDK, Xcode, CocoaPods, iOS 13.0+)
- Add step-by-step setup instructions for Flutter installation
- Add iOS dependencies installation steps
- Document configuration changes (iOS deployment target update)
- Add troubleshooting section for common issues
- Include instructions for running on iOS simulator and device
@denischilik denischilik marked this pull request as ready for review November 18, 2025 18:40
@denischilik
Copy link
Contributor Author

That is Example app update to show how we can wait until sdk will be fully initialized

@denischilik
Copy link
Contributor Author

Do not merge

@denischilik denischilik marked this pull request as draft November 18, 2025 19:49
@denischilik denischilik requested a review from rmi22186 November 18, 2025 19:50
- iOS: Use EventChannel-based signaling from native layer
- Android/other platforms: Use direct initialization with null check
- Add isInitialized flag in AppDelegate to handle late subscriptions
- Add debug logging for initialization events
@denischilik denischilik force-pushed the feat/SDKE-608-iOS-Flutter-Signaling-POC branch from 0f0207b to b4dad6a Compare November 18, 2025 19:54
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

Successfully merging this pull request may close these issues.

3 participants