FuelLabs/sway · error · anyhow::Error
missing path for new command
Error message
missing path for new command
What it means
forc new falls back to the final path component as the project name when --name is absent; Path::file_name() returns None for paths with no final component — a path ending in '..' or a root like '/' — and this ok_or_else converts that into "missing path for new command" before validate_project_name ever runs.
Source
Thrown at forc/src/cli/commands/new.rs:65
let Command {
contract,
script,
predicate,
library,
workspace,
name,
path,
} = command;
match &name {
Some(name) => validate_project_name(name)?,
None => {
// If there is no name specified for the project, the last component of the `path` (directory name)
// will be used by default so we should also check that.
let project_path = PathBuf::from(&path);
let directory_name = project_path
.file_name()
.ok_or_else(|| anyhow!("missing path for new command"))?
.to_string_lossy();
validate_project_name(&directory_name)?;
}
}
let dir_path = Path::new(&path);
if dir_path.exists() {
forc_result_bail!(
"Directory \"{}\" already exists.\nIf you wish to initialise a forc project inside \
this directory, consider using `forc init --path {}`",
dir_path.canonicalize()?.display(),
dir_path.display(),
);
} else {
std::fs::create_dir_all(dir_path)?;
}
let init_cmd = InitCommand {View on GitHub (pinned to 47e5e902fa)
Solutions
- Pass an explicit project name: `forc new --name myproj --path <dir>`
- Give a path whose last component is a real directory name (no trailing '..' or '/')
- Sanitize script variables so empty strings don't turn the path into '..'
Example fix
# before forc new --path .. # after forc new --name my_project --path ../my_project
Defensive patterns
Strategy: validation
Validate before calling
// Mirror forc's own logic: without --name the last path component becomes the project name.
let name = match (&command.name, std::path::Path::new(&command.path).file_name()) {
(Some(n), _) => n.clone(),
(None, Some(last)) => last.to_string_lossy().into_owned(),
(None, None) => anyhow::bail!("--path must end in a directory name, or pass --name"),
}; Type guard
fn path_has_file_name(p: &str) -> bool {
std::path::Path::new(p).file_name().is_some()
} Prevention
- Always pass --name in scripts that compute destination paths from variables
- Reject paths ending in '..', '/', or drive roots before shelling out to forc new
When it happens
Trigger: `forc new --path ..`, `forc new --path .` is fine ('.' has file_name "."), but `--path ..` or `--path /` yields None. Concretely any path whose last component normalizes to a parent reference or the filesystem root.
Common situations: Shell scripts computing a destination path that collapses to '..' (e.g. joining an empty variable), or invoking forc new at the filesystem root / with a trailing '..' in CI.
Related errors
- Could not get plugin info: {}
- failed to find a template `{}` in {}
- Failed to run forc plugins
- Could not get plugin description.
- failed to read {}: {}
AI-assisted analysis of FuelLabs/sway@47e5e902fa (2026-08-16).
Data as JSON: /api/errors/e8f1198b15916e27.
Report an issue: GitHub.