jdx/mise · error
packslip:{project} is not on a forge mise knows, so nothing
Error message
packslip:{project} is not on a forge mise knows, so nothing pins its signer; set `pubkey`, or `identity` and `issuer`, in its tool options What it means
Packslip verifies release signatures, so mise must pin a signer: either explicit user options (`pubkey`, or `identity`+`issuer`) or a built-in trust policy for a known forge. `pin` bails when the project is on an unknown host — no built-in policy exists and the user supplied no explicit signer material — so verification would be meaningless.
Source
Thrown at src/backend/packslip.rs:448
file::read_to_string(&pubkey)?
} else {
pubkey
};
let key = packslip::minisign::PublicKey::parse(&text)
.map_err(|e| eyre!("packslip:{project}: pubkey: {e}"))?;
return Ok(Pin::Key(key));
}
let explicit = Policy {
issuer: opts.issuer(),
identity: opts.identity(),
identity_prefix: opts.identity_prefix(),
};
if !explicit.is_empty() {
return Ok(Pin::Identity(explicit));
}
match Policy::for_project(project) {
Some(policy) => Ok(Pin::Identity(policy)),
None => bail!(
"packslip:{project} is not on a forge mise knows, so nothing pins its signer; set `pubkey`, or `identity` and `issuer`, in its tool options"
),
}
}
impl Pin {
/// A vendor may publish its index from a different workflow than its bundles.
/// The override replaces only the list's subject constraint, retaining the issuer.
fn for_release_list(&self, opts: &PackslipOptions<'_>) -> Result<Self> {
let Some(value) = opts.raw.opts.get("list_identity_prefix") else {
return Ok(self.clone());
};
let Some(prefix) = value.as_str().filter(|prefix| !prefix.trim().is_empty()) else {
bail!("packslip: list_identity_prefix must be a non-empty string");
};
let Self::Identity(policy) = self else {
bail!("packslip: list_identity_prefix cannot be combined with pubkey");
};View on GitHub (pinned to afd2eddd3a)
Solutions
- Add a `pubkey` tool option with the project's signing public key.
- Alternatively set `identity` and `issuer` options for signature identity verification.
- Host the tool on a forge mise knows (github.com/gitlab.com) so the built-in policy applies.
Example fix
// before
[tools]
"packslip:releases.corp.example/infra/tool" = "1.4"
// after
[tools]
"packslip:releases.corp.example/infra/tool" = { version = "1.4", pubkey = "<minisign public key>" } Defensive patterns
Strategy: validation
Validate before calling
const KNOWN_FORGES = ["github.com", "gitlab.com"];
const host = new URL("https://" + project.split("/")[0]).hostname;
const hasSigner = opts.pubkey || (opts.identity && opts.issuer);
if (!KNOWN_FORGES.includes(host) && !hasSigner)
throw new Error(`set pubkey (or identity+issuer) for packslip:${project}`); Prevention
- Always ship a `pubkey` (or `identity`+`issuer`) option for custom-host packslip tools.
- Keep signing keys in versioned, reviewed config rather than ad-hoc installs.
- Prefer known forges so mise's built-in trust policies apply automatically.
When it happens
Trigger: Using a `packslip:tool.example.com/owner/repo`-style tool on a self-hosted or niche forge without setting `pubkey` or `identity`/`issuer` tool options.
Common situations: Self-hosted Gitea/Forgejo or corporate artifact hosts publishing packslip manifests; migrating a tool from github.com to a private host without updating its options.
Related errors
- packslip:{project}: this release {}. If the vendor announce
- must not record a pin before replacement succeeds
- packslip:{tool_name} is not a project name; use github.com/o
- the packslip lists {a} and {b} for this host and mise will n
- packslip: list_identity_prefix must be a non-empty string
AI-assisted analysis of jdx/mise@afd2eddd3a (2026-09-09).
Data as JSON: /api/errors/69cc6dc1d1a711cb.
Report an issue: GitHub.