graphql.mjs 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122
  1. import { devAssert } from './jsutils/devAssert.mjs';
  2. import { isPromise } from './jsutils/isPromise.mjs';
  3. import { parse } from './language/parser.mjs';
  4. import { validateSchema } from './type/validate.mjs';
  5. import { validate } from './validation/validate.mjs';
  6. import { execute } from './execution/execute.mjs';
  7. /**
  8. * This is the primary entry point function for fulfilling GraphQL operations
  9. * by parsing, validating, and executing a GraphQL document along side a
  10. * GraphQL schema.
  11. *
  12. * More sophisticated GraphQL servers, such as those which persist queries,
  13. * may wish to separate the validation and execution phases to a static time
  14. * tooling step, and a server runtime step.
  15. *
  16. * Accepts either an object with named arguments, or individual arguments:
  17. *
  18. * schema:
  19. * The GraphQL type system to use when validating and executing a query.
  20. * source:
  21. * A GraphQL language formatted string representing the requested operation.
  22. * rootValue:
  23. * The value provided as the first argument to resolver functions on the top
  24. * level type (e.g. the query object type).
  25. * contextValue:
  26. * The context value is provided as an argument to resolver functions after
  27. * field arguments. It is used to pass shared information useful at any point
  28. * during executing this query, for example the currently logged in user and
  29. * connections to databases or other services.
  30. * variableValues:
  31. * A mapping of variable name to runtime value to use for all variables
  32. * defined in the requestString.
  33. * operationName:
  34. * The name of the operation to use if requestString contains multiple
  35. * possible operations. Can be omitted if requestString contains only
  36. * one operation.
  37. * fieldResolver:
  38. * A resolver function to use when one is not provided by the schema.
  39. * If not provided, the default field resolver is used (which looks for a
  40. * value or method on the source value with the field's name).
  41. * typeResolver:
  42. * A type resolver function to use when none is provided by the schema.
  43. * If not provided, the default type resolver is used (which looks for a
  44. * `__typename` field or alternatively calls the `isTypeOf` method).
  45. */
  46. export function graphql(args) {
  47. // Always return a Promise for a consistent API.
  48. return new Promise((resolve) => resolve(graphqlImpl(args)));
  49. }
  50. /**
  51. * The graphqlSync function also fulfills GraphQL operations by parsing,
  52. * validating, and executing a GraphQL document along side a GraphQL schema.
  53. * However, it guarantees to complete synchronously (or throw an error) assuming
  54. * that all field resolvers are also synchronous.
  55. */
  56. export function graphqlSync(args) {
  57. const result = graphqlImpl(args); // Assert that the execution was synchronous.
  58. if (isPromise(result)) {
  59. throw new Error('GraphQL execution failed to complete synchronously.');
  60. }
  61. return result;
  62. }
  63. function graphqlImpl(args) {
  64. // Temporary for v15 to v16 migration. Remove in v17
  65. arguments.length < 2 ||
  66. devAssert(
  67. false,
  68. 'graphql@16 dropped long-deprecated support for positional arguments, please pass an object instead.',
  69. );
  70. const {
  71. schema,
  72. source,
  73. rootValue,
  74. contextValue,
  75. variableValues,
  76. operationName,
  77. fieldResolver,
  78. typeResolver,
  79. } = args; // Validate Schema
  80. const schemaValidationErrors = validateSchema(schema);
  81. if (schemaValidationErrors.length > 0) {
  82. return {
  83. errors: schemaValidationErrors,
  84. };
  85. } // Parse
  86. let document;
  87. try {
  88. document = parse(source);
  89. } catch (syntaxError) {
  90. return {
  91. errors: [syntaxError],
  92. };
  93. } // Validate
  94. const validationErrors = validate(schema, document);
  95. if (validationErrors.length > 0) {
  96. return {
  97. errors: validationErrors,
  98. };
  99. } // Execute
  100. return execute({
  101. schema,
  102. document,
  103. rootValue,
  104. contextValue,
  105. variableValues,
  106. operationName,
  107. fieldResolver,
  108. typeResolver,
  109. });
  110. }