GraphQL - Global field resolvers

Viewed 253

Say I have the following schema:

type CodeName {
  code: Int!
  name: String!
}

type Person {
  id: Int!
  weapon: Weapon
  hat: Hat
  codeName: CodeName!
}

type Weapon {
  id: Int!
  type: String!
  codeName: CodeName!
}

type Hat {
  id: Int!
  size: Int!
  codeName: CodeName!
}

type Query {
  Person(id: Int!): Person!
  Weapon(id: Int!): Weapon!
  Hat(id: Int!): Hat!
}

then, I would define my resolvers like so:

const resolvers = {
  Weapon: {
    codeName: CodeNameResolver,
  },
  Hat: {
    codeName: CodeNameResolver,
  },
  Person: {
    codeName: CodeNameResolver,
    weapon: WeaponResolver,
    hat: HatResolver
  },
  Query: {
    Person: PersonResolver,
    Weapon: WeaponResolver,
    Hat: HatResolver,
  }
}

However, I have to repeat codeName: CodeNameResolver multiple times in the code, every time I have a field whose type is CodeName.
Is there a way to use a global field resolver, or type resolver, so that I don't have to do that?

1 Answers

If your resolver functions are identical, then you're about as DRY as you're going to get. GraphQL doesn't have a mechanism for globally specifying a resolver based on the field's type.

You could potentially accomplish this using graphql-middleware

const codeNameMiddleware = async (resolve, root, args, context, info) => {
  if (info.returnType.toString() === 'CodeName!') {
    // resolve the field here
    return someValue
  }
  return resolve(root, args, context, info)
}

You should be cautious when applying this sort of pattern, though. A field's type only describes the shape of the data it returns -- it says nothing about how that data is fetched. Even if all your resolvers for CodeName fields look the same now, that may not be the case in the future.

Related