Weft Review

One commit, one change, one honest verdict.

Monorepo review the way the biggest shops actually run it: the unit of review is a commit with a stable Change-Id, approval sufficiency is computed from OWNERS files in your tree, and landing goes through a queue that promotes trunk fast-forward — through the same compare-and-swap every push uses.

Changes and patchsets, not branch soup

A change is one commit's review identity, keyed by its Change-Id trailer, so it survives rebase and amend. Each revision becomes a numbered patchset; registering the same commit twice acks instead of duplicating. Push a branch, register its tip, review commit by commit.

OWNERS files govern, and explain

Hierarchical OWNERS files — people, teams, *, set noparent — resolved against your org's live membership on every evaluation. Every verdict arrives in words:

blocked: needs an owner of /payments/gateway.rs (owners: alice@acme.dev, @payments)

Approvals that mean something

Approvals attach to a patchset, never to the change: push a revision and the count starts over, because yesterday's approval says nothing about code it never saw. Approvals come from people — a service token asking to approve is refused, in those words.

A queue, not a merge button

Landing re-verifies sufficiency at claim time, proves the fast-forward with a bounded ancestry walk, and promotes trunk by compare-and-swap. Landing a stack's top lands the whole stack. Ejections say exactly why —ejected: not fast-forward from 3f2a91c04d1b — and webhooks announce change.landed and change.ejected beside push.

A trunk nobody can push around

Protect a branch and it moves only through the queue. Every other door —git push over HTTP and SSH, the commits API, reset, revert, delete — answers with one sentence: branch 'main' is protected: land through review. Set the default branch per repo; protect it, and the verdict stops being advice.

Review at line resolution

The change view is one screen: the line diff, the conversation and the verdict side by side. Comments anchor to the exact line of the patchset and stay pinned when a revision answers them — "this was about patchset 1" is visible forever, and CI can say the perf suite regressed as honestly as a person.

How a landing works

1 — enqueue

The land request prechecks the verdict and refuses with its words if it blocks. Otherwise the change enters the queue as landing.

2 — re-verify

The lander re-runs sufficiency at claim time. An approval revoked in between counts: ejected: sufficiency lost.

3 — prove

A bounded ancestor walk proves the patchset descends from trunk's tip. Moved trunk? ejected: not fast-forward.

4 — promote

One compare-and-swap moves the ref. A racing push simply wins or loses the same CAS — never a forced ref, never a corrupt clone.

What ships today, and what is in design

Shipping now: changes, patchsets, per-patchset approvals, the OWNERS sufficiency engine with per-path explanations, the fast-forward land queue with stack landing, branch protection with a per-repo default branch, line-anchored review comments, and the Changes tab in the dashboard. In design for Repos customers: speculative batching in the queue, target-aware parallel landing, three-way merge for changes that drift, and interdiff review between patchsets. We publish what the queue cannot do as plainly as what it can.

Read the review docsWeft Repos, the storage under it