Skip to content

fix(lazy install): keep production focused installs production - #367

Merged
arcanis merged 3 commits into
mainfrom
mael/lazy-install-production
Oct 14, 2026
Merged

arcanis merged 3 commits into
mainfrom
mael/lazy-install-production

Conversation

@arcanis

@arcanis arcanis commented Oct 8, 2026 •

Copy link
Copy Markdown
Member

Issue: after yarn workspaces focus <ws> --production, the first command run from that workspace triggered a full install. The lazy install check included devDependencies, so workspaces only reachable through them looked missing.

Fix: the install state records whether the install was a production one. If it was, the check only follows production dependencies. Covered by a lazy-install test.


Note

Medium Risk
Changes lazy-install eligibility and focused-install extension behavior for monorepos; incorrect handling could skip needed installs or omit dev deps when users expect a full tree.

Overview
Fixes lazy install treating production yarn workspaces focus … --production installs like full installs, which could trigger an unnecessary reinstall or pull devDependencies back in when extending coverage.

Install state now records a production flag (from prune_dev_dependencies during install) and persists it with the rest of InstallState. Lazy install reads that flag: workspace closure and focused-install extension only follow production/optional deps when production is true, and any triggered install keeps prune_dev_dependencies aligned so dev deps are not re-added.

Acceptance tests cover skipping lazy install after a production focus and keeping dev packages out of .pnp.cjs when another workspace extends the tree.

Reviewed by Cursor Bugbot for commit 6e89dc5. Bugbot is set up for automated code reviews on this repo. Configure here.

After `yarn workspaces focus <ws> --production`, the first command run
from that workspace started a full install. The lazy install check
included devDependencies when computing the workspaces the current one
needs, so workspaces only reachable through devDependencies looked
missing.

The install state now records whether the install was a production
one. If it was, the check only follows production dependencies.

@cursor cursor Bot left a comment •

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes using default effort and found 1 potential issue.

Autofix Details

Bugbot Autofix prepared a fix for the issue found in the latest run.

  • ✅ Fixed: Production mode dropped on lazy reinstall
    • Modified lazy_install to respect the stored production flag when calling run_install and when extending focused install roots, preventing production mode from being cleared on implicit reinstalls.

Create PR

Or push these changes by commenting:

@cursor push 907129ace1
Preview (907129ace1)
diff --git a/packages/zpm/src/project.rs b/packages/zpm/src/project.rs
--- a/packages/zpm/src/project.rs
+++ b/packages/zpm/src/project.rs
@@ -1526,7 +1526,7 @@
                             .chain(required_workspaces.iter())
                             .cloned();
 
-                        Some(self.workspace_dependency_closure(roots, true)?)
+                        Some(self.workspace_dependency_closure(roots, include_dev_dependencies)?)
                     } else {
                         None
                     }
@@ -1536,11 +1536,14 @@
             None
         };
 
+        let prune_dev_dependencies
+            = self.install_state.as_ref().is_some_and(|install_state| install_state.production);
+
         let install = self.run_install(RunInstallOptions {
             check_checksums: false,
             check_resolutions: false,
             enforced_resolutions: BTreeMap::new(),
-            prune_dev_dependencies: false,
+            prune_dev_dependencies,
             refresh_lockfile: false,
             silent_or_error: true,
             mode: None,

You can send follow-ups to the cloud agent here.

Comment thread packages/zpm/src/project.rs Resolved
@netlify

netlify Bot commented Oct 8, 2026 •

Copy link
Copy Markdown

✅ Deploy Preview for yarn-v6 ready!

Name Link
🔨 Latest commit 6e89dc5
🔍 Latest deploy log https://app.netlify.com/projects/yarn-v6/deploys/6acf38cb578c2aa18cac648a
😎 Deploy Preview https://deploy-preview-367--yarn-v6.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.
🤖 Make changes Run an agent on this branch

To edit notification comments on pull requests, go to your Netlify project configuration.

@github-actions

github-actions Bot commented Oct 8, 2026 •

Copy link
Copy Markdown

⏱️ Benchmark Results

gatsby install-full-cold

Metric Base Head Difference
Mean 4.352s 4.405s +1.20% ⚠️
Median 4.353s 4.408s +1.27% ⚠️
Min 4.253s 4.288s
Max 4.465s 4.484s
Std Dev 0.062s 0.050s
📊 Raw benchmark data (gatsby install-full-cold)

Base times: 4.312s, 4.365s, 4.329s, 4.329s, 4.278s, 4.253s, 4.374s, 4.272s, 4.429s, 4.274s, 4.306s, 4.350s, 4.400s, 4.355s, 4.267s, 4.322s, 4.319s, 4.307s, 4.461s, 4.465s, 4.443s, 4.440s, 4.394s, 4.364s, 4.416s, 4.375s, 4.398s, 4.392s, 4.289s, 4.292s

Head times: 4.404s, 4.437s, 4.311s, 4.377s, 4.437s, 4.373s, 4.385s, 4.440s, 4.419s, 4.401s, 4.362s, 4.451s, 4.484s, 4.370s, 4.288s, 4.412s, 4.479s, 4.334s, 4.457s, 4.417s, 4.388s, 4.484s, 4.362s, 4.415s, 4.360s, 4.484s, 4.383s, 4.425s, 4.417s, 4.386s


gatsby install-cache-only

Metric Base Head Difference
Mean 1.332s 1.332s -0.02% ✅
Median 1.331s 1.326s -0.38% ✅
Min 1.315s 1.300s
Max 1.360s 1.514s
Std Dev 0.012s 0.037s
📊 Raw benchmark data (gatsby install-cache-only)

Base times: 1.338s, 1.322s, 1.334s, 1.355s, 1.328s, 1.352s, 1.331s, 1.325s, 1.320s, 1.322s, 1.360s, 1.331s, 1.323s, 1.316s, 1.320s, 1.330s, 1.317s, 1.319s, 1.357s, 1.333s, 1.332s, 1.315s, 1.336s, 1.343s, 1.347s, 1.322s, 1.332s, 1.334s, 1.332s, 1.337s

Head times: 1.300s, 1.322s, 1.337s, 1.334s, 1.339s, 1.338s, 1.325s, 1.348s, 1.344s, 1.330s, 1.334s, 1.336s, 1.327s, 1.322s, 1.339s, 1.342s, 1.352s, 1.328s, 1.514s, 1.317s, 1.302s, 1.305s, 1.304s, 1.318s, 1.319s, 1.315s, 1.320s, 1.320s, 1.312s, 1.311s


gatsby install-cache-and-lock (warm, with lockfile)

Metric Base Head Difference
Mean 0.372s 0.377s +1.25% ⚠️
Median 0.370s 0.372s +0.61% ⚠️
Min 0.364s 0.367s
Max 0.395s 0.497s
Std Dev 0.007s 0.023s
📊 Raw benchmark data (gatsby install-cache-and-lock (warm, with lockfile))

Base times: 0.368s, 0.371s, 0.368s, 0.368s, 0.370s, 0.370s, 0.370s, 0.373s, 0.370s, 0.368s, 0.369s, 0.369s, 0.367s, 0.364s, 0.364s, 0.365s, 0.366s, 0.369s, 0.368s, 0.380s, 0.377s, 0.381s, 0.378s, 0.379s, 0.375s, 0.376s, 0.380s, 0.395s, 0.369s, 0.372s

Head times: 0.373s, 0.372s, 0.368s, 0.371s, 0.367s, 0.370s, 0.373s, 0.497s, 0.372s, 0.370s, 0.367s, 0.374s, 0.380s, 0.375s, 0.373s, 0.368s, 0.374s, 0.374s, 0.390s, 0.376s, 0.372s, 0.368s, 0.367s, 0.369s, 0.372s, 0.372s, 0.372s, 0.372s, 0.370s, 0.380s

When a command outside the focused workspaces extended a production
install, the lazy install followed devDependencies and ran without
pruning them, putting them back in the tree and clearing the flag.
Both now follow the production setting of the previous install.

@cursor cursor Bot left a comment •

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes using default effort and found 1 potential issue.

Fix All in Cursor

Bugbot Autofix prepared a fix for the issue found in the latest run.

  • ✅ Fixed: Full lazy install strips dests
    • Changed prune_dev_dependencies to only be true when both production mode AND install_roots is Some (focused install), preventing lockfile corruption when unfocused installs rewrite the lockfile.

Create PR

Or push these changes by commenting:

@cursor push 7c0c72135a
Preview (7c0c72135a)
diff --git a/packages/zpm/src/project.rs b/packages/zpm/src/project.rs
--- a/packages/zpm/src/project.rs
+++ b/packages/zpm/src/project.rs
@@ -1542,7 +1542,7 @@
             check_checksums: false,
             check_resolutions: false,
             enforced_resolutions: BTreeMap::new(),
-            prune_dev_dependencies: production,
+            prune_dev_dependencies: production && install_roots.is_some(),
             refresh_lockfile: false,
             silent_or_error: true,
             mode: None,

You can send follow-ups to the cloud agent here.

Reviewed by Cursor Bugbot for commit a8f1f57. Configure here.

Comment thread packages/zpm/src/project.rs Resolved
…duction

# Conflicts:
#	tests/acceptance-tests/pkg-tests-specs/sources/features/lazyInstalls.test.ts
@cursor

cursor Bot commented Oct 14, 2026

Copy link
Copy Markdown
Contributor

Bugbot couldn't run - usage limit reached

Bugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit.

A user or team admin can review and increase usage limits in the Cursor dashboard.

(requestId: e4c770f7-173b-4f60-9fa4-1f30e1944c4f)

@arcanis
arcanis merged commit 9964e68 into main Oct 14, 2026
27 checks passed
@arcanis
arcanis deleted the mael/lazy-install-production branch October 14, 2026 09:03

This branch was successfully deployed

1 active deployment
test-reports — 6e89dc54 Deployed Oct 14, 2026 by arcanis via Reporting test results #1465
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant