Frameworks come and go on a 4-year cycle. The patterns underneath them — composition, state shape, render boundaries, accessibility — outlast every rewrite. We build interfaces against the patterns, then choose the framework that costs you the least to live with.
Each row reflects what we'd actually pick for a new build today, scored against five axes that matter once an app reaches production. Updated quarterly. We've been wrong before; we'll be wrong again.
Use means we'd pick it for a new project today. Watch means we'd inherit it gracefully but not start there. Rescue means we extract you from it — we don't write more of it.
Real timing trace from a cold load of a Brillix.ai dashboard, captured in a Toronto edge POP. Every band below is a contract we negotiate with the browser, not a coincidence.
Brillix.ai needed a chat interface that could route between nine LLM providers without the user ever feeling a stall. The first token had to land before the human noticed they were waiting.
We built the interface as three concentric loops: an edge-rendered shell that paints in 280ms, an island-hydrated chat surface that listens before it's interactive, and a streaming token reducer that commits to the DOM at 120fps without ever triggering a layout pass.
The result is an interface where the perceived latency is the network — never the framework, never the bundle, never the renderer. When a provider stalls, we fall through to a warm replica and the user sees a tone shift, not a spinner.
— Eng lead, Brillix.ai
Give us thirty minutes. We'll tell you whether it's the framework, the patterns, or the people — and what each fix actually costs.