7ae283ea

hopinion: static analysis that enforces the code review standards

One commit against an empty repository, so the diff is the whole tool.

## Where to start

1. `README.md` — what it is, and the open decisions, split into yours and mine.
2. `plan/bootstrap.md` — why the shape is this shape, and what contact with a
   real repository changed about it.
3. The three checks, which are the point of the layout:
   `hopinion/src/Hopinion/Check/Comment/BareTodo.hs` (10 lines of rule),
   `.../Check/Package/GenValidInGenPackage.hs`, and
   `.../Check/Project/GenValidSpecPerGenValid.hs` (the hard one).
4. `hopinion/src/Hopinion/Rule.hs` for what a rule is, then `Run.hs` for the
   envelope that never learns what any rule means.

The ratio is deliberate and worth checking: about 1,300 lines of infrastructure
carrying 55 lines of rules. If adding the fourth rule is not a module and a
line, the layout is wrong.

## Feedback loops

In order of increasing cost, from `CLAUDE.md`:

```
nix develop --command cabal build all --enable-tests
nix develop --command cabal test hopinion-test --test-options="--ai-executor"
nix flake check
scripts/corpus-run.sh
```

All green. `nix flake check` includes hopinion running on itself, `weeder-check`,
the pre-commit hooks, and `plan/scripts/check-plan.sh`, which asserts the design
documents agree with each other and with the committed corpus data.

## Evidence it works on something that is not itself

Run against nix-ci, on a branch, with the artifacts fed in by the Nix builders:

- **122** `TestGenValidSpecPerGenValid` findings, **0 false positives**. Not a
  sample: all 122 were acted on, and each is now a written `genValidSpec` in the
  package that declares the instance. Three of the types did have a spec in
  another package's test suite, which is the case the rule is for rather than a
  mistake by it.
- **33** `CommentBareTodo` findings, all read, **0 false positives**.
- **0** `HsGenValidInGenPackage` findings there, because nix-ci already satisfies
  the layout rules. That check is pinned instead by its own fixtures and by
  sydtest, where it must report 7. On a compliant repository a correct check is
  silent, so silence is never the only evidence.
- Cost: it roughly doubles the wall clock of a build that was already happening.
  `plan/corpus.md` has the table.

## Deliberately not here

The other 122 rules, the `RuleId` codegen, the types tier, and `fix`. `annotate`
is in, because adoption depends on it.

`plan/` is planning material and is meant to be deleted in one `rm` when it has
served its purpose. `README.md` and `CLAUDE.md` are the entry points and survive
that.

Suite timing

Time to Start Worker time Duration Time to finish Idle
Config 14s 1s 1s 15s 14s
Eval 2m37s 13s 13s 2m51s 2m21s
Build 2m42s 0s - - 0s
Suite 14s 15s - - 2h34m16s