6b863fe294
Follow-up to https://github.com/vercel/next.js/pull/32337 this removes the un-necessary step where we fetch all of the tags which requires pulling a lot of un-necessary git history inflating cache size and publish times. The only reason these tags were needing to be fetched is due to an issue in how the `actions/checkout` step works (https://github.com/actions/checkout/issues/882). This reduces the publish times by at least 4 minutes by removing the tags fetching step https://github.com/vercel/next.js/actions/runs/3598569786/jobs/6061449995#step:16:14 As a further optimization this adds concurrency to the `npm publish` calls themselves to hopefully reduce time spent there as well.
98 lines
2.3 KiB
JavaScript
Executable file
98 lines
2.3 KiB
JavaScript
Executable file
#!/usr/bin/env node
|
|
// @ts-check
|
|
|
|
const path = require('path')
|
|
const execa = require('execa')
|
|
const { Sema } = require('async-sema')
|
|
const { execSync } = require('child_process')
|
|
const { readJson, readdir } = require('fs-extra')
|
|
|
|
const cwd = process.cwd()
|
|
|
|
;(async function () {
|
|
let isCanary = true
|
|
|
|
try {
|
|
const tagOutput = execSync(
|
|
`node ${path.join(__dirname, 'check-is-release.js')}`
|
|
).toString()
|
|
console.log(tagOutput)
|
|
|
|
if (tagOutput.trim().startsWith('v')) {
|
|
isCanary = tagOutput.includes('-canary')
|
|
}
|
|
} catch (err) {
|
|
console.log(err)
|
|
|
|
if (err.message && err.message.includes('no tag exactly matches')) {
|
|
console.log('Nothing to publish, exiting...')
|
|
return
|
|
}
|
|
throw err
|
|
}
|
|
console.log(`Publishing ${isCanary ? 'canary' : 'stable'}`)
|
|
|
|
if (!process.env.NPM_TOKEN) {
|
|
console.log('No NPM_TOKEN, exiting...')
|
|
return
|
|
}
|
|
|
|
const packagesDir = path.join(cwd, 'packages')
|
|
const packageDirs = await readdir(packagesDir)
|
|
const publishSema = new Sema(2)
|
|
|
|
const publish = async (pkg, retry = 0) => {
|
|
try {
|
|
await publishSema.acquire()
|
|
await execa(
|
|
`npm`,
|
|
[
|
|
'publish',
|
|
`${path.join(packagesDir, pkg)}`,
|
|
'--access',
|
|
'public',
|
|
...(isCanary ? ['--tag', 'canary'] : []),
|
|
],
|
|
{ stdio: 'inherit' }
|
|
)
|
|
} catch (err) {
|
|
console.error(`Failed to publish ${pkg}`, err)
|
|
|
|
if (
|
|
err.message &&
|
|
err.message.includes(
|
|
'You cannot publish over the previously published versions'
|
|
)
|
|
) {
|
|
console.error('Ignoring already published error', pkg)
|
|
return
|
|
}
|
|
|
|
if (retry < 3) {
|
|
const retryDelaySeconds = 15
|
|
console.log(`retrying in ${retryDelaySeconds}s`)
|
|
await new Promise((resolve) =>
|
|
setTimeout(resolve, retryDelaySeconds * 1000)
|
|
)
|
|
await publish(pkg, retry + 1)
|
|
}
|
|
throw err
|
|
} finally {
|
|
publishSema.release()
|
|
}
|
|
}
|
|
|
|
await Promise.all(
|
|
packageDirs.map(async (packageDir) => {
|
|
const pkgJson = await readJson(
|
|
path.join(packagesDir, packageDir, 'package.json')
|
|
)
|
|
|
|
if (pkgJson.private) {
|
|
console.log(`Skipping private package ${packageDir}`)
|
|
return
|
|
}
|
|
await publish(packageDir)
|
|
})
|
|
)
|
|
})()
|