UniqueDirectiveNames.js.flow 1.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455
  1. // @flow strict
  2. import { GraphQLError } from '../../error/GraphQLError';
  3. import { type ASTVisitor } from '../../language/visitor';
  4. import { type SDLValidationContext } from '../ValidationContext';
  5. export function duplicateDirectiveNameMessage(directiveName: string): string {
  6. return `There can be only one directive named "${directiveName}".`;
  7. }
  8. export function existedDirectiveNameMessage(directiveName: string): string {
  9. return `Directive "${directiveName}" already exists in the schema. It cannot be redefined.`;
  10. }
  11. /**
  12. * Unique directive names
  13. *
  14. * A GraphQL document is only valid if all defined directives have unique names.
  15. */
  16. export function UniqueDirectiveNames(
  17. context: SDLValidationContext,
  18. ): ASTVisitor {
  19. const knownDirectiveNames = Object.create(null);
  20. const schema = context.getSchema();
  21. return {
  22. DirectiveDefinition(node) {
  23. const directiveName = node.name.value;
  24. if (schema && schema.getDirective(directiveName)) {
  25. context.reportError(
  26. new GraphQLError(
  27. existedDirectiveNameMessage(directiveName),
  28. node.name,
  29. ),
  30. );
  31. return;
  32. }
  33. if (knownDirectiveNames[directiveName]) {
  34. context.reportError(
  35. new GraphQLError(duplicateDirectiveNameMessage(directiveName), [
  36. knownDirectiveNames[directiveName],
  37. node.name,
  38. ]),
  39. );
  40. } else {
  41. knownDirectiveNames[directiveName] = node.name;
  42. }
  43. return false;
  44. },
  45. };
  46. }