Introducing Barad-dûr#
☝️ What the heckin’ heck is Barad-dûr?
Well, officially, if you are familiar with Lord of the Rings, it is the name of the tower in which the Eye of Sauron is seated. Watching carefully over middle-earth.
The technical implementation is not that different. It is a “smart” file watcher that will watch for specfic file changes and execute commands for you.
Motivation For The Project#
At some point, I’m willing to bet this totally non-fictional conversation has occurred in Slack in some organization:
Git Hooks Kind Of Suck#
I really despise git hooks. Not because I don’t think that they are a bad idea. I actually think git hooks are a great idea; I just happen to disagree with the implementation and where they move the problems you inevitably bump into. Git hooks move the problem to deal with generally accepted team-wide rules adopted by CI before you push any code. Preventing time spent from having to circle back and make a minor correct.
Here’s where they fall short of my efficiency expectations. Each is an identifying pain point that Barad-dûr attempts to solve.
Timing#
Git Hooks fire when you git commit. By then you (or — let’s be honest — it’s 2026, Claude) have already written 200 lines and lost the context for what broke.
Baraddur The feedback is instantaneous. Depending on how you configure your personal/developer needs, the valuable feedback can be gathered in near realtime while you’re still making changes.
Flow#
Git Hooks turn git commit into a coin flip. Maybe it works. Maybe you’re now debugging for ten minutes. Maybe your static code analysis tool takes 5 minutes and you need to set your machine inside your fridge to cool off. That’s a context switch from “shipping” mode back to “fixing” mode at exactly the wrong moment. WIP commits, fixup commits, “save my place” commits, sharing a broken branch with a coworker — all legitimate uses of git commit that hooks punish. Git hooks conflate Code correctness and committing.
Baraddur Runs in a side window, another tmux pane, whatever. You glance at the results, fix, move on.
The --no-verify problem#
Git
Teams with pre-commit hooks eventually devolve into a --no-verify culture.
The hook is slow, or flakey, or wrong about something, and people learn the escape hatch.
Are you really, in good conscience, going to tell me that your team does not wind up abusing it?
Baraddur There is nothing to bypass here. It is pure feedback (hopefully lickety-split). You either fix the thing or don’t fix the thing. It’s up to you, dawg!
No team install ceremony#
Git
Wanna dance? Here’s a dance for you.
Hooks need husky / pre-commit / lefthook / a core.hooksPath, plus an inevitable “did you run <some_third_party_tool> install?” Slack/Email/Teams thread every onboarding.
Baraddur Barad-dûr is your tool with config in the repo. No team-wide adoption fight, no enforcement debate, no “Jimothy’s hooks are out of date again.”
Mid-run cancellation#
Git Hooks run to completion even if you’ve already noticed the bug and moved on.
Baraddur Barad-dûr kills the in-flight pipeline the moment you save again. You’re never waiting on stale work.
Parallelism + filtering#
Git Hooks are typically a sequential script.
Baraddur Barad-dûr stages parallel steps (e.g. Rust projects: clippy + test concurrently) and uses if_changed globs with {files} substitution. So you only run the tests touching the files you actually changed. Faster signal, less to read.
Doesn’t fight git#
Git Rebases, amends, cherry-picks, interactive history surgery — hooks fire on all of these and slow them to a crawl, or worse, fail spuriously and leave you mid-rebase.
Baraddur Doesn’t know or care that you’re rewriting history.
Failure ergonomics#
Git Totally absent.
Baraddur The on_failure hook pipes failure output to whatever you want (an LLM, a notifier, a script). Browse-mode r and f keys rerun the whole pipeline or just the failed steps.
To Sum It All Up#
Hooks gate the wrong event (committing) at the wrong time (after you’ve lost context) using the wrong mechanism (blocking a shared workflow everyone learns to bypass). A smart watcher gives you the same signal earlier, out-of-band, with no team politics and nothing to disable.
What it isn’t#
Barad-dûr is not a CI replacement. It’s not a build system. It doesn’t try to be bazel or nx or turbo. It’s a watcher with a typed pipeline and three extra ways to fire it.
If your team is happy with hooks, keep them. If you’re making a habit of typing --no-verify, give it the ol’ whirligig.
cargo install baraddur
baraddur init
baraddurP.S.#
Usage of LLMs is attempted to be used responsibly™ here.
I heavily leaned on architecting, planning, and reviewing using LLMs. I’m not a Rust developer by trade, but wanted to use the language to develop this specifically for the CLI. If there is a better way to engineer the application, I am all ears. Feel free to open a PR or an issue! All feedback is welcomed.
