2
votes

I have a simple graphql query and a directive

directive @isOwner(postID: String!) on FIELD_DEFINITION

type Query {
  post(postID: String!): Post! @isOwner(postID: postID)
}

The problem is that I'm using GQLGen to generate my boilerplate code for Go, and directives are treated differently from the input values. This presents a unique challenge where authorization logic is almost isolated from the actual db reads, which makes the logic very inefficient, in that I have to eiither make a database read twice: during validation and the actual db read. The data required for validation is also required for the db read, and I would have to edit my whole code to inject this data into context. Is there a way of passing the input arguements dynamically to the directive and have the validation done dynamically and is it a good pracise in the first place?

1

1 Answers

1
votes

Arguments passed to schema directives are evaluated when your schema is initially built, so they can't be dynamic. In this particular case, you don't need an argument at all -- you can just read the value of the field's arguments.

visitFieldDefinition(field) {
  const { resolve = defaultFieldResolver } = field
  field.resolve = async function (parent, args, context, info) {
    console.log(args.postID)    

    return resolve.apply(this, [parent, args, context, info])
  }
}

However, if the name of the argument varies by field, then you can pass that as an argument to your directive

directive @isOwner(argName: String!) on FIELD_DEFINITION
visitFieldDefinition(field) {
  const { resolve = defaultFieldResolver } = field
  const { argName } = this.args
  field.resolve = async function (parent, args, context, info) {
    console.log(args[argName])    

    return resolve.apply(this, [parent, args, context, info])
  }
}