# sad

> Batch file search-and-replace tool that shows a diff preview before writing changes; optional fzf selection of hunks and delta/diff-so-fancy colorizing.

Stars: 2.0k · Language: Rust · License: MIT · Categories: Search

- Repository: https://github.com/ms-jpq/sad
- Page: https://www.trmn.sh/tools/sad

## Install

- Homebrew: `brew install sad`
- Pacman: `pacman -Syu sad`
- Cargo: `cargo install --locked --all-features \`
- Cargo: `--git https://github.com/ms-jpq/sad --branch senpai`

## Overview

sad (Space Age seD) is a batch file edit tool. It reads a list of file paths from stdin, applies a regex search and replace across those files, and shows a diff of the proposed changes before anything is written. This addresses the main risk of sed: a mistyped pattern edits files with no chance to review it first.

Usage is `find "$FIND_ARGS" | sad '<pattern>' '<replacement>'`. If fzf is installed, sad uses it for selection, so you can pick which changes to apply, and files can be multi-selected with Shift+Tab. Hunk size is set with `--unified=<n>`, as in GNU diff. Without fzf, sad prints the diff to stdout, which can be piped to any git-compatible colorizer such as delta or diff-so-fancy, or passed via `--pager` or `GIT_PAGER`. With delta, `--pager 'delta -s'` gives a side-by-side view.

Other flags include `-k`/`--commit` to write all changes without a preview, `-0`/`--read0` for NUL-delimited input, `-e`/`--exact` for string-literal matching, and `-f`/`--flags` for regex flags. The flags cover case-insensitive (`i`), multiline (`m`), dot-matches-newline (`s`), swapped lazy/greedy (`u`), and extended whitespace and comments (`x`). By default sad uses smartcase and multiline matching. Exit codes are 0 for success, 1 for failure, and 130 for interruption; with fzf it always exits 130.

It suits developers who do project-wide refactors or renames from the shell and want to review or selectively accept edits. For plain stdin-to-stdout replacement, the README points to sd or ripgrep with `--replace`.

### Installation

```bash
# via Homebrew
brew install sad
```

```bash
# via Pacman
pacman -Syu sad
```

```bash
# via Cargo
cargo install --locked --all-features \
  --git https://github.com/ms-jpq/sad --branch senpai
```

![sad with fzf selecting changes](https://media.trmn.sh/cached/c13915870daa401f6f1dc1de3e2dd537b33fa452eaee2120dae3c4cad2598443.gif)

![sad without fzf in the chromium repo](https://media.trmn.sh/cached/52cfff116869d74fb995d2efd9e1f7042994039ab815f6feb55051b2854a3bd2.gif)

## Alternatives

- [television](https://www.trmn.sh/tools/television.md): Fuzzy finder for the terminal that searches files, text, git repositories, and custom data sources in real-time (Rust, 6.4k stars)
- [skim](https://www.trmn.sh/tools/skim.md): Fuzzy finder written in Rust with interactive search capabilities and shell integration (Rust, 7.0k stars)
- [rga](https://www.trmn.sh/tools/rga.md): Line-oriented search tool that extends ripgrep to search inside PDFs, archives, documents, and multimedia files (Rust, 9.9k stars)
- [ast-grep](https://www.trmn.sh/tools/ast-grep.md): CLI for structural code search, lint, and rewriting that matches tree-sitter AST nodes using patterns written as ordinary code. Written in Rust. (Rust, 16.4k stars)
- [fd](https://www.trmn.sh/tools/fd.md): Fast filesystem search tool that replaces find with regex patterns and smart defaults (Rust, 44.9k stars)

---

Canonical: https://www.trmn.sh/tools/sad
