UNPKG

@ardatan/relay-compiler

Version:

Fork of `relay-compiler`

195 lines (163 loc) 5.58 kB
/** * Copyright (c) Facebook, Inc. and its affiliates. * * This source code is licensed under the MIT license found in the * LICENSE file in the root directory of this source tree. * * * @format */ // flowlint ambiguous-object-type:error 'use strict'; var Profiler = require('./GraphQLCompilerProfiler'); var invariant = require('invariant'); var _require = require('./CompilerError'), createUserError = _require.createUserError; // $FlowFixMe[untyped-import] - immutable.js is not flow-typed var _require2 = require('immutable'), ImmutableOrderedMap = _require2.OrderedMap; /** * An immutable representation of a corpus of documents being compiled together. * For each document, the context stores the IR and any validation errors. */ var CompilerContext = /*#__PURE__*/ (function () { // $FlowFixMe[value-as-type] function CompilerContext(schema) { this._isMutable = false; this._documents = new ImmutableOrderedMap(); this._withTransform = new WeakMap(); this._schema = schema; } /** * Returns the documents for the context in the order they were added. */ var _proto = CompilerContext.prototype; _proto.documents = function documents() { return Array.from(this._documents.values()); }; _proto.forEachDocument = function forEachDocument(fn) { this._documents.forEach(fn); }; _proto.replace = function replace(node) { return this._update( this._documents.update(node.name, function (existing) { !existing ? process.env.NODE_ENV !== 'production' ? invariant( false, 'CompilerContext: Expected to replace existing node %s, but ' + 'one was not found in the context.', node.name, ) : invariant(false) : void 0; return node; }), ); }; _proto.add = function add(node) { return this._update( this._documents.update(node.name, function (existing) { !!existing ? process.env.NODE_ENV !== 'production' ? invariant( false, 'CompilerContext: Duplicate document named `%s`. GraphQL ' + 'fragments and roots must have unique names.', node.name, ) : invariant(false) : void 0; return node; }), ); }; _proto.addAll = function addAll(nodes) { return this.withMutations(function (mutable) { return nodes.reduce(function (ctx, definition) { return ctx.add(definition); }, mutable); }); }; /** * Apply a list of compiler transforms and return a new compiler context. */ _proto.applyTransforms = function applyTransforms(transforms, reporter) { var _this = this; return Profiler.run('applyTransforms', function () { return transforms.reduce(function (ctx, transform) { return ctx.applyTransform(transform, reporter); }, _this); }); }; /** * Applies a transform to this context, returning a new context. * * This is memoized such that applying the same sequence of transforms will * not result in duplicated work. */ _proto.applyTransform = function applyTransform(transform, reporter) { var transformed = this._withTransform.get(transform); if (!transformed) { var start = process.hrtime(); transformed = Profiler.instrument(transform)(this); var delta = process.hrtime(start); var deltaMs = Math.round((delta[0] * 1e9 + delta[1]) / 1e6); reporter && reporter.reportTime(transform.name, deltaMs); this._withTransform.set(transform, transformed); } return transformed; }; _proto.get = function get(name) { return this._documents.get(name); }; _proto.getFragment = function getFragment(name, referencedFrom) { var node = this._documents.get(name); if (node == null) { throw createUserError( "Cannot find fragment '".concat(name, "'."), referencedFrom != null ? [referencedFrom] : null, ); } else if (node.kind !== 'Fragment') { throw createUserError( "Cannot find fragment '".concat(name, "', a document with this name exists ") + 'but is not a fragment.', [node.loc, referencedFrom].filter(Boolean), ); } return node; }; _proto.getRoot = function getRoot(name) { var node = this._documents.get(name); if (node == null) { throw createUserError("Cannot find root '".concat(name, "'.")); } else if (node.kind !== 'Root') { throw createUserError( "Cannot find root '".concat(name, "', a document with this name exists but ") + 'is not a root.', [node.loc], ); } return node; }; _proto.remove = function remove(name) { return this._update(this._documents['delete'](name)); }; _proto.withMutations = function withMutations(fn) { var mutableCopy = this._update(this._documents.asMutable()); mutableCopy._isMutable = true; var result = fn(mutableCopy); result._isMutable = false; result._documents = result._documents.asImmutable(); return this._documents === result._documents ? this : result; }; _proto._update = function _update(documents) { var context = this._isMutable ? this : new CompilerContext(this.getSchema()); context._documents = documents; return context; }; _proto.getSchema = function getSchema() { return this._schema; }; return CompilerContext; })(); module.exports = CompilerContext;