jdx/mise · error

must provide a version for

Error message

must provide a version for {}

What it means

`mise link` creates a symlink exposing a local path as an installed tool version, which requires a concrete version or ref to name the install directory. If the tool request omits a version entirely (only the backend/name was given), mise cannot derive where to link, so it throws this error naming the tool request.

Solutions

  1. Add a concrete version to the tool argument: `mise link node@22.1.0 /path/to/dir`
  2. Use a ref form if linking a source checkout: `mise link node@ref:main /path/to/dir`
  3. Check `mise ls-remote <tool>` for a valid version string to use

Example fix

// before
mise link node ./node-build
// after
mise link node@22.1.0 ./node-build
Defensive patterns

Strategy: validation

Validate before calling

// bash: ensure a version is present before linking
[[ "$1" == *@* || "$1" == *@ref:* ]] || { echo "usage: mise link <tool>@<version> <path>"; exit 1; }

Prevention

When it happens

Trigger: Running `mise link <tool> --path <path>` without a version argument, e.g. `mise link node ./my-node` instead of `mise link node@22.1.0 ./my-node`, so `self.tool.tvr` is None.

Common situations: Users forgetting the `@version` suffix because `mise install node` works without one; scripts built for `mise use`/`mise install` syntax reused for `mise link`.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of jdx/mise@533346cc37 (2026-09-17). Data as JSON: /api/errors/ef4586ecf23cb566. Report an issue: GitHub.

Appendix: source

Thrown at src/cli/link.rs:55

    /// The local path to the tool version
    /// e.g.: ~/.nvm/versions/node/v20.0.0
    #[usage(value_hint = ValueHint::DirPath, verbatim_doc_comment)]
    path: PathBuf,

    /// Overwrite an existing tool version if it exists
    #[usage(long, short = 'f')]
    force: bool,
}

impl Link {
    pub(crate) async fn run(self) -> Result<()> {
        let tvr = match self.tool.tvr.as_ref() {
            Some(tvr @ (ToolRequest::Version { .. } | ToolRequest::Ref { .. })) => tvr,
            Some(tvr) => bail!(
                "mise link only supports concrete versions and refs, not {}",
                tvr.version()
            ),
            None => bail!("must provide a version for {}", self.tool.style()),
        };
        let config = Config::get().await?;
        let version_pathname = match tvr {
            ToolRequest::Version { version, .. } => {
                let backend = tvr.backend()?;
                let resolved_alias = config.resolve_alias(&backend, version).await?;
                if version == "latest"
                    || resolved_alias != *version
                    || backend.is_rolling_channel(version)
                {
                    bail!(
                        "mise link only supports concrete versions and refs, not {}",
                        tvr.version()
                    );
                }
                ToolVersion::new(tvr.clone(), version.clone()).tv_pathname()
            }
            ToolRequest::Ref { .. } => ToolVersion::new(tvr.clone(), tvr.version()).tv_pathname(),

View on GitHub (pinned to 533346cc37)