-
Notifications
You must be signed in to change notification settings - Fork 2.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
RFC: Auth Enhancements - Easier Federation with Cognito User Pools and Hosted UI #2716
Comments
Cannot +100 this enough 🙏 |
Yes yes yes! This sounds awesome and will be really helpful. 😍😍😍 |
Potentially include scopes per: #297 |
You can't deliver this soon enough! Is this correct?
Seems that if the call to |
Might also be more orthogonal if |
@rcbrown Good catch, I was actually commenting more with respect to the implementation but yes you are correct that token isn't required here as the IdP will pass it back. I'll update the posting. |
Really looking forward to this. |
See also this amplify-cli RFC thread comment for their first release. |
Hello everyone - we have a PR for this and published to our beta tag on NPM. While I've done a lot of testing myself and with team members if the community could run some tests in the next couple days it would help us have confidence to release sooner. You'll see the instructions here: #3005 (comment) Note that through our design reviews and implementation we've been able to infer the setup and operations via the config in @ceich @serartmar @ddennis @justingrant @donaldev @rcbrown @khola @baffleinc |
Hi I have tested. Notice i have not used the CLI. I don't want to use the hosted-ui - and i would prefer to manually send the facebook token.
My test - using authorization code grantpackage.json
This is my config:
Notice that the scope exist multiple times. This is copy pasted from you example in the #3005 (comment) i uncommented one of them. The user is created in my User Pool, but
I tried loggin in multiple times and i took me through facebook login flow. I getting a I might have change something, but not really sure. I tried deleting the user in my User Pool , it does not recreate the user. Any ideas on why its not working? I am expecting Auth.handleOAuthResponse() to return an idToken i can decode on my server. |
Thanks much for testing @ddennis .
If you are using the older version of
If you want to do this with the new flow then don't pass in tokens to |
Yes as stated i am using your example. For reference, the full code is here: As shown in the previous post, this is package.json
I am experiencing the same as before:I am taken through the facebook login flow. Then redirected back to http://localhost:3000/?code=*****-1e88-44c9-9ce1-bfc19369d5c7&state=*****dAeWGjQ9ozbLKiV.yrLAKTG_S. I getting a 400 after calling Auth.handleOAuthResponse to this url: https://******-testing.auth.eu-central-1.amazoncognito.com/oauth2/token The user is created in my User Pool, but
Nothing is set in localstorage? So my questions:
|
@ddennis did you enable "Authorization code grant" check box for the "userPoolWebClientId" that you have configured on that User Pool? It's under App Integration -> App Client Settings in the Cognito User Pool console. Note the new Amplify CLI does this automatically however if you're using an existing User Pool you'll need to manually do this. |
Yes - my settings is as below. Enabled Identity Providers Allowed OAuth Flows Allowed OAuth Scopes |
Made a video showing my experience: https://www.dropbox.com/s/0ohk2de9gwshv9t/cognito.webm?dl=0 |
Both
|
@undefobj - is there a reason to avoid async/await? Seems clearer to do something like this: const res = await Auth.handleAuthResponse();
try {
const session = await Auth.currentSession();
console.log(" App.js > session = ", session);
} catch (err) {
console.log(" App.js > err = ", err);
} |
@justingrant no reason you can do that too. |
But should't there be data in localstorage? As shown in the video, everything is empty except the query string. And whats causing the Auth.handleOAuthResponse() to throw a 400 It does not make any sense!!! |
@ddennis Thanks for sending your gist. There are a couple things going on that we were able to simplify the beta codebase as well as clarify in our docs:
Here is a CodeSandbox with your endpoint that works: https://codesandbox.io/s/jnn33xzwy5?fontsize=14 |
@undefobj Thanks alot for your time and for helping me with this. I never manged to get the first version to work. I am really curious about why the first version did not work, could it be because the hosted-ui was not working? or did i not enable it? This should be the url of the hosted UI: Thanks again. |
@ddennis excellent glad you have it working. Not sure about the first one, could have been a typo in the redirect URIs inside the console. Also we're working on a big doc update with a concepts section and easier explanation & navigation. If you or anyone else in this thread have any thoughts in the next 24 hours that would be great. Here they are on my fork: |
Hello everyone - We have merged this feature and published it to NPM. The new documentation will be going live tomorrow. |
Does the same apply for React Native? Ive implement the same as above and Im navigating out of the app to verify with facebook
|
Me too, seems OAuth is still broken with react-native (without the hosted UI). |
@chriscraiclabs @davidfarinha the solution works with React Native as well. Please open up a new issue for a team member to help you with troubleshooting as this issue is closed. |
Overview: Based on feedback there is a fair amount of confusion when using User Pools for Social Provider Federation, especially when building a custom UI and bypassing the default Cognito Hosted UI. While Amplify documentation gives an overview of using redirects within the OAuth flow, this is cumbersome, error prone, and seen as difficult by customers who are unfamiliar with these flows. Therefore we wish to build this into Amplify's Auth category via a simple, declarative API. There are several phases and potential future options with different trade-offs which are outlined below.
Please reply with a +1 or detailed comment on a feature if you have specific thoughts around how it should work.
Related Issues:
#1316
#2644
#2543
#2525
#2518
#2512
#2503
#2456
#2423
#2283
#2168
#2156
#2115
#1585
#1521
#1392
#1386
#1281
Phase 1: Add User Pool Federation to federatedSignIn()
Amplify has an
Auth.federatedSignIn()
method today which allows customers to pass tokens to Cognito Identity and retrieve AWS credentials, which are then used to sign requests (with Signature Version 4) to AWS services. Request signing happens automatically when using other Amplify categories.UPDATE: A new value of
federationTarget
will not be needed to the config. Instead in the design we are inferring the behavior from the existing configuration values.Depending on the presence of Cognito User Pool or Identity Pool value passed to
Amplify.configure()
, the call tofederatedSignIn()
will use User Pools or Identity Pools as appropriate passing along the social provider token. In the case where both are present in your configuration, the social provider federation will go to User Pools, and the returned JWT token will be sent to Identity Pools thus federating the User Pool with that Identity Pool and providing AWS credentials to the caller automatically as well.The existing behavior when only using an Identity Pool remains unchanged, and the only required arguments are the provider and token.
UPDATED: When using User Pools, there are no arguments required and provider is optional. If a provider is not given the User Pool Hosted UI will be displayed. If a provider is given the page will redirect to the Hosted UI, but we'll add a query string to signal an immediate redirect to the social provider's login page (Facebook, G+, etc.). This allows you to build your own UI but still leverage the User Pool federation. In either case after the user signs in with that provider an account will be created in User Pools and a JWT token returned.
The user object contains information for you to use when calling
Auth.currentSession()
and returns a CognitoUserSession object. If you do not pass this object we will attempt to automatically populate the name, email, and phone_number attributes from the social provider based on known mechanisms (for example - Facebook requires a call to '/me' to retrieve details after authenticating) but if we are unable to retrieve the attributes we'll populate them as UNDEF.The expiresIn value controls when Amplify will attempt to refresh the token from the social provider, and when the time comes do so automatically behind the scenes. This value was previously required and is now optional as we will default by default attempt to retrieve the attribute from the social token, and if it does not exist we will set it to 1 hour. If you provide a value then Amplify will honor your provided time.
The IdentityID value is strictly for Cognito Identity Pools and allows you to set an Identity ID to retrieve credentials for a specific Cognito Identity ID: https://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/CognitoIdentityCredentials.html#identityId-property
Implementation
Identity Pool federation will stay as-is today, with the only changes being automatic generation of expiresIn logic. For User Pools
Amplify.configure()
will require domain, redirectSignIn, redirectSignOut, and responseType from https://aws-amplify.github.io/docs/js/authentication#configuring-the-hosted-ui. The scope will be optional (for discussion - should this move into the options object?). Note that in the future the Amplify CLI will set all this up see aws-amplify/amplify-cli#766. Under the covers, we will manage the OAuth redirects on behalf of the developer such as the code below, which must be manually called today:We will provide a config option (or another mechanism) for customers to override what "opening a url" means in the different platforms (e.g. using Expo's WebBrowser in React Native).
Potential future Option: Add Federation to signIn() and deprecate federatedSignIn()
We are not doing this as part of this feature work but are including in the RFC to get early opinions for the future
One future option is to take all of the implementation and functionality as above, however we would move this into
Auth.signIn()
instead ofAuth.federatedSignIn()
.PROS: Less APIs to learn, potentially simpler code that is standardized for many situations. Auth codebase could also have a “cascading rule set” depending on config leading to less logic branches.
CONS: This will take a larger effort as it introduces more code complexity into the existing signIn() method. There is also the fundamental question of whether or not the action of “federation” is actually a “sign-in” action (more below in Option 3). We would also need to deprecate the federatedSignIn() method requiring customers to update their code in the future if they upgrade versions. Perhaps the biggest issue though is that there is “no free lunch” and that while the code may become simpler from a customer perspective, you must push the logic somewhere and naturally that would go into
Amplify.configure()
to know what actions to take. This ultimately means that finding the appropriate API setting will be less intuitive.Potential future Option: Introduce a new API for Federation
We are not doing this as part of this feature work but are including in the RFC to get early opinions for the future
All of the implementation and functionality as above, however we introduce a new API in Auth - Auth.XXX.
The reason for this discussion is should federation be an action tied to Login? The Wikipedia definition of federation (https://en.wikipedia.org/wiki/Federation_(information_technology)) has no terms around authentication but rather a “joining” or “association” of separate systems. In the Amplify case that can be either the joining of separate Identity Providers or it can be joining them to a single “logical identity”, ultimately all in order to provide authorization to resources (via OIDC tokens or AWS Credentials). This begs the question is there a more descriptive API such as simply Auth.federate() and, if one exists, is the name so much better that it makes performing these actions that much easier for customers?
The text was updated successfully, but these errors were encountered: