sxyazi/yazi · error · io::Error
trash info has no Path
Error message
trash info has no Path
What it means
`parse_original` (trash_info.rs:55) scans lines after the header until it finds one starting with `Path=`; hitting EOF first means the file has no put-back path at all, so it fails with `ErrorKind::InvalidData`, `trash info has no Path`. The key is required by the freedesktop trash spec.
Source
Thrown at yazi-fs/src/trash/freedesktop/trash_info.rs:55
}
Ok(Self { root: root.to_owned(), backing: root.join("files").join(stem), original })
}
fn parse_original(info: &Path, root: &Path) -> io::Result<PathBuf> {
let mut reader = BufReader::new(File::open(info)?);
let mut line = Vec::new();
reader.read_until(b'\n', &mut line)?;
Self::trim_line(&mut line);
if line != b"[Trash Info]" {
return Err(io::Error::new(io::ErrorKind::InvalidData, "invalid trash info header"));
}
loop {
line.clear();
if reader.read_until(b'\n', &mut line)? == 0 {
return Err(io::Error::new(io::ErrorKind::InvalidData, "trash info has no Path"));
}
Self::trim_line(&mut line);
let Some(value) = line.strip_prefix(b"Path=") else { continue };
let decoded: Cow<[u8]> = percent_decode(value).into();
let path = Path::new(OsStr::from_bytes(decoded.as_ref()));
if path.as_os_str().is_empty() || !path.is_absolute() && path.has_parent_component() {
return Err(io::Error::new(io::ErrorKind::InvalidData, "invalid original trash path"));
}
return Ok(if path.is_absolute() {
path.to_owned()
} else {
Self::mount_point(root)?.join(path)
});
}
}View on GitHub (pinned to 94abcfa92f)
Solutions
- Add a valid `Path=<absolute-original-path>` line to the file and retry the restore.
- If the original location is unknown, remove the `.trashinfo` and manually salvage the backing file from `<root>/files/`.
- Report/fix whichever tool produced header-only trashinfo files.
Example fix
# before [Trash Info] DeletionDate=2026-01-01T00:00:00 # after [Trash Info] Path=/home/alice/report.pdf DeletionDate=2026-01-01T00:00:00
Defensive patterns
Strategy: try-catch
Validate before calling
fn has_path_line(p: &std::path::Path) -> std::io::Result<bool> {
use std::io::BufRead;
let mut r = std::io::BufReader::new(std::fs::File::open(p)?);
let mut line = Vec::new();
r.read_until(b'\n', &mut line)?; // header
loop {
line.clear();
if r.read_until(b'\n', &mut line)? == 0 { return Ok(false); }
while matches!(line.last(), Some(b'\n' | b'\r')) { line.pop(); }
if line.starts_with(b"Path=") { return Ok(true); }
}
} Try / catch
match trash.entry(&id) {
Ok(e) => { /* ... */ }
Err(e) if e.kind() == io::ErrorKind::InvalidData => {
// missing Path= line: add `Path=/abs/original` to the .trashinfo, or purge the item
}
Err(e) => return Err(e),
} Prevention
- Never truncate or hand-strip lines from .trashinfo files; Path= is mandatory.
- After crashes, scan trash info for header-only files and repair them.
- When generating metadata, write Path= first so partial writes still often succeed.
When it happens
Trigger: A `.trashinfo` containing only the `[Trash Info]` header, or with keys like `DeletionDate=` but no `Path=` line; files truncated mid-write.
Common situations: A crash or full disk while the trash implementation was writing metadata; trash info generated by buggy third-party tools.
Related errors
- invalid trash info header
- invalid trash info path
- invalid original trash path
- invalid trash mount point
- Invalid cache stamp
AI-assisted analysis of sxyazi/yazi@94abcfa92f (2026-08-16).
Data as JSON: /api/errors/c7a808516fe1a677.
Report an issue: GitHub.