rust-lang/cargo · error · anyhow::Error

unknown vcs specification: `{}`

Error message

unknown vcs specification: `{}`

What it means

Thrown by VersionControl::from_str when parsing a VCS name supplied via the --vcs flag or the [cargo-new] vcs config key. The parser only recognizes the exact lowercase tokens git, hg, pijul, fossil, none; any other string is rejected before a repository is touched. It exists to fail fast on an unsupported/typo'd VCS choice rather than silently skipping VCS setup.

Source

Thrown at src/ops/cargo_new.rs:40

pub enum VersionControl {
    Git,
    Hg,
    Pijul,
    Fossil,
    NoVcs,
}

impl FromStr for VersionControl {
    type Err = anyhow::Error;

    fn from_str(s: &str) -> Result<Self, anyhow::Error> {
        match s {
            "git" => Ok(VersionControl::Git),
            "hg" => Ok(VersionControl::Hg),
            "pijul" => Ok(VersionControl::Pijul),
            "fossil" => Ok(VersionControl::Fossil),
            "none" => Ok(VersionControl::NoVcs),
            other => anyhow::bail!("unknown vcs specification: `{}`", other),
        }
    }
}

impl<'de> de::Deserialize<'de> for VersionControl {
    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
    where
        D: de::Deserializer<'de>,
    {
        let s = String::deserialize(deserializer)?;
        FromStr::from_str(&s).map_err(de::Error::custom)
    }
}

#[derive(Debug)]
pub struct NewOptions {
    pub version_control: Option<VersionControl>,
    pub kind: NewProjectKind,

View on GitHub (pinned to 0e07a15537)

Solutions

  1. Use one of the supported lowercase tokens: --vcs git | hg | pijul | fossil | none
  2. If the value came from config, edit ~/.cargo/config.toml and fix the [cargo-new] vcs entry to a supported value
  3. Check for trailing whitespace or capitalization in the token
  4. Omit --vcs entirely to let Cargo auto-detect (defaults to git when available)

Example fix

# before
cargo new --vcs SVN myproj
# after
cargo new --vcs git myproj   # or: --vcs none
Defensive patterns

Strategy: validation

Validate before calling

fn is_supported_vcs(s: &str) -> bool {
    matches!(s, "git" | "hg" | "pijul" | "fossil" | "none")
}

// before calling cargo or parsing config:
let vcs = read_vcs_from_config_or_args();
assert!(is_supported_vcs(vcs), "unsupported vcs: {vcs}");

Type guard

const SUPPORTED_VCS: &[&str] = &["git", "hg", "pijul", "fossil", "none"];
fn isVersionControl(s: string): s is typeof SUPPORTED_VCS[number] {
  return (SUPPORTED_VCS as readonly string[]).includes(s);
}

Prevention

When it happens

Trigger: Run `cargo new --vcs svn myproj`, set `[cargo-new] vcs = "github"` in ~/.cargo/config.toml, or call `VersionControl::from_str("subversion")` programmatically. Any token outside {git,hg,pijul,fossil,none} hits the `other` arm at cargo_new.rs:40.

Common situations: Typos like `--vcs git2` or `--vcs GitHub`, copy-pasting a config from a tutorial that used a non-supported value, or assuming a VCS (e.g. `svn`, `bzr`, `jj`) is supported when it is not. Case sensitivity also bites: `Git`/`GIT` are rejected.

Related errors


AI-assisted analysis of rust-lang/cargo@0e07a15537 (2026-08-06). Data as JSON: /data/errors/2e54611e6ec7e21e.json. Report an issue: GitHub.