ОБНОВЛЕНИЕ (15 июля 2020 г.)
Ответ mFeinstein на данный момент является единственным ответом, который дает мне первое приемлемое решение.
ВОПРОС
Я должен спросить вас, как лучше всего делать то, что я пытаюсь сделать:
- Вызов веб-службы в asyn c mode
- Ответ на синтаксический анализ
- Выполнение массовых операций с базой данных
Все это без остановки анимации прогресса, например, неопределенного индикатора выполнения.
Нет проблем по первому и второму пунктам. Проблема возникает на третьем этапе, когда выполняется массивная вставка в базу данных. И я еще не понимаю, как правильно реализовать это.
Какой-то псевдокод для уточнения
UI (отображается диалоговое окно и отображается индикатор выполнения .. .)
void callWS() async {
MyProgressDialog _dialog = DialogHelper.showMyProgressDialog(_context, "Data", "Loading...");
await getDataFromService();
_dialog.close();
}
ПОДКЛЮЧЕНИЕ (замораживание не происходит на индикаторе выполнения)
static Future<void> getDataFromService() async {
String uri = MY_URI;
String wsMethod = MY_WS_METHOD;
String wsContract = MY_WS_CONTRACT;
SoapObject myRequest = SoapObject.fromSoapObject(namespace: my_namespace, name: wsMethod);
MyConnectionResult response = await _openMyConnection(myRequest, uri, wsContract, wsMethod);
if (response.result == MyResultEnum.OK) {
await _parseResponse(response.data);
}
}
DATABASE (замораживание происходит в индикаторе выполнения )
static Future<void> _parseResponse(xml.XmlElement elements) async {
Database db = await MyDatabaseHelper.openConnection();
db.transaction((tx) async {
Batch batch = tx.batch();
for (xml.XmlElement oi in elements.children) {
int id = int.parse(oi.findElements("ID").first.text);
String name = oi.findElements("NAME").first.text;
DatabaseHelper.insertElement(
tx,
id: id,
name: name,
);
}
batch.commit(noResult: true);
});
}
НЕ РАБОТАЕТ АЛЬТЕРНАТИВА
Я тоже видел подход функции "вычислить", но похоже, что проблема в sqflite package
, когда я называю операцию db. Например:
static Future<void> performDelete() async {
Database db = await openMyConnection();
compute(_performDeleteCompute, db);
}
static void _performDeleteCompute(Database db) async {
db.rawQuery("DELETE MYTABLE");
}
Console error:'
-> Unhandled Exception: Exception: ServicesBinding.defaultBinaryMessenger was accessed before the binding was initialized.
-> If you are running an application and need to access the binary messenger before runApp() has been called (for example, during plugin initialization),
then you need to explicitly call the WidgetsFlutterBinding.ensureInitialized() first.
-> error defaultBinaryMessenger.<anonymous closure> (package:flutter/src/services/binary_messenger.dart:76:7)
#1 defaultBinaryMessenger (package:flutter/src/services/binary_messenger.dart:89:4)
#2 MethodChannel.binaryMessenger (package:flutter/src/services/platform_channel.dart:140:62)
#3 MethodChannel._invokeMethod (package:flutter/src/services/platform_channel.dart:146:35)
#4 MethodChannel.invokeMethod (package:flutter/src/services/platform_channel.dart:329:12)
#5 invokeMethod (package:sqflite/src/sqflite_impl.dart:17:13)
#6 SqfliteDatabaseFactoryImpl.invokeMethod (package:sqflite/src/factory_impl.dart:31:7)
#7 SqfliteDatabaseMixin.invokeMethod (package:sqflite_common/src/database_mixin.dart:287:15)
#8 SqfliteDatabaseMixin.safeInvokeMethod.<anonymous closure> (package:sqflite_common/src/database_mixin.dart:208:43)
#9 wrapDatabaseException (package:sqflite/src/exception_impl.dart:7:32)
#10 SqfliteDatabaseFactoryImpl.wrapDatabaseException (package:sqflite/src/factory_impl.dart:27:7)
#11 SqfliteDatabaseMixin.safeInvokeMethod (package:sqflite_common/src/database_mixin.dart:208:15)
#12 SqfliteDatabaseMixin.txnRawQuery.<anonymous closure> (package:sqflite_common/src/database_mixin.dart:394:36)
#13 SqfliteDatabaseMixin.txnSynchronized.<anonymous closure> (package:sqflite_common/src/database_mixin.dart:327:22)
#14 BasicLock.synchronized (package:synchronized/src/basic_lock.dart:32:26)
#15 SqfliteDatabaseMixin.txnSynchronized (package:sqflite_common/src/database_mixin.dart:323:33)
#16 SqfliteDatabaseMixin.txnRawQuery (package:sqflite_common/src/database_mixin.dart:393:12)
#17 SqfliteDatabaseExecutorMixin._rawQuery (package:sqflite_common/src/database_mixin.dart:126:15)
#18 SqfliteDatabaseExecutorMixin.rawQuery (package:sqflite_common/src/database_mixin.dart:120:12)
#19 DatabaseHelper._performDeleteCompute(package:flutter_infocad/Database/DatabaseHelper.dart:368:8)'
А также явный вызов WidgetsFlutterBinding.ensureInitialized()
первым в runApp (), как указано в журнале ошибок, ничего не происходит.