repgrep turns ripgrep into an interactive find and replace
An interactive replacer for ripgrep that makes it easy to find and replace across files on the command line.
At a glance
- What is it?
- repgrep is an Apache-2.0 or MIT or Unlicense Rust tool that keeps ripgrep as its search engine and adds a terminal interface for choosing which matches to replace, with a live preview. It is a review step, not a batch step, and the same binary can be told to skip the interface entirely.
- Who is it for?
- repgrep is a good fit for a developer who knows exactly which files need changing but does not want to write a sed script with a regular expression they have to get right blind, since the preview turns the replacement into something you look at before you commit it.
- Can I use it commercially?
- Yes. Apache-2.0 is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository last received commits 51 days ago.
- What is it written in?
- Mainly Rust, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.
Editorial analysis
It is ripgrep with a decision layer on top
repgrep describes itself as an interactive replacer for ripgrep, and the README makes the division of labour explicit: it uses ripgrep to find, and then provides a simple interface to see the replacements in real time and conditionally replace matches. The binary is named rgr, which the README explains as thinking of rg plus replace, and it takes ripgrep's own arguments, so rgr and rg are close enough in shape that muscle memory carries over. The design decision worth noticing is that the search engine is not reimplemented. ripgrep's matcher crates are in the dependency list, along with grep-regex, grep-pcre2 and grep-matcher, so pattern handling is handled by the same code that makes rg fast, and rgr adds the terminal interface, the preview and the write step.
The interactive flow and the live preview
The example in the README runs rgr with a context flag to see the neighbourhood of each match:
rgr -C5 dreamcastand then the replacement text is entered, with the screenshot in the doc directory showing the result. The features list names the pieces: an interactive interface for selecting which matches should be replaced or not, and a live preview of the replacements. Capturing groups work, with the example given being replacing /foo (\w+)/ with bar $1, so the replacement is not a flat string but a template over the match. This is where the tool earns its keep. A command line replacement tool gives you one shot at a regular expression, and the failure mode is a broad replacement you did not intend. Here you see each candidate in context and decide, and the preview means the decision is made on the output rather than on the intention.
The same binary can be told not to ask
Interactive does not have to mean blocking, and the README describes two ways to prefill the replacement. Passing ripgrep's -r or --replace option fills the replacement text in while keeping the interactive match selection and confirmation steps:
rgr 'old_name' -r 'new_name'The second combines rgr's own -y or --autoreplace option with -r or --replace, and replaces every match without opening the interactive interface at all:
rgr -y 'old_name' -r 'new_name'The argument contract is simply ripgrep's, with the note that rgr --help has the details:
rgr <rg arguments> # See `rgr --help` for more detailsSo the same installation serves a careful one-file edit and a scripted sweep, and the difference is a flag rather than a different tool. That matters in practice, because the tool that trained you on the careful mode is the tool you will reach for when the sweep is boring.
Encoding handling is a real feature, not a footnote
The README lists the supported file encodings as ASCII, UTF8, UTF16BE and UTF16LE, and notes that other encodings are possibly supported but untested at the moment, with a link to an issue asking for more information. That claim is backed by the dependency list: chardet for character detection and the encoding crate for the transcoding itself, along with base64-simd configured with the detect feature. The practical effect is that a repository containing a mix of UTF-8 source and a UTF-16 resource does not get mangled on the way through a replace. It also means the tool makes a guess when the encoding is not one of the four, and the README is honest that this area is not fully covered, so a directory with legacy encodings deserves a spot check before a bulk replace.
The dependency list shows the interface is a real terminal app
Cargo.toml for the crate pins the version at 0.17.1, the edition to 2024 and the minimum Rust version to 1.96, and the binary entry is named rgr with its path at src/main.rs. The interface stack is visible in the dependencies: crossterm with the use-dev-tty feature for terminal control, ratatui for the terminal user interface, unicode-width for correct handling of wide characters in a grid layout, and lexopt for argument parsing. The search side comes from the grep matcher family. The logging stack is flexi_logger and log, and anyhow handles error propagation, and serde and serde_json for structured output, with tempfile among the main dependencies. The release profile is tuned for a small, fast binary, with codegen-units set to 1, lto enabled, opt-level 3, panic set to abort and symbols stripped.
Installing it, and the ripgrep prerequisite
The first instruction in the installation section is that ripgrep, the rg binary, must already be installed, with a link to the ripgrep installation instructions. After that there are four routes. Pre-compiled binaries are on the releases page. Cargo is the route most Rust developers will use, and the README notes the minimum Rust version required is 1.96.0:
cargo install repgrepArch Linux has it in the official repositories:
pacman -S repgrepand macOS can use MacPorts:
sudo port install repgrepBuilding from source is the fourth:
git clone https://github.com/acheronfail/repgrep/
cd repgrep
cargo install --path .The Cargo.toml also carries a rust-toolchain.toml, so a checkout pins its own toolchain, and a Cross.toml plus a ci/ directory point at cross-compilation being part of the release process.
How the project is developed and measured
The justfile is the clearest statement of the working method. A setup recipe installs cargo-bump and cargo-readme, then conditionally installs ripgrep through pacman or apt-get, and finally checks that rg is on the path, exiting with please install rg! if it is not. Formatting runs rustfmt through the nightly toolchain, and the test recipe runs the whole suite with logging at trace level and all features enabled. There are separate recipes for running the tool locally with logging and for tailing that log, and one that generates the benchmark input by capturing ripgrep's own JSON output over the repository before running cargo bench. The dev dependencies back that up: criterion for the benchmark harness, insta for snapshot testing, memmap and rayon for the parallel work, pretty_assertions for readable diffs, and hex and paste for test fixtures. The benchmark target in Cargo.toml is parsing_json, which measures how the tool parses ripgrep's JSON stream, and the release profile is configured to make that parsing cheap.
Where repgrep is the wrong tool
Three cases. The first is a large mechanical rename across a whole repository, where a scripted tool that is not reading files into a pager and rendering a grid will finish in seconds what repgrep makes you page through, and where the autoreplace mode exists but the review step is exactly what you do not want at that scale. The second is a non-interactive pipeline, since repgrep is built for a human at a terminal and its value is the interface, so scripting it means using the -y path and giving up the reason to use it. The third is a repository with mixed legacy encodings, since UTF-16 is covered and other encodings are described as possibly supported but untested. Against the alternative of using sed -i or a small Python script, the difference in approach is that repgrep reuses a fast search engine, keeps the surrounding context visible, supports capture group templates, and refuses to write anything until you have seen the result. The cost is a terminal interface in your way and a dependency on ripgrep being present.
Editorial conclusion
repgrep is a good fit for a developer who knows exactly which files need changing but does not want to write a sed script with a regular expression they have to get right blind, since the preview turns the replacement into something you look at before you commit it. It is a poor fit for a large mechanical refactor across thousands of files, for a non-interactive pipeline, and for anyone who does not already have ripgrep installed, because rg is a hard prerequisite rather than a bundled library. Check three things before you adopt it: that rg is on the machine, since the setup recipe in the justfile exits with please install rg when it is missing, that your Rust toolchain is 1.96.0 or newer if you build from source, since both the Cargo install and the from source instructions state that floor, and that the licence choice is acceptable, because the package is published as Unlicense OR MIT OR Apache-2.0, which is about as permissive as a Rust crate can be.
Frequently asked questions
What is repgrep and what does it do?
It is an interactive command line tool for find and replacement, written in Rust, that uses ripgrep to find matches and then provides an interface to see the replacements in real time and conditionally replace them. The binary is named rgr, and it takes ripgrep's own arguments.
How do I install repgrep?
First install ripgrep, which is a prerequisite. Then use pre-compiled binaries from the releases page, cargo install repgrep, pacman -S repgrep on Arch Linux, sudo port install repgrep on macOS with MacPorts, or clone the repository and run cargo install --path . to build from source. The minimum Rust version is 1.96.0.
Can repgrep replace every match without asking me?
Yes. Combining rgr's -y or --autoreplace option with ripgrep's -r or --replace replaces every match without opening the interactive interface, for example rgr -y 'old_name' -r 'new_name'. Using -r on its own prefills the replacement while keeping the interactive selection and confirmation steps.
Does repgrep support capture groups in the replacement?
Yes. The README describes replacing using capturing groups, for example replacing /foo (\w+)/ with bar $1, so the replacement text is a template over the match rather than a fixed string.
Which file encodings does repgrep support?
The README lists ASCII, UTF8, UTF16BE and UTF16LE as supported, and says other encodings are possibly supported but untested at the moment, with a link to an issue for more information.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/acheronfail-repgrep)Was this useful?