fix(mobile): keep startup independent of crash reporting

Co-authored-by: npub1ft62tztwwm2x9xamk25smmuaj4sfckdkldksruf2x2jwqalffkrq0g7arr <4af4a5896e76d4629bbbb2a90def9d95609c59b6fb6d01f12a32a4e077e94d86@sprout-oss.stage.blox.sqprod.co>
Signed-off-by: npub1ft62tztwwm2x9xamk25smmuaj4sfckdkldksruf2x2jwqalffkrq0g7arr <4af4a5896e76d4629bbbb2a90def9d95609c59b6fb6d01f12a32a4e077e94d86@sprout-oss.stage.blox.sqprod.co>
This commit is contained in:
npub1ft62tztwwm2x9xamk25smmuaj4sfckdkldksruf2x2jwqalffkrq0g7arr
2026-07-19 13:51:52 -07:00
parent fb375ddf24
commit bdfc94b217
3 changed files with 69 additions and 2 deletions
+19 -2
View File
@@ -6,7 +6,7 @@ import 'app.dart';
import 'shared/diagnostics/diagnostics.dart';
import 'shared/theme/theme_provider.dart';
void main() async {
Future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
// Pre-load preferences so startup can apply saved diagnostics consent and
@@ -17,7 +17,7 @@ void main() async {
config: const SentryConfig.fromEnvironment(),
crashReporter: const SentryCrashReporter(),
);
await diagnosticsController.applyStartupConsent();
await applyStartupDiagnosticsConsent(diagnosticsController);
runApp(
ProviderScope(
@@ -31,3 +31,20 @@ void main() async {
),
);
}
/// Applies diagnostics consent without allowing optional crash reporting to
/// prevent the app from starting.
@visibleForTesting
Future<void> applyStartupDiagnosticsConsent(
DiagnosticsController diagnosticsController, {
DiagnosticsLog? log,
}) async {
try {
await diagnosticsController.applyStartupConsent();
} on Object catch (error, stackTrace) {
(log ?? debugPrint)(
'Diagnostics startup failed; continuing without crash reporting: '
'$error\n$stackTrace',
);
}
}
+3
View File
@@ -32,6 +32,9 @@ dependencies:
app_badge_plus: ^1.2.10
app_links: ^6.4.0
scrollable_positioned_list: ^0.3.8
# 9.24.0 still pins jni 0.14.2, so the resolver also selects the
# compatible path_provider_android 2.2.23 instead of the prior jni 1.0.0
# graph. Keep this exact pin until Sentry publishes a compatible release.
sentry_flutter: 9.24.0
dev_dependencies:
+47
View File
@@ -0,0 +1,47 @@
import 'package:buzz/main.dart' as app;
import 'package:buzz/shared/diagnostics/diagnostics.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:shared_preferences/shared_preferences.dart';
void main() {
test('startup continues when crash reporting initialization fails', () async {
SharedPreferences.setMockInitialValues({
diagnosticsConsentPreferenceKey: true,
});
final preferences = await SharedPreferences.getInstance();
final logs = <String>[];
final controller = DiagnosticsController(
preferences: preferences,
config: const SentryConfig(
dsn: 'https://public@example.invalid/1',
release: 'buzz@1.2.3',
dist: '42',
environment: 'production',
),
crashReporter: _FailingCrashReporter(),
);
await expectLater(
app.applyStartupDiagnosticsConsent(controller, log: logs.add),
completes,
);
expect(
logs.single,
contains(
'Diagnostics startup failed; continuing without crash reporting: '
'Bad state: init failed',
),
);
});
}
class _FailingCrashReporter implements CrashReporter {
@override
Future<void> initialize(SentryConfig config) async {
throw StateError('init failed');
}
@override
Future<void> close() async {}
}