fix: minor bugs
This commit is contained in:
@@ -23,8 +23,9 @@ import 'package:sentry_flutter/sentry_flutter.dart';
|
||||
import 'package:shared_preferences/shared_preferences.dart';
|
||||
import 'package:window_manager/window_manager.dart';
|
||||
|
||||
final _loggy = Loggy('bootstrap');
|
||||
final _logger = Loggy('bootstrap');
|
||||
const _testCrashReport = false;
|
||||
final _loggers = MultiLogPrinter(const PrettyPrinter(), []);
|
||||
|
||||
Future<void> lazyBootstrap(
|
||||
WidgetsBinding widgetsBinding,
|
||||
@@ -32,6 +33,7 @@ Future<void> lazyBootstrap(
|
||||
) async {
|
||||
FlutterNativeSplash.preserve(widgetsBinding: widgetsBinding);
|
||||
if (PlatformUtils.isDesktop) await windowManager.ensureInitialized();
|
||||
Loggy.initLoggy();
|
||||
|
||||
final appInfo = await AppRepositoryImpl.getAppInfo(env);
|
||||
final sharedPreferences = await SharedPreferences.getInstance();
|
||||
@@ -43,6 +45,8 @@ Future<void> lazyBootstrap(
|
||||
);
|
||||
|
||||
final enableAnalytics = container.read(enableAnalyticsProvider);
|
||||
final sentryLogger = SentryLoggyIntegration();
|
||||
_loggers.addPrinter(sentryLogger);
|
||||
|
||||
await SentryFlutter.init(
|
||||
(options) {
|
||||
@@ -52,8 +56,14 @@ Future<void> lazyBootstrap(
|
||||
options.dsn = "";
|
||||
}
|
||||
|
||||
options.environment = env.toString();
|
||||
options.environment = env.name;
|
||||
options.dist = appInfo.release.name;
|
||||
options.debug = kDebugMode;
|
||||
options.enableNativeCrashHandling = true;
|
||||
options.enableNdkScopeSync = true;
|
||||
options.attachThreads = true;
|
||||
options.tracesSampleRate = 0.25;
|
||||
options.addIntegration(sentryLogger);
|
||||
},
|
||||
appRunner: () => _lazyBootstrap(widgetsBinding, container, env),
|
||||
);
|
||||
@@ -70,7 +80,7 @@ Future<void> _lazyBootstrap(
|
||||
await filesEditor.init();
|
||||
|
||||
initLoggers(container.read, debug);
|
||||
_loggy.info(
|
||||
_logger.info(
|
||||
"os: [${Platform.operatingSystem}](${Platform.operatingSystemVersion}), processor count [${Platform.numberOfProcessors}]",
|
||||
);
|
||||
|
||||
@@ -89,8 +99,10 @@ Future<void> _lazyBootstrap(
|
||||
runApp(
|
||||
ProviderScope(
|
||||
parent: container,
|
||||
child: SentryUserInteractionWidget(
|
||||
child: const AppView(),
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
if (!silentStart) FlutterNativeSplash.remove();
|
||||
@@ -102,13 +114,13 @@ void initLoggers(
|
||||
) {
|
||||
final logLevel = debug ? LogLevel.all : LogLevel.info;
|
||||
final logToFile = debug || (!Platform.isAndroid && !Platform.isIOS);
|
||||
if (logToFile) {
|
||||
_loggers.addPrinter(
|
||||
FileLogPrinter(read(filesEditorServiceProvider).appLogsPath),
|
||||
);
|
||||
}
|
||||
Loggy.initLoggy(
|
||||
logPrinter: MultiLogPrinter(
|
||||
const PrettyPrinter(),
|
||||
logToFile
|
||||
? FileLogPrinter(read(filesEditorServiceProvider).appLogsPath)
|
||||
: null,
|
||||
),
|
||||
logPrinter: _loggers,
|
||||
logOptions: LogOptions(logLevel),
|
||||
);
|
||||
}
|
||||
@@ -116,19 +128,19 @@ void initLoggers(
|
||||
Future<void> initAppServices(
|
||||
Result Function<Result>(ProviderListenable<Result>) read,
|
||||
) async {
|
||||
_loggy.debug("initializing app services");
|
||||
_logger.debug("initializing app services");
|
||||
await Future.wait(
|
||||
[
|
||||
read(singboxServiceProvider).init(),
|
||||
],
|
||||
);
|
||||
_loggy.debug('initialized app services');
|
||||
_logger.debug('initialized app services');
|
||||
}
|
||||
|
||||
Future<void> initControllers(
|
||||
Result Function<Result>(ProviderListenable<Result>) read,
|
||||
) async {
|
||||
_loggy.debug("initializing controllers");
|
||||
_logger.debug("initializing controllers");
|
||||
await Future.wait(
|
||||
[
|
||||
read(activeProfileProvider.future),
|
||||
@@ -136,5 +148,5 @@ Future<void> initControllers(
|
||||
if (PlatformUtils.isDesktop) read(systemTrayControllerProvider.future),
|
||||
],
|
||||
);
|
||||
_loggy.debug("initialized base controllers");
|
||||
_logger.debug("initialized base controllers");
|
||||
}
|
||||
|
||||
@@ -4,6 +4,7 @@ import 'package:hiddify/core/prefs/prefs.dart';
|
||||
import 'package:hiddify/core/router/routes/routes.dart';
|
||||
import 'package:hiddify/services/deep_link_service.dart';
|
||||
import 'package:riverpod_annotation/riverpod_annotation.dart';
|
||||
import 'package:sentry_flutter/sentry_flutter.dart';
|
||||
|
||||
part 'app_router.g.dart';
|
||||
|
||||
@@ -30,6 +31,9 @@ GoRouter router(RouterRef ref) {
|
||||
initialLocation: initialLocation,
|
||||
debugLogDiagnostics: true,
|
||||
routes: $routes,
|
||||
observers: [
|
||||
SentryNavigatorObserver(),
|
||||
],
|
||||
redirect: (context, state) {
|
||||
if (!introCompleted && state.uri.path != const IntroRoute().location) {
|
||||
return const IntroRoute().location;
|
||||
|
||||
@@ -12,6 +12,7 @@ import 'package:hiddify/domain/core_facade.dart';
|
||||
import 'package:hiddify/domain/profiles/profiles.dart';
|
||||
import 'package:hiddify/services/service_providers.dart';
|
||||
import 'package:riverpod_annotation/riverpod_annotation.dart';
|
||||
import 'package:sentry_dio/sentry_dio.dart';
|
||||
import 'package:shared_preferences/shared_preferences.dart';
|
||||
|
||||
part 'data_providers.g.dart';
|
||||
@@ -31,7 +32,7 @@ Dio dio(DioRef ref) => Dio(
|
||||
"User-Agent": ref.watch(appInfoProvider).userAgent,
|
||||
},
|
||||
),
|
||||
);
|
||||
)..addSentry();
|
||||
|
||||
@Riverpod(keepAlive: true)
|
||||
ProfilesDao profilesDao(ProfilesDaoRef ref) => ProfilesDao(
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import 'package:hiddify/core/prefs/prefs.dart';
|
||||
import 'package:hiddify/domain/singbox/config_options.dart';
|
||||
import 'package:hiddify/utils/pref_notifier.dart';
|
||||
import 'package:riverpod_annotation/riverpod_annotation.dart';
|
||||
@@ -67,7 +68,9 @@ final setSystemProxyStore =
|
||||
|
||||
@riverpod
|
||||
ConfigOptions configOptions(ConfigOptionsRef ref) => ConfigOptions(
|
||||
executeConfigAsIs: ref.watch(executeConfigAsIs),
|
||||
executeConfigAsIs: ref.watch(debugModeNotifierProvider)
|
||||
? ref.watch(executeConfigAsIs)
|
||||
: false,
|
||||
logLevel: ref.watch(logLevelStore),
|
||||
resolveDestination: ref.watch(resolveDestinationStore),
|
||||
ipv6Mode: ref.watch(ipv6ModeStore),
|
||||
|
||||
@@ -104,8 +104,8 @@ class CustomToast extends StatelessWidget {
|
||||
}
|
||||
|
||||
void show(BuildContext context) {
|
||||
FToast().init(context);
|
||||
FToast().showToast(
|
||||
final fToast = FToast().init(context);
|
||||
fToast.showToast(
|
||||
child: this,
|
||||
gravity: ToastGravity.BOTTOM,
|
||||
toastDuration: duration,
|
||||
|
||||
@@ -3,15 +3,24 @@ import 'dart:io';
|
||||
import 'package:loggy/loggy.dart';
|
||||
|
||||
class MultiLogPrinter extends LoggyPrinter {
|
||||
MultiLogPrinter(this.consolePrinter, this.filePrinter);
|
||||
MultiLogPrinter(
|
||||
this.consolePrinter,
|
||||
this.otherPrinters,
|
||||
);
|
||||
|
||||
final LoggyPrinter consolePrinter;
|
||||
final LoggyPrinter? filePrinter;
|
||||
List<LoggyPrinter> otherPrinters;
|
||||
|
||||
void addPrinter(LoggyPrinter printer) {
|
||||
otherPrinters.add(printer);
|
||||
}
|
||||
|
||||
@override
|
||||
void onLog(LogRecord record) {
|
||||
consolePrinter.onLog(record);
|
||||
filePrinter?.onLog(record);
|
||||
for (final printer in otherPrinters) {
|
||||
printer.onLog(record);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
95
lib/utils/sentry_loggy_integration.dart
Normal file
95
lib/utils/sentry_loggy_integration.dart
Normal file
@@ -0,0 +1,95 @@
|
||||
import 'package:loggy/loggy.dart';
|
||||
import 'package:sentry_flutter/sentry_flutter.dart';
|
||||
|
||||
// modified version of https://github.com/getsentry/sentry-dart/tree/main/logging
|
||||
class SentryLoggyIntegration extends LoggyPrinter
|
||||
implements Integration<SentryOptions> {
|
||||
SentryLoggyIntegration({
|
||||
LogLevel minBreadcrumbLevel = LogLevel.info,
|
||||
LogLevel minEventLevel = LogLevel.error,
|
||||
}) : _minBreadcrumbLevel = minBreadcrumbLevel,
|
||||
_minEventLevel = minEventLevel;
|
||||
|
||||
final LogLevel _minBreadcrumbLevel;
|
||||
final LogLevel _minEventLevel;
|
||||
|
||||
late Hub _hub;
|
||||
|
||||
@override
|
||||
void call(Hub hub, SentryOptions options) {
|
||||
_hub = hub;
|
||||
options.sdk.addIntegration('LoggyIntegration');
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> close() async {}
|
||||
|
||||
bool _shouldLog(LogLevel logLevel, LogLevel minLevel) {
|
||||
if (logLevel == LogLevel.off) {
|
||||
return false;
|
||||
}
|
||||
return logLevel.priority >= minLevel.priority;
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> onLog(LogRecord record) async {
|
||||
if (_shouldLog(record.level, _minEventLevel)) {
|
||||
await _hub.captureEvent(
|
||||
record.toEvent(),
|
||||
stackTrace: record.stackTrace,
|
||||
hint: Hint.withMap({TypeCheckHint.record: record}),
|
||||
);
|
||||
}
|
||||
|
||||
if (_shouldLog(record.level, _minBreadcrumbLevel)) {
|
||||
await _hub.addBreadcrumb(
|
||||
record.toBreadcrumb(),
|
||||
hint: Hint.withMap({TypeCheckHint.record: record}),
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
extension LogRecordX on LogRecord {
|
||||
Breadcrumb toBreadcrumb() {
|
||||
return Breadcrumb(
|
||||
category: 'log',
|
||||
type: 'debug',
|
||||
timestamp: time.toUtc(),
|
||||
level: level.toSentryLevel(),
|
||||
message: message,
|
||||
data: <String, Object>{
|
||||
if (object != null) 'LogRecord.object': object!,
|
||||
if (error != null) 'LogRecord.error': error!,
|
||||
if (stackTrace != null) 'LogRecord.stackTrace': stackTrace!,
|
||||
'LogRecord.loggerName': loggerName,
|
||||
'LogRecord.sequenceNumber': sequenceNumber,
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
SentryEvent toEvent() {
|
||||
return SentryEvent(
|
||||
timestamp: time.toUtc(),
|
||||
logger: loggerName,
|
||||
level: level.toSentryLevel(),
|
||||
message: SentryMessage(message),
|
||||
throwable: error,
|
||||
// ignore: deprecated_member_use
|
||||
extra: <String, Object>{
|
||||
if (object != null) 'LogRecord.object': object!,
|
||||
'LogRecord.sequenceNumber': sequenceNumber,
|
||||
},
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
extension LogLevelX on LogLevel {
|
||||
SentryLevel? toSentryLevel() => switch (this) {
|
||||
LogLevel.all || LogLevel.debug => SentryLevel.debug,
|
||||
LogLevel.info => SentryLevel.info,
|
||||
LogLevel.warning => SentryLevel.warning,
|
||||
LogLevel.error => SentryLevel.error,
|
||||
_ => null,
|
||||
};
|
||||
}
|
||||
@@ -10,6 +10,7 @@ export 'mutation_state.dart';
|
||||
export 'number_formatters.dart';
|
||||
export 'placeholders.dart';
|
||||
export 'platform_utils.dart';
|
||||
export 'sentry_loggy_integration.dart';
|
||||
export 'text_utils.dart';
|
||||
export 'uri_utils.dart';
|
||||
export 'validators.dart';
|
||||
|
||||
@@ -1053,6 +1053,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "7.10.1"
|
||||
sentry_dio:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: sentry_dio
|
||||
sha256: "4455340dce8abf0790155fd0f6a8bcd84ab505417f2106fdc9582efe4fb4f350"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "7.10.1"
|
||||
sentry_flutter:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
|
||||
@@ -54,7 +54,10 @@ dependencies:
|
||||
url_launcher: ^6.1.14
|
||||
vclibs: ^0.1.0
|
||||
launch_at_startup: ^0.2.2
|
||||
|
||||
# analytics
|
||||
sentry_flutter: ^7.10.1
|
||||
sentry_dio: ^7.10.1
|
||||
|
||||
# utils
|
||||
combine: ^0.5.6
|
||||
|
||||
Reference in New Issue
Block a user