I would like to use only Cognito User Pool, and therefore I want to use identity federation with Cognito User Pools, without Cognito Federated Identities (identity pools).
I have followed the documentation, but I couldn't succeed.
http://docs.aws.amazon.com/cognito/latest/developerguide/cognito-user-pools-social.html
Her is my User Pool configuration.
How can I combine Google and Cognito in User Pool without using identity pool (Federated Identities). Or is that possible?
Based on your comment to Summer Guo, here's what it seems like you're having an issue with...
A lot of details missing here, but if you're using a Cognito Authorizer in your API Gateway, then it doesn't know about any 3rd party IdP -- it just knows about your Cognito User Pool. So sending the CUP JWT will work, while sending anything else won't. If you want to use a Google auth token, then you need to implement a Custom Authorizer that verifies this token with Google.
I presented on this topic during reInvent. Here's the video that goes into the details:
https://www.youtube.com/watch?v=VZqG7HjT2AQ
it is possible to have a user pool with google configured as an identity provider without using Cognito Federated Identities. Cognito has SDKs available for Android, iOS, and Javascript, you can find them on github(https://github.com/aws/). Can you be more specific about the problem you are running into when trying to do this?
Looks like they only allow User Pool Federation with their own UI/SDK. What I ended up doing for react-native was
get facebook token
sign up the user into the user pool with a custom attribute to track facebook Id and generic password
use the temporary credentials (need to setup IAM for cognito user pool - adminMovetoGroup to move the user into the auto created user pool federated group.
create lambda function to auto-confirm the end user.
This way the user can log in and get credentials using federated identities, but then they also have an account in the event they stop using facebook. They would also need to reset their password.
If you are using your own Custom UI, you will need to create a button/anchor to redirect to the user.
This is what I use to create a url (JS Code):
`https://${domain}/oauth2/authorize`,
`?redirect_uri=${redirectSignIn}`,
`&response_type=${responseType}`,
`&client_id=${userPoolWebClientId}`,
`&identity_provider=${providerName.toString()}`
providerName is either Facebook/Google
responseType is either token/code
domain your domain in cognito userpool config
redirectSignIn your redirect sign in in Cognito User Pool Config
You will need to call window.location.assign({the url generated above}). When user clicks the button, it will redirect to either Facebook/Google page asking for Account/Permission.
As for as I know, Facebook/Google dialog for custom UI is not yet supported.
Example code from AWS Amplify
import { Auth } from 'aws-amplify';
const config = Auth.configure();
const {
domain,
redirectSignIn,
redirectSignOut,
responseType } = config.oauth;
const clientId = config.userPoolWebClientId;
// The url of the Cognito Hosted UI
const url = 'https://' + domain + '/login?redirect_uri=' + redirectSignIn + '&response_type=' + responseType + '&client_id=' + clientId;
// Launch hosted UI
window.location.assign(url);
Link: https://aws-amplify.github.io/docs/js/authentication
Another thing, you can link federated identity to a user pool account.
https://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/CognitoIdentityServiceProvider.html#adminLinkProviderForUser-property
Related
We are trying FusionAuth & looking to have a single step flow for Sign up + Sign In.
After user signs up, we want to show/land him directly to our application's dashboard page (without showing him login page in between the flow). The authentication should happen but internally i.e we are expecting OAuth2 standard IdToken in response to "WebApplication" so that web application can use IdToken to allow user to application.
Please note that we don't want to use approaches where we need to pass Username/password to our web application, don't want to handle user credentials. Also that we dont want to use Authentication Tokens returned in Registration flow because AuthenticationTokens are not that secure, looking to use OAuth2 based IdToken instead.
I have came across this post "https://fusionauth.io/community/forum/topic/165/taking-a-user-directly-to-the-registration-page/3" and tried following request, but it is showing Login page instead of registration.
/oauth2/register?client_id=<Configured_client_id>&redirect_uri=<Configured_redirect_uri>&response_type=code
(I have not used CSRF parameter though)
Please can you suggest why its showing Login Page?
You should be able to have a user register and be sent directly to your application, as long as you set the correct redirect_uri and put that on the registration URL:
https://local.fusionauth.io/oauth2/register?client_id=c50329fa-93e5-4618-8d9f-73d0ab069a23&response_type=code&redirect_uri=https%3A%2F%2Fapp.example.com%2F
The application will then receive a code that can be exchanged for an access token. You can call the userinfo endpoint with that token and get user information like email address, etc.
What you won't get that it seems like you might want is an id token. For that you'll have to send the user through the login process with a scope of profile. However, you could mind your own 'id token'-lite using the values from the userinfo endpoint and the JWT vending: https://fusionauth.io/docs/v1/tech/apis/jwt/#vend-a-jwt
I am developing a python application whose purpose is to upload data to S3. Since it must be installed on different devices independently, I wouldn’t want store aws credentials on every platform but I want to create an authentication method based on Amazon Cognito.
It is necessary a login method based on username and password, so the user must be authenticated before being authorized to upload files.
I've created a Users Pool and Identity Pool and this is the pattern I want to follow:
This is the code I wrote to authenticate user:
import os
import boto3
username = "user1997"
password = "abcd1234!!"
client = boto3.client("cognito-idp", region_name="ap-south-1")
response = client.initiate_auth(
ClientId=os.getenv("COGNITO_USER_CLIENT_ID"),
AuthFlow="USER_PASSWORD_AUTH",
AuthParameters={"USERNAME": username, "PASSWORD": password},
)
access_token = response["AuthenticationResult"]["AccessToken"]
But I don't know how to use access_token to get temporary credentials from Identity Pool.
Access token isn't what you want here. You can use the identity token with get_id and get_credentials_for_identity calls to finally get temporary AWS credentials. For Example:
identityId = identity.get_id(
IdentityPoolId='us-east-1:xyxyxyxy-ab23-9989-7767-776x7676f5',
Logins={
'cognito-idp.us-east-1.amazonaws.com/us-east-1_xxxxxxx': id_tok
}
)['IdentityId']
aws_cred = identity.get_credentials_for_identity(
IdentityId=identityId,
Logins={
'cognito-idp.us-east-1.amazonaws.com/us-east-1_xxxxxxx': id_tok
}
)['Credentials']
aws_cred will have access key, secret key and session token. You can use these to sign AWS calls.
client type: Spa
grant type: implicit or code(pkce)
As a user, I want to be able to get silently authenticated if I have already logged with my identity provider. If not stay on the client side just like a guest user. And if I want to login to the client I should be able to get authenticated manually through the login page.
This has both manual sign-in and automatic sign-in scenarios. How would you handle such cases in Open ID Connect?
By adding the prompt=none in client settings will silently get a new token if user has a valid session. But if not I want the user to be able to manually authenticate through the login page upon his/her wish.
If I set prompt=none this will never have any user interaction such as authentication.
tags: Silent authentication oidc, automatic login, SSO
It is quite a deep subject, and the flow typically works like this:
CLASSIC OIDC SOLUTION
User is redirected for each SPA
If signed in already at the IDP there is no login prompt
OAuth state is stored in local storage (though it is recommended to only store actual tokens in memory)
When an access token expires (or before) do an iframe token renewal with prompt=none
When a new browser tab is opened do an iframe token renewal to get tokens for that tab - to avoid a full redirect
When the user logs out remove OAuth state from local storage
The most widely used library is OIDC Client which will do a lot of the hard work for you. See also my blog post + code sample for how this looks visually.
PROBLEM AREAS
It is worth being aware also that iframe silent renewal does not work by default in the Safari browser in 2020. Some notes on this here.
Alternatively, you can use signinSilent(). I have used it on my login page ngOnInit (since AuthGuard will anyway redirect the user to login, I thought it will be the perfect place in my scenario).
// login.ts
ngOnInit(): void {
this.authService.signinSilent().then(_ => {}).catch(_ => {});
}
// authService
public signinSilent() {
return this.userManager.signinSilent();
}
signinSilent method will return the user object if user already has a valid session with idp. else it will throw an error, probably login_required.
I am developing an Angular2 app which uses auth0 for authentication. I used the auth0 lock widget to authenticate users.
Now, I want to use auth0-js instead of the lock widget for authentication. I followed this guide to add auth0-js to the app.
After adding auth-js, when a new user tries to log in to the app, Auth0 displays following consent screen to the user.
I want the users to be able to directly access my app, without needing to accept a consent screen. The consent question asked in this dialog can be confusing to users since it mentions about tenants.
When I searched for a solution, the solution mentioned in various places was to make the client a first party client. But, I cannot find any place in the management console to make the client a first party client.
How can I disable this consent screen?
Following is the auth-js config I used in the app.
auth0 = new auth0.WebAuth({
clientID: 'my_client_id',
domain: 'my_domain.auth0.com',
responseType: 'token id_token',
audience: 'https://my_domain.auth0.com/userinfo',
redirectUri: window.location.origin + '/auth_loading',
scope: 'openid'
});
In Auth0 Dashboard, under APIs -> Auth0 Management API -> Settings (tab)
If you are using a specific audience for a Resource API you have defined yourself in the Dashboard, then there is a similar Allow Skipping User Consent toggle for that particuar API. Use that. audience specifies the target API for your access token. If you don't want to call a specific API, keep it set to https://my_domain.auth0.com/userinfo
Re. question about First Party. If you created your client in the Auth0 Dashboard, then it is Firsty Party by default. Only first-party clients can skip the consent dialog, assuming the resource server they are trying to access on behalf of the user has the "Allow Skipping User Consent" option enabled. The Auth0 Dashboard does not offer a flag for this, but if you use the Auth0 Management API v2 Get Clients endpoint, then you will see the flag (boolean) value listed for your client eg.
"is_first_party": true
See https://auth0.com/docs/api/management/v2#!/Clients/get_clients for details.
Finally, please note the following: https://auth0.com/docs/api-auth/user-consent#skipping-consent-for-first-party-clients - in particular note that consent cannot be skipped on localhost. As per the docs (link above), During development, you can work around this by modifying your /etc/hosts file (which is supported on Windows as well as Unix-based OS's) to add an entry such as the following:
127.0.0.1 myapp.dev
I am setting up my own CAS. A authentication handler was written and username/password are authenticated against a MySQL db. I also add signup page and related logic.
Now I would like to let user automatically log on when he/she has registered as a user. How to achieve this?
The comment above is incorrect - CAS clients do not have access to the cookie, only the CAS Server does - CAS is not a shared-cookie protocol.
If you only have a single site, you can just create a session on the client, using the standard mechanisms for Java, Ruby, whatever platform you're using.
If you want to create an SSO session for login to multiple applications, basically you need to:
Create a SSO session (via the CAS server)
Redirect to the CAS Server
Have the user redirected back to your application.
To accomplish the first one, you likely will want to modify the CAS LoginFlow to allow you to authenticate the user, either via one-time token or a similar mechanism.
Here is my implementation. The idea is borrowed from class org.jasig.cas.web.flow.AuthenticationViaFormAction.
In my web controller handling unlock request which is often from a registration email of a new user.
String oneTimeAuthToken = this.userManager.generateOneTimeAuthToken(userEmail);
UsernamePasswordCredentials credentials = new UsernamePasswordCredentials();
credentials.setUsername(userEmail);
credentials.setPassword(oneTimeAuthToken);
String tgt = centralAuthenticationService.createTicketGrantingTicket(credentials);
ticketGrantingTicketCookieGenerator.addCookie(request, response, tgt);
log.debug("Current user was unlocked and logged in.");
The fundamentals behind this is to create a temp password-like token to authenticate. Of course, userManager should clear this token automatically once authentication is successful.
Hope this is clear. Let me know if you observe anything wrong.