test('spins up a min app and performs various checks', async t => { await execa(IGNITE, ['new', APP_DIR, '--min']) process.chdir(APP_DIR) // check the contents of ignite/ignite.json const igniteJSON = jetpack.read('ignite/ignite.json') t.is(typeof igniteJSON, 'string') t.regex(igniteJSON, /"generators": {/) // check the Containers/App.js file const appJS = jetpack.read('App/Containers/App.js') t.regex(appJS, /class App extends Component {/) // run ignite g component await execa(IGNITE, ['g', 'component', 'Test']) t.is(jetpack.inspect('App/Components/Test.js').type, 'file') // spork a screen and edit it await execa(IGNITE, ['spork', 'component.ejs']) const sporkedFile = 'ignite/Spork/ignite-ir-boilerplate/component.ejs' t.is(jetpack.inspect(sporkedFile).type, 'file') await jetpack.write(sporkedFile, 'SPORKED!') await execa(IGNITE, ['generate', 'component', 'Sporkified']) t.is(jetpack.read('App/Components/Sporkified.js'), 'SPORKED!') // TODO: add more end-to-end tests here })
async function bootstrap({ directory, template }) { const shouldInstallScripts = process.env.CI && process.env.CI !== 'false'; await Promise.all( ['public/', 'src/', 'package.json'].map(async file => fs.copy(path.join(template, file), path.join(directory, file)) ) ); if (shouldInstallScripts) { const packageJson = fs.readJsonSync(path.join(directory, 'package.json')); packageJson.dependencies = Object.assign({}, packageJson.dependencies, { 'react-scripts': 'latest', }); fs.writeJsonSync(path.join(directory, 'package.json'), packageJson); } await execa('yarnpkg', ['install', '--mutex', 'network'], { cwd: directory }); if (!shouldInstallScripts) { fs.ensureSymlinkSync( path.resolve( path.join( __dirname, '..', 'packages', 'react-scripts', 'bin', 'react-scripts.js' ) ), path.join(directory, 'node_modules', '.bin', 'react-scripts') ); await execa('yarnpkg', ['link', 'react-scripts'], { cwd: directory }); } }
async function fn({ cwd, isFlowProject } /* : TaskOptions */) { const { pkg } = await readPkgUp({ cwd }); const pkgs = [ // we use prettier instead of standard-via-eslint 'eslint-config-semistandard', 'eslint-config-standard', 'eslint-config-standard-jsx', 'eslint-config-standard-react', 'eslint-plugin-standard', 'fixpack', // use sort-package-json now instead 'greenkeeper-postpublish', // Greenkeeper doesn't use this now 'prettier', // run this via npx instead of as a devDep ]; if (!isFlowProject) { pkgs.push('flow-bin'); } // npm 5.2.x bundle includes npx if (pkg.engines && pkg.engines.npm && !intersects(pkg.engines.npm, '<5.2')) { pkgs.push('npx'); } const deps = intersection(pkgs, Object.keys(pkg.dependencies || {})); if (deps.length) { await execa('npm', ['uninstall', '--save', ...deps], { cwd }); } const devDeps = intersection(pkgs, Object.keys(pkg.devDependencies || {})); if (devDeps.length) { await execa('npm', ['uninstall', '--save-dev', ...devDeps], { cwd }); } }
test.concurrent("bootstraps all packages", async () => { const cwd = await initFixture("BootstrapCommand/integration-lifecycle"); await execa("npm", ["install", "--cache-min=99999"], { cwd }); const { stdout, stderr } = await execa("npm", ["test", "--silent"], { cwd }); expect(stdout).toMatchSnapshot("npm postinstall: stdout"); expect(stderr).toMatchSnapshot("npm postinstall: stderr"); });
test("remoteBranchExists", async () => { const { cwd } = await cloneFixture("root-manifest-only"); expect(remoteBranchExists("origin", "new-branch", { cwd })).toBe(false); await execa("git", ["checkout", "-b", "new-branch"], { cwd }); await execa("git", ["push", "-u", "origin", "new-branch"], { cwd }); expect(remoteBranchExists("origin", "new-branch", { cwd })).toBe(true); });
test('get the trash path on a mounted drive with a top trash', async t => { const name = path.join(__dirname, 'test-disk-top'); const dirname = path.join(name, '.Trash', String(process.getuid())); await execa(path.join(__dirname, 'mount_create'), [name, '--with-trash']); const dir = await trashdir(name); t.is(dirname, dir); await execa(path.join(__dirname, 'mount_clean'), [name]); });
async function install() { await execa("rm", ["-rf", "node_modules"]); await execa("yarn", ["install"]); const status = await execa.stdout("git", ["ls-files", "-m"]); if (status) { throw Error( "The lockfile needs to be updated, commit it before making the release." ); } }
test('get the trash path on a mounted drive', async t => { const name = path.join(__dirname, 'test-disk'); const dirname = path.join(name, '.Trash-') + process.getuid(); await execa(path.join(__dirname, 'mount_create'), [name]); const dir = await trashdir(name); t.is(dirname, dir); await execa(path.join(__dirname, 'mount_clean'), [name]); });
module.exports = opts => { opts = opts || {}; const ret = readPkgUp.sync({ cwd: opts.cwd, normalize: false }); const pkg = ret.pkg || {}; const pkgPath = ret.path || path.resolve(opts.cwd || process.cwd(), 'package.json'); const pkgCwd = path.dirname(pkgPath); const cli = opts.args || process.argv.slice(2); const args = arrExclude(cli, ['--init', '--unicorn']); const cmd = 'ava' + (args.length > 0 ? ' ' + args.join(' ') : ''); const s = pkg.scripts = pkg.scripts ? pkg.scripts : {}; if (s.test && s.test !== DEFAULT_TEST_SCRIPT) { s.test = s.test.replace(/\bnode (test\/)?test\.js\b/, cmd); if (!/\bava\b/.test(s.test)) { s.test += ` && ${cmd}`; } } else { s.test = cmd; } writePkg.sync(pkgPath, pkg); const post = () => { // For personal use if (cli.indexOf('--unicorn') !== -1) { const pkg = JSON.parse(fs.readFileSync(pkgPath, 'utf8')); pkg.devDependencies.ava = '*'; writePkg.sync(pkgPath, pkg); } }; if (opts.skipInstall) { return Promise.resolve(post); } if (hasYarn(pkgCwd)) { return execa('yarn', ['add', '--dev', 'ava'], {cwd: pkgCwd}).then(post); } return execa('npm', ['install', '--save-dev', 'ava'], { cwd: pkgCwd, stdio: 'inherit' }).then(post); };
module.exports = mem(() => { const envVar = getEnvVar(); if (envVar) { return Promise.resolve(envVar); } if (process.platform === 'darwin' || process.platform === 'linux') { return execa('id', ['-un']).then(x => x.stdout).catch(noop); } else if (process.platform === 'win32') { return execa('whoami').then(x => cleanWinCmd(x.stdout)).catch(noop); } return Promise.resolve(); });
.map(projectDirectory => { const projectWorkingDirectory = path.resolve(process.cwd(), projectDirectory); const projectPackageJsonPath = path.resolve(projectWorkingDirectory, 'package.json'); const projectPackageJson = attemptRequire(projectPackageJsonPath); if (!projectPackageJson) { console.error(` Unable to read '${projectPackageJsonPath}'. Project '${projectDirectory}' is skipped.`); return; } const currentDependencyVersion = projectPackageJson.dependencies && projectPackageJson.dependencies[packageJson.name]; const currentDevDependencyVersion = projectPackageJson.devDependencies && projectPackageJson.devDependencies[packageJson.name]; if (!currentDependencyVersion && !currentDevDependencyVersion) { if (argv.verbose) { console.log(` '${projectDirectory}': skipped (does not depend).`); } return; } // Allow --check to skip actually linking. if (argv.check) { console.log(` '${projectDirectory}': Would be linked.`); return; } console.log(` '${projectDirectory}': Linking…`); return execa('npm', ['link', packageJson.name], { cwd: projectWorkingDirectory }); })
test('filter', async t => { t.is((await execa('./cli.js', [ '<a><b>c</b></a>', '--tagFilter=b', '--no-pretty' ])).stdout, filterFixture); });
it("defaults user name and email to git config", async () => { const cwd = await initRemoteFixture("basic"); const name = "Git McGitterson"; const email = "*****@*****.**"; // overwrite test defaults so it's really obvious await execa("git", ["config", "user.name", name], { cwd }); await execa("git", ["config", "user.email", email], { cwd }); // ignore test defaults as well as ~/.npmrc process.env.npm_config_userconfig = "/dev/null"; await lernaCreate(cwd)("git-fallback"); expect(await manifestCreated(cwd)).toHaveProperty("author", `${name} <${email}>`); });
test('attr', async t => { t.is((await execa('./cli.js', [ '<a id="foo"><b>c</b></a>', '--strip-attributes ', '--no-pretty' ])).stdout, noAttrFixture); });
test('instruction', async t => { t.is((await execa('./cli.js', [ '<?xml foo="blerg" ?><a><b>c</b></a>', '--no-strip-instruction ', '--no-pretty' ])).stdout, instructionFixture); });
test('comment', async t => { t.is((await execa('./cli.js', [ '<a><!-- foo --><b>c</b></a>', '--no-strip-comments ', '--no-pretty' ])).stdout, commentFixture); });
test('doctype', async t => { t.is((await execa('./cli.js', [ '<!DOCTYPE HTML "-//W3C//DTD..."><a><b>c</b></a>', '--no-strip-doctype ', '--no-pretty' ])).stdout, doctypeFixture); });
async function getOutputDevelopment({ directory, env = {} }) { try { const { stdout, stderr } = await execa( './node_modules/.bin/react-scripts', ['start', '--smoke-test'], { cwd: directory, env: Object.assign( {}, { BROWSER: 'none', PORT: await getPort(), CI: 'false', FORCE_COLOR: '0', }, env ), } ); return { stdout: stripAnsi(stdout), stderr: stripAnsi(stderr) }; } catch (err) { return { stdout: '', stderr: stripAnsi( err.message .split(os.EOL) .slice(2) .join(os.EOL) ), }; } }
module.exports.rollback = function runRollback(context) { const {dir, version, previousVersion} = context.instance; const semver = require('semver'); const contentDir = path.join(dir, 'content'); const currentDir = path.join(dir, 'current'); let knexMigratorPromise, args; // Ghost 2.0.0 uses the new knex-migrator version. We have to ensure you can still use CLI 1.9 with an older blog, because // we haven't restricted a CLI version range in Ghost (we only used cli: > X.X.X) if (semver.major(version) === 2) { args = ['--force', '--v', previousVersion, '--mgpath', currentDir]; } else { args = ['--force', '--mgpath', currentDir]; } // If we're using sqlite and the ghost user owns the content folder, then // we should run sudo, otherwise run normally if (ghostUser.shouldUseGhostUser(contentDir)) { const knexMigratorPath = path.resolve(dir, 'current/node_modules/.bin/knex-migrator-rollback'); knexMigratorPromise = context.ui.sudo(`${knexMigratorPath} ${args.join(' ')}`, {sudoArgs: '-E -u ghost'}); } else { knexMigratorPromise = execa('knex-migrator-rollback', args, { preferLocal: true, localDir: path.join(dir, 'current') }); } return knexMigratorPromise.catch(errorHandler(context)); };
task: () => execa('eslint', ['--config', path.join(cwd, 'index.js'), dest], {cwd, localDir: __dirname}) .catch(err => { if (!/✖ \d+ problems? \(\d+ errors?, \d+ warnings?\)/.test(err.message)) { err.package = name; throw err; } })
function npm(args) { const opts = { cwd: process.cwd(), stdio: isInstall(args) ? 'ignore' : 'inherit' }; return spawn('npm', args, opts); }
task: () => execa('codecov', [], { env: { FORCE_COLOR: true }, }).then(({ stdout }) => { // eslint-disable-next-line no-console console.log(stdout); }),
exports.sh = function (prog, args, cb) { execa(prog, args).then(function (result) { setImmediate(cb, null, result) }).catch(function (err) { setImmediate(cb, err) }) }
function fallback() { if (process.platform === 'darwin') { return passwdUser() .then(user => { fullname = user.fullname; return fullname; }) .catch(() => { return execa.stdout('osascript', ['-e', 'long user name of (system info)']).then(stdout => { fullname = stdout; return fullname; }); }); } if (process.platform === 'win32') { // try git first since fullname is usually not set by default in the system on Windows 7+ return execa('git', ['config', '--global', 'user.name']) .then(res => { fullname = res.stdout; if (!fullname) { throw new Error(); } }) .catch(() => { return execa.stdout('wmic', ['useraccount', 'where', 'name="%username%"', 'get', 'fullname']) .then(stdout => { fullname = stdout.replace('FullName', ''); return fullname; }); }); } return passwdUser() .then(user => { fullname = user.fullname; if (!fullname) { throw new Error(); } }) .catch(() => { return execa.shell('getent passwd $(whoami)') .then(res => { fullname = (res.stdout.split(':')[4] || '').replace(/,.*/, ''); if (!fullname) { throw new Error(); } }); }) .catch(() => { return execa.stdout('git', ['config', '--global', 'user.name']) .then(stdout => { fullname = stdout; return fullname; }); }); }
test('cdata', async t => { t.is((await execa('./cli.js', [ '<a><![CDATA[ my-cdata ]]><b>c</b></a>', '--no-strip-cdata', '--no-pretty' ])).stdout, cdataFixture); });
test('No input', async t => { await execa('./cli.js').catch(err => { console.log(err); t.is(err.stderr, 'No matching color. See --help.\n'); t.is(err.code, 1); }); });
return new PCancelable((onCancel, resolve, reject) => { const converter = execa(ffmpegPath, args); let amountOfFrames; onCancel(() => { converter.kill(); }); converter.stderr.on('data', data => { data = data.toString().trim(); const matchesDuration = durationRegex.exec(data); const matchesFrame = frameRegex.exec(data); if (matchesDuration) { amountOfFrames = Math.ceil(moment.duration(matchesDuration[1]).asSeconds() * 30); } else if (matchesFrame) { const currentFrame = matchesFrame[1]; opts.progressCallback(currentFrame / amountOfFrames); } }); converter.on('error', reject); converter.on('exit', code => { if (code === 0) { resolve(outputPath); } else { reject(code); } }); converter.catch(reject); });
function exec (cmd, args, opts, callback) { if (typeof opts === 'function') { callback = opts opts = {} } opts = Object.assign({}, { stdout: noop, stderr: noop }, opts) log(path.basename(cmd), args.join(' ')) const command = execa(cmd, args, { env: opts.env }) command.stderr.on('data', opts.stderr) command.stdout.on('data', opts.stdout) command .then(r => { callback(null, r) }) .catch(err => { callback(err) }) return command }
gulp.task('test:ignorefailure', function (callback) { const p = execa('gulp', ['cucumber:ignorefailure']); const chunks = []; p.stderr.pipe(process.stderr); p.stdout.pipe(process.stdout); p.stdout.setEncoding('utf8'); p.stdout.on('data', function (chunk) { chunks.push(chunk); }); p.on('close', function (status) { try { if (status !== 0) { throw new Error('gulp-cucumber exited: ' + status); } else { const text = chunks.join(''); expect(text).to.match(/Starting 'cucumber:ignorefailure'.../); expect(text).to.match(/Meow!/); expect(text).to.match(/AssertionError/); expect(text).to.match(/-100/); expect(text).to.match(/\+200/); expect(text).to.match(/Finished 'cucumber:ignorefailure'/); } callback(); } catch (e) { callback(e); } }); });
function prune () { if (!config.prune) { return Promise.resolve() } const prefix = config.archivePrefix ? ['--prefix', config.archivePrefix] : [] return runCommandAndWriteToFile( execa( config.borgPath || 'borg', [ 'prune', config.repository, '-v', '--show-rc', '--list', ...prefix, ...(config.prune.options || []) ], execaOptions ), 'prune' ) }