pubm 0.0.4 → 0.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +60 -126
- package/bin/cli.js +958 -315
- package/dist/index.cjs +999 -83
- package/dist/index.d.cts +183 -2
- package/dist/index.d.ts +183 -2
- package/dist/index.js +980 -82
- package/package.json +92 -84
package/dist/index.js
CHANGED
|
@@ -711,7 +711,7 @@ var init_mjs = __esm({
|
|
|
711
711
|
"node_modules/.pnpm/signal-exit@4.1.0/node_modules/signal-exit/dist/mjs/index.js"() {
|
|
712
712
|
"use strict";
|
|
713
713
|
init_signals();
|
|
714
|
-
processOk = (
|
|
714
|
+
processOk = (process16) => !!process16 && typeof process16 === "object" && typeof process16.removeListener === "function" && typeof process16.emit === "function" && typeof process16.reallyExit === "function" && typeof process16.listeners === "function" && typeof process16.kill === "function" && typeof process16.pid === "number" && typeof process16.on === "function";
|
|
715
715
|
kExitEmitter = Symbol.for("signal-exit emitter");
|
|
716
716
|
global = globalThis;
|
|
717
717
|
ObjectDefineProperty = Object.defineProperty.bind(Object);
|
|
@@ -793,7 +793,7 @@ var init_mjs = __esm({
|
|
|
793
793
|
}
|
|
794
794
|
};
|
|
795
795
|
SignalExit = class extends SignalExitBase {
|
|
796
|
-
constructor(
|
|
796
|
+
constructor(process16) {
|
|
797
797
|
super();
|
|
798
798
|
__privateAdd(this, _SignalExit_instances);
|
|
799
799
|
// "SIGHUP" throws an `ENOSYS` error on Windows,
|
|
@@ -807,13 +807,13 @@ var init_mjs = __esm({
|
|
|
807
807
|
__privateAdd(this, _originalProcessReallyExit);
|
|
808
808
|
__privateAdd(this, _sigListeners, {});
|
|
809
809
|
__privateAdd(this, _loaded, false);
|
|
810
|
-
__privateSet(this, _process,
|
|
810
|
+
__privateSet(this, _process, process16);
|
|
811
811
|
__privateSet(this, _sigListeners, {});
|
|
812
812
|
for (const sig of signals) {
|
|
813
813
|
__privateGet(this, _sigListeners)[sig] = () => {
|
|
814
814
|
const listeners = __privateGet(this, _process).listeners(sig);
|
|
815
815
|
let { count } = __privateGet(this, _emitter);
|
|
816
|
-
const p =
|
|
816
|
+
const p = process16;
|
|
817
817
|
if (typeof p.__signal_exit_emitter__ === "object" && typeof p.__signal_exit_emitter__.count === "number") {
|
|
818
818
|
count += p.__signal_exit_emitter__.count;
|
|
819
819
|
}
|
|
@@ -822,12 +822,12 @@ var init_mjs = __esm({
|
|
|
822
822
|
const ret = __privateGet(this, _emitter).emit("exit", null, sig);
|
|
823
823
|
const s = sig === "SIGHUP" ? __privateGet(this, _hupSig) : sig;
|
|
824
824
|
if (!ret)
|
|
825
|
-
|
|
825
|
+
process16.kill(process16.pid, s);
|
|
826
826
|
}
|
|
827
827
|
};
|
|
828
828
|
}
|
|
829
|
-
__privateSet(this, _originalProcessReallyExit,
|
|
830
|
-
__privateSet(this, _originalProcessEmit,
|
|
829
|
+
__privateSet(this, _originalProcessReallyExit, process16.reallyExit);
|
|
830
|
+
__privateSet(this, _originalProcessEmit, process16.emit);
|
|
831
831
|
}
|
|
832
832
|
onExit(cb, opts) {
|
|
833
833
|
if (!processOk(__privateGet(this, _process))) {
|
|
@@ -4376,7 +4376,7 @@ var Listr = (_a23 = class {
|
|
|
4376
4376
|
// src/tasks/runner.ts
|
|
4377
4377
|
import SemVer from "semver";
|
|
4378
4378
|
import { isCI as isCI2 } from "std-env";
|
|
4379
|
-
import { exec as
|
|
4379
|
+
import { exec as exec7 } from "tinyexec";
|
|
4380
4380
|
|
|
4381
4381
|
// src/error.ts
|
|
4382
4382
|
var AbstractError = class extends Error {
|
|
@@ -4391,10 +4391,13 @@ function replaceCode(code) {
|
|
|
4391
4391
|
}
|
|
4392
4392
|
function formatError(error) {
|
|
4393
4393
|
if (!(error instanceof Error)) return `${error}`;
|
|
4394
|
-
const message = typeof error.message === "string" ? replaceCode(error.message) :
|
|
4394
|
+
const message = typeof error.message === "string" ? replaceCode(error.message) : (
|
|
4395
|
+
/* v8 ignore next */
|
|
4396
|
+
formatError(error)
|
|
4397
|
+
);
|
|
4395
4398
|
let stringifyError = `${color.bgRed(` ${error.name} `)}${color.reset("")} ${message}
|
|
4396
4399
|
`;
|
|
4397
|
-
stringifyError += error.stack?.split("\n").slice(1).join("\n").replace(/at/g, color.dim("at")).replace(/\(([
|
|
4400
|
+
stringifyError += error.stack?.split("\n").slice(1).join("\n").replace(/at/g, color.dim("at")).replace(/\(([^(].+)\)/g, `(${color.blue("$1")})`);
|
|
4398
4401
|
if (error.cause) {
|
|
4399
4402
|
stringifyError += "\n\nCaused: ";
|
|
4400
4403
|
stringifyError += formatError(error.cause);
|
|
@@ -4425,8 +4428,7 @@ var GitError = class extends AbstractError {
|
|
|
4425
4428
|
};
|
|
4426
4429
|
var Git = class {
|
|
4427
4430
|
async git(args) {
|
|
4428
|
-
const { stdout
|
|
4429
|
-
if (stderr) throw stderr;
|
|
4431
|
+
const { stdout } = await exec2("git", args, { throwOnError: true });
|
|
4430
4432
|
return stdout;
|
|
4431
4433
|
}
|
|
4432
4434
|
async userName() {
|
|
@@ -4447,7 +4449,7 @@ var Git = class {
|
|
|
4447
4449
|
}
|
|
4448
4450
|
async tags() {
|
|
4449
4451
|
try {
|
|
4450
|
-
return (await this.git(["tag", "-l"])).trim().split("\n").
|
|
4452
|
+
return (await this.git(["tag", "-l"])).trim().split("\n").sort(semver.compareIdentifiers);
|
|
4451
4453
|
} catch (error) {
|
|
4452
4454
|
throw new GitError("Failed to run `git config --get user.name`", {
|
|
4453
4455
|
cause: error
|
|
@@ -4457,7 +4459,8 @@ var Git = class {
|
|
|
4457
4459
|
async previousTag(tag) {
|
|
4458
4460
|
try {
|
|
4459
4461
|
const tags = await this.tags();
|
|
4460
|
-
|
|
4462
|
+
const strip = (t) => t.replace(/^v/, "");
|
|
4463
|
+
return tags.at(tags.findIndex((t) => strip(t) === strip(tag)) - 1) ?? null;
|
|
4461
4464
|
} catch {
|
|
4462
4465
|
return null;
|
|
4463
4466
|
}
|
|
@@ -4562,13 +4565,8 @@ var Git = class {
|
|
|
4562
4565
|
async checkTagExist(tag) {
|
|
4563
4566
|
try {
|
|
4564
4567
|
return (await this.git(["rev-parse", "-q", "--verify", `refs/tags/${tag}`])).trim() !== "";
|
|
4565
|
-
} catch
|
|
4566
|
-
|
|
4567
|
-
`Failed to run \`git rev-parse -q --verify refs/tags/${tag}\``,
|
|
4568
|
-
{
|
|
4569
|
-
cause: error
|
|
4570
|
-
}
|
|
4571
|
-
);
|
|
4568
|
+
} catch {
|
|
4569
|
+
return false;
|
|
4572
4570
|
}
|
|
4573
4571
|
}
|
|
4574
4572
|
async deleteTag(tag) {
|
|
@@ -4919,17 +4917,222 @@ async function getPackageManager() {
|
|
|
4919
4917
|
return "npm";
|
|
4920
4918
|
}
|
|
4921
4919
|
|
|
4920
|
+
// src/ecosystem/rust.ts
|
|
4921
|
+
import { readFile as readFile2, stat as stat2, writeFile as writeFile2 } from "node:fs/promises";
|
|
4922
|
+
import path2 from "node:path";
|
|
4923
|
+
import { parse, stringify } from "smol-toml";
|
|
4924
|
+
|
|
4925
|
+
// src/ecosystem/ecosystem.ts
|
|
4926
|
+
var Ecosystem = class {
|
|
4927
|
+
constructor(packagePath) {
|
|
4928
|
+
this.packagePath = packagePath;
|
|
4929
|
+
}
|
|
4930
|
+
};
|
|
4931
|
+
|
|
4932
|
+
// src/ecosystem/rust.ts
|
|
4933
|
+
var RustEcosystem = class extends Ecosystem {
|
|
4934
|
+
static async detect(packagePath) {
|
|
4935
|
+
try {
|
|
4936
|
+
return (await stat2(path2.join(packagePath, "Cargo.toml"))).isFile();
|
|
4937
|
+
} catch {
|
|
4938
|
+
return false;
|
|
4939
|
+
}
|
|
4940
|
+
}
|
|
4941
|
+
async readCargoToml() {
|
|
4942
|
+
const raw = await readFile2(
|
|
4943
|
+
path2.join(this.packagePath, "Cargo.toml"),
|
|
4944
|
+
"utf-8"
|
|
4945
|
+
);
|
|
4946
|
+
return parse(raw);
|
|
4947
|
+
}
|
|
4948
|
+
async packageName() {
|
|
4949
|
+
const cargo = await this.readCargoToml();
|
|
4950
|
+
const pkg = cargo.package;
|
|
4951
|
+
return pkg.name;
|
|
4952
|
+
}
|
|
4953
|
+
async readVersion() {
|
|
4954
|
+
const cargo = await this.readCargoToml();
|
|
4955
|
+
const pkg = cargo.package;
|
|
4956
|
+
return pkg.version;
|
|
4957
|
+
}
|
|
4958
|
+
async writeVersion(newVersion) {
|
|
4959
|
+
const filePath = path2.join(this.packagePath, "Cargo.toml");
|
|
4960
|
+
const raw = await readFile2(filePath, "utf-8");
|
|
4961
|
+
const cargo = parse(raw);
|
|
4962
|
+
const pkg = cargo.package;
|
|
4963
|
+
pkg.version = newVersion;
|
|
4964
|
+
await writeFile2(filePath, stringify(cargo));
|
|
4965
|
+
}
|
|
4966
|
+
manifestFiles() {
|
|
4967
|
+
return ["Cargo.toml"];
|
|
4968
|
+
}
|
|
4969
|
+
defaultTestCommand() {
|
|
4970
|
+
return "cargo test";
|
|
4971
|
+
}
|
|
4972
|
+
defaultBuildCommand() {
|
|
4973
|
+
return "cargo build --release";
|
|
4974
|
+
}
|
|
4975
|
+
supportedRegistries() {
|
|
4976
|
+
return ["crates"];
|
|
4977
|
+
}
|
|
4978
|
+
};
|
|
4979
|
+
|
|
4980
|
+
// src/registry/crates.ts
|
|
4981
|
+
import { exec as exec3 } from "tinyexec";
|
|
4982
|
+
|
|
4983
|
+
// src/registry/registry.ts
|
|
4984
|
+
var Registry = class {
|
|
4985
|
+
constructor(packageName, registry) {
|
|
4986
|
+
this.packageName = packageName;
|
|
4987
|
+
this.registry = registry;
|
|
4988
|
+
}
|
|
4989
|
+
};
|
|
4990
|
+
|
|
4991
|
+
// src/registry/crates.ts
|
|
4992
|
+
var CratesError = class extends AbstractError {
|
|
4993
|
+
constructor() {
|
|
4994
|
+
super(...arguments);
|
|
4995
|
+
__publicField(this, "name", "crates.io Error");
|
|
4996
|
+
}
|
|
4997
|
+
};
|
|
4998
|
+
var USER_AGENT = "pubm (https://github.com/syi0808/pubm)";
|
|
4999
|
+
var CratesRegistry = class extends Registry {
|
|
5000
|
+
constructor() {
|
|
5001
|
+
super(...arguments);
|
|
5002
|
+
__publicField(this, "registry", "https://crates.io");
|
|
5003
|
+
}
|
|
5004
|
+
get headers() {
|
|
5005
|
+
return { "User-Agent": USER_AGENT };
|
|
5006
|
+
}
|
|
5007
|
+
async ping() {
|
|
5008
|
+
try {
|
|
5009
|
+
const response = await fetch(`${this.registry}/api/v1`, {
|
|
5010
|
+
headers: this.headers
|
|
5011
|
+
});
|
|
5012
|
+
return response.ok;
|
|
5013
|
+
} catch (error) {
|
|
5014
|
+
throw new CratesError("Failed to ping crates.io", { cause: error });
|
|
5015
|
+
}
|
|
5016
|
+
}
|
|
5017
|
+
async isInstalled() {
|
|
5018
|
+
try {
|
|
5019
|
+
await exec3("cargo", ["--version"]);
|
|
5020
|
+
return true;
|
|
5021
|
+
} catch {
|
|
5022
|
+
return false;
|
|
5023
|
+
}
|
|
5024
|
+
}
|
|
5025
|
+
async distTags() {
|
|
5026
|
+
return [];
|
|
5027
|
+
}
|
|
5028
|
+
async version() {
|
|
5029
|
+
try {
|
|
5030
|
+
const response = await fetch(
|
|
5031
|
+
`${this.registry}/api/v1/crates/${this.packageName}`,
|
|
5032
|
+
{ headers: this.headers }
|
|
5033
|
+
);
|
|
5034
|
+
if (!response.ok) {
|
|
5035
|
+
throw new Error(`Crate '${this.packageName}' not found`);
|
|
5036
|
+
}
|
|
5037
|
+
const data = await response.json();
|
|
5038
|
+
return data.crate.max_version;
|
|
5039
|
+
} catch (error) {
|
|
5040
|
+
throw new CratesError(
|
|
5041
|
+
`Failed to fetch version for crate '${this.packageName}'`,
|
|
5042
|
+
{ cause: error }
|
|
5043
|
+
);
|
|
5044
|
+
}
|
|
5045
|
+
}
|
|
5046
|
+
async publish() {
|
|
5047
|
+
try {
|
|
5048
|
+
await exec3("cargo", ["publish"], { throwOnError: true });
|
|
5049
|
+
return true;
|
|
5050
|
+
} catch (error) {
|
|
5051
|
+
throw new CratesError("Failed to run `cargo publish`", {
|
|
5052
|
+
cause: error
|
|
5053
|
+
});
|
|
5054
|
+
}
|
|
5055
|
+
}
|
|
5056
|
+
async isPublished() {
|
|
5057
|
+
try {
|
|
5058
|
+
const response = await fetch(
|
|
5059
|
+
`${this.registry}/api/v1/crates/${this.packageName}`,
|
|
5060
|
+
{ headers: this.headers }
|
|
5061
|
+
);
|
|
5062
|
+
return response.ok;
|
|
5063
|
+
} catch {
|
|
5064
|
+
return false;
|
|
5065
|
+
}
|
|
5066
|
+
}
|
|
5067
|
+
async hasPermission() {
|
|
5068
|
+
if (process.env.CARGO_REGISTRY_TOKEN) return true;
|
|
5069
|
+
return this.isInstalled();
|
|
5070
|
+
}
|
|
5071
|
+
async isPackageNameAvaliable() {
|
|
5072
|
+
try {
|
|
5073
|
+
const response = await fetch(
|
|
5074
|
+
`${this.registry}/api/v1/crates/${this.packageName}`,
|
|
5075
|
+
{ headers: this.headers }
|
|
5076
|
+
);
|
|
5077
|
+
return !response.ok;
|
|
5078
|
+
} catch {
|
|
5079
|
+
return true;
|
|
5080
|
+
}
|
|
5081
|
+
}
|
|
5082
|
+
};
|
|
5083
|
+
async function cratesRegistry(packageName) {
|
|
5084
|
+
return new CratesRegistry(packageName);
|
|
5085
|
+
}
|
|
5086
|
+
|
|
5087
|
+
// src/tasks/crates.ts
|
|
5088
|
+
var CratesError2 = class extends AbstractError {
|
|
5089
|
+
constructor(message, { cause } = {}) {
|
|
5090
|
+
super(message, { cause });
|
|
5091
|
+
__publicField(this, "name", "crates.io Error");
|
|
5092
|
+
this.stack = "";
|
|
5093
|
+
}
|
|
5094
|
+
};
|
|
5095
|
+
async function getCrateName() {
|
|
5096
|
+
const eco = new RustEcosystem(process.cwd());
|
|
5097
|
+
return await eco.packageName();
|
|
5098
|
+
}
|
|
5099
|
+
var cratesAvailableCheckTasks = {
|
|
5100
|
+
title: "Checking crates.io availability",
|
|
5101
|
+
task: async () => {
|
|
5102
|
+
const packageName = await getCrateName();
|
|
5103
|
+
const registry = new CratesRegistry(packageName);
|
|
5104
|
+
if (!await registry.isInstalled()) {
|
|
5105
|
+
throw new CratesError2(
|
|
5106
|
+
"cargo is not installed. Please install Rust toolchain to proceed."
|
|
5107
|
+
);
|
|
5108
|
+
}
|
|
5109
|
+
if (!await registry.hasPermission()) {
|
|
5110
|
+
throw new CratesError2(
|
|
5111
|
+
"No crates.io credentials found. Run `cargo login` or set CARGO_REGISTRY_TOKEN."
|
|
5112
|
+
);
|
|
5113
|
+
}
|
|
5114
|
+
}
|
|
5115
|
+
};
|
|
5116
|
+
var cratesPublishTasks = {
|
|
5117
|
+
title: "Publishing to crates.io",
|
|
5118
|
+
task: async () => {
|
|
5119
|
+
const packageName = await getCrateName();
|
|
5120
|
+
const registry = new CratesRegistry(packageName);
|
|
5121
|
+
await registry.publish();
|
|
5122
|
+
}
|
|
5123
|
+
};
|
|
5124
|
+
|
|
4922
5125
|
// src/tasks/jsr.ts
|
|
4923
5126
|
import process8 from "node:process";
|
|
4924
5127
|
import { ListrEnquirerPromptAdapter } from "@listr2/prompt-adapter-enquirer";
|
|
4925
5128
|
|
|
4926
5129
|
// src/registry/jsr.ts
|
|
4927
|
-
import { exec as
|
|
5130
|
+
import { NonZeroExitError, exec as exec4 } from "tinyexec";
|
|
4928
5131
|
|
|
4929
5132
|
// src/utils/db.ts
|
|
4930
5133
|
import { createCipheriv, createDecipheriv, createHash } from "node:crypto";
|
|
4931
5134
|
import { mkdirSync, readFileSync, statSync, writeFileSync } from "node:fs";
|
|
4932
|
-
import
|
|
5135
|
+
import path3 from "node:path";
|
|
4933
5136
|
var a = "aes-256-cbc";
|
|
4934
5137
|
var n = statSync(import.meta.dirname);
|
|
4935
5138
|
var k = `${n.rdev}${n.birthtimeMs}${n.nlink}${n.gid}`;
|
|
@@ -4944,7 +5147,7 @@ function d(g, h) {
|
|
|
4944
5147
|
}
|
|
4945
5148
|
var Db = class {
|
|
4946
5149
|
constructor() {
|
|
4947
|
-
__publicField(this, "path",
|
|
5150
|
+
__publicField(this, "path", path3.resolve(import.meta.dirname, ".pubm"));
|
|
4948
5151
|
try {
|
|
4949
5152
|
if (!statSync(this.path).isDirectory()) {
|
|
4950
5153
|
mkdirSync(this.path);
|
|
@@ -4955,7 +5158,7 @@ var Db = class {
|
|
|
4955
5158
|
}
|
|
4956
5159
|
set(field, value) {
|
|
4957
5160
|
writeFileSync(
|
|
4958
|
-
|
|
5161
|
+
path3.resolve(this.path, Buffer.from(e(field, field)).toString("base64")),
|
|
4959
5162
|
Buffer.from(e(`${value}`, field)),
|
|
4960
5163
|
{ encoding: "binary" }
|
|
4961
5164
|
);
|
|
@@ -4965,7 +5168,7 @@ var Db = class {
|
|
|
4965
5168
|
return d(
|
|
4966
5169
|
Buffer.from(
|
|
4967
5170
|
readFileSync(
|
|
4968
|
-
|
|
5171
|
+
path3.resolve(
|
|
4969
5172
|
this.path,
|
|
4970
5173
|
Buffer.from(e(field, field)).toString("base64")
|
|
4971
5174
|
)
|
|
@@ -5020,14 +5223,6 @@ function isValidPackageName(packageName) {
|
|
|
5020
5223
|
return true;
|
|
5021
5224
|
}
|
|
5022
5225
|
|
|
5023
|
-
// src/registry/registry.ts
|
|
5024
|
-
var Registry = class {
|
|
5025
|
-
constructor(packageName, registry) {
|
|
5026
|
-
this.packageName = packageName;
|
|
5027
|
-
this.registry = registry;
|
|
5028
|
-
}
|
|
5029
|
-
};
|
|
5030
|
-
|
|
5031
5226
|
// src/registry/jsr.ts
|
|
5032
5227
|
var JsrError = class extends AbstractError {
|
|
5033
5228
|
constructor() {
|
|
@@ -5048,13 +5243,12 @@ var JsrRegisry = class extends Registry {
|
|
|
5048
5243
|
this.client = new JsrClient(getApiEndpoint(this.registry));
|
|
5049
5244
|
}
|
|
5050
5245
|
async jsr(args) {
|
|
5051
|
-
const { stdout
|
|
5052
|
-
if (stderr) throw stderr;
|
|
5246
|
+
const { stdout } = await exec4("jsr", args, { throwOnError: true });
|
|
5053
5247
|
return stdout;
|
|
5054
5248
|
}
|
|
5055
5249
|
async isInstalled() {
|
|
5056
5250
|
try {
|
|
5057
|
-
await this.jsr(["--
|
|
5251
|
+
await this.jsr(["--version"]);
|
|
5058
5252
|
return true;
|
|
5059
5253
|
} catch {
|
|
5060
5254
|
return false;
|
|
@@ -5065,12 +5259,11 @@ var JsrRegisry = class extends Registry {
|
|
|
5065
5259
|
}
|
|
5066
5260
|
async ping() {
|
|
5067
5261
|
try {
|
|
5068
|
-
const { stdout
|
|
5069
|
-
|
|
5070
|
-
"-c",
|
|
5071
|
-
|
|
5072
|
-
|
|
5073
|
-
if (stderr) throw stderr;
|
|
5262
|
+
const { stdout } = await exec4(
|
|
5263
|
+
"ping",
|
|
5264
|
+
[new URL(this.registry).hostname, "-c", "1"],
|
|
5265
|
+
{ throwOnError: true }
|
|
5266
|
+
);
|
|
5074
5267
|
return stdout.includes("1 packets transmitted");
|
|
5075
5268
|
} catch (error) {
|
|
5076
5269
|
throw new JsrError(
|
|
@@ -5081,7 +5274,7 @@ var JsrRegisry = class extends Registry {
|
|
|
5081
5274
|
}
|
|
5082
5275
|
async publish() {
|
|
5083
5276
|
try {
|
|
5084
|
-
await
|
|
5277
|
+
await exec4(
|
|
5085
5278
|
"jsr",
|
|
5086
5279
|
["publish", "--allow-dirty", "--token", `${JsrClient.token}`],
|
|
5087
5280
|
{
|
|
@@ -5090,8 +5283,10 @@ var JsrRegisry = class extends Registry {
|
|
|
5090
5283
|
);
|
|
5091
5284
|
return true;
|
|
5092
5285
|
} catch (error) {
|
|
5286
|
+
const stderr = error instanceof NonZeroExitError ? error.output?.stderr : void 0;
|
|
5093
5287
|
throw new JsrError(
|
|
5094
|
-
|
|
5288
|
+
`Failed to run \`jsr publish --allow-dirty --token ***\`${stderr ? `
|
|
5289
|
+
${stderr}` : ""}`,
|
|
5095
5290
|
{
|
|
5096
5291
|
cause: error
|
|
5097
5292
|
}
|
|
@@ -5272,7 +5467,7 @@ async function jsrRegistry() {
|
|
|
5272
5467
|
}
|
|
5273
5468
|
|
|
5274
5469
|
// src/registry/npm.ts
|
|
5275
|
-
import { exec as
|
|
5470
|
+
import { NonZeroExitError as NonZeroExitError2, exec as exec5 } from "tinyexec";
|
|
5276
5471
|
var NpmError = class extends AbstractError {
|
|
5277
5472
|
constructor() {
|
|
5278
5473
|
super(...arguments);
|
|
@@ -5285,13 +5480,12 @@ var NpmRegistry = class extends Registry {
|
|
|
5285
5480
|
__publicField(this, "registry", "https://registry.npmjs.org");
|
|
5286
5481
|
}
|
|
5287
5482
|
async npm(args) {
|
|
5288
|
-
const { stdout
|
|
5289
|
-
if (stderr) throw stderr;
|
|
5483
|
+
const { stdout } = await exec5("npm", args, { throwOnError: true });
|
|
5290
5484
|
return stdout;
|
|
5291
5485
|
}
|
|
5292
5486
|
async isInstalled() {
|
|
5293
5487
|
try {
|
|
5294
|
-
await this.npm(["--
|
|
5488
|
+
await this.npm(["--version"]);
|
|
5295
5489
|
return true;
|
|
5296
5490
|
} catch {
|
|
5297
5491
|
return false;
|
|
@@ -5330,7 +5524,7 @@ var NpmRegistry = class extends Registry {
|
|
|
5330
5524
|
await this.npm(["whoami"]);
|
|
5331
5525
|
return true;
|
|
5332
5526
|
} catch (error) {
|
|
5333
|
-
if (
|
|
5527
|
+
if (error instanceof NonZeroExitError2 && error.output?.stderr.includes("ENEEDAUTH")) {
|
|
5334
5528
|
return false;
|
|
5335
5529
|
}
|
|
5336
5530
|
throw new NpmError("Failed to run `npm whoami`", { cause: error });
|
|
@@ -5382,7 +5576,7 @@ var NpmRegistry = class extends Registry {
|
|
|
5382
5576
|
}
|
|
5383
5577
|
async ping() {
|
|
5384
5578
|
try {
|
|
5385
|
-
await
|
|
5579
|
+
await exec5("npm", ["ping"], { throwOnError: true });
|
|
5386
5580
|
return true;
|
|
5387
5581
|
} catch (error) {
|
|
5388
5582
|
throw new NpmError("Failed to run `npm ping`", { cause: error });
|
|
@@ -5390,15 +5584,12 @@ var NpmRegistry = class extends Registry {
|
|
|
5390
5584
|
}
|
|
5391
5585
|
async publishProvenance() {
|
|
5392
5586
|
try {
|
|
5393
|
-
|
|
5394
|
-
await this.npm(["publish", "--provenance", "--access", "public"]);
|
|
5395
|
-
} catch (error) {
|
|
5396
|
-
if (`${error}`.includes("EOTP")) {
|
|
5397
|
-
return false;
|
|
5398
|
-
}
|
|
5399
|
-
}
|
|
5587
|
+
await this.npm(["publish", "--provenance", "--access", "public"]);
|
|
5400
5588
|
return true;
|
|
5401
5589
|
} catch (error) {
|
|
5590
|
+
if (error instanceof NonZeroExitError2 && error.output?.stderr.includes("EOTP")) {
|
|
5591
|
+
return false;
|
|
5592
|
+
}
|
|
5402
5593
|
throw new NpmError(
|
|
5403
5594
|
"Failed to run `npm publish --provenance --access public`",
|
|
5404
5595
|
{
|
|
@@ -5410,15 +5601,12 @@ var NpmRegistry = class extends Registry {
|
|
|
5410
5601
|
async publish(otp) {
|
|
5411
5602
|
const args = otp ? ["publish", "--otp", otp] : ["publish"];
|
|
5412
5603
|
try {
|
|
5413
|
-
|
|
5414
|
-
await this.npm(args);
|
|
5415
|
-
} catch (error) {
|
|
5416
|
-
if (`${error}`.includes("EOTP")) {
|
|
5417
|
-
return false;
|
|
5418
|
-
}
|
|
5419
|
-
}
|
|
5604
|
+
await this.npm(args);
|
|
5420
5605
|
return true;
|
|
5421
5606
|
} catch (error) {
|
|
5607
|
+
if (error instanceof NonZeroExitError2 && error.output?.stderr.includes("EOTP")) {
|
|
5608
|
+
return false;
|
|
5609
|
+
}
|
|
5422
5610
|
throw new NpmError(`Failed to run \`npm ${args.join(" ")}\``, {
|
|
5423
5611
|
cause: error
|
|
5424
5612
|
});
|
|
@@ -5826,14 +6014,14 @@ var prerequisitesCheckTask = (options) => {
|
|
|
5826
6014
|
import { ListrEnquirerPromptAdapter as ListrEnquirerPromptAdapter4 } from "@listr2/prompt-adapter-enquirer";
|
|
5827
6015
|
|
|
5828
6016
|
// src/registry/custom-registry.ts
|
|
5829
|
-
import { exec as
|
|
6017
|
+
import { exec as exec6 } from "tinyexec";
|
|
5830
6018
|
var CustomRegistry = class extends NpmRegistry {
|
|
5831
6019
|
async npm(args) {
|
|
5832
|
-
const { stdout
|
|
6020
|
+
const { stdout } = await exec6(
|
|
5833
6021
|
"npm",
|
|
5834
|
-
args.concat("--registry", this.registry)
|
|
6022
|
+
args.concat("--registry", this.registry),
|
|
6023
|
+
{ throwOnError: true }
|
|
5835
6024
|
);
|
|
5836
|
-
if (stderr) throw stderr;
|
|
5837
6025
|
return stdout;
|
|
5838
6026
|
}
|
|
5839
6027
|
};
|
|
@@ -5847,7 +6035,10 @@ var registryMap = {
|
|
|
5847
6035
|
npm: npmRegistry,
|
|
5848
6036
|
jsr: jsrRegistry
|
|
5849
6037
|
};
|
|
5850
|
-
async function getRegistry(registryKey) {
|
|
6038
|
+
async function getRegistry(registryKey, packageName) {
|
|
6039
|
+
if (registryKey === "crates") {
|
|
6040
|
+
return await cratesRegistry(packageName ?? "unknown");
|
|
6041
|
+
}
|
|
5851
6042
|
const registry = registryMap[registryKey];
|
|
5852
6043
|
if (!registry) {
|
|
5853
6044
|
return await customRegistry();
|
|
@@ -5977,6 +6168,8 @@ var requiredConditionsCheckTask = (options) => createListr({
|
|
|
5977
6168
|
return npmAvailableCheckTasks;
|
|
5978
6169
|
case "jsr":
|
|
5979
6170
|
return jsrAvailableCheckTasks;
|
|
6171
|
+
case "crates":
|
|
6172
|
+
return cratesAvailableCheckTasks;
|
|
5980
6173
|
default:
|
|
5981
6174
|
return npmAvailableCheckTasks;
|
|
5982
6175
|
}
|
|
@@ -6023,6 +6216,8 @@ async function run(options) {
|
|
|
6023
6216
|
return npmPublishTasks;
|
|
6024
6217
|
case "jsr":
|
|
6025
6218
|
return jsrPublishTasks;
|
|
6219
|
+
case "crates":
|
|
6220
|
+
return cratesPublishTasks;
|
|
6026
6221
|
default:
|
|
6027
6222
|
return npmPublishTasks;
|
|
6028
6223
|
}
|
|
@@ -6035,16 +6230,9 @@ async function run(options) {
|
|
|
6035
6230
|
title: "Running tests",
|
|
6036
6231
|
task: async (ctx2) => {
|
|
6037
6232
|
const packageManager = await getPackageManager();
|
|
6038
|
-
|
|
6039
|
-
|
|
6040
|
-
|
|
6041
|
-
]);
|
|
6042
|
-
if (stderr) {
|
|
6043
|
-
throw new AbstractError(
|
|
6044
|
-
`Failed to run \`${packageManager} run ${ctx2.testScript}\``,
|
|
6045
|
-
{ cause: stderr }
|
|
6046
|
-
);
|
|
6047
|
-
}
|
|
6233
|
+
await exec7(packageManager, ["run", ctx2.testScript], {
|
|
6234
|
+
throwOnError: true
|
|
6235
|
+
});
|
|
6048
6236
|
}
|
|
6049
6237
|
},
|
|
6050
6238
|
{
|
|
@@ -6053,7 +6241,7 @@ async function run(options) {
|
|
|
6053
6241
|
task: async (ctx2) => {
|
|
6054
6242
|
const packageManager = await getPackageManager();
|
|
6055
6243
|
try {
|
|
6056
|
-
await
|
|
6244
|
+
await exec7(packageManager, ["run", ctx2.buildScript], {
|
|
6057
6245
|
throwOnError: true
|
|
6058
6246
|
});
|
|
6059
6247
|
} catch (error) {
|
|
@@ -6107,6 +6295,8 @@ async function run(options) {
|
|
|
6107
6295
|
return npmPublishTasks;
|
|
6108
6296
|
case "jsr":
|
|
6109
6297
|
return jsrPublishTasks;
|
|
6298
|
+
case "crates":
|
|
6299
|
+
return cratesPublishTasks;
|
|
6110
6300
|
default:
|
|
6111
6301
|
return npmPublishTasks;
|
|
6112
6302
|
}
|
|
@@ -6172,11 +6362,719 @@ ${repositoryUrl}/compare/${lastRev}...${latestTag}`;
|
|
|
6172
6362
|
}
|
|
6173
6363
|
}
|
|
6174
6364
|
|
|
6365
|
+
// src/changeset/bump-utils.ts
|
|
6366
|
+
var BUMP_ORDER = {
|
|
6367
|
+
patch: 0,
|
|
6368
|
+
minor: 1,
|
|
6369
|
+
major: 2
|
|
6370
|
+
};
|
|
6371
|
+
function maxBump(a2, b) {
|
|
6372
|
+
return BUMP_ORDER[a2] >= BUMP_ORDER[b] ? a2 : b;
|
|
6373
|
+
}
|
|
6374
|
+
|
|
6375
|
+
// src/changeset/changelog.ts
|
|
6376
|
+
var SECTION_ORDER = [
|
|
6377
|
+
{ type: "major", heading: "Major Changes" },
|
|
6378
|
+
{ type: "minor", heading: "Minor Changes" },
|
|
6379
|
+
{ type: "patch", heading: "Patch Changes" }
|
|
6380
|
+
];
|
|
6381
|
+
function generateChangelog(version2, entries, depUpdates) {
|
|
6382
|
+
const lines = [`## ${version2}`];
|
|
6383
|
+
for (const section of SECTION_ORDER) {
|
|
6384
|
+
const sectionEntries = entries.filter((e2) => e2.type === section.type);
|
|
6385
|
+
if (sectionEntries.length === 0) continue;
|
|
6386
|
+
lines.push("");
|
|
6387
|
+
lines.push(`### ${section.heading}`);
|
|
6388
|
+
lines.push("");
|
|
6389
|
+
for (const entry of sectionEntries) {
|
|
6390
|
+
lines.push(`- ${entry.summary}`);
|
|
6391
|
+
}
|
|
6392
|
+
}
|
|
6393
|
+
if (depUpdates && depUpdates.length > 0) {
|
|
6394
|
+
lines.push("");
|
|
6395
|
+
lines.push("### Dependency Updates");
|
|
6396
|
+
lines.push("");
|
|
6397
|
+
for (const dep of depUpdates) {
|
|
6398
|
+
lines.push(`- Updated \`${dep.name}\` to ${dep.version}`);
|
|
6399
|
+
}
|
|
6400
|
+
}
|
|
6401
|
+
return `${lines.join("\n")}
|
|
6402
|
+
`;
|
|
6403
|
+
}
|
|
6404
|
+
|
|
6405
|
+
// src/changeset/migrate.ts
|
|
6406
|
+
import { copyFileSync, existsSync, mkdirSync as mkdirSync2, readdirSync } from "node:fs";
|
|
6407
|
+
import path4 from "node:path";
|
|
6408
|
+
import process11 from "node:process";
|
|
6409
|
+
var SKIPPED_FILES = /* @__PURE__ */ new Set(["config.json", "README.md"]);
|
|
6410
|
+
function migrateFromChangesets(cwd = process11.cwd()) {
|
|
6411
|
+
const changesetDir = path4.join(cwd, ".changeset");
|
|
6412
|
+
if (!existsSync(changesetDir)) {
|
|
6413
|
+
return {
|
|
6414
|
+
success: false,
|
|
6415
|
+
error: ".changeset/ directory not found",
|
|
6416
|
+
migratedFiles: [],
|
|
6417
|
+
configMigrated: false
|
|
6418
|
+
};
|
|
6419
|
+
}
|
|
6420
|
+
const pubmDir = path4.join(cwd, ".pubm", "changesets");
|
|
6421
|
+
mkdirSync2(pubmDir, { recursive: true });
|
|
6422
|
+
const files = readdirSync(changesetDir);
|
|
6423
|
+
const migratedFiles = [];
|
|
6424
|
+
let configMigrated = false;
|
|
6425
|
+
for (const file of files) {
|
|
6426
|
+
if (file === "config.json") {
|
|
6427
|
+
configMigrated = true;
|
|
6428
|
+
continue;
|
|
6429
|
+
}
|
|
6430
|
+
if (SKIPPED_FILES.has(file)) {
|
|
6431
|
+
continue;
|
|
6432
|
+
}
|
|
6433
|
+
if (file === "pre.json") {
|
|
6434
|
+
copyFileSync(
|
|
6435
|
+
path4.join(changesetDir, file),
|
|
6436
|
+
path4.resolve(cwd, ".pubm", "pre.json")
|
|
6437
|
+
);
|
|
6438
|
+
migratedFiles.push(file);
|
|
6439
|
+
continue;
|
|
6440
|
+
}
|
|
6441
|
+
if (file.endsWith(".md")) {
|
|
6442
|
+
const src = path4.join(changesetDir, file);
|
|
6443
|
+
const dest = path4.join(pubmDir, file);
|
|
6444
|
+
copyFileSync(src, dest);
|
|
6445
|
+
migratedFiles.push(file);
|
|
6446
|
+
}
|
|
6447
|
+
}
|
|
6448
|
+
return {
|
|
6449
|
+
success: true,
|
|
6450
|
+
migratedFiles,
|
|
6451
|
+
configMigrated
|
|
6452
|
+
};
|
|
6453
|
+
}
|
|
6454
|
+
|
|
6455
|
+
// src/changeset/parser.ts
|
|
6456
|
+
import { parse as parseYaml } from "yaml";
|
|
6457
|
+
var VALID_BUMP_TYPES = /* @__PURE__ */ new Set(["patch", "minor", "major"]);
|
|
6458
|
+
function parseChangeset(content, fileName) {
|
|
6459
|
+
const frontmatterRegex = /^---\n([\s\S]*?)---/;
|
|
6460
|
+
const match = content.match(frontmatterRegex);
|
|
6461
|
+
if (!match) {
|
|
6462
|
+
throw new Error(
|
|
6463
|
+
`Invalid changeset format in "${fileName}": missing frontmatter`
|
|
6464
|
+
);
|
|
6465
|
+
}
|
|
6466
|
+
const yamlContent = match[1];
|
|
6467
|
+
const body = content.slice(match[0].length).trim();
|
|
6468
|
+
const parsed = parseYaml(yamlContent);
|
|
6469
|
+
const releases = [];
|
|
6470
|
+
if (parsed) {
|
|
6471
|
+
for (const [name, type] of Object.entries(parsed)) {
|
|
6472
|
+
if (!VALID_BUMP_TYPES.has(type)) {
|
|
6473
|
+
throw new Error(
|
|
6474
|
+
`Invalid bump type "${type}" for package "${name}" in "${fileName}". Expected: patch, minor, or major.`
|
|
6475
|
+
);
|
|
6476
|
+
}
|
|
6477
|
+
releases.push({ name, type });
|
|
6478
|
+
}
|
|
6479
|
+
}
|
|
6480
|
+
const id = fileName.replace(/\.md$/, "");
|
|
6481
|
+
return {
|
|
6482
|
+
id,
|
|
6483
|
+
summary: body,
|
|
6484
|
+
releases
|
|
6485
|
+
};
|
|
6486
|
+
}
|
|
6487
|
+
|
|
6488
|
+
// src/changeset/reader.ts
|
|
6489
|
+
import { existsSync as existsSync2, readdirSync as readdirSync2, readFileSync as readFileSync2 } from "node:fs";
|
|
6490
|
+
import path5 from "node:path";
|
|
6491
|
+
import process12 from "node:process";
|
|
6492
|
+
function readChangesets(cwd = process12.cwd()) {
|
|
6493
|
+
const changesetsDir = path5.join(cwd, ".pubm", "changesets");
|
|
6494
|
+
if (!existsSync2(changesetsDir)) {
|
|
6495
|
+
return [];
|
|
6496
|
+
}
|
|
6497
|
+
const files = readdirSync2(changesetsDir);
|
|
6498
|
+
const changesets = [];
|
|
6499
|
+
for (const file of files) {
|
|
6500
|
+
if (!file.endsWith(".md") || file === "README.md") {
|
|
6501
|
+
continue;
|
|
6502
|
+
}
|
|
6503
|
+
const filePath = path5.join(changesetsDir, file);
|
|
6504
|
+
const content = readFileSync2(filePath, "utf-8");
|
|
6505
|
+
changesets.push(parseChangeset(content, file));
|
|
6506
|
+
}
|
|
6507
|
+
return changesets;
|
|
6508
|
+
}
|
|
6509
|
+
|
|
6510
|
+
// src/changeset/status.ts
|
|
6511
|
+
import process13 from "node:process";
|
|
6512
|
+
function getStatus(cwd = process13.cwd()) {
|
|
6513
|
+
const changesets = readChangesets(cwd);
|
|
6514
|
+
const packages = /* @__PURE__ */ new Map();
|
|
6515
|
+
for (const changeset of changesets) {
|
|
6516
|
+
for (const release of changeset.releases) {
|
|
6517
|
+
const existing = packages.get(release.name);
|
|
6518
|
+
if (existing) {
|
|
6519
|
+
existing.bumpType = maxBump(existing.bumpType, release.type);
|
|
6520
|
+
existing.changesetCount += 1;
|
|
6521
|
+
existing.summaries.push(changeset.summary);
|
|
6522
|
+
} else {
|
|
6523
|
+
packages.set(release.name, {
|
|
6524
|
+
bumpType: release.type,
|
|
6525
|
+
changesetCount: 1,
|
|
6526
|
+
summaries: [changeset.summary]
|
|
6527
|
+
});
|
|
6528
|
+
}
|
|
6529
|
+
}
|
|
6530
|
+
}
|
|
6531
|
+
return {
|
|
6532
|
+
packages,
|
|
6533
|
+
changesets,
|
|
6534
|
+
hasChangesets: changesets.length > 0
|
|
6535
|
+
};
|
|
6536
|
+
}
|
|
6537
|
+
|
|
6538
|
+
// src/changeset/version.ts
|
|
6539
|
+
import process14 from "node:process";
|
|
6540
|
+
import { inc } from "semver";
|
|
6541
|
+
function calculateVersionBumps(currentVersions, cwd = process14.cwd()) {
|
|
6542
|
+
const changesets = readChangesets(cwd);
|
|
6543
|
+
const bumpTypes = /* @__PURE__ */ new Map();
|
|
6544
|
+
for (const changeset of changesets) {
|
|
6545
|
+
for (const release of changeset.releases) {
|
|
6546
|
+
if (!currentVersions.has(release.name)) continue;
|
|
6547
|
+
const existing = bumpTypes.get(release.name);
|
|
6548
|
+
if (existing) {
|
|
6549
|
+
bumpTypes.set(release.name, maxBump(existing, release.type));
|
|
6550
|
+
} else {
|
|
6551
|
+
bumpTypes.set(release.name, release.type);
|
|
6552
|
+
}
|
|
6553
|
+
}
|
|
6554
|
+
}
|
|
6555
|
+
const result = /* @__PURE__ */ new Map();
|
|
6556
|
+
for (const [name, bumpType] of bumpTypes) {
|
|
6557
|
+
const currentVersion = currentVersions.get(name);
|
|
6558
|
+
if (!currentVersion) continue;
|
|
6559
|
+
const newVersion = inc(currentVersion, bumpType);
|
|
6560
|
+
if (newVersion) {
|
|
6561
|
+
result.set(name, {
|
|
6562
|
+
currentVersion,
|
|
6563
|
+
newVersion,
|
|
6564
|
+
bumpType
|
|
6565
|
+
});
|
|
6566
|
+
}
|
|
6567
|
+
}
|
|
6568
|
+
return result;
|
|
6569
|
+
}
|
|
6570
|
+
|
|
6571
|
+
// src/changeset/writer.ts
|
|
6572
|
+
import { mkdirSync as mkdirSync3, writeFileSync as writeFileSync2 } from "node:fs";
|
|
6573
|
+
import path6 from "node:path";
|
|
6574
|
+
import process15 from "node:process";
|
|
6575
|
+
import { stringify as stringifyYaml } from "yaml";
|
|
6576
|
+
var adjectives = [
|
|
6577
|
+
"brave",
|
|
6578
|
+
"calm",
|
|
6579
|
+
"dark",
|
|
6580
|
+
"eager",
|
|
6581
|
+
"fair",
|
|
6582
|
+
"glad",
|
|
6583
|
+
"happy",
|
|
6584
|
+
"idle",
|
|
6585
|
+
"jolly",
|
|
6586
|
+
"keen",
|
|
6587
|
+
"lame",
|
|
6588
|
+
"mild",
|
|
6589
|
+
"neat",
|
|
6590
|
+
"odd",
|
|
6591
|
+
"pale",
|
|
6592
|
+
"quick",
|
|
6593
|
+
"rare",
|
|
6594
|
+
"safe",
|
|
6595
|
+
"tall",
|
|
6596
|
+
"ugly",
|
|
6597
|
+
"vast",
|
|
6598
|
+
"warm",
|
|
6599
|
+
"young",
|
|
6600
|
+
"zany",
|
|
6601
|
+
"bold",
|
|
6602
|
+
"cool",
|
|
6603
|
+
"dry",
|
|
6604
|
+
"fast",
|
|
6605
|
+
"good",
|
|
6606
|
+
"hot",
|
|
6607
|
+
"icy",
|
|
6608
|
+
"loud"
|
|
6609
|
+
];
|
|
6610
|
+
var nouns = [
|
|
6611
|
+
"ant",
|
|
6612
|
+
"bear",
|
|
6613
|
+
"cat",
|
|
6614
|
+
"dog",
|
|
6615
|
+
"elk",
|
|
6616
|
+
"fox",
|
|
6617
|
+
"goat",
|
|
6618
|
+
"hawk",
|
|
6619
|
+
"ibis",
|
|
6620
|
+
"jay",
|
|
6621
|
+
"kite",
|
|
6622
|
+
"lion",
|
|
6623
|
+
"mole",
|
|
6624
|
+
"newt",
|
|
6625
|
+
"owl",
|
|
6626
|
+
"puma",
|
|
6627
|
+
"quail",
|
|
6628
|
+
"ram",
|
|
6629
|
+
"seal",
|
|
6630
|
+
"toad",
|
|
6631
|
+
"urchin",
|
|
6632
|
+
"vole",
|
|
6633
|
+
"wolf",
|
|
6634
|
+
"yak",
|
|
6635
|
+
"zebra",
|
|
6636
|
+
"ape",
|
|
6637
|
+
"bat",
|
|
6638
|
+
"cow",
|
|
6639
|
+
"deer",
|
|
6640
|
+
"emu",
|
|
6641
|
+
"frog",
|
|
6642
|
+
"gull"
|
|
6643
|
+
];
|
|
6644
|
+
function generateChangesetId() {
|
|
6645
|
+
const adjective = adjectives[Math.floor(Math.random() * adjectives.length)];
|
|
6646
|
+
const noun = nouns[Math.floor(Math.random() * nouns.length)];
|
|
6647
|
+
const suffix = Math.random().toString(36).slice(2, 6);
|
|
6648
|
+
return `${adjective}-${noun}-${suffix}`;
|
|
6649
|
+
}
|
|
6650
|
+
function generateChangesetContent(releases, summary) {
|
|
6651
|
+
let content = "---\n";
|
|
6652
|
+
if (releases.length > 0) {
|
|
6653
|
+
const yamlObj = {};
|
|
6654
|
+
for (const release of releases) {
|
|
6655
|
+
yamlObj[release.name] = release.type;
|
|
6656
|
+
}
|
|
6657
|
+
content += stringifyYaml(yamlObj);
|
|
6658
|
+
}
|
|
6659
|
+
content += "---\n";
|
|
6660
|
+
if (summary) {
|
|
6661
|
+
content += `
|
|
6662
|
+
${summary}
|
|
6663
|
+
`;
|
|
6664
|
+
}
|
|
6665
|
+
return content;
|
|
6666
|
+
}
|
|
6667
|
+
function writeChangeset(releases, summary, cwd = process15.cwd()) {
|
|
6668
|
+
const changesetsDir = path6.join(cwd, ".pubm", "changesets");
|
|
6669
|
+
mkdirSync3(changesetsDir, { recursive: true });
|
|
6670
|
+
const id = generateChangesetId();
|
|
6671
|
+
const fileName = `${id}.md`;
|
|
6672
|
+
const filePath = path6.join(changesetsDir, fileName);
|
|
6673
|
+
const content = generateChangesetContent(releases, summary);
|
|
6674
|
+
writeFileSync2(filePath, content, "utf-8");
|
|
6675
|
+
return filePath;
|
|
6676
|
+
}
|
|
6677
|
+
|
|
6678
|
+
// src/config/defaults.ts
|
|
6679
|
+
var defaultValidate = {
|
|
6680
|
+
cleanInstall: true,
|
|
6681
|
+
entryPoints: true,
|
|
6682
|
+
extraneousFiles: true
|
|
6683
|
+
};
|
|
6684
|
+
var defaultSnapshot = {
|
|
6685
|
+
useCalculatedVersion: false,
|
|
6686
|
+
prereleaseTemplate: "{tag}-{timestamp}"
|
|
6687
|
+
};
|
|
6688
|
+
var defaultConfig = {
|
|
6689
|
+
versioning: "independent",
|
|
6690
|
+
branch: "main",
|
|
6691
|
+
changelog: true,
|
|
6692
|
+
changelogFormat: "default",
|
|
6693
|
+
commit: false,
|
|
6694
|
+
access: "public",
|
|
6695
|
+
fixed: [],
|
|
6696
|
+
linked: [],
|
|
6697
|
+
updateInternalDependencies: "patch",
|
|
6698
|
+
ignore: [],
|
|
6699
|
+
tag: "latest",
|
|
6700
|
+
contents: ".",
|
|
6701
|
+
saveToken: true,
|
|
6702
|
+
releaseDraft: true,
|
|
6703
|
+
releaseNotes: true,
|
|
6704
|
+
registries: ["npm", "jsr"],
|
|
6705
|
+
rollbackStrategy: "individual"
|
|
6706
|
+
};
|
|
6707
|
+
function resolveConfig(config) {
|
|
6708
|
+
const packages = config.packages ?? [
|
|
6709
|
+
{ path: ".", registries: ["npm", "jsr"] }
|
|
6710
|
+
];
|
|
6711
|
+
return {
|
|
6712
|
+
...defaultConfig,
|
|
6713
|
+
...config,
|
|
6714
|
+
packages,
|
|
6715
|
+
validate: { ...defaultValidate, ...config.validate },
|
|
6716
|
+
snapshot: { ...defaultSnapshot, ...config.snapshot }
|
|
6717
|
+
};
|
|
6718
|
+
}
|
|
6719
|
+
|
|
6720
|
+
// src/config/loader.ts
|
|
6721
|
+
import { stat as stat3 } from "node:fs/promises";
|
|
6722
|
+
import path7 from "node:path";
|
|
6723
|
+
var CONFIG_FILES = [
|
|
6724
|
+
"pubm.config.ts",
|
|
6725
|
+
"pubm.config.mts",
|
|
6726
|
+
"pubm.config.cts",
|
|
6727
|
+
"pubm.config.js",
|
|
6728
|
+
"pubm.config.mjs",
|
|
6729
|
+
"pubm.config.cjs"
|
|
6730
|
+
];
|
|
6731
|
+
async function findConfigFile(cwd) {
|
|
6732
|
+
for (const file of CONFIG_FILES) {
|
|
6733
|
+
const filePath = path7.join(cwd, file);
|
|
6734
|
+
try {
|
|
6735
|
+
if ((await stat3(filePath)).isFile()) {
|
|
6736
|
+
return filePath;
|
|
6737
|
+
}
|
|
6738
|
+
} catch {
|
|
6739
|
+
}
|
|
6740
|
+
}
|
|
6741
|
+
return null;
|
|
6742
|
+
}
|
|
6743
|
+
async function loadConfig(cwd = process.cwd()) {
|
|
6744
|
+
const configPath = await findConfigFile(cwd);
|
|
6745
|
+
if (!configPath) return null;
|
|
6746
|
+
const { createJiti } = await import("jiti");
|
|
6747
|
+
const jiti = createJiti(cwd, { interopDefault: true });
|
|
6748
|
+
const mod = await jiti.import(configPath);
|
|
6749
|
+
return mod.default ?? mod;
|
|
6750
|
+
}
|
|
6751
|
+
|
|
6752
|
+
// src/config/types.ts
|
|
6753
|
+
function defineConfig(config) {
|
|
6754
|
+
return config;
|
|
6755
|
+
}
|
|
6756
|
+
|
|
6757
|
+
// src/monorepo/dependency-graph.ts
|
|
6758
|
+
function buildDependencyGraph(packages) {
|
|
6759
|
+
const packageNames = new Set(packages.map((pkg) => pkg.name));
|
|
6760
|
+
const graph = /* @__PURE__ */ new Map();
|
|
6761
|
+
for (const pkg of packages) {
|
|
6762
|
+
const internalDeps = Object.keys(pkg.dependencies).filter(
|
|
6763
|
+
(dep) => packageNames.has(dep)
|
|
6764
|
+
);
|
|
6765
|
+
graph.set(pkg.name, internalDeps);
|
|
6766
|
+
}
|
|
6767
|
+
return graph;
|
|
6768
|
+
}
|
|
6769
|
+
function topologicalSort(graph) {
|
|
6770
|
+
const inDegree = /* @__PURE__ */ new Map();
|
|
6771
|
+
for (const name of graph.keys()) {
|
|
6772
|
+
inDegree.set(name, 0);
|
|
6773
|
+
}
|
|
6774
|
+
for (const [, deps] of graph) {
|
|
6775
|
+
for (const dep of deps) {
|
|
6776
|
+
inDegree.set(dep, (inDegree.get(dep) ?? 0) + 1);
|
|
6777
|
+
}
|
|
6778
|
+
}
|
|
6779
|
+
const queue = [];
|
|
6780
|
+
for (const [name, degree] of inDegree) {
|
|
6781
|
+
if (degree === 0) {
|
|
6782
|
+
queue.push(name);
|
|
6783
|
+
}
|
|
6784
|
+
}
|
|
6785
|
+
const sorted = [];
|
|
6786
|
+
while (queue.length > 0) {
|
|
6787
|
+
const node = queue.shift();
|
|
6788
|
+
sorted.push(node);
|
|
6789
|
+
for (const dep of graph.get(node) ?? []) {
|
|
6790
|
+
const newDegree = (inDegree.get(dep) ?? 0) - 1;
|
|
6791
|
+
inDegree.set(dep, newDegree);
|
|
6792
|
+
if (newDegree === 0) {
|
|
6793
|
+
queue.push(dep);
|
|
6794
|
+
}
|
|
6795
|
+
}
|
|
6796
|
+
}
|
|
6797
|
+
if (sorted.length !== graph.size) {
|
|
6798
|
+
throw new Error("Circular dependency detected");
|
|
6799
|
+
}
|
|
6800
|
+
return sorted.reverse();
|
|
6801
|
+
}
|
|
6802
|
+
|
|
6803
|
+
// src/monorepo/groups.ts
|
|
6804
|
+
import micromatch from "micromatch";
|
|
6805
|
+
function resolveGroups(groups, allPackages) {
|
|
6806
|
+
return groups.map((group) => {
|
|
6807
|
+
const resolved = /* @__PURE__ */ new Set();
|
|
6808
|
+
for (const pattern of group) {
|
|
6809
|
+
const matches = micromatch(allPackages, pattern);
|
|
6810
|
+
for (const match of matches) {
|
|
6811
|
+
resolved.add(match);
|
|
6812
|
+
}
|
|
6813
|
+
}
|
|
6814
|
+
return [...resolved];
|
|
6815
|
+
});
|
|
6816
|
+
}
|
|
6817
|
+
function applyFixedGroup(bumps, group) {
|
|
6818
|
+
let max = null;
|
|
6819
|
+
for (const pkg of group) {
|
|
6820
|
+
const bump = bumps.get(pkg);
|
|
6821
|
+
if (bump) {
|
|
6822
|
+
max = max ? maxBump(max, bump) : bump;
|
|
6823
|
+
}
|
|
6824
|
+
}
|
|
6825
|
+
if (!max) return;
|
|
6826
|
+
for (const pkg of group) {
|
|
6827
|
+
bumps.set(pkg, max);
|
|
6828
|
+
}
|
|
6829
|
+
}
|
|
6830
|
+
function applyLinkedGroup(bumps, group) {
|
|
6831
|
+
let max = null;
|
|
6832
|
+
for (const pkg of group) {
|
|
6833
|
+
const bump = bumps.get(pkg);
|
|
6834
|
+
if (bump) {
|
|
6835
|
+
max = max ? maxBump(max, bump) : bump;
|
|
6836
|
+
}
|
|
6837
|
+
}
|
|
6838
|
+
if (!max) return;
|
|
6839
|
+
for (const pkg of group) {
|
|
6840
|
+
if (bumps.has(pkg)) {
|
|
6841
|
+
bumps.set(pkg, max);
|
|
6842
|
+
}
|
|
6843
|
+
}
|
|
6844
|
+
}
|
|
6845
|
+
|
|
6846
|
+
// src/monorepo/workspace.ts
|
|
6847
|
+
import { existsSync as existsSync3, readFileSync as readFileSync3 } from "node:fs";
|
|
6848
|
+
import { join } from "node:path";
|
|
6849
|
+
import { parse as parse2 } from "yaml";
|
|
6850
|
+
function detectWorkspace(cwd) {
|
|
6851
|
+
const root = cwd ?? process.cwd();
|
|
6852
|
+
const pnpmWorkspacePath = join(root, "pnpm-workspace.yaml");
|
|
6853
|
+
if (existsSync3(pnpmWorkspacePath)) {
|
|
6854
|
+
const content = readFileSync3(pnpmWorkspacePath, "utf-8");
|
|
6855
|
+
const parsed = parse2(content);
|
|
6856
|
+
const packages = parsed?.packages ?? [];
|
|
6857
|
+
return { type: "pnpm", patterns: packages };
|
|
6858
|
+
}
|
|
6859
|
+
const packageJsonPath = join(root, "package.json");
|
|
6860
|
+
if (existsSync3(packageJsonPath)) {
|
|
6861
|
+
const content = readFileSync3(packageJsonPath, "utf-8");
|
|
6862
|
+
const pkg = JSON.parse(content);
|
|
6863
|
+
if (pkg.workspaces) {
|
|
6864
|
+
if (Array.isArray(pkg.workspaces)) {
|
|
6865
|
+
return { type: "npm", patterns: pkg.workspaces };
|
|
6866
|
+
}
|
|
6867
|
+
if (typeof pkg.workspaces === "object" && Array.isArray(pkg.workspaces.packages)) {
|
|
6868
|
+
return { type: "yarn", patterns: pkg.workspaces.packages };
|
|
6869
|
+
}
|
|
6870
|
+
}
|
|
6871
|
+
}
|
|
6872
|
+
return null;
|
|
6873
|
+
}
|
|
6874
|
+
|
|
6875
|
+
// src/prerelease/pre.ts
|
|
6876
|
+
import {
|
|
6877
|
+
existsSync as existsSync4,
|
|
6878
|
+
mkdirSync as mkdirSync4,
|
|
6879
|
+
readFileSync as readFileSync4,
|
|
6880
|
+
rmSync,
|
|
6881
|
+
writeFileSync as writeFileSync3
|
|
6882
|
+
} from "node:fs";
|
|
6883
|
+
import path8 from "node:path";
|
|
6884
|
+
function getPreStatePath(cwd) {
|
|
6885
|
+
return path8.resolve(cwd ?? process.cwd(), ".pubm", "pre.json");
|
|
6886
|
+
}
|
|
6887
|
+
function readPreState(cwd) {
|
|
6888
|
+
const filePath = getPreStatePath(cwd);
|
|
6889
|
+
if (!existsSync4(filePath)) {
|
|
6890
|
+
return null;
|
|
6891
|
+
}
|
|
6892
|
+
const content = readFileSync4(filePath, "utf-8");
|
|
6893
|
+
return JSON.parse(content);
|
|
6894
|
+
}
|
|
6895
|
+
function enterPreMode(tag, cwd) {
|
|
6896
|
+
const filePath = getPreStatePath(cwd);
|
|
6897
|
+
if (existsSync4(filePath)) {
|
|
6898
|
+
throw new Error(
|
|
6899
|
+
"Already in pre mode. Exit pre mode first before entering a new one."
|
|
6900
|
+
);
|
|
6901
|
+
}
|
|
6902
|
+
const dir = path8.dirname(filePath);
|
|
6903
|
+
if (!existsSync4(dir)) {
|
|
6904
|
+
mkdirSync4(dir, { recursive: true });
|
|
6905
|
+
}
|
|
6906
|
+
const state = {
|
|
6907
|
+
mode: "pre",
|
|
6908
|
+
tag,
|
|
6909
|
+
packages: {}
|
|
6910
|
+
};
|
|
6911
|
+
writeFileSync3(filePath, JSON.stringify(state, null, 2), "utf-8");
|
|
6912
|
+
}
|
|
6913
|
+
function exitPreMode(cwd) {
|
|
6914
|
+
const filePath = getPreStatePath(cwd);
|
|
6915
|
+
if (!existsSync4(filePath)) {
|
|
6916
|
+
throw new Error("Not in pre mode. Enter pre mode first before exiting.");
|
|
6917
|
+
}
|
|
6918
|
+
rmSync(filePath);
|
|
6919
|
+
}
|
|
6920
|
+
|
|
6921
|
+
// src/prerelease/snapshot.ts
|
|
6922
|
+
function formatTimestamp(date) {
|
|
6923
|
+
const year = date.getUTCFullYear();
|
|
6924
|
+
const month = String(date.getUTCMonth() + 1).padStart(2, "0");
|
|
6925
|
+
const day = String(date.getUTCDate()).padStart(2, "0");
|
|
6926
|
+
const hours = String(date.getUTCHours()).padStart(2, "0");
|
|
6927
|
+
const minutes = String(date.getUTCMinutes()).padStart(2, "0");
|
|
6928
|
+
const seconds = String(date.getUTCSeconds()).padStart(2, "0");
|
|
6929
|
+
return `${year}${month}${day}T${hours}${minutes}${seconds}`;
|
|
6930
|
+
}
|
|
6931
|
+
function generateSnapshotVersion(options) {
|
|
6932
|
+
const tag = options.tag ?? "snapshot";
|
|
6933
|
+
const base = options.useCalculatedVersion && options.baseVersion ? options.baseVersion : "0.0.0";
|
|
6934
|
+
const now = /* @__PURE__ */ new Date();
|
|
6935
|
+
const timestamp = formatTimestamp(now);
|
|
6936
|
+
if (options.template) {
|
|
6937
|
+
return options.template.replace(/\{base\}/g, base).replace(/\{tag\}/g, tag).replace(/\{timestamp\}/g, timestamp).replace(/\{commit\}/g, options.commit ?? "").replace(/\{datetime\}/g, timestamp);
|
|
6938
|
+
}
|
|
6939
|
+
return `${base}-${tag}-${timestamp}`;
|
|
6940
|
+
}
|
|
6941
|
+
|
|
6942
|
+
// src/validate/entry-points.ts
|
|
6943
|
+
import { existsSync as existsSync5 } from "node:fs";
|
|
6944
|
+
import path9 from "node:path";
|
|
6945
|
+
var SIMPLE_FIELDS = ["main", "module", "types", "typings"];
|
|
6946
|
+
function checkPath(filePath, cwd) {
|
|
6947
|
+
return existsSync5(path9.resolve(cwd, filePath));
|
|
6948
|
+
}
|
|
6949
|
+
function validateExports(exports, cwd, prefix = "exports") {
|
|
6950
|
+
const errors = [];
|
|
6951
|
+
if (typeof exports === "string") {
|
|
6952
|
+
if (!checkPath(exports, cwd)) {
|
|
6953
|
+
errors.push({ field: prefix, path: exports });
|
|
6954
|
+
}
|
|
6955
|
+
return errors;
|
|
6956
|
+
}
|
|
6957
|
+
if (typeof exports === "object" && exports !== null) {
|
|
6958
|
+
for (const [key, value] of Object.entries(exports)) {
|
|
6959
|
+
if (typeof value === "string") {
|
|
6960
|
+
if (!checkPath(value, cwd)) {
|
|
6961
|
+
errors.push({ field: `${prefix}["${key}"]`, path: value });
|
|
6962
|
+
}
|
|
6963
|
+
} else if (typeof value === "object" && value !== null) {
|
|
6964
|
+
errors.push(...validateExports(value, cwd, `${prefix}["${key}"]`));
|
|
6965
|
+
}
|
|
6966
|
+
}
|
|
6967
|
+
}
|
|
6968
|
+
return errors;
|
|
6969
|
+
}
|
|
6970
|
+
function validateEntryPoints(pkg, cwd) {
|
|
6971
|
+
const errors = [];
|
|
6972
|
+
for (const field of SIMPLE_FIELDS) {
|
|
6973
|
+
const value = pkg[field];
|
|
6974
|
+
if (typeof value === "string" && !checkPath(value, cwd)) {
|
|
6975
|
+
errors.push({ field, path: value });
|
|
6976
|
+
}
|
|
6977
|
+
}
|
|
6978
|
+
if (pkg.exports !== void 0) {
|
|
6979
|
+
errors.push(...validateExports(pkg.exports, cwd));
|
|
6980
|
+
}
|
|
6981
|
+
if (pkg.bin !== void 0) {
|
|
6982
|
+
if (typeof pkg.bin === "string") {
|
|
6983
|
+
if (!checkPath(pkg.bin, cwd)) {
|
|
6984
|
+
errors.push({ field: "bin", path: pkg.bin });
|
|
6985
|
+
}
|
|
6986
|
+
} else if (typeof pkg.bin === "object" && pkg.bin !== null) {
|
|
6987
|
+
for (const [name, binPath] of Object.entries(
|
|
6988
|
+
pkg.bin
|
|
6989
|
+
)) {
|
|
6990
|
+
if (!checkPath(binPath, cwd)) {
|
|
6991
|
+
errors.push({ field: `bin.${name}`, path: binPath });
|
|
6992
|
+
}
|
|
6993
|
+
}
|
|
6994
|
+
}
|
|
6995
|
+
}
|
|
6996
|
+
return errors;
|
|
6997
|
+
}
|
|
6998
|
+
|
|
6999
|
+
// src/validate/extraneous-files.ts
|
|
7000
|
+
import micromatch2 from "micromatch";
|
|
7001
|
+
var PATTERNS = [
|
|
7002
|
+
{
|
|
7003
|
+
pattern: [".env", ".env.*"],
|
|
7004
|
+
reason: "potentially contains secrets",
|
|
7005
|
+
basename: true
|
|
7006
|
+
},
|
|
7007
|
+
{
|
|
7008
|
+
pattern: ["*.test.*", "*.spec.*"],
|
|
7009
|
+
reason: "test file",
|
|
7010
|
+
basename: true
|
|
7011
|
+
},
|
|
7012
|
+
{
|
|
7013
|
+
pattern: ["**/__tests__/**"],
|
|
7014
|
+
reason: "test file"
|
|
7015
|
+
},
|
|
7016
|
+
{ pattern: ["*.map"], reason: "source map", basename: true },
|
|
7017
|
+
{
|
|
7018
|
+
pattern: [
|
|
7019
|
+
".eslintrc*",
|
|
7020
|
+
".prettierrc*",
|
|
7021
|
+
"tsconfig.json",
|
|
7022
|
+
"tsconfig.*.json",
|
|
7023
|
+
".babelrc*",
|
|
7024
|
+
"jest.config.*",
|
|
7025
|
+
"vitest.config.*",
|
|
7026
|
+
".editorconfig",
|
|
7027
|
+
"biome.json"
|
|
7028
|
+
],
|
|
7029
|
+
reason: "development config file",
|
|
7030
|
+
basename: true
|
|
7031
|
+
}
|
|
7032
|
+
];
|
|
7033
|
+
function detectExtraneousFiles(files) {
|
|
7034
|
+
const result = [];
|
|
7035
|
+
const seen = /* @__PURE__ */ new Set();
|
|
7036
|
+
for (const { pattern, reason, basename } of PATTERNS) {
|
|
7037
|
+
const options = basename ? { basename: true } : {};
|
|
7038
|
+
const matched = micromatch2(files, pattern, options);
|
|
7039
|
+
for (const file of matched) {
|
|
7040
|
+
if (!seen.has(file)) {
|
|
7041
|
+
seen.add(file);
|
|
7042
|
+
result.push({ file, reason });
|
|
7043
|
+
}
|
|
7044
|
+
}
|
|
7045
|
+
}
|
|
7046
|
+
return result;
|
|
7047
|
+
}
|
|
7048
|
+
|
|
6175
7049
|
// src/index.ts
|
|
6176
7050
|
async function pubm(options) {
|
|
6177
7051
|
const resolvedOptions = resolveOptions({ ...options });
|
|
6178
7052
|
await run(resolvedOptions);
|
|
6179
7053
|
}
|
|
6180
7054
|
export {
|
|
6181
|
-
|
|
7055
|
+
applyFixedGroup,
|
|
7056
|
+
applyLinkedGroup,
|
|
7057
|
+
buildDependencyGraph,
|
|
7058
|
+
calculateVersionBumps,
|
|
7059
|
+
defineConfig,
|
|
7060
|
+
detectExtraneousFiles,
|
|
7061
|
+
detectWorkspace,
|
|
7062
|
+
enterPreMode,
|
|
7063
|
+
exitPreMode,
|
|
7064
|
+
generateChangelog,
|
|
7065
|
+
generateChangesetContent,
|
|
7066
|
+
generateChangesetId,
|
|
7067
|
+
generateSnapshotVersion,
|
|
7068
|
+
getStatus,
|
|
7069
|
+
loadConfig,
|
|
7070
|
+
migrateFromChangesets,
|
|
7071
|
+
parseChangeset,
|
|
7072
|
+
pubm,
|
|
7073
|
+
readChangesets,
|
|
7074
|
+
readPreState,
|
|
7075
|
+
resolveConfig,
|
|
7076
|
+
resolveGroups,
|
|
7077
|
+
topologicalSort,
|
|
7078
|
+
validateEntryPoints,
|
|
7079
|
+
writeChangeset
|
|
6182
7080
|
};
|