Skip to content

Commit eb785b0

Browse files
committed
fix: resolve workspace:* references when publishing to npm
- Add scripts/publish.ts to resolve workspace:* to actual versions before npm publish - Update changeset:version to use bun update for lockfile sync - Update changeset:release to use custom publish script with OIDC provenance - Fix workflow action versions and add registry-url for OIDC Fixes #2702
1 parent 4c34bda commit eb785b0

File tree

4 files changed

+171
-5
lines changed

4 files changed

+171
-5
lines changed
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
---
2+
"@node-minify/babel-minify": patch
3+
"@node-minify/clean-css": patch
4+
"@node-minify/cli": patch
5+
"@node-minify/core": patch
6+
"@node-minify/crass": patch
7+
"@node-minify/cssnano": patch
8+
"@node-minify/csso": patch
9+
"@node-minify/esbuild": patch
10+
"@node-minify/google-closure-compiler": patch
11+
"@node-minify/html-minifier": patch
12+
"@node-minify/jsonminify": patch
13+
"@node-minify/lightningcss": patch
14+
"@node-minify/no-compress": patch
15+
"@node-minify/oxc": patch
16+
"@node-minify/run": patch
17+
"@node-minify/sqwish": patch
18+
"@node-minify/swc": patch
19+
"@node-minify/terser": patch
20+
"@node-minify/types": patch
21+
"@node-minify/uglify-es": patch
22+
"@node-minify/uglify-js": patch
23+
"@node-minify/utils": patch
24+
"@node-minify/yui": patch
25+
---
26+
27+
Fix npm install error caused by unresolved workspace:\* references in published packages

.github/workflows/publish.yml

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -26,11 +26,14 @@ jobs:
2626

2727
- name: 📦 Setup Bun
2828
uses: oven-sh/setup-bun@v2
29+
with:
30+
bun-version: "1.3.5"
2931

3032
- name: ⚙️ Setup Node
3133
uses: actions/setup-node@v6
3234
with:
33-
node-version: '22'
35+
node-version: "22"
36+
registry-url: "https://registry.npmjs.org"
3437

3538
- name: 🔧 Upgrade npm for OIDC support
3639
run: npm install -g npm@latest
@@ -42,8 +45,8 @@ jobs:
4245
uses: changesets/action@v1
4346
id: changesets
4447
with:
45-
publish: bun changeset:release
46-
version: bun changeset:version
48+
publish: bun run changeset:release
49+
version: bun run changeset:version
4750
createGithubReleases: true
4851
env:
4952
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,8 @@
3434
"test:watch": "vitest",
3535
"test:coverage": "vitest run --coverage",
3636
"changeset": "changeset",
37-
"changeset:version": "changeset version && bun install --no-frozen-lockfile",
38-
"changeset:release": "bun run build && changeset publish --provenance",
37+
"changeset:version": "changeset version && bun update",
38+
"changeset:release": "bun run build && bun scripts/publish.ts",
3939
"format:check": "bun run --filter '*' format:check",
4040
"format": "biome check --write .",
4141
"typecheck": "bun run --filter '*' typecheck"

scripts/publish.ts

Lines changed: 136 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,136 @@
1+
#!/usr/bin/env bun
2+
/*! node-minify - MIT Licensed */
3+
4+
import { execSync } from "node:child_process";
5+
import { existsSync, readdirSync, readFileSync, writeFileSync } from "node:fs";
6+
import { dirname, join } from "node:path";
7+
import { fileURLToPath } from "node:url";
8+
9+
interface PackageJson {
10+
name: string;
11+
version: string;
12+
private?: boolean;
13+
dependencies?: Record<string, string>;
14+
devDependencies?: Record<string, string>;
15+
peerDependencies?: Record<string, string>;
16+
optionalDependencies?: Record<string, string>;
17+
}
18+
19+
const __dirname = dirname(fileURLToPath(import.meta.url));
20+
const PACKAGES_DIR = join(__dirname, "..", "packages");
21+
22+
function getPackageDirs(): string[] {
23+
return readdirSync(PACKAGES_DIR, { withFileTypes: true })
24+
.filter((entry) => entry.isDirectory())
25+
.filter((entry) =>
26+
existsSync(join(PACKAGES_DIR, entry.name, "package.json"))
27+
)
28+
.map((entry) => entry.name)
29+
.sort();
30+
}
31+
32+
function readPackageJson(packageDir: string): PackageJson {
33+
const pkgPath = join(PACKAGES_DIR, packageDir, "package.json");
34+
return JSON.parse(readFileSync(pkgPath, "utf-8"));
35+
}
36+
37+
function buildVersionMap(): Map<string, string> {
38+
const versionMap = new Map<string, string>();
39+
40+
for (const dir of getPackageDirs()) {
41+
const pkg = readPackageJson(dir);
42+
versionMap.set(pkg.name, pkg.version);
43+
}
44+
45+
return versionMap;
46+
}
47+
48+
function resolveDependencies(
49+
deps: Record<string, string> | undefined,
50+
versionMap: Map<string, string>
51+
): Record<string, string> | undefined {
52+
if (!deps) return deps;
53+
54+
const resolved: Record<string, string> = {};
55+
for (const [name, version] of Object.entries(deps)) {
56+
if (version.startsWith("workspace:")) {
57+
const actualVersion = versionMap.get(name);
58+
if (actualVersion) {
59+
resolved[name] = actualVersion;
60+
} else {
61+
console.warn(
62+
`Warning: Could not resolve workspace reference for ${name}`
63+
);
64+
resolved[name] = version;
65+
}
66+
} else {
67+
resolved[name] = version;
68+
}
69+
}
70+
71+
return resolved;
72+
}
73+
74+
async function main() {
75+
const packageDirs = getPackageDirs();
76+
const versionMap = buildVersionMap();
77+
78+
console.log(`Found ${packageDirs.length} packages to publish\n`);
79+
80+
for (const dir of packageDirs) {
81+
const pkgPath = join(PACKAGES_DIR, dir, "package.json");
82+
const originalContent = readFileSync(pkgPath, "utf-8");
83+
const pkg: PackageJson = JSON.parse(originalContent);
84+
85+
if (pkg.private) {
86+
console.log(`Skipping private package: ${pkg.name}`);
87+
continue;
88+
}
89+
90+
pkg.dependencies = resolveDependencies(pkg.dependencies, versionMap);
91+
pkg.devDependencies = resolveDependencies(
92+
pkg.devDependencies,
93+
versionMap
94+
);
95+
pkg.peerDependencies = resolveDependencies(
96+
pkg.peerDependencies,
97+
versionMap
98+
);
99+
pkg.optionalDependencies = resolveDependencies(
100+
pkg.optionalDependencies,
101+
versionMap
102+
);
103+
104+
writeFileSync(pkgPath, `${JSON.stringify(pkg, null, 2)}\n`);
105+
106+
console.log(`Publishing ${pkg.name}@${pkg.version}...`);
107+
108+
try {
109+
execSync("npm publish --access public --provenance", {
110+
cwd: join(PACKAGES_DIR, dir),
111+
stdio: "inherit",
112+
});
113+
console.log(`Published ${pkg.name}@${pkg.version}\n`);
114+
} catch {
115+
console.log(
116+
`Failed to publish ${pkg.name}@${pkg.version} (may already exist)\n`
117+
);
118+
}
119+
120+
writeFileSync(pkgPath, originalContent);
121+
}
122+
123+
console.log("\nCreating git tags...");
124+
try {
125+
execSync("changeset tag", { stdio: "inherit" });
126+
} catch {
127+
console.log("Failed to create tags (may already exist)");
128+
}
129+
130+
console.log("\nDone!");
131+
}
132+
133+
main().catch((error) => {
134+
console.error("Publish failed:", error);
135+
process.exit(1);
136+
});

0 commit comments

Comments
 (0)