From 324d8cd8c87802f56874caa16267cc8de68bf0e0 Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Wed, 3 Jan 2024 20:20:37 +0530 Subject: [PATCH 01/19] written test for post_modal.dart --- lib/widgets/post_modal.dart | 4 + .../widget_tests/widgets/post_modal_test.dart | 160 ++++++++++++++++++ 2 files changed, 164 insertions(+) create mode 100644 test/widget_tests/widgets/post_modal_test.dart diff --git a/lib/widgets/post_modal.dart b/lib/widgets/post_modal.dart index 327934b01..35d9ba054 100644 --- a/lib/widgets/post_modal.dart +++ b/lib/widgets/post_modal.dart @@ -44,6 +44,7 @@ class PostBottomModal extends StatelessWidget { ), ), TextButton( + key: const Key('reportPost'), onPressed: () { navigationService.showTalawaErrorSnackBar( 'Your Report has been sent to the Admin', @@ -74,6 +75,7 @@ class PostBottomModal extends StatelessWidget { ), ), TextButton( + key: const Key('deletePost'), onPressed: () { deletePost != null ? deletePost!(post) @@ -89,6 +91,7 @@ class PostBottomModal extends StatelessWidget { ), actions: [ TextButton( + key: const Key('yes'), onPressed: () { navigationService.showTalawaErrorSnackBar( 'Post was deleted if you had the rights!', @@ -99,6 +102,7 @@ class PostBottomModal extends StatelessWidget { child: const Text("Yes"), ), TextButton( + key: const Key('no'), onPressed: () { Navigator.pop(context); }, diff --git a/test/widget_tests/widgets/post_modal_test.dart b/test/widget_tests/widgets/post_modal_test.dart new file mode 100644 index 000000000..05854296b --- /dev/null +++ b/test/widget_tests/widgets/post_modal_test.dart @@ -0,0 +1,160 @@ +import 'package:flutter/material.dart'; +import 'package:flutter_localizations/flutter_localizations.dart'; +import 'package:flutter_test/flutter_test.dart'; +import 'package:mockito/mockito.dart'; +import 'package:talawa/enums/enums.dart'; +import 'package:talawa/models/comment/comment_model.dart'; +import 'package:talawa/models/organization/org_info.dart'; +import 'package:talawa/models/post/post_model.dart'; +import 'package:talawa/models/user/user_info.dart'; +import 'package:talawa/services/navigation_service.dart'; +import 'package:talawa/services/size_config.dart'; +import 'package:talawa/utils/app_localization.dart'; +import 'package:talawa/view_model/lang_view_model.dart'; +import 'package:talawa/views/base_view.dart'; +import 'package:talawa/widgets/post_modal.dart'; + +import '../../helpers/test_helpers.dart'; +import '../../helpers/test_locator.dart'; + +class MockFunction extends Mock { + void call(Post post); +} + +class MockNavigationService extends Mock implements NavigationService {} + +final MockFunction mockDeletePost = MockFunction(); +final LikedBy user = LikedBy(sId: "test_id"); + +final u1 = User( + id: '123', + firstName: 'Lakshay', + lastName: 'Gupta', + email: 'test@test.com', +); +final u2 = User( + id: '123', + firstName: 'Ankit', + lastName: 'Varshney', + email: 'test@test.com', +); +final List users = [u1, u2]; +List comments = [ + Comments(sId: 'comment1'), + Comments(sId: 'comment2'), + Comments(sId: 'comment3'), + Comments(sId: 'comment4'), + Comments(sId: 'comment5'), + Comments(sId: 'comment6'), +]; +final comment = Comment( + creator: User( + id: '123', + firstName: 'Ankit', + lastName: 'Varshney', + email: 'test@test.com', + ), + createdAt: '123456', + text: 'test text', + post: 'test post', + likeCount: 'test count', +); + +final LikedBy l1 = LikedBy(sId: 'test1'); +final LikedBy l2 = LikedBy(sId: 'test2'); +final List likeby = [l1, l2]; + +final comment1 = Comments(sId: 'comment1'); +final comment2 = Comments(sId: 'comment2'); +final comment3 = Comments(sId: 'comment3'); +final List comments1 = [comment1, comment2, comment3]; + +final myBirthday = DateTime.utc(2004, DateTime.june, 16, 5, 30, 0, 0, 0); +final post = Post( + creator: User( + id: '123', + firstName: 'John', + lastName: 'Doe', + email: 'test@test.com', + ), + sId: "sid", + createdAt: myBirthday, + description: 'test description', + organization: OrgInfo(admins: users), + likedBy: likeby, + comments: comments1, +); +Widget createPostBottomModal() { + return BaseView( + onModelReady: (model) => model.initialize(), + builder: (context, model, child) { + return MaterialApp( + locale: const Locale('en'), + localizationsDelegates: const [ + AppLocalizationsDelegate(isTest: true), + GlobalMaterialLocalizations.delegate, + GlobalWidgetsLocalizations.delegate, + ], + home: PostBottomModal( + post: post, + deletePost: mockDeletePost, + ), + navigatorKey: navigationService.navigatorKey, + ); + }, + ); +} + +void main() { + SizeConfig().test(); + testSetupLocator(); + + setUp(() { + registerServices(); + }); + tearDown(() => unregisterServices()); + + group('PostBottomModalTest -', () { + testWidgets('has a post widget', (tester) async { + await tester.pumpWidget(createPostBottomModal()); + await tester.pumpAndSettle(); + + expect(find.byType(PostBottomModal), findsOneWidget); + expect(find.byKey(const Key('reportPost')), findsOneWidget); + + await tester.tap(find.byKey(const Key('reportPost'))); + await tester.pumpAndSettle(); + verify( + navigationService.showTalawaErrorSnackBar( + 'Your Report has been sent to the Admin', + MessageType.info, + ), + ).called(1); + }); + testWidgets('Testing the delete Post button', (WidgetTester tester) async { + await tester.pumpWidget(createPostBottomModal()); + await tester.pumpAndSettle(); + expect(find.byIcon(Icons.delete), findsOneWidget); + expect(find.byKey(const Key("deletePost")), findsOneWidget); + await tester.tap(find.byKey(const Key("deletePost"))); + await tester.pumpAndSettle(); + + verify(mockDeletePost.call(post)).called(1); + + expect(find.byType(AlertDialog), findsOneWidget); + expect(find.byKey(const Key("yes")), findsOneWidget); + expect(find.byKey(const Key('no')), findsOneWidget); + expect(find.text("The post was deleted"), findsOneWidget); + + await tester.tap(find.byKey(const Key("yes"))); + await tester.pumpAndSettle(); + + verify( + navigationService.showTalawaErrorSnackBar( + 'Post was deleted if you had the rights!', + MessageType.info, + ), + ).called(1); + }); + }); +} From bef405a1b04701139cdffb187eb2b7f6fe035347 Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Sun, 7 Jan 2024 01:19:41 +0530 Subject: [PATCH 02/19] written the missing test --- pubspec.lock | 40 +++++++++++++++---- .../widget_tests/widgets/post_modal_test.dart | 18 ++++++++- 2 files changed, 49 insertions(+), 9 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index d8d0d720c..eaa73413a 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -1013,6 +1013,30 @@ packages: url: "https://pub.dev" source: hosted version: "6.7.1" + leak_tracker: + dependency: transitive + description: + name: leak_tracker + sha256: "41b90ceaec6d79819f31e975e61d479516efe701dea35f891b2f986c1b031422" + url: "https://pub.dev" + source: hosted + version: "9.0.17" + leak_tracker_flutter_testing: + dependency: transitive + description: + name: leak_tracker_flutter_testing + sha256: "54808cfcfa87dbc0d74c61ac063d624adf1bd5c0407301f32b06c783c60dc4ca" + url: "https://pub.dev" + source: hosted + version: "2.0.0" + leak_tracker_testing: + dependency: transitive + description: + name: leak_tracker_testing + sha256: "7e71be3c161472f6c9158ac8875dd8de575060d60b5d159ebca3600ea32c9116" + url: "https://pub.dev" + source: hosted + version: "1.0.6" lint: dependency: "direct dev" description: @@ -1033,26 +1057,26 @@ packages: dependency: transitive description: name: matcher - sha256: "1803e76e6653768d64ed8ff2e1e67bea3ad4b923eb5c56a295c3e634bad5960e" + sha256: d2323aa2060500f906aa31a895b4030b6da3ebdcc5619d14ce1aada65cd161cb url: "https://pub.dev" source: hosted - version: "0.12.16" + version: "0.12.16+1" material_color_utilities: dependency: transitive description: name: material_color_utilities - sha256: "9528f2f296073ff54cb9fee677df673ace1218163c3bc7628093e7eed5203d41" + sha256: "0e0a020085b65b6083975e499759762399b4475f766c21668c4ecca34ea74e5a" url: "https://pub.dev" source: hosted - version: "0.5.0" + version: "0.8.0" meta: dependency: transitive description: name: meta - sha256: a6e590c838b18133bb482a2745ad77c5bb7715fb0451209e1a7567d416678b8e + sha256: d584fa6707a52763a52446f02cc621b077888fb63b93bbcb1143a7be5a0c0c04 url: "https://pub.dev" source: hosted - version: "1.10.0" + version: "1.11.0" mime: dependency: transitive description: @@ -1137,10 +1161,10 @@ packages: dependency: transitive description: name: path - sha256: "8829d8a55c13fc0e37127c29fedf290c102f4e40ae94ada574091fe0ff96c917" + sha256: "087ce49c3f0dc39180befefc60fdb4acd8f8620e5682fe2476afd0b3688bb4af" url: "https://pub.dev" source: hosted - version: "1.8.3" + version: "1.9.0" path_parsing: dependency: transitive description: diff --git a/test/widget_tests/widgets/post_modal_test.dart b/test/widget_tests/widgets/post_modal_test.dart index 05854296b..fa0b8ac3b 100644 --- a/test/widget_tests/widgets/post_modal_test.dart +++ b/test/widget_tests/widgets/post_modal_test.dart @@ -143,9 +143,9 @@ void main() { expect(find.byType(AlertDialog), findsOneWidget); expect(find.byKey(const Key("yes")), findsOneWidget); - expect(find.byKey(const Key('no')), findsOneWidget); expect(find.text("The post was deleted"), findsOneWidget); + await tester.pumpAndSettle(); await tester.tap(find.byKey(const Key("yes"))); await tester.pumpAndSettle(); @@ -156,5 +156,21 @@ void main() { ), ).called(1); }); + testWidgets("Testing no button of alertDialogBox", + (WidgetTester tester) async { + await tester.pumpWidget(createPostBottomModal()); + await tester.pumpAndSettle(); + expect(find.byKey(const Key("deletePost")), findsOneWidget); + await tester.tap(find.byKey(const Key("deletePost"))); + await tester.pumpAndSettle(); + + verify(mockDeletePost.call(post)).called(1); + + expect(find.byType(AlertDialog), findsOneWidget); + expect(find.byKey(const Key('no')), findsOneWidget); + await tester.tap(find.byKey(const Key("no"))); + await tester.pumpAndSettle(); + expect(find.byType(AlertDialog), findsNothing); + }); }); } From b83921aea37b1e2bb93420c3db94cf0e4fdf746d Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Sun, 7 Jan 2024 09:54:20 +0530 Subject: [PATCH 03/19] descriptive name to the key --- lib/widgets/post_modal.dart | 4 +- pubspec.lock | 106 ++++++++++++------ .../widget_tests/widgets/post_modal_test.dart | 52 ++++++--- 3 files changed, 114 insertions(+), 48 deletions(-) diff --git a/lib/widgets/post_modal.dart b/lib/widgets/post_modal.dart index 35d9ba054..c15977dd7 100644 --- a/lib/widgets/post_modal.dart +++ b/lib/widgets/post_modal.dart @@ -91,7 +91,7 @@ class PostBottomModal extends StatelessWidget { ), actions: [ TextButton( - key: const Key('yes'), + key: const Key('alert_dialog_yes_btn'), onPressed: () { navigationService.showTalawaErrorSnackBar( 'Post was deleted if you had the rights!', @@ -102,7 +102,7 @@ class PostBottomModal extends StatelessWidget { child: const Text("Yes"), ), TextButton( - key: const Key('no'), + key: const Key('alert-dialog_no_btn'), onPressed: () { Navigator.pop(context); }, diff --git a/pubspec.lock b/pubspec.lock index eaa73413a..1f4ed3a84 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -1013,30 +1013,6 @@ packages: url: "https://pub.dev" source: hosted version: "6.7.1" - leak_tracker: - dependency: transitive - description: - name: leak_tracker - sha256: "41b90ceaec6d79819f31e975e61d479516efe701dea35f891b2f986c1b031422" - url: "https://pub.dev" - source: hosted - version: "9.0.17" - leak_tracker_flutter_testing: - dependency: transitive - description: - name: leak_tracker_flutter_testing - sha256: "54808cfcfa87dbc0d74c61ac063d624adf1bd5c0407301f32b06c783c60dc4ca" - url: "https://pub.dev" - source: hosted - version: "2.0.0" - leak_tracker_testing: - dependency: transitive - description: - name: leak_tracker_testing - sha256: "7e71be3c161472f6c9158ac8875dd8de575060d60b5d159ebca3600ea32c9116" - url: "https://pub.dev" - source: hosted - version: "1.0.6" lint: dependency: "direct dev" description: @@ -1057,26 +1033,26 @@ packages: dependency: transitive description: name: matcher - sha256: d2323aa2060500f906aa31a895b4030b6da3ebdcc5619d14ce1aada65cd161cb + sha256: "1803e76e6653768d64ed8ff2e1e67bea3ad4b923eb5c56a295c3e634bad5960e" url: "https://pub.dev" source: hosted - version: "0.12.16+1" + version: "0.12.16" material_color_utilities: dependency: transitive description: name: material_color_utilities - sha256: "0e0a020085b65b6083975e499759762399b4475f766c21668c4ecca34ea74e5a" + sha256: "9528f2f296073ff54cb9fee677df673ace1218163c3bc7628093e7eed5203d41" url: "https://pub.dev" source: hosted - version: "0.8.0" + version: "0.5.0" meta: dependency: transitive description: name: meta - sha256: d584fa6707a52763a52446f02cc621b077888fb63b93bbcb1143a7be5a0c0c04 + sha256: a6e590c838b18133bb482a2745ad77c5bb7715fb0451209e1a7567d416678b8e url: "https://pub.dev" source: hosted - version: "1.11.0" + version: "1.10.0" mime: dependency: transitive description: @@ -1161,10 +1137,10 @@ packages: dependency: transitive description: name: path - sha256: "087ce49c3f0dc39180befefc60fdb4acd8f8620e5682fe2476afd0b3688bb4af" + sha256: "8829d8a55c13fc0e37127c29fedf290c102f4e40ae94ada574091fe0ff96c917" url: "https://pub.dev" source: hosted - version: "1.9.0" + version: "1.8.3" path_parsing: dependency: transitive description: @@ -1689,6 +1665,70 @@ packages: url: "https://pub.dev" source: hosted version: "0.1.0" + url_launcher: + dependency: "direct main" + description: + name: url_launcher + sha256: e9aa5ea75c84cf46b3db4eea212523591211c3cf2e13099ee4ec147f54201c86 + url: "https://pub.dev" + source: hosted + version: "6.2.2" + url_launcher_android: + dependency: transitive + description: + name: url_launcher_android + sha256: "31222ffb0063171b526d3e569079cf1f8b294075ba323443fdc690842bfd4def" + url: "https://pub.dev" + source: hosted + version: "6.2.0" + url_launcher_ios: + dependency: transitive + description: + name: url_launcher_ios + sha256: bba3373219b7abb6b5e0d071b0fe66dfbe005d07517a68e38d4fc3638f35c6d3 + url: "https://pub.dev" + source: hosted + version: "6.2.1" + url_launcher_linux: + dependency: transitive + description: + name: url_launcher_linux + sha256: ab360eb661f8879369acac07b6bb3ff09d9471155357da8443fd5d3cf7363811 + url: "https://pub.dev" + source: hosted + version: "3.1.1" + url_launcher_macos: + dependency: transitive + description: + name: url_launcher_macos + sha256: b7244901ea3cf489c5335bdacda07264a6e960b1c1b1a9f91e4bc371d9e68234 + url: "https://pub.dev" + source: hosted + version: "3.1.0" + url_launcher_platform_interface: + dependency: "direct dev" + description: + name: url_launcher_platform_interface + sha256: "980e8d9af422f477be6948bdfb68df8433be71f5743a188968b0c1b887807e50" + url: "https://pub.dev" + source: hosted + version: "2.2.0" + url_launcher_web: + dependency: transitive + description: + name: url_launcher_web + sha256: "7286aec002c8feecc338cc33269e96b73955ab227456e9fb2a91f7fab8a358e9" + url: "https://pub.dev" + source: hosted + version: "2.2.2" + url_launcher_windows: + dependency: transitive + description: + name: url_launcher_windows + sha256: ecf9725510600aa2bb6d7ddabe16357691b6d2805f66216a97d1b881e21beff7 + url: "https://pub.dev" + source: hosted + version: "3.1.1" uuid: dependency: transitive description: @@ -1859,4 +1899,4 @@ packages: version: "3.1.2" sdks: dart: ">=3.2.0 <3.13.0" - flutter: ">=3.16.0" + flutter: ">=3.16.0" \ No newline at end of file diff --git a/test/widget_tests/widgets/post_modal_test.dart b/test/widget_tests/widgets/post_modal_test.dart index fa0b8ac3b..94f5cf3af 100644 --- a/test/widget_tests/widgets/post_modal_test.dart +++ b/test/widget_tests/widgets/post_modal_test.dart @@ -17,15 +17,18 @@ import 'package:talawa/widgets/post_modal.dart'; import '../../helpers/test_helpers.dart'; import '../../helpers/test_locator.dart'; +//Mock classes class MockFunction extends Mock { void call(Post post); } class MockNavigationService extends Mock implements NavigationService {} +//test data final MockFunction mockDeletePost = MockFunction(); final LikedBy user = LikedBy(sId: "test_id"); +//fake user data final u1 = User( id: '123', firstName: 'Lakshay', @@ -39,6 +42,7 @@ final u2 = User( email: 'test@test.com', ); final List users = [u1, u2]; + List comments = [ Comments(sId: 'comment1'), Comments(sId: 'comment2'), @@ -47,6 +51,8 @@ List comments = [ Comments(sId: 'comment5'), Comments(sId: 'comment6'), ]; + +//fake comment data final comment = Comment( creator: User( id: '123', @@ -70,6 +76,8 @@ final comment3 = Comments(sId: 'comment3'); final List comments1 = [comment1, comment2, comment3]; final myBirthday = DateTime.utc(2004, DateTime.june, 16, 5, 30, 0, 0, 0); + +//fake post data final post = Post( creator: User( id: '123', @@ -84,6 +92,7 @@ final post = Post( likedBy: likeby, comments: comments1, ); + Widget createPostBottomModal() { return BaseView( onModelReady: (model) => model.initialize(), @@ -112,6 +121,7 @@ void main() { setUp(() { registerServices(); }); + tearDown(() => unregisterServices()); group('PostBottomModalTest -', () { @@ -119,11 +129,14 @@ void main() { await tester.pumpWidget(createPostBottomModal()); await tester.pumpAndSettle(); + // Verify the existence of PostBottomModal widget and reportPost button expect(find.byType(PostBottomModal), findsOneWidget); expect(find.byKey(const Key('reportPost')), findsOneWidget); + // Tap the reportPost button and verify the behavior await tester.tap(find.byKey(const Key('reportPost'))); await tester.pumpAndSettle(); + verify( navigationService.showTalawaErrorSnackBar( 'Your Report has been sent to the Admin', @@ -131,22 +144,28 @@ void main() { ), ).called(1); }); - testWidgets('Testing the delete Post button', (WidgetTester tester) async { + + testWidgets('Testing the delete Post button', (tester) async { await tester.pumpWidget(createPostBottomModal()); await tester.pumpAndSettle(); + + // Verify the existence of delete Post button expect(find.byIcon(Icons.delete), findsOneWidget); - expect(find.byKey(const Key("deletePost")), findsOneWidget); - await tester.tap(find.byKey(const Key("deletePost"))); + expect(find.byKey(const Key('deletePost')), findsOneWidget); + + // Tap the delete Post button and verify the behavior + await tester.tap(find.byKey(const Key('deletePost'))); await tester.pumpAndSettle(); verify(mockDeletePost.call(post)).called(1); + // Verify the presence of AlertDialog and its elements expect(find.byType(AlertDialog), findsOneWidget); - expect(find.byKey(const Key("yes")), findsOneWidget); - expect(find.text("The post was deleted"), findsOneWidget); + expect(find.byKey(const Key('alert_dialog_yes_btn')), findsOneWidget); + expect(find.text('The post was deleted'), findsOneWidget); - await tester.pumpAndSettle(); - await tester.tap(find.byKey(const Key("yes"))); + // Tap the yes button in AlertDialog and verify the behavior + await tester.tap(find.byKey(const Key('alert_dialog_yes_btn'))); await tester.pumpAndSettle(); verify( @@ -156,20 +175,27 @@ void main() { ), ).called(1); }); - testWidgets("Testing no button of alertDialogBox", - (WidgetTester tester) async { + + testWidgets("Testing no button of alertDialogBox", (tester) async { await tester.pumpWidget(createPostBottomModal()); await tester.pumpAndSettle(); - expect(find.byKey(const Key("deletePost")), findsOneWidget); - await tester.tap(find.byKey(const Key("deletePost"))); + + // Tap the delete Post button and verify the behavior + expect(find.byKey(const Key('deletePost')), findsOneWidget); + await tester.tap(find.byKey(const Key('deletePost'))); await tester.pumpAndSettle(); verify(mockDeletePost.call(post)).called(1); + // Verify the presence of AlertDialog and its no button expect(find.byType(AlertDialog), findsOneWidget); - expect(find.byKey(const Key('no')), findsOneWidget); - await tester.tap(find.byKey(const Key("no"))); + expect(find.byKey(const Key('dialog_no_btn')), findsOneWidget); + + // Tap the no button in AlertDialog and verify the behavior + await tester.tap(find.byKey(const Key('dialog_no_btn'))); await tester.pumpAndSettle(); + + // Verify that AlertDialog is dismissed expect(find.byType(AlertDialog), findsNothing); }); }); From 742eaf7e8521fb53664ae4887dcd90461a986026 Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Sun, 7 Jan 2024 10:14:33 +0530 Subject: [PATCH 04/19] fix failing test --- lib/widgets/post_modal.dart | 2 +- test/widget_tests/widgets/post_modal_test.dart | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/lib/widgets/post_modal.dart b/lib/widgets/post_modal.dart index c15977dd7..6a47c9e00 100644 --- a/lib/widgets/post_modal.dart +++ b/lib/widgets/post_modal.dart @@ -102,7 +102,7 @@ class PostBottomModal extends StatelessWidget { child: const Text("Yes"), ), TextButton( - key: const Key('alert-dialog_no_btn'), + key: const Key('alert_dialog_no_btn'), onPressed: () { Navigator.pop(context); }, diff --git a/test/widget_tests/widgets/post_modal_test.dart b/test/widget_tests/widgets/post_modal_test.dart index 94f5cf3af..0ee90eb12 100644 --- a/test/widget_tests/widgets/post_modal_test.dart +++ b/test/widget_tests/widgets/post_modal_test.dart @@ -189,10 +189,10 @@ void main() { // Verify the presence of AlertDialog and its no button expect(find.byType(AlertDialog), findsOneWidget); - expect(find.byKey(const Key('dialog_no_btn')), findsOneWidget); + expect(find.byKey(const Key('alert_dialog_no_btn')), findsOneWidget); // Tap the no button in AlertDialog and verify the behavior - await tester.tap(find.byKey(const Key('dialog_no_btn'))); + await tester.tap(find.byKey(const Key('alert_dialog_no_btn'))); await tester.pumpAndSettle(); // Verify that AlertDialog is dismissed From 618879b67217d349d6d73aa63a7b5b099fb42808 Mon Sep 17 00:00:00 2001 From: Shaik Azad <120930148+Azad99-9@users.noreply.github.com> Date: Thu, 4 Jan 2024 22:41:35 +0530 Subject: [PATCH 05/19] created settings page (#2299) * created settings page * formatted the code * fixed failing tests * resolved requested changes * fixed failing tests --- android/app/src/main/AndroidManifest.xml | 7 + ios/Runner/Info.plist | 5 + lib/locator.dart | 2 + .../profile_page_view_model.dart | 41 --- .../app_setting_view_model.dart | 76 ++++ .../app_settings/app_settings_page.dart | 342 ++++++++++++++++-- .../profile/profile_page.dart | 55 +-- lib/views/demo_screens/profile_page_demo.dart | 10 +- lib/widgets/lang_switch.dart | 8 +- lib/widgets/theme_switch.dart | 9 +- pubspec.yaml | 3 + test/helpers/test_locator.dart | 2 + .../profile_page_view_model_test.dart | 75 ---- .../app_setting_view_model_test.dart | 153 ++++++++ .../profile/profile_page_test.dart | 10 +- .../demo_screens/profile_page_demo_test.dart | 23 +- .../app_settings/app_setting_page_test.dart | 66 +++- .../widgets/theme_switch_test.dart | 5 +- 18 files changed, 652 insertions(+), 240 deletions(-) create mode 100644 lib/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart create mode 100644 test/view_model_tests/after_auth_view_model_tests/settings_view_models_test/app_setting_view_model_test.dart diff --git a/android/app/src/main/AndroidManifest.xml b/android/app/src/main/AndroidManifest.xml index 061b52373..6a17167af 100644 --- a/android/app/src/main/AndroidManifest.xml +++ b/android/app/src/main/AndroidManifest.xml @@ -5,6 +5,13 @@ + + + + + + + diff --git a/ios/Runner/Info.plist b/ios/Runner/Info.plist index d44908106..55fd5a24c 100644 --- a/ios/Runner/Info.plist +++ b/ios/Runner/Info.plist @@ -57,5 +57,10 @@ NSCameraUsageDescription This app needs camera access to scan QR codes + LSApplicationQueriesSchemes + + sms + tel + \ No newline at end of file diff --git a/lib/locator.dart b/lib/locator.dart index 0c7dd4f3d..b3746ea41 100644 --- a/lib/locator.dart +++ b/lib/locator.dart @@ -28,6 +28,7 @@ import 'package:talawa/view_model/after_auth_view_models/event_view_models/explo import 'package:talawa/view_model/after_auth_view_models/feed_view_models/organization_feed_view_model.dart'; import 'package:talawa/view_model/after_auth_view_models/profile_view_models/edit_profile_view_model.dart'; import 'package:talawa/view_model/after_auth_view_models/profile_view_models/profile_page_view_model.dart'; +import 'package:talawa/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart'; import 'package:talawa/view_model/after_auth_view_models/task_view_models/create_task_view_model.dart'; import 'package:talawa/view_model/after_auth_view_models/task_view_models/explore_tasks_view_model.dart'; import 'package:talawa/view_model/lang_view_model.dart'; @@ -135,6 +136,7 @@ void setupLocator() { locator.registerFactory(() => EditEventViewModel()); locator.registerFactory(() => AddPostViewModel()); locator.registerFactory(() => EventInfoViewModel()); + locator.registerFactory(() => AppSettingViewModel()); //Widgets viewModels locator.registerFactory(() => ProgressDialogViewModel()); diff --git a/lib/view_model/after_auth_view_models/profile_view_models/profile_page_view_model.dart b/lib/view_model/after_auth_view_models/profile_view_models/profile_page_view_model.dart index 9bbdb9330..b8444880b 100644 --- a/lib/view_model/after_auth_view_models/profile_view_models/profile_page_view_model.dart +++ b/lib/view_model/after_auth_view_models/profile_view_models/profile_page_view_model.dart @@ -15,8 +15,6 @@ import 'package:talawa/services/user_config.dart'; import 'package:talawa/utils/app_localization.dart'; import 'package:talawa/view_model/base_view_model.dart'; import 'package:talawa/view_model/lang_view_model.dart'; -import 'package:talawa/widgets/custom_alert_dialog.dart'; -import 'package:talawa/widgets/talawa_error_dialog.dart'; /// ProfilePageViewModel class helps to interact with model to serve data and react to user's input in Profile Page view. /// @@ -78,18 +76,6 @@ class ProfilePageViewModel extends BaseModel { setState(ViewState.idle); } - /// This method destroys the user's session or sign out the user from app, The function asks for the confimation in Custom Alert Dialog. - /// - /// **params**: - /// * `context`: BuildContext of the widget - /// - /// **returns**: - /// * `Future`: Resolves when user logout - Future logout(BuildContext context) async { - // push custom alert dialog with the confirmation message. - navigationService.pushDialog(logoutDialog()); - } - /// This method changes the currency of the user for donation purpose. /// /// **params**: @@ -185,33 +171,6 @@ class ProfilePageViewModel extends BaseModel { ); } - Widget logoutDialog() { - return CustomAlertDialog( - reverse: true, - dialogSubTitle: 'Are you sure you want to logout?', - successText: 'Logout', - success: () async { - await userConfig.userLogOut(); - navigationService.pop(); - if (userConfig.loggedIn) { - navigationService.pushDialog( - const TalawaErrorDialog( - 'Unable to logout, please try again.', - key: Key('TalawaError'), - messageType: MessageType.error, - ), - ); - } else { - navigationService.removeAllAndPush( - '/selectLang', - '/', - arguments: '0', - ); - } - }, - ); - } - /// This widget returns the button for social media sharing option. /// /// **params**: diff --git a/lib/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart b/lib/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart new file mode 100644 index 000000000..243802059 --- /dev/null +++ b/lib/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart @@ -0,0 +1,76 @@ +import 'package:flutter/material.dart'; +import 'package:talawa/enums/enums.dart'; +import 'package:talawa/locator.dart'; +import 'package:talawa/services/navigation_service.dart'; +import 'package:talawa/view_model/base_view_model.dart'; +import 'package:talawa/widgets/custom_alert_dialog.dart'; +import 'package:talawa/widgets/talawa_error_dialog.dart'; +import 'package:url_launcher/url_launcher_string.dart'; + +/// ViewModel for the App Settings functionality. +/// +/// This ViewModel handles the logic and data for the application settings. +class AppSettingViewModel extends BaseModel { + // Services + final _navigationService = locator(); + // final _appLanguageService = locator(); + + /// This method destroys the user's session or sign out the user from app, The function asks for the confimation in Custom Alert Dialog. + /// + /// **params**: + /// * `context`: BuildContext of the widget + /// + /// **returns**: + /// * `Future`: Resolves when user logout + Future logout(BuildContext context) async { + // push custom alert dialog with the confirmation message. + _navigationService.pushDialog(logoutDialog()); + } + + /// Launches a website using the provided URL. + /// + /// **params**: + /// * `url`: A [String] representing the URL of the website to be launched. + /// + /// **returns**: + /// * `Future`: A [Future] that resolves to a [bool] value indicating + /// whether the website launch was successful. + Future launchWebsite(String url) async => await launchUrlString(url); + + /// Creates a custom alert dialog for the logout confirmation. + /// + /// This dialog prompts the user with a confirmation message for logout. + /// The dialog provides options to logout or cancel the operation. + /// + /// **params**: + /// None + /// + /// **returns**: + /// * `Widget`: A [Widget] representing the custom logout confirmation dialog. + Widget logoutDialog() { + return CustomAlertDialog( + reverse: true, + dialogSubTitle: 'Are you sure you want to logout?', + successText: 'Logout', + success: () async { + await userConfig.userLogOut(); + navigationService.pop(); + if (userConfig.loggedIn) { + navigationService.pushDialog( + const TalawaErrorDialog( + 'Unable to logout, please try again.', + key: Key('TalawaError'), + messageType: MessageType.error, + ), + ); + } else { + navigationService.removeAllAndPush( + '/selectLang', + '/', + arguments: '0', + ); + } + }, + ); + } +} diff --git a/lib/views/after_auth_screens/app_settings/app_settings_page.dart b/lib/views/after_auth_screens/app_settings/app_settings_page.dart index 88387999b..95f0294fc 100644 --- a/lib/views/after_auth_screens/app_settings/app_settings_page.dart +++ b/lib/views/after_auth_screens/app_settings/app_settings_page.dart @@ -1,56 +1,320 @@ import 'package:flutter/material.dart'; +import 'package:talawa/constants/routing_constants.dart'; import 'package:talawa/locator.dart'; +import 'package:talawa/services/size_config.dart'; import 'package:talawa/utils/app_localization.dart'; +import 'package:talawa/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart'; +import 'package:talawa/views/base_view.dart'; import 'package:talawa/widgets/lang_switch.dart'; import 'package:talawa/widgets/theme_switch.dart'; -/// AppSettingsPage is a widget that has mutable state _AppSettingsPageState. -class AppSettingsPage extends StatefulWidget { - const AppSettingsPage({super.key}); +/// Widget representing the App Settings page. +/// +/// This widget represents the settings page of the application. +/// It allows users to configure various application settings. +class AppSettingsPage extends StatelessWidget { + const AppSettingsPage({ + super.key, + }); - @override - _AppSettingsPageState createState() => _AppSettingsPageState(); -} - -/// _AppSettingsPageState is state which return a widget for talawa app setting page. -class _AppSettingsPageState extends State { @override Widget build(BuildContext context) { // Scaffold implements the basic Material Design visual layout structure. //Learn more about Scaffold class //[here](https://api.flutter.dev/flutter/material/Scaffold-class.html). - return Scaffold( - key: const Key('AppSettingScaffold'), - // AppBar is a horizontal bar typically shown at the top of an app using the appBar property. - appBar: AppBar( - iconTheme: Theme.of(context).iconTheme, - backgroundColor: Theme.of(context).primaryColor, - elevation: 0.0, - centerTitle: true, - // title of the page in appBar property - title: Text( - // title text translation according to the app language. - AppLocalizations.of(context)!.strictTranslate('Settings'), - style: Theme.of(context).textTheme.titleLarge!.copyWith( - fontWeight: FontWeight.w600, - fontSize: 20, - ), - ), - leading: IconButton( - icon: const Icon(Icons.arrow_back), - onPressed: () => navigationService.pop(), - ), + // const String _talawaWebsite = ''; + const String talawaDocs = 'https://docs.talawa.io'; + const String talawaGithub = + 'https://github.com/PalisadoesFoundation/talawa'; + return BaseView( + builder: (context, model, child) { + return Scaffold( + key: const Key('AppSettingScaffold'), + // AppBar is a horizontal bar typically shown at the top of an app using the appBar property. + appBar: AppBar( + iconTheme: Theme.of(context).iconTheme, + backgroundColor: Theme.of(context).primaryColor, + elevation: 0.0, + centerTitle: true, + // title of the page in appBar property + title: Text( + // title text translation according to the app language. + AppLocalizations.of(context)!.strictTranslate('Settings'), + style: Theme.of(context).textTheme.titleLarge!.copyWith( + fontWeight: FontWeight.w600, + fontSize: 20, + ), + ), + leading: IconButton( + icon: const Icon(Icons.arrow_back), + onPressed: () => navigationService.pop(), + ), + ), + // style of the AppBar. + body: Padding( + padding: const EdgeInsets.symmetric(vertical: 0, horizontal: 20), + child: Column( + mainAxisAlignment: MainAxisAlignment.spaceBetween, + children: [ + // SizedBox( + // height: SizeConfig.screenHeight! * 0.77, + // child: + // ), + Flexible( + child: SingleChildScrollView( + scrollDirection: Axis.vertical, + child: Column( + children: [ + userConfig.loggedIn + ? category( + context: context, + title: 'Profile', + listItems: [ + customListTile( + leading: const Icon(Icons.edit), + content: Text( + AppLocalizations.of(context)! + .strictTranslate('Edit Profile'), + ), + trailing: chevronButton(context: context), + onTap: () { + navigationService + .pushScreen(Routes.editProfilePage); + }, + ), + ], + ) + : Container(), + category( + context: context, + title: 'General', + listItems: [ + const ChangeThemeTile(), + const LanguageTile(), + ], + ), + category( + context: context, + title: 'Help & Support', + listItems: [ + customListTile( + leading: const Icon(Icons.description), + content: Text( + AppLocalizations.of(context)! + .strictTranslate('Talawa Docs'), + ), + trailing: chevronButton( + context: context, + ), + onTap: () { + model.launchWebsite(talawaDocs); + }, + ), + customListTile( + leading: const Icon(Icons.code), + content: Text( + AppLocalizations.of(context)! + .strictTranslate('Talawa Git-Hub'), + ), + trailing: chevronButton( + context: context, + ), + onTap: () { + model.launchWebsite(talawaGithub); + }, + ), + ], + ), + ], + ), + ), + ), + footerTile(context: context, model: model), + ], + ), + ), + ); + }, + ); + } + + /// Generates an Icon widget for a chevron (right arrow). + /// + /// **params**: + /// * `context`: The BuildContext of the widget used to derive the theme's primary color. + /// + /// **returns**: + /// * `Icon`: An Icon widget representing a chevron (right arrow). + Icon chevronButton({required BuildContext context}) { + return Icon( + Icons.chevron_right, + color: Theme.of(context).colorScheme.primary, + ); + } + + /// Custom List Tile Widget. + /// + /// This widget creates a custom list tile with customizable components such as + /// leading, content, trailing, and an optional onTap callback. + /// + /// **params**: + /// * `leading`: Widget displayed at the start of the list tile. + /// * `content`: Widget displayed as the main content of the list tile. + /// * `trailing`: Widget displayed at the end of the list tile. + /// * `onTap`: Callback function triggered when the list tile is tapped. + /// + /// **returns**: + /// * `Widget`: Returns a ListTile widget customized with the provided components. + Widget customListTile({ + Widget? leading, + required Widget content, + required Widget trailing, + required void Function()? onTap, + }) { + return ListTile( + contentPadding: EdgeInsets.symmetric( + horizontal: SizeConfig.blockSizeHorizontal!, ), - // style of the AppBar. - body: const Padding( - padding: EdgeInsets.symmetric(vertical: 10, horizontal: 20), - child: Column( - children: [ - ChangeThemeTile(), - LanguageTile(), - ], - ), + leading: leading, + title: content, + trailing: trailing, + onTap: onTap, + ); + } + + /// Widget representing a category with a title and a list of items. + /// + /// Displays a category title along with a list of widgets. + /// + /// **params**: + /// * `context`: The [BuildContext] of the widget. + /// * `title`: The title of the category to be displayed. + /// * `listItems`: A list of [Widget]s representing items in the category. + /// + /// **returns**: + /// * `Widget`: A [Padding] widget containing a [Column] with the category title displayed using + /// [catergoryHeader] and followed by the list of `listItems`. + Widget category({ + required BuildContext context, + required String title, + required List listItems, + }) { + return Padding( + padding: + EdgeInsets.symmetric(vertical: SizeConfig.blockSizeVertical! * 1.5), + child: Column( + children: [ + catergoryHeader(context: context, title: title), + ] + + listItems, ), ); } + + /// Creates a header widget for a category. + /// + /// This widget displays a title for a category with a divider line underneath. + /// + /// **params**: + /// * `context`: The [BuildContext] associated with the widget. + /// * `title`: The title string to be displayed for the category. + /// + /// **returns**: + /// * `Widget`: Returns a [Widget] that represents the category header. + Widget catergoryHeader({ + required BuildContext context, + required String title, + }) { + return Padding( + padding: EdgeInsets.only(top: SizeConfig.blockSizeVertical!), + child: Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + Padding( + padding: const EdgeInsets.only(bottom: 2), + child: Text( + AppLocalizations.of(context)!.strictTranslate(title), + style: Theme.of(context) + .textTheme + .headlineSmall! + .copyWith(color: Theme.of(context).colorScheme.primary), + ), + ), + customDivider(context: context), + ], + ), + ); + } + + /// Widget representing a footer tile that performs different actions based on user login status. + /// + /// **params**: + /// * `context`: The [BuildContext] of the widget. + /// * `model`: An instance of [AppSettingViewModel] used for handling app settings. + /// + /// **returns**: + /// * `Widget`: Returns a [Column] widget displaying a divider and a [TextButton] that varies its behavior based on user login status. + Widget footerTile({ + required BuildContext context, + required AppSettingViewModel model, + }) { + return Column( + children: [ + customDivider(context: context), + TextButton( + child: Center( + child: Row( + mainAxisAlignment: MainAxisAlignment.center, + children: [ + userConfig.loggedIn + ? const Icon( + Icons.logout, + color: Colors.red, + ) + : Icon( + Icons.add, + color: Theme.of(context).colorScheme.secondary, + ), + SizedBox( + width: SizeConfig.blockSizeHorizontal! * 3, + ), + Text( + AppLocalizations.of(context)!.strictTranslate( + userConfig.loggedIn ? 'Logout' : 'Join an Organisation', + ), + style: Theme.of(context).textTheme.bodyLarge, + ), + ], + ), + ), + onPressed: () { + userConfig.loggedIn + ? model.logout(context) + : navigationService.pushScreen( + Routes.setUrlScreen, + arguments: '', + ); + }, + ), + ], + ); + } + + /// Builds a customized Divider widget based on the provided [BuildContext]. + /// + /// This function creates a Divider widget using the provided [context] to obtain + /// the appropriate divider color from the current app's theme. + /// + /// **params**: + /// * `context`: The BuildContext used to access the current app's theme. + /// + /// **returns**: + /// * `Widget`: Returns a Divider widget customized with the color from the app's theme. + Widget customDivider({ + required BuildContext context, + }) { + return Divider( + color: Theme.of(context).dividerColor, + ); + } } diff --git a/lib/views/after_auth_screens/profile/profile_page.dart b/lib/views/after_auth_screens/profile/profile_page.dart index 787bbd875..8c0f8584f 100644 --- a/lib/views/after_auth_screens/profile/profile_page.dart +++ b/lib/views/after_auth_screens/profile/profile_page.dart @@ -60,60 +60,7 @@ class ProfilePage extends StatelessWidget { IconButton( key: const Key('settingIcon'), onPressed: () { - showModalBottomSheet( - context: context, - builder: (BuildContext context) { - return Container( - key: const Key('sheetContainer'), - height: SizeConfig.screenHeight! * 0.17, - decoration: const BoxDecoration( - borderRadius: BorderRadius.only( - bottomLeft: Radius.zero, - bottomRight: Radius.zero, - topLeft: Radius.circular(16), - topRight: Radius.circular(16), - ), - ), - child: Center( - child: Column( - mainAxisAlignment: MainAxisAlignment.center, - mainAxisSize: MainAxisSize.min, - children: [ - TextButton( - onPressed: () { - navigationService - .pushScreen("/editProfilePage"); - }, - child: Text( - AppLocalizations.of(context)! - .strictTranslate("Edit Profile"), - style: const TextStyle( - fontFamily: 'open-sans', - ), - ), - ), - Divider( - endIndent: SizeConfig.screenHeight! * 0.03, - indent: SizeConfig.screenHeight! * 0.03, - ), - TextButton( - onPressed: () { - model.logout(context); - }, - child: Text( - AppLocalizations.of(context)! - .strictTranslate("Log Out"), - style: const TextStyle( - fontFamily: 'open-sans', - ), - ), - ), - ], - ), - ), - ); - }, - ); + navigationService.pushScreen(Routes.appSettings); }, icon: const Icon(Icons.settings), ), diff --git a/lib/views/demo_screens/profile_page_demo.dart b/lib/views/demo_screens/profile_page_demo.dart index 41303f513..840edd4f3 100644 --- a/lib/views/demo_screens/profile_page_demo.dart +++ b/lib/views/demo_screens/profile_page_demo.dart @@ -1,5 +1,6 @@ import 'package:contained_tab_bar_view/contained_tab_bar_view.dart'; import 'package:flutter/material.dart'; +import 'package:talawa/constants/routing_constants.dart'; import 'package:talawa/locator.dart'; import 'package:talawa/services/size_config.dart'; import 'package:talawa/utils/app_localization.dart'; @@ -47,7 +48,14 @@ class DemoProfilePage extends StatelessWidget { ), ), actions: [ - Container(), + IconButton( + key: const Key('settingIcon'), + onPressed: () { + print('came'); + navigationService.pushScreen(Routes.appSettings); + }, + icon: const Icon(Icons.settings), + ), ], ), // if data fetching is under process then renders Circular Progress Icon diff --git a/lib/widgets/lang_switch.dart b/lib/widgets/lang_switch.dart index e9451539b..2ffa67209 100644 --- a/lib/widgets/lang_switch.dart +++ b/lib/widgets/lang_switch.dart @@ -1,11 +1,9 @@ -// ignore_for_file: talawa_api_doc -// ignore_for_file: talawa_good_doc_comments - import 'package:flutter/material.dart'; import 'package:provider/provider.dart'; import 'package:talawa/constants/constants.dart'; import 'package:talawa/locator.dart'; import 'package:talawa/models/language/language_model.dart'; +import 'package:talawa/services/size_config.dart'; import 'package:talawa/utils/app_localization.dart'; import 'package:talawa/view_model/lang_view_model.dart'; @@ -26,7 +24,9 @@ class LanguageTile extends StatelessWidget { ); return ListTile( key: const Key('LanguageTile'), - contentPadding: EdgeInsets.zero, + contentPadding: EdgeInsets.symmetric( + horizontal: SizeConfig.blockSizeHorizontal!, + ), title: Text(AppLocalizations.of(context)!.strictTranslate("Language")), trailing: TextButton( diff --git a/lib/widgets/theme_switch.dart b/lib/widgets/theme_switch.dart index 035d4a922..4df56a15c 100644 --- a/lib/widgets/theme_switch.dart +++ b/lib/widgets/theme_switch.dart @@ -1,13 +1,10 @@ -// ignore_for_file: talawa_api_doc -// ignore_for_file: talawa_good_doc_comments - import 'package:flutter/material.dart'; import 'package:provider/provider.dart'; +import 'package:talawa/services/size_config.dart'; import 'package:talawa/utils/app_localization.dart'; import 'package:talawa/view_model/theme_view_model.dart'; /// This class enables theme switch. -/// It returns a ListTile which contains a Toggle button to switch between Dark and Light Themes. class ChangeThemeTile extends StatelessWidget { const ChangeThemeTile({super.key}); @@ -16,7 +13,9 @@ class ChangeThemeTile extends StatelessWidget { final themeProvider = Provider.of(context); return ListTile( key: const Key('ThemeSwitch'), - contentPadding: EdgeInsets.zero, + contentPadding: EdgeInsets.symmetric( + horizontal: SizeConfig.blockSizeHorizontal!, + ), title: Text(AppLocalizations.of(context)!.strictTranslate("Dark Theme")), trailing: Switch( key: const Key('ToggleTheme'), diff --git a/pubspec.yaml b/pubspec.yaml index ffc2396a9..af6ac2916 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -78,6 +78,7 @@ dependencies: timelines: ^0.1.0 tutorial_coach_mark: ^1.2.11 uni_links: ^0.5.1 + url_launcher: ^6.2.2 vibration: ^1.8.4 video_player: ^2.8.1 visibility_detector: ^0.4.0+2 @@ -96,6 +97,8 @@ dev_dependencies: talawa_lint: path: talawa_lint/ + url_launcher_platform_interface: any + flutter: uses-material-design: true assets: diff --git a/test/helpers/test_locator.dart b/test/helpers/test_locator.dart index f3a58d3bb..481f5a465 100644 --- a/test/helpers/test_locator.dart +++ b/test/helpers/test_locator.dart @@ -28,6 +28,7 @@ import 'package:talawa/view_model/after_auth_view_models/event_view_models/explo import 'package:talawa/view_model/after_auth_view_models/feed_view_models/organization_feed_view_model.dart'; import 'package:talawa/view_model/after_auth_view_models/profile_view_models/edit_profile_view_model.dart'; import 'package:talawa/view_model/after_auth_view_models/profile_view_models/profile_page_view_model.dart'; +import 'package:talawa/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart'; import 'package:talawa/view_model/after_auth_view_models/task_view_models/create_task_view_model.dart'; import 'package:talawa/view_model/after_auth_view_models/task_view_models/explore_tasks_view_model.dart'; import 'package:talawa/view_model/lang_view_model.dart'; @@ -112,6 +113,7 @@ void testSetupLocator() { locator.registerFactory(() => AddPostViewModel()); locator.registerFactory(() => EventInfoViewModel()); locator.registerFactory(() => ExploreTasksViewModel()); + locator.registerFactory(() => AppSettingViewModel()); //Widgets viewModels locator.registerFactory(() => ProgressDialogViewModel()); diff --git a/test/view_model_tests/after_auth_view_model_tests/profile_view_model_tests/profile_page_view_model_test.dart b/test/view_model_tests/after_auth_view_model_tests/profile_view_model_tests/profile_page_view_model_test.dart index b67434290..3b5ffab6e 100644 --- a/test/view_model_tests/after_auth_view_model_tests/profile_view_model_tests/profile_page_view_model_test.dart +++ b/test/view_model_tests/after_auth_view_model_tests/profile_view_model_tests/profile_page_view_model_test.dart @@ -7,12 +7,9 @@ import 'package:flutter_test/flutter_test.dart'; import 'package:mockito/mockito.dart'; import 'package:qr_flutter/qr_flutter.dart'; import 'package:talawa/enums/enums.dart'; -import 'package:talawa/router.dart' as router; import 'package:talawa/services/size_config.dart'; import 'package:talawa/utils/app_localization.dart'; import 'package:talawa/view_model/after_auth_view_models/profile_view_models/profile_page_view_model.dart'; -import 'package:talawa/view_model/lang_view_model.dart'; -import 'package:talawa/views/base_view.dart'; import '../../../helpers/test_helpers.dart'; import '../../../helpers/test_locator.dart'; @@ -55,12 +52,6 @@ void main() async { expect(model.currentOrg, userConfig.currentOrg); expect(model.currentUser, userConfig.currentUser); }); - - test('test logout function', () async { - final model = ProfilePageViewModel(); - final context = MockBuildContext(); - await model.logout(context); - }); testWidgets('changeCurrency test', (WidgetTester tester) async { final model = ProfilePageViewModel(); model.initialize(); @@ -105,72 +96,6 @@ void main() async { verify(navigationService.pop()); }); - testWidgets("Test logout dialog when logout successful.", (tester) async { - const userLoggedin = false; - when(userConfig.loggedIn).thenAnswer((_) => userLoggedin); - final model = ProfilePageViewModel(); - - final widget = BaseView( - onModelReady: (model) => model.initialize(), - builder: (context, langModel, child) { - return MaterialApp( - locale: const Locale('en'), - localizationsDelegates: [ - const AppLocalizationsDelegate(isTest: true), - GlobalMaterialLocalizations.delegate, - GlobalWidgetsLocalizations.delegate, - ], - home: Scaffold( - body: model.logoutDialog(), - ), - navigatorKey: navigationService.navigatorKey, - onGenerateRoute: router.generateRoute, - ); - }, - ); - - await tester.pumpWidget(widget); - await tester.pumpAndSettle(); - - await tester.tap(find.textContaining('Logout')); - await tester.pumpAndSettle(); - - verify(navigationService.navigatorKey); - }); - - testWidgets("Test logout dialog when logout unsuccessful.", (tester) async { - final model = ProfilePageViewModel(); - const userLoggedIn = true; - when(userConfig.loggedIn).thenAnswer((_) => userLoggedIn); - - final widget = BaseView( - onModelReady: (model) => model.initialize(), - builder: (context, langModel, child) { - return MaterialApp( - locale: const Locale('en'), - localizationsDelegates: [ - const AppLocalizationsDelegate(isTest: true), - GlobalMaterialLocalizations.delegate, - GlobalWidgetsLocalizations.delegate, - ], - home: Scaffold( - body: model.logoutDialog(), - ), - navigatorKey: navigationService.navigatorKey, - onGenerateRoute: router.generateRoute, - ); - }, - ); - - await tester.pumpWidget(widget); - await tester.pumpAndSettle(); - - await tester.tap(find.textContaining('Logout')); - await tester.pumpAndSettle(); - - verify(navigationService.navigatorKey); - }); - test("Test updateSheetHeight function", () { final model = ProfilePageViewModel(); model.initialize(); diff --git a/test/view_model_tests/after_auth_view_model_tests/settings_view_models_test/app_setting_view_model_test.dart b/test/view_model_tests/after_auth_view_model_tests/settings_view_models_test/app_setting_view_model_test.dart new file mode 100644 index 000000000..edcf1b768 --- /dev/null +++ b/test/view_model_tests/after_auth_view_model_tests/settings_view_models_test/app_setting_view_model_test.dart @@ -0,0 +1,153 @@ +// ignore_for_file: talawa_api_doc +// ignore_for_file: talawa_good_doc_comments + +import 'dart:io'; + +import 'package:flutter/material.dart'; +import 'package:flutter_localizations/flutter_localizations.dart'; +import 'package:flutter_test/flutter_test.dart'; +import 'package:hive/hive.dart'; +import 'package:mockito/mockito.dart'; +import 'package:plugin_platform_interface/plugin_platform_interface.dart'; +import 'package:talawa/models/organization/org_info.dart'; +import 'package:talawa/models/user/user_info.dart'; +import 'package:talawa/router.dart' as router; +import 'package:talawa/services/size_config.dart'; +import 'package:talawa/utils/app_localization.dart'; +import 'package:talawa/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart'; +import 'package:talawa/view_model/lang_view_model.dart'; +import 'package:talawa/views/base_view.dart'; +import 'package:url_launcher_platform_interface/url_launcher_platform_interface.dart'; +import '../../../helpers/test_helpers.dart'; +import '../../../helpers/test_locator.dart'; +import '../../../router_test.dart'; + +class MockUrlLauncher extends Mock + with MockPlatformInterfaceMixin + implements UrlLauncherPlatform { + @override + Future launchUrl(String url, LaunchOptions? options) { + if (url == 'http://www.success.com') return Future.value(true); + return Future.value(false); + } +} + +void main() async { + SizeConfig().test(); + testSetupLocator(); + + final Directory dir = Directory('test/fixtures/core1'); + + Hive + ..init(dir.path) + ..registerAdapter(UserAdapter()) + ..registerAdapter(OrgInfoAdapter()); + + await Hive.openBox('currentUser'); + await Hive.openBox('url'); + await Hive.openBox('currentOrg'); + + group('Test for appSettingviewModel', () { + setUpAll(() async { + getAndRegisterNavigationService(); + getAndRegisterUserConfig(); + final mock = MockUrlLauncher(); + UrlLauncherPlatform.instance = mock; + }); + + tearDownAll(() async { + await Hive.close(); + + // Clean up the test directory if needed + dir.delete(recursive: true); + }); + + test('Test logout function.', () { + final model = AppSettingViewModel(); + final context = MockBuildContext(); + model.logout(context); + }); + + testWidgets("Test logout dialog when logout successful.", (tester) async { + const userLoggedin = false; + when(userConfig.loggedIn).thenAnswer((_) => userLoggedin); + final model = AppSettingViewModel(); + + final widget = BaseView( + onModelReady: (model) => model.initialize(), + builder: (context, langModel, child) { + return MaterialApp( + locale: const Locale('en'), + localizationsDelegates: [ + const AppLocalizationsDelegate(isTest: true), + GlobalMaterialLocalizations.delegate, + GlobalWidgetsLocalizations.delegate, + ], + home: Scaffold( + body: model.logoutDialog(), + ), + navigatorKey: navigationService.navigatorKey, + onGenerateRoute: router.generateRoute, + ); + }, + ); + + await tester.pumpWidget(widget); + await tester.pumpAndSettle(); + + await tester.tap(find.textContaining('Logout')); + await tester.pumpAndSettle(); + + verify(navigationService.navigatorKey); + }); + + testWidgets("Test logout dialog when logout unsuccessful.", (tester) async { + final model = AppSettingViewModel(); + const userLoggedIn = true; + when(userConfig.loggedIn).thenAnswer((_) => userLoggedIn); + + final widget = BaseView( + onModelReady: (model) => model.initialize(), + builder: (context, langModel, child) { + return MaterialApp( + locale: const Locale('en'), + localizationsDelegates: [ + const AppLocalizationsDelegate(isTest: true), + GlobalMaterialLocalizations.delegate, + GlobalWidgetsLocalizations.delegate, + ], + home: Scaffold( + body: model.logoutDialog(), + ), + navigatorKey: navigationService.navigatorKey, + onGenerateRoute: router.generateRoute, + ); + }, + ); + + await tester.pumpWidget(widget); + await tester.pumpAndSettle(); + + await tester.tap(find.textContaining('Logout')); + await tester.pumpAndSettle(); + + verify(navigationService.navigatorKey); + }); + + test('test for launchWebsite method', () async { + final model = AppSettingViewModel(); + const successUrl = 'http://www.success.com'; + const failUrl = 'http://www.fail.com'; + + bool opened = false; + + // if successfully launches the website. + opened = await model.launchWebsite(successUrl); + expect(opened, true); + + // if failed to launch the website. + opened = await model.launchWebsite(failUrl); + expect(opened, false); + }); + }); +} diff --git a/test/views/after_auth_screens/profile/profile_page_test.dart b/test/views/after_auth_screens/profile/profile_page_test.dart index 64a7ced12..b3dd1928e 100644 --- a/test/views/after_auth_screens/profile/profile_page_test.dart +++ b/test/views/after_auth_screens/profile/profile_page_test.dart @@ -4,6 +4,7 @@ import 'package:flutter/material.dart'; import 'package:flutter_localizations/flutter_localizations.dart'; import 'package:flutter_test/flutter_test.dart'; import 'package:hive/hive.dart'; +import 'package:mockito/mockito.dart'; import 'package:talawa/constants/custom_theme.dart'; import 'package:talawa/models/organization/org_info.dart'; import 'package:talawa/models/user/user_info.dart'; @@ -125,17 +126,16 @@ void main() async { await tester.tap(find.text('Invite')); await tester.pumpAndSettle(); }); - testWidgets('check if modal sheet for settings shows up', (tester) async { + testWidgets('check if settings page is opening up', (tester) async { await tester.pumpWidget( createProfilePage( mainScreenViewModel: locator(), ), ); await tester.pumpAndSettle(); - await tester.ensureVisible(find.byKey(const Key('settingIcon'))); - await tester.tap(find.byKey(const Key('settingIcon'))); - await tester.pumpAndSettle(); - expect(find.byKey(const Key('sheetContainer')), findsOneWidget); + final settingsIcon = find.byKey(const Key('settingIcon')); + await tester.tap(settingsIcon); + verify(navigationService.navigatorKey); }); }); } diff --git a/test/views/demo_screens/profile_page_demo_test.dart b/test/views/demo_screens/profile_page_demo_test.dart index bfe863406..7e9426c1b 100644 --- a/test/views/demo_screens/profile_page_demo_test.dart +++ b/test/views/demo_screens/profile_page_demo_test.dart @@ -41,13 +41,12 @@ Widget createProfileScreen({required bool demoMode}) { void main() async { testSetupLocator(); - setUp(() { - registerServices(); - locator().test(); - locator().test(); - }); - group('Profile Page tests', () { + setUpAll(() { + registerServices(); + locator().test(); + locator().test(); + }); testWidgets('Test for donate button.', (tester) async { await tester.pumpWidget(createProfileScreen(demoMode: true)); @@ -73,5 +72,17 @@ void main() async { expect(find.byKey(const Key("Drawer")), findsOneWidget); }); + + testWidgets('check if settings page is opening up', (tester) async { + await tester.pumpWidget( + createProfileScreen( + demoMode: true, + ), + ); + await tester.pumpAndSettle(const Duration(seconds: 1)); + final settingsIcon = find.byKey(const Key('settingIcon')); + await tester.tap(settingsIcon); + verify(navigationService.pushScreen('/appSettingsPage')); + }); }); } diff --git a/test/widget_tests/after_auth_screens/app_settings/app_setting_page_test.dart b/test/widget_tests/after_auth_screens/app_settings/app_setting_page_test.dart index f2c5d7bd0..58742d74d 100644 --- a/test/widget_tests/after_auth_screens/app_settings/app_setting_page_test.dart +++ b/test/widget_tests/after_auth_screens/app_settings/app_setting_page_test.dart @@ -19,6 +19,7 @@ import 'package:talawa/view_model/theme_view_model.dart'; import 'package:talawa/views/after_auth_screens/app_settings/app_settings_page.dart'; import 'package:talawa/views/base_view.dart'; +import '../../../helpers/test_helpers.dart'; import '../../../helpers/test_locator.dart'; class MockBuildContext extends Mock implements BuildContext {} @@ -46,7 +47,9 @@ Widget createChangePassScreenLight({ThemeMode themeMode = ThemeMode.light}) => theme: Provider.of(context, listen: true).isdarkTheme ? TalawaTheme.darkTheme : TalawaTheme.lightTheme, - home: const AppSettingsPage(), + home: const AppSettingsPage( + key: Key('AppSettingsPage'), + ), navigatorKey: locator().navigatorKey, onGenerateRoute: router.generateRoute, ); @@ -74,7 +77,9 @@ Widget createChangePassScreenDark({ThemeMode themeMode = ThemeMode.dark}) => theme: Provider.of(context, listen: true).isdarkTheme ? TalawaTheme.darkTheme : TalawaTheme.lightTheme, - home: const AppSettingsPage(), + home: const AppSettingsPage( + key: Key('AppSettingsPage'), + ), navigatorKey: locator().navigatorKey, onGenerateRoute: router.generateRoute, ); @@ -87,7 +92,8 @@ Future main() async { testSetupLocator(); TestWidgetsFlutterBinding.ensureInitialized(); locator().test(); - locator().test(); + SizeConfig().test(); + registerServices(); group('Setting Page Screen Widget Test in dark mode', () { testWidgets("Testing if Settings Screen shows up", (tester) async { @@ -109,12 +115,7 @@ Future main() async { await tester.tap(backButton); await tester.pumpAndSettle(); - expect( - find.byKey( - const Key('AppSettingScaffold'), - ), - findsNothing, - ); + verify(navigationService.navigatorKey); }); testWidgets( "Testing if Settings Screen shows up in dark mode with Theme selection tile", @@ -240,5 +241,52 @@ Future main() async { TalawaTheme.darkTheme.scaffoldBackgroundColor, ); }); + testWidgets('Test Edit Profile Tile is visible and works properly', + (tester) async { + when(userConfig.loggedIn).thenReturn(true); + await tester.pumpWidget(createChangePassScreenDark()); + await tester.pumpAndSettle(); + expect(find.text('Profile'), findsOneWidget); + + final editProfile = find.textContaining('Edit Profile'); + await tester.tap(editProfile); + + verify(navigationService.navigatorKey); + }); + testWidgets('Test if help and support tiles are working', (tester) async { + when(userConfig.loggedIn).thenReturn(true); + await tester.pumpWidget(createChangePassScreenDark()); + await tester.pumpAndSettle(); + + final talawaDocs = find.textContaining('Talawa Docs'); + final talawaGitHub = find.textContaining('Talawa Git-Hub'); + + await tester.tap(talawaDocs); + await tester.tap(talawaGitHub); + }); + testWidgets('Test if footerTile is working.', (tester) async { + const userLoggedIn = true; + when(userConfig.loggedIn).thenAnswer((_) => userLoggedIn); + + await tester.pumpWidget(createChangePassScreenDark()); + await tester.pumpAndSettle(); + + final logoutButton = find.textContaining('Logout'); + await tester.tap(logoutButton); + + unregisterServices(); + registerServices(); + + const loggedIn = false; + when(userConfig.loggedIn).thenAnswer((_) => loggedIn); + + await tester.pumpWidget(createChangePassScreenDark()); + await tester.pumpAndSettle(); + + final joinOrgButton = find.textContaining('Join an Organisation'); + await tester.tap(joinOrgButton); + + verify(navigationService.navigatorKey); + }); }); } diff --git a/test/widget_tests/widgets/theme_switch_test.dart b/test/widget_tests/widgets/theme_switch_test.dart index a44d22abc..0da53d784 100644 --- a/test/widget_tests/widgets/theme_switch_test.dart +++ b/test/widget_tests/widgets/theme_switch_test.dart @@ -78,7 +78,10 @@ void main() { final listTileFinder = find.byType(ListTile).first; final listTile = tester.firstWidget(listTileFinder); - expect((listTile as ListTile).contentPadding, EdgeInsets.zero); + expect( + (listTile as ListTile).contentPadding, + const EdgeInsets.fromLTRB(3.6, 0.0, 3.6, 0.0), + ); expect((listTile.trailing! as Switch).autofocus, true); expect((listTile.trailing! as Switch).value, true); From 99c0d9b032a24ddd6faa5b0cb66ec731664036af Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Mon, 8 Jan 2024 16:40:12 +0530 Subject: [PATCH 06/19] rebased --- lib/widgets/post_modal.dart | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/widgets/post_modal.dart b/lib/widgets/post_modal.dart index 6a47c9e00..c15977dd7 100644 --- a/lib/widgets/post_modal.dart +++ b/lib/widgets/post_modal.dart @@ -102,7 +102,7 @@ class PostBottomModal extends StatelessWidget { child: const Text("Yes"), ), TextButton( - key: const Key('alert_dialog_no_btn'), + key: const Key('alert-dialog_no_btn'), onPressed: () { Navigator.pop(context); }, From 40099ff1048210ed133936d88adbefd1950cdc8f Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Sun, 7 Jan 2024 09:54:20 +0530 Subject: [PATCH 07/19] descriptive name to the key --- pubspec.lock | 42 +++++++++++++++++++++++++++++++++--------- 1 file changed, 33 insertions(+), 9 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index 1f4ed3a84..36d5b5438 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -1013,6 +1013,30 @@ packages: url: "https://pub.dev" source: hosted version: "6.7.1" + leak_tracker: + dependency: transitive + description: + name: leak_tracker + sha256: "41b90ceaec6d79819f31e975e61d479516efe701dea35f891b2f986c1b031422" + url: "https://pub.dev" + source: hosted + version: "9.0.17" + leak_tracker_flutter_testing: + dependency: transitive + description: + name: leak_tracker_flutter_testing + sha256: "54808cfcfa87dbc0d74c61ac063d624adf1bd5c0407301f32b06c783c60dc4ca" + url: "https://pub.dev" + source: hosted + version: "2.0.0" + leak_tracker_testing: + dependency: transitive + description: + name: leak_tracker_testing + sha256: "7e71be3c161472f6c9158ac8875dd8de575060d60b5d159ebca3600ea32c9116" + url: "https://pub.dev" + source: hosted + version: "1.0.6" lint: dependency: "direct dev" description: @@ -1033,26 +1057,26 @@ packages: dependency: transitive description: name: matcher - sha256: "1803e76e6653768d64ed8ff2e1e67bea3ad4b923eb5c56a295c3e634bad5960e" + sha256: d2323aa2060500f906aa31a895b4030b6da3ebdcc5619d14ce1aada65cd161cb url: "https://pub.dev" source: hosted - version: "0.12.16" + version: "0.12.16+1" material_color_utilities: dependency: transitive description: name: material_color_utilities - sha256: "9528f2f296073ff54cb9fee677df673ace1218163c3bc7628093e7eed5203d41" + sha256: "0e0a020085b65b6083975e499759762399b4475f766c21668c4ecca34ea74e5a" url: "https://pub.dev" source: hosted - version: "0.5.0" + version: "0.8.0" meta: dependency: transitive description: name: meta - sha256: a6e590c838b18133bb482a2745ad77c5bb7715fb0451209e1a7567d416678b8e + sha256: d584fa6707a52763a52446f02cc621b077888fb63b93bbcb1143a7be5a0c0c04 url: "https://pub.dev" source: hosted - version: "1.10.0" + version: "1.11.0" mime: dependency: transitive description: @@ -1137,10 +1161,10 @@ packages: dependency: transitive description: name: path - sha256: "8829d8a55c13fc0e37127c29fedf290c102f4e40ae94ada574091fe0ff96c917" + sha256: "087ce49c3f0dc39180befefc60fdb4acd8f8620e5682fe2476afd0b3688bb4af" url: "https://pub.dev" source: hosted - version: "1.8.3" + version: "1.9.0" path_parsing: dependency: transitive description: @@ -1899,4 +1923,4 @@ packages: version: "3.1.2" sdks: dart: ">=3.2.0 <3.13.0" - flutter: ">=3.16.0" \ No newline at end of file + flutter: ">=3.16.0" From 4deb30a13c28c5aa960249210615f3398e7dadbd Mon Sep 17 00:00:00 2001 From: Shivam Gupta Date: Sun, 7 Jan 2024 00:08:20 +0530 Subject: [PATCH 08/19] Select contact test (#2301) * Created Test * Updated Formatting --- .../select_contact_view_model.dart | 26 ++++++++++---- .../chat/select_contact.dart | 8 ++--- .../chat/select_contact_test.dart | 36 ++++++++++++++++--- 3 files changed, 53 insertions(+), 17 deletions(-) diff --git a/lib/view_model/after_auth_view_models/chat_view_models/select_contact_view_model.dart b/lib/view_model/after_auth_view_models/chat_view_models/select_contact_view_model.dart index 35265c394..321db17e1 100644 --- a/lib/view_model/after_auth_view_models/chat_view_models/select_contact_view_model.dart +++ b/lib/view_model/after_auth_view_models/chat_view_models/select_contact_view_model.dart @@ -1,6 +1,3 @@ -// ignore_for_file: talawa_api_doc -// ignore_for_file: talawa_good_doc_comments - import 'package:talawa/locator.dart'; import 'package:talawa/models/user/user_info.dart'; import 'package:talawa/services/org_service.dart'; @@ -12,20 +9,35 @@ import 'package:talawa/view_model/base_view_model.dart'; /// * `getCurrentOrgUsersList` : to get all users of current organization. class SelectContactViewModel extends BaseModel { late OrganizationService _organizationService; + + /// orgMembersList is used to store all users of current organization. late List orgMembersList = []; - // initialisation + /// This function initializes the [SelectContactViewModel] class. + /// + /// more_info_if_required + /// + /// **params**: + /// None + /// + /// **returns**: + /// None void initialise() { _organizationService = locator(); } - /// This function is used to get all users list of an current organization. + /// function to get all users of current organization. + /// + /// **params**: + /// None + /// + /// **returns**: + /// * `Future`: void Future getCurrentOrgUsersList() async { if (orgMembersList.isEmpty) { orgMembersList = await _organizationService .getOrgMembersList(userConfig.currentOrg.id!); + notifyListeners(); } - - //return orgMembersList; } } diff --git a/lib/views/after_auth_screens/chat/select_contact.dart b/lib/views/after_auth_screens/chat/select_contact.dart index 94b014afa..180abe47c 100644 --- a/lib/views/after_auth_screens/chat/select_contact.dart +++ b/lib/views/after_auth_screens/chat/select_contact.dart @@ -1,6 +1,3 @@ -// ignore_for_file: talawa_api_doc -// ignore_for_file: talawa_good_doc_comments - import 'package:flutter/material.dart'; import 'package:talawa/locator.dart'; import 'package:talawa/view_model/after_auth_view_models/chat_view_models/select_contact_view_model.dart'; @@ -38,15 +35,16 @@ class _SelectContactState extends State { ), ), body: BaseView( - onModelReady: (model) { + onModelReady: (model) async { model.initialise(); - model.getCurrentOrgUsersList(); + await model.getCurrentOrgUsersList(); }, builder: (context, model, child) { return ListView.builder( itemCount: model.orgMembersList.length, itemBuilder: (context, index) { return GestureDetector( + key: Key('select_contact_gesture_$index'), onTap: () { // Navigator.push(context, MaterialPageRoute(builder: (context)=>ChatMessageScreen(chat: ChatListTileDataModel(ChatUser(model.orgMembersList[index].firstName,model.orgMembersList[index].id,model.orgMembersList[index].image),null,0)))); }, diff --git a/test/views/after_auth_screens/chat/select_contact_test.dart b/test/views/after_auth_screens/chat/select_contact_test.dart index 1513df7e5..e581e4f52 100644 --- a/test/views/after_auth_screens/chat/select_contact_test.dart +++ b/test/views/after_auth_screens/chat/select_contact_test.dart @@ -1,6 +1,3 @@ -// ignore_for_file: talawa_api_doc -// ignore_for_file: talawa_good_doc_comments - import 'package:flutter/material.dart'; import 'package:flutter_localizations/flutter_localizations.dart'; import 'package:flutter_test/flutter_test.dart'; @@ -78,8 +75,8 @@ void main() { registerViewModels(); final model = SelectContactViewModel(); model.initialise(); - final User user1 = User(id: "fakeUser1"); - final User user2 = User(id: "fakeUser2"); + final User user1 = User(id: "fakeUser1", firstName: "Shivam"); + final User user2 = User(id: "fakeUser2", firstName: "Talawa"); final List users = [user1, user2]; when(organizationService.getOrgMembersList("XYZ")) @@ -109,4 +106,33 @@ void main() { expect(find.byType(Scaffold), findsOneWidget); }); + + testWidgets("Test if list view is visible", (WidgetTester tester) async { + await tester.runAsync(() async { + await tester.pumpWidget(createApp()); + await tester.pump(); + await tester.pumpAndSettle(const Duration(milliseconds: 4000)); + + expect(find.byType(ListView), findsOneWidget); + expect( + find.byKey( + const ValueKey('select_contact_gesture_0'), + ), + findsNWidgets(1), + ); + expect( + find.byKey( + const ValueKey('select_contact_gesture_1'), + ), + findsNWidgets(1), + ); + final gesturedetect = find.byKey( + const ValueKey('select_contact_gesture_1'), + ); + await tester.tap(gesturedetect); + + expect(find.text('Shivam'), findsOneWidget); + expect(find.text('Talawa'), findsOneWidget); + }); + }); } From 066f23e12682b8eabf2802540b449a02ff3540f5 Mon Sep 17 00:00:00 2001 From: Shaik Azad <120930148+Azad99-9@users.noreply.github.com> Date: Sun, 7 Jan 2024 01:03:05 +0530 Subject: [PATCH 09/19] fixed fetch events bug (#2308) * fixed events fetching bug * fixed failing tests * added comments to event_queries * fixed failing test --- lib/utils/event_queries.dart | 75 ++++++++++++++++++++++++------ test/utils/event_queries_test.dart | 8 ---- 2 files changed, 61 insertions(+), 22 deletions(-) diff --git a/lib/utils/event_queries.dart b/lib/utils/event_queries.dart index 23b06458b..14c9e82e5 100644 --- a/lib/utils/event_queries.dart +++ b/lib/utils/event_queries.dart @@ -1,9 +1,15 @@ -// ignore_for_file: talawa_api_doc -// ignore_for_file: talawa_good_doc_comments - ///This class creates queries related to the events. class EventQueries { - //Returns a query to fetch an organization's events + /// Fetches events by organization ID. + /// + /// **params**: + /// * `orgId`: The ID of the organization to fetch events for. + /// + /// **returns**: + /// * `String`: Returns a GraphQL query string to fetch events associated with the specified organization ID. + /// + /// This function generates a GraphQL query string to retrieve events + /// based on the provided organization ID. String fetchOrgEvents(String orgId) { return """ query { @@ -34,17 +40,21 @@ class EventQueries { firstName lastName } - registrants { - user { - _id - } - } } } """; } - //returns a query to get the registrants of a particular event. + /// Fetches registrants by event ID. + /// + /// **params**: + /// * `eventId`: The ID of the event to fetch registrants for. + /// + /// **returns**: + /// * `String`: Returns a GraphQL query string to retrieve registrants associated with the specified event ID. + /// + /// This function generates a GraphQL query string to fetch registrants + /// based on the provided event ID. String registrantsByEvent(String eventId) { return ''' query { @@ -58,7 +68,15 @@ class EventQueries { '''; } - //returns a query to add an event. + /// Creates a GraphQL mutation for adding an event. + /// + /// **params**: + /// None + /// + /// **returns**: + /// * `String`: Returns a GraphQL mutation string to create an event. + /// + /// This function generates a GraphQL mutation string for creating an event. String addEvent() { return """ mutation createEvent( \$organizationId: ID!, @@ -98,7 +116,15 @@ class EventQueries { """; } - //returns a query to register for an event + /// Creates a GraphQL mutation for registering for an event. + /// + /// **params**: + /// None + /// + /// **returns**: + /// * `String`: Returns a GraphQL mutation string to register for the specified event. + /// + /// This function generates a GraphQL mutation string for registering an individual for an event. String registerForEvent() { return """ mutation registerForEvent(\$eventId: ID!) { @@ -112,7 +138,16 @@ class EventQueries { """; } - //returns a query to delete an event + /// Creates a GraphQL mutation for deleting an event. + /// + /// **params**: + /// * `id`: The ID of the event to delete. + /// + /// **returns**: + /// * `String`: Returns a GraphQL mutation string to delete the specified event. + /// + /// This function generates a GraphQL mutation string for removing/deleting an event + /// based on the provided event ID. String deleteEvent(String id) { return """ mutation { @@ -125,7 +160,19 @@ class EventQueries { """; } - //returns a query to update an event + /// Creates a GraphQL mutation for updating an event. + /// + /// **params**: + /// * `eventId`: The ID of the event to update. + /// + /// **returns**: + /// * `String`: Returns a GraphQL mutation string to update the specified event. + /// + /// This function generates a GraphQL mutation string for updating an event + /// based on the provided parameters. It takes the event ID along with updated + /// details. + /// The mutation updates the event details and returns the ID, title, and description + /// of the updated event. String updateEvent({ eventId, }) { diff --git a/test/utils/event_queries_test.dart b/test/utils/event_queries_test.dart index a3d03a86f..cb9fe23fe 100644 --- a/test/utils/event_queries_test.dart +++ b/test/utils/event_queries_test.dart @@ -1,6 +1,3 @@ -// ignore_for_file: talawa_api_doc -// ignore_for_file: talawa_good_doc_comments - import 'package:flutter_test/flutter_test.dart'; import 'package:talawa/utils/event_queries.dart'; @@ -36,11 +33,6 @@ void main() { firstName lastName } - registrants { - user { - _id - } - } } } """; From 733444a8740449c11c92fbf390a4043d37586afe Mon Sep 17 00:00:00 2001 From: Parag Gupta <103507835+Dante291@users.noreply.github.com> Date: Sun, 7 Jan 2024 01:05:12 +0530 Subject: [PATCH 10/19] Refactor: Decouple ViewModel by Moving UI Logic to View (#2306) * Refactor: Decouple ViewModel by Moving UI Logic to View * refactoring app_settings_view_model and app_seetings_page * writing test for missing lines --- .../app_setting_view_model.dart | 48 +----------- .../app_settings/app_settings_page.dart | 33 +++++++- .../app_setting_view_model_test.dart | 76 +------------------ .../app_settings/app_setting_page_test.dart | 22 +++++- 4 files changed, 56 insertions(+), 123 deletions(-) diff --git a/lib/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart b/lib/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart index 243802059..2a63951ee 100644 --- a/lib/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart +++ b/lib/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart @@ -1,18 +1,11 @@ -import 'package:flutter/material.dart'; -import 'package:talawa/enums/enums.dart'; import 'package:talawa/locator.dart'; -import 'package:talawa/services/navigation_service.dart'; import 'package:talawa/view_model/base_view_model.dart'; -import 'package:talawa/widgets/custom_alert_dialog.dart'; -import 'package:talawa/widgets/talawa_error_dialog.dart'; import 'package:url_launcher/url_launcher_string.dart'; /// ViewModel for the App Settings functionality. /// /// This ViewModel handles the logic and data for the application settings. class AppSettingViewModel extends BaseModel { - // Services - final _navigationService = locator(); // final _appLanguageService = locator(); /// This method destroys the user's session or sign out the user from app, The function asks for the confimation in Custom Alert Dialog. @@ -22,9 +15,9 @@ class AppSettingViewModel extends BaseModel { /// /// **returns**: /// * `Future`: Resolves when user logout - Future logout(BuildContext context) async { + Future logout() async { // push custom alert dialog with the confirmation message. - _navigationService.pushDialog(logoutDialog()); + await userConfig.userLogOut(); } /// Launches a website using the provided URL. @@ -36,41 +29,4 @@ class AppSettingViewModel extends BaseModel { /// * `Future`: A [Future] that resolves to a [bool] value indicating /// whether the website launch was successful. Future launchWebsite(String url) async => await launchUrlString(url); - - /// Creates a custom alert dialog for the logout confirmation. - /// - /// This dialog prompts the user with a confirmation message for logout. - /// The dialog provides options to logout or cancel the operation. - /// - /// **params**: - /// None - /// - /// **returns**: - /// * `Widget`: A [Widget] representing the custom logout confirmation dialog. - Widget logoutDialog() { - return CustomAlertDialog( - reverse: true, - dialogSubTitle: 'Are you sure you want to logout?', - successText: 'Logout', - success: () async { - await userConfig.userLogOut(); - navigationService.pop(); - if (userConfig.loggedIn) { - navigationService.pushDialog( - const TalawaErrorDialog( - 'Unable to logout, please try again.', - key: Key('TalawaError'), - messageType: MessageType.error, - ), - ); - } else { - navigationService.removeAllAndPush( - '/selectLang', - '/', - arguments: '0', - ); - } - }, - ); - } } diff --git a/lib/views/after_auth_screens/app_settings/app_settings_page.dart b/lib/views/after_auth_screens/app_settings/app_settings_page.dart index 95f0294fc..4fb2d3029 100644 --- a/lib/views/after_auth_screens/app_settings/app_settings_page.dart +++ b/lib/views/after_auth_screens/app_settings/app_settings_page.dart @@ -1,11 +1,14 @@ import 'package:flutter/material.dart'; import 'package:talawa/constants/routing_constants.dart'; +import 'package:talawa/enums/enums.dart'; import 'package:talawa/locator.dart'; import 'package:talawa/services/size_config.dart'; import 'package:talawa/utils/app_localization.dart'; import 'package:talawa/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart'; import 'package:talawa/views/base_view.dart'; +import 'package:talawa/widgets/custom_alert_dialog.dart'; import 'package:talawa/widgets/lang_switch.dart'; +import 'package:talawa/widgets/talawa_error_dialog.dart'; import 'package:talawa/widgets/theme_switch.dart'; /// Widget representing the App Settings page. @@ -262,6 +265,7 @@ class AppSettingsPage extends StatelessWidget { children: [ customDivider(context: context), TextButton( + key: const Key('Logout'), child: Center( child: Row( mainAxisAlignment: MainAxisAlignment.center, @@ -289,7 +293,34 @@ class AppSettingsPage extends StatelessWidget { ), onPressed: () { userConfig.loggedIn - ? model.logout(context) + ? showDialog( + context: context, + builder: (context) { + return CustomAlertDialog( + reverse: true, + dialogSubTitle: 'Are you sure you want to logout?', + successText: 'LogOut', + success: () async { + try { + await model.logout(); + navigationService.pop(); + navigationService.removeAllAndPush( + '/selectLang', + '/', + ); + } catch (e) { + navigationService.pushDialog( + const TalawaErrorDialog( + 'Unable to logout, please try again.', + key: Key('TalawaError'), + messageType: MessageType.error, + ), + ); + } + }, + ); + }, + ) : navigationService.pushScreen( Routes.setUrlScreen, arguments: '', diff --git a/test/view_model_tests/after_auth_view_model_tests/settings_view_models_test/app_setting_view_model_test.dart b/test/view_model_tests/after_auth_view_model_tests/settings_view_models_test/app_setting_view_model_test.dart index edcf1b768..3827b490f 100644 --- a/test/view_model_tests/after_auth_view_model_tests/settings_view_models_test/app_setting_view_model_test.dart +++ b/test/view_model_tests/after_auth_view_model_tests/settings_view_models_test/app_setting_view_model_test.dart @@ -3,24 +3,17 @@ import 'dart:io'; -import 'package:flutter/material.dart'; -import 'package:flutter_localizations/flutter_localizations.dart'; import 'package:flutter_test/flutter_test.dart'; import 'package:hive/hive.dart'; import 'package:mockito/mockito.dart'; import 'package:plugin_platform_interface/plugin_platform_interface.dart'; import 'package:talawa/models/organization/org_info.dart'; import 'package:talawa/models/user/user_info.dart'; -import 'package:talawa/router.dart' as router; import 'package:talawa/services/size_config.dart'; -import 'package:talawa/utils/app_localization.dart'; import 'package:talawa/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart'; -import 'package:talawa/view_model/lang_view_model.dart'; -import 'package:talawa/views/base_view.dart'; import 'package:url_launcher_platform_interface/url_launcher_platform_interface.dart'; import '../../../helpers/test_helpers.dart'; import '../../../helpers/test_locator.dart'; -import '../../../router_test.dart'; class MockUrlLauncher extends Mock with MockPlatformInterfaceMixin @@ -64,74 +57,7 @@ void main() async { test('Test logout function.', () { final model = AppSettingViewModel(); - final context = MockBuildContext(); - model.logout(context); - }); - - testWidgets("Test logout dialog when logout successful.", (tester) async { - const userLoggedin = false; - when(userConfig.loggedIn).thenAnswer((_) => userLoggedin); - final model = AppSettingViewModel(); - - final widget = BaseView( - onModelReady: (model) => model.initialize(), - builder: (context, langModel, child) { - return MaterialApp( - locale: const Locale('en'), - localizationsDelegates: [ - const AppLocalizationsDelegate(isTest: true), - GlobalMaterialLocalizations.delegate, - GlobalWidgetsLocalizations.delegate, - ], - home: Scaffold( - body: model.logoutDialog(), - ), - navigatorKey: navigationService.navigatorKey, - onGenerateRoute: router.generateRoute, - ); - }, - ); - - await tester.pumpWidget(widget); - await tester.pumpAndSettle(); - - await tester.tap(find.textContaining('Logout')); - await tester.pumpAndSettle(); - - verify(navigationService.navigatorKey); - }); - - testWidgets("Test logout dialog when logout unsuccessful.", (tester) async { - final model = AppSettingViewModel(); - const userLoggedIn = true; - when(userConfig.loggedIn).thenAnswer((_) => userLoggedIn); - - final widget = BaseView( - onModelReady: (model) => model.initialize(), - builder: (context, langModel, child) { - return MaterialApp( - locale: const Locale('en'), - localizationsDelegates: [ - const AppLocalizationsDelegate(isTest: true), - GlobalMaterialLocalizations.delegate, - GlobalWidgetsLocalizations.delegate, - ], - home: Scaffold( - body: model.logoutDialog(), - ), - navigatorKey: navigationService.navigatorKey, - onGenerateRoute: router.generateRoute, - ); - }, - ); - - await tester.pumpWidget(widget); - await tester.pumpAndSettle(); - - await tester.tap(find.textContaining('Logout')); - await tester.pumpAndSettle(); - - verify(navigationService.navigatorKey); + model.logout(); }); test('test for launchWebsite method', () async { diff --git a/test/widget_tests/after_auth_screens/app_settings/app_setting_page_test.dart b/test/widget_tests/after_auth_screens/app_settings/app_setting_page_test.dart index 58742d74d..2705a2181 100644 --- a/test/widget_tests/after_auth_screens/app_settings/app_setting_page_test.dart +++ b/test/widget_tests/after_auth_screens/app_settings/app_setting_page_test.dart @@ -14,6 +14,7 @@ import 'package:talawa/services/graphql_config.dart'; import 'package:talawa/services/navigation_service.dart'; import 'package:talawa/services/size_config.dart'; import 'package:talawa/utils/app_localization.dart'; +import 'package:talawa/view_model/after_auth_view_models/settings_view_models/app_setting_view_model.dart'; import 'package:talawa/view_model/lang_view_model.dart'; import 'package:talawa/view_model/theme_view_model.dart'; import 'package:talawa/views/after_auth_screens/app_settings/app_settings_page.dart'; @@ -271,7 +272,10 @@ Future main() async { await tester.pumpWidget(createChangePassScreenDark()); await tester.pumpAndSettle(); - final logoutButton = find.textContaining('Logout'); + await tester.tap(find.byKey(const Key('Logout'))); + await tester.pumpAndSettle(); + + final logoutButton = find.textContaining('LogOut'); await tester.tap(logoutButton); unregisterServices(); @@ -288,5 +292,21 @@ Future main() async { verify(navigationService.navigatorKey); }); + testWidgets('Test if Logout is unsuccessful.', (tester) async { + final model = AppSettingViewModel(); + when(model.logout()).thenThrow(Exception('Test error')); + + const userLoggedIn = true; + when(userConfig.loggedIn).thenAnswer((_) => userLoggedIn); + + await tester.pumpWidget(createChangePassScreenDark()); + await tester.pumpAndSettle(); + + await tester.tap(find.byKey(const Key('Logout'))); + await tester.pumpAndSettle(); + + final logoutButton = find.textContaining('LogOut'); + await tester.tap(logoutButton); + }); }); } From 82cf3db613813943fcb8598dcb27e2a47aadd7ab Mon Sep 17 00:00:00 2001 From: Abhishek Saini <78199221+Abhisheksainii@users.noreply.github.com> Date: Mon, 8 Jan 2024 04:26:06 +0530 Subject: [PATCH 11/19] fix: Removed all references to Google firebase (#2257) * feature: Removed all references to Google firebase * formatted firebase_mocks.dart * removed ignore directive for custom lint rule * formatted login_view_model file * removal of commented code * removed fcmToken test * avoid dynamic calls check passed * format check * fixed linting issue * added documentation for event_queries file * format check --- android/app/src/main/AndroidManifest.xml | 3 - lib/firebase_options.dart | 93 ---- lib/main.dart | 156 ------- lib/services/database_mutation_functions.dart | 12 - lib/utils/event_queries.dart | 1 + lib/utils/queries.dart | 32 +- .../login_view_model.dart | 38 +- pubspec.lock | 78 +--- pubspec.yaml | 4 - test/helpers/setup_firebase_mocks.dart | 402 +++++++++--------- test/utils_tests/queries_test.dart | 10 - .../login_view_model_test.dart | 23 - .../events/edit_event_page_test.dart | 5 - .../pre_auth_screens/splash_screen_test.dart | 6 - 14 files changed, 216 insertions(+), 647 deletions(-) delete mode 100644 lib/firebase_options.dart diff --git a/android/app/src/main/AndroidManifest.xml b/android/app/src/main/AndroidManifest.xml index 6a17167af..937b31192 100644 --- a/android/app/src/main/AndroidManifest.xml +++ b/android/app/src/main/AndroidManifest.xml @@ -64,9 +64,6 @@ - androidFirebaseOptions, - Map iosFirebaseOptions, - ) { - if (kIsWeb) { - throw UnsupportedError( - 'DefaultFirebaseOptions have not been configured for web - ' - 'you can reconfigure this by running the FlutterFire CLI again.', - ); - } - switch (defaultTargetPlatform) { - case TargetPlatform.android: - return android(androidFirebaseOptions); - case TargetPlatform.iOS: - return ios(iosFirebaseOptions); - case TargetPlatform.macOS: - throw UnsupportedError( - 'DefaultFirebaseOptions have not been configured for macos - ' - 'you can reconfigure this by running the FlutterFire CLI again.', - ); - default: - throw UnsupportedError( - 'DefaultFirebaseOptions are not supported for this platform.', - ); - } - } - - /// Scaffolds androidFirebaseOptions around FirebaseOptions. - /// - /// **params**: - /// * `androidFirebaseOptions`: The options which we want to scaffold - /// - /// **returns**: - /// * `FirebaseOptions`: Scaffolded FirebaseOptions - static FirebaseOptions android(Map androidFirebaseOptions) => - FirebaseOptions( - apiKey: androidFirebaseOptions['apiKey'] as String, - appId: androidFirebaseOptions['appId'] as String, - messagingSenderId: - androidFirebaseOptions['messagingSenderId'] as String, - projectId: androidFirebaseOptions['projectId'] as String, - storageBucket: androidFirebaseOptions['storageBucket'] as String, - ); - - /// Scaffolds iosFirebaseOptions around FirebaseOptions. - /// - /// more_info_if_required - /// - /// **params**: - /// * `iosFirebaseOptions`: The options which we want to scaffold - /// - /// **returns**: - /// * `FirebaseOptions`: Scaffolded FirebaseOptions - static FirebaseOptions ios(Map iosFirebaseOptions) => - FirebaseOptions( - apiKey: iosFirebaseOptions['apiKey'] as String, - appId: iosFirebaseOptions['appId'] as String, - messagingSenderId: iosFirebaseOptions['messagingSenderId'] as String, - projectId: iosFirebaseOptions['projectId'] as String, - storageBucket: iosFirebaseOptions['storageBucket'] as String, - iosClientId: iosFirebaseOptions['iosClientId'] as String, - iosBundleId: iosFirebaseOptions['iosBundleId'] as String, - ); -} diff --git a/lib/main.dart b/lib/main.dart index 4ed80df74..f0e11a8d3 100644 --- a/lib/main.dart +++ b/lib/main.dart @@ -1,11 +1,7 @@ import 'dart:io'; -import 'package:firebase_core/firebase_core.dart'; -import 'package:firebase_messaging/firebase_messaging.dart'; -import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:flutter/services.dart' as fs; -import 'package:flutter_local_notifications/flutter_local_notifications.dart'; import 'package:flutter_localizations/flutter_localizations.dart'; import 'package:hive/hive.dart'; import 'package:path_provider/path_provider.dart' as path; @@ -13,7 +9,6 @@ import 'package:provider/provider.dart'; import 'package:quick_actions/quick_actions.dart'; import 'package:talawa/constants/custom_theme.dart'; import 'package:talawa/constants/quick_actions.dart'; -import 'package:talawa/firebase_options.dart'; import 'package:talawa/locator.dart'; import 'package:talawa/models/asymetric_keys/asymetric_keys.dart'; import 'package:talawa/models/organization/org_info.dart'; @@ -26,51 +21,6 @@ import 'package:talawa/view_model/lang_view_model.dart'; import 'package:talawa/view_model/theme_view_model.dart'; import 'package:talawa/views/base_view.dart'; -/// Define a top-level named handler which background/terminated messages will call. -/// -/// To verify things are working, check out the native platform logs. -/// **params**: -/// * `message`: incoming messsage. -/// -/// **returns**: -/// * `Future`: promise that will be fulfilled message background activities are successful. -Future _firebaseMessagingBackgroundHandler(RemoteMessage message) async { - // If you're going to use other Firebase services in the background, such as Firestore, - // make sure you call `initializeApp` before using other Firebase services. - final Directory dir = await path.getApplicationDocumentsDirectory(); - Hive.init(dir.path); - await setUpFirebaseKeys(); - await setUpFirebase(); -} - -/// Initializes the firebase in the app according to the userplatform (android/iOS). -/// -/// **params**: -/// None -/// -/// **returns**: -/// * `Future`: promise that will be fulfilled Firebase is setted up in app. -Future setUpFirebase() async { - await Firebase.initializeApp( - options: DefaultFirebaseOptions.currentPlatform( - androidFirebaseOptions, - iosFirebaseOptions, - ), - ); -} - -/// HashMap of Firebase options for android. -late Map androidFirebaseOptions; - -/// HashMap of Firebase options for android. -late Map iosFirebaseOptions; - -/// Create a [AndroidNotificationChannel] for heads up notifications. -late AndroidNotificationChannel channel; - -/// Initialize the [FlutterLocalNotificationsPlugin] package. -late FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin; - /// First function to initialize the application, invoked automatically. /// /// **params**: @@ -82,26 +32,6 @@ Future main() async { // Returns an instance of the binding that implements WidgetsBinding. WidgetsFlutterBinding.ensureInitialized(); - if (!kIsWeb) { - channel = const AndroidNotificationChannel( - 'high_importance_channel', // id - 'High Importance Notifications', // title - description: - 'This channel is used for important notifications.', // description - importance: Importance.high, - ); - - flutterLocalNotificationsPlugin = FlutterLocalNotificationsPlugin(); - - // Create an Android Notification Channel. - // We use this channel in the `AndroidManifest.xml` file to override the - // default FCM channel to enable heads up notifications. - await flutterLocalNotificationsPlugin - .resolvePlatformSpecificImplementation< - AndroidFlutterLocalNotificationsPlugin>() - ?.createNotificationChannel(channel); - } - final Directory dir = await path.getApplicationDocumentsDirectory(); Hive ..init(dir.path) @@ -115,52 +45,11 @@ Future main() async { await Hive.openBox('pluginBox'); await Hive.openBox('url'); - final urlBox = await Hive.openBox('url'); - - try { - if (urlBox.get('url') != null) { - await setUpFirebaseKeys(); - - await setUpFirebase(); - await setUpFirebaseMessaging(); - } - } catch (e) { - print("Firebase not working"); - } - setupLocator(); // The runApp() function takes the given Widget and makes it the root of the widget tree. runApp(MyApp()); } -/// Initializes the firebase keys in the app according to the userplatform (android/iOS). -/// -/// **params**: -/// None -/// -/// **returns**: -/// * `Future`: promise that will be fulfilled Firebase keys are setted up. -Future setUpFirebaseKeys() async { - final androidFirebaseOptionsBox = - await Hive.openBox('androidFirebaseOptions'); - final androidFirebaseOptionsMap = androidFirebaseOptionsBox - .get('androidFirebaseOptions') as Map?; - - final iosFirebaseOptionsBox = await Hive.openBox('iosFirebaseOptions'); - final iosFirebaseOptionsMap = - iosFirebaseOptionsBox.get('iosFirebaseOptions') as Map?; - if (androidFirebaseOptionsMap != null) { - androidFirebaseOptions = androidFirebaseOptionsMap.map((key, value) { - return MapEntry(key.toString(), value); - }); - } - if (iosFirebaseOptionsMap != null) { - iosFirebaseOptions = iosFirebaseOptionsMap.map((key, value) { - return MapEntry(key.toString(), value); - }); - } -} - /// Main widget that sets up the quick actions, internationalization, routing , notifications. class MyApp extends StatefulWidget { // This widget is the root of your application. @@ -332,48 +221,3 @@ class DemoViewModel extends BaseModel { /// * `String`: title of the model String get title => _title; } - -/// Set up firebase instance, enbables messaging,listens to icoming messages. -/// -/// **params**: -/// None -/// -/// **returns**: -/// * `Future`: promise that will be fulfilled Firebase is setted up. -Future setUpFirebaseMessaging() async { - /// Set the background messaging handler early on, as a named top-level function - FirebaseMessaging.onBackgroundMessage(_firebaseMessagingBackgroundHandler); - - // Update the iOS foreground notification presentation options to allow heads up notifications. - await FirebaseMessaging.instance.setForegroundNotificationPresentationOptions( - alert: true, - badge: true, - sound: true, - ); - - FirebaseMessaging.instance - .getInitialMessage() - .then((RemoteMessage? message) {}); - - FirebaseMessaging.onMessage.listen((RemoteMessage message) { - final RemoteNotification? notification = message.notification; - final AndroidNotification? android = message.notification?.android; - if (notification != null && android != null && !kIsWeb) { - flutterLocalNotificationsPlugin.show( - notification.hashCode, - notification.title, - notification.body, - NotificationDetails( - android: AndroidNotificationDetails( - channel.id, - channel.name, - channelDescription: channel.description, - icon: 'launch_background', - ), - ), - ); - } - }); - - FirebaseMessaging.onMessageOpenedApp.listen((RemoteMessage message) {}); -} diff --git a/lib/services/database_mutation_functions.dart b/lib/services/database_mutation_functions.dart index 03d6b1d95..d9aeec90e 100644 --- a/lib/services/database_mutation_functions.dart +++ b/lib/services/database_mutation_functions.dart @@ -191,18 +191,6 @@ class DataBaseMutationFunctions { } return false; } - if (exception.graphqlErrors[i].message == - notifFeatureNotInstalled.message) { - if (showSnackBar) { - WidgetsBinding.instance.addPostFrameCallback( - (_) => navigationService.showTalawaErrorDialog( - "Notification Feature is not installed", - MessageType.error, - ), - ); - } - return false; - } } // if the error is unknown diff --git a/lib/utils/event_queries.dart b/lib/utils/event_queries.dart index 14c9e82e5..6944de83f 100644 --- a/lib/utils/event_queries.dart +++ b/lib/utils/event_queries.dart @@ -10,6 +10,7 @@ class EventQueries { /// /// This function generates a GraphQL query string to retrieve events /// based on the provided organization ID. + String fetchOrgEvents(String orgId) { return """ query { diff --git a/lib/utils/queries.dart b/lib/utils/queries.dart index 8a91298f4..446c66880 100644 --- a/lib/utils/queries.dart +++ b/lib/utils/queries.dart @@ -147,22 +147,7 @@ class Queries { } } refreshToken - androidFirebaseOptions { - apiKey - appId - messagingSenderId - projectId - storageBucket - } - iosFirebaseOptions { - apiKey - appId - messagingSenderId - projectId - storageBucket - iosClientId - iosBundleId - } + } } """; @@ -193,21 +178,6 @@ class Queries { """; } - /// To save fcm token the backend fro notification. - /// - /// **params**: - /// * `token`: fcm token, read firebase docs for more info - /// - /// **returns**: - /// * `String`: return the mutation - String saveFcmToken(String? token) { - return """ - mutation { - saveFcmToken(token: "$token") - } - """; - } - /// logout muiation. /// /// **params**: diff --git a/lib/view_model/pre_auth_view_models/login_view_model.dart b/lib/view_model/pre_auth_view_models/login_view_model.dart index 0f909bfdb..3a8b637a6 100644 --- a/lib/view_model/pre_auth_view_models/login_view_model.dart +++ b/lib/view_model/pre_auth_view_models/login_view_model.dart @@ -1,12 +1,10 @@ -// ignore_for_file: talawa_api_doc, avoid_dynamic_calls -// ignore_for_file: talawa_good_doc_comments +// ignore_for_file: avoid_dynamic_calls -import 'package:firebase_messaging/firebase_messaging.dart'; import 'package:flutter/material.dart'; -import 'package:hive/hive.dart'; +// import 'package:hive/hive.dart'; import 'package:talawa/constants/routing_constants.dart'; import 'package:talawa/locator.dart'; -import 'package:talawa/main.dart'; +// import 'package:talawa/main.dart'; import 'package:talawa/models/mainscreen_navigation_args.dart'; import 'package:talawa/models/user/user_info.dart'; import 'package:talawa/utils/encryptor.dart'; @@ -105,36 +103,6 @@ class LoginViewModel extends BaseModel { arguments: MainScreenArgs(mainScreenIndex: 0, fromSignUp: false), ); } - final loginResult = result.data['login'] as Map; - androidFirebaseOptions = - loginResult['androidFirebaseOptions'] as Map; - iosFirebaseOptions = - loginResult['iosFirebaseOptions'] as Map; - if (androidFirebaseOptions['apiKey'] != null || - iosFirebaseOptions['apiKey'] != null) { - await setUpFirebase(); - - final token = await FirebaseMessaging.instance.getToken(); - await databaseFunctions.gqlAuthMutation( - queries.saveFcmToken(token), - ); - - await setUpFirebaseMessaging(); - - final androidFirebaseOptionsBox = - await Hive.openBox('androidFirebaseOptions'); - androidFirebaseOptionsBox.put( - 'androidFirebaseOptions', - androidFirebaseOptions, - ); - - final iosFirebaseOptionsBox = - await Hive.openBox('iosFirebaseOptions'); - iosFirebaseOptionsBox.put( - 'iosFirebaseOptions', - iosFirebaseOptions, - ); - } } } on Exception catch (e) { print('here'); diff --git a/pubspec.lock b/pubspec.lock index 36d5b5438..7d75e820d 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -17,14 +17,6 @@ packages: url: "https://pub.dev" source: hosted version: "61.0.0" - _flutterfire_internals: - dependency: transitive - description: - name: _flutterfire_internals - sha256: f5628cd9c92ed11083f425fd1f8f1bc60ecdda458c81d73b143aeda036c35fe7 - url: "https://pub.dev" - source: hosted - version: "1.3.16" analyzer: dependency: transitive description: @@ -213,10 +205,10 @@ packages: dependency: transitive description: name: collection - sha256: ee67cb0715911d28db6bf4af1026078bd6f0128b07a5f66fb2ed94ec6783c09a + sha256: f092b211a4319e98e5ff58223576de6c2803db36221657b46c82574721240687 url: "https://pub.dev" source: hosted - version: "1.18.0" + version: "1.17.2" connectivity_plus: dependency: "direct main" description: @@ -409,54 +401,6 @@ packages: url: "https://pub.dev" source: hosted version: "0.9.3+1" - firebase_core: - dependency: "direct main" - description: - name: firebase_core - sha256: "96607c0e829a581c2a483c658f04e8b159964c3bae2730f73297070bc85d40bb" - url: "https://pub.dev" - source: hosted - version: "2.24.2" - firebase_core_platform_interface: - dependency: "direct main" - description: - name: firebase_core_platform_interface - sha256: c437ae5d17e6b5cc7981cf6fd458a5db4d12979905f9aafd1fea930428a9fe63 - url: "https://pub.dev" - source: hosted - version: "5.0.0" - firebase_core_web: - dependency: transitive - description: - name: firebase_core_web - sha256: d585bdf3c656c3f7821ba1bd44da5f13365d22fcecaf5eb75c4295246aaa83c0 - url: "https://pub.dev" - source: hosted - version: "2.10.0" - firebase_messaging: - dependency: "direct main" - description: - name: firebase_messaging - sha256: "199fe8186a5370d1cf5ce0819191079afc305914e8f38715f5e23943940dfe2d" - url: "https://pub.dev" - source: hosted - version: "14.7.9" - firebase_messaging_platform_interface: - dependency: "direct main" - description: - name: firebase_messaging_platform_interface - sha256: "54e283a0e41d81d854636ad0dad73066adc53407a60a7c3189c9656e2f1b6107" - url: "https://pub.dev" - source: hosted - version: "4.5.18" - firebase_messaging_web: - dependency: transitive - description: - name: firebase_messaging_web - sha256: "90dc7ed885e90a24bb0e56d661d4d2b5f84429697fd2cbb9e5890a0ca370e6f4" - url: "https://pub.dev" - source: hosted - version: "3.5.18" fixnum: dependency: transitive description: @@ -1542,18 +1486,18 @@ packages: dependency: transitive description: name: stack_trace - sha256: "73713990125a6d93122541237550ee3352a2d84baad52d375a4cad2eb9b7ce0b" + sha256: c3c7d8edb15bee7f0f74debd4b9c5f3c2ea86766fe4178eb2a18eb30a0bdaed5 url: "https://pub.dev" source: hosted - version: "1.11.1" + version: "1.11.0" stream_channel: dependency: transitive description: name: stream_channel - sha256: ba2aa5d8cc609d96bbb2899c28934f9e1af5cddbd60a827822ea467161eb54e7 + sha256: "83615bee9045c1d322bbbd1ba209b7a749c2cbcdcb3fdd1df8eb488b3279c1c8" url: "https://pub.dev" source: hosted - version: "2.1.2" + version: "2.1.1" stream_transform: dependency: transitive description: @@ -1621,10 +1565,10 @@ packages: dependency: transitive description: name: test_api - sha256: "5c2f730018264d276c20e4f1503fd1308dfbbae39ec8ee63c5236311ac06954b" + sha256: "75760ffd7786fffdfb9597c35c5b27eaeec82be8edfb6d71d32651128ed7aab8" url: "https://pub.dev" source: hosted - version: "0.6.1" + version: "0.6.0" timelines: dependency: "direct main" description: @@ -1869,10 +1813,10 @@ packages: dependency: transitive description: name: web - sha256: afe077240a270dcfd2aafe77602b4113645af95d0ad31128cc02bce5ac5d5152 + sha256: dc8ccd225a2005c1be616fe02951e2e342092edf968cf0844220383757ef8f10 url: "https://pub.dev" source: hosted - version: "0.3.0" + version: "0.1.4-beta" web_socket_channel: dependency: transitive description: @@ -1923,4 +1867,4 @@ packages: version: "3.1.2" sdks: dart: ">=3.2.0 <3.13.0" - flutter: ">=3.16.0" + flutter: ">=3.16.0" \ No newline at end of file diff --git a/pubspec.yaml b/pubspec.yaml index af6ac2916..58fece18e 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -32,10 +32,6 @@ dependencies: # custom_lint_builder: ^0.4.0 ################################ file: ^7.0.0 - firebase_core: ^2.24.2 - firebase_core_platform_interface: ^5.0.0 - firebase_messaging: ^14.7.9 - firebase_messaging_platform_interface: ^4.5.17 flutter: sdk: flutter diff --git a/test/helpers/setup_firebase_mocks.dart b/test/helpers/setup_firebase_mocks.dart index 622f975ac..ec3064674 100644 --- a/test/helpers/setup_firebase_mocks.dart +++ b/test/helpers/setup_firebase_mocks.dart @@ -3,206 +3,204 @@ // ignore_for_file: return_of_invalid_type -import 'package:firebase_core/firebase_core.dart'; +// import 'package:firebase_core/firebase_core.dart'; // import 'package:firebase_core_platform_interface/firebase_core_platform_interface.dart'; -import 'package:firebase_messaging_platform_interface/firebase_messaging_platform_interface.dart'; -import 'package:flutter/services.dart'; -import 'package:flutter_test/flutter_test.dart'; -import 'package:mockito/mockito.dart'; -import 'package:plugin_platform_interface/plugin_platform_interface.dart'; - -final kMockMessagingPlatform = MockFirebaseMessaging(); - -Future neverEndingFuture() async { - // ignore: literal_only_boolean_expressions - while (true) { - await Future.delayed(const Duration(minutes: 5)); - } -} - -void setupFirebaseMocks() { - TestWidgetsFlutterBinding.ensureInitialized(); - - const firebaseChannel = MethodChannel( - 'plugins.flutter.io/firebase_core', - ); - - // ignore: deprecated_member_use - firebaseChannel.setMockMethodCallHandler((call) async { - if (call.method == 'Firebase#initializeCore') { - return [ - { - 'name': defaultFirebaseAppName, - 'options': { - 'apiKey': '123', - 'appId': '123', - 'messagingSenderId': '123', - 'projectId': '123', - }, - 'pluginConstants': {}, - } - ]; - } - - if (call.method == 'Firebase#initializeApp') { - return { - 'name': call.arguments['appName'], - 'options': call.arguments['options'], - 'pluginConstants': {}, - }; - } - - return null; - }); - - when(kMockMessagingPlatform.delegateFor(app: anyNamed('app'))) - .thenReturn(kMockMessagingPlatform); - when( - kMockMessagingPlatform.setInitialValues( - isAutoInitEnabled: anyNamed('isAutoInitEnabled'), - ), - ).thenReturn(kMockMessagingPlatform); -} - -class MockFirebaseMessaging extends Mock - with MockPlatformInterfaceMixin - implements FirebaseMessagingPlatform { - MockFirebaseMessaging() { - TestFirebaseMessagingPlatform(); - } - - @override - bool get isAutoInitEnabled { - return super.noSuchMethod( - Invocation.getter(#isAutoInitEnabled), - returnValue: true, - returnValueForMissingStub: true, - ); - } - - @override - FirebaseMessagingPlatform delegateFor({FirebaseApp? app}) { - return super.noSuchMethod( - Invocation.method(#delegateFor, [], {#app: app}), - returnValue: TestFirebaseMessagingPlatform(), - returnValueForMissingStub: TestFirebaseMessagingPlatform(), - ); - } - - @override - FirebaseMessagingPlatform setInitialValues({bool? isAutoInitEnabled}) { - return super.noSuchMethod( - Invocation.method( - #setInitialValues, - [], - {#isAutoInitEnabled: isAutoInitEnabled}, - ), - returnValue: TestFirebaseMessagingPlatform(), - returnValueForMissingStub: TestFirebaseMessagingPlatform(), - ); - } - - @override - Future getInitialMessage() { - return super.noSuchMethod( - Invocation.method(#getInitialMessage, []), - returnValue: neverEndingFuture(), - returnValueForMissingStub: neverEndingFuture(), - ); - } - - @override - Future deleteToken() { - return super.noSuchMethod( - Invocation.method(#deleteToken, []), - returnValue: Future.value(), - returnValueForMissingStub: Future.value(), - ); - } - - @override - Future getAPNSToken() { - return super.noSuchMethod( - Invocation.method(#getAPNSToken, []), - returnValue: Future.value(''), - returnValueForMissingStub: Future.value(''), - ); - } - - @override - Future getToken({String? vapidKey}) { - return super.noSuchMethod( - Invocation.method(#getToken, [], {#vapidKey: vapidKey}), - returnValue: Future.value(''), - returnValueForMissingStub: Future.value(''), - ); - } - - @override - Future setAutoInitEnabled(bool? enabled) { - return super.noSuchMethod( - Invocation.method(#setAutoInitEnabled, [enabled]), - returnValue: Future.value(), - returnValueForMissingStub: Future.value(), - ); - } - - @override - Stream get onTokenRefresh { - return super.noSuchMethod( - Invocation.getter(#onTokenRefresh), - returnValue: const Stream.empty(), - returnValueForMissingStub: const Stream.empty(), - ); - } - -// Comment out the notification logic for the MVP -// TODO: Re-enable notifications when needed for the final release. - - // @override - // Future requestPermission({ - // bool? alert = true, - // bool? announcement = false, - // bool? badge = true, - // bool? carPlay = false, - // bool? criticalAlert = false, - // bool? provisional = false, - // bool? sound = true, - // }) { - // return super.noSuchMethod( - // Invocation.method(#requestPermission, [], { - // #alert: alert, - // #announcement: announcement, - // #badge: badge, - // #carPlay: carPlay, - // #criticalAlert: criticalAlert, - // #provisional: provisional, - // #sound: sound, - // }), - // returnValue: neverEndingFuture(), - // returnValueForMissingStub: neverEndingFuture(), - // ); - // } - - @override - Future subscribeToTopic(String? topic) { - return super.noSuchMethod( - Invocation.method(#subscribeToTopic, [topic]), - returnValue: Future.value(), - returnValueForMissingStub: Future.value(), - ); - } - - @override - Future unsubscribeFromTopic(String? topic) { - return super.noSuchMethod( - Invocation.method(#unsubscribeFromTopic, [topic]), - returnValue: Future.value(), - returnValueForMissingStub: Future.value(), - ); - } -} - -class TestFirebaseMessagingPlatform extends FirebaseMessagingPlatform { - TestFirebaseMessagingPlatform() : super(); -} +// import 'package:firebase_messaging_platform_interface/firebase_messaging_platform_interface.dart'; +// import 'package:flutter/services.dart'; +// import 'package:flutter_test/flutter_test.dart'; +// import 'package:mockito/mockito.dart'; +// import 'package:plugin_platform_interface/plugin_platform_interface.dart'; + +// final kMockMessagingPlatform = MockFirebaseMessaging(); + +// Future neverEndingFuture() async { +// // ignore: literal_only_boolean_expressions +// while (true) { +// await Future.delayed(const Duration(minutes: 5)); +// } +// } + +// void setupFirebaseMocks() { +// TestWidgetsFlutterBinding.ensureInitialized(); + +// const firebaseChannel = MethodChannel( +// 'plugins.flutter.io/firebase_core', +// ); + +// // ignore: deprecated_member_use +// firebaseChannel.setMockMethodCallHandler((call) async { +// if (call.method == 'Firebase#initializeCore') { +// return [ +// { +// 'name': defaultFirebaseAppName, +// 'options': { +// 'apiKey': '123', +// 'appId': '123', +// 'messagingSenderId': '123', +// 'projectId': '123', +// }, +// 'pluginConstants': {}, +// } +// ]; +// } + +// if (call.method == 'Firebase#initializeApp') { +// return { +// 'name': call.arguments['appName'], +// 'options': call.arguments['options'], +// 'pluginConstants': {}, +// }; +// } + +// return null; +// }); + +// when(kMockMessagingPlatform.delegateFor(app: anyNamed('app'))) +// .thenReturn(kMockMessagingPlatform); +// when( +// kMockMessagingPlatform.setInitialValues( +// isAutoInitEnabled: anyNamed('isAutoInitEnabled'), +// ), +// ).thenReturn(kMockMessagingPlatform); +// } + +// class MockFirebaseMessaging extends Mock with MockPlatformInterfaceMixin { +// MockFirebaseMessaging() { +// // TestFirebaseMessagingPlatform(); +// } + +// @override +// bool get isAutoInitEnabled { +// return super.noSuchMethod( +// Invocation.getter(#isAutoInitEnabled), +// returnValue: true, +// returnValueForMissingStub: true, +// ); +// } + +// // @override +// // FirebaseMessagingPlatform delegateFor({FirebaseApp? app}) { +// // return super.noSuchMethod( +// // Invocation.method(#delegateFor, [], {#app: app}), +// // returnValue: TestFirebaseMessagingPlatform(), +// // returnValueForMissingStub: TestFirebaseMessagingPlatform(), +// // ); +// // } + +// // @override +// // FirebaseMessagingPlatform setInitialValues({bool? isAutoInitEnabled}) { +// // return super.noSuchMethod( +// // Invocation.method( +// // #setInitialValues, +// // [], +// // {#isAutoInitEnabled: isAutoInitEnabled}, +// // ), +// // returnValue: TestFirebaseMessagingPlatform(), +// // returnValueForMissingStub: TestFirebaseMessagingPlatform(), +// // ); +// // } + +// // @override +// // Future getInitialMessage() { +// // return super.noSuchMethod( +// // Invocation.method(#getInitialMessage, []), +// // returnValue: neverEndingFuture(), +// // returnValueForMissingStub: neverEndingFuture(), +// // ); +// // } + +// @override +// Future deleteToken() { +// return super.noSuchMethod( +// Invocation.method(#deleteToken, []), +// returnValue: Future.value(), +// returnValueForMissingStub: Future.value(), +// ); +// } + +// @override +// Future getAPNSToken() { +// return super.noSuchMethod( +// Invocation.method(#getAPNSToken, []), +// returnValue: Future.value(''), +// returnValueForMissingStub: Future.value(''), +// ); +// } + +// @override +// Future getToken({String? vapidKey}) { +// return super.noSuchMethod( +// Invocation.method(#getToken, [], {#vapidKey: vapidKey}), +// returnValue: Future.value(''), +// returnValueForMissingStub: Future.value(''), +// ); +// } + +// @override +// Future setAutoInitEnabled(bool? enabled) { +// return super.noSuchMethod( +// Invocation.method(#setAutoInitEnabled, [enabled]), +// returnValue: Future.value(), +// returnValueForMissingStub: Future.value(), +// ); +// } + +// @override +// Stream get onTokenRefresh { +// return super.noSuchMethod( +// Invocation.getter(#onTokenRefresh), +// returnValue: const Stream.empty(), +// returnValueForMissingStub: const Stream.empty(), +// ); +// } + +// // Comment out the notification logic for the MVP +// // TODO: Re-enable notifications when needed for the final release. + +// // @override +// // Future requestPermission({ +// // bool? alert = true, +// // bool? announcement = false, +// // bool? badge = true, +// // bool? carPlay = false, +// // bool? criticalAlert = false, +// // bool? provisional = false, +// // bool? sound = true, +// // }) { +// // return super.noSuchMethod( +// // Invocation.method(#requestPermission, [], { +// // #alert: alert, +// // #announcement: announcement, +// // #badge: badge, +// // #carPlay: carPlay, +// // #criticalAlert: criticalAlert, +// // #provisional: provisional, +// // #sound: sound, +// // }), +// // returnValue: neverEndingFuture(), +// // returnValueForMissingStub: neverEndingFuture(), +// // ); +// // } + +// @override +// Future subscribeToTopic(String? topic) { +// return super.noSuchMethod( +// Invocation.method(#subscribeToTopic, [topic]), +// returnValue: Future.value(), +// returnValueForMissingStub: Future.value(), +// ); +// } + +// @override +// Future unsubscribeFromTopic(String? topic) { +// return super.noSuchMethod( +// Invocation.method(#unsubscribeFromTopic, [topic]), +// returnValue: Future.value(), +// returnValueForMissingStub: Future.value(), +// ); +// } +// } + +// // class TestFirebaseMessagingPlatform extends FirebaseMessagingPlatform { +// // TestFirebaseMessagingPlatform() : super(); +// // } diff --git a/test/utils_tests/queries_test.dart b/test/utils_tests/queries_test.dart index 610147ca2..6fffa6739 100644 --- a/test/utils_tests/queries_test.dart +++ b/test/utils_tests/queries_test.dart @@ -27,16 +27,6 @@ void main() { } expect(mutation, true); }); - test("Check if saveFcmToken works correctly", () { - var mutation = false; - expect(mutation, false); - - final fnData = Queries().saveFcmToken('token123'); - if (fnData.contains('token123')) { - mutation = true; - } - expect(mutation, true); - }); test("Check if logout works correctly", () { const mutation = false; expect(mutation, false); diff --git a/test/view_model_tests/pre_auth_view_models/login_view_model_test.dart b/test/view_model_tests/pre_auth_view_models/login_view_model_test.dart index 41360dbe7..7f9af6d62 100644 --- a/test/view_model_tests/pre_auth_view_models/login_view_model_test.dart +++ b/test/view_model_tests/pre_auth_view_models/login_view_model_test.dart @@ -1,8 +1,6 @@ // ignore_for_file: talawa_api_doc // ignore_for_file: talawa_good_doc_comments -// import 'package:firebase_core/firebase_core.dart'; -// import 'package:firebase_messaging_platform_interface/firebase_messaging_platform_interface.dart'; // import 'package:flutter/material.dart'; import 'package:flutter_test/flutter_test.dart'; // import 'package:graphql_flutter/graphql_flutter.dart'; @@ -15,7 +13,6 @@ import 'package:talawa/services/user_config.dart'; // import 'package:talawa/utils/queries.dart'; // import 'package:talawa/view_model/pre_auth_view_models/login_view_model.dart'; -// import '../../helpers/setup_firebase_mocks.dart'; // import '../../helpers/test_helpers.dart'; final data = { @@ -28,32 +25,12 @@ final data = { }, 'accessToken': 'testtoken', 'refreshToken': 'testtoken', - 'androidFirebaseOptions': { - 'apiKey': 'test', - 'appId': 'test', - 'messagingSenderId': 'test', - 'projectId': 'test', - 'storageBucket': 'test', - }, - 'iosFirebaseOptions': { - 'apiKey': 'test', - 'appId': 'test', - 'messagingSenderId': 'test', - 'projectId': 'test', - 'storageBucket': 'test', - 'iosClientId': 'test', - 'iosBundleId': 'test', - }, }, }; bool empty = false; Future main() async { - // setupFirebaseMocks(); - // await Firebase.initializeApp(); - // FirebaseMessagingPlatform.instance = kMockMessagingPlatform; - // setUp(() async { // locator.registerSingleton(Queries()); // registerServices(); diff --git a/test/widget_tests/after_auth_screens/events/edit_event_page_test.dart b/test/widget_tests/after_auth_screens/events/edit_event_page_test.dart index c2eb5df00..821cad531 100644 --- a/test/widget_tests/after_auth_screens/events/edit_event_page_test.dart +++ b/test/widget_tests/after_auth_screens/events/edit_event_page_test.dart @@ -3,7 +3,6 @@ // ignore_for_file: unused_import -import 'package:firebase_core/firebase_core.dart'; import 'package:flutter/material.dart'; import 'package:flutter_localizations/flutter_localizations.dart'; import 'package:flutter_test/flutter_test.dart'; @@ -22,7 +21,6 @@ import 'package:talawa/views/after_auth_screens/events/edit_events_form.dart'; import 'package:talawa/views/base_view.dart'; import 'package:talawa/widgets/event_date_time_tile.dart'; -import '../../../helpers/setup_firebase_mocks.dart'; import '../../../helpers/test_helpers.dart'; import '../../../helpers/test_helpers.mocks.dart'; @@ -75,9 +73,6 @@ void main() { setupLocator(); graphqlConfig.test(); - setupFirebaseMocks(); - // await Firebase.initializeApp(); - group("Edit Event Screen Widget Test in dark mode", () { testWidgets("Testing if dark mode is applied", (tester) async { await tester.pumpWidget( diff --git a/test/widget_tests/pre_auth_screens/splash_screen_test.dart b/test/widget_tests/pre_auth_screens/splash_screen_test.dart index d8d490941..84c3c4856 100644 --- a/test/widget_tests/pre_auth_screens/splash_screen_test.dart +++ b/test/widget_tests/pre_auth_screens/splash_screen_test.dart @@ -3,7 +3,6 @@ // ignore_for_file: unused_import -import 'package:firebase_core/firebase_core.dart'; import 'package:flutter/material.dart'; import 'package:flutter_localizations/flutter_localizations.dart'; import 'package:flutter_test/flutter_test.dart'; @@ -16,8 +15,6 @@ import 'package:talawa/utils/app_localization.dart'; import 'package:talawa/view_model/lang_view_model.dart'; import 'package:talawa/views/base_view.dart'; -import '../../helpers/setup_firebase_mocks.dart'; - Widget createSplashScreenLight({ThemeMode themeMode = ThemeMode.light}) => BaseView( onModelReady: (model) => model.initialize(), @@ -68,9 +65,6 @@ Future main() async { setupLocator(); graphqlConfig.test(); - // setupFirebaseMocks(); - // await Firebase.initializeApp(); - group('Splash Screen Widget Test in light mode', () { testWidgets("Testing if Splash Screen shows up", (tester) async { await tester.pumpWidget(createSplashScreenLight()); From 3d2108e07d412d7c18267feb951b85a3e6b5a088 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sun, 7 Jan 2024 19:37:09 -0800 Subject: [PATCH 12/19] Bump syncfusion_flutter_datepicker from 24.1.43 to 24.1.44 (#2315) Bumps [syncfusion_flutter_datepicker](https://github.com/syncfusion/flutter-widgets/tree/master/packages) from 24.1.43 to 24.1.44. - [Release notes](https://github.com/syncfusion/flutter-widgets/releases) - [Commits](https://github.com/syncfusion/flutter-widgets/commits/HEAD/packages) --- updated-dependencies: - dependency-name: syncfusion_flutter_datepicker dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- pubspec.lock | 30 +++++++++++++++--------------- pubspec.yaml | 2 +- 2 files changed, 16 insertions(+), 16 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index 7d75e820d..7bad6c82a 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -205,10 +205,10 @@ packages: dependency: transitive description: name: collection - sha256: f092b211a4319e98e5ff58223576de6c2803db36221657b46c82574721240687 + sha256: ee67cb0715911d28db6bf4af1026078bd6f0128b07a5f66fb2ed94ec6783c09a url: "https://pub.dev" source: hosted - version: "1.17.2" + version: "1.18.0" connectivity_plus: dependency: "direct main" description: @@ -1486,18 +1486,18 @@ packages: dependency: transitive description: name: stack_trace - sha256: c3c7d8edb15bee7f0f74debd4b9c5f3c2ea86766fe4178eb2a18eb30a0bdaed5 + sha256: "73713990125a6d93122541237550ee3352a2d84baad52d375a4cad2eb9b7ce0b" url: "https://pub.dev" source: hosted - version: "1.11.0" + version: "1.11.1" stream_channel: dependency: transitive description: name: stream_channel - sha256: "83615bee9045c1d322bbbd1ba209b7a749c2cbcdcb3fdd1df8eb488b3279c1c8" + sha256: ba2aa5d8cc609d96bbb2899c28934f9e1af5cddbd60a827822ea467161eb54e7 url: "https://pub.dev" source: hosted - version: "2.1.1" + version: "2.1.2" stream_transform: dependency: transitive description: @@ -1526,18 +1526,18 @@ packages: dependency: transitive description: name: syncfusion_flutter_core - sha256: "1b40729aa10a727150a6cc56e532c770f4baded83846fca8700efd908d0f4d0a" + sha256: "083d4a0ddb25435d267328a30c3938d09599f7578f5f0d28fbd9fd5424c1cd51" url: "https://pub.dev" source: hosted - version: "24.1.43" + version: "24.1.44" syncfusion_flutter_datepicker: dependency: "direct main" description: name: syncfusion_flutter_datepicker - sha256: "3f9a8e8b585dd992d2321c899ec8d914634fb99eba02cf7a91c48a098bf62820" + sha256: "3bad2603b77d5a65e1a324b09480865531ae8026b95e63b1b253b93c26204f0a" url: "https://pub.dev" source: hosted - version: "24.1.43" + version: "24.1.44" synchronized: dependency: transitive description: @@ -1565,10 +1565,10 @@ packages: dependency: transitive description: name: test_api - sha256: "75760ffd7786fffdfb9597c35c5b27eaeec82be8edfb6d71d32651128ed7aab8" + sha256: "5c2f730018264d276c20e4f1503fd1308dfbbae39ec8ee63c5236311ac06954b" url: "https://pub.dev" source: hosted - version: "0.6.0" + version: "0.6.1" timelines: dependency: "direct main" description: @@ -1813,10 +1813,10 @@ packages: dependency: transitive description: name: web - sha256: dc8ccd225a2005c1be616fe02951e2e342092edf968cf0844220383757ef8f10 + sha256: afe077240a270dcfd2aafe77602b4113645af95d0ad31128cc02bce5ac5d5152 url: "https://pub.dev" source: hosted - version: "0.1.4-beta" + version: "0.3.0" web_socket_channel: dependency: transitive description: @@ -1867,4 +1867,4 @@ packages: version: "3.1.2" sdks: dart: ">=3.2.0 <3.13.0" - flutter: ">=3.16.0" \ No newline at end of file + flutter: ">=3.16.0" diff --git a/pubspec.yaml b/pubspec.yaml index 58fece18e..39e911295 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -70,7 +70,7 @@ dependencies: shimmer: ^3.0.0 social_share: ^2.2.1 syncfusion_flutter_calendar: ^24.1.43 - syncfusion_flutter_datepicker: 24.1.43 + syncfusion_flutter_datepicker: 24.1.44 timelines: ^0.1.0 tutorial_coach_mark: ^1.2.11 uni_links: ^0.5.1 From 5b91039eeeabb1d2c3e82a7b370c2a070ddc021b Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sun, 7 Jan 2024 19:47:16 -0800 Subject: [PATCH 13/19] Bump url_launcher_platform_interface from 2.2.0 to 2.3.0 (#2314) Bumps [url_launcher_platform_interface](https://github.com/flutter/packages/tree/main/packages/url_launcher) from 2.2.0 to 2.3.0. - [Release notes](https://github.com/flutter/packages/releases) - [Commits](https://github.com/flutter/packages/commits/url_launcher_platform_interface-v2.3.0/packages/url_launcher) --- updated-dependencies: - dependency-name: url_launcher_platform_interface dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- pubspec.lock | 4 ++-- pubspec.yaml | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index 7bad6c82a..19c3b436b 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -1677,10 +1677,10 @@ packages: dependency: "direct dev" description: name: url_launcher_platform_interface - sha256: "980e8d9af422f477be6948bdfb68df8433be71f5743a188968b0c1b887807e50" + sha256: "4aca1e060978e19b2998ee28503f40b5ba6226819c2b5e3e4d1821e8ccd92198" url: "https://pub.dev" source: hosted - version: "2.2.0" + version: "2.3.0" url_launcher_web: dependency: transitive description: diff --git a/pubspec.yaml b/pubspec.yaml index 39e911295..8246569cb 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -93,7 +93,7 @@ dev_dependencies: talawa_lint: path: talawa_lint/ - url_launcher_platform_interface: any + url_launcher_platform_interface: 2.3.0 flutter: uses-material-design: true From 6e21a80a2a35973655a4910f41b513fe3297b0ea Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sun, 7 Jan 2024 19:47:37 -0800 Subject: [PATCH 14/19] Bump image_picker from 1.0.5 to 1.0.6 (#2313) Bumps [image_picker](https://github.com/flutter/packages/tree/main/packages/image_picker) from 1.0.5 to 1.0.6. - [Release notes](https://github.com/flutter/packages/releases) - [Commits](https://github.com/flutter/packages/commits/image_picker-v1.0.6/packages/image_picker) --- updated-dependencies: - dependency-name: image_picker dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- pubspec.lock | 4 ++-- pubspec.yaml | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index 19c3b436b..0b297cdaf 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -849,10 +849,10 @@ packages: dependency: "direct main" description: name: image_picker - sha256: fc712337719239b0b6e41316aa133350b078fa39b6cbd706b61f3fd421b03c77 + sha256: "340efe08645537d6b088a30620ee5752298b1630f23a829181172610b868262b" url: "https://pub.dev" source: hosted - version: "1.0.5" + version: "1.0.6" image_picker_android: dependency: transitive description: diff --git a/pubspec.yaml b/pubspec.yaml index 8246569cb..a27946309 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -53,7 +53,7 @@ dependencies: hive: ^2.2.3 http: 1.1.2 image_cropper: ^5.0.1 - image_picker: ^1.0.5 + image_picker: ^1.0.6 intl: ^0.18.0 json_annotation: ^4.7.0 mockito: ^5.4.4 From 15c15cc0180f0af843ba2ac751b0d14176acb541 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sun, 7 Jan 2024 19:48:01 -0800 Subject: [PATCH 15/19] Bump video_player from 2.8.1 to 2.8.2 (#2317) Bumps [video_player](https://github.com/flutter/packages/tree/main/packages/video_player) from 2.8.1 to 2.8.2. - [Release notes](https://github.com/flutter/packages/releases) - [Commits](https://github.com/flutter/packages/commits/video_player-v2.8.2/packages/video_player) --- updated-dependencies: - dependency-name: video_player dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- pubspec.lock | 4 ++-- pubspec.yaml | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index 0b297cdaf..fad9e8124 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -1749,10 +1749,10 @@ packages: dependency: "direct main" description: name: video_player - sha256: e16f0a83601a78d165dabc17e4dac50997604eb9e4cc76e10fa219046b70cef3 + sha256: fbf28ce8bcfe709ad91b5789166c832cb7a684d14f571a81891858fefb5bb1c2 url: "https://pub.dev" source: hosted - version: "2.8.1" + version: "2.8.2" video_player_android: dependency: transitive description: diff --git a/pubspec.yaml b/pubspec.yaml index a27946309..7155d6904 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -76,7 +76,7 @@ dependencies: uni_links: ^0.5.1 url_launcher: ^6.2.2 vibration: ^1.8.4 - video_player: ^2.8.1 + video_player: ^2.8.2 visibility_detector: ^0.4.0+2 dev_dependencies: From e22de04b62e282354bb5ef051b3e5da28dee24f1 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sun, 7 Jan 2024 19:48:24 -0800 Subject: [PATCH 16/19] Bump google_maps_flutter from 2.5.0 to 2.5.1 (#2316) Bumps [google_maps_flutter](https://github.com/flutter/packages/tree/main/packages/google_maps_flutter) from 2.5.0 to 2.5.1. - [Release notes](https://github.com/flutter/packages/releases) - [Commits](https://github.com/flutter/packages/commits/google_maps_flutter-v2.5.1/packages/google_maps_flutter) --- updated-dependencies: - dependency-name: google_maps_flutter dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- pubspec.lock | 4 ++-- pubspec.yaml | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index fad9e8124..e9fecacc2 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -641,10 +641,10 @@ packages: dependency: "direct main" description: name: google_maps_flutter - sha256: d4914cb38b3dcb62c39c085d968d434de0f8050f00f4d9f5ba4a7c7e004934cb + sha256: c98817e21fcdc8e02db0c77e2411374293641d41f5b4d056dd28ee1ef6982f68 url: "https://pub.dev" source: hosted - version: "2.5.0" + version: "2.5.1" google_maps_flutter_android: dependency: transitive description: diff --git a/pubspec.yaml b/pubspec.yaml index 7155d6904..5c5625cc4 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -47,7 +47,7 @@ dependencies: geocoding: ^2.1.1 geolocator: ^10.1.0 get_it: ^7.5.0 - google_maps_flutter: ^2.3.0 + google_maps_flutter: ^2.5.1 googleapis: 12.0.0 graphql_flutter: ^5.1.2 hive: ^2.2.3 From 87a5c4ecaa2a9b2da486bc990d684117e1299dad Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Mon, 8 Jan 2024 16:37:13 +0530 Subject: [PATCH 17/19] merged develop branch --- pubspec.lock | 80 ++++++++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 68 insertions(+), 12 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index e9fecacc2..36d5b5438 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -17,6 +17,14 @@ packages: url: "https://pub.dev" source: hosted version: "61.0.0" + _flutterfire_internals: + dependency: transitive + description: + name: _flutterfire_internals + sha256: f5628cd9c92ed11083f425fd1f8f1bc60ecdda458c81d73b143aeda036c35fe7 + url: "https://pub.dev" + source: hosted + version: "1.3.16" analyzer: dependency: transitive description: @@ -401,6 +409,54 @@ packages: url: "https://pub.dev" source: hosted version: "0.9.3+1" + firebase_core: + dependency: "direct main" + description: + name: firebase_core + sha256: "96607c0e829a581c2a483c658f04e8b159964c3bae2730f73297070bc85d40bb" + url: "https://pub.dev" + source: hosted + version: "2.24.2" + firebase_core_platform_interface: + dependency: "direct main" + description: + name: firebase_core_platform_interface + sha256: c437ae5d17e6b5cc7981cf6fd458a5db4d12979905f9aafd1fea930428a9fe63 + url: "https://pub.dev" + source: hosted + version: "5.0.0" + firebase_core_web: + dependency: transitive + description: + name: firebase_core_web + sha256: d585bdf3c656c3f7821ba1bd44da5f13365d22fcecaf5eb75c4295246aaa83c0 + url: "https://pub.dev" + source: hosted + version: "2.10.0" + firebase_messaging: + dependency: "direct main" + description: + name: firebase_messaging + sha256: "199fe8186a5370d1cf5ce0819191079afc305914e8f38715f5e23943940dfe2d" + url: "https://pub.dev" + source: hosted + version: "14.7.9" + firebase_messaging_platform_interface: + dependency: "direct main" + description: + name: firebase_messaging_platform_interface + sha256: "54e283a0e41d81d854636ad0dad73066adc53407a60a7c3189c9656e2f1b6107" + url: "https://pub.dev" + source: hosted + version: "4.5.18" + firebase_messaging_web: + dependency: transitive + description: + name: firebase_messaging_web + sha256: "90dc7ed885e90a24bb0e56d661d4d2b5f84429697fd2cbb9e5890a0ca370e6f4" + url: "https://pub.dev" + source: hosted + version: "3.5.18" fixnum: dependency: transitive description: @@ -641,10 +697,10 @@ packages: dependency: "direct main" description: name: google_maps_flutter - sha256: c98817e21fcdc8e02db0c77e2411374293641d41f5b4d056dd28ee1ef6982f68 + sha256: d4914cb38b3dcb62c39c085d968d434de0f8050f00f4d9f5ba4a7c7e004934cb url: "https://pub.dev" source: hosted - version: "2.5.1" + version: "2.5.0" google_maps_flutter_android: dependency: transitive description: @@ -849,10 +905,10 @@ packages: dependency: "direct main" description: name: image_picker - sha256: "340efe08645537d6b088a30620ee5752298b1630f23a829181172610b868262b" + sha256: fc712337719239b0b6e41316aa133350b078fa39b6cbd706b61f3fd421b03c77 url: "https://pub.dev" source: hosted - version: "1.0.6" + version: "1.0.5" image_picker_android: dependency: transitive description: @@ -1526,18 +1582,18 @@ packages: dependency: transitive description: name: syncfusion_flutter_core - sha256: "083d4a0ddb25435d267328a30c3938d09599f7578f5f0d28fbd9fd5424c1cd51" + sha256: "1b40729aa10a727150a6cc56e532c770f4baded83846fca8700efd908d0f4d0a" url: "https://pub.dev" source: hosted - version: "24.1.44" + version: "24.1.43" syncfusion_flutter_datepicker: dependency: "direct main" description: name: syncfusion_flutter_datepicker - sha256: "3bad2603b77d5a65e1a324b09480865531ae8026b95e63b1b253b93c26204f0a" + sha256: "3f9a8e8b585dd992d2321c899ec8d914634fb99eba02cf7a91c48a098bf62820" url: "https://pub.dev" source: hosted - version: "24.1.44" + version: "24.1.43" synchronized: dependency: transitive description: @@ -1677,10 +1733,10 @@ packages: dependency: "direct dev" description: name: url_launcher_platform_interface - sha256: "4aca1e060978e19b2998ee28503f40b5ba6226819c2b5e3e4d1821e8ccd92198" + sha256: "980e8d9af422f477be6948bdfb68df8433be71f5743a188968b0c1b887807e50" url: "https://pub.dev" source: hosted - version: "2.3.0" + version: "2.2.0" url_launcher_web: dependency: transitive description: @@ -1749,10 +1805,10 @@ packages: dependency: "direct main" description: name: video_player - sha256: fbf28ce8bcfe709ad91b5789166c832cb7a684d14f571a81891858fefb5bb1c2 + sha256: e16f0a83601a78d165dabc17e4dac50997604eb9e4cc76e10fa219046b70cef3 url: "https://pub.dev" source: hosted - version: "2.8.2" + version: "2.8.1" video_player_android: dependency: transitive description: From bcb0864e38d03a3afc5449fefcf4bda49b973ae5 Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Mon, 8 Jan 2024 16:46:55 +0530 Subject: [PATCH 18/19] fix --- pubspec.lock | 43 ++++++++++--------------------------------- 1 file changed, 10 insertions(+), 33 deletions(-) diff --git a/pubspec.lock b/pubspec.lock index 1f8e3731e..77e2873cb 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -957,30 +957,6 @@ packages: url: "https://pub.dev" source: hosted version: "6.7.1" - leak_tracker: - dependency: transitive - description: - name: leak_tracker - sha256: "41b90ceaec6d79819f31e975e61d479516efe701dea35f891b2f986c1b031422" - url: "https://pub.dev" - source: hosted - version: "9.0.17" - leak_tracker_flutter_testing: - dependency: transitive - description: - name: leak_tracker_flutter_testing - sha256: "54808cfcfa87dbc0d74c61ac063d624adf1bd5c0407301f32b06c783c60dc4ca" - url: "https://pub.dev" - source: hosted - version: "2.0.0" - leak_tracker_testing: - dependency: transitive - description: - name: leak_tracker_testing - sha256: "7e71be3c161472f6c9158ac8875dd8de575060d60b5d159ebca3600ea32c9116" - url: "https://pub.dev" - source: hosted - version: "1.0.6" lint: dependency: "direct dev" description: @@ -1001,26 +977,26 @@ packages: dependency: transitive description: name: matcher - sha256: d2323aa2060500f906aa31a895b4030b6da3ebdcc5619d14ce1aada65cd161cb + sha256: "1803e76e6653768d64ed8ff2e1e67bea3ad4b923eb5c56a295c3e634bad5960e" url: "https://pub.dev" source: hosted - version: "0.12.16+1" + version: "0.12.16" material_color_utilities: dependency: transitive description: name: material_color_utilities - sha256: "0e0a020085b65b6083975e499759762399b4475f766c21668c4ecca34ea74e5a" + sha256: "9528f2f296073ff54cb9fee677df673ace1218163c3bc7628093e7eed5203d41" url: "https://pub.dev" source: hosted - version: "0.8.0" + version: "0.5.0" meta: dependency: transitive description: name: meta - sha256: d584fa6707a52763a52446f02cc621b077888fb63b93bbcb1143a7be5a0c0c04 + sha256: a6e590c838b18133bb482a2745ad77c5bb7715fb0451209e1a7567d416678b8e url: "https://pub.dev" source: hosted - version: "1.11.0" + version: "1.10.0" mime: dependency: transitive description: @@ -1105,10 +1081,10 @@ packages: dependency: transitive description: name: path - sha256: "087ce49c3f0dc39180befefc60fdb4acd8f8620e5682fe2476afd0b3688bb4af" + sha256: "8829d8a55c13fc0e37127c29fedf290c102f4e40ae94ada574091fe0ff96c917" url: "https://pub.dev" source: hosted - version: "1.9.0" + version: "1.8.3" path_parsing: dependency: transitive description: @@ -1680,6 +1656,7 @@ packages: sha256: "4aca1e060978e19b2998ee28503f40b5ba6226819c2b5e3e4d1821e8ccd92198" url: "https://pub.dev" source: hosted + version: "2.3.0" url_launcher_web: dependency: transitive description: @@ -1866,4 +1843,4 @@ packages: version: "3.1.2" sdks: dart: ">=3.2.0 <3.13.0" - flutter: ">=3.16.0" + flutter: ">=3.16.0" \ No newline at end of file From a2f6f954ce6d0518a151b43753db75bc1d990cdc Mon Sep 17 00:00:00 2001 From: Ankit Varshney Date: Mon, 8 Jan 2024 23:08:57 +0530 Subject: [PATCH 19/19] fix failing test --- lib/widgets/post_modal.dart | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/widgets/post_modal.dart b/lib/widgets/post_modal.dart index c15977dd7..6a47c9e00 100644 --- a/lib/widgets/post_modal.dart +++ b/lib/widgets/post_modal.dart @@ -102,7 +102,7 @@ class PostBottomModal extends StatelessWidget { child: const Text("Yes"), ), TextButton( - key: const Key('alert-dialog_no_btn'), + key: const Key('alert_dialog_no_btn'), onPressed: () { Navigator.pop(context); },