diff --git a/lib/features/base/reloadable/reloadable_controller.dart b/lib/features/base/reloadable/reloadable_controller.dart index fbfa11842..f0750cec7 100644 --- a/lib/features/base/reloadable/reloadable_controller.dart +++ b/lib/features/base/reloadable/reloadable_controller.dart @@ -36,7 +36,7 @@ abstract class ReloadableController extends BaseController { goToLogin(); } else if (failure is GetSessionFailure) { logError('$runtimeType::handleFailureViewState():Failure = $failure'); - _handleGetSessionFailure(failure.exception); + handleGetSessionFailure(failure.exception); } else if (failure is UpdateAccountCacheFailure) { logError('$runtimeType::handleFailureViewState():Failure = $failure'); _handleUpdateAccountCacheCompleted( @@ -127,7 +127,7 @@ abstract class ReloadableController extends BaseController { consumeState(_getSessionInteractor.execute()); } - void _handleGetSessionFailure(GetSessionFailure failure) { + void handleGetSessionFailure(GetSessionFailure failure) { if (failure.exception is! BadCredentialsException) { toastManager.showMessageFailure(failure); } diff --git a/lib/features/starting_page/domain/usecase/sign_in_saas_interactor.dart b/lib/features/starting_page/domain/usecase/sign_in_saas_interactor.dart index 74117e54f..4e5379b3c 100644 --- a/lib/features/starting_page/domain/usecase/sign_in_saas_interactor.dart +++ b/lib/features/starting_page/domain/usecase/sign_in_saas_interactor.dart @@ -1,13 +1,11 @@ import 'package:core/presentation/state/failure.dart'; import 'package:core/presentation/state/success.dart'; import 'package:dartz/dartz.dart'; -import 'package:flutter/services.dart'; import 'package:model/account/authentication_type.dart'; import 'package:model/account/personal_account.dart'; import 'package:model/oidc/oidc_configuration.dart'; import 'package:model/oidc/token_oidc.dart'; import 'package:rich_text_composer/views/commons/logger.dart'; -import 'package:tmail_ui_user/features/login/domain/exceptions/login_exception.dart'; import 'package:tmail_ui_user/features/login/domain/repository/account_repository.dart'; import 'package:tmail_ui_user/features/login/domain/repository/authentication_oidc_repository.dart'; import 'package:tmail_ui_user/features/login/domain/repository/credential_repository.dart'; @@ -51,13 +49,6 @@ class SignInSaasInteractor { ); yield Right(SignInSaasSuccess(tokenOIDC, baseUri, oidcConfiguration)); - } on PlatformException catch (e) { - logError('SignInSaasInteractor::execute():PlatformException ${e.message} - ${e.stacktrace}'); - if (NoSuitableBrowserForOIDCException.verifyException(e)) { - yield Left(SignInSaasFailure(NoSuitableBrowserForOIDCException())); - } else { - yield Left(SignInSaasFailure(e)); - } } catch (e) { logError('SignInSaasInteractor::execute():Exception = $e'); yield Left(SignInSaasFailure(e)); diff --git a/lib/features/starting_page/presentation/twake_welcome/twake_welcome_controller.dart b/lib/features/starting_page/presentation/twake_welcome/twake_welcome_controller.dart index 662347759..0a0d54add 100644 --- a/lib/features/starting_page/presentation/twake_welcome/twake_welcome_controller.dart +++ b/lib/features/starting_page/presentation/twake_welcome/twake_welcome_controller.dart @@ -1,14 +1,19 @@ +import 'package:core/presentation/state/failure.dart'; import 'package:core/presentation/state/success.dart'; import 'package:dartz/dartz.dart'; +import 'package:flutter/cupertino.dart'; import 'package:jmap_dart_client/jmap/core/session/session.dart'; import 'package:model/oidc/oidc_configuration.dart'; +import 'package:tip_dialog/tip_dialog.dart'; import 'package:tmail_ui_user/features/base/reloadable/reloadable_controller.dart'; +import 'package:tmail_ui_user/features/home/domain/state/get_session_state.dart'; import 'package:tmail_ui_user/features/login/data/network/config/oidc_constant.dart'; import 'package:tmail_ui_user/features/login/domain/exceptions/authentication_exception.dart'; import 'package:tmail_ui_user/features/login/presentation/login_form_type.dart'; import 'package:tmail_ui_user/features/login/presentation/model/login_arguments.dart'; import 'package:tmail_ui_user/features/starting_page/domain/state/sign_in_saas_state.dart'; import 'package:tmail_ui_user/features/starting_page/domain/usecase/sign_in_saas_interactor.dart'; +import 'package:tmail_ui_user/main/localizations/app_localizations.dart'; import 'package:tmail_ui_user/main/routes/app_routes.dart'; import 'package:tmail_ui_user/main/routes/route_navigation.dart'; import 'package:tmail_ui_user/main/routes/route_utils.dart'; @@ -31,7 +36,9 @@ class TwakeWelcomeController extends ReloadableController { AppUtils.launchLink(AppConfig.linagoraPrivacyUrl); } - void onClickSignIn() { + void onClickSignIn(BuildContext context) { + TipDialogHelper.loading(AppLocalizations.of(context).loadingPleaseWait); + if (AppConfig.saasServerUrl.isEmpty) { consumeState(Stream.value(Left(SignInSaasFailure(CanNotFoundSaasServerUrl())))); return; @@ -63,13 +70,31 @@ class TwakeWelcomeController extends ReloadableController { } } + @override + void handleFailureViewState(Failure failure) { + if (failure is SignInSaasFailure) { + _handleSignInSaasFailure(failure); + } else { + super.handleFailureViewState(failure); + } + } + @override void handleReloaded(Session session) { + TipDialogHelper.dismiss(); + popAndPush( RouteUtils.generateNavigationRoute(AppRoutes.dashboard), arguments: session); } + @override + void handleGetSessionFailure(GetSessionFailure failure) { + TipDialogHelper.dismiss(); + + toastManager.showMessageFailure(failure); + } + void _handleSignInSaasSuccess(SignInSaasSuccess success) { dynamicUrlInterceptors.setJmapUrl(success.baseUri.toString()); dynamicUrlInterceptors.changeBaseUrl(success.baseUri.toString()); @@ -81,4 +106,10 @@ class TwakeWelcomeController extends ReloadableController { newConfig: success.oidcConfiguration); getSessionAction(); } + + void _handleSignInSaasFailure(SignInSaasFailure failure) { + TipDialogHelper.dismiss(); + + toastManager.showMessageFailure(failure); + } } \ No newline at end of file diff --git a/lib/features/starting_page/presentation/twake_welcome/twake_welcome_view.dart b/lib/features/starting_page/presentation/twake_welcome/twake_welcome_view.dart index b95b20219..82df68aef 100644 --- a/lib/features/starting_page/presentation/twake_welcome/twake_welcome_view.dart +++ b/lib/features/starting_page/presentation/twake_welcome/twake_welcome_view.dart @@ -3,6 +3,7 @@ import 'package:flutter/services.dart'; import 'package:flutter_svg/flutter_svg.dart'; import 'package:get/get.dart'; import 'package:linagora_design_flutter/linagora_design_flutter.dart'; +import 'package:tip_dialog/tip_dialog.dart'; import 'package:tmail_ui_user/features/starting_page/presentation/twake_welcome/twake_welcome_controller.dart'; import 'package:tmail_ui_user/features/starting_page/presentation/twake_welcome/twake_welcome_view_style.dart'; import 'package:tmail_ui_user/main/localizations/app_localizations.dart'; @@ -19,32 +20,45 @@ class TwakeWelcomeView extends GetWidget { DeviceOrientation.portraitDown ]); - return TwakeWelcomeScreen( - logo: Padding( - padding: const EdgeInsetsDirectional.only(bottom: 16), - child: SvgPicture.asset( - controller.imagePaths.icLogoTwakeWelcome, - width: TwakeWelcomeViewStyle.logoWidth, - height: TwakeWelcomeViewStyle.logoHeight, + return Stack( + children: [ + TwakeWelcomeScreen( + logo: Padding( + padding: const EdgeInsetsDirectional.only(bottom: 16), + child: SvgPicture.asset( + controller.imagePaths.icLogoTwakeWelcome, + width: TwakeWelcomeViewStyle.logoWidth, + height: TwakeWelcomeViewStyle.logoHeight, + ), + ), + focusColor: Colors.transparent, + hoverColor: Colors.transparent, + highlightColor: Colors.transparent, + overlayColor: WidgetStateProperty.all(Colors.transparent), + signInTitle: AppConfig.isSaasPlatForm + ? AppLocalizations.of(context).signIn.capitalizeFirst ?? '' + : null, + onSignInOnTap: () => controller.onClickSignIn(context), + createTwakeIdTitle: AppConfig.isSaasPlatForm + ? AppLocalizations.of(context).createTwakeId + : null, + useCompanyServerTitle: AppLocalizations.of(context).useCompanyServer, + description: AppLocalizations.of(context).descriptionWelcomeTo, + privacyPolicy: AppLocalizations.of(context).privacyPolicy, + descriptionPrivacyPolicy: AppLocalizations.of(context).byContinuingYouAreAgreeingToOur, + onPrivacyPolicyOnTap: controller.onClickPrivacyPolicy, + onUseCompanyServerOnTap: controller.handleUseCompanyServer, ), - ), - focusColor: Colors.transparent, - hoverColor: Colors.transparent, - highlightColor: Colors.transparent, - overlayColor: WidgetStateProperty.all(Colors.transparent), - signInTitle: AppConfig.isSaasPlatForm - ? AppLocalizations.of(context).signIn.capitalizeFirst ?? '' - : null, - onSignInOnTap: controller.onClickSignIn, - createTwakeIdTitle: AppConfig.isSaasPlatForm - ? AppLocalizations.of(context).createTwakeId - : null, - useCompanyServerTitle: AppLocalizations.of(context).useCompanyServer, - description: AppLocalizations.of(context).descriptionWelcomeTo, - privacyPolicy: AppLocalizations.of(context).privacyPolicy, - descriptionPrivacyPolicy: AppLocalizations.of(context).byContinuingYouAreAgreeingToOur, - onPrivacyPolicyOnTap: controller.onClickPrivacyPolicy, - onUseCompanyServerOnTap: controller.handleUseCompanyServer, + TipDialogContainer( + duration: const Duration(seconds: 2), + outsideTouchable: true, + onOutsideTouch: (tipDialog) { + if (tipDialog is TipDialog && tipDialog.type == TipDialogType.LOADING) { + TipDialogHelper.dismiss(); + } + } + ) + ], ); } } \ No newline at end of file diff --git a/lib/l10n/intl_messages.arb b/lib/l10n/intl_messages.arb index aae5a70fa..07e62d999 100644 --- a/lib/l10n/intl_messages.arb +++ b/lib/l10n/intl_messages.arb @@ -4059,5 +4059,11 @@ "type": "text", "placeholders_order": [], "placeholders": {} + }, + "sigInSaasFailed": "Login failed. Please check again.", + "@sigInSaasFailed": { + "type": "text", + "placeholders_order": [], + "placeholders": {} } } \ No newline at end of file diff --git a/lib/main/localizations/app_localizations.dart b/lib/main/localizations/app_localizations.dart index c9d72b6c4..d6a36648e 100644 --- a/lib/main/localizations/app_localizations.dart +++ b/lib/main/localizations/app_localizations.dart @@ -4259,4 +4259,11 @@ class AppLocalizations { name: 'useCompanyServer', ); } + + String get sigInSaasFailed { + return Intl.message( + 'Login failed. Please check again.', + name: 'sigInSaasFailed', + ); + } } diff --git a/lib/main/utils/toast_manager.dart b/lib/main/utils/toast_manager.dart index 03a6317c9..d6e497005 100644 --- a/lib/main/utils/toast_manager.dart +++ b/lib/main/utils/toast_manager.dart @@ -8,6 +8,7 @@ import 'package:tmail_ui_user/features/home/data/exceptions/session_exceptions.d import 'package:tmail_ui_user/features/home/domain/state/get_session_state.dart'; import 'package:tmail_ui_user/features/login/data/network/oidc_error.dart'; import 'package:tmail_ui_user/features/login/domain/exceptions/authentication_exception.dart'; +import 'package:tmail_ui_user/features/starting_page/domain/state/sign_in_saas_state.dart'; import 'package:tmail_ui_user/features/thread/domain/state/empty_spam_folder_state.dart'; import 'package:tmail_ui_user/features/thread/domain/state/move_multiple_email_to_mailbox_state.dart'; import 'package:tmail_ui_user/main/exceptions/remote_exception.dart'; @@ -64,6 +65,8 @@ class ToastManager { && failure.emailActionType == EmailActionType.moveToSpam && failure.moveAction == MoveAction.moving) { message = AppLocalizations.of(currentContext!).markAsSpamFailed; + } else if (failure is SignInSaasFailure) { + message = AppLocalizations.of(currentContext!).sigInSaasFailed; } if (message?.isNotEmpty == true) { diff --git a/pubspec.lock b/pubspec.lock index b4001a09f..a6d0fc0af 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -1330,6 +1330,14 @@ packages: url: "https://pub.dev" source: hosted version: "2.1.1" + loading_view: + dependency: transitive + description: + name: loading_view + sha256: "3d31c2c5293c2e3518b7330ffdc2fab5c83daaa9218cc45d4406c875f08f0795" + url: "https://pub.dev" + source: hosted + version: "1.1.0" logging: dependency: transitive description: @@ -2016,6 +2024,14 @@ packages: url: "https://pub.dev" source: hosted version: "1.0.1" + tip_dialog: + dependency: "direct main" + description: + name: tip_dialog + sha256: edc1ebbb4b9f9575220c85206cf6986921c2b63d173744be0babac00c2e48bd0 + url: "https://pub.dev" + source: hosted + version: "4.0.0" typed_data: dependency: transitive description: diff --git a/pubspec.yaml b/pubspec.yaml index 77f3116d2..f85093add 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -255,6 +255,8 @@ dependencies: web_socket_channel: 2.4.3 + tip_dialog: 4.0.0 + dev_dependencies: flutter_test: sdk: flutter