Skip to content

fix(ruby): fetch precompiled binary by release tag instead of listing all releases#8488

Merged
jdx merged 2 commits intomainfrom
fix/ruby-precompiled-pagination
Mar 7, 2026
Merged

fix(ruby): fetch precompiled binary by release tag instead of listing all releases#8488
jdx merged 2 commits intomainfrom
fix/ruby-precompiled-pagination

Conversation

@jdx
Copy link
Copy Markdown
Owner

@jdx jdx commented Mar 7, 2026

Summary

  • Precompiled Ruby lookup used list_releases which only fetches the first page (30 releases) from GitHub
  • Older versions like 3.2.2 were beyond the first page, causing silent fallback to compiling from source
  • Switch to get_release(repo, version) which fetches the specific release by tag directly

Test plan

  • Verified mise x ruby@3.2.2 -- ruby -v now downloads precompiled binary instead of compiling
  • CI tests pass

🤖 Generated with Claude Code


Note

Low Risk
Small, localized change to Ruby precompiled download lookup logic; main risk is incorrect tag/asset matching causing a fallback to source builds.

Overview
Fixes precompiled Ruby asset discovery to fetch the specific GitHub release by tag via github::get_release(repo, version) instead of listing releases and scanning the first page.

This prevents older Ruby versions (beyond GitHub’s default first-page results) from silently missing precompiled assets and falling back to compiling from source, while keeping the existing no-YJIT vs standard asset selection behavior.

Written by Cursor Bugbot for commit 48bfa11. This will update automatically on new commits. Configure here.

… all releases

The precompiled Ruby lookup used `list_releases` which only fetches
the first page (30 releases) from GitHub. Older Ruby versions like
3.2.2 were beyond the first page, causing the lookup to fail silently
and fall through to compiling from source via ruby-build.

Switch to `get_release(repo, version)` which fetches the specific
release by tag, avoiding pagination issues entirely.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@gemini-code-assist
Copy link
Copy Markdown
Contributor

Summary of Changes

Hello, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

This pull request addresses a critical issue in the Ruby plugin's precompiled binary lookup mechanism. Previously, the system relied on listing all GitHub releases, which was limited to the first page of results. This limitation prevented older Ruby versions from finding their precompiled binaries, leading to slower source compilation. The updated approach directly fetches the specific release by its version tag, ensuring that all supported Ruby versions can leverage precompiled binaries for faster and more consistent installations.

Highlights

  • Ruby Precompiled Binary Fetching: The method for fetching precompiled Ruby binaries was updated to use get_release by tag, resolving an issue where list_releases only retrieved the first 30 releases from GitHub.
  • Older Ruby Versions: This change ensures that older Ruby versions, such as 3.2.2, can now correctly download precompiled binaries instead of silently falling back to compiling from source.
  • GitHub API Usage: The implementation now directly fetches a specific GitHub release by its tag, improving the reliability and accuracy of binary lookups.
Changelog
  • src/plugins/core/ruby.rs
    • Replaced the github::list_releases function with github::get_release(repo, version) to fetch a specific GitHub release.
    • Updated the asset search loop to iterate directly over the assets of the single fetched release, removing the outer loop that iterated over multiple releases.
Activity
  • No human activity has been recorded on this pull request yet.
Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

@greptile-apps
Copy link
Copy Markdown
Contributor

greptile-apps bot commented Mar 7, 2026

Greptile Summary

This PR fixes a bug where precompiled Ruby binaries for older versions (e.g. 3.2.2) were silently unavailable because list_releases only fetched the first page (30 releases) from GitHub. The fix switches find_precompiled_asset_in_repo to use get_release(repo, version), which directly fetches the specific release by tag, avoiding any pagination limitation.

Key changes:

  • Replaces github::list_releases(repo) with github::get_release(repo, version) in find_precompiled_asset_in_repo
  • Removes the outer loop over releases (now a single release is returned directly)
  • Errors from get_release are silently swallowed via Err(_) => return Ok(None), causing any failure (including network errors or rate-limiting) to silently fall back to compiling from source rather than surfacing to the user

Confidence Score: 4/5

  • This PR is safe to merge — it correctly resolves a real pagination bug with a simple, well-scoped change.
  • The fix is logically correct and directly addresses the root cause by switching from paginated list_releases to targeted get_release. The change is low-risk with no breaking changes or data loss potential. The only non-critical concern is that all errors from get_release are silently swallowed rather than logged at debug level, which could make troubleshooting harder if transient network or rate-limiting failures occur — but this doesn't prevent merging, just affects debuggability.
  • No files require special attention.

Sequence Diagram

sequenceDiagram
    participant User
    participant mise
    participant GitHub API

    Note over mise,GitHub API: Before (broken for older versions)
    User->>mise: mise x ruby@3.2.2
    mise->>GitHub API: GET /repos/jdx/ruby/releases (page 1, 30 results)
    GitHub API-->>mise: releases [3.4.x ... 3.3.x] (3.2.2 not in first page)
    mise-->>User: Falls back to compiling from source ❌

    Note over mise,GitHub API: After (this PR)
    User->>mise: mise x ruby@3.2.2
    mise->>GitHub API: GET /repos/jdx/ruby/releases/tags/3.2.2
    GitHub API-->>mise: Release with assets for 3.2.2
    mise-->>User: Downloads precompiled binary ✅
Loading

Fix All in Claude Code

Last reviewed commit: fa003aa

Comment on lines +488 to +491
let release = match github::get_release(repo, version).await {
Ok(r) => r,
Err(_) => return Ok(None),
};
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.

Silent swallowing of all errors

All errors from get_release — including transient network failures, GitHub API rate-limiting (HTTP 403), and authentication issues — are silently discarded and treated the same as "release not found", causing a silent fallback to compiling from source. Users could end up waiting for a lengthy source compilation without any indication that a network/rate-limit error occurred.

Consider at least logging the error at debug level before returning Ok(None), similar to how fetch_ruby_release_dates handles errors:

Suggested change
let release = match github::get_release(repo, version).await {
Ok(r) => r,
Err(_) => return Ok(None),
};
let release = match github::get_release(repo, version).await {
Ok(r) => r,
Err(err) => {
debug!("No precompiled release found for ruby@{version}: {err}");
return Ok(None);
}
};

Fix in Claude Code

Copy link
Copy Markdown

@cursor cursor bot left a comment

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 and found 2 potential issues.

Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

let release = match github::get_release(repo, version).await {
Ok(r) => r,
Err(_) => return Ok(None),
};
Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Missing draft/prerelease filtering on fetched release

Low Severity

The old list_releases path filtered out draft and prerelease releases via releases.retain(|r| !r.draft && !r.prerelease). The new get_release path returns whatever the GitHub API returns for the tag, including draft or prerelease releases. This could cause the code to serve assets from an incomplete or in-progress release.

Fix in Cursor Fix in Web

Copy link
Copy Markdown
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

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

Code Review

This pull request aims to resolve an issue where precompiled Ruby binaries for older versions could not be found due to GitHub API pagination by fetching a specific release by its tag. However, it introduces a potential path traversal vulnerability as the version string is not URL-encoded or sanitized before being used to build the API URL, which could allow an attacker to redirect downloads to a malicious repository. Additionally, consider enhancing error handling by logging failures during the release fetch to prevent silent fallbacks and aid debugging.

Comment on lines +488 to +491
let release = match github::get_release(repo, version).await {
Ok(r) => r,
Err(_) => return Ok(None),
};
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.

security-high high

The version string used in github::get_release(repo, version) is not URL-encoded or sanitized, creating a path traversal vulnerability. An attacker could craft a malicious version string (e.g., ruby = "3.3.0/../../attacker/repo/releases/tags/v1") to redirect the API call to an arbitrary GitHub repository, potentially leading to Server-Side Request Forgery (SSRF) or Remote Code Execution (RCE). While addressing this critical vulnerability, it's also beneficial to log errors from github::get_release for debugging, preventing silent fallbacks to source compilation for transient issues.

Suggested change
let release = match github::get_release(repo, version).await {
Ok(r) => r,
Err(_) => return Ok(None),
};
let release = match github::get_release(repo, version).await {
Ok(r) => r,
Err(err) => {
debug!("Failed to get GitHub release for ruby@{version}: {err}");
return Ok(None);
}
};

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@jdx jdx enabled auto-merge (squash) March 7, 2026 01:19
@jdx jdx merged commit 69cefbf into main Mar 7, 2026
35 checks passed
@jdx jdx deleted the fix/ruby-precompiled-pagination branch March 7, 2026 01:32
@github-actions
Copy link
Copy Markdown

github-actions bot commented Mar 7, 2026

Hyperfine Performance

mise x -- echo

Command Mean [ms] Min [ms] Max [ms] Relative
mise-2026.3.3 x -- echo 24.7 ± 0.8 23.1 27.8 1.00
mise x -- echo 25.0 ± 1.1 23.1 32.8 1.01 ± 0.06

mise env

Command Mean [ms] Min [ms] Max [ms] Relative
mise-2026.3.3 env 24.1 ± 0.8 22.4 26.3 1.00
mise env 24.2 ± 1.1 22.6 31.4 1.01 ± 0.06

mise hook-env

Command Mean [ms] Min [ms] Max [ms] Relative
mise-2026.3.3 hook-env 24.6 ± 1.1 23.0 29.7 1.00
mise hook-env 24.7 ± 0.9 23.2 27.4 1.01 ± 0.06

mise ls

Command Mean [ms] Min [ms] Max [ms] Relative
mise-2026.3.3 ls 23.8 ± 0.9 22.4 26.3 1.00
mise ls 23.8 ± 0.9 22.5 27.1 1.00 ± 0.05

xtasks/test/perf

Command mise-2026.3.3 mise Variance
install (cached) 157ms 156ms +0%
ls (cached) 84ms 85ms -1%
bin-paths (cached) 87ms 88ms -1%
task-ls (cached) 850ms 852ms +0%

mise-en-dev added a commit that referenced this pull request Mar 7, 2026
### 🚀 Features

- **(github)** keep exe extensions on Windows by @iki in
[#8424](#8424)
- **(task)** add `interactive` field for exclusive terminal access by
@jdx in [#8491](#8491)
- add header comment to generated lockfiles by @ivy in
[#8481](#8481)
- runtime musl/glibc detection for correct libc variant selection by
@jdx in [#8490](#8490)

### 🐛 Bug Fixes

- **(github)** use registry platform options during install by @jdx in
[#8492](#8492)
- **(http)** store tool opts as native TOML to fix platform switching by
@jdx in [#8448](#8448)
- **(installer)** error if MISE_INSTALL_PATH is a directory by @jdx in
[#8468](#8468)
- **(prepare)** resolve sources/outputs relative to `dir` when set by
@jdx in [#8472](#8472)
- **(ruby)** fetch precompiled binary by release tag instead of listing
all releases by @jdx in [#8488](#8488)
- **(schema)** support structured objects in task depends by @risu729 in
[#8463](#8463)
- **(task)** replace println!/eprintln! with calm_io in task output
macros by @vmaleze in [#8485](#8485)
- handle scoped npm package names without backend prefix by @jdx in
[#8477](#8477)

### 📦️ Dependency Updates

- update ghcr.io/jdx/mise:copr docker digest to c485c4c by
@renovate[bot] in [#8484](#8484)
- update ghcr.io/jdx/mise:alpine docker digest to 8118bc7 by
@renovate[bot] in [#8483](#8483)

### 📦 Registry

- disable sd version test by @jdx in
[#8489](#8489)

### New Contributors

- @ivy made their first contribution in
[#8481](#8481)
- @iki made their first contribution in
[#8424](#8424)

## 📦 Aqua Registry Updates

#### New Packages (5)

- [`datadog-labs/pup`](https://github.com/datadog-labs/pup)
- [`k1LoW/mo`](https://github.com/k1LoW/mo)
- [`rtk-ai/rtk`](https://github.com/rtk-ai/rtk)
-
[`suzuki-shunsuke/docfresh`](https://github.com/suzuki-shunsuke/docfresh)
- [`yashikota/exiftool-go`](https://github.com/yashikota/exiftool-go)

#### Updated Packages (6)

- [`cloudflare/cloudflared`](https://github.com/cloudflare/cloudflared)
- [`mozilla/sccache`](https://github.com/mozilla/sccache)
- [`owenlamont/ryl`](https://github.com/owenlamont/ryl)
- [`spinel-coop/rv`](https://github.com/spinel-coop/rv)
-
[`technicalpickles/envsense`](https://github.com/technicalpickles/envsense)
- [`weaviate/weaviate`](https://github.com/weaviate/weaviate)
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