|
| 1 | +#!/usr/bin/env node |
| 2 | +const fs = require('fs'); |
| 3 | +const childProcess = require('child_process'); |
| 4 | +const _ = require('lodash'); |
| 5 | + |
| 6 | +const WORKDIR = process.cwd(); |
| 7 | +const PACKAGE_DIR = `${WORKDIR}/project`; |
| 8 | +const SRC_DIR = `${PACKAGE_DIR}/src`; |
| 9 | +const DOCGENCONFIG_PATH = `${PACKAGE_DIR}/docgen.json`; |
| 10 | +const TSCONFIG_PATH = `${PACKAGE_DIR}/tsconfig.json`; |
| 11 | +const PACKAGEJSON_PATH = `${PACKAGE_DIR}/package.json`; |
| 12 | + |
| 13 | +if (!fs.existsSync(SRC_DIR)) { throw new Error(`${SRC_DIR} does not exist`) } |
| 14 | +if (!fs.existsSync(DOCGENCONFIG_PATH)) { throw new Error(`${DOCGENCONFIG_PATH} does not exist`); } |
| 15 | + |
| 16 | +const PACKAGEJSON = JSON.parse(fs.readFileSync(PACKAGEJSON_PATH)); |
| 17 | +const DOCGENCONFIG = getDocgenConfig(); |
| 18 | +const TSCONFIG_COPY = JSON.parse(fs.readFileSync(TSCONFIG_PATH).toString()); |
| 19 | + |
| 20 | +// Merge tsconfig block from docgen.json into tsconfig.json |
| 21 | +_.merge(TSCONFIG_COPY, DOCGENCONFIG.tsconfig); |
| 22 | +fs.writeFileSync(`${WORKDIR}/tsconfig.json`, JSON.stringify(TSCONFIG_COPY, null, 2)); |
| 23 | + |
| 24 | +function getDocgenConfig() { |
| 25 | + const config = JSON.parse(fs.readFileSync(DOCGENCONFIG_PATH)); |
| 26 | + const requiredKeys = ['navigation', 'tsconfig']; |
| 27 | + const missing = requiredKeys.find((key) => !_.has(config, key)); |
| 28 | + if (missing) { |
| 29 | + console.error(`${DOCGENCONFIG_PATH} does not contain configuration key: '${missing}'`); |
| 30 | + process.exit(1); |
| 31 | + } |
| 32 | + return config; |
| 33 | +} |
| 34 | + |
| 35 | +// Fetch all included packages (i.e., core module) |
| 36 | +const CLONE_COMMANDS = ['#!/usr/bin/env bash', 'set -x']; |
| 37 | + |
| 38 | +(DOCGENCONFIG.include || []).forEach(include => { |
| 39 | + const { pkg, repo, branch } = include; |
| 40 | + const semver = ['peerDependencies', 'dependencies', 'devDependencies'] |
| 41 | + .map((key) => (PACKAGEJSON[key] || {})[pkg]) |
| 42 | + .find((x) => !!x); |
| 43 | + |
| 44 | + const version = branch || findSemverPackage(pkg, semver); |
| 45 | + CLONE_COMMANDS.push(`./clone.sh ${repo} ${PACKAGE_DIR}/src/includes/${pkg} ${version}`); |
| 46 | +}); |
| 47 | + |
| 48 | +fs.writeFileSync('clone_repos.sh', CLONE_COMMANDS.join('\n')); |
| 49 | + |
| 50 | +// Finds the newest version of a package published to NPM that matches the desired semver range |
| 51 | +function findSemverPackage(packageName, semver) { |
| 52 | + const stdout = childProcess.execSync(`npm info ${packageName}@${semver} version`).toString(); |
| 53 | + const lines = stdout.split(/\n/).filter(x => x.length); |
| 54 | + if (lines.length === 0) { |
| 55 | + throw new Error(`No published package matched ${packageName}@${semver}`) |
| 56 | + } else if (lines.length === 1) { |
| 57 | + return lines[ 0 ]; |
| 58 | + } else { |
| 59 | + const line = stdout.trim().split(/\n/).pop().trim(); |
| 60 | + const [, version] = /.* '(.*)'$/.exec(line) || []; |
| 61 | + if (!version) { |
| 62 | + console.log({ stdout, line }); |
| 63 | + throw new Error(`Couldn't find version matching ${packageName}@${semver} in npm registry`) |
| 64 | + } |
| 65 | + return version; |
| 66 | + } |
| 67 | +} |
0 commit comments