import 'dart:async'; import 'dart:developer'; import 'package:bloc/bloc.dart'; import 'package:cloud_firestore/cloud_firestore.dart'; import 'package:firebase_auth/firebase_auth.dart'; import 'package:flutter/widgets.dart'; class AppBlocObserver extends BlocObserver { @override void onChange(BlocBase bloc, Change change) { super.onChange(bloc, change); log('onChange(${bloc.runtimeType}, $change)'); } @override void onError(BlocBase bloc, Object error, StackTrace stackTrace) { log('onError(${bloc.runtimeType}, $error, $stackTrace)'); super.onError(bloc, error, stackTrace); } } typedef BootstrapBuilder = Future Function( FirebaseFirestore firestore, FirebaseAuth firebaseAuth, ); Future bootstrap(BootstrapBuilder builder) async { WidgetsFlutterBinding.ensureInitialized(); FlutterError.onError = (details) { log(details.exceptionAsString(), stackTrace: details.stack); }; await runZonedGuarded( () async { await BlocOverrides.runZoned( () async => runApp( await builder( FirebaseFirestore.instance, FirebaseAuth.instance, ), ), blocObserver: AppBlocObserver(), ); }, (error, stackTrace) => log(error.toString(), stackTrace: stackTrace), ); }