Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

AppSync: Get user information in $context when using AWS_IAM auth

In AppSync, when you use Cognito User Pools as your auth setting your identity you get

identity: 
   { sub: 'bcb5cd53-315a-40df-a41b-1db02a4c1bd9',
     issuer: 'https://cognito-idp.us-west-2.amazonaws.com/us-west-2_oicu812',
     username: 'skillet',
     claims: 
      { sub: 'bcb5cd53-315a-40df-a41b-1db02a4c1bd9',
        aud: '7re1oap5fhm3ngpje9r81vgpoe',
        email_verified: true,
        event_id: 'bb65ba5d-4689-11e8-bee7-2d0da8da81ab',
        token_use: 'id',
        auth_time: 1524441800,
        iss: 'https://cognito-idp.us-west-2.amazonaws.com/us-west-2_oicu812',
        'cognito:username': 'skillet',
        exp: 1524459387,
        iat: 1524455787,
        email: '[email protected]' },
     sourceIp: [ '11.222.33.200' ],
     defaultAuthStrategy: 'ALLOW',
     groups: null }

However when you use AWS_IAM auth you get

identity:
{ accountId: '12121212121', //<--- my amazon account ID
  cognitoIdentityPoolId: 'us-west-2:39b1f3e4-330e-40f6-b738-266682302b59',
  cognitoIdentityId: 'us-west-2:a458498b-b1ac-46c1-9c5e-bf932bad0d95',
  sourceIp: [ '33.222.11.200' ],
  username: 'AROAJGBZT5A433EVW6O3Q:CognitoIdentityCredentials',
  userArn: 'arn:aws:sts::454227793445:assumed-role/MEMORYCARDS-CognitoAuthorizedRole-dev/CognitoIdentityCredentials',
  cognitoIdentityAuthType: 'authenticated',
  cognitoIdentityAuthProvider: '"cognito-idp.us-west-2.amazonaws.com/us-west-2_HighBob","cognito-idp.us-west-2.amazonaws.com/us-west-2_HighBob:CognitoSignIn:1a072f08-5c61-4c89-807e-417d22702eb7"' }

The Docs says that this is expected, https://docs.aws.amazon.com/appsync/latest/devguide/resolver-context-reference.html . However, if you use AWS_IAM connected to Cognito (which is required to have unauthenticated access), how are you supposed to get at the User's username, email, sub, etc? I need access to the user's claims when using AWS_IAM type Auth.

like image 751
honkskillet Avatar asked Apr 29 '18 10:04

honkskillet


People also ask

Can AppSync call API gateway?

And thanks to AWS signatures this can happen in a secure way: AppSync can call the API as it can use an IAM Role with the necessary permissions, but for the public it's not available. In this article, we'll see how to configure AppSync to send a signed request to an API Gateway HTTP API using the HTTP data source.

How do I query AWS AppSync?

In the AWS AppSync console choose the Queries tab on the left hand side. The pane on the right side enables you to click through the operations, including queries, mutations, and subscriptions that your schema has exposed. Choose the Mutation node to see a mutation.

Where does AppSync store data?

Application data is stored at rest in your AWS account and not in the AWS AppSync service. You can protect access to this data from applications by using security controls with AWS AppSync including AWS Identity and Access Management (IAM), as well as Amazon Cognito User Pools.

What is resolver in AppSync?

Data sources and resolvers are how AWS AppSync translates GraphQL requests and fetches information from your AWS resources. AWS AppSync has support for automatic provisioning and connections with certain data source types.


1 Answers

For making User's username, email, sub etc. accessible through AppSync API, there's an answer for that: https://stackoverflow.com/a/42405528/1207523

To sum it up, you want to send User Pools ID token to your API (e.g. AppSync or API Gateway). Your API request is IAM authenticated. Then you validate the ID token in a Lambda function and now you have your validated IAM user and User Pools data together.

You want to use the IAM's identity.cognitoIdentityId as primary key for you User table. Add the data included in ID token (username, email, etc.) as attributes.

This way you can make user's claims available through you API. Now, for example, you can set $ctx.identity.cognitoIdentityId as the owner of an item. Then maybe other users can see the name of the owner via GraphQL resolvers.

If you need to access the user's claims in your resolver I'm afraid that doesn't seems to be possible at the moment. I have made a question about this as it would be very helpful for authorization: Group authorization in AppSync using IAM authentication

In this case, instead of using a resolver you could use Lambda as a data source and retrieve the user's claims from the above-mentioned User table.

It's all a bit difficult at the moment :)

like image 130
Mikael Lindlöf Avatar answered Oct 21 '22 15:10

Mikael Lindlöf