Mirror: Modular GraphQL.js import paths without the hassle.
0
fork

Configure Feed

Select the types of activity you want to include in your feed.

Initial Commit

Phil Pluckthun d4e46c0c

+318
+2
.gitignore
··· 1 + import-map.json 2 + node_modules
+46
index.js
··· 1 + export default function({ types: t }) { 2 + const importMap = require('./import-map.json'); 3 + const PKG_NAME = 'graphql'; 4 + 5 + return { 6 + visitor: { 7 + ImportDeclaration: { 8 + exit(path) { 9 + const { node } = path; 10 + if (node.source.value !== PKG_NAME || !node.specifiers.length) return; 11 + 12 + const imports = node.specifiers.reduce((acc, specifier) => { 13 + if (t.isImportSpecifier(specifier)) { 14 + const imported = specifier.imported.name; 15 + const declaration = importMap[imported]; 16 + const from = declaration ? declaration.from : PKG_NAME; 17 + if (!acc[from]) { 18 + acc[from] = t.importDeclaration([], t.stringLiteral(from)); 19 + } 20 + 21 + const localName = specifier.local.name; 22 + const newImportedName = declaration ? declaration.local : imported; 23 + 24 + acc[from].specifiers.push( 25 + t.importSpecifier( 26 + t.identifier(localName), 27 + t.identifier(newImportedName) 28 + ) 29 + ); 30 + } 31 + 32 + return acc; 33 + }, {}); 34 + 35 + const importFiles = Object.keys(imports); 36 + if ( 37 + importFiles.length && 38 + (importFiles.length !== 1 || importFiles[0] !== PKG_NAME) 39 + ) { 40 + path.replaceWithMultiple(importFiles.map(key => imports[key])); 41 + } 42 + }, 43 + }, 44 + }, 45 + }; 46 + }
+20
package.json
··· 1 + { 2 + "name": "babel-plugin-modular-graphql", 3 + "version": "0.1.0", 4 + "main": "index.js", 5 + "license": "MIT", 6 + "files": [ 7 + "import-map.json", 8 + "index.js" 9 + ], 10 + "scripts": { 11 + "build": "node scripts/generate-import-map.js", 12 + "prepublishOnly": "node scripts/generate-import-map.js" 13 + }, 14 + "devDependencies": { 15 + "@rollup/plugin-node-resolve": "^7.1.3", 16 + "acorn-walk": "^7.1.1", 17 + "graphql": "^15.0.0", 18 + "rollup": "^2.6.1" 19 + } 20 + }
+122
scripts/generate-import-map.js
··· 1 + const fs = require('fs'); 2 + const path = require('path'); 3 + 4 + const { rollup } = require('rollup'); 5 + 6 + const cwd = process.cwd(); 7 + const basepath = path.resolve(cwd, 'node_modules/graphql/'); 8 + 9 + function generateImportMapPlugin(opts = {}) { 10 + const maxDepth = opts.maxDepth || 2; 11 + const filename = opts.filename || 'import-map.json'; 12 + const map = new Map(); 13 + 14 + const resolveFile = (from, to) => { 15 + return path.join(from, to); 16 + }; 17 + 18 + const resolveFromMap = (id, name, depth = 0) => { 19 + const exports = map.get(id); 20 + if (!exports || !exports.has(name)) return null; 21 + 22 + const declaration = exports.get(name); 23 + if (depth >= maxDepth || declaration.from === id) { 24 + return declaration; 25 + } 26 + 27 + return resolveFromMap(declaration.from, declaration.local, depth + 1) 28 + || declaration; 29 + }; 30 + 31 + return { 32 + name: 'generate-import-map', 33 + transform(code, id) { 34 + const relative = path.relative(basepath, id); 35 + const dirname = path.dirname(relative); 36 + const exports = new Map(); 37 + 38 + this.parse(code).body 39 + .filter(x => x.type === 'ExportNamedDeclaration') 40 + .forEach(node => { 41 + const source = node.source 42 + ? resolveFile(dirname, node.source.value) 43 + : relative; 44 + 45 + node.specifiers.forEach(specifier => { 46 + exports.set(specifier.exported.name, { 47 + local: specifier.local.name, 48 + from: source 49 + }); 50 + }); 51 + 52 + if (node.declaration) { 53 + (node.declaration.declarations || [node.declaration]) 54 + .forEach(declaration => { 55 + if (declaration && declaration.id) { 56 + const { name } = declaration.id; 57 + exports.set(declaration.id.name, { 58 + local: name, 59 + from: source 60 + }); 61 + } 62 + }); 63 + } 64 + }); 65 + 66 + map.set(relative, exports); 67 + return null; 68 + }, 69 + renderChunk(_code, chunk) { 70 + const id = chunk.facadeModuleId; 71 + const relative = path.relative(basepath, id); 72 + 73 + if (chunk.isEntry) { 74 + const importMap = chunk.exports.reduce((acc, name) => { 75 + const declaration = resolveFromMap(relative, name); 76 + if (declaration) { 77 + const dirname = path.join('graphql/', path.dirname(declaration.from)); 78 + const filename = path.basename(declaration.from, '.mjs'); 79 + 80 + acc[name] = { 81 + local: declaration.local, 82 + from: path.join(dirname, filename), 83 + }; 84 + } 85 + 86 + return acc; 87 + }, {}); 88 + 89 + this.emitFile({ 90 + type: 'asset', 91 + filename, 92 + name: filename, 93 + source: JSON.stringify(importMap, null, 2) 94 + }); 95 + } 96 + }, 97 + }; 98 + } 99 + 100 + (async () => { 101 + const bundle = await rollup({ 102 + input: path.join(basepath, 'index.mjs'), 103 + external: (id) => !/^\.{0,2}\//.test(id), 104 + preserveModules: true, 105 + plugins: [ 106 + require('@rollup/plugin-node-resolve')(), 107 + generateImportMapPlugin({ 108 + filename: 'import-map.json' 109 + }) 110 + ], 111 + }); 112 + 113 + const { output } = await bundle.generate({}); 114 + 115 + fs.writeFileSync( 116 + path.resolve(cwd, 'import-map.json'), 117 + output.find(asset => asset.type === 'asset').source 118 + ); 119 + })().catch((err) => { 120 + console.error(`${err.name}: ${err.message}`); 121 + process.exit(1); 122 + });
+128
yarn.lock
··· 1 + # THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. 2 + # yarn lockfile v1 3 + 4 + 5 + "@rollup/plugin-node-resolve@^7.1.3": 6 + version "7.1.3" 7 + resolved "https://registry.yarnpkg.com/@rollup/plugin-node-resolve/-/plugin-node-resolve-7.1.3.tgz#80de384edfbd7bfc9101164910f86078151a3eca" 8 + integrity sha512-RxtSL3XmdTAE2byxekYLnx+98kEUOrPHF/KRVjLH+DEIHy6kjIw7YINQzn+NXiH/NTrQLAwYs0GWB+csWygA9Q== 9 + dependencies: 10 + "@rollup/pluginutils" "^3.0.8" 11 + "@types/resolve" "0.0.8" 12 + builtin-modules "^3.1.0" 13 + is-module "^1.0.0" 14 + resolve "^1.14.2" 15 + 16 + "@rollup/pluginutils@^3.0.8": 17 + version "3.0.9" 18 + resolved "https://registry.yarnpkg.com/@rollup/pluginutils/-/pluginutils-3.0.9.tgz#aa6adca2c45e5a1b950103a999e3cddfe49fd775" 19 + integrity sha512-TLZavlfPAZYI7v33wQh4mTP6zojne14yok3DNSLcjoG/Hirxfkonn6icP5rrNWRn8nZsirJBFFpijVOJzkUHDg== 20 + dependencies: 21 + "@types/estree" "0.0.39" 22 + estree-walker "^1.0.1" 23 + micromatch "^4.0.2" 24 + 25 + "@types/estree@0.0.39": 26 + version "0.0.39" 27 + resolved "https://registry.yarnpkg.com/@types/estree/-/estree-0.0.39.tgz#e177e699ee1b8c22d23174caaa7422644389509f" 28 + integrity sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw== 29 + 30 + "@types/node@*": 31 + version "13.11.1" 32 + resolved "https://registry.yarnpkg.com/@types/node/-/node-13.11.1.tgz#49a2a83df9d26daacead30d0ccc8762b128d53c7" 33 + integrity sha512-eWQGP3qtxwL8FGneRrC5DwrJLGN4/dH1clNTuLfN81HCrxVtxRjygDTUoZJ5ASlDEeo0ppYFQjQIlXhtXpOn6g== 34 + 35 + "@types/resolve@0.0.8": 36 + version "0.0.8" 37 + resolved "https://registry.yarnpkg.com/@types/resolve/-/resolve-0.0.8.tgz#f26074d238e02659e323ce1a13d041eee280e194" 38 + integrity sha512-auApPaJf3NPfe18hSoJkp8EbZzer2ISk7o8mCC3M9he/a04+gbMF97NkpD2S8riMGvm4BMRI59/SZQSaLTKpsQ== 39 + dependencies: 40 + "@types/node" "*" 41 + 42 + acorn-walk@^7.1.1: 43 + version "7.1.1" 44 + resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-7.1.1.tgz#345f0dffad5c735e7373d2fec9a1023e6a44b83e" 45 + integrity sha512-wdlPY2tm/9XBr7QkKlq0WQVgiuGTX6YWPyRyBviSoScBuLfTVQhvwg6wJ369GJ/1nPfTLMfnrFIfjqVg6d+jQQ== 46 + 47 + braces@^3.0.1: 48 + version "3.0.2" 49 + resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.2.tgz#3454e1a462ee8d599e236df336cd9ea4f8afe107" 50 + integrity sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A== 51 + dependencies: 52 + fill-range "^7.0.1" 53 + 54 + builtin-modules@^3.1.0: 55 + version "3.1.0" 56 + resolved "https://registry.yarnpkg.com/builtin-modules/-/builtin-modules-3.1.0.tgz#aad97c15131eb76b65b50ef208e7584cd76a7484" 57 + integrity sha512-k0KL0aWZuBt2lrxrcASWDfwOLMnodeQjodT/1SxEQAXsHANgo6ZC/VEaSEHCXt7aSTZ4/4H5LKa+tBXmW7Vtvw== 58 + 59 + estree-walker@^1.0.1: 60 + version "1.0.1" 61 + resolved "https://registry.yarnpkg.com/estree-walker/-/estree-walker-1.0.1.tgz#31bc5d612c96b704106b477e6dd5d8aa138cb700" 62 + integrity sha512-1fMXF3YP4pZZVozF8j/ZLfvnR8NSIljt56UhbZ5PeeDmmGHpgpdwQt7ITlGvYaQukCvuBRMLEiKiYC+oeIg4cg== 63 + 64 + fill-range@^7.0.1: 65 + version "7.0.1" 66 + resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-7.0.1.tgz#1919a6a7c75fe38b2c7c77e5198535da9acdda40" 67 + integrity sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ== 68 + dependencies: 69 + to-regex-range "^5.0.1" 70 + 71 + fsevents@~2.1.2: 72 + version "2.1.2" 73 + resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.1.2.tgz#4c0a1fb34bc68e543b4b82a9ec392bfbda840805" 74 + integrity sha512-R4wDiBwZ0KzpgOWetKDug1FZcYhqYnUYKtfZYt4mD5SBz76q0KR4Q9o7GIPamsVPGmW3EYPPJ0dOOjvx32ldZA== 75 + 76 + graphql@^15.0.0: 77 + version "15.0.0" 78 + resolved "https://registry.yarnpkg.com/graphql/-/graphql-15.0.0.tgz#042a5eb5e2506a2e2111ce41eb446a8e570b8be9" 79 + integrity sha512-ZyVO1xIF9F+4cxfkdhOJINM+51B06Friuv4M66W7HzUOeFd+vNzUn4vtswYINPi6sysjf1M2Ri/rwZALqgwbaQ== 80 + 81 + is-module@^1.0.0: 82 + version "1.0.0" 83 + resolved "https://registry.yarnpkg.com/is-module/-/is-module-1.0.0.tgz#3258fb69f78c14d5b815d664336b4cffb6441591" 84 + integrity sha1-Mlj7afeMFNW4FdZkM2tM/7ZEFZE= 85 + 86 + is-number@^7.0.0: 87 + version "7.0.0" 88 + resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" 89 + integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== 90 + 91 + micromatch@^4.0.2: 92 + version "4.0.2" 93 + resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-4.0.2.tgz#4fcb0999bf9fbc2fcbdd212f6d629b9a56c39259" 94 + integrity sha512-y7FpHSbMUMoyPbYUSzO6PaZ6FyRnQOpHuKwbo1G+Knck95XVU4QAiKdGEnj5wwoS7PlOgthX/09u5iFJ+aYf5Q== 95 + dependencies: 96 + braces "^3.0.1" 97 + picomatch "^2.0.5" 98 + 99 + path-parse@^1.0.6: 100 + version "1.0.6" 101 + resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.6.tgz#d62dbb5679405d72c4737ec58600e9ddcf06d24c" 102 + integrity sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw== 103 + 104 + picomatch@^2.0.5: 105 + version "2.2.2" 106 + resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.2.2.tgz#21f333e9b6b8eaff02468f5146ea406d345f4dad" 107 + integrity sha512-q0M/9eZHzmr0AulXyPwNfZjtwZ/RBZlbN3K3CErVrk50T2ASYI7Bye0EvekFY3IP1Nt2DHu0re+V2ZHIpMkuWg== 108 + 109 + resolve@^1.14.2: 110 + version "1.15.1" 111 + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.15.1.tgz#27bdcdeffeaf2d6244b95bb0f9f4b4653451f3e8" 112 + integrity sha512-84oo6ZTtoTUpjgNEr5SJyzQhzL72gaRodsSfyxC/AXRvwu0Yse9H8eF9IpGo7b8YetZhlI6v7ZQ6bKBFV/6S7w== 113 + dependencies: 114 + path-parse "^1.0.6" 115 + 116 + rollup@^2.6.1: 117 + version "2.6.1" 118 + resolved "https://registry.yarnpkg.com/rollup/-/rollup-2.6.1.tgz#8354e67caa7b8bf24c2488d9e2f64da2be62eebe" 119 + integrity sha512-1RhFDRJeg027YjBO6+JxmVWkEZY0ASztHhoEUEWxOwkh4mjO58TFD6Uo7T7Y3FbmDpRTfKhM5NVxJyimCn0Elg== 120 + optionalDependencies: 121 + fsevents "~2.1.2" 122 + 123 + to-regex-range@^5.0.1: 124 + version "5.0.1" 125 + resolved "https://registry.yarnpkg.com/to-regex-range/-/to-regex-range-5.0.1.tgz#1648c44aae7c8d988a326018ed72f5b4dd0392e4" 126 + integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== 127 + dependencies: 128 + is-number "^7.0.0"