An app is communicating via the Open ID Connect protocol with AWS Cognito, which is connected to ADFS, communicating via SAML. Cognito is essentially "proxying" the ADFS server.
ADFS holds a group mapping that the app requires, and I would like to import these groups into Cognito as actual Cognito Group - which will then be read by the app from the cognito:groups from the ID-token Cognito provides.
In the AWS Cognito User Pool setup, I don't see a way to map ADFS groups to Cognito Groups - must I absolutely rely on a custom attribute for my User Pool that I can map to the ADFS-property, or am I missing some piece of configuration that allows Cognito to create new groups on the fly and automatically assign the users to the groups in Cognito?
edit: To clarify, Is it possible to setup Cognito to add/create groups (not as a custom property, but a actual manageable cognito groups) when it imports users?
I had the same issue, and I have not found a static mapping option in Cognito either.
The only way I see is to map the AD groups to custom:adgroups attribute in Cognito, and set up a Cognito "Pre Token Generation" lambda trigger. The lambda reads the value of the custom:adgroups and manually overrides the user's Cognito groups.
NB - this does not change the cognito user's group permanently, only for the current session, but from the application perspective that's exactly what I needed.
Please see a dummy static (non conditional) ADMIN group assignment example here:
def lambda_handler(event, context):
print(f'incoming event: {json.dumps(event)}')
# manual cognito group override
if event['triggerSource'] == "TokenGeneration_HostedAuth":
event['response'] = {
"claimsOverrideDetails": {
"groupOverrideDetails": {
"groupsToOverride": [
"ADMIN"
]
}
}
}
return event
More detailed documentation here: https://docs.aws.amazon.com/cognito/latest/developerguide/user-pool-lambda-pre-token-generation.html
Could you use the Post authentication Lambda trigger to update the user's group in the Cognito User Pool based off the group in AD? You could use the APIs: AdminAddUserToGroup and AdminRemoveUserFromGroup. The only issue with this approach is that if you change the user's group in AD, it won't be updated in Cognito until the user authenticates to Cognito again.
How to setup ADFS with Cognito is documented in this link. The section answering your question is the mapping in step 4, item 5. I'm copying the relevant text below:
Choose Attribute mapping. These mappings map the claims from the SAML assertion from AD FS to the user pool attributes.
Make sure that ADFS is sending the groups in the assertions. For setting up the ADFS side for groups this link might be useful.
You could debug the flow with SAML-tracer plugin in Firefox.
Related
We have an existing system where we create the user id (db) internally and use it across db tables as refrential integrity. We are looking to move to Cognito and Api Gateway for authentication and authorization flow. However, we would like to retain the existing identity (user id in db) internally once we authenticate at Api Gateway using Cognito. To do this, we are thinking of using Pre-Signup Lambda trigger to first create the user in our system via that and then Cognito will create the user in the userpool. This way we can associate custom attribute (user id) information using Pre-Token generation lambda which will be passed to Api Gateway with ID Token.
Is this the right approach to create the user first in our system (via Pre-Signup lambda) and then in Cognito?
I installed a vault and configured OIDC with gsuite, that was already an adventure in itself as the documentation is limited and even wrong at more than one place.
Finally I have a working authentication with my google accounts and I began to create roles, and there I saw a huge issue. How do you restrict google users from using a role. Let's say I create a gsuite-admin role that has access to all of vault administration, any user entering the role before login can assume it.
I tried to use the different claims but those seems to be only for vault created groups or other things.
Does anyone has a solution for that?
Thank you in advance.
EDIT:
The configuration I'm using whith group claims:
{
“allowed_redirect_uris”: “https://URL/ui/vault/auth/oidc/oidc/callback,http://localhost:8250/oidc/callback”,
“user_claim”: “sub”,
“policies”: “vault_admin”,
“ttl”: “24h”,
“groups_claim”: “devops”,
“oidc_scopes”: “profile”,
“bound_claims”: {
“group”: [“devops”]
}
}
That configuration only provides a lock of the role that can't be used anymore by anyone. From what I could see the JWT doesn't have any informations and that is why we used the config with the fetchgroup option in the oidc configuration.
I found a solution for this problem. Firstly, we need to ensure that a user is part of a G Suite group. Then mapping the G Suite group with Vault group (that has a policy assigned) ensures that the user is bound to the Vault policy.
This article contains some example steps and might be helpful.
Any Cognito User Pool gurus out there? I've been using Cognito for a while now but this one has me a bit stumped.
We allow users to sign up and sign in using social accounts like Facebook which are set up as Identity Providers in the User Pool.
Users need to complete a custom registration form before they can use the main app - we don't use the hosted UI for login or signup
One step of the custom registration process allows the user to indicate which social provider then want to use
This allows us to pull back the users email, first and last names from the social provider which is great - we use a cognito client and callback to do this currently
But in doing so, this provisions a user within the Userpool before the registration process is complete - in fact this makes sense- in order for Cognito to provide us the user info it needs to have called into the social providers /userinfo endpoint to populate the user data
So, the issue we now have is that whilst the user is half way through the registration process I have a confirmed user account - eg. before the user has completed the registration process
This is an issue because a user could sign into the the app using their social login without ever have completed the registration process
So as I see it I have two options:
PostConfirmation Lambda trigger which uses the cognito-idp SDK to disable the user just after it was confirmed
Don't use Cognito to obtain the user info like firstname, lastname, email, picture etc - however this would require us to write a solution for every current and future social provider which isn't something I'm keen on
Am I missing something obvious?
Thanks in advance!
I would say PostConfirmation Lambda trigger is a good approach - however instead use adminDisableProviderForUser to disable the user from signing in with the specified external (SAML or social) identity provider
adminDisableProviderForUser
You can later call adminLinkProviderForUser to link the existing user account in the user pool to the external identity provider.
adminLinkProviderForUser
An alternative solution is to prevent the user from signing in if they have not fully completed the registration process via a Pre Authentication Lambda Trigger checking for a unique identifier with respect to your completed registration process
The simplest solution in the end for us was a Pre Token Generation Trigger in Cognito like this:
exports.handler = async (event) => {
if(event.triggerSource==="TokenGeneration_HostedAuth") {
//check db/api etc to see if we have a valid registration stored for user
if(!hasCompletedRegistration) {
//throw auth exception which we can catch on the frontend to inform user
throw new Error("REGISTRATION_NOT_COMPLETE")
}
}
return event
};
For username/password sign ins the TriggerSource will be TokenGeneration_Authentication
For federated/social sign ins the TriggerSource will be TokenGeneration_HostedAuth
I have a Cognito Identity Pool set up to use a Cognito user pool as a source of identity. Now, in my case the Cognito User Pool has 2 different client id, one for my mobile application and one for my website. In order to support login from both I need to add both client ids in the Authentication Providers settings but it seems that you can add only 1 client id at a time. Is there a way to configure Cognito Identity Pool to accept 2 different Cognito Pool client IDs?
I don't wanna use the same client id cause I need to do different user validations on user sign-up based on where the user came from (app or web) and the client id is the only parameter passed to my lambda that allows me to identify from where a user came from.
From the Identity Pool Cloudformation docs, it looks like you can provide a list of identity providers. A user pool identity provider is defined as the user pool ID plus the client ID. It seems like you should be able to specify two different ones with the same user pool ID and different client IDs. I don't know whether this is possible through the console.
I have a web application where people can upload files and I want a login for this so some functions can only be accessed by people who are logged in. I want to have one fixed pair of username and password, so there should be no option for users to create their own account (only the people who have the right information can access). I have a login paige where I proof with JavaScript if the fields are filled and if they are there should be invoked a lambda function to set the user to auth in Cognito to login. I created a fixed user in Cognito with username and password and I now want to proof if the entries of the fields are the same like the created user so that the user is logged in and can use the functions on the web app.
I read a lot of tutorials how to set up an authentication with cognito and lambda, but totally different to what I want to do. So I really have no idea how I can write the lambda function to do what I want.
Has anyone an idea how I can build up my plan or is it a bad idea like that?
Thank you for your help
you don't need the user/pass, in api gateway in the lambda method set the auth type to AWS_IAM, so only auth users will be able to call the lambda method... and then only that specific user will be able to call your lambda method.
inside the lambda method you can access
event.requestContext.identity.cognitoAuthenticationProvider
and
event.requestContext.identity.cognitoIdentityId
to get the user that was auth by AWS