# refactor\(web\): ChatView's machine and server-update banners live in useSystemComposerBanners · PR \#22710 · pingdotgg/t3code

[View on GitCafe](https://git.cafe/pingdotgg/t3code/pull/22710)

Repository: [pingdotgg/t3code](https://git.cafe/pingdotgg/t3code)

Visibility: public

State: merged

Source repository: pingdotgg/t3code

Source branch: refactor/chatview-system-banners

Target branch: refactor/chatview-timeline-follow

Head commit: 7de6e9a6fca9d5acba44242a5a102749d4878e08

[Discussion and reviews](https://git.cafe/pingdotgg/t3code/pull/22710)

[Commits](https://git.cafe/pingdotgg/t3code/pull/22710/commits?format=markdown)

[Files changed](https://git.cafe/pingdotgg/t3code/pull/22710/diffs?format=markdown)

## Description

---

ChatView spread about 260 lines of state for the composer's system banners across two places: reconnect grace, disconnect, version mismatch, and server update. All of it ended up as one `systemComposerBannerItems` array.

`chat/useSystemComposerBanners.tsx` now builds that array and owns the retry and disable commands. `EnvironmentUnavailableState` moved there too. ChatView keeps the active environment and its unavailable state, which other code still reads.

| | previous layer | this layer |
|---|---|---|
| ChatView.tsx lines | 7,927 | 7,665 |

Renders were counted with the `rc-init.js` fiber counter on a dev server seeded from real data (median of 3 runs; base [6a6c84f](https://github.com/pingdotgg/t3code/commit/6a6c84f990) vs the stack top before its rebase onto current main):

| Interaction | main: commits / renders (ChatView) | stack top: commits / renders (ChatView) |
|---|---|---|
| Type 20 chars in the composer | 22 / 678 (1) | 22 / 678 (1) |
| Switch threads | 14 / 779 (5) | 14 / 777 (5) |
| Open + close the terminal drawer | 15 / 494 (3) | 15 / 497 (3) |
| Open + close the right panel | 21 / 723 (4) | 21 / 726 (4) |
| Drag the right panel's resize handle | 13 / 139 (1) | 1 / 1 (0) |

The +3 renders are the new `ChatTerminalDrawers` and `ChatRightPanel` wrappers. The drag row is the [right panel layer](https://github.com/pingdotgg/t3code/pull/22700): the drag's final width commit used to re-render ChatView and the whole chat column, and now re-renders only `ChatRightPanel`.

Tests: `vp test run src/reactCompilerCoverage.test.ts` for ChatView and every new file (0 bailouts), `tsc-rs --noEmit` for apps/web, and oxlint on the changed files.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

