diff --git a/README.md b/README.md index 9b205245..f187ddbb 100644 --- a/README.md +++ b/README.md @@ -137,6 +137,32 @@ And in your JavaScript: import { MyQuery1, MyQuery2 } from 'query.gql' ``` +#### Support for fragments + +With the webpack loader, you can import fragments by name: + +In a file called `query.gql`: +```graphql +fragment MyFragment1 on MyType1 { + ... +} + +fragment MyFragment2 on MyType2 { + ... +} +``` + +And in your JavaScript: + +```javascript +import { MyFragment1, MyFragment2 } from 'query.gql' +``` + +Note: If your fragment references other fragments, the resulting document will +have multiple fragments in it. In this case you must still specify the fragment +name when using the fragment. For example, with `apollo-client` you would specify +the `fragmentName` option when using the fragment for cache operations. + ### Warnings This package will emit a warning if you have multiple fragments of the same name. You can disable this with: diff --git a/loader.js b/loader.js index 4ceac4d3..4d835a83 100644 --- a/loader.js +++ b/loader.js @@ -53,7 +53,7 @@ module.exports = function(source) { // at compile time, and then uses those at load time to create minimal query documents // We cannot do the latter at compile time due to how the #import code works. let operationCount = doc.definitions.reduce(function(accum, op) { - if (op.kind === "OperationDefinition") { + if (op.kind === "OperationDefinition" || op.kind === "FragmentDefinition") { return accum + 1; } @@ -161,12 +161,12 @@ module.exports = function(source) { return newDoc; } - - module.exports = doc; + + module.exports = Object.assign({default: doc}, doc); ` for (const op of doc.definitions) { - if (op.kind === "OperationDefinition") { + if (op.kind === "OperationDefinition" || op.kind === "FragmentDefinition") { if (!op.name) { if (operationCount > 1) { throw "Query/mutation names are required for a document with multiple definitions"; diff --git a/test/graphql.js b/test/graphql.js index 726e3918..150b2445 100644 --- a/test/graphql.js +++ b/test/graphql.js @@ -92,7 +92,7 @@ const assert = require('chai').assert; gql.disableExperimentalFragmentVariables() }); - + // see https://github.com/apollographql/graphql-tag/issues/168 it('does not nest queries needlessly in named exports', () => { const jsSource = loader.call({ cacheable() {} }, ` @@ -143,6 +143,17 @@ const assert = require('chai').assert; assert.equal(Q3[1].name.value, 'F1'); assert.equal(Q3[2].name.value, 'F2'); + const F1 = module.exports.F1.definitions; + const F2 = module.exports.F2.definitions; + const F3 = module.exports.F3.definitions; + + assert.equal(F1.length, 1); + assert.equal(F1[0].name.value, 'F1'); + assert.equal(F2.length, 1); + assert.equal(F2[0].name.value, 'F2'); + assert.equal(F3.length, 1); + assert.equal(F3[0].name.value, 'F3'); + }); it('tracks fragment dependencies across nested fragments', () => { @@ -182,6 +193,20 @@ const assert = require('chai').assert; assert.equal(Q1[3].name.value, 'F11'); assert.equal(Q2.length, 1); + + const F11 = module.exports.F11.definitions; + const F22 = module.exports.F22.definitions; + const F33 = module.exports.F33.definitions; + + assert.equal(F11.length, 1); + assert.equal(F11[0].name.value, 'F11'); + assert.equal(F22.length, 2); + assert.equal(F22[0].name.value, 'F22'); + assert.equal(F22[1].name.value, 'F11'); + assert.equal(F33.length, 3); + assert.equal(F33[0].name.value, 'F33'); + assert.equal(F33[1].name.value, 'F22'); + assert.equal(F33[2].name.value, 'F11'); }); it('correctly imports other files through the webpack loader', () => {