Skip to content

Commit aff2d0f

Browse files
authored
fix: yarn v4 support for monorepos (#171)
1 parent 0ce8359 commit aff2d0f

File tree

3 files changed

+42
-8
lines changed

3 files changed

+42
-8
lines changed

CHANGELOG.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@
33
Placeholder for the next version (at the beginning of the line):
44
## **WORK IN PROGRESS**
55
-->
6+
## **WORK IN PROGRESS**
7+
* `package` plugin: Support monorepos managed with Yarn v4
8+
69
## 3.7.2 (2024-06-24)
710
* `iobroker` plugin: Fixed issue in changelog cleanup routine introduced in `3.7.1`
811

packages/plugin-package/src/index.test.ts

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -170,6 +170,11 @@ describe("Package plugin", () => {
170170
".yarnrc.yml": fixtures.yarnrc_commented_out,
171171
});
172172

173+
context.sys.mockExec((cmd) => {
174+
if (cmd === "yarn --version") return "3.4.5";
175+
return "";
176+
});
177+
173178
await assertReleaseError(() => pkgPlugin.executeStage(context, DefaultStages.check), {
174179
fatal: true,
175180
messageMatches: /plugin import version/i,
@@ -240,11 +245,10 @@ describe("Package plugin", () => {
240245
context.setData("version_new", newVersion);
241246
context.setData("monorepo", "yarn");
242247

243-
context.sys.mockExec((cmd) =>
244-
cmd.includes("changed list")
245-
? "" // no changes!
246-
: "",
247-
);
248+
context.sys.mockExec((cmd) => {
249+
if (cmd === "yarn --version") return "3.4.5";
250+
return "";
251+
});
248252

249253
await assertReleaseError(() => pkgPlugin.executeStage(context, DefaultStages.check), {
250254
fatal: true,
@@ -405,6 +409,7 @@ describe("Package plugin", () => {
405409
"yarn",
406410
"changed",
407411
"foreach",
412+
"--all",
408413
`--git-range=v${pack.version}`,
409414
"version",
410415
newVersion,

packages/plugin-package/src/index.ts

Lines changed: 29 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,15 @@ async function getUpdatePackages(
4646
return updatePackages;
4747
}
4848

49+
async function getYarnVersion(context: Context): Promise<string> {
50+
const { stdout: output } = await context.sys.exec("yarn", ["--version"], { cwd: context.cwd });
51+
const version = output.trim();
52+
if (!semver.valid(version)) {
53+
context.cli.fatal(`Invalid yarn version "${version}"`);
54+
}
55+
return version;
56+
}
57+
4958
class PackagePlugin implements Plugin {
5059
public readonly id = "package";
5160
public readonly stages = [DefaultStages.check, DefaultStages.edit, DefaultStages.commit];
@@ -100,6 +109,8 @@ class PackagePlugin implements Plugin {
100109
// we need some yarn plugins to be able to handle this
101110
const yarnRcPath = path.join(context.cwd, ".yarnrc.yml");
102111
if (await fs.pathExists(yarnRcPath)) {
112+
const yarnVersion = await getYarnVersion(context);
113+
103114
const yarnRc = await fs.readFile(yarnRcPath, "utf8");
104115
const yarnPlugins = yarnRc
105116
.split("\n")
@@ -114,11 +125,16 @@ class PackagePlugin implements Plugin {
114125
);
115126
// A list of required plugins and how to import them
116127
const requiredPlugins: Record<string, string> = {
117-
"workspace-tools": "workspace-tools",
118-
version: "version",
119128
changed:
120129
"https://github.com/Dcard/yarn-plugins/releases/latest/download/plugin-changed.js",
121130
};
131+
if (semver.lt(yarnVersion, "4.0.0")) {
132+
// Yarn v4 includes these plugins by default
133+
Object.assign(requiredPlugins, {
134+
"workspace-tools": "workspace-tools",
135+
version: "version",
136+
});
137+
}
122138
const missingPlugins = Object.keys(requiredPlugins).filter(
123139
(plugin) => !yarnPlugins.includes(plugin),
124140
);
@@ -137,6 +153,7 @@ Alternatively, you can use ${context.cli.colors.blue("lerna")} to manage the mon
137153

138154
// All good, remember that we use yarn to manage the monorepo
139155
context.setData("monorepo", "yarn");
156+
context.setData("yarn_version", yarnVersion);
140157

141158
// One last check: make sure there is anything to publish
142159
// We cannot use getEffectivePublishAllFlag here without introducing a circular dependency
@@ -280,11 +297,20 @@ Alternatively, you can use ${context.cli.colors.blue("lerna")} to manage the mon
280297
await deleteStableVersions();
281298
const commands = [
282299
publishAll
283-
? ["yarn", "workspaces", "foreach", "version", newVersion, "--deferred"]
300+
? [
301+
"yarn",
302+
"workspaces",
303+
"foreach",
304+
"--all",
305+
"version",
306+
newVersion,
307+
"--deferred",
308+
]
284309
: [
285310
"yarn",
286311
"changed",
287312
"foreach",
313+
"--all",
288314
`--git-range=v${pack.version}`,
289315
"version",
290316
newVersion,

0 commit comments

Comments
 (0)