I am trying to set up an Apollo backend for a project I'm working on, where I'm attempting to implement schema directives. However, I am not able to add my schema directive to mutations. So to my main question: How do I implement an auth directive for mutations?
I have added @auth(requires: ADMIN)
to the end of my users query, which is working fine. Apollo will then require a bearer token with admin access for performing the users query.
extend type Query {
user(id: ID!): User
users: [User!]! @auth(requires: ADMIN)
}
When I tried to do it in the same way for the editMyUser mutation, the auth directive seems to be enforced for all the mutations, instead of just the one I wanted. Even the signUp mutation will give "not authorized" error, when I add the @auth part to the editMyUser mutation. Even though there is no relation between them.
The role field which is supposed to be passed to the auth directive when invoked is logging out empty.
extend type Mutation {
signUp(
username: String!
firstName: String
lastName: String
password: String!
isAdmin: Boolean
isActive: Boolean): User!
login(
username: String!
password: String!): User!
editMyUser(
id: ID!
firstName: String
lastName: String
password: String): User! @auth(requires: USER)
adminEditUser(
id: ID!
firstName: String
lastName: String
password: String
isActive: Boolean
isAdmin: Boolean
isBanned: Boolean): User!
}
This is how I implemented the schema directive
export default gql`
directive @auth(requires: Role = ADMIN) on OBJECT | FIELD_DEFINITION
enum Role {
ADMIN
USER
}
https://github.com/jwhenshaw/graphql-directives-auth This is the Auth Directive I've implemented in my code for reference.
So to summarise, when I implement auth directives for mutations they are implemented for all mutations, instead of just the one, and it is not even working correctly, as roles are not passed on to the directive.
I would love to get some help with this. Thanks!
Within that repo the AuthDirective
class passes the objectType
of the field being wrapped into the ensureFieldWrapped
method. What this means is that for your example where you are assigning the directive directly onto a field, editMyUser
, on the object of Mutation
the method is wrapping all the children of Mutation
(I believe the same should be true for your Queries as well actually).
So, within the example repo, this is fine as we have an Object type User
and we wrap it and its fields. However, if you do not wish to do this we can alter the AuthDirective
class to wrap just the field it is on.
I have done this and pushed to the repo, https://github.com/jwhenshaw/graphql-directives-auth, where you can see there is now a FieldAuthDirective
and a ObjectAuthDirective
. I still need to clean the code a bit but pushed a working example and left some logs to help highlight the differences. You can view it here https://qzj70qn2mj.sse.codesandbox.io/ if you don't fancy running it locally.
Hope this helps, let me know if I need to elaborate some more.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With