Google Actions Account Linking Flow - actions-on-google

I've written an authorization flow for my action, to do account linking with the "Implicit flow". I have been testing it using the web simulator. When I try to run the action in the web simulator it tells me to link my account, and provides a URL:
"https://assistant.google.com/services/auth/handoffs/auth/start?provider=hello_dev&return_url=https://www.google.com/"
I run that URL and this is what happens:
My Java servlet receives the auth request from google. It contains what is documented, a GOOGLE_CLIENT_ID, a REDIRECT_URI, a STATE and "response_type=token"
I create an access-token from the Google ID that is logged in by using UserServiceFactory.getUserService().getCurrentUser().getUserId()
I craft a URL to the redirect-uri that contains my ACCESS_TOKEN, token_type=bearer, and state= the state string I originally received
I create a web page for the user that contains that link so they can click it and it executes the link and my account is linked.
That works great and the response is a blank page with a URL that says: "https://www.google.com/?result_code=SUCCESS&result_message=Accounts+now+linked."
However, I wanted a flow that allowed the user to ensure they are logged in, and logged into the Google Account they wanted to link
So, I also present a link that logs them out if they'd like. The link is created by using userService.createLogoutURL(thisUrl)
If they do that, I then present them a link to log in, created using userService.createLoginURL(thisUrl)
Once they have logged in, with a different Google ID, they are back on the original page which allows them to log out again or click the "link account" link.
The situation is, that if they click the "link account" link now, the EXACT same link that would have worked successfully before they logged out (except a different ACCESS_TOKEN value) and logged back in with a different account, the response is a blank page with a URL that says: "https://www.google.com/?result_code=FAILURE&result_message=Account+linking+failed"
Two things of note:
If they log out and log back in with the same account, then the "link account" URL works fine
If they are not logged in at all when beginning the process, and then log in and then use the "link account" link it works fine
So, the only time it fails is when they are logged in, log out, log in with a different account, and click to link accounts. That's when it fails.
The account doesn't matter, multiple different accounts work, as long as the browser is logged into the first account and doesn't change during the flow.
I honestly cannot imagine how this is happening.
This gets even worse if I do it in the Google Home app, as it then returns some "malformed request error" page and basically stops working, PERMANENTLY. Stopping/Starting the action didn't help. Stopping/Starting the Web service didn't help. Rebooting the Android device didn't help. Link Account from the Google Home app was permanently broken. The only way I was able to get it working again was to use the Account Link URL (gotten from the web simulator) in the Chrome Browser on my Android device, which seemed to "reset" everything.

At this time, we require that the Google user who initiates the account linking process, both via the simulator and Google Home application, be the same Google user that logs in via a Google Sign-in option, if it is offered as part of your auth flow. This is a hard requirement.
For this reason, we'd suggest not offering a Google logout option as part of your account linking process.

Related

Google not showing promt to select google account

We have web application with keycloak as identity broker, google SAML app as IDP for google managed workspace for domain say mycompany.com. Integration works fine for except a case described below.
If user is logged in with only one non SAML app google account, google returns
403 Error: app_not_configured_for_user.
i.e. If I am logged as with my personal gmail acccount & not with mycompany.com account
I have inspected SAML AuthnRequest payload SAML tracer which has ForceAuthn="true" but still it does not show up account chooser page.
I went through couple of stackoverflow threads. Few provided solution about using account chooser url and redirecting it to auth page https://accounts.google.com/accountchooser?continue={theredirectURL}.
Looking at community to help suggesting clean solution.
This error pretty much depends on which account is the primary one in the Google account chooser as it always takes that to complete the sign in process automatically.
There is no official way or setting from Google to do this, however the mosto commonly used workaround is to add the following URL to the Start URL section of the SAML app settings for it to force the authentication whenever you click on it.
https://accounts.google.com/AccountChooser?continue=https://accounts.google.com/o/saml2/initsso?idpid=[REPLACE]s&spid=[REPLACE]&forceauthn=false
There are 2 parameters that you need to replace in that URL and you need to get them from the Google apps menu next to your profile picture, then hover over the SAML app that you want to change and right click on it, then copy the link address and that will show the idpid and spid values.

Logout seems to not invalidate session in Azure Static Web Apps

I created a static Web site using Azure Static Web Apps (under the Free plan for now -- not sure if that's relevant to the issue at hand.) I can access the Web site through an ***.azurestaticapps.net URL.
I then tried to test Azure Active Directory authentication per Microsoft's instruction from this page:
https://learn.microsoft.com/en-us/azure/static-web-apps/authentication-authorization
My problem is that logging out does not seems to work as I would expect on a normal Web site. I could log out, but when I tried to login again (hoping to use a different Azure AD account,) the Microsoft login screen flashes by and I got logged right back in with the user that I just logged out from. Switching to a different tab doesn't help.
Steps to repro:
Navigate to /.auth/login/aad and login using a Microsoft Account. Say NO to 'Stay signed in?' prompt.
Navigate to /.auth/me to see the basic information on the logged in account to prove that I'm in the logged in state.
Navigate to /.auth/logout to logout. Immediately, navigate to /.auth/me again to confirm that my static Web App regards me as 'logged out.' I'd see this:
{"clientPrincipal": null}
Navigate to /.auth/login/aad again. Microsoft login page flashes by, and I am logged right back in with the previously logged out user.
Things that sort of worked
Any of the two actions below alone seems to make the browser forget my logged-in state:
Close the whole browser and relaunch it. I'd get asked to pick the previous user (and then enter the password) or choose a new user. This sort of works but reminds me of some Web sites 15-20 years ago that said 'For security reasons, please don't forget to close your entire browser after logging out from this one tab.'
Open a new tab in the same browser, and navigate to hotmail.com. That tab will enjoy my logged-in state from the Static Web Apps tab. I'd see my mails right away. Then I log out from the hotmail.com tab, switch back to ***.azurestaticapps.net tab and see that I am still logged into my Static Web App. Good! Then if I log out from my Static Web App and try to log back in, it has forgotten my logged-in state this time. In other words, logging out from the hotmail.com tab is somehow more powerful.
I also tested /.auth/login/google too and the same problem arises! So the issue seems to be on the Azure Static Web Apps side, not how idPs handle their logout process.
Am I missing anything obvious?

Google Identity Toolkit - Twitter sign in prompts to authorize app every time

I've using Twitter as one of the IDPs in my Google Identity Toolkit configuration. I followed all the required steps. I'm able to sign in with Twitter and it works fine for the most part except for 2 issues highlighted below. In my Twitter application settings, Permission is set to "Read only".
Every time I try to sign in with Twitter using an account used previously to sign in, it prompts me to "Authorize app" again. As I understand, the authorization should be one time only unless revoked. Why do I need to authorize with every sign in?
I found this thread: https://twittercommunity.com/t/why-does-my-app-need-permission-granted-every-time-the-user-authenticates-through-oauth/10251/5
It seems like Sign in with Twitter button seems to be routing to 'https://api.twitter.com/oauth/authorize' instead of 'https://api.twitter.com/oauth/authenticate'. Is this a bug in the GIT?
If I click Cancel instead of Authorize app, it brings me back to my callback page but I get a verifyAssertion error:
[identitytoolkit] verifyAssertion: {"error":{"errors":[{"domain":"global","reason":"invalid","message":""}],"code":400,"message":""}}
What is causing this error?
Any help would be appreciated.
Identity Toolkit is intended to use https://api.twitter.com/oauth/authorize because according to https://dev.twitter.com/oauth/reference/get/oauth/authorize, desktop app has to use this.
Which platform are you working on?
If you click Cancel instead of Authorize, Twitter will redirect user to Identity Toolkit with an error response. As a result, Identity Toolkit cannot verify user's identity, and fails the verifyAssertion.

facebook external login not redirect back

I have a MVC5 application with external login. When I use Facebook login, after I put in my login information into facebook login page, facebook fails to direct me back to my application.
I got a white page with the following URL in Chrome's URL bar:
https://www.facebook.com/dialog/oauth?response_type=code&client_id=632877723495196&redirect_uri=http%3A%2F%2Flocalhost%2FMPOS%2Fsignin-facebook&scope=email&state=l2oJwWdkbRsgZHyr6-5lL9ZTZc-eMbRBkH73L-h1ZN_MWvWriNeEdCxuNspi4QptZAna60SQIJX4NB5AItzP6NxpDCz10m48JInWUfvQGWkgFgZhZNFIaTz6ju-kEQ-RyiObgiMOKvBougeeaSHD7CAzTrvc1Gj6XdGgGbUgyrM9d1KZUEGbqh_MdyBPg4wTFbQEiui-2GzvcIvhOVtTRC12NnhgnVyLCrrKEDFaWdU
If I use IE, I got "The website cannot display the page" error page with the following URL on the borwser's URL bar:
https://www.facebook.com/login.php?login_attempt=1&next=https%3A%2F%2Fwww.facebook.com%2Fv2.1%2Fdialog%2Foauth%3Fredirect_uri%3Dhttp%253A%252F%252Flocalhost%252FMPOS%252Fsignin-facebook%26state%3DWbWcYquZJnjvo8Db42l6goqpMUrioHL6HBVIUMu74QvqMuAjNzWizophJhNpf3NHCbw1-Dw1tsdgmv2h1f0ct1zcLJ_jlSXQ3ImCHVN_PXRkRedVB3gjTQb59-tbxPKxJQTuNhPvOKLq6aBjakP_fJDw5zXKZ55LrRzHVzEQ39Qff7WXsNJpke2BTHILHLI0I5jcWiXEgE-HeH7La19ttaL9LhrcyXP4DBiWaXuUNZc%26scope%3Demail%26response_type%3Dcode%26client_id%3D632877723495196%26ret%3Dlogin
Anyone has an answer to this problem? Thanks!
Thanks Nathan, clear cache on browser didn't help. I tried to clear cache/cookies on both IE and Chrome several times before I post the question.
The weird thing is that if I create an app under my personal facebook account and use the FacebookAppID/FacebookAppSecret for my app, the external login works fine. That's how I did all my testing.
But when I try to deploy the website I want to create the app under company's facebook account. I set up the app under the company's facebook account exactly the same way as I did when using my personal facebook account, then I got this redirect problem. If I switch back the FacebookAppID/FacebookAppSecret to the one I created under my personal account, everything works fine. That's even more puzzling.
I finally figured out the problem. I forgot to turn on "make this app and all its live features available to the general public" setting for the app I created in Facebook. So the login was only available to the developer who created the app. After I turn that setting on (it is under the Status and Review Tab), everything works fine.

Facebook Third Party Site Confusing Login Issue

I am using the Javascript SDK in order to have users log into my Facebook App on my Web Site. I have coded and configured in the App Dashboard everything according to the documentation, including the appId and channelUrl (which is //localhost/WebPage for now) in the Javascript, and the App Domain (localhost), the Site URL (http://localhost/WebPage), User & Friend Permissions, as well as Extended Permissions in the App Dashboard.
When I log using a developer Account (using the Login Button on my Site), which owns the App, but after removing the App itself from the “My App” Section in Facebook (in the same Facebook Account), everything works properly (the Login Button directs me to a New Page, asks to log in, and then asks me to Allow for the Permissions required by my App), which confirms that all my settings (and code) appear to be configured properly.
Meanwhile, when I use another Account (which obviously does not own the App) I receive the following error message: “An error occurred. Please try again later.” Nonetheless, upon clicking Okay in the Browser window, the user is still logged into the Main Page of Facebook (in that same Window). Meanwhile, the user does not get logged into the initial Browser Page (my Web Site). What confuses me even more is that when I refresh the initial Browser Window (which is obviously in the same Browser Application), the user is still not logged into Facebook on that Page (my Web Site). One would think that the cookies should be set properly (for that Browser) and the Browser should access them, and display the user as being logged in on my Web Site.
Would someone have an idea of what is happening?
I'd wager that #ifaour's Sandbox Mode comment is the right answer.
Although "An error occurred. Please try again later." is a very generic Facebook error, there was a recent Facebook policy change that resulted in many apps silently being switched into Sandbox Mode.
Excerpt from here:
Privacy policy alert
Apps that do not include a valid privacy policy URL (see Platform
Policy II.3) in the dedicated field in App Dashboard will see an alert
in the App Dashboard and app details pages. In an effort to make it
easier for you to validate, we will include a 'privacy policy URL
test' link that will check if your app meets the privacy policy URL
requirements. If you do not comply your app may be placed in Sandbox
mode. You can disable Sandbox mode once you meet the privacy policy
URL requirements.
This is exacerbated by the fact that detecting that your app is in Sandbox Mode is made more difficult because you have to hit the "Edit" button in order for the option to toggle its status even appears.