Essentials icon indicating copy to clipboard operation
Essentials copied to clipboard

[Bug] [UWP] WebAuthenticator calls an unsupported method WebAuthenticationBroker.AuthenticateAsync

Open SymboLinker opened this issue 4 years ago • 10 comments

Description

Inside of WebAuthenticator.uwp.cs: the method WebAuthenticationBroker.AuthenticateAsync from the Windows.Security.Authentication.Web namespace seems to work for Google, but not for Dropbox. For Dropbox, it shows "Can't connect to the service".

Fastest way to reproduce:

Use var requestUri = new Uri("https://dropbox.com/oauth2/authorize?dummyQueryString"); in a call with

var response = await WebAuthenticationBroker.AuthenticateAsync(WebAuthenticationOptions.None, requestUri, new Uri("dummycallbackUri:/"));

This results in: Can't connect to the service

Calling it with

var requestUri = new Uri("https://accounts.google.com/o/oauth2/auth?dummyQueryString");

results in Google-content being displayed (a 400 Bad Request, but that is as expected with a dummy query string).

I tested another random requestUri "https://stackoverflow.com/" that has nothing to do with OAuth, I get:

WebAuthenticationBrokers seems to use Internet Explorer

This last example may provide some information on how the WebAuthenticationBroker works...

At StackOverflow I asked:

  • is the WebAuthenticationBroker really using an old browser while I'm using the latest version of Mozilla FireFox as my default browser?
  • How can I use WebAuthenticationBroker.AuthenticateAsync for Dropbox?

The answer has surprised me: the WebAuthenticationBroker probably uses an old browser engine and could be considered a "web view", which is unsupported in OAuth flows.

UWP's WebAuthenticator.PlatformAuthenticateAsync should probably be modified to use a system browser.

SymboLinker avatar May 14 '21 00:05 SymboLinker

I've just created pull request #1828 that is a potential fix for this problem. I suspect that the Xamarin.Essentials team waits until the AuthenticationBroker team comes up with a fix and that the pull request will not be merged.

However, if you are an app developer, it may be helpful to see what classes and methods you can use in your own app, working around the temporary shortcoming of the WebAuthenticator for UWP and doing your OAuth flow for UWP without using the WebAuthenticator of Xamarin.Essentials.

SymboLinker avatar Jun 11 '21 12:06 SymboLinker

I also encountered this issue when I work with AWS Cognito UserPool on UWP where as everything work well on iOS, Android, MacOS. and I have to write my own implementation which replaces the AuthenticationBroker. I follow this guide to make it work on other platform, but it does not work on UWP https://dev.to/pietervdw/using-aws-cognito-with-xamarin-forms-46l5

ledangvu avatar Sep 06 '21 07:09 ledangvu

So sad to have something normal like OAuth2 being broken in the Xamarin framework.

Is there any ETA when this will be fixed? Seems like this bug ticket is totally abandoned by the Xamarin team :disappointed:

marvinside avatar Sep 07 '21 10:09 marvinside

Xamarin is getting a major refactor. It will be renamed “.NET MAUI”. The Xamarin.Essentials team is also refactoring the Essentials library to work with MAUI. So, probably after the library is stable for MAUI, open bugs will be taken on.

However, this bug may be out of scope for the Essentials team, because it’s also an issue for the AuthenticationBroker team. Not very nice news to hear… It took me a while too to find this out.

Check out the PR I did to fix it for your app. If you need help, let me know. I can help.

SymboLinker avatar Sep 07 '21 10:09 SymboLinker

@SymboLinker I used your solution in my Xamarin project with AWS Cognito User Pool. Your solution works in some cases. But for a special case I did with aws cognito, it is likely we need to investigate morewhen we create a new user in aws cognito user pool and set an email as username. Just follow this guide to create a user, but instead of using a normal username, you just need to put an email as username. https://dev.to/pietervdw/using-aws-cognito-with-xamarin-forms-46l5

jerryno6 avatar Sep 08 '21 03:09 jerryno6

@SymboLinker I've found out that when we use Chrome or Edge (chromium core), it does not work with these type of accounts from AWS Cognito, but when we use Firefox as external webbrowser, It works. But the problem is that we cannot ask endusers to install firefox onto their PC to use our app, so I made a solution to make it work without depending on the external browser as a pull request in my own repository below. The trick is to use internal webview with URI activation to make it work together. pull request for using webView and UriActivation

I also created a pull request which uses your solution to test for these accounts on aws cognito Pull request for using external webbrowser

If you have time, please take a look at it. You can use your credential from other Identity services (dropbox/facebook/) to test this solution or You can use users/password that I provide below to test it on your project. Authenticate URL: https://vuleinip.auth.us-east-2.amazoncognito.com/login?client_id=5d55renrdia8r2cg2hocmn98me&response_type=token&scope=aws.cognito.signin.user.admin+email+openid+phone+profile&redirect_uri=myxfcognitoapp:// Callback URL: myxfcognitoapp://

Test accounts: username / password: test01 / Test@123 test02 / Test@123 [email protected] / Test@123

Thanks for your contribution.

jerryno6 avatar Sep 09 '21 02:09 jerryno6

I've found out that when we use Chrome or Edge (chromium core), it does not work with these type of accounts from AWS Cognito, but when we use Firefox as external webbrowser, It works.

I know nothing about AWS Cognito and its type of accounts. What I do know, is that the full OAuth (PKCE) flow for Dropbox works via FireFox (version 91.0.2), Chrome (Version 93.0.4577.63) and Edge (Version 93.0.961.38). I've just tested those again.

The trick is to use internal webview with URI activation to make it work together.

Using a web view for OAuth might become forbidden in the future. Google and Dropbox do not support it. I've not searched for other organisations that follow the same rule.

If you have time, please take a look at it.

In your pull request that uses an external browser, I think you should ~HtmlEncode~UrlEncode the callback url when you launch the browser. A querystring parameter value with - for example - a slash in it won't work unless you've ~HtmlEncoded~UrlEncoded it as "%2F".

SymboLinker avatar Sep 09 '21 04:09 SymboLinker

@SymboLinker Thanks for sharing. At the moment aws cognito works well with webview, it is more stable like it works on Android & iOS, it's better than external webbrowser works in some cases. I will temporarily use it until Microsoft fix for the Broker. or we will wait and move to MAUI. When I have a chance to work with google or dropbox, I will remember the solution from you: use external webbrowser for Oauth2.

As for HtmlEncode, I also use HttpUtility.UrlEncode(callbackUrl.OriginalString) but does not return valid string, and I have to replace it with Uri.Uri.EscapeUriString(string).

jerryno6 avatar Sep 09 '21 06:09 jerryno6

As for HtmlEncode, I also use HttpUtility.UrlEncode(callbackUrl.OriginalString) but does not return valid string, and I have to replace it with Uri.Uri.EscapeUriString(string).

Hmmm, HtmlEncoding seems not correct indeed. For my app, I skip the step of escaping the url, because a Dropbox library does that for me. Thanks for the feedback!

EDIT (later added): Luckily I used HttpUtility.UrlEncode in the PR I did. In LinqPad I've just tested that System.Web.HttpUtility.UrlEncode("test://") gives "test%3a%2f%2f".

SymboLinker avatar Sep 09 '21 16:09 SymboLinker

October 2023.

I am running into this issue Authenticating users with New York City Board of Ed OAuth.

On UWP, getting the error that "Internet Explorer is not supported"

Has anyone resolved this issue? (thread seems to be dormant for 2 years)

I am using version 1.8 of Xamarin Essentials (latest)

Thanks

solomonfried avatar Oct 05 '23 20:10 solomonfried