FuelLabs/sway · error
failed to serialize lock file: {}
Error message
failed to serialize lock file: {} What it means
While persisting a freshly generated lock, toml::ser::to_string_pretty(&new_lock) failed; {} is the serde error. The in-memory lock could not be represented as TOML, which the Lock model normally guarantees - so this almost always indicates a bug in forc-pkg or pathological package metadata (e.g. a dependency key that is not TOML-representable) rather than ordinary misconfiguration.
Source
Thrown at forc-pkg/src/pkg.rs:751
if locked {
bail!(
"The lock file {} needs to be updated (Cause: {}) \
but --locked was passed to prevent this.",
lock_path.to_string_lossy(),
cause,
);
}
println_action_green(
"Creating",
&format!("a new `Forc.lock` file. (Cause: {cause})"),
);
let member_names = manifests
.values()
.map(|manifest| manifest.project.name.to_string())
.collect();
crate::lock::print_diff(&member_names, &lock_diff);
let string = toml::ser::to_string_pretty(&new_lock)
.map_err(|e| anyhow!("failed to serialize lock file: {}", e))?;
fs::write(lock_path, string)
.map_err(|e| anyhow!("failed to write lock file: {}", e))?;
debug!(" Created new lock file at {}", lock_path.display());
}
Ok(plan)
}
/// Produce an iterator yielding all contract dependencies of given node in the order of
/// compilation.
pub fn contract_dependencies(&self, node: NodeIx) -> impl Iterator<Item = NodeIx> + '_ {
let graph = self.graph();
let connected: HashSet<_> = Dfs::new(graph, node).iter(graph).collect();
self.compilation_order()
.iter()
.cloned()
.filter(move |&n| n != node)
.filter(|&n| {View on GitHub (pinned to 47e5e902fa)
Solutions
- Inspect the printed serde error to see which value failed to serialize.
- Run 'forc update' to regenerate the lock from scratch.
- Simplify unusual package/dependency names and retry.
- If it reproduces with a clean state, report it to FuelLabs/sway with the manifest and full error text.
Defensive patterns
Strategy: try-catch
Try / catch
match forc_pkg::pkg::BuildPlan::from_lock_and_manifests(&lock_path, manifests, locked, offline, &ipfs_node) {
Ok(plan) => { /* ... */ }
Err(e) if e.to_string().starts_with("failed to serialize lock file") => {
// not user-fixable config: capture state and report to FuelLabs/sway
}
Err(e) => return Err(e),
} Prevention
- Keep package and dependency names to plain alphanumeric characters, '-' and '_'.
- Regenerate locks with 'forc update' rather than carrying them across forc upgrades.
When it happens
Trigger: A package or dependency name containing values the TOML serializer rejects; an internal invariant violation producing a non-serializable Lock; essentially only reachable through exotic inputs or a forc-pkg regression.
Common situations: Rare in practice; seen with unusual package names or after upgrading to a forc version with a lock-schema bug.
Related errors
- failed to parse manifest: {}.
- lock file did not exist
- Invalid lock: {}
- lock file did not match manifest
- failed to write lock file: {}
AI-assisted analysis of FuelLabs/sway@47e5e902fa (2026-08-16).
Data as JSON: /api/errors/1f6c3df1d33a02dc.
Report an issue: GitHub.