Skip to content

Prefer compatible package binaries by default - #156

Merged
t-kalinowski merged 13 commits into
mainfrom
feat/prefer-package-binaries
Oct 1, 2026
Merged

t-kalinowski merged 13 commits into
mainfrom
feat/prefer-package-binaries

Conversation

@t-kalinowski

@t-kalinowski t-kalinowski commented Sep 30, 2026 •

Copy link
Copy Markdown
Member

A new CRAN release can be available as source for days, sometimes up to a week, before its pre-built binaries are ready. During that gap, IR currently picks the newest version. I recently ran into this with DuckDB: IR started a slow source build even though an older compatible binary was available.

This PR makes IR prefer compatible binaries, including older versions, for ordinary package requests and their dependencies. Source-only packages can still install alongside binaries.

Set IR_PREFER_BINARIES=0 to keep prioritizing newer versions. This does not force source installation. Exact pins, minimum versions, and explicit Git, local, URL, or source requests still control what IR installs. MCP Console gets the new default automatically, without configuration changes.

IR still uses pak to resolve dependencies and renv to install them:

  • Ordinary requests go into a temporary DESCRIPTION file with a unique package name so pak applies its binary preference to requested packages too. This uses pak's public API and adds no pkgdepends dependency or vendored solver code.
  • IR passes the selected versions and URLs to renv::restore(), preserving the chosen binary through installation.
  • If a binary download returns HTTP 404 or 410, IR asks pak to resolve once more using source for that package. pak recalculates the dependencies for the source version. Other errors remain visible. IR may use source even when another older binary could work.
  • Cache keys include the binary preference and selected artifacts. Unset and 1 share cached resolutions; 0 is separate. Old plans and incomplete installations are bypassed.

Downloaded archives stay under IR's resolver lock. renv's installed-package cache remains shared, with artifact keys scoped to the IR cache root so concurrent runs using separate roots cannot replace each other's entries.

Local repository tests reproduce the release-lag case: a 1.0.0 binary, a 2.0.0 source release, and a source-only dependency. They check the installed artifact, constraints, fallback, and cache reuse. A synchronized regression also replaces a cached binary during installation and checks that IR still produces a complete library. Documentation includes opt-out examples and a release note about the default and cache transition.

With renv 1.3.0 in an isolated library, NEXTEST_TEST_THREADS=2 scripts/check.sh passed on macOS: formatting, Clippy, and all 222 tests, with none skipped. Quarto render tests share a nextest group to avoid concurrent writes to Quarto’s Sass cache.

Keep source candidates in pak's dependency solve while preferring compatible
repository binaries, including older releases. Preserve selected artifacts
through renv and re-solve after missing binary downloads.

Add IR_PREFER_BINARIES=0, version policy and artifact cache identities, and
cover release lag, constraints, fallback, and cache transitions with local
repository CLI fixtures. Document the default and opt-out.
@chatgpt-codex-connector

chatgpt-codex-connector Bot commented Sep 30, 2026 •

Copy link
Copy Markdown

Codex Review Summary

This comment shows the latest Codex review activity on this pull request.

Review Status Commit Review trigger
📝 Code Review ✅ Completed 2026-10-01T12:32:22.386851Z f1258c6 New commits
🔒 Security Review ✅ Completed 2026-09-30T17:42:50.084712Z 58d7d41 PR opened
ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review" or "@codex security review".

Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings.

Resolve ordinary requests through pak's lazy dependency policy and restore
selected artifact URLs through renv's lockfile interface. Re-solve once
with source requests for missing binaries, preserving constraints and
separate policy cache identities.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: d6d9e1c794

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread driver/resolve.R
Comment thread driver/resolve.R Outdated
Allow the documented driver entry point without private policy flags and
report conflicting flags explicitly. Exercise its binary default and
version-freshness mode against the local repository fixture.

Verify that ambient user-library installations cannot supply the isolated
environment's artifact. pak already resolves against an empty library;
document that boundary without changing its public API usage.
The direct-driver regression is cross-platform, but stderr() was gated
to macOS. Remove that restriction so the Linux and Windows test targets
compile with the same diagnostic assertion.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 56e87090c5

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread driver/resolve.R Outdated
Read a fresh inventory before verifying restored packages and versions.
Qualify namespace calls so the resolver works with reduced default packages.

Cover stale inventories and reduced-default binary installation and source
fallback through the public CLI.
Place renv's mutable archive downloads under the existing resolver lock so
concurrent resolutions with separate IR caches cannot overwrite each other.
Keep explicit download-cache overrides and the shared installed-package cache.
Independent IR caches have separate resolver locks. Sharing the same renv
artifact entry lets one restore temporarily remove a package still linked
by another.

Include the normalized IR cache root in artifact and library identities,
and update the resolution cache format. Reproduce cache replacement with
local packages and socket checkpoints, and cover the cache transition
through the CLI.
Drop inherited R_LIBS so ambient packages cannot override the fixture's
fake installer through R_LIBS_USER.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: f96dbcd3e0

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread driver/resolve.R Outdated
Use the temporary directory name to keep the synthetic root distinct from
repository packages. Cover direct and transitive requests for irrequirements
through the public CLI.
Use a nextest group for real Quarto renders so concurrent tests cannot
contend for the shared Sass database. Keep other tests parallel.
@t-kalinowski
t-kalinowski merged commit efcd616 into main Oct 1, 2026
3 of 4 checks passed
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