Amplify-cli: GraphQL SDL: Access type properties within @auth header

Created on 4 Sep 2018  路  8Comments  路  Source: aws-amplify/amplify-cli

Do you want to request a feature or report a bug?
Feature request

What is the current behavior?
Users are unable to access the properties of the type when setting @auth rules, etc.

What is the expected behavior?
Would be nice if users could, for example, allow only users who are in a group that is listed in the object's properties, could read or perform mutations on the object, like this:

type Posts 
  @model 
  @auth(rules: [
      {allow: groups, groups: this.groups, mutations: [create, update, delete]} // this line
    ])
{
  id: ID!
  name: String
  groups: [String]!
}

This way, if the Post had a group named Admin listed, then only users who were in the Admin group could interact with it. Ideally, if at least one group matched then the user would have access.

It may also be worth looking into allowing access to user attributes in the @auth header (if there is not already), citing the limit of 25 groups/Cognito User Pool.

References
https://stackoverflow.com/questions/52133847/graphql-access-type-properties-within-auth-header/52159490#52159490

feature-request graphql-transformer

All 8 comments

Hey you actually can do this already using the groupsField argument passed to @auth. Search for "Dynamic Group Auth" on this page https://github.com/aws-amplify/amplify-cli/blob/master/graphql-transform-tutorial.md

@mikeparisstuff That's so cool, I can't believe I missed that.ill search that document for this is next question when I get to my desk soon, but so we also have access to user attributes there?

There is a similar "ownerField" concept for owner auth. Note: lists of owners are not yet supported however lists when using the "groupsField" are supported.

@mikeparisstuff copy that, I appreciate the help. I saw that but I'm afraid it just won't fit my use case. I'm designing a loosely multi-tenant system and 25 groups just isn't enough. Suppose I'll have to use some lambdas as the resolvers and read a DynamoDB table of users with their corresponding groups.

This is a fair bit more complexity and overhead, but I don't see a way around it, unless you have another suggestion?

You can implement groups and manage group membership yourself using @models & @connection but it takes a little designing. We haven't implemented many to many out of the box yet but you can implement it yourself using two one-to-many connections and a joining @model.

@mikeparisstuff Thanks again for the great information. However, I must be missing something. I know that I can implement the relationship between users and groups in the schema, but how would I go about enforcing access via these models in the schema? I'll continue to dig through the documentation to try to find the missing pieces.

EDIT: I was reading your comment in the wrong context, but I'm tracking what you're saying now. You're saying to use the relationship itself as the access control. I'll go ahead and try to model this out, but with a complex relationship of models it'll definitely take some work, just like you said.

Something like this:

Organization:

  • Many Users
  • Many Products

User

  • One Organization
  • Many Products

Product

  • One Organization
  • Many Users

@nickdb93 Closing this issue, for now, feel free to re-open this if the problem still persists.

So if I was to do a dynamic group / roles system:

type Post @model @auth(rules: [{allow: groups, groupsField: "groups"}]) { id: ID! title: String groups: [String] }

The groups: [String] => why couldn't this store the Cognito user ID?

Something like this?

type Group @model @auth(rules: [ {allow: owner, ownerField: "owner", mutations: [create, update, delete], queries: [get, list]}, {rules for admins}, {rules for mods}, {rules for members} ]) { id: ID! title: String owner: Cogintio user ids admins: [Cogintio user ids] mods: [Cogintio user ids] members: [Cognito user ids] }

This wouldn't have to use the Coginto groups which is limited to 25. We can just store the IDS in the table.

I am doing a dynamic group / member system. like a social network. Members can belong to many groups with different roles for each group.

So I been able to grab the coginto user and save a profile, but I can't save the Coginto sub as the ID in the user table. So is there a way around that? I have to let the ID be generated and save the sub as another field.

Was this page helpful?
0 / 5 - 0 ratings