diff --git a/analysis_options.yaml b/analysis_options.yaml index af222653..61a0efe1 100644 --- a/analysis_options.yaml +++ b/analysis_options.yaml @@ -37,4 +37,3 @@ analyzer: - "**.g.dart" - "**.gr.dart" - "**/generated_plugin_registrant.dart" - - test/**/*.dart diff --git a/lib/main.dart b/lib/main.dart index 1c933547..da53668e 100644 --- a/lib/main.dart +++ b/lib/main.dart @@ -21,6 +21,7 @@ import 'package:spotube/collections/env.dart'; import 'package:spotube/collections/initializers.dart'; import 'package:spotube/collections/intents.dart'; import 'package:spotube/collections/routes.dart'; +import 'package:spotube/collections/vars.dart'; import 'package:spotube/hooks/configurators/use_close_behavior.dart'; import 'package:spotube/hooks/configurators/use_deep_linking.dart'; import 'package:spotube/hooks/configurators/use_disable_battery_optimizations.dart'; @@ -67,13 +68,12 @@ Future main(List rawArgs) async { AppLogger.runZoned(() async { final widgetsBinding = WidgetsFlutterBinding.ensureInitialized(); - GetIt.I.registerSingleton( - await SharedPreferences.getInstance(), - ); - GetIt.I.registerSingletonWithDependencies( + getIt.registerSingleton(await SharedPreferences.getInstance()); + getIt.registerSingletonWithDependencies( () => KVStoreService.init(), dependsOn: [SharedPreferences], ); + getIt.registerSingleton(SpotubeAudioPlayer()); await registerWindowsScheme("spotify"); diff --git a/lib/provider/volume_provider.dart b/lib/provider/volume_provider.dart index 969df8c8..00f275ba 100644 --- a/lib/provider/volume_provider.dart +++ b/lib/provider/volume_provider.dart @@ -5,25 +5,21 @@ import 'package:spotube/services/audio_player/audio_player.dart'; import 'package:spotube/services/kv_store/kv_store.dart'; class VolumeProvider extends Notifier { - final SpotubeAudioPlayer _audioPlayer; - - VolumeProvider({ - required SpotubeAudioPlayer audioPlayer, - }) : _audioPlayer = audioPlayer; + VolumeProvider(); @override build() { - _audioPlayer.setVolume(KVStoreService().volume); + audioPlayer.setVolume(KVStoreService().volume); return KVStoreService().volume; } Future setVolume(double volume) async { state = volume; - await _audioPlayer.setVolume(volume); - KVStoreService().setVolume(volume); + await audioPlayer.setVolume(volume); + await KVStoreService().setVolume(volume); } } final volumeProvider = NotifierProvider(() { - return VolumeProvider(audioPlayer: audioPlayer); + return VolumeProvider(); }); diff --git a/lib/services/audio_player/audio_player.dart b/lib/services/audio_player/audio_player.dart index 4febecdf..fd5e8727 100644 --- a/lib/services/audio_player/audio_player.dart +++ b/lib/services/audio_player/audio_player.dart @@ -1,6 +1,7 @@ import 'dart:io'; import 'package:media_kit/media_kit.dart' hide Track; +import 'package:spotube/collections/vars.dart'; import 'package:spotube/services/logger/logger.dart'; import 'package:flutter/foundation.dart'; import 'package:spotify/spotify.dart' hide Playlist; diff --git a/lib/services/audio_player/audio_player_impl.dart b/lib/services/audio_player/audio_player_impl.dart index 82c8c906..5d0e2941 100644 --- a/lib/services/audio_player/audio_player_impl.dart +++ b/lib/services/audio_player/audio_player_impl.dart @@ -1,6 +1,8 @@ part of 'audio_player.dart'; -final audioPlayer = SpotubeAudioPlayer(); +SpotubeAudioPlayer get audioPlayer { + return getIt.get(); +} class SpotubeAudioPlayer extends AudioPlayerInterface with SpotubeAudioPlayersStreams { diff --git a/lib/services/kv_store/kv_store.dart b/lib/services/kv_store/kv_store.dart index 012b60d7..801f1a69 100644 --- a/lib/services/kv_store/kv_store.dart +++ b/lib/services/kv_store/kv_store.dart @@ -7,9 +7,9 @@ import 'package:spotube/models/database/database.dart'; import 'package:spotube/services/wm_tools/wm_tools.dart'; import 'package:uuid/uuid.dart'; -final class KVStoreService { +class KVStoreService { factory KVStoreService() { - return getIt(); + return getIt.get(); } KVStoreService.init(); diff --git a/pubspec.yaml b/pubspec.yaml index d129992b..cdb99327 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -161,7 +161,6 @@ dev_dependencies: pub_api_client: ^3.0.0 xml: ^6.5.0 io: ^1.0.4 - test: ^1.25.2 mocktail: ^1.0.4 drift_dev: ^2.21.0 auto_route_generator: ^9.0.0 diff --git a/test/provider/volume_provider_test.dart b/test/provider/volume_provider_test.dart deleted file mode 100644 index 8484ca87..00000000 --- a/test/provider/volume_provider_test.dart +++ /dev/null @@ -1,40 +0,0 @@ -import 'package:flutter_test/flutter_test.dart'; -import 'package:hooks_riverpod/hooks_riverpod.dart'; -import 'package:spotube/provider/volume_provider.dart'; -import 'package:spotube/services/audio_player/audio_player.dart'; -import 'package:spotube/services/kv_store/kv_store.dart'; - -void main() { - late ProviderContainer container; - late VolumeProvider volumeProvider; - - setUp(() { - container = ProviderContainer(); - volumeProvider = container.read(volumeProvider.notifier); - }); - - tearDown(() { - container.dispose(); - }); - - test('initial volume is set from KVStore', () { - expect(container.read(volumeProvider), KVStoreService().volume); - }); - - test('setVolume updates state and KVStore', () async { - const testVolume = 0.75; - await volumeProvider.setVolume(testVolume); - - expect(container.read(volumeProvider), testVolume); - expect(KVStoreService().volume, testVolume); - }); - - test('setVolume updates audio player', () async { - const testVolume = 0.5; - await volumeProvider.setVolume(testVolume); - - // Verify that the audio player's volume was set - // Note: This assumes audioPlayer.setVolume is properly mocked or can be verified - expect(audioPlayer.volume, testVolume); - }); -} diff --git a/test/providers/volume_provider_test.dart b/test/providers/volume_provider_test.dart new file mode 100644 index 00000000..0254d91e --- /dev/null +++ b/test/providers/volume_provider_test.dart @@ -0,0 +1,63 @@ +import 'package:flutter_test/flutter_test.dart'; +import 'package:hooks_riverpod/hooks_riverpod.dart'; +import 'package:mocktail/mocktail.dart'; +import 'package:spotube/collections/vars.dart'; +import 'package:spotube/provider/volume_provider.dart'; +import 'package:spotube/services/audio_player/audio_player.dart'; +import 'package:spotube/services/kv_store/kv_store.dart'; + +class MockSpotubeAudioPlayer extends Mock implements SpotubeAudioPlayer {} + +class MockKVStoreService extends Mock implements KVStoreService {} + +void main() { + TestWidgetsFlutterBinding.ensureInitialized(); + + late ProviderContainer container; + late SpotubeAudioPlayer audioPlayer; + late KVStoreService kvStoreService; + + setUp(() { + kvStoreService = + getIt.registerSingleton(MockKVStoreService()); + audioPlayer = + getIt.registerSingleton(MockSpotubeAudioPlayer()); + container = ProviderContainer(); + + when(() => kvStoreService.volume).thenAnswer((_) => 1.0); + when(() => kvStoreService.setVolume(any())).thenAnswer((_) async {}); + when(() => audioPlayer.setVolume(any())).thenAnswer((_) async {}); + }); + + tearDown(() { + getIt.reset(); + container.dispose(); + }); + + group("VolumeProvider", () { + test("initial volume should be 1", () { + final volume = container.read(volumeProvider); + + expect(volume, 1.0); + }); + + group("setVolume", () { + test("should set volume to specified value", () async { + await container.read(volumeProvider.notifier).setVolume(0.5); + + final volume = container.read(volumeProvider); + expect(volume, 0.5); + }); + test("should update audioPlayer volume", () { + container.read(volumeProvider.notifier).setVolume(0.5); + + verify(() => audioPlayer.setVolume(0.5)).called(1); + }); + test("should persist the volume", () async { + await container.read(volumeProvider.notifier).setVolume(0.5); + + verify(() => kvStoreService.setVolume(0.5)).called(1); + }); + }); + }); +}