mirror of
https://github.com/KRTirtho/spotube.git
synced 2025-09-13 07:55:18 +00:00
refactor: remove catcher_2 and use custom zoned based error handling
This commit is contained in:
parent
d115e57058
commit
f9087b63d5
@ -1,4 +1,3 @@
|
|||||||
import 'package:catcher_2/catcher_2.dart';
|
|
||||||
import 'package:flutter/foundation.dart' hide Category;
|
import 'package:flutter/foundation.dart' hide Category;
|
||||||
import 'package:flutter/widgets.dart';
|
import 'package:flutter/widgets.dart';
|
||||||
import 'package:go_router/go_router.dart';
|
import 'package:go_router/go_router.dart';
|
||||||
@ -46,7 +45,7 @@ import 'package:spotube/pages/root/root_app.dart';
|
|||||||
import 'package:spotube/pages/settings/settings.dart';
|
import 'package:spotube/pages/settings/settings.dart';
|
||||||
import 'package:spotube/pages/mobile_login/mobile_login.dart';
|
import 'package:spotube/pages/mobile_login/mobile_login.dart';
|
||||||
|
|
||||||
final rootNavigatorKey = Catcher2.navigatorKey;
|
final rootNavigatorKey = GlobalKey<NavigatorState>();
|
||||||
final shellRouteNavigatorKey = GlobalKey<NavigatorState>();
|
final shellRouteNavigatorKey = GlobalKey<NavigatorState>();
|
||||||
final routerProvider = Provider((ref) {
|
final routerProvider = Provider((ref) {
|
||||||
return GoRouter(
|
return GoRouter(
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:flutter_hooks/flutter_hooks.dart';
|
import 'package:flutter_hooks/flutter_hooks.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
import 'package:spotify/spotify.dart';
|
import 'package:spotify/spotify.dart';
|
||||||
@ -62,7 +62,7 @@ void useEndlessPlayback(WidgetRef ref) {
|
|||||||
}),
|
}),
|
||||||
);
|
);
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
127
lib/main.dart
127
lib/main.dart
@ -1,4 +1,5 @@
|
|||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'dart:async';
|
||||||
|
|
||||||
import 'package:dart_discord_rpc/dart_discord_rpc.dart';
|
import 'package:dart_discord_rpc/dart_discord_rpc.dart';
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
@ -19,7 +20,6 @@ import 'package:spotube/hooks/configurators/use_disable_battery_optimizations.da
|
|||||||
import 'package:spotube/hooks/configurators/use_get_storage_perms.dart';
|
import 'package:spotube/hooks/configurators/use_get_storage_perms.dart';
|
||||||
import 'package:spotube/provider/tray_manager/tray_manager.dart';
|
import 'package:spotube/provider/tray_manager/tray_manager.dart';
|
||||||
import 'package:spotube/l10n/l10n.dart';
|
import 'package:spotube/l10n/l10n.dart';
|
||||||
import 'package:spotube/models/logger.dart';
|
|
||||||
import 'package:spotube/models/skip_segment.dart';
|
import 'package:spotube/models/skip_segment.dart';
|
||||||
import 'package:spotube/models/source_match.dart';
|
import 'package:spotube/models/source_match.dart';
|
||||||
import 'package:spotube/provider/connect/clients.dart';
|
import 'package:spotube/provider/connect/clients.dart';
|
||||||
@ -30,6 +30,7 @@ import 'package:spotube/provider/user_preferences/user_preferences_provider.dart
|
|||||||
import 'package:spotube/services/audio_player/audio_player.dart';
|
import 'package:spotube/services/audio_player/audio_player.dart';
|
||||||
import 'package:spotube/services/cli/cli.dart';
|
import 'package:spotube/services/cli/cli.dart';
|
||||||
import 'package:spotube/services/kv_store/kv_store.dart';
|
import 'package:spotube/services/kv_store/kv_store.dart';
|
||||||
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:spotube/services/wm_tools/wm_tools.dart';
|
import 'package:spotube/services/wm_tools/wm_tools.dart';
|
||||||
import 'package:spotube/themes/theme.dart';
|
import 'package:spotube/themes/theme.dart';
|
||||||
import 'package:spotube/utils/persisted_state_notifier.dart';
|
import 'package:spotube/utils/persisted_state_notifier.dart';
|
||||||
@ -44,98 +45,73 @@ import 'package:window_manager/window_manager.dart';
|
|||||||
|
|
||||||
Future<void> main(List<String> rawArgs) async {
|
Future<void> main(List<String> rawArgs) async {
|
||||||
final arguments = await startCLI(rawArgs);
|
final arguments = await startCLI(rawArgs);
|
||||||
|
AppLogger.initialize(arguments["verbose"]);
|
||||||
|
|
||||||
final widgetsBinding = WidgetsFlutterBinding.ensureInitialized();
|
AppLogger.runZoned(() async {
|
||||||
|
final widgetsBinding = WidgetsFlutterBinding.ensureInitialized();
|
||||||
|
|
||||||
await registerWindowsScheme("spotify");
|
await registerWindowsScheme("spotify");
|
||||||
|
|
||||||
tz.initializeTimeZones();
|
tz.initializeTimeZones();
|
||||||
|
|
||||||
FlutterNativeSplash.preserve(widgetsBinding: widgetsBinding);
|
FlutterNativeSplash.preserve(widgetsBinding: widgetsBinding);
|
||||||
|
|
||||||
MediaKit.ensureInitialized();
|
MediaKit.ensureInitialized();
|
||||||
|
|
||||||
// force High Refresh Rate on some Android devices (like One Plus)
|
// force High Refresh Rate on some Android devices (like One Plus)
|
||||||
if (kIsAndroid) {
|
if (kIsAndroid) {
|
||||||
await FlutterDisplayMode.setHighRefreshRate();
|
await FlutterDisplayMode.setHighRefreshRate();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (kIsDesktop) {
|
if (kIsDesktop) {
|
||||||
await windowManager.setPreventClose(true);
|
await windowManager.setPreventClose(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
await SystemTheme.accentColor.load();
|
await SystemTheme.accentColor.load();
|
||||||
|
|
||||||
if (!kIsWeb) {
|
if (!kIsWeb) {
|
||||||
MetadataGod.initialize();
|
MetadataGod.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (kIsWindows || kIsLinux) {
|
if (kIsWindows || kIsLinux) {
|
||||||
DiscordRPC.initialize();
|
DiscordRPC.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
await KVStoreService.initialize();
|
await KVStoreService.initialize();
|
||||||
|
|
||||||
final hiveCacheDir =
|
final hiveCacheDir =
|
||||||
kIsWeb ? null : (await getApplicationSupportDirectory()).path;
|
kIsWeb ? null : (await getApplicationSupportDirectory()).path;
|
||||||
|
|
||||||
Hive.init(hiveCacheDir);
|
Hive.init(hiveCacheDir);
|
||||||
|
|
||||||
Hive.registerAdapter(SkipSegmentAdapter());
|
Hive.registerAdapter(SkipSegmentAdapter());
|
||||||
|
|
||||||
Hive.registerAdapter(SourceMatchAdapter());
|
Hive.registerAdapter(SourceMatchAdapter());
|
||||||
Hive.registerAdapter(SourceTypeAdapter());
|
Hive.registerAdapter(SourceTypeAdapter());
|
||||||
|
|
||||||
// Cache versioning entities with Adapter
|
// Cache versioning entities with Adapter
|
||||||
SourceMatch.version = 'v1';
|
SourceMatch.version = 'v1';
|
||||||
SkipSegment.version = 'v1';
|
SkipSegment.version = 'v1';
|
||||||
|
|
||||||
await Hive.openLazyBox<SourceMatch>(
|
await Hive.openLazyBox<SourceMatch>(
|
||||||
SourceMatch.boxName,
|
SourceMatch.boxName,
|
||||||
path: hiveCacheDir,
|
path: hiveCacheDir,
|
||||||
);
|
);
|
||||||
await Hive.openLazyBox(
|
await Hive.openLazyBox(
|
||||||
SkipSegment.boxName,
|
SkipSegment.boxName,
|
||||||
path: hiveCacheDir,
|
path: hiveCacheDir,
|
||||||
);
|
);
|
||||||
await PersistedStateNotifier.initializeBoxes(
|
await PersistedStateNotifier.initializeBoxes(
|
||||||
path: hiveCacheDir,
|
path: hiveCacheDir,
|
||||||
);
|
);
|
||||||
|
|
||||||
if (kIsDesktop) {
|
if (kIsDesktop) {
|
||||||
await localNotifier.setup(appName: "Spotube");
|
await localNotifier.setup(appName: "Spotube");
|
||||||
await WindowManagerTools.initialize();
|
await WindowManagerTools.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
Catcher2(
|
runApp(const ProviderScope(child: Spotube()));
|
||||||
enableLogger: arguments["verbose"],
|
});
|
||||||
debugConfig: Catcher2Options(
|
|
||||||
SilentReportMode(),
|
|
||||||
[
|
|
||||||
ConsoleHandler(
|
|
||||||
enableDeviceParameters: false,
|
|
||||||
enableApplicationParameters: false,
|
|
||||||
),
|
|
||||||
if (!kIsWeb) FileHandler(await getLogsPath(), printLogs: false),
|
|
||||||
],
|
|
||||||
),
|
|
||||||
releaseConfig: Catcher2Options(
|
|
||||||
SilentReportMode(),
|
|
||||||
[
|
|
||||||
if (arguments["verbose"] ?? false) ConsoleHandler(),
|
|
||||||
if (!kIsWeb)
|
|
||||||
FileHandler(
|
|
||||||
await getLogsPath(),
|
|
||||||
printLogs: false,
|
|
||||||
),
|
|
||||||
],
|
|
||||||
),
|
|
||||||
runAppFunction: () {
|
|
||||||
runApp(
|
|
||||||
const ProviderScope(child: Spotube()),
|
|
||||||
);
|
|
||||||
},
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class Spotube extends HookConsumerWidget {
|
class Spotube extends HookConsumerWidget {
|
||||||
@ -166,6 +142,7 @@ class Spotube extends HookConsumerWidget {
|
|||||||
|
|
||||||
useEffect(() {
|
useEffect(() {
|
||||||
FlutterNativeSplash.remove();
|
FlutterNativeSplash.remove();
|
||||||
|
|
||||||
return () {
|
return () {
|
||||||
/// For enabling hot reload for audio player
|
/// For enabling hot reload for audio player
|
||||||
if (!kDebugMode) return;
|
if (!kDebugMode) return;
|
||||||
|
@ -73,10 +73,10 @@ class AuthenticationCredentials {
|
|||||||
),
|
),
|
||||||
);
|
);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
if (rootNavigatorKey?.currentContext != null) {
|
if (rootNavigatorKey.currentContext != null) {
|
||||||
showPromptDialog(
|
showPromptDialog(
|
||||||
context: rootNavigatorKey!.currentContext!,
|
context: rootNavigatorKey.currentContext!,
|
||||||
title: rootNavigatorKey!.currentContext!.l10n
|
title: rootNavigatorKey.currentContext!.l10n
|
||||||
.error("Authentication Failure"),
|
.error("Authentication Failure"),
|
||||||
message: e.toString(),
|
message: e.toString(),
|
||||||
cancelText: null,
|
cancelText: null,
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import 'dart:convert';
|
import 'dart:convert';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
import 'package:spotify/spotify.dart';
|
import 'package:spotify/spotify.dart';
|
||||||
import 'package:spotube/models/connect/connect.dart';
|
import 'package:spotube/models/connect/connect.dart';
|
||||||
@ -99,10 +99,7 @@ class ConnectNotifier extends AsyncNotifier<WebSocketChannel?> {
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
onError: (error) {
|
onError: (error) {
|
||||||
Catcher2.reportCheckedError(
|
AppLogger.reportError(error, StackTrace.current);
|
||||||
error,
|
|
||||||
StackTrace.current,
|
|
||||||
);
|
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -113,7 +110,7 @@ class ConnectNotifier extends AsyncNotifier<WebSocketChannel?> {
|
|||||||
|
|
||||||
return channel;
|
return channel;
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
rethrow;
|
rethrow;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3,7 +3,7 @@ import 'dart:convert';
|
|||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
import 'dart:math';
|
import 'dart:math';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:shelf/shelf.dart';
|
import 'package:shelf/shelf.dart';
|
||||||
import 'package:shelf/shelf_io.dart';
|
import 'package:shelf/shelf_io.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
@ -215,7 +215,7 @@ final connectServerProvider = FutureProvider((ref) async {
|
|||||||
ref.read(volumeProvider.notifier).setVolume(event.data);
|
ref.read(volumeProvider.notifier).setVolume(event.data);
|
||||||
});
|
});
|
||||||
} catch (e, stackTrace) {
|
} catch (e, stackTrace) {
|
||||||
Catcher2.reportCheckedError(e, stackTrace);
|
AppLogger.reportError(e, stackTrace);
|
||||||
channel.sink.add(WebSocketErrorEvent(e.toString()).toJson());
|
channel.sink.add(WebSocketErrorEvent(e.toString()).toJson());
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:collection/collection.dart';
|
import 'package:collection/collection.dart';
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:flutter_cache_manager/flutter_cache_manager.dart';
|
import 'package:flutter_cache_manager/flutter_cache_manager.dart';
|
||||||
@ -130,7 +130,7 @@ class DownloadManagerProvider extends ChangeNotifier {
|
|||||||
|
|
||||||
return Uint8List.fromList(bytes);
|
return Uint8List.fromList(bytes);
|
||||||
} catch (e, stackTrace) {
|
} catch (e, stackTrace) {
|
||||||
Catcher2.reportCheckedError(e, stackTrace);
|
AppLogger.reportError(e, stackTrace);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -216,7 +216,7 @@ class DownloadManagerProvider extends ChangeNotifier {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
Catcher2.reportCheckedError(e, StackTrace.current);
|
AppLogger.reportError(e, StackTrace.current);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
||||||
import 'package:metadata_god/metadata_god.dart';
|
import 'package:metadata_god/metadata_god.dart';
|
||||||
@ -56,7 +56,7 @@ final localTracksProvider =
|
|||||||
try {
|
try {
|
||||||
entities.addAll(Directory(location).listSync(recursive: true));
|
entities.addAll(Directory(location).listSync(recursive: true));
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -92,7 +92,7 @@ final localTracksProvider =
|
|||||||
if (e is FfiException) {
|
if (e is FfiException) {
|
||||||
return {"file": file};
|
return {"file": file};
|
||||||
}
|
}
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@ -119,7 +119,7 @@ final localTracksProvider =
|
|||||||
}
|
}
|
||||||
return tracks;
|
return tracks;
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
import 'package:piped_client/piped_client.dart';
|
import 'package:piped_client/piped_client.dart';
|
||||||
import 'package:spotube/services/sourced_track/sources/piped.dart';
|
import 'package:spotube/services/sourced_track/sources/piped.dart';
|
||||||
@ -10,7 +10,7 @@ final pipedInstancesFutureProvider = FutureProvider<List<PipedInstance>>(
|
|||||||
|
|
||||||
return await pipedClient.instanceList();
|
return await pipedClient.instanceList();
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
return <PipedInstance>[];
|
return <PipedInstance>[];
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:palette_generator/palette_generator.dart';
|
import 'package:palette_generator/palette_generator.dart';
|
||||||
import 'package:spotube/components/image/universal_image.dart';
|
import 'package:spotube/components/image/universal_image.dart';
|
||||||
import 'package:spotube/extensions/image.dart';
|
import 'package:spotube/extensions/image.dart';
|
||||||
@ -86,7 +86,7 @@ extension ProxyPlaylistListeners on ProxyPlaylistNotifier {
|
|||||||
history.addTrack(playlist.activeTrack!);
|
history.addTrack(playlist.activeTrack!);
|
||||||
lastScrobbled = uid;
|
lastScrobbled = uid;
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:dio/dio.dart';
|
import 'package:dio/dio.dart';
|
||||||
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
||||||
import 'package:spotube/models/skip_segment.dart';
|
import 'package:spotube/models/skip_segment.dart';
|
||||||
@ -71,7 +71,7 @@ Future<List<SkipSegment>> getAndCacheSkipSegments(String id) async {
|
|||||||
return List.castFrom<dynamic, SkipSegment>(segments);
|
return List.castFrom<dynamic, SkipSegment>(segments);
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
await SkipSegment.box.put(id, []);
|
await SkipSegment.box.put(id, []);
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
return List.castFrom<dynamic, SkipSegment>([]);
|
return List.castFrom<dynamic, SkipSegment>([]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
import 'package:scrobblenaut/scrobblenaut.dart';
|
import 'package:scrobblenaut/scrobblenaut.dart';
|
||||||
import 'package:spotify/spotify.dart';
|
import 'package:spotify/spotify.dart';
|
||||||
@ -52,7 +52,7 @@ class ScrobblerNotifier extends PersistedStateNotifier<ScrobblerState?> {
|
|||||||
trackNumber: track.trackNumber,
|
trackNumber: track.trackNumber,
|
||||||
);
|
);
|
||||||
} catch (e, stackTrace) {
|
} catch (e, stackTrace) {
|
||||||
Catcher2.reportCheckedError(e, stackTrace);
|
AppLogger.reportError(e, stackTrace);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
import 'dart:math';
|
import 'dart:math';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:dio/dio.dart' hide Response;
|
import 'package:dio/dio.dart' hide Response;
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
@ -108,7 +108,7 @@ class PlaybackServer {
|
|||||||
headers: res.headers.map,
|
headers: res.headers.map,
|
||||||
);
|
);
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
return Response.internalServerError();
|
return Response.internalServerError();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -145,7 +145,7 @@ class SyncedLyricsNotifier extends FamilyAsyncNotifier<SubtitleSimple, Track?>
|
|||||||
|
|
||||||
return lyrics;
|
return lyrics;
|
||||||
} catch (e, stackTrace) {
|
} catch (e, stackTrace) {
|
||||||
Catcher2.reportCheckedError(e, stackTrace);
|
AppLogger.reportError(e, stackTrace);
|
||||||
rethrow;
|
rethrow;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -24,7 +24,7 @@ final generatePlaylistProvider = FutureProvider.autoDispose
|
|||||||
?.cast<String, num>(),
|
?.cast<String, num>(),
|
||||||
)
|
)
|
||||||
.catchError((e, stackTrace) {
|
.catchError((e, stackTrace) {
|
||||||
Catcher2.reportCheckedError(e, stackTrace);
|
AppLogger.reportError(e, stackTrace);
|
||||||
return Recommendations();
|
return Recommendations();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -2,7 +2,7 @@ library spotify;
|
|||||||
|
|
||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:collection/collection.dart';
|
import 'package:collection/collection.dart';
|
||||||
import 'package:dio/dio.dart';
|
import 'package:dio/dio.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:spotify/spotify.dart';
|
import 'package:spotify/spotify.dart';
|
||||||
import 'package:spotube/models/local_track.dart';
|
import 'package:spotube/models/local_track.dart';
|
||||||
@ -57,7 +57,7 @@ abstract class AudioPlayerInterface {
|
|||||||
),
|
),
|
||||||
) {
|
) {
|
||||||
_mkPlayer.stream.error.listen((event) {
|
_mkPlayer.stream.error.listen((event) {
|
||||||
Catcher2.reportCheckedError(event, StackTrace.current);
|
AppLogger.reportError(event, StackTrace.current);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:media_kit/media_kit.dart';
|
import 'package:media_kit/media_kit.dart';
|
||||||
import 'package:flutter_broadcasts/flutter_broadcasts.dart';
|
import 'package:flutter_broadcasts/flutter_broadcasts.dart';
|
||||||
import 'package:package_info_plus/package_info_plus.dart';
|
import 'package:package_info_plus/package_info_plus.dart';
|
||||||
@ -48,7 +48,7 @@ class CustomPlayer extends Player {
|
|||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
stream.error.listen((event) {
|
stream.error.listen((event) {
|
||||||
Catcher2.reportCheckedError('[MediaKitError] \n$event', null);
|
AppLogger.reportError('[MediaKitError] \n$event', StackTrace.current);
|
||||||
}),
|
}),
|
||||||
];
|
];
|
||||||
PackageInfo.fromPlatform().then((packageInfo) {
|
PackageInfo.fromPlatform().then((packageInfo) {
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
import 'dart:collection';
|
import 'dart:collection';
|
||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:collection/collection.dart';
|
import 'package:collection/collection.dart';
|
||||||
|
|
||||||
import 'package:dio/dio.dart';
|
import 'package:dio/dio.dart';
|
||||||
@ -148,7 +148,7 @@ class DownloadManager {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (e, stackTrace) {
|
} catch (e, stackTrace) {
|
||||||
Catcher2.reportCheckedError(e, stackTrace);
|
AppLogger.reportError(e, stackTrace);
|
||||||
|
|
||||||
var task = getDownload(url)!;
|
var task = getDownload(url)!;
|
||||||
if (task.status.value != DownloadStatus.canceled &&
|
if (task.status.value != DownloadStatus.canceled &&
|
||||||
|
53
lib/services/logger/logger.dart
Normal file
53
lib/services/logger/logger.dart
Normal file
@ -0,0 +1,53 @@
|
|||||||
|
import 'dart:async';
|
||||||
|
import 'dart:isolate';
|
||||||
|
|
||||||
|
import 'package:flutter/foundation.dart';
|
||||||
|
import 'package:logger/logger.dart';
|
||||||
|
|
||||||
|
class AppLogger {
|
||||||
|
static late final Logger log;
|
||||||
|
|
||||||
|
static initialize(bool verbose) {
|
||||||
|
log = Logger(
|
||||||
|
level: kDebugMode || (verbose && kReleaseMode) ? Level.all : Level.info,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
static R? runZoned<R>(R Function() body) {
|
||||||
|
FlutterError.onError = (details) {
|
||||||
|
reportError(details.exception, details.stack ?? StackTrace.current);
|
||||||
|
};
|
||||||
|
|
||||||
|
PlatformDispatcher.instance.onError = (error, stackTrace) {
|
||||||
|
reportError(error, stackTrace);
|
||||||
|
return true;
|
||||||
|
};
|
||||||
|
|
||||||
|
if (!kIsWeb) {
|
||||||
|
Isolate.current.addErrorListener(
|
||||||
|
RawReceivePort((pair) async {
|
||||||
|
final isolateError = pair as List<dynamic>;
|
||||||
|
reportError(
|
||||||
|
isolateError.first.toString(),
|
||||||
|
isolateError.last,
|
||||||
|
);
|
||||||
|
}).sendPort,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
return runZonedGuarded<R>(
|
||||||
|
body,
|
||||||
|
(error, stackTrace) {
|
||||||
|
reportError(error, stackTrace);
|
||||||
|
},
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void reportError(
|
||||||
|
dynamic error, [
|
||||||
|
StackTrace? stackTrace,
|
||||||
|
message = "",
|
||||||
|
]) {
|
||||||
|
log.e(message, error: error, stackTrace: stackTrace);
|
||||||
|
}
|
||||||
|
}
|
@ -2,7 +2,7 @@ library song_link;
|
|||||||
|
|
||||||
import 'dart:convert';
|
import 'dart:convert';
|
||||||
|
|
||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:dio/dio.dart';
|
import 'package:dio/dio.dart';
|
||||||
import 'package:freezed_annotation/freezed_annotation.dart';
|
import 'package:freezed_annotation/freezed_annotation.dart';
|
||||||
import 'package:html/parser.dart';
|
import 'package:html/parser.dart';
|
||||||
@ -47,7 +47,7 @@ abstract class SongLinkService {
|
|||||||
return songLinks?.map((link) => SongLink.fromJson(link)).toList() ??
|
return songLinks?.map((link) => SongLink.fromJson(link)).toList() ??
|
||||||
<SongLink>[];
|
<SongLink>[];
|
||||||
} catch (e, stackTrace) {
|
} catch (e, stackTrace) {
|
||||||
Catcher2.reportCheckedError(e, stackTrace);
|
AppLogger.reportError(e, stackTrace);
|
||||||
return <SongLink>[];
|
return <SongLink>[];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,9 +1,9 @@
|
|||||||
import 'package:catcher_2/core/catcher_2.dart';
|
|
||||||
import 'package:collection/collection.dart';
|
import 'package:collection/collection.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
import 'package:http/http.dart';
|
import 'package:http/http.dart';
|
||||||
import 'package:spotify/spotify.dart';
|
import 'package:spotify/spotify.dart';
|
||||||
import 'package:spotube/models/source_match.dart';
|
import 'package:spotube/models/source_match.dart';
|
||||||
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
import 'package:spotube/services/song_link/song_link.dart';
|
import 'package:spotube/services/song_link/song_link.dart';
|
||||||
import 'package:spotube/services/sourced_track/enums.dart';
|
import 'package:spotube/services/sourced_track/enums.dart';
|
||||||
import 'package:spotube/services/sourced_track/exceptions.dart';
|
import 'package:spotube/services/sourced_track/exceptions.dart';
|
||||||
@ -236,7 +236,7 @@ class YoutubeSourcedTrack extends SourcedTrack {
|
|||||||
];
|
];
|
||||||
} on VideoUnplayableException catch (e, stack) {
|
} on VideoUnplayableException catch (e, stack) {
|
||||||
// Ignore this error and continue with the search
|
// Ignore this error and continue with the search
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
import 'package:catcher_2/catcher_2.dart';
|
import 'package:spotube/services/logger/logger.dart';
|
||||||
|
|
||||||
/// Parses duration string formatted by Duration.toString() to [Duration].
|
/// Parses duration string formatted by Duration.toString() to [Duration].
|
||||||
/// The string should be of form hours:minutes:seconds.microseconds
|
/// The string should be of form hours:minutes:seconds.microseconds
|
||||||
@ -51,7 +51,7 @@ Duration? tryParseDuration(String input) {
|
|||||||
try {
|
try {
|
||||||
return parseDuration(input);
|
return parseDuration(input);
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
Catcher2.reportCheckedError(e, stack);
|
AppLogger.reportError(e, stack);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user