@graphql-codegen/client-preset
Version:
GraphQL Code Generator preset for client.
82 lines (81 loc) • 2.74 kB
JavaScript
Object.defineProperty(exports, "__esModule", { value: true });
exports.processSources = processSources;
function processSources(sources, buildName) {
const sourcesWithOperations = [];
for (const originalSource of sources) {
const source = fixLinebreaks(originalSource);
const { document } = source;
const operations = [];
for (const definition of document?.definitions ?? []) {
if (definition?.kind !== `OperationDefinition` && definition?.kind !== 'FragmentDefinition')
continue;
if (definition.name?.kind !== `Name`) {
if (definition?.kind === `OperationDefinition`) {
// eslint-disable-next-line no-console
console.warn(`[client-preset] the following anonymous operation is skipped: ${source.rawSDL}`);
}
continue;
}
operations.push({
initialName: buildName(definition),
definition,
});
}
if (operations.length === 0)
continue;
sourcesWithOperations.push({
source,
operations,
});
}
return sourcesWithOperations;
}
/**
* https://github.com/dotansimha/graphql-code-generator/issues/7362
*
* Source file is read by @graphql/tools using fs.promises.readFile,
* which means that the linebreaks are read as-is and the result will be different
* depending on the OS: it will contain LF (\n) on Linux/MacOS and CRLF (\r\n) on Windows.
*
* In most scenarios that would be OK. However, front-end preset is using the resulting string
* as a TypeScript type. Which means that the string will be compared against a template literal,
* for example:
*
* <pre><code>
* `
* query a {
* a
* }
* ` === '\n query a {\n a\n }\n '
* </code></pre>
*
* According to clause 12.8.6.2 of ECMAScript Language Specification
* (https://tc39.es/ecma262/#sec-static-semantics-trv),
* when comparing strings, JavaScript doesn't care which linebreaks does the source file contain,
* any linebreak (CR, LF or CRLF) is LF from JavaScript standpoint
* (otherwise the result of the above comparison would be OS-dependent, which doesn't make sense).
*
* Therefore gql-tag-operation would break on Windows as it would generate
*
* '\r\n query a {\r\n a\r\n }\r\n '
*
* which is NOT equal to
*
* <pre><code>
* `
* query a {
* a
* }
* `
* </code></pre>
*
* Therefore we need to replace \r\n with \n in the string.
*
* @param source
*/
function fixLinebreaks(source) {
const fixedSource = { ...source };
fixedSource.rawSDL = source.rawSDL.replace(/\r\n/g, '\n');
return fixedSource;
}
;