From 0a4a6c694d60fe992e448b5957498aae8871307a Mon Sep 17 00:00:00 2001 From: Timo Stamm Date: Mon, 14 Oct 2024 18:25:26 +0200 Subject: [PATCH] Add script to guard against publishing with the wrong dist-tag (#457) --- .github/RELEASING.md | 2 +- scripts/release.mjs | 78 ++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 79 insertions(+), 1 deletion(-) create mode 100644 scripts/release.mjs diff --git a/.github/RELEASING.md b/.github/RELEASING.md index 5bc1b370..d13a023a 100644 --- a/.github/RELEASING.md +++ b/.github/RELEASING.md @@ -27,7 +27,7 @@ 7. After approval, run the following commands to publish to npmjs.com: ```bash - pnpm install && pnpm run all && pnpm --filter "./packages/*" publish + pnpm install && pnpm run all && node scripts/release.mjs ``` 8. Merge your PR. diff --git a/scripts/release.mjs b/scripts/release.mjs new file mode 100644 index 00000000..bf25ad17 --- /dev/null +++ b/scripts/release.mjs @@ -0,0 +1,78 @@ +// Copyright 2021-2024 The Connect Authors +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +import { readdirSync, readFileSync } from "fs"; +import { join } from "path"; +import { existsSync } from "node:fs"; +import { execSync } from "node:child_process"; + +/* + * Publish connect-query-es. See .github/RELEASING.md + */ + +const tag = determinePublishTag(findWorkspaceVersion("packages")); +const command = `pnpm --filter "./packages/*" publish --tag ${tag}`; +execSync(command, { + stdio: "inherit", +}); + +/** + * @param {string} version + * @returns {string} + */ +function determinePublishTag(version) { + if (/^\d+\.\d+\.\d+$/.test(version)) { + return "latest"; + } else if (/^\d+\.\d+\.\d+-alpha.*$/.test(version)) { + return "alpha"; + } else if (/^\d+\.\d+\.\d+-beta.*$/.test(version)) { + return "beta"; + } else if (/^\d+\.\d+\.\d+-rc.*$/.test(version)) { + return "rc"; + } else { + throw new Error(`Unable to determine publish tag from version ${version}`); + } +} + +/** + * @param {string} packagesDir + * @returns {string} + */ +function findWorkspaceVersion(packagesDir) { + let version = undefined; + for (const entry of readdirSync(packagesDir, { withFileTypes: true })) { + if (!entry.isDirectory()) { + continue; + } + const path = join(packagesDir, entry.name, "package.json"); + if (existsSync(path)) { + const pkg = JSON.parse(readFileSync(path, "utf-8")); + if (pkg.private === true) { + continue; + } + if (!pkg.version) { + throw new Error(`${path} is missing "version"`); + } + if (version === undefined) { + version = pkg.version; + } else if (version !== pkg.version) { + throw new Error(`${path} has unexpected version ${pkg.version}`); + } + } + } + if (version === undefined) { + throw new Error(`unable to find workspace version`); + } + return version; +}