wavetermdev/waveterm · error
error writing to file %s: %w
Error message
error writing to file %s: %w
What it means
When the --output-file flag is set, wsh writes the scrollback text with os.WriteFile using 0644 permissions. Any filesystem failure (bad path, missing directory, permission denied, disk full) is wrapped with this message naming the file.
Source
Thrown at cmd/wsh/cmd/wshcmd-termscrollback.go:96
result, err := wshclient.TermGetScrollbackLinesCommand(RpcClient, scrollbackData, &wshrpc.RpcOpts{
Route: wshutil.MakeFeBlockRouteId(fullORef.OID),
Timeout: 5000,
})
if err != nil {
return fmt.Errorf("error getting terminal scrollback: %w", err)
}
// Format the output
output := strings.Join(result.Lines, "\n")
if len(result.Lines) > 0 {
output += "\n" // Add final newline
}
// Write to file or stdout
if termScrollbackOutputFile != "" {
err = os.WriteFile(termScrollbackOutputFile, []byte(output), 0644)
if err != nil {
return fmt.Errorf("error writing to file %s: %w", termScrollbackOutputFile, err)
}
fmt.Printf("terminal scrollback written to %s (%d lines)\n", termScrollbackOutputFile, len(result.Lines))
} else {
fmt.Print(output)
}
return nil
}
View on GitHub (pinned to a4447c1563)
Solutions
- Check the path exists and is writable: verify the parent directory exists (`mkdir -p`) and fix the filename.
- Avoid `~` — pass an absolute path since os.WriteFile does not expand tilde.
- Check filesystem permissions and free space (`ls -ld`, `df -h`).
Example fix
// before
err = os.WriteFile(termScrollbackOutputFile, []byte(output), 0644)
// after
expandedPath, err := wavebase.ExpandHomeDir(termScrollbackOutputFile)
if err != nil {
return fmt.Errorf("invalid output path %s: %w", termScrollbackOutputFile, err)
}
if err := os.MkdirAll(filepath.Dir(expandedPath), 0755); err != nil {
return fmt.Errorf("creating output dir: %w", err)
}
err = os.WriteFile(expandedPath, []byte(output), 0644) Defensive patterns
Strategy: validation
Validate before calling
// validate the output path before writing
if termScrollbackOutputFile != "" {
path, _ := filepath.Abs(os.ExpandEnv(termScrollbackOutputFile))
if st, err := os.Stat(filepath.Dir(path)); err != nil || !st.IsDir() {
fmt.Fprintf(os.Stderr, "output directory does not exist: %s\n", filepath.Dir(path))
os.Exit(1)
}
} Try / catch
err = os.WriteFile(termScrollbackOutputFile, []byte(output), 0644)
if err != nil {
if errors.Is(err, fs.ErrPermission) {
// permission denied: fix ownership/mode or pick another path
} else if errors.Is(err, fs.ErrNotExist) {
// create parent dirs first
}
return fmt.Errorf("error writing to file %s: %w", termScrollbackOutputFile, err)
} Prevention
- Use absolute paths; expand `~` and env vars yourself before passing them.
- Pre-create the output directory (`mkdir -p`).
- Check disk space and permissions when writing to shared/system locations.
When it happens
Trigger: os.WriteFile failing for termScrollbackOutputFile: parent directory doesn't exist, no write permission, read-only filesystem, or path is a directory.
Common situations: Typo in the output path; writing into a directory created by root; output on a full or read-only disk; using `~` unexpanded because the CLI doesn't expand it.
Understand the failure class
Background: "Permission denied" / "Failed to write" file errors: why a library can't write its files to disk (EACCES, EPERM, ENOSPC) and how to fix them — this error's family across 43 libraries.
Related errors
- reading from stdin: %w
- reading file %s: %w
- failed to read JWT token from stdin: %w
- reading stdin: %w
- getting absolute path: %w
AI-assisted analysis of wavetermdev/waveterm@a4447c1563 (2026-09-01).
Data as JSON: /api/errors/14cc7694eb108bdb.
Report an issue: GitHub.