[READ ONLY MIRROR] Open Source TikTok alternative built on AT Protocol github.com/sprksocial/client
flutter atproto video dart
10
fork

Configure Feed

Select the types of activity you want to include in your feed.

perf: resource management and memory leaks

+30 -1
+5 -1
lib/src/core/storage/cache/download_manager_impl.dart
··· 241 241 task.onComplete(task); 242 242 } catch (e, s) { 243 243 task.status = DownloadTaskStatus.failed; 244 - _logger.w('Failed to cache media for ${task.uri}'); 244 + _logger.w( 245 + 'Failed to cache media for ${task.uri}', 246 + error: e, 247 + stackTrace: s, 248 + ); 245 249 task.onError(task, e, s); 246 250 } finally { 247 251 // Remove from the main queue regardless of outcome, as it's processed.
+19
lib/src/features/posting/providers/camera_provider.dart
··· 1 1 import 'dart:async'; 2 2 3 3 import 'package:camera/camera.dart'; 4 + import 'package:flutter/material.dart'; 4 5 import 'package:flutter/scheduler.dart'; 5 6 import 'package:get_it/get_it.dart'; 6 7 import 'package:riverpod_annotation/riverpod_annotation.dart'; ··· 12 13 @riverpod 13 14 class Camera extends _$Camera { 14 15 late final SparkLogger _logger; 16 + AppLifecycleListener? _lifecycleListener; 15 17 16 18 @override 17 19 FutureOr<CameraState> build() async { 18 20 _logger = GetIt.instance<LogService>().getLogger('Camera'); 19 21 20 22 ref.onDispose(_disposeCamera); 23 + 24 + // Listen to app lifecycle to dispose camera when backgrounded 25 + _lifecycleListener = AppLifecycleListener( 26 + onHide: _onAppBackgrounded, 27 + onInactive: _onAppBackgrounded, 28 + ); 21 29 22 30 _logger.i('Initializing camera provider'); 23 31 ··· 313 321 Future<void> _disposeCamera() async { 314 322 _logger.d('Disposing camera'); 315 323 324 + // Dispose lifecycle listener to prevent further callbacks 325 + _lifecycleListener?.dispose(); 326 + _lifecycleListener = null; 327 + 316 328 try { 317 329 final currentState = state.value; 318 330 final controller = currentState?.controller; ··· 373 385 _logger.d('Clearing camera error'); 374 386 state = AsyncValue.data(currentState.copyWith(error: null)); 375 387 } 388 + } 389 + 390 + /// Handles app lifecycle changes when app is backgrounded or becomes inactive. 391 + /// Disposes the camera to free resources and prevent battery drain. 392 + void _onAppBackgrounded() { 393 + _logger.i('App backgrounded/inactive, disposing camera'); 394 + _disposeCamera(); 376 395 } 377 396 378 397 Future<void> disposeCamera() async {
+6
lib/src/features/posting/providers/recording_provider.dart
··· 25 25 state = state.copyWith(isRecording: true, error: null); 26 26 27 27 _timer = Timer.periodic(const Duration(milliseconds: 100), (timer) { 28 + // Guard against accessing state after provider disposal 29 + if (!ref.mounted) { 30 + timer.cancel(); 31 + return; 32 + } 33 + 28 34 final newDuration = 29 35 state.elapsedDuration + const Duration(milliseconds: 100); 30 36