rtk-ai/rtk · error
at could not be read; leaving it alone.
Error message
{} at {} could not be read; leaving it alone. What it means
During `rtk init` uninstall/cleanup of the Pi extension, rtk checks whether the existing plugin file contains RTK content to decide if it is safe to remove. If the file exists but cannot be read (permissions, IO error, symlink issues), rtk refuses to guess and aborts with this bail instead of deleting or modifying an unreadable file. This is a deliberate safety guard: never remove a file whose ownership is unknown.
Solutions
- Check file permissions with `ls -l <path>` and fix them (e.g. `chmod u+r <path>`) or run rtk with sufficient privileges.
- Manually inspect and remove the file yourself (`rm <path>` or back it up), then rerun `rtk init`.
- Use `rtk init --dry-run` to see which path is affected before retrying.
- If the file is on a flaky mount, remount or copy it to a local disk and retry.
Example fix
// before (shell) rtk init # fails: could not be read # after (shell) chmod u+r ~/.pi/extensions/rtk.ts && rtk init
Defensive patterns
Strategy: fallback
Validate before calling
path=$(ls ~/.pi/extensions/rtk.* 2>/dev/null | head -1) if [ -n "$path" ] && [ ! -r "$path" ]; then echo "Cannot read $path — fix permissions before running rtk init" exit 1 fi
Try / catch
rtk init || { echo 'rtk init failed; run with --dry-run to inspect the affected file' >&2; exit 1; } Prevention
- Run rtk init as the same user that owns the agent config directory.
- Check `ls -l` on agent extension files before uninstalling.
- Prefer `--dry-run` first to spot unreadable paths safely.
When it happens
Trigger: Running `rtk init` (Pi mode uninstall/patch flow) when the Pi extension file at the target path exists but `std::fs::read_to_string` fails — e.g. file has no read permission, is owned by another user, sits on a failing mount, or an IO error occurs mid-read.
Common situations: Plugin file created by root or another user while rtk runs unprivileged; restrictive umask or corporate-managed dotfiles; network/overlay filesystem hiccup in a container or NFS home directory.
Understand the failure class
Background: "failed to read file", EACCES, ENOENT and "could not read <path>" errors: when a program can't read a file from disk — this error's family across 49 libraries.
Related errors
- Failed to uninstall RTK from one or more Droid hook files
- OMP extension at contains RTK content that does not match…
- OMP extension at was not changed; remove or back up the…
- Pi extension at contains RTK content that does not match…
- Pi extension at was not changed; remove or back up the file…
AI-assisted analysis of rtk-ai/rtk@0924356b4c (2026-09-19).
Data as JSON: /api/errors/caa10f240c9456c2.
Report an issue: GitHub.
Appendix: source
Thrown at src/hooks/init.rs:4320
match fs::read_to_string(path) {
Ok(content) => Ok(Some(content)),
Err(error) => {
eprintln!(
"[warn] {} at {} could not be read; leaving it alone: {}",
name,
path.display(),
error
);
if ctx.dry_run {
println!(
"[dry-run] would leave unreadable {} unchanged: {}",
name,
path.display()
);
print_dry_run_footer();
Ok(None)
} else {
anyhow::bail!(
"{} at {} could not be read; leaving it alone.",
name,
path.display()
);
}
}
}
}
/// Uninstall Pi extension for the given scope.
/// Mirrors `uninstall_codex` / `uninstall_hermes`: extracted from the dispatcher
/// so it can be tested and reasoned about independently.
fn uninstall_pi_with_patch_mode(
global: bool,
patch_mode: PatchMode,
ctx: InitContext,
) -> Result<()> {
let InitContext {View on GitHub (pinned to 0924356b4c)