# codebook, a spell checker for code that only flags what you wrote

> Codebook is a Rust spell checker for source code, built on Tree-sitter and Spellbook and shipped as a language server. Its defining rule is that it marks words where they are defined rather than everywhere they are used, which keeps the signal high and the noise low.

**blopker/codebook** — An unholy spell checker for code

- Repository: https://github.com/blopker/codebook
- Stars: 925 · Forks: 59
- Language: Rust
- License: MIT
- Published: 2026-10-20 · Updated: 2026-10-20 · Language: en
- Canonical page: https://hysenlabs.com/projects/blopker-codebook

## It marks the definition, not every use of it

Codebook is described as a spell checker for code, and the README opens with the rule that makes it different from a prose checker. Codebook will try to only mark issues for words that you create, where they are initially defined.

The reasoning is spelled out in the goals section. A misspelled word in an imported function should not be highlighted, because the user cannot do anything about it. So Codebook only marks issues for terms where they are defined, and not where they are used. Correcting both the definition and all the subsequent uses is left to other language specific tooling, usually available as an LSP for that language.

That division is the entire product idea, and it is a sensible one. A spell checker that flags every occurrence of a third-party name produces a wall of yellow and teaches the user to ignore the tool. A checker that flags only the identifier you just typed tells you something you can act on immediately.

The scope is code-aware rather than language-aware. Codebook only checks the parts of your code where a normal linter would not: comments, string literals and variable definitions, for example. It knows how to split camel case and snake case variables, and it makes suggestions in the original case, so a misspelled camelCase identifier gets a camelCase suggestion rather than a lower case word.

The README is direct about what this is not. If you are looking for a traditional spell checker for prose, Codebook may not be what you are looking for. Capitalization issues are handled loosely and grammar checking is out of scope.

## Tree-sitter and Spellbook, both driven from Rust

Codebook binds together Tree Sitter, the parser generator, and Spellbook, the fast spell checker from the Helix editor. Everything is done in Rust, and the stated reason is to keep response times snappy and memory usage low.

The Cargo manifest shows how that is assembled. The workspace has four crates, codebook, codebook-config, codebook-lsp and downloader, at edition 2024. Parsing is Tree-sitter, pinned below version 0.27, with a separate grammar crate per language, so tree-sitter-bash, tree-sitter-c, tree-sitter-c-sharp, tree-sitter-cpp, tree-sitter-css, tree-sitter-dart, tree-sitter-elixir, tree-sitter-erlang, tree-sitter-go, tree-sitter-haskell, tree-sitter-html, tree-sitter-java, tree-sitter-javascript and the rest of the list. The dictionary side is spellbook, pinned below 0.5.0, and the language server protocol is tower-lsp at 0.20.0, with tokio for the async runtime.

One dependency rule in the manifest is worth noting for anyone forking the project. A comment in the workspace dependencies section states that all dependencies must be available on crates.io, with no git imports, because Codebook cannot be released as a crate otherwise. That single constraint shapes the dependency list, which is why every grammar is a published version rather than a git reference.

The network stack is reqwest with the rustls feature and default features off, plus rustls-platform-verifier and webpki-roots. The dictionaries are cached locally once downloaded, which is what makes the offline goal achievable, and the downloader crate is a separate workspace member so that the fetching logic is separated from the checking logic.

## Three goals that settle every feature argument

The README states that spell checking is complicated, and that opinions about how it should be done, especially for code, differ. The goals section then lays out the trade-offs that steer the decisions, and reading it is the fastest way to predict how the maintainer will answer a question.

Privacy is the first. No remote calls for spell checking or analytics. Once dictionaries are cached, Codebook needs to be usable offline, and Codebook will never send the contents of files to a remote server. The tool is a local process that happens to speak a protocol that editors understand, and the protocol is the only reason it looks like a service.

Do not be annoying is the second, and it is the one with the most teeth. High signal and low noise, and it should only highlight words that users have control over. The definition-only rule is the consequence of that goal, not an independent decision.

Efficient is the third. All features will be weighed against their impact on CPU and memory, and Codebook should be fast enough to spell check on every keystroke even on low-end hardware. The Makefile carries a benchmark target that runs the codebook binary with a --benchmark flag, so the goal is at least measurable.

The three goals are in tension with each other, which is why they are written down. A larger dictionary improves signal and costs memory. Checking more node types improves coverage and increases noise. A checker that understands the whole file would catch more, and would also be slower and would flag names you did not write.

## Five ways to get the language server onto your PATH

Unless you use Zed, you need the codebook-lsp binary available on your $PATH. The README lists several routes, and the choice is mostly about how you like to manage binaries.

Prebuilt archives are published for macOS on x86_64 and aarch64, Linux on x86_64 and aarch64, and Windows on x86_64 and arm64. Windows artefacts are zip files and the macOS and Linux ones are tar.gz archives. You extract the binary and move it somewhere on your PATH, with ~/.local/bin/codebook-lsp and /usr/bin/codebook-lsp given as examples.

Package managers come next. eget installs the latest release:

```sh
eget blopker/codebook
```

Arch Linux has it in pacman:

```sh
pacman -S codebook-lsp
```

Cargo works for the crates.io version:

```sh
cargo install codebook-lsp
```

Homebrew has a formula:

```sh
brew install codebook-lsp
```

And for the repository itself rather than the published crate, Cargo can build straight from git:

```sh
cargo install --git https://github.com/blopker/codebook codebook-lsp
```

For local development, the README says you may build codebook from source by cloning the repository and running make build, and the Makefile confirms that the build target compiles the codebook-lsp crate in release mode. The same Makefile runs the test suite with cargo nextest when it is available and falls back to cargo test, and the integration tests are driven by bun test in the integration_tests directory, whose package.json is a small module with the bun test script and the bun type definitions.

## The Zed extension downloads the server onto remote hosts

Codebook started life as a Zed extension, and the README says it is the most popular spell checker for Zed. Installing it is a matter of opening the Extension tab in Zed and looking for Codebook.

There is a versioning subtlety. The version Zed shows in the extension menus is the version of the Zed extension, which lives in its own repository, and not the version of the LSP in this repository. The extension updates the LSP automatically, and if that updater breaks, uninstalling and reinstalling the extension is the documented fix.

Remote development is where this gets interesting. When Zed opens a remote project over SSH or WSL2, the extension runs on the remote host and downloads the language server there. The README warns that restricted or flaky network access on the remote, a common WSL2 issue, can break that download. The workaround is clean: the extension always prefers a codebook-lsp binary found on the PATH, so installing it on the remote host sidesteps the downloader entirely.

One more setting is needed for quickfix code actions in specific languages. The language_servers list in settings.json has to include the special "..." value or the "codebook" value:

```json
"languages": {
  "Python": {
    "language_servers": ["pyright", "ruff", "..."],
    // OR
    "language_servers": ["pyright", "ruff", "codebook"],
    "format_on_save": "on"
  }
},
```

For Helix, the language server is enabled by adding codebook-lsp to the languages.toml configuration file, with the binary on the PATH as the prerequisite.

## Language support is tiered, and the tiers are visible

The supported language list is split into two tiers, which is unusual and useful.

The good to go group is C, Go, Java, JavaScript, Lua, Markdown, Odin, Plain Text, Python, Ruby, Rust, TOML, TypeScript and Zig.

The second group is marked as supported but needing more testing, with an invitation to help: Astro, Bash, C#, C++, CSS, Dart, Elixir, Erlang, Haskell, HTML, Just, LaTeX, OCaml, PHP, Svelte, Swift, Typst, VHDL, Vue and YAML. If Codebook is not marking issues you think it should, the README asks you to file a GitHub issue.

That split tells you something about the tree-sitter grammars in the dependency list. Having a grammar available and having it behave correctly against Codebook's definition-versus-use rules are two different things, and a grammar that parses a language in an unusual dialect can mark the wrong nodes. A YAML file with a long list of short keys, for example, gives the definition rule much less to work with.

The repository layout supports that development model. There is a word_lists/ directory for the dictionaries, a codebook.toml configuration file, an examples/ directory with a sample file per language, an integration_tests/ directory run with bun, and a journal/ directory alongside the CHANGELOG.md and the SECURITY.md.

## Conclusion

codebook suits a developer who wants typos in comments, string literals and variable names caught as they type, without a background service sending their source anywhere. It does not suit someone looking for prose spell checking or grammar checking, and it does not replace the language-specific tooling that should rename every use of a renamed identifier. Before you adopt it, install the codebook-lsp binary on each machine you edit on, including remote and container hosts, and try it on a language from the list that is still marked as needing more testing.

## FAQ

### What is Codebook and how is it different from a prose spell checker?

Codebook is a spell checker for source code, combining Tree-sitter for parsing with Spellbook for dictionary lookups, and it marks issues only where terms are defined rather than everywhere they are used. It is not a prose checker: capitalization is handled loosely and grammar checking is out of scope.

### How do I install the Codebook language server?

You can download a prebuilt archive from the releases page for macOS, Linux or Windows and put the binary on your PATH, or use eget blopker/codebook, pacman -S codebook-lsp, cargo install codebook-lsp, or brew install codebook-lsp. Building from source means cloning the repository and running make build.

### Does Codebook send my source code to a server?

No. The README states there are no remote calls for spell checking or analytics, that Codebook never sends the contents of files to a remote server, and that once dictionaries are cached it is usable offline.

### How do I enable Codebook in Helix and in Zed?

In Helix you add codebook-lsp to the languages.toml configuration file, with the binary installed on your PATH. In Zed you install the Codebook extension from the Extension tab, and for quickfix code actions in specific languages you add the special "..." or "codebook" value to the language_servers list in settings.json.

### Why does Codebook not flag a misspelled word every time it appears?

Because it only marks issues for terms where they are defined and not where they are used, so that the signal stays high and users are not shown problems they cannot fix. Renaming every use of a renamed identifier is left to language specific tooling.

## Sources

- [blopker/codebook on GitHub](https://github.com/blopker/codebook)
- [Issues](https://github.com/blopker/codebook/issues)
- [License: MIT](https://github.com/blopker/codebook/blob/main/LICENSE)
- [README](https://github.com/blopker/codebook/blob/main/README.md)
- [Releases](https://github.com/blopker/codebook/releases)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/blopker-codebook
