Отправить платформенное сообщение в метод Android из изолята фонового флаттера

Я хочу, чтобы фоновый сервис dart работал вечно (изолирует), который будет взаимодействовать с сервером через веб-сокеты. И у меня есть API для Android, который собирает информацию для отправки на сервер. Как я могу вызвать те методы Android, которые используют обратные вызовы и все из фоновой изоляции?

РЕДАКТИРОВАТЬ

До сих пор в dart я создавал Isolate для периодического вызова метода poolSong в фоновом режиме, даже если пользователь использует другое приложение или экран отключен.

Но это дает мне ошибку ниже... по поводу проблем с github говорят, что я не могу отправить сообщение платформы с другого Isolate, если оно не является основным. Но если я сделаю это из основного изолята, то при выходе пользователя приложение, которое изолирует, тоже прекратит работу.

MainDart

class _MyHomePageState extends State<MyHomePage> {
    final GlobalKey<ScaffoldState> scaffoldKey = new GlobalKey<ScaffoldState>();
    static const platform = const MethodChannel('mainService');

    static _poolSong(SendPort sendPort) async {
        const oneSec = const Duration(seconds:1);
        new Timer.periodic(oneSec, (Timer t) => platform.invokeMethod('poolSong'));
    }

    @override
    void initState() {
        super.initState();
        ReceivePort receivePort = ReceivePort();
        Isolate.spawn(_poolSong, receivePort.sendPort);
    }
        ·
        ·
        ·

MainActivityJava

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    GeneratedPluginRegistrant.registerWith(this);

    new MethodChannel(getFlutterView(), CHANNEL).setMethodCallHandler(
        (call, result) -> {
            if (call.method.equals("startService"))
                startService();
            if (call.method.equals("poolSong"))
                poolSong();
        }
    );
}

ОШИБКА

E/flutter (25412): [ERROR:flutter/runtime/dart_isolate.cc(717)] Isolate (765499726) 'main.dart:_poolSong()' exited with an error
E/flutter (25412): [ERROR:flutter/shell/common/shell.cc(186)] Dart Error: Unhandled exception:
E/flutter (25412): error: native function 'Window_sendPlatformMessage' (4 arguments) cannot be found
E/flutter (25412): #0   Window.sendPlatformMessage (dart:ui/window.dart:811:9)
E/flutter (25412): #1   BinaryMessages._sendPlatformMessage (package:flutter/src/services/platform_messages.dart:39:15)
E/flutter (25412): #2   BinaryMessages.send (package:flutter/src/services/platform_messages.dart:87:12)
E/flutter (25412): #3   MethodChannel.invokeMethod (package:flutter/src/services/platform_channel.dart:286:49)
E/flutter (25412): <asynchronous suspension>
E/flutter (25412): #4   _MyHomePageState._poolSong.<anonymous closure> (package:musictie/main.dart:37:54)
E/flutter (25412): #5   _Timer._runTimers (dart:isolate/runtime/libtimer_impl.dart:382:19)
E/flutter (25412): #6   _Timer._handleMessage (dart:isolate/runtime/libtimer_impl.dart:416:5)
E/flutter (25412): #7   _RawReceivePortImpl._handleMessage (dart:isolate/runtime/libisolate_patch.dart:171:12)

3 ответа

Решение

После прочтения известной статьи, где объясняется, как использовать фоновые сервисы во флаттере, и понимаешь, что это нелепо сложно, я заметил, что весь мой код Android мог быть написан непосредственно в javascript с использованием JS-версии API.

Так что, используя плагин interactive_webview для трепетания, я переведу весь код Android в js... и все. Мне больше не нужно беспокоиться о написании конкретного кода платформы для iOS и Android. Плюс приложение флаттера по умолчанию работает в фоновом режиме (наверное).

Эта ошибка возникает при попытке запустить код дротика, когда приложение находится в мусоре (приложение закрыто). До сих пор лучший способ справиться с фоновой службой - делать то, что вам нужно в собственном коде, и не пытаться запускать что-либо из дротика, когда приложение закрыто.

Поскольку плагины и каналы платформы Flutter 3.7 можно использовать из любого изолята, а не только из корневого.

Использованная литература:

Другие вопросы по тегам