diff --git a/lib/pangea/login/widgets/p_sso_button.dart b/lib/pangea/login/widgets/p_sso_button.dart index d89c0e0e1..a02219333 100644 --- a/lib/pangea/login/widgets/p_sso_button.dart +++ b/lib/pangea/login/widgets/p_sso_button.dart @@ -9,12 +9,12 @@ import 'package:matrix/matrix.dart'; import 'package:universal_html/html.dart' as html; import 'package:fluffychat/config/app_config.dart'; -import 'package:fluffychat/pages/homeserver_picker/homeserver_picker.dart'; import 'package:fluffychat/pangea/common/utils/firebase_analytics.dart'; import 'package:fluffychat/pangea/login/sso_provider_enum.dart'; import 'package:fluffychat/pangea/login/widgets/p_sso_dialog.dart'; import 'package:fluffychat/utils/platform_infos.dart'; import 'package:fluffychat/widgets/fluffy_chat_app.dart'; +import 'package:fluffychat/widgets/future_loading_dialog.dart'; import 'package:fluffychat/widgets/matrix.dart'; class PangeaSsoButton extends StatelessWidget { @@ -27,23 +27,25 @@ class PangeaSsoButton extends StatelessWidget { super.key, }); - Future _runSSOLogin(BuildContext context) => showAdaptiveDialog( - context: context, - builder: (context) => SSODialog( - future: () => _ssoAction( - IdentityProvider( - id: provider.id, - name: provider.name, - ), - context, - ), - ), - ); + Future _runSSOLogin(BuildContext context) async { + final token = await showAdaptiveDialog( + context: context, + builder: (context) => SSODialog( + future: () => _getSSOToken(context), + ), + ); - Future _ssoAction( - IdentityProvider provider, - BuildContext context, - ) async { + if (token == null || token.isEmpty) { + return; + } + + await showFutureLoadingDialog( + context: context, + future: () => _ssoAction(token, context), + ); + } + + Future _getSSOToken(BuildContext context) async { final bool isDefaultPlatform = (PlatformInfos.isMobile || PlatformInfos.isWeb || PlatformInfos.isMacOS); @@ -58,7 +60,7 @@ class PangeaSsoButton extends StatelessWidget { : 'http://localhost:3001//login'; final client = await Matrix.of(context).getLoginClient(); final url = client.homeserver!.replace( - path: '/_matrix/client/v3/login/sso/redirect/${provider.id ?? ''}', + path: '/_matrix/client/v3/login/sso/redirect/${provider.id}', queryParameters: {'redirectUrl': redirectUrl}, ); @@ -74,13 +76,20 @@ class PangeaSsoButton extends StatelessWidget { } catch (err) { if (err is PlatformException && err.code == 'CANCELED') { debugPrint("user cancelled SSO login"); - return; + return null; } rethrow; } final token = Uri.parse(result).queryParameters['loginToken']; - if (token?.isEmpty ?? false) return; + if (token?.isEmpty ?? false) return null; + return token; + } + Future _ssoAction( + String token, + BuildContext context, + ) async { + final client = Matrix.of(context).client; final redirect = client.onLoginStateChanged.stream .where((state) => state == LoginState.loggedIn) .first @@ -110,7 +119,7 @@ class PangeaSsoButton extends StatelessWidget { await redirect; } - GoogleAnalytics.login(provider.name!, loginRes.userId); + GoogleAnalytics.login(provider.name, loginRes.userId); } @override diff --git a/lib/pangea/login/widgets/p_sso_dialog.dart b/lib/pangea/login/widgets/p_sso_dialog.dart index fb7184672..2620c3a11 100644 --- a/lib/pangea/login/widgets/p_sso_dialog.dart +++ b/lib/pangea/login/widgets/p_sso_dialog.dart @@ -5,11 +5,10 @@ import 'package:flutter/material.dart'; import 'package:flutter_linkify/flutter_linkify.dart'; import 'package:fluffychat/l10n/l10n.dart'; -import 'package:fluffychat/utils/localized_exception_extension.dart'; import 'package:fluffychat/utils/url_launcher.dart'; class SSODialog extends StatefulWidget { - final Future Function() future; + final Future Function() future; const SSODialog({ super.key, required this.future, @@ -22,7 +21,6 @@ class SSODialog extends StatefulWidget { class SSODialogState extends State { Timer? _hintTimer; bool _showHint = false; - Object? _error; @override void initState() { @@ -43,9 +41,10 @@ class SSODialogState extends State { Future _runFuture() async { try { - await widget.future(); + final token = await widget.future(); + Navigator.of(context).pop(token); } catch (e) { - setState(() => _error = e); + Navigator.of(context).pop(); } } @@ -69,17 +68,11 @@ class SSODialogState extends State { icon: const Icon(Icons.close), ), ), - _error == null - ? Text( - L10n.of(context).ssoDialogTitle, - style: Theme.of(context).textTheme.headlineMedium, - textAlign: TextAlign.center, - ) - : Icon( - Icons.error_outline_outlined, - color: Theme.of(context).colorScheme.error, - size: 48, - ), + Text( + L10n.of(context).ssoDialogTitle, + style: Theme.of(context).textTheme.headlineMedium, + textAlign: TextAlign.center, + ), Container( alignment: Alignment.center, constraints: const BoxConstraints(minHeight: 150), @@ -88,39 +81,29 @@ class SSODialogState extends State { spacing: 16.0, mainAxisSize: MainAxisSize.min, children: [ - if (_error != null) - Text( - _error!.toLocalizedString(context), - style: Theme.of(context).textTheme.titleMedium, - textAlign: TextAlign.center, - ) - else ...[ - SelectableLinkify( - text: L10n.of(context).ssoDialogDesc, - textScaleFactor: - MediaQuery.textScalerOf(context).scale(1), - linkStyle: TextStyle( - color: Theme.of(context).colorScheme.primary, - decorationColor: Theme.of(context).colorScheme.primary, - ), - options: const LinkifyOptions(humanize: false), - onOpen: (url) => - UrlLauncher(context, url.url).launchUrl(), - style: Theme.of(context).textTheme.bodyLarge, - textAlign: TextAlign.center, + SelectableLinkify( + text: L10n.of(context).ssoDialogDesc, + textScaleFactor: MediaQuery.textScalerOf(context).scale(1), + linkStyle: TextStyle( + color: Theme.of(context).colorScheme.primary, + decorationColor: Theme.of(context).colorScheme.primary, ), - _showHint - ? Text( - L10n.of(context).ssoDialogHelpText, - style: Theme.of(context).textTheme.bodyLarge, - textAlign: TextAlign.center, - ) - : const SizedBox( - height: 16.0, - width: 16.0, - child: CircularProgressIndicator.adaptive(), - ), - ], + options: const LinkifyOptions(humanize: false), + onOpen: (url) => UrlLauncher(context, url.url).launchUrl(), + style: Theme.of(context).textTheme.bodyLarge, + textAlign: TextAlign.center, + ), + _showHint + ? Text( + L10n.of(context).ssoDialogHelpText, + style: Theme.of(context).textTheme.bodyLarge, + textAlign: TextAlign.center, + ) + : const SizedBox( + height: 16.0, + width: 16.0, + child: CircularProgressIndicator.adaptive(), + ), ], ), ),