public WKWebViewController(ExtendedBrowserOptions options, CancellationToken cancellationToken)
        {
            _options = options;

            var webViewConfig = new WKWebViewConfiguration();

            webViewConfig.WebsiteDataStore = WKWebsiteDataStore.NonPersistentDataStore;
            //webViewConfig.SetUrlSchemeHandler(new CallbackHandler(), endUrl.Scheme);
            WebView = new WKWebView(new CGRect(0, 0, 0, 0), webViewConfig);

            WebView.WeakNavigationDelegate = this;

            // Setup cancellation action
            cancellationToken.Register(() => UIApplication.SharedApplication.InvokeOnMainThread(() => ActivityMediator.Instance.Cancel()));

            var request = new NSMutableUrlRequest(new NSUrl(options.LoadDetourUrl ? options.DetourUrl : options.StartUrl));

            if (_options.Headers != null)
            {
                var updatedRequest = UpdateHeaders(new NSMutableUrlRequest(new NSUrl(options.LoadDetourUrl ? options.DetourUrl : options.StartUrl)),
                                                   _options.Headers.ToDictionary(k => k.Key.ToString(), v => v.Value.ToString()));
                if (updatedRequest != null)
                {
                    WebView.LoadRequest(updatedRequest);
                    return;
                }
            }
            WebView.LoadRequest(request);
        }
        internal static Task <BrowserResult> Start(ExtendedBrowserOptions options, CancellationToken cancellationToken)
        {
            var tcs = new TaskCompletionSource <BrowserResult>();

            // Create web view controller
            var browserController = new UINavigationController(new WKWebViewController(options, cancellationToken)
            {
                ModalPresentationStyle = UIModalPresentationStyle.FormSheet,
            });

            browserController.PresentationController.Delegate = new DismissablePresentationControllerDelegate();

            async void Callback(string response)
            {
                ActivityMediator.Instance.ActivityMessageReceived -= Callback;

                if (response == "UserCancel")
                {
                    BrowserMediator.Instance.Cancel();
                    await browserController.DismissViewControllerAsync(true); // Close web view

                    browserController.Dispose();
                    tcs.SetResult(Canceled());
                }
                else if (response == "RestartFlow")
                {
                    // Close existing
                    await browserController.DismissViewControllerAsync(true); // Close web view

                    browserController.Dispose();

                    // Launch new
                    FindRootController().PresentViewController(browserController, true, null);
                }
                else
                {
                    BrowserMediator.Instance.Success();
                    await browserController.DismissViewControllerAsync(true); // Close web view

                    browserController.Dispose();
                    tcs.SetResult(Success(response));
                }
            }

            ActivityMediator.Instance.ActivityMessageReceived += Callback;

            // Launch web view
            FindRootController().PresentViewController(browserController, true, null);

            return(tcs.Task);
        }
示例#3
0
        /// <inheritdoc/>
        public Task <BrowserResult> InvokeAsync(ExtendedBrowserOptions options, CancellationToken cancellationToken = default)
        {
            if (string.IsNullOrWhiteSpace(options.StartUrl))
            {
                throw new ArgumentException("Missing StartUrl", nameof(options));
            }

            if (string.IsNullOrWhiteSpace(options.EndUrl))
            {
                throw new ArgumentException("Missing EndUrl", nameof(options));
            }

            return(Launch(options, cancellationToken));
        }
        public override async Task <LoginResult> DetouredLoginAsync(string detourUrl, LoginRequest request = null, CancellationToken cancellationToken = default)
        {
            if (request == null)
            {
                request = new LoginRequest();
            }

            if (OidcClient.Options.Browser is WKWebViewBrowser browser)
            {
                var authState = await OidcClient.PrepareLoginAsync(cancellationToken : cancellationToken);

                var browserOptions = new ExtendedBrowserOptions(authState.StartUrl, OidcClient.Options.RedirectUri)
                {
                    Timeout       = TimeSpan.FromSeconds(request.BrowserTimeout),
                    DisplayMode   = request.BrowserDisplayMode,
                    LoadDetourUrl = true,
                    DetourUrl     = detourUrl
                };

                if (OidcClient.Options.ResponseMode == OidcClientOptions.AuthorizeResponseMode.FormPost)
                {
                    browserOptions.ResponseMode = OidcClientOptions.AuthorizeResponseMode.FormPost;
                }
                else
                {
                    browserOptions.ResponseMode = OidcClientOptions.AuthorizeResponseMode.Redirect;
                }

                var browserResult = await browser.InvokeAsync(browserOptions, cancellationToken);

                if (browserResult.ResultType == BrowserResultType.Success)
                {
                    var result = await ProcessResponseAsync(
                        browserResult.Response,
                        authState,
                        request.BackChannelExtraParameters);

                    return(result);
                }

                return(new LoginResult(browserResult.Error ?? browserResult.ResultType.ToString()));
            }

            await OidcClient.Options.Browser.InvokeAsync(new BrowserOptions(detourUrl, "null"), cancellationToken);

            return(new LoginResult("UserCancel"));
        }