-
Notifications
You must be signed in to change notification settings - Fork 1.8k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
4 changed files
with
213 additions
and
24 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,184 @@ | ||
/** | ||
* Inlined GraphQL printer, | ||
* forked from https://github.com/graphql/graphql-js/blob/v15.3.0/src/language/printer.js | ||
* | ||
* This ensure compatibility with document hash generated by the Relay compiler. | ||
* graphql-js' printer is incompatible with Relay's one since v15.4 | ||
* | ||
* TODO: Canonicalize printer spec for Relay projects | ||
* | ||
* @see https://github.com/facebook/relay/pull/3628 | ||
* @see https://github.com/facebook/relay/issues/4226 | ||
*/ | ||
|
||
const { visit } = require('graphql'); | ||
|
||
/** | ||
* Converts an AST into a string, using one set of reasonable | ||
* formatting rules. | ||
*/ | ||
function print(ast: any): string { | ||
return visit(ast, { leave: printDocASTReducer }); | ||
} | ||
|
||
const printDocASTReducer: any = { | ||
Name: (node) => node.value, | ||
Variable: (node) => '$' + node.name, | ||
|
||
// Document | ||
|
||
Document: (node) => join(node.definitions, '\n\n') + '\n', | ||
|
||
OperationDefinition(node) { | ||
const op = node.operation; | ||
const name = node.name; | ||
const varDefs = wrap('(', join(node.variableDefinitions, ', '), ')'); | ||
const directives = join(node.directives, ' '); | ||
const selectionSet = node.selectionSet; | ||
// Anonymous queries with no directives or variable definitions can use | ||
// the query short form. | ||
return !name && !directives && !varDefs && op === 'query' | ||
? selectionSet | ||
: join([op, join([name, varDefs]), directives, selectionSet], ' '); | ||
}, | ||
|
||
VariableDefinition: ({ variable, type, defaultValue, directives }) => | ||
variable + | ||
': ' + | ||
type + | ||
wrap(' = ', defaultValue) + | ||
wrap(' ', join(directives, ' ')), | ||
SelectionSet: ({ selections }) => block(selections), | ||
|
||
Field: ({ alias, name, arguments: args, directives, selectionSet }) => | ||
join( | ||
[ | ||
wrap('', alias, ': ') + name + wrap('(', join(args, ', '), ')'), | ||
join(directives, ' '), | ||
selectionSet, | ||
], | ||
' ', | ||
), | ||
|
||
Argument: ({ name, value }) => name + ': ' + value, | ||
|
||
// Fragments | ||
|
||
FragmentSpread: ({ name, directives }) => | ||
'...' + name + wrap(' ', join(directives, ' ')), | ||
|
||
InlineFragment: ({ typeCondition, directives, selectionSet }) => | ||
join( | ||
['...', wrap('on ', typeCondition), join(directives, ' '), selectionSet], | ||
' ', | ||
), | ||
|
||
FragmentDefinition: ({ | ||
name, | ||
typeCondition, | ||
variableDefinitions, | ||
directives, | ||
selectionSet, | ||
}) => | ||
// Note: fragment variable definitions are experimental and may be changed | ||
// or removed in the future. | ||
`fragment ${name}${wrap('(', join(variableDefinitions, ', '), ')')} ` + | ||
`on ${typeCondition} ${wrap('', join(directives, ' '), ' ')}` + | ||
selectionSet, | ||
|
||
// Value | ||
|
||
IntValue: ({ value }) => value, | ||
FloatValue: ({ value }) => value, | ||
StringValue: ({ value, block: isBlockString }, key) => | ||
isBlockString | ||
? printBlockString(value, key === 'description' ? '' : ' ') | ||
: JSON.stringify(value), | ||
BooleanValue: ({ value }) => (value ? 'true' : 'false'), | ||
NullValue: () => 'null', | ||
EnumValue: ({ value }) => value, | ||
ListValue: ({ values }) => '[' + join(values, ', ') + ']', | ||
ObjectValue: ({ fields }) => '{' + join(fields, ', ') + '}', | ||
ObjectField: ({ name, value }) => name + ': ' + value, | ||
|
||
// Directive | ||
|
||
Directive: ({ name, arguments: args }) => | ||
'@' + name + wrap('(', join(args, ', '), ')'), | ||
|
||
// Type | ||
|
||
NamedType: ({ name }) => name, | ||
ListType: ({ type }) => '[' + type + ']', | ||
NonNullType: ({ type }) => type + '!', | ||
|
||
// Type System Definitions | ||
// Removed since that never included in the Relay documents | ||
}; | ||
|
||
/** | ||
* Given maybeArray, print an empty string if it is null or empty, otherwise | ||
* print all items together separated by separator if provided | ||
*/ | ||
function join(maybeArray: ?Array<string>, separator = '') { | ||
return maybeArray?.filter((x) => x).join(separator) ?? ''; | ||
} | ||
|
||
/** | ||
* Given array, print each item on its own line, wrapped in an | ||
* indented "{ }" block. | ||
*/ | ||
function block(array) { | ||
return array && array.length !== 0 | ||
? '{\n' + indent(join(array, '\n')) + '\n}' | ||
: ''; | ||
} | ||
|
||
/** | ||
* If maybeString is not null or empty, then wrap with start and end, otherwise | ||
* print an empty string. | ||
*/ | ||
function wrap(start, maybeString, end = '') { | ||
return maybeString ? start + maybeString + end : ''; | ||
} | ||
|
||
function indent(maybeString) { | ||
return maybeString && ' ' + maybeString.replace(/\n/g, '\n '); | ||
} | ||
|
||
/** | ||
* Print a block string in the indented block form by adding a leading and | ||
* trailing blank line. However, if a block string starts with whitespace and is | ||
* a single-line, adding a leading blank line would strip that whitespace. | ||
* | ||
* @internal | ||
*/ | ||
function printBlockString( | ||
value: string, | ||
indentation?: string = '', | ||
preferMultipleLines?: boolean = false, | ||
): string { | ||
const isSingleLine = value.indexOf('\n') === -1; | ||
const hasLeadingSpace = value[0] === ' ' || value[0] === '\t'; | ||
const hasTrailingQuote = value[value.length - 1] === '"'; | ||
const hasTrailingSlash = value[value.length - 1] === '\\'; | ||
const printAsMultipleLines = | ||
!isSingleLine || | ||
hasTrailingQuote || | ||
hasTrailingSlash || | ||
preferMultipleLines; | ||
|
||
let result = ''; | ||
// Format a multi-line block quote to account for leading space. | ||
if (printAsMultipleLines && !(isSingleLine && hasLeadingSpace)) { | ||
result += '\n' + indentation; | ||
} | ||
result += indentation ? value.replace(/\n/g, '\n' + indentation) : value; | ||
if (printAsMultipleLines) { | ||
result += '\n'; | ||
} | ||
|
||
return '"""' + result.replace(/"""/g, '\\"""') + '"""'; | ||
} | ||
|
||
module.exports = print; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -348,27 +348,27 @@ globals@^11.1.0: | |
resolved "https://registry.yarnpkg.com/globals/-/globals-11.12.0.tgz#ab8795338868a0babd8525758018c2a7eb95c42e" | ||
integrity sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA== | ||
|
||
graphql@15.3.0: | ||
version "15.3.0" | ||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-15.3.0.tgz#3ad2b0caab0d110e3be4a5a9b2aa281e362b5278" | ||
integrity sha512-GTCJtzJmkFLWRfFJuoo9RWWa/FfamUHgiFosxi/X1Ani4AVWbeyBenZTNX6dM+7WSbbFfTo/25eh0LLkwHMw2w== | ||
graphql@^16.8.1: | ||
version "16.8.1" | ||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-16.8.1.tgz#1930a965bef1170603702acdb68aedd3f3cf6f07" | ||
integrity sha512-59LZHPdGZVh695Ud9lRzPBVTtlX9ZCV150Er2W43ro37wVof0ctenSaskPPjN7lVTIN8mSZt8PHUNKZuNQUuxw== | ||
|
||
has-flag@^3.0.0: | ||
version "3.0.0" | ||
resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" | ||
integrity sha1-tdRU3CGZriJWmfNGfloH87lVuv0= | ||
|
||
hermes-estree@0.16.0: | ||
version "0.16.0" | ||
resolved "https://registry.yarnpkg.com/hermes-estree/-/hermes-estree-0.16.0.tgz#e2c76a1e9d5a4d620790b9fe05fb01f2d53da07d" | ||
integrity sha512-XCoTuBU8S+Jg8nFzaqgy6pNEYo0WYkbMmuJldb3svzpJ2SNUYJDg28b1ltoDMo7k3YlJwPRg7ZS3JTWV3DkDZA== | ||
hermes-estree@0.20.1: | ||
version "0.20.1" | ||
resolved "https://registry.yarnpkg.com/hermes-estree/-/hermes-estree-0.20.1.tgz#0b9a544cf883a779a8e1444b915fa365bef7f72d" | ||
integrity sha512-SQpZK4BzR48kuOg0v4pb3EAGNclzIlqMj3Opu/mu7bbAoFw6oig6cEt/RAi0zTFW/iW6Iz9X9ggGuZTAZ/yZHg== | ||
|
||
hermes-parser@0.16.0: | ||
version "0.16.0" | ||
resolved "https://registry.yarnpkg.com/hermes-parser/-/hermes-parser-0.16.0.tgz#92d0a34ff4f9b7ffcb04511dfed0cc19df5038e0" | ||
integrity sha512-tdJJntb45DUpv8j7ybHfq8NfIQgz8AgaD+PVFyfjK+O+v2N5zbsSDtlvQN2uxCghoTkQL86BEs9oi8IPrUE9Pg== | ||
hermes-parser@0.20.1: | ||
version "0.20.1" | ||
resolved "https://registry.yarnpkg.com/hermes-parser/-/hermes-parser-0.20.1.tgz#ad10597b99f718b91e283f81cbe636c50c3cff92" | ||
integrity sha512-BL5P83cwCogI8D7rrDCgsFY0tdYUtmFP9XaXtl2IQjC+2Xo+4okjfXintlTxcIwl4qeGddEl28Z11kbVIw0aNA== | ||
dependencies: | ||
hermes-estree "0.16.0" | ||
hermes-estree "0.20.1" | ||
|
||
is-arrayish@^0.2.1: | ||
version "0.2.1" | ||
|
@@ -443,14 +443,14 @@ picocolors@^1.0.0: | |
resolved "https://registry.yarnpkg.com/picocolors/-/picocolors-1.0.0.tgz#cb5bdc74ff3f51892236eaf79d68bc44564ab81c" | ||
integrity sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ== | ||
|
||
prettier-plugin-hermes-parser@0.16.0: | ||
version "0.16.0" | ||
resolved "https://registry.yarnpkg.com/prettier-plugin-hermes-parser/-/prettier-plugin-hermes-parser-0.16.0.tgz#4393d43a4a6f4ed976493dccbbb93f62c44215c3" | ||
integrity sha512-J4HdSmlxf3a0nVHVi0G6JJJ7sDVtSb5a+QR52LpiQonpQzMkqgIqyCg+Gt1sGMTJqn19Z0yTHxwCmUicVYXUVg== | ||
prettier-plugin-hermes-parser@0.20.1: | ||
version "0.20.1" | ||
resolved "https://registry.yarnpkg.com/prettier-plugin-hermes-parser/-/prettier-plugin-hermes-parser-0.20.1.tgz#a5f395ae77170813e631f4538c9ef29311b4db1d" | ||
integrity sha512-T6dfa1++ckTxd3MbLxS6sTv1T3yvTu1drahNt3g34hyCzSwYTKTByocLyhd1A9j9uCUlIPD+ogum7+i1h3+CEw== | ||
dependencies: | ||
hermes-estree "0.16.0" | ||
hermes-parser "0.16.0" | ||
prettier-plugin-hermes-parser "0.16.0" | ||
hermes-estree "0.20.1" | ||
hermes-parser "0.20.1" | ||
prettier-plugin-hermes-parser "0.20.1" | ||
|
||
[email protected]: | ||
version "2.8.8" | ||
|