1 |
|
2 |
|
3 |
|
4 |
|
5 |
|
6 |
|
7 |
|
8 |
|
9 |
|
10 | 'use strict';
|
11 |
|
12 | var _objectSpread2 = require("@babel/runtime/helpers/interopRequireDefault")(require("@babel/runtime/helpers/objectSpread"));
|
13 |
|
14 | var _toConsumableArray2 = require("@babel/runtime/helpers/interopRequireDefault")(require("@babel/runtime/helpers/toConsumableArray"));
|
15 |
|
16 | function generate(node, options) {
|
17 | var ast = require("./GraphQLIRVisitor").visit(node, createVisitor(options));
|
18 |
|
19 | return require("@babel/generator")["default"](ast).code;
|
20 | }
|
21 |
|
22 | function makeProp(_ref, state, unmasked, concreteType) {
|
23 | var key = _ref.key,
|
24 | schemaName = _ref.schemaName,
|
25 | value = _ref.value,
|
26 | conditional = _ref.conditional,
|
27 | nodeType = _ref.nodeType,
|
28 | nodeSelections = _ref.nodeSelections;
|
29 |
|
30 | if (nodeType) {
|
31 | value = require("./RelayFlowTypeTransformers").transformScalarType(nodeType, state, selectionsToBabel([Array.from(require("nullthrows")(nodeSelections).values())], state, unmasked));
|
32 | }
|
33 |
|
34 | if (schemaName === '__typename' && concreteType) {
|
35 | value = require("@babel/types").stringLiteralTypeAnnotation(concreteType);
|
36 | }
|
37 |
|
38 | var typeProperty = require("./RelayFlowBabelFactories").readOnlyObjectTypeProperty(key, value);
|
39 |
|
40 | if (conditional) {
|
41 | typeProperty.optional = true;
|
42 | }
|
43 |
|
44 | return typeProperty;
|
45 | }
|
46 |
|
47 | var isTypenameSelection = function isTypenameSelection(selection) {
|
48 | return selection.schemaName === '__typename';
|
49 | };
|
50 |
|
51 | var hasTypenameSelection = function hasTypenameSelection(selections) {
|
52 | return selections.some(isTypenameSelection);
|
53 | };
|
54 |
|
55 | var onlySelectsTypename = function onlySelectsTypename(selections) {
|
56 | return selections.every(isTypenameSelection);
|
57 | };
|
58 |
|
59 | function selectionsToBabel(selections, state, unmasked, refTypeName) {
|
60 | var baseFields = new Map();
|
61 | var byConcreteType = {};
|
62 | flattenArray(selections).forEach(function (selection) {
|
63 | var concreteType = selection.concreteType;
|
64 |
|
65 | if (concreteType) {
|
66 | var _byConcreteType$concr;
|
67 |
|
68 | byConcreteType[concreteType] = (_byConcreteType$concr = byConcreteType[concreteType]) !== null && _byConcreteType$concr !== void 0 ? _byConcreteType$concr : [];
|
69 | byConcreteType[concreteType].push(selection);
|
70 | } else {
|
71 | var previousSel = baseFields.get(selection.key);
|
72 | baseFields.set(selection.key, previousSel ? mergeSelection(selection, previousSel) : selection);
|
73 | }
|
74 | });
|
75 | var types = [];
|
76 |
|
77 | if (Object.keys(byConcreteType).length && onlySelectsTypename(Array.from(baseFields.values())) && (hasTypenameSelection(Array.from(baseFields.values())) || Object.keys(byConcreteType).every(function (type) {
|
78 | return hasTypenameSelection(byConcreteType[type]);
|
79 | }))) {
|
80 | (function () {
|
81 | var typenameAliases = new Set();
|
82 |
|
83 | var _loop = function _loop(concreteType) {
|
84 | types.push(groupRefs((0, _toConsumableArray2["default"])(Array.from(baseFields.values())).concat((0, _toConsumableArray2["default"])(byConcreteType[concreteType]))).map(function (selection) {
|
85 | if (selection.schemaName === '__typename') {
|
86 | typenameAliases.add(selection.key);
|
87 | }
|
88 |
|
89 | return makeProp(selection, state, unmasked, concreteType);
|
90 | }));
|
91 | };
|
92 |
|
93 | for (var concreteType in byConcreteType) {
|
94 | _loop(concreteType);
|
95 | }
|
96 |
|
97 |
|
98 |
|
99 |
|
100 | types.push(Array.from(typenameAliases).map(function (typenameAlias) {
|
101 | var otherProp = require("./RelayFlowBabelFactories").readOnlyObjectTypeProperty(typenameAlias, require("@babel/types").stringLiteralTypeAnnotation('%other'));
|
102 |
|
103 | otherProp.leadingComments = require("./RelayFlowBabelFactories").lineComments("This will never be '%other', but we need some", 'value in case none of the concrete values match.');
|
104 | return otherProp;
|
105 | }));
|
106 | })();
|
107 | } else {
|
108 | var selectionMap = selectionsToMap(Array.from(baseFields.values()));
|
109 |
|
110 | for (var concreteType in byConcreteType) {
|
111 | selectionMap = mergeSelections(selectionMap, selectionsToMap(byConcreteType[concreteType].map(function (sel) {
|
112 | return (0, _objectSpread2["default"])({}, sel, {
|
113 | conditional: true
|
114 | });
|
115 | })));
|
116 | }
|
117 |
|
118 | var selectionMapValues = groupRefs(Array.from(selectionMap.values())).map(function (sel) {
|
119 | return isTypenameSelection(sel) && sel.concreteType ? makeProp((0, _objectSpread2["default"])({}, sel, {
|
120 | conditional: false
|
121 | }), state, unmasked, sel.concreteType) : makeProp(sel, state, unmasked);
|
122 | });
|
123 | types.push(selectionMapValues);
|
124 | }
|
125 |
|
126 | return require("./RelayFlowBabelFactories").unionTypeAnnotation(types.map(function (props) {
|
127 | if (refTypeName) {
|
128 | props.push(require("./RelayFlowBabelFactories").readOnlyObjectTypeProperty('$refType', require("@babel/types").genericTypeAnnotation(require("@babel/types").identifier(refTypeName))));
|
129 | }
|
130 |
|
131 | return unmasked ? require("@babel/types").objectTypeAnnotation(props) : require("./RelayFlowBabelFactories").exactObjectTypeAnnotation(props);
|
132 | }));
|
133 | }
|
134 |
|
135 | function mergeSelection(a, b) {
|
136 | if (!a) {
|
137 | return (0, _objectSpread2["default"])({}, b, {
|
138 | conditional: true
|
139 | });
|
140 | }
|
141 |
|
142 | return (0, _objectSpread2["default"])({}, a, {
|
143 | nodeSelections: a.nodeSelections ? mergeSelections(a.nodeSelections, require("nullthrows")(b.nodeSelections)) : null,
|
144 | conditional: a.conditional && b.conditional
|
145 | });
|
146 | }
|
147 |
|
148 | function mergeSelections(a, b) {
|
149 | var merged = new Map();
|
150 | var _iteratorNormalCompletion = true;
|
151 | var _didIteratorError = false;
|
152 | var _iteratorError = undefined;
|
153 |
|
154 | try {
|
155 | for (var _iterator = a.entries()[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
|
156 | var _step$value = _step.value,
|
157 | key = _step$value[0],
|
158 | value = _step$value[1];
|
159 | merged.set(key, value);
|
160 | }
|
161 | } catch (err) {
|
162 | _didIteratorError = true;
|
163 | _iteratorError = err;
|
164 | } finally {
|
165 | try {
|
166 | if (!_iteratorNormalCompletion && _iterator["return"] != null) {
|
167 | _iterator["return"]();
|
168 | }
|
169 | } finally {
|
170 | if (_didIteratorError) {
|
171 | throw _iteratorError;
|
172 | }
|
173 | }
|
174 | }
|
175 |
|
176 | var _iteratorNormalCompletion2 = true;
|
177 | var _didIteratorError2 = false;
|
178 | var _iteratorError2 = undefined;
|
179 |
|
180 | try {
|
181 | for (var _iterator2 = b.entries()[Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) {
|
182 | var _step2$value = _step2.value,
|
183 | key = _step2$value[0],
|
184 | value = _step2$value[1];
|
185 | merged.set(key, mergeSelection(a.get(key), value));
|
186 | }
|
187 | } catch (err) {
|
188 | _didIteratorError2 = true;
|
189 | _iteratorError2 = err;
|
190 | } finally {
|
191 | try {
|
192 | if (!_iteratorNormalCompletion2 && _iterator2["return"] != null) {
|
193 | _iterator2["return"]();
|
194 | }
|
195 | } finally {
|
196 | if (_didIteratorError2) {
|
197 | throw _iteratorError2;
|
198 | }
|
199 | }
|
200 | }
|
201 |
|
202 | return merged;
|
203 | }
|
204 |
|
205 | function isPlural(node) {
|
206 | return Boolean(node.metadata && node.metadata.plural);
|
207 | }
|
208 |
|
209 | function createVisitor(options) {
|
210 | var state = {
|
211 | customScalars: options.customScalars,
|
212 | enumsHasteModule: options.enumsHasteModule,
|
213 | existingFragmentNames: options.existingFragmentNames,
|
214 | generatedFragments: new Set(),
|
215 | generatedInputObjectTypes: {},
|
216 | optionalInputFields: options.optionalInputFields,
|
217 | usedEnums: {},
|
218 | usedFragments: new Set(),
|
219 | useHaste: options.useHaste,
|
220 | useSingleArtifactDirectory: options.useSingleArtifactDirectory,
|
221 | noFutureProofEnums: options.noFutureProofEnums
|
222 | };
|
223 | var hasMatchField = false;
|
224 | return {
|
225 | leave: {
|
226 | Root: function Root(node) {
|
227 | var inputVariablesType = generateInputVariablesType(node, state);
|
228 | var inputObjectTypes = generateInputObjectTypes(state);
|
229 |
|
230 | var responseType = require("./RelayFlowBabelFactories").exportType("".concat(node.name, "Response"), selectionsToBabel(node.selections, state, false));
|
231 |
|
232 | var operationType = require("./RelayFlowBabelFactories").exportType(node.name, require("./RelayFlowBabelFactories").exactObjectTypeAnnotation([require("@babel/types").objectTypeProperty(require("@babel/types").identifier('variables'), require("@babel/types").genericTypeAnnotation(require("@babel/types").identifier("".concat(node.name, "Variables")))), require("@babel/types").objectTypeProperty(require("@babel/types").identifier('response'), require("@babel/types").genericTypeAnnotation(require("@babel/types").identifier("".concat(node.name, "Response"))))]));
|
233 |
|
234 | var importedTypes = [];
|
235 |
|
236 | if (hasMatchField) {
|
237 | importedTypes.push('MatchPointer');
|
238 | }
|
239 |
|
240 | return require("@babel/types").program((0, _toConsumableArray2["default"])(getFragmentImports(state)).concat((0, _toConsumableArray2["default"])(getEnumDefinitions(state)), [importedTypes.length ? require("./RelayFlowBabelFactories").importTypes(importedTypes, 'relay-runtime') : null], (0, _toConsumableArray2["default"])(inputObjectTypes), [inputVariablesType, responseType, operationType]).filter(Boolean));
|
241 | },
|
242 | Fragment: function Fragment(node) {
|
243 | var selections = flattenArray(node.selections);
|
244 | var numConecreteSelections = selections.filter(function (s) {
|
245 | return s.concreteType;
|
246 | }).length;
|
247 | selections = selections.map(function (selection) {
|
248 | if (numConecreteSelections <= 1 && isTypenameSelection(selection) && !require("./GraphQLSchemaUtils").isAbstractType(node.type)) {
|
249 | return [(0, _objectSpread2["default"])({}, selection, {
|
250 | concreteType: node.type.toString()
|
251 | })];
|
252 | }
|
253 |
|
254 | return [selection];
|
255 | });
|
256 | state.generatedFragments.add(node.name);
|
257 | var refTypeName = getRefTypeName(node.name);
|
258 |
|
259 | var refType = require("@babel/types").declareExportDeclaration(require("@babel/types").declareOpaqueType(require("@babel/types").identifier(refTypeName), null, require("@babel/types").genericTypeAnnotation(require("@babel/types").identifier('FragmentReference'))));
|
260 |
|
261 | var unmasked = node.metadata && node.metadata.mask === false;
|
262 | var baseType = selectionsToBabel(selections, state, unmasked, unmasked ? undefined : refTypeName);
|
263 | var type = isPlural(node) ? require("./RelayFlowBabelFactories").readOnlyArrayOfType(baseType) : baseType;
|
264 | var importedTypes = ['FragmentReference'];
|
265 |
|
266 | if (hasMatchField) {
|
267 | importedTypes.push('MatchPointer');
|
268 | }
|
269 |
|
270 | return require("@babel/types").program((0, _toConsumableArray2["default"])(getFragmentImports(state)).concat((0, _toConsumableArray2["default"])(getEnumDefinitions(state)), [require("./RelayFlowBabelFactories").importTypes(importedTypes, 'relay-runtime'), refType, require("./RelayFlowBabelFactories").exportType(node.name, type)]));
|
271 | },
|
272 | InlineFragment: function InlineFragment(node) {
|
273 | var typeCondition = node.typeCondition;
|
274 | return flattenArray(node.selections).map(function (typeSelection) {
|
275 | return require("./GraphQLSchemaUtils").isAbstractType(typeCondition) ? (0, _objectSpread2["default"])({}, typeSelection, {
|
276 | conditional: true
|
277 | }) : (0, _objectSpread2["default"])({}, typeSelection, {
|
278 | concreteType: typeCondition.toString()
|
279 | });
|
280 | });
|
281 | },
|
282 | Condition: function Condition(node) {
|
283 | return flattenArray(node.selections).map(function (selection) {
|
284 | return (0, _objectSpread2["default"])({}, selection, {
|
285 | conditional: true
|
286 | });
|
287 | });
|
288 | },
|
289 | ScalarField: function ScalarField(node) {
|
290 | var _node$alias;
|
291 |
|
292 | return [{
|
293 | key: (_node$alias = node.alias) !== null && _node$alias !== void 0 ? _node$alias : node.name,
|
294 | schemaName: node.name,
|
295 | value: require("./RelayFlowTypeTransformers").transformScalarType(node.type, state)
|
296 | }];
|
297 | },
|
298 | LinkedField: function LinkedField(node) {
|
299 | var _node$alias2;
|
300 |
|
301 | return [{
|
302 | key: (_node$alias2 = node.alias) !== null && _node$alias2 !== void 0 ? _node$alias2 : node.name,
|
303 | schemaName: node.name,
|
304 | nodeType: node.type,
|
305 | nodeSelections: selectionsToMap(flattenArray(node.selections))
|
306 | }];
|
307 | },
|
308 | MatchField: function MatchField(node) {
|
309 | var _node$alias3;
|
310 |
|
311 | hasMatchField = true;
|
312 | return [{
|
313 | key: (_node$alias3 = node.alias) !== null && _node$alias3 !== void 0 ? _node$alias3 : node.name,
|
314 | schemaName: node.name,
|
315 | value: require("@babel/types").nullableTypeAnnotation(require("@babel/types").genericTypeAnnotation(require("@babel/types").identifier('MatchPointer')))
|
316 | }];
|
317 | },
|
318 | FragmentSpread: function FragmentSpread(node) {
|
319 | state.usedFragments.add(node.name);
|
320 | return [{
|
321 | key: '__fragments_' + node.name,
|
322 | ref: node.name
|
323 | }];
|
324 | }
|
325 | }
|
326 | };
|
327 | }
|
328 |
|
329 | function selectionsToMap(selections) {
|
330 | var map = new Map();
|
331 | selections.forEach(function (selection) {
|
332 | var previousSel = map.get(selection.key);
|
333 | map.set(selection.key, previousSel ? mergeSelection(previousSel, selection) : selection);
|
334 | });
|
335 | return map;
|
336 | }
|
337 |
|
338 | function flattenArray(arrayOfArrays) {
|
339 | var result = [];
|
340 | arrayOfArrays.forEach(function (array) {
|
341 | return result.push.apply(result, (0, _toConsumableArray2["default"])(array));
|
342 | });
|
343 | return result;
|
344 | }
|
345 |
|
346 | function generateInputObjectTypes(state) {
|
347 | return Object.keys(state.generatedInputObjectTypes).map(function (typeIdentifier) {
|
348 | var inputObjectType = state.generatedInputObjectTypes[typeIdentifier];
|
349 | !(typeof inputObjectType !== 'string') ? process.env.NODE_ENV !== "production" ? require("fbjs/lib/invariant")(false, 'RelayCompilerFlowGenerator: Expected input object type to have been' + ' defined before calling `generateInputObjectTypes`') : require("fbjs/lib/invariant")(false) : void 0;
|
350 | return require("./RelayFlowBabelFactories").exportType(typeIdentifier, inputObjectType);
|
351 | });
|
352 | }
|
353 |
|
354 | function generateInputVariablesType(node, state) {
|
355 | return require("./RelayFlowBabelFactories").exportType("".concat(node.name, "Variables"), require("./RelayFlowBabelFactories").exactObjectTypeAnnotation(node.argumentDefinitions.map(function (arg) {
|
356 | var property = require("@babel/types").objectTypeProperty(require("@babel/types").identifier(arg.name), require("./RelayFlowTypeTransformers").transformInputType(arg.type, state));
|
357 |
|
358 | if (!(arg.type instanceof require("graphql").GraphQLNonNull)) {
|
359 | property.optional = true;
|
360 | }
|
361 |
|
362 | return property;
|
363 | })));
|
364 | }
|
365 |
|
366 | function groupRefs(props) {
|
367 | var result = [];
|
368 | var refs = [];
|
369 | props.forEach(function (prop) {
|
370 | if (prop.ref) {
|
371 | refs.push(prop.ref);
|
372 | } else {
|
373 | result.push(prop);
|
374 | }
|
375 | });
|
376 |
|
377 | if (refs.length > 0) {
|
378 | var value = require("./RelayFlowBabelFactories").intersectionTypeAnnotation(refs.map(function (ref) {
|
379 | return require("@babel/types").genericTypeAnnotation(require("@babel/types").identifier(getRefTypeName(ref)));
|
380 | }));
|
381 |
|
382 | result.push({
|
383 | key: '$fragmentRefs',
|
384 | conditional: false,
|
385 | value: value
|
386 | });
|
387 | }
|
388 |
|
389 | return result;
|
390 | }
|
391 |
|
392 | function getFragmentImports(state) {
|
393 | var imports = [];
|
394 |
|
395 | if (state.usedFragments.size > 0) {
|
396 | var usedFragments = Array.from(state.usedFragments).sort();
|
397 | var _iteratorNormalCompletion3 = true;
|
398 | var _didIteratorError3 = false;
|
399 | var _iteratorError3 = undefined;
|
400 |
|
401 | try {
|
402 | for (var _iterator3 = usedFragments[Symbol.iterator](), _step3; !(_iteratorNormalCompletion3 = (_step3 = _iterator3.next()).done); _iteratorNormalCompletion3 = true) {
|
403 | var usedFragment = _step3.value;
|
404 | var refTypeName = getRefTypeName(usedFragment);
|
405 |
|
406 | if (!state.generatedFragments.has(usedFragment)) {
|
407 | if (state.useHaste && state.existingFragmentNames.has(usedFragment)) {
|
408 |
|
409 |
|
410 | imports.push(require("./RelayFlowBabelFactories").importTypes([refTypeName], usedFragment + '.graphql'));
|
411 | } else if (state.useSingleArtifactDirectory && state.existingFragmentNames.has(usedFragment)) {
|
412 | imports.push(require("./RelayFlowBabelFactories").importTypes([refTypeName], './' + usedFragment + '.graphql'));
|
413 | } else {
|
414 | imports.push(require("./RelayFlowBabelFactories").anyTypeAlias(refTypeName));
|
415 | }
|
416 | }
|
417 | }
|
418 | } catch (err) {
|
419 | _didIteratorError3 = true;
|
420 | _iteratorError3 = err;
|
421 | } finally {
|
422 | try {
|
423 | if (!_iteratorNormalCompletion3 && _iterator3["return"] != null) {
|
424 | _iterator3["return"]();
|
425 | }
|
426 | } finally {
|
427 | if (_didIteratorError3) {
|
428 | throw _iteratorError3;
|
429 | }
|
430 | }
|
431 | }
|
432 | }
|
433 |
|
434 | return imports;
|
435 | }
|
436 |
|
437 | function getEnumDefinitions(_ref2) {
|
438 | var enumsHasteModule = _ref2.enumsHasteModule,
|
439 | usedEnums = _ref2.usedEnums,
|
440 | noFutureProofEnums = _ref2.noFutureProofEnums;
|
441 | var enumNames = Object.keys(usedEnums).sort();
|
442 |
|
443 | if (enumNames.length === 0) {
|
444 | return [];
|
445 | }
|
446 |
|
447 | if (enumsHasteModule) {
|
448 | return [require("./RelayFlowBabelFactories").importTypes(enumNames, enumsHasteModule)];
|
449 | }
|
450 |
|
451 | return enumNames.map(function (name) {
|
452 | var values = usedEnums[name].getValues().map(function (_ref3) {
|
453 | var value = _ref3.value;
|
454 | return value;
|
455 | });
|
456 | values.sort();
|
457 |
|
458 | if (!noFutureProofEnums) {
|
459 | values.push('%future added value');
|
460 | }
|
461 |
|
462 | return require("./RelayFlowBabelFactories").exportType(name, require("@babel/types").unionTypeAnnotation(values.map(function (value) {
|
463 | return require("@babel/types").stringLiteralTypeAnnotation(value);
|
464 | })));
|
465 | });
|
466 | }
|
467 |
|
468 | function getRefTypeName(name) {
|
469 | return "".concat(name, "$ref");
|
470 | }
|
471 |
|
472 | var FLOW_TRANSFORMS = [require("./RelayRelayDirectiveTransform").transform, require("./RelayMaskTransform").transform, require("./RelayMatchTransform").transform, require("./FlattenTransform").transformWithOptions({})];
|
473 | module.exports = {
|
474 | generate: require("./GraphQLCompilerProfiler").instrument(generate, 'RelayFlowGenerator.generate'),
|
475 | transforms: FLOW_TRANSFORMS
|
476 | }; |
\ | No newline at end of file |