denoland/deno · error
Unexpected package json dependency string: "{string_value}"
Error message
Unexpected package json dependency string: "{string_value}" in {} What it means
When the dependency manager rewrites a version in package.json, it handles `npm:`-aliased entries and plain versions. Any other value containing `:` — `jsr:@scope/pkg@^1`, `http:...`, `git+ssh:...` — hits this bail because rewriting it would corrupt an unsupported scheme.
Source
Thrown at cli/tools/pm/deps.rs:1165
);
continue;
};
let Some(string_value) = cst_string_literal(&property) else {
continue;
};
let new_value = if string_value.starts_with("npm:") {
// aliased
let rest = string_value.trim_start_matches("npm:");
let mut parts = rest.split('@');
let first = parts.next().unwrap();
if first.is_empty() {
let scope_and_name = parts.next().unwrap();
format!("npm:@{scope_and_name}@{version_req}")
} else {
format!("npm:{first}@{version_req}")
}
} else if string_value.contains(":") {
bail!(
"Unexpected package json dependency string: \"{string_value}\" in {}",
arc.path.display()
);
} else {
version_req.to_string()
};
property
.set_value(jsonc_parser::cst::CstInputValue::String(new_value));
}
DepLocation::Catalog {
path, key_paths, ..
} => {
let updater =
get_or_create_updater(&mut config_updaters, &dep.location)?;
if !updater
.update_catalog_entry(key_paths, &version_req.to_string())
{
log::warn!(View on GitHub (pinned to 9ad36f7a2c)
Solutions
- Move `jsr:` dependencies into deno.json `imports` and keep plain npm versions in package.json.
- For npm-aliased entries keep the `npm:name` form (supported) rather than other schemes.
- After editing, re-run the original command to confirm the rewrite succeeds.
Example fix
// package.json (before)
{
"dependencies": { "my-lib": "jsr:@scope/my-lib@^1.0.0" }
}
// deno.json (after)
{
"imports": { "my-lib": "jsr:@scope/my-lib@^1.0.0" }
}
// package.json (after)
{
"dependencies": {}
} Defensive patterns
Strategy: validation
Validate before calling
const pkg = JSON.parse(readFileSync("package.json", "utf8"));
const deps = { ...pkg.dependencies, ...pkg.devDependencies };
const bad = Object.entries(deps).filter(([, v]) => v.includes(":") && !String(v).startsWith("npm:"));
if (bad.length) {
console.error(`non-npm specifiers in package.json: ${bad.map(([k, v]) => `${k}@${v}`).join(", ")}`);
process.exit(1);
} Type guard
const isRewritablePkgJsonDep = (v: string): boolean =>
!v.includes(":") || v.startsWith("npm:"); Prevention
- Store jsr:/http:/git specifiers in deno.json imports, never in package.json dependencies.
- Only `npm:`-prefixed aliases and plain semver strings are safe in package.json for the Deno updater.
- Lint mixed projects for cross-registry specifier leaks in CI.
When it happens
Trigger: `deno add`/`deno remove`/`deno install` updating a package.json whose dependencies/devDependencies contain a non-npm scheme string, e.g. `"my-lib": "jsr:@scope/my-lib@^1.0.0"`. A hand-edited package.json using jsr: or a git URL where a plain version is expected.
Common situations: Mixed Deno/npm projects that stored JSR deps in package.json; copying an import-map entry into package.json dependencies; converting npm deps to jsr without moving them to deno.json imports.
Related errors
- missing version in package.json of npm package
- Only npm packages are supported: {}
- {entry_text} is missing a prefix. Did you mean `{}`?
- '{}' did not have a bin property with a string or non-empty
- '{}' did not have a bin entry for '{}'{}
AI-assisted analysis of denoland/deno@9ad36f7a2c (2026-08-20).
Data as JSON: /api/errors/b76ecd6c4fc126d8.
Report an issue: GitHub.