Mise Attestation Verification Error
问题描述
在运行 make sync-lock 或 mise install 时,可能会遇到以下错误:
mise ERROR github:astral-sh/ruff@0.15.10 has no provenance verification on linux-x64-musl,
but github:astral-sh/ruff@0.15.9 had github-attestations. This could indicate a supply chain attack.
Verify the release is authentic before proceeding.根本原因
这个错误是由于 mise 使用 Aqua Registry 作为后端来安装工具,而不是直接从 GitHub 下载。
🚨 为什么必须禁止 Aqua Registry?
供应链完整性问题
- Aqua Registry 会重新打包 GitHub Releases 的二进制文件
- 重新打包过程会导致 GitHub Artifact Attestations(来源证明)丢失
- 这使得无法验证二进制文件的真实来源和完整性
误报供应链攻击
- mise 检测到新版本(如 0.15.10)没有 attestations
- 但旧版本(如 0.15.9)有 attestations
- mise 会误报为潜在的供应链攻击
- 实际上这是 Aqua Registry 的问题,不是真正的攻击
官方维护者确认
- Ruff 官方维护者在 Issue #2071091068 中明确指出
- Aqua Registry 的重新打包导致 provenance 丢失
- 这不是 Ruff 的问题,而是 Aqua 的设计缺陷
mise 的默认行为
- 当你在
.mise.toml中写github:astral-sh/ruff时 - mise 实际上使用
aqua:astral-sh/ruff作为后端 - metadata 查询来自 GitHub API
- 但二进制下载来自 Aqua Registry(默认优先)
- 这就是"明明写 github:,却不是从 GitHub 下载"的根本原因
- 当你在
技术细节
Mise 的后端机制
- 当你在
.mise.toml中指定github:astral-sh/ruff时 - mise 实际上使用
aqua:astral-sh/ruff作为后端 - 可以在 https://mise-versions.jdx.dev/tools/ruff 查看
- 当你在
Aqua Registry 配置
- Aqua Registry 在
pkgs/astral-sh/ruff/registry.yaml中配置了github_artifact_attestations - 配置要求验证 GitHub Artifact Attestations(来源证明)
- Aqua Registry 在
验证失败的原因
- mise 在某些平台(如 linux-x64-musl, linux-arm64, macos-x64 等)上无法找到或验证 attestations
- 这可能是由于:
- mise 的 attestation 验证逻辑有 bug
- GitHub API 返回的 attestation 数据格式变化
- 网络问题导致无法下载 attestation 文件
- Aqua Registry 的配置与实际 release 不匹配
实际情况
- 经过验证,ruff 0.15.9 和 0.15.10 都有 GitHub Artifact Attestations
- 可以通过
gh attestation verify命令验证 - 这不是真正的供应链攻击,而是 mise 的误报
解决方案
🛡️ 方案 1: 三层防御 - 完全禁止 Aqua Registry(强烈推荐)
这是最彻底的解决方案,确保 mise 永远只从 GitHub Releases 下载二进制文件。
第一层:mise 配置文件
在 .mise.toml 的 [settings] 部分添加:
toml
[settings]
# 🛡️ Supply Chain Security: Disable Aqua Registry Backend
# CRITICAL: Force mise to download binaries ONLY from GitHub Releases,
# not from Aqua Registry which may repackage binaries and lose provenance.
aqua.baked_registry = false
aqua.github_attestations = false
aqua.slsa = false
aqua.cosign = false
aqua.minisign = false第二层:环境变量强制
在 .mise.toml 的 [env] 部分添加:
toml
[env]
# 🛡️ Layer 2: Environment Variable Enforcement
# Force disable Aqua Registry even if settings are overridden
MISE_DISABLE_AQUA = "1"或者在 shell 配置文件(~/.bashrc, ~/.zshrc)中添加:
bash
export MISE_DISABLE_AQUA=1第三层:CI 环境变量
在 CI 配置中添加环境变量:
yaml
# .github/workflows/ci.yml
env:
MISE_DISABLE_AQUA: 1验证配置是否生效
bash
# 1. 检查 aqua 设置是否已禁用
mise settings ls | grep aqua
# 应该看到:
# aqua.baked_registry false
# aqua.cosign false
# aqua.github_attestations false
# aqua.minisign false
# aqua.slsa false
# 2. 测试安装工具(使用 verbose 模式)
MISE_VERBOSE=1 mise install github:astral-sh/ruff@0.15.10 2>&1 | grep -i "aqua\|github"
# 应该看到:
# - 没有任何 "aqua" 字样
# - 下载 URL 应该是 https://github.com/astral-sh/ruff/releases/download/...方案 2: 临时跳过验证(不推荐,仅用于紧急情况)
使用环境变量临时跳过校验和验证:
bash
export MISE_SKIP_CHECKSUM=1
make sync-lock警告: 这会跳过所有完整性验证,存在安全风险。
方案 3: 手动验证后继续
- 手动验证 release 的真实性:
bash
# 下载 ruff 二进制文件
gh release download 0.15.10 --repo astral-sh/ruff --pattern "ruff-x86_64-unknown-linux-gnu.tar.gz"
# 验证 attestation
gh attestation verify ruff-x86_64-unknown-linux-gnu.tar.gz --repo astral-sh/ruff- 确认验证通过后,使用
--yes标志强制安装:
bash
mise install github:astral-sh/ruff@0.15.10 --yes方案 4: 降级到已知可用的版本
如果 attestation 验证持续失败,可以暂时使用 0.15.9:
toml
# .mise.toml
[tools]
"github:astral-sh/ruff" = "0.15.9"方案 5: 切换到其他安装方式
使用 pipx 或 cargo 安装 ruff,而不是通过 mise:
toml
# .mise.toml
[tools]
# 使用 pipx 安装(Python 包)
"pipx:ruff" = "0.15.10"
# 或使用 cargo 安装(Rust 包)
"cargo:ruff" = "0.15.10"验证步骤
1. 检查 mise 使用的后端
bash
# 查看 mise 版本信息
mise --version
# 查看工具的后端信息
mise ls --json | jq '.[] | select(.name == "ruff")'2. 手动验证 GitHub Attestations
bash
# 安装 GitHub CLI(如果还没有)
brew install gh # macOS
# 或
apt install gh # Linux
# 验证 attestation
gh attestation verify <downloaded-file> --repo astral-sh/ruff3. 检查 Aqua Registry 配置
查看 Aqua Registry 中 ruff 的配置: https://github.com/aquaproj/aqua-registry/blob/main/pkgs/astral-sh/ruff/registry.yaml
预防措施
1. 锁定版本
在 mise.lock 中锁定已验证的版本:
bash
# 生成或更新 lockfile
mise install
mise lock2. 使用 CI 缓存
在 CI 中缓存 mise 安装的工具,避免每次都重新验证:
yaml
# .github/workflows/ci.yml
- uses: actions/cache@v4
with:
path: ~/.local/share/mise
key: mise-${{ runner.os }}-${{ hashFiles('mise.lock') }}3. 监控 mise 更新
关注 mise 的更新日志,查看 attestation 验证相关的修复:
相关链接
报告问题
如果你认为这是 mise 的 bug,可以在以下位置报告:
- Mise 项目: https://github.com/jdx/mise/issues
- Aqua Registry: https://github.com/aquaproj/aqua-registry/issues
报告时请包含:
- mise 版本 (
mise --version) - 操作系统和架构
- 完整的错误信息
MISE_VERBOSE=1的详细日志
