diff --git a/ios/Runner.xcodeproj/project.pbxproj b/ios/Runner.xcodeproj/project.pbxproj index a982556..3a65395 100644 --- a/ios/Runner.xcodeproj/project.pbxproj +++ b/ios/Runner.xcodeproj/project.pbxproj @@ -10,12 +10,12 @@ 1498D2341E8E89220040F4C2 /* GeneratedPluginRegistrant.m in Sources */ = {isa = PBXBuildFile; fileRef = 1498D2331E8E89220040F4C2 /* GeneratedPluginRegistrant.m */; }; 331C808B294A63AB00263BE5 /* RunnerTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 331C807B294A618700263BE5 /* RunnerTests.swift */; }; 3B3967161E833CAA004F5970 /* AppFrameworkInfo.plist in Resources */ = {isa = PBXBuildFile; fileRef = 3B3967151E833CAA004F5970 /* AppFrameworkInfo.plist */; }; + 40721B3F0DC8DB0598443DBF /* Pods_Runner.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 1E824BDA50EF77318022F59D /* Pods_Runner.framework */; }; 478CFA942E638C8E0064F3D7 /* GoogleService-Info.plist in Resources */ = {isa = PBXBuildFile; fileRef = 478CFA932E638C8E0064F3D7 /* GoogleService-Info.plist */; }; 74858FAF1ED2DC5600515810 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 74858FAE1ED2DC5600515810 /* AppDelegate.swift */; }; 97C146FC1CF9000F007C117D /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FA1CF9000F007C117D /* Main.storyboard */; }; 97C146FE1CF9000F007C117D /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FD1CF9000F007C117D /* Assets.xcassets */; }; 97C147011CF9000F007C117D /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FF1CF9000F007C117D /* LaunchScreen.storyboard */; }; - B976FB9C47411C32B24D5E01 /* Pods_Runner.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = ACE60DF9393168FD748550B3 /* Pods_Runner.framework */; }; /* End PBXBuildFile section */ /* Begin PBXContainerItemProxy section */ @@ -44,16 +44,16 @@ /* Begin PBXFileReference section */ 1498D2321E8E86230040F4C2 /* GeneratedPluginRegistrant.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GeneratedPluginRegistrant.h; sourceTree = ""; }; 1498D2331E8E89220040F4C2 /* GeneratedPluginRegistrant.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GeneratedPluginRegistrant.m; sourceTree = ""; }; + 1E824BDA50EF77318022F59D /* Pods_Runner.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_Runner.framework; sourceTree = BUILT_PRODUCTS_DIR; }; 331C807B294A618700263BE5 /* RunnerTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RunnerTests.swift; sourceTree = ""; }; 331C8081294A63A400263BE5 /* RunnerTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = RunnerTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; 3B3967151E833CAA004F5970 /* AppFrameworkInfo.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; name = AppFrameworkInfo.plist; path = Flutter/AppFrameworkInfo.plist; sourceTree = ""; }; 478CFA932E638C8E0064F3D7 /* GoogleService-Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = "GoogleService-Info.plist"; sourceTree = ""; }; 478CFA952E6E20A60064F3D7 /* Runner.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = Runner.entitlements; sourceTree = ""; }; + 62D069322AC3B532E0B4F137 /* Pods-Runner.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.debug.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig"; sourceTree = ""; }; 74858FAD1ED2DC5600515810 /* Runner-Bridging-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Runner-Bridging-Header.h"; sourceTree = ""; }; 74858FAE1ED2DC5600515810 /* AppDelegate.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; - 7595037DD52211B91157B0F3 /* Pods-Runner.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.release.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig"; sourceTree = ""; }; 7AFA3C8E1D35360C0083082E /* Release.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; name = Release.xcconfig; path = Flutter/Release.xcconfig; sourceTree = ""; }; - 8E12CEEB8E334EE22D5259D7 /* Pods-Runner.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.debug.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig"; sourceTree = ""; }; 9740EEB21CF90195004384FC /* Debug.xcconfig */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.xcconfig; name = Debug.xcconfig; path = Flutter/Debug.xcconfig; sourceTree = ""; }; 9740EEB31CF90195004384FC /* Generated.xcconfig */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.xcconfig; name = Generated.xcconfig; path = Flutter/Generated.xcconfig; sourceTree = ""; }; 97C146EE1CF9000F007C117D /* Runner.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Runner.app; sourceTree = BUILT_PRODUCTS_DIR; }; @@ -61,8 +61,8 @@ 97C146FD1CF9000F007C117D /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 97C147001CF9000F007C117D /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; 97C147021CF9000F007C117D /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; - ACE60DF9393168FD748550B3 /* Pods_Runner.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_Runner.framework; sourceTree = BUILT_PRODUCTS_DIR; }; - D6BB17A036DF7FCE75271203 /* Pods-Runner.profile.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.profile.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.profile.xcconfig"; sourceTree = ""; }; + B35471C63C8DD1B1DECDB3A5 /* Pods-Runner.profile.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.profile.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.profile.xcconfig"; sourceTree = ""; }; + D0FB40CE52522242F351743B /* Pods-Runner.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.release.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig"; sourceTree = ""; }; /* End PBXFileReference section */ /* Begin PBXFrameworksBuildPhase section */ @@ -70,7 +70,7 @@ isa = PBXFrameworksBuildPhase; buildActionMask = 2147483647; files = ( - B976FB9C47411C32B24D5E01 /* Pods_Runner.framework in Frameworks */, + 40721B3F0DC8DB0598443DBF /* Pods_Runner.framework in Frameworks */, ); runOnlyForDeploymentPostprocessing = 0; }; @@ -88,9 +88,9 @@ 79DD2093A1D9674C94359FC8 /* Pods */ = { isa = PBXGroup; children = ( - 8E12CEEB8E334EE22D5259D7 /* Pods-Runner.debug.xcconfig */, - 7595037DD52211B91157B0F3 /* Pods-Runner.release.xcconfig */, - D6BB17A036DF7FCE75271203 /* Pods-Runner.profile.xcconfig */, + 62D069322AC3B532E0B4F137 /* Pods-Runner.debug.xcconfig */, + D0FB40CE52522242F351743B /* Pods-Runner.release.xcconfig */, + B35471C63C8DD1B1DECDB3A5 /* Pods-Runner.profile.xcconfig */, ); path = Pods; sourceTree = ""; @@ -114,7 +114,7 @@ 97C146EF1CF9000F007C117D /* Products */, 331C8082294A63A400263BE5 /* RunnerTests */, 79DD2093A1D9674C94359FC8 /* Pods */, - A07D637C76A0ABB38659D189 /* Frameworks */, + C1312CE4ABEB9ED47FF21174 /* Frameworks */, ); sourceTree = ""; }; @@ -144,10 +144,10 @@ path = Runner; sourceTree = ""; }; - A07D637C76A0ABB38659D189 /* Frameworks */ = { + C1312CE4ABEB9ED47FF21174 /* Frameworks */ = { isa = PBXGroup; children = ( - ACE60DF9393168FD748550B3 /* Pods_Runner.framework */, + 1E824BDA50EF77318022F59D /* Pods_Runner.framework */, ); name = Frameworks; sourceTree = ""; @@ -176,15 +176,15 @@ isa = PBXNativeTarget; buildConfigurationList = 97C147051CF9000F007C117D /* Build configuration list for PBXNativeTarget "Runner" */; buildPhases = ( - BFED6CCFE59BB148875A533B /* [CP] Check Pods Manifest.lock */, + E3E41B3FF6C30233949963A9 /* [CP] Check Pods Manifest.lock */, 9740EEB61CF901F6004384FC /* Run Script */, 97C146EA1CF9000F007C117D /* Sources */, 97C146EB1CF9000F007C117D /* Frameworks */, 97C146EC1CF9000F007C117D /* Resources */, 9705A1C41CF9048500538489 /* Embed Frameworks */, 3B06AD1E1E4923F5004D2608 /* Thin Binary */, - 8372B02399CDF54531650AD4 /* [CP] Embed Pods Frameworks */, - 81DE7C26F41956799E954FCE /* [CP] Copy Pods Resources */, + 968C3FBB62CE1E0E307ECBCE /* [CP] Embed Pods Frameworks */, + CC3E3923FDE40035D0CA6762 /* [CP] Copy Pods Resources */, ); buildRules = ( ); @@ -273,24 +273,7 @@ shellPath = /bin/sh; shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" embed_and_thin"; }; - 81DE7C26F41956799E954FCE /* [CP] Copy Pods Resources */ = { - isa = PBXShellScriptBuildPhase; - buildActionMask = 2147483647; - files = ( - ); - inputFileListPaths = ( - "${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-input-files.xcfilelist", - ); - name = "[CP] Copy Pods Resources"; - outputFileListPaths = ( - "${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-output-files.xcfilelist", - ); - runOnlyForDeploymentPostprocessing = 0; - shellPath = /bin/sh; - shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources.sh\"\n"; - showEnvVarsInLog = 0; - }; - 8372B02399CDF54531650AD4 /* [CP] Embed Pods Frameworks */ = { + 968C3FBB62CE1E0E307ECBCE /* [CP] Embed Pods Frameworks */ = { isa = PBXShellScriptBuildPhase; buildActionMask = 2147483647; files = ( @@ -322,7 +305,24 @@ shellPath = /bin/sh; shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" build"; }; - BFED6CCFE59BB148875A533B /* [CP] Check Pods Manifest.lock */ = { + CC3E3923FDE40035D0CA6762 /* [CP] Copy Pods Resources */ = { + isa = PBXShellScriptBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + inputFileListPaths = ( + "${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-input-files.xcfilelist", + ); + name = "[CP] Copy Pods Resources"; + outputFileListPaths = ( + "${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-output-files.xcfilelist", + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources.sh\"\n"; + showEnvVarsInLog = 0; + }; + E3E41B3FF6C30233949963A9 /* [CP] Check Pods Manifest.lock */ = { isa = PBXShellScriptBuildPhase; buildActionMask = 2147483647; files = ( diff --git a/lib/core/api/api_client.dart b/lib/core/api/api_client.dart index a4e76fc..dc8b576 100644 --- a/lib/core/api/api_client.dart +++ b/lib/core/api/api_client.dart @@ -9,7 +9,6 @@ import 'package:hmg_patient_app_new/core/dependencies.dart'; import 'package:hmg_patient_app_new/core/utils/utils.dart'; import 'package:hmg_patient_app_new/routes/app_routes.dart'; import 'package:hmg_patient_app_new/services/analytics/analytics_service.dart'; -import 'package:hmg_patient_app_new/services/logger_service.dart'; import 'package:hmg_patient_app_new/services/navigation_service.dart'; import 'package:http/http.dart' as http; @@ -80,14 +79,11 @@ abstract class ApiClient { class ApiClientImp implements ApiClient { final _analytics = getIt(); - final LoggerService _loggerService; final AppState _appState; ApiClientImp({ - required LoggerService loggerService, required AppState appState, - }) : _appState = appState, - _loggerService = loggerService; + }) : _appState = appState; @override post( @@ -200,7 +196,6 @@ class ApiClientImp implements ApiClient { final int statusCode = response.statusCode; log("response.body: ${response.body}"); if (statusCode < 200 || statusCode >= 400) { - var parsed = json.decode(utf8.decode(response.bodyBytes)); onFailure('Error While Fetching data', statusCode, failureType: StatusCodeFailure("Error While Fetching data")); logApiEndpointError(endPoint, 'Error While Fetching data', statusCode); } else { @@ -218,6 +213,7 @@ class ApiClientImp implements ApiClient { } else { if (parsed['ErrorType'] == 4) { //TODO : handle app update + onFailure(parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage'], statusCode, failureType: AppUpdateFailure("parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage']")); logApiEndpointError(endPoint, parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage'], statusCode); } if (parsed['ErrorType'] == 2) { @@ -225,9 +221,9 @@ class ApiClientImp implements ApiClient { onFailure( parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage'], statusCode, - failureType: MessageStatusFailure(parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage']), + failureType: UnAuthenticatedUserFailure(parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage'] ?? "User is not Authenticated", url: url), ); - // logApiEndpointError(endPoint, "session logged out", statusCode); + // logApiEndpointError(endPoint, "session logged out", statusCode); } if (isAllowAny) { onSuccess(parsed, statusCode, messageStatus: parsed['MessageStatus'], errorMessage: parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage']); @@ -248,6 +244,12 @@ class ApiClientImp implements ApiClient { } } else if (parsed['MessageStatus'] == 1 || parsed['SMSLoginRequired'] == true) { onSuccess(parsed, statusCode, messageStatus: parsed['MessageStatus'], errorMessage: parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage']); + } else if (parsed['IsAuthenticated'] == false) { + onFailure( + "User is not Authenticated", + statusCode, + failureType: UnAuthenticatedUserFailure(parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage'] ?? "User is not Authenticated", url: url), + ); } else if (parsed['MessageStatus'] == 2 && parsed['IsAuthenticated']) { if (parsed['SameClinicApptList'] != null) { onSuccess(parsed, statusCode, messageStatus: parsed['MessageStatus'], errorMessage: parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage']); @@ -277,7 +279,6 @@ class ApiClientImp implements ApiClient { logApiEndpointError(endPoint, parsed['message'] ?? parsed['message'], statusCode); } } - } else if (!parsed['IsAuthenticated']) { } else { if (parsed['SameClinicApptList'] != null) { onSuccess(parsed, statusCode, messageStatus: parsed['MessageStatus'], errorMessage: parsed['ErrorEndUserMessage'] ?? parsed['ErrorMessage']); diff --git a/lib/core/dependencies.dart b/lib/core/dependencies.dart index b42706f..1fe2317 100644 --- a/lib/core/dependencies.dart +++ b/lib/core/dependencies.dart @@ -77,7 +77,7 @@ class AppDependencies { final sharedPreferences = await SharedPreferences.getInstance(); getIt.registerLazySingleton(() => CacheServiceImp(sharedPreferences: sharedPreferences, loggerService: getIt())); - getIt.registerLazySingleton(() => ApiClientImp(loggerService: getIt(), appState: getIt())); + getIt.registerLazySingleton(() => ApiClientImp(appState: getIt())); // Repositories getIt.registerLazySingleton(() => CommonRepoImp(loggerService: getIt())); @@ -126,11 +126,7 @@ class AppDependencies { ); getIt.registerLazySingleton( - () => MyAppointmentsViewModel( - myAppointmentsRepo: getIt(), - errorHandlerService: getIt(), - appState: getIt() - ), + () => MyAppointmentsViewModel(myAppointmentsRepo: getIt(), errorHandlerService: getIt(), appState: getIt()), ); getIt.registerLazySingleton( @@ -155,13 +151,7 @@ class AppDependencies { ); getIt.registerLazySingleton( - () => BookAppointmentsViewModel( - bookAppointmentsRepo: getIt(), - errorHandlerService: getIt(), - navigationService: getIt(), - myAppointmentsViewModel: getIt(), - locationUtils: getIt() - ), + () => BookAppointmentsViewModel(bookAppointmentsRepo: getIt(), errorHandlerService: getIt(), navigationService: getIt(), myAppointmentsViewModel: getIt(), locationUtils: getIt()), ); getIt.registerLazySingleton( diff --git a/lib/core/exceptions/api_failure.dart b/lib/core/exceptions/api_failure.dart index c950195..0c5bc66 100644 --- a/lib/core/exceptions/api_failure.dart +++ b/lib/core/exceptions/api_failure.dart @@ -7,7 +7,9 @@ abstract class Failure extends Equatable implements Exception { } class ServerFailure extends Failure { - const ServerFailure(super.message); + final String url; + + const ServerFailure(super.message, {this.url = ""}); @override List get props => [message]; @@ -27,6 +29,13 @@ class MessageStatusFailure extends Failure { List get props => [message]; } +class AppUpdateFailure extends Failure { + const AppUpdateFailure(super.message); + + @override + List get props => [message]; +} + class StatusCodeFailure extends Failure { const StatusCodeFailure(super.message); @@ -34,6 +43,15 @@ class StatusCodeFailure extends Failure { List get props => [message]; } +class UnAuthenticatedUserFailure extends Failure { + final String url; + + const UnAuthenticatedUserFailure(super.message, {this.url = ""}); + + @override + List get props => [message]; +} + class ConnectivityFailure extends Failure { const ConnectivityFailure(super.message); @@ -56,7 +74,9 @@ class DataParsingFailure extends Failure { } class UnknownFailure extends Failure { - const UnknownFailure(super.message); + final String url; + + const UnknownFailure(super.message, {this.url = ""}); @override List get props => [message]; diff --git a/lib/features/authentication/authentication_view_model.dart b/lib/features/authentication/authentication_view_model.dart index c8adf78..b43858c 100644 --- a/lib/features/authentication/authentication_view_model.dart +++ b/lib/features/authentication/authentication_view_model.dart @@ -1,16 +1,16 @@ import 'dart:convert'; import 'dart:developer'; import 'dart:io'; + import 'package:easy_localization/easy_localization.dart'; -import 'package:flutter/services.dart' show rootBundle; import 'package:flutter/material.dart'; +import 'package:flutter/services.dart' show rootBundle; import 'package:get_it/get_it.dart'; import 'package:hijri_gregorian_calendar/hijri_gregorian_calendar.dart'; import 'package:hmg_patient_app_new/core/app_state.dart'; import 'package:hmg_patient_app_new/core/cache_consts.dart'; import 'package:hmg_patient_app_new/core/common_models/nationality_country_model.dart'; import 'package:hmg_patient_app_new/core/common_models/privilege/HMCProjectListModel.dart'; -import 'package:hmg_patient_app_new/core/common_models/privilege/PrivilegeModel.dart'; import 'package:hmg_patient_app_new/core/common_models/privilege/ProjectDetailListModel.dart'; import 'package:hmg_patient_app_new/core/common_models/privilege/VidaPlusProjectListModel.dart'; import 'package:hmg_patient_app_new/core/enums.dart'; @@ -18,7 +18,6 @@ import 'package:hmg_patient_app_new/core/utils/loading_utils.dart'; import 'package:hmg_patient_app_new/core/utils/request_utils.dart'; import 'package:hmg_patient_app_new/core/utils/utils.dart'; import 'package:hmg_patient_app_new/core/utils/validation_utils.dart'; -import 'package:hmg_patient_app_new/extensions/context_extensions.dart'; import 'package:hmg_patient_app_new/extensions/string_extensions.dart'; import 'package:hmg_patient_app_new/features/authentication/authentication_repo.dart'; import 'package:hmg_patient_app_new/features/authentication/models/request_models/check_activation_code_register_request_model.dart'; @@ -37,7 +36,6 @@ import 'package:hmg_patient_app_new/services/error_handler_service.dart'; import 'package:hmg_patient_app_new/services/localauth_service.dart'; import 'package:hmg_patient_app_new/services/navigation_service.dart'; import 'package:hmg_patient_app_new/widgets/loader/bottomsheet_loader.dart'; -import 'package:hmg_patient_app_new/widgets/bottomsheet/exception_bottom_sheet.dart'; import 'package:sms_otp_auto_verify/sms_otp_auto_verify.dart'; import 'models/request_models/get_user_mobile_device_data.dart'; diff --git a/lib/presentation/lab/lab_results/lab_result_details.dart b/lib/presentation/lab/lab_results/lab_result_details.dart index e3ffaea..3e9558c 100644 --- a/lib/presentation/lab/lab_results/lab_result_details.dart +++ b/lib/presentation/lab/lab_results/lab_result_details.dart @@ -1,29 +1,23 @@ -import 'dart:math'; -import 'package:dartz/dartz.dart'; import 'package:easy_localization/easy_localization.dart'; import 'package:flutter/material.dart'; import 'package:hmg_patient_app_new/core/app_assets.dart'; -import 'package:hmg_patient_app_new/core/common_models/data_points.dart'; import 'package:hmg_patient_app_new/core/utils/size_utils.dart'; import 'package:hmg_patient_app_new/core/utils/utils.dart'; import 'package:hmg_patient_app_new/extensions/string_extensions.dart'; import 'package:hmg_patient_app_new/extensions/widget_extensions.dart'; -import 'package:hmg_patient_app_new/features/lab/history/lab_history_viewmodel.dart'; import 'package:hmg_patient_app_new/features/lab/lab_range_view_model.dart' show LabRangeViewModel; import 'package:hmg_patient_app_new/features/lab/lab_view_model.dart'; import 'package:hmg_patient_app_new/features/lab/models/resp_models/lab_result.dart'; -import 'package:hmg_patient_app_new/presentation/lab/collapsing_list_view.dart'; import 'package:hmg_patient_app_new/presentation/lab/lab_results/lab_result_calender.dart'; import 'package:hmg_patient_app_new/presentation/lab/lab_results/lab_result_list_item.dart'; import 'package:hmg_patient_app_new/theme/colors.dart' show AppColors; +import 'package:hmg_patient_app_new/widgets/appbar/collapsing_list_view.dart'; import 'package:hmg_patient_app_new/widgets/graph/custom_graph.dart'; import 'package:provider/provider.dart' show Consumer, Provider; import '../../../widgets/common_bottom_sheet.dart' show showCommonBottomSheetWithoutHeight; -import '../../book_appointment/widgets/appointment_calendar.dart' - show AppointmentCalendar; class LabResultDetails extends StatelessWidget { final LabResult recentLabResult; diff --git a/lib/presentation/medical_file/medical_file_page.dart b/lib/presentation/medical_file/medical_file_page.dart index 28045fb..04bb658 100644 --- a/lib/presentation/medical_file/medical_file_page.dart +++ b/lib/presentation/medical_file/medical_file_page.dart @@ -36,7 +36,7 @@ import 'package:hmg_patient_app_new/presentation/medical_file/vaccine_list_page. import 'package:hmg_patient_app_new/presentation/medical_file/widgets/lab_rad_card.dart'; import 'package:hmg_patient_app_new/presentation/medical_file/widgets/medical_file_card.dart'; import 'package:hmg_patient_app_new/presentation/medical_file/widgets/patient_sick_leave_card.dart'; -import 'package:hmg_patient_app_new/presentation/my_family/my_Family.dart'; +import 'package:hmg_patient_app_new/presentation/my_family/my_family.dart'; import 'package:hmg_patient_app_new/presentation/my_family/widget/my_family_sheet.dart'; import 'package:hmg_patient_app_new/presentation/prescriptions/prescriptions_list_page.dart'; import 'package:hmg_patient_app_new/services/navigation_service.dart'; diff --git a/lib/presentation/my_family/my_Family.dart b/lib/presentation/my_family/my_family.dart similarity index 96% rename from lib/presentation/my_family/my_Family.dart rename to lib/presentation/my_family/my_family.dart index 6e4ef91..25f5f3c 100644 --- a/lib/presentation/my_family/my_Family.dart +++ b/lib/presentation/my_family/my_family.dart @@ -1,11 +1,9 @@ import 'package:easy_localization/easy_localization.dart'; import 'package:flutter/material.dart'; -import 'package:flutter_svg/flutter_svg.dart'; import 'package:hmg_patient_app_new/core/app_assets.dart'; import 'package:hmg_patient_app_new/core/app_export.dart'; import 'package:hmg_patient_app_new/core/dependencies.dart'; import 'package:hmg_patient_app_new/core/enums.dart'; -import 'package:hmg_patient_app_new/core/utils/utils.dart'; import 'package:hmg_patient_app_new/core/utils/validation_utils.dart'; import 'package:hmg_patient_app_new/extensions/string_extensions.dart'; import 'package:hmg_patient_app_new/extensions/widget_extensions.dart'; @@ -13,7 +11,6 @@ import 'package:hmg_patient_app_new/features/authentication/authentication_view_ import 'package:hmg_patient_app_new/features/medical_file/models/family_file_response_model.dart'; import 'package:hmg_patient_app_new/generated/locale_keys.g.dart'; import 'package:hmg_patient_app_new/presentation/my_family/widget/family_cards.dart'; -import 'package:hmg_patient_app_new/services/dialog_service.dart'; import 'package:hmg_patient_app_new/theme/colors.dart'; import 'package:hmg_patient_app_new/widgets/appbar/app_bar_widget.dart'; import 'package:hmg_patient_app_new/widgets/buttons/custom_button.dart'; @@ -27,10 +24,10 @@ class FamilyMedicalScreen extends StatefulWidget { final Function(FamilyFileResponseModelLists) onSelect; const FamilyMedicalScreen({ - Key? key, + super.key, required this.profiles, required this.onSelect, - }) : super(key: key); + }); @override State createState() => _FamilyMedicalScreenState(); @@ -85,9 +82,9 @@ class _FamilyMedicalScreenState extends State { ); } - void showModelSheet() { + Future showModelSheet() async { AuthenticationViewModel authVm = getIt.get(); - return showCommonBottomSheetWithoutHeight(context, + return await showCommonBottomSheetWithoutHeight(context, title: "Add Family Member", child: Column( crossAxisAlignment: CrossAxisAlignment.start, diff --git a/lib/presentation/my_family/widget/family_cards.dart b/lib/presentation/my_family/widget/family_cards.dart index 480f91f..306692b 100644 --- a/lib/presentation/my_family/widget/family_cards.dart +++ b/lib/presentation/my_family/widget/family_cards.dart @@ -43,9 +43,7 @@ class _FamilyCardsState extends State { ), itemBuilder: (context, index) { final profile = widget.profiles[index]; - final isActive = (profile.responseId == appState - .getAuthenticatedUser() - ?.patientId); + final isActive = (profile.responseId == appState.getAuthenticatedUser()?.patientId); return Container( padding: EdgeInsets.symmetric(vertical: 15.h, horizontal: 15.h), decoration: RoundedRectangleBorder().toSmoothCornerDecoration(color: AppColors.whiteColor, borderRadius: 24), @@ -73,13 +71,13 @@ class _FamilyCardsState extends State { widget.isShowDetails ? SizedBox(height: 4.h) : SizedBox(), widget.isShowDetails ? CustomChipWidget( - chipType: ChipTypeEnum.alert, - backgroundColor: AppColors.lightGrayBGColor, - chipText: "Age: ${profile.age ?? "N/A"} Years", - isShowBorder: false, - borderRadius: 8.h, - textColor: AppColors.textColor, - ) + chipType: ChipTypeEnum.alert, + backgroundColor: AppColors.lightGrayBGColor, + chipText: "Age: ${profile.age ?? "N/A"} Years", + isShowBorder: false, + borderRadius: 8.h, + textColor: AppColors.textColor, + ) : SizedBox(), widget.isShowDetails ? SizedBox(height: 8.h) : SizedBox(), Spacer(), @@ -102,7 +100,7 @@ class _FamilyCardsState extends State { borderColor: AppColors.secondaryLightRedColor, textColor: AppColors.primaryRedColor, fontSize: 13.h, - icon: widget.isBottomSheet ? null : AppAssets.heart, + icon: widget.isBottomSheet ? null : AppAssets.heart, iconColor: AppColors.primaryRedColor, padding: EdgeInsets.symmetric(vertical: 0, horizontal: 0), ).paddingOnly(top: 0, bottom: 0), diff --git a/lib/presentation/my_family/widget/my_family_sheet.dart b/lib/presentation/my_family/widget/my_family_sheet.dart index a119906..da822b1 100644 --- a/lib/presentation/my_family/widget/my_family_sheet.dart +++ b/lib/presentation/my_family/widget/my_family_sheet.dart @@ -1,15 +1,13 @@ import 'package:flutter/material.dart'; -import 'package:hmg_patient_app_new/core/utils/utils.dart'; import 'package:hmg_patient_app_new/extensions/string_extensions.dart'; import 'package:hmg_patient_app_new/features/medical_file/models/family_file_response_model.dart'; -import 'package:hmg_patient_app_new/presentation/my_family/my_Family.dart'; import 'package:hmg_patient_app_new/presentation/my_family/widget/family_cards.dart'; import 'package:hmg_patient_app_new/theme/colors.dart'; import 'package:hmg_patient_app_new/widgets/common_bottom_sheet.dart'; class MyFamilySheet { - static void show(BuildContext context, List familyLists, Function(FamilyFileResponseModelLists) onSelect) { - return showCommonBottomSheetWithoutHeight( + static Future show(BuildContext context, List familyLists, Function(FamilyFileResponseModelLists) onSelect) async { + return await showCommonBottomSheetWithoutHeight( context, titleWidget: Column( crossAxisAlignment: CrossAxisAlignment.start, diff --git a/lib/services/dialog_service.dart b/lib/services/dialog_service.dart index 29aee3d..6ee0ddc 100644 --- a/lib/services/dialog_service.dart +++ b/lib/services/dialog_service.dart @@ -4,18 +4,15 @@ import 'package:hmg_patient_app_new/core/app_assets.dart'; import 'package:hmg_patient_app_new/core/utils/size_utils.dart'; import 'package:hmg_patient_app_new/extensions/route_extensions.dart'; import 'package:hmg_patient_app_new/extensions/string_extensions.dart'; -import 'package:hmg_patient_app_new/extensions/widget_extensions.dart'; -import 'package:hmg_patient_app_new/features/authentication/authentication_view_model.dart'; import 'package:hmg_patient_app_new/generated/locale_keys.g.dart'; import 'package:hmg_patient_app_new/services/navigation_service.dart'; import 'package:hmg_patient_app_new/theme/colors.dart'; import 'package:hmg_patient_app_new/widgets/bottomsheet/exception_bottom_sheet.dart'; import 'package:hmg_patient_app_new/widgets/buttons/custom_button.dart'; import 'package:hmg_patient_app_new/widgets/common_bottom_sheet.dart'; -import 'package:provider/provider.dart'; abstract class DialogService { - Future showErrorBottomSheet({required String message, Function()? onOkPressed}); + Future showErrorBottomSheet({String title = "", required String message, Function()? onOkPressed, Function()? onCancelPressed}); Future showExceptionBottomSheet({required String message, required Function() onOkPressed, Function()? onCancelPressed}); @@ -28,21 +25,40 @@ abstract class DialogService { class DialogServiceImp implements DialogService { final NavigationService navigationService; + bool _isErrorSheetShowing = false; + DialogServiceImp({required this.navigationService}); @override - Future showErrorBottomSheet({required String message, Function()? onOkPressed}) async { + Future showErrorBottomSheet({String title = "", required String message, Function()? onOkPressed, Function()? onCancelPressed}) async { + if (_isErrorSheetShowing) return; final context = navigationService.navigatorKey.currentContext; if (context == null) return; + _isErrorSheetShowing = true; await showModalBottomSheet( context: context, isScrollControlled: false, shape: const RoundedRectangleBorder( borderRadius: BorderRadius.vertical(top: Radius.circular(16)), ), - builder: (_) => _ErrorBottomSheet(message: message, onOkPressed: onOkPressed ?? () {}), + builder: (_) => ExceptionBottomSheet( + // title: title, + message: message, + showCancel: onCancelPressed != null ? true : false, + onOkPressed: () { + if (onOkPressed != null) { + onOkPressed(); + } + }, + onCancelPressed: () { + if (onCancelPressed != null) { + context.pop(); + } + }, + ), ); + _isErrorSheetShowing = false; } @override @@ -73,9 +89,8 @@ class DialogServiceImp implements DialogService { Future showCommonBottomSheetWithoutH({String? label, required String message, required Function() onOkPressed, Function()? onCancelPressed}) async { final context = navigationService.navigatorKey.currentContext; if (context == null) return; - showCommonBottomSheetWithoutHeight(context, title: label ?? "", child: exceptionBottomSheetWidget(context: context, message: message, onOkPressed: onOkPressed, onCancelPressed: onCancelPressed), - callBackFunc: () { - }); + showCommonBottomSheetWithoutHeight(context, + title: label ?? "", child: exceptionBottomSheetWidget(context: context, message: message, onOkPressed: onOkPressed, onCancelPressed: onCancelPressed), callBackFunc: () {}); } @override @@ -90,10 +105,10 @@ class DialogServiceImp implements DialogService { Widget exceptionBottomSheetWidget({required BuildContext context, required String message, required Function() onOkPressed, Function()? onCancelPressed}) { return Column( children: [ - (message ?? "").toText16(isBold: false, color: AppColors.textColor), + (message).toText16(isBold: false, color: AppColors.textColor), SizedBox(height: 10.h), SizedBox(height: 24.h), - if (onOkPressed != null && onCancelPressed != null) + if (onCancelPressed != null) Row( children: [ Expanded( @@ -112,7 +127,7 @@ Widget exceptionBottomSheetWidget({required BuildContext context, required Strin SizedBox(width: 5.h), Expanded( child: CustomButton( - text: onCancelPressed != null ? LocaleKeys.confirm.tr() : LocaleKeys.ok.tr(), + text: LocaleKeys.confirm.tr(), onPressed: onOkPressed, backgroundColor: AppColors.bgGreenColor, borderColor: AppColors.bgGreenColor, @@ -122,14 +137,14 @@ Widget exceptionBottomSheetWidget({required BuildContext context, required Strin ), ], ), - if (onOkPressed != null && onCancelPressed == null) + if (onCancelPressed == null) Padding( padding: EdgeInsets.only(bottom: 10.h), child: CustomButton( text: LocaleKeys.ok.tr(), - onPressed: (onOkPressed != null && onCancelPressed == null) + onPressed: (onCancelPressed == null) ? () { - Navigator.of(context).pop(); + context.pop(); } : onOkPressed, backgroundColor: AppColors.primaryRedColor, @@ -144,7 +159,6 @@ Widget exceptionBottomSheetWidget({required BuildContext context, required Strin Widget showPhoneNumberPickerWidget({required BuildContext context, String? message, required Function() onSMSPress, required Function() onWhatsappPress}) { return StatefulBuilder(builder: (BuildContext context, StateSetter setModalState) { - AuthenticationViewModel authViewModel = context.read(); return Column( children: [ (message ?? "").toText16(isBold: false, color: AppColors.textColor), @@ -202,56 +216,3 @@ Widget showPhoneNumberPickerWidget({required BuildContext context, String? messa // ); }); } - -class _ErrorBottomSheet extends StatelessWidget { - final String message; - final Function()? onOkPressed; - - const _ErrorBottomSheet({required this.message, this.onOkPressed}); - - @override - Widget build(BuildContext context) { - return Padding( - padding: const EdgeInsets.all(16), - child: Column( - mainAxisSize: MainAxisSize.min, - children: [ - const Icon(Icons.error_outline, color: Colors.red, size: 40), - const SizedBox(height: 12), - Text( - "Error", - style: Theme.of(context).textTheme.titleLarge?.copyWith( - color: Colors.red, - fontWeight: FontWeight.bold, - ), - ), - const SizedBox(height: 8), - Text( - message, - textAlign: TextAlign.center, - style: Theme.of(context).textTheme.bodyMedium, - ), - const SizedBox(height: 16), - ElevatedButton( - onPressed: () { - if (onOkPressed != null) { - onOkPressed!(); - } else { - context.pop(); - } - }, - style: ElevatedButton.styleFrom( - backgroundColor: Colors.red, - shape: RoundedRectangleBorder( - borderRadius: BorderRadius.circular(8), - ), - ), - child: const Text("OK", style: TextStyle(color: Colors.white)).onPress(() { - Navigator.of(context).pop(); - }), - ), - ], - ), - ); - } -} diff --git a/lib/services/error_handler_service.dart b/lib/services/error_handler_service.dart index c29dc17..aeefefb 100644 --- a/lib/services/error_handler_service.dart +++ b/lib/services/error_handler_service.dart @@ -3,7 +3,6 @@ import 'dart:io'; import 'package:hmg_patient_app_new/core/exceptions/api_exception.dart'; import 'package:hmg_patient_app_new/core/exceptions/api_failure.dart'; import 'package:hmg_patient_app_new/core/utils/loading_utils.dart'; -import 'package:hmg_patient_app_new/extensions/route_extensions.dart'; import 'package:hmg_patient_app_new/services/dialog_service.dart'; import 'package:hmg_patient_app_new/services/logger_service.dart'; import 'package:hmg_patient_app_new/services/navigation_service.dart'; @@ -28,46 +27,54 @@ class ErrorHandlerServiceImp implements ErrorHandlerService { if (failure is APIException) { loggerService.errorLogs("API Exception: ${failure.message}"); } else if (failure is ServerFailure) { - loggerService.errorLogs("Server Failure: ${failure.message}"); - await _showDialog(failure); + loggerService.errorLogs("URL: ${failure.url} \n Server Failure: ${failure.message}"); + await _showDialog(failure, title: "Server Failure"); } else if (failure is DataParsingFailure) { loggerService.errorLogs("Data Parsing Failure: ${failure.message}"); await _showDialog(failure, title: "Data Error"); } else if (failure is StatusCodeFailure) { loggerService.errorLogs("StatusCode Failure: ${failure.message}"); - await _showDialog(failure, title: "Status Code Failure Error"); + await _showDialog(failure, title: "StatusCodeFailure"); + } else if (failure is ConnectivityFailure) { + loggerService.errorLogs("ConnectivityFailure : ${failure.message}"); + await _showDialog(failure, title: "ConnectivityFailure ", onOkPressed: () {}); + } else if (failure is UnAuthenticatedUserFailure) { + loggerService.errorLogs("URL: ${failure.url} \n UnAuthenticatedUser Failure: ${failure.message}"); + await _showDialog(failure, title: "UnAuthenticatedUser Failure", onOkPressed: () => navigationService.replaceAllRoutesAndNavigateToLanding()); + } else if (failure is AppUpdateFailure) { + loggerService.errorLogs("AppUpdateFailure : ${failure.message}"); + await _showDialog(failure, title: "AppUpdateFailure Error", onOkPressed: () => navigationService.replaceAllRoutesAndNavigateToLanding()); } else if (failure is HttpException) { loggerService.errorLogs("Http Exception: ${failure.message}"); await _showDialog(failure, title: "Network Error"); } else if (failure is UnknownFailure) { - loggerService.errorLogs("Unknown Failure: ${failure.message}"); - await _showDialog(failure, title: "Unknown Error"); + loggerService.errorLogs("URL: ${failure.url} \n Unknown Failure: ${failure.message}"); + await _showDialog(failure, title: "Unknown Failure"); } else if (failure is InvalidCredentials) { loggerService.errorLogs("Invalid Credentials : ${failure.message}"); - await _showDialog(failure, title: "Unknown Error"); + await _showDialog(failure, title: "Invalid Credentials "); } else if (failure is UserIntimationFailure) { if (onUnHandledFailure != null) { onUnHandledFailure(failure); } else { - await _showDialog(failure, title: "Error", onOkPressed: onOkPressed); + await _showDialog(failure, title: "UserIntimationFailure", onOkPressed: onOkPressed); } } else if (failure is MessageStatusFailure) { if (onMessageStatusFailure != null) { onMessageStatusFailure(failure); } else { - await _showDialog(failure, title: "Error", onOkPressed: onOkPressed); + await _showDialog(failure, title: "MessageStatusFailure", onOkPressed: onOkPressed); } } else { loggerService.errorLogs("Unhandled failure type: $failure"); - await _showDialog(failure, title: "Error", onOkPressed: onOkPressed); + await _showDialog(failure, title: "Unhandled Error", onOkPressed: onOkPressed); } } - Future _showDialog(Failure failure, {String title = "Error", Function()? onOkPressed}) async { + Future _showDialog(Failure failure, {required String title, Function()? onOkPressed}) async { if (LoadingUtils.isLoading) { LoadingUtils.hideFullScreenLoader(); } - - await dialogService.showErrorBottomSheet(message: failure.message, onOkPressed: onOkPressed); + await dialogService.showErrorBottomSheet(title: title, message: failure.message, onOkPressed: onOkPressed); } } diff --git a/lib/services/navigation_service.dart b/lib/services/navigation_service.dart index 420c4cf..bfdedef 100644 --- a/lib/services/navigation_service.dart +++ b/lib/services/navigation_service.dart @@ -1,5 +1,8 @@ import 'package:flutter/material.dart'; +import 'package:hmg_patient_app_new/core/app_state.dart'; +import 'package:hmg_patient_app_new/core/dependencies.dart'; import 'package:hmg_patient_app_new/features/authentication/widgets/otp_verification_screen.dart'; +import 'package:hmg_patient_app_new/routes/app_routes.dart'; class NavigationService { final GlobalKey navigatorKey = GlobalKey(); @@ -18,6 +21,15 @@ class NavigationService { navigatorKey.currentState?.popUntil(ModalRoute.withName(routeName)); } + void replaceAllRoutesAndNavigateToLanding() { + AppState appState = getIt.get(); + appState.isAuthenticated = false; + navigatorKey.currentState?.pushNamedAndRemoveUntil( + AppRoutes.landingScreen, + (Route route) => false, + ); + } + void pushAndReplace(String routeName) { navigatorKey.currentState?.pushReplacementNamed(routeName); } diff --git a/lib/widgets/bottomsheet/exception_bottom_sheet.dart b/lib/widgets/bottomsheet/exception_bottom_sheet.dart index f0ea651..c11dec1 100644 --- a/lib/widgets/bottomsheet/exception_bottom_sheet.dart +++ b/lib/widgets/bottomsheet/exception_bottom_sheet.dart @@ -11,13 +11,14 @@ import 'package:hmg_patient_app_new/theme/colors.dart'; import 'package:hmg_patient_app_new/widgets/buttons/custom_button.dart'; class ExceptionBottomSheet extends StatelessWidget { - String message; - bool showOKButton; - bool showCancel; - Function() onOkPressed; - Function()? onCancelPressed; + final String? title; + final String message; + final bool showOKButton; + final bool showCancel; + final Function() onOkPressed; + final Function()? onCancelPressed; - ExceptionBottomSheet({Key? key, required this.message, this.showOKButton = true, this.showCancel = false, required this.onOkPressed, this.onCancelPressed}) : super(key: key); + const ExceptionBottomSheet({super.key, this.title, required this.message, this.showOKButton = true, this.showCancel = false, required this.onOkPressed, this.onCancelPressed}); @override Widget build(BuildContext context) { @@ -44,7 +45,7 @@ class ExceptionBottomSheet extends StatelessWidget { Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ - LocaleKeys.notice.tr().toText28(), + (title ?? LocaleKeys.notice.tr()).toText28(), InkWell( onTap: () { Navigator.of(context).pop(); @@ -54,7 +55,7 @@ class ExceptionBottomSheet extends StatelessWidget { ], ), SizedBox(height: 10.h), - (message ?? "").toText16(isBold: false, color: AppColors.textColor), + (message).toText16(isBold: false, color: AppColors.textColor), SizedBox(height: 10.h), SizedBox(height: 24.h), if (showOKButton && showCancel) diff --git a/lib/widgets/common_bottom_sheet.dart b/lib/widgets/common_bottom_sheet.dart index c50ffad..29df19b 100644 --- a/lib/widgets/common_bottom_sheet.dart +++ b/lib/widgets/common_bottom_sheet.dart @@ -104,7 +104,7 @@ class ButtonSheetContent extends StatelessWidget { } } -void showCommonBottomSheetWithoutHeight( +Future showCommonBottomSheetWithoutHeight( BuildContext context, { required Widget child, required VoidCallback callBackFunc, @@ -113,7 +113,7 @@ void showCommonBottomSheetWithoutHeight( bool isFullScreen = true, bool isDismissible = true, Widget? titleWidget, -}) { +}) async { showModalBottomSheet( sheetAnimationStyle: AnimationStyle( duration: Duration(milliseconds: 500), // Custom animation duration