jdx/mise · error
null values cannot be represented in mise.lock
Error message
null values cannot be represented in mise.lock
What it means
yaml_to_toml, used when converting an aube (npm) lockfile from YAML to mise.lock TOML, hit a YAML null value. TOML has no null, so the value cannot be represented in mise.lock and conversion aborts; the upstream lockfile's null entry is the input at fault.
Solutions
- Replace the null with a concrete string/number value
- Remove the key entirely if the value is meaningless
- Restore mise.lock from git
- Delete and regenerate the lockfile
Example fix
# before checksum: null # after checksum: "sha256:abc123..."
Defensive patterns
Strategy: validation
Validate before calling
yq -e '[.. | tag == "!!null"] | length == 0' mise.lock >/dev/null || git checkout -- mise.lock
Prevention
- Give every lockfile key a concrete value or remove the key
- Never leave empty values (`key:`) when editing YAML/TOML by hand
- Regenerate the lockfile after conflict resolution
When it happens
Trigger: mise.lock aube YAML has an explicit `null`/`~` or an empty key value (`key:` with nothing) somewhere in the graph.
Common situations: Hand-edited lockfile leaving a key with no value; a generator emitting YAML nulls; merge conflict resolution leaving placeholders.
Understand the failure class
Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.
Related errors
- aube lockfile mapping keys must be strings
- non-finite numbers cannot be represented in mise.lock
- unsupported number in aube lockfile
- additional_artifacts must be an array in lockfile
- aube lockfile must contain a mapping
AI-assisted analysis of jdx/mise@533346cc37 (2026-09-17).
Data as JSON: /api/errors/5f88a391d615354c.
Report an issue: GitHub.
Appendix: source
Thrown at src/lockfile.rs:197
}
Value::String(value) => toml::Value::String(value),
Value::Sequence(values) => toml::Value::Array(
values
.into_iter()
.map(yaml_to_toml)
.collect::<Result<_>>()?,
),
Value::Mapping(values) => {
let mut table = toml::Table::new();
for (key, value) in values {
let Value::String(key) = key else {
bail!("aube lockfile mapping keys must be strings")
};
table.insert(key, yaml_to_toml(value)?);
}
toml::Value::Table(table)
}
Value::Null => bail!("null values cannot be represented in mise.lock"),
Value::Tagged(value) => yaml_to_toml(value.value)?,
})
}
fn toml_to_yaml(value: toml::Value) -> serde_yaml::Value {
use serde_yaml::{Mapping, Number, Value};
match value {
toml::Value::String(value) => Value::String(value),
toml::Value::Integer(value) => Value::Number(Number::from(value)),
toml::Value::Float(value) => Value::Number(Number::from(value)),
toml::Value::Boolean(value) => Value::Bool(value),
toml::Value::Datetime(value) => Value::String(value.to_string()),
toml::Value::Array(values) => {
Value::Sequence(values.into_iter().map(toml_to_yaml).collect())
}
toml::Value::Table(values) => {
let mut mapping = Mapping::new();
for (key, value) in values {View on GitHub (pinned to 533346cc37)