Repository navigation
Commit 0df10f5
feat(lazurio): Buddy's T3 Code is Buddy's one conversation, framed by the bubble
Root decision 0210, plan DEV-6676 (row 25). With T3CODE_LAZURIO_BUDDY=1 the web
client is Buddy's surface: a header with Mattyčus, the conversation's days in a
pane where the window has room and a date line above each day's first message,
and no thread list, new thread, fork, rollback or thread details card. `/`
opens Buddy's one thread through the thread route, and a message sent during a
turn steers it; queueing is the explicit alternative. In Buddy's bubble the
surface speaks the frame's side of lazurio.buddy.* v1, written from the
protocol's description: it says it is ready, keeps the last valid page context
from its parent on the host's exact origin, and asks for its window's size from
its header and on Escape, which asks for the panel unless a dialog, menu or
list is open in the surface or something inside stopped the key (the editor
marks every Escape as handled). A day in the pane turns off following the end
first, as the timeline's minimap does, so the jump stays. In the bubble the
surface wears the host page's appearance through T3's own appearance
preference; where T3 cannot wear it (storage blocked, or a saved
single-appearance theme), the document wears T3's standard palette in the
host's appearance (request of 2026-10-25).
The server holds the same for every client and agent. Decorators where
it builds the orchestrator and the checkpoint store refuse forks,
rollbacks, other threads and deleting Buddy's thread, and take no
checkpoints in Buddy's project, which is the managed Folder's
(T3CODE_LAZURIO_FOLDER=<Folder>/.agents/buddy) and else
~/Lazurio/.agents/buddy. A thread.create with Buddy's thread id passes
only while Buddy's thread route makes the thread (MakingBuddysThread),
so a client cannot spend the route's fixed command on a thread of its
own. A startup phase before recovery turns off continuing threads after
an update, the agent browser, and Codex and Claude, once, recorded in
<state>/lazurio/buddy-surface.json so that later choices stay. `GET
/api/lazurio/buddy/days` lists the conversation's days for the pane. The
day lines and the day jump check Buddy mode once per timeline, for the
timeline's own Environment, and the rows read it from the timeline's
shared state, so no other Environment's timeline does that work or takes
a jump.
On v0.1.3 two web seams are rebuilt and one server refusal is added.
- Upstream installs the chat route's shortcuts once at app start (pingdotgg#25366
removed ChatRouteGlobalShortcuts), so Buddy's condition joins their `when`
in shortcuts/chatRouteCommands.ts: `isBuddySurfaceNow()` reads the primary
server config from the app's atom registry when a key is pressed. Without it
Shift+Mod+N on Buddy's surface would try a new thread that the server then
refuses.
- The timeline no longer takes onManualNavigation (pingdotgg#25463); the day jump is
called below the timeline's own navigateTimeline and passes it, and the day
line sits beside upstream's AudioPreviewUnmountContext (pingdotgg#21363).
- Upstream's guest share of a thread (pingdotgg#24104) is refused in Buddy's T3 Code:
thread.guest-share.open, .redeem and thread.guest-message.submit fail in the
command guard, because Buddy's conversation belongs to a Personalspace, which
is never shared (root decision 0091); closing a share stays possible. The
root renders no GuestShareDialogHost on Buddy's surface. A test drives a
guest share of Buddy's thread through the server's orchestrator.
Settings and Usage are modals over the thread now (pingdotgg#24847); the prompt-link
draft stays off Buddy's surface inside the rewritten ChatRouteLayout, and the
first-run gate stays off on NEW's slimmer root. The guards are Effect.fn
decorators (effectFnOpportunity), the two effects of BuddySurface.tsx carry
justified react-effect-budget suppressions, and the file headers are cut to
the four-line comment limit.
Any other thread of Buddy's Environment, opened by a link or a typed address,
leads to Buddy's thread as `/` does: the chat layout shows BuddySurfaceIndex,
which asks the server for Buddy's thread and replaces the address, so that
thread never renders under Buddy's presentation. A thread of another
Environment stays T3's, and ChatView and the thread details ask about the
thread's own Environment. A browser test opens such an address directly.
On v0.1.4: the root keeps upstream's local-Environment switch beside the
Buddy surface check (pingdotgg#26207); the timeline finds upstream's unmatched
pending approvals (pingdotgg#26255) after the day lines and adds the day keys to
upstream's list data next to its new footer. ThreadDetailsPanel no
longer exports its props type (pingdotgg#26238), so Buddy's panel takes
ComponentProps of it, and the effect suppressions use the renamed lint
rule t3code/no-unreasoned-state-sync (pingdotgg#26161). The host appearance,
which row 28's commit carried on v0.1.3, comes back to this row: T3 no
longer re-applies its theme from useTheme's effect (pingdotgg#25007, pingdotgg#25461), so
the stand-in follows every application of T3's saved theme through
subscribeRenderedAppearance, and the theme tests apply T3's stored
appearance as app start does. Upstream's linked Environments
(pingdotgg#16655, pingdotgg#16684, pingdotgg#17129) let a peer read and send into this server's threads; a
Personalspace is never shared (0091), so withoutLinkedEnvironments reads
linkedEnvironmentsEnabled as false in Buddy's T3 Code whatever is
stored, which turns off every upstream gate that reads it (peer-link
OAuth, a linked client's /mcp, outbound links, link requests, remote
tasks). Every settings write through it also stores the switch off, the
startup's Buddy defaults included, so a value stored before Buddy is
read as off and the next settings write through it stores it off (the
settings file's own migration write at load keeps what is stored, which
every read still masks); `t3 environment
link`, which builds its own settings (cli/environment.ts), takes the
same guard, so a command run without T3CODE_LAZURIO_BUDDY reads what
Buddy's server stored.
On v0.1.5 the imports in runtimeLayer.ts and ws.ts sit next to
ScratchThreadPromotion (pingdotgg#26767). Upstream's pre-commit hook runs knip
(pingdotgg#26167), so BUDDY_DAYS_ROUTE, withBuddyDefaults and
buddySurfaceProtocol.ts's constants and helpers that only that file uses
are module-private.
On v0.1.6 a side chat (pingdotgg#26901) renders ChatView embedded, without the
header, the branch restore host or the thread details; Buddy's hidden
header and BuddyThreadDetailsPanel sit inside upstream's new embedded
branches. Buddy's one conversation offers no side chat: sideChatsOffered
is false on Buddy's surface, so neither the panel nor the slash menu offer
one, and a typed /side or /btw gets "Buddy's conversation has no side
chats." as the reason instead of reaching Buddy as text (the server would
refuse its thread.fork anyway). The timeline's day lines sit before
upstream's new set of matched approval requests (pingdotgg#27420).
On v0.1.7: upstream now gives the CLI's settings layer the managed policy
(`ManagedPolicy.layer`). The CLI keeps the Buddy guard around
`ServerSettings.layer` and provides `ManagedPolicy.layer` beside the
secret store and persistence. The startup test provides
`ManagedPolicy.layerTest()` and `NodeCrypto.layer`, which Effect 4.1.2 no
longer brings with `NodeServices.layer`. ServerSettingsService on v0.1.7
also carries the managed policy summary (managedPolicy), which clients read
to lock their controls; withoutLinkedEnvironments passes it on, and
buddySurfaceGuards.test.ts fails without it.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>1 parent f4d1d4c commit 0df10f5
38 files changed
Lines changed: 2459 additions & 60 deletions
File tree
- apps
- server/src
- cli
- lazurio
- orchestration-v2
- web
- public/assets
- src
- components
- chat
- lazurio
- brand
- routes
- shortcuts
- packages/contracts/src
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
16 | 16 | | |
17 | 17 | | |
18 | 18 | | |
| 19 | + | |
19 | 20 | | |
20 | 21 | | |
21 | 22 | | |
| |||
44 | 45 | | |
45 | 46 | | |
46 | 47 | | |
47 | | - | |
| 48 | + | |
48 | 49 | | |
49 | 50 | | |
50 | 51 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
11 | 11 | | |
12 | 12 | | |
13 | 13 | | |
| 14 | + | |
14 | 15 | | |
15 | 16 | | |
16 | 17 | | |
| |||
24 | 25 | | |
25 | 26 | | |
26 | 27 | | |
| 28 | + | |
27 | 29 | | |
28 | 30 | | |
29 | 31 | | |
30 | 32 | | |
| 33 | + | |
31 | 34 | | |
32 | | - | |
33 | | - | |
34 | | - | |
35 | | - | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
36 | 39 | | |
37 | 40 | | |
38 | 41 | | |
| |||
48 | 51 | | |
49 | 52 | | |
50 | 53 | | |
51 | | - | |
| 54 | + | |
| 55 | + | |
| 56 | + | |
| 57 | + | |
| 58 | + | |
52 | 59 | | |
53 | 60 | | |
54 | 61 | | |
| |||
75 | 82 | | |
76 | 83 | | |
77 | 84 | | |
78 | | - | |
| 85 | + | |
79 | 86 | | |
80 | 87 | | |
81 | 88 | | |
| |||
87 | 94 | | |
88 | 95 | | |
89 | 96 | | |
90 | | - | |
91 | | - | |
92 | | - | |
93 | | - | |
94 | | - | |
95 | | - | |
96 | | - | |
97 | | - | |
98 | | - | |
99 | | - | |
100 | | - | |
101 | | - | |
102 | | - | |
103 | | - | |
104 | | - | |
105 | | - | |
106 | | - | |
107 | | - | |
108 | | - | |
| 97 | + | |
| 98 | + | |
| 99 | + | |
109 | 100 | | |
110 | 101 | | |
111 | 102 | | |
| |||
128 | 119 | | |
129 | 120 | | |
130 | 121 | | |
| 122 | + | |
131 | 123 | | |
132 | 124 | | |
133 | 125 | | |
134 | 126 | | |
135 | 127 | | |
136 | 128 | | |
| 129 | + | |
| 130 | + | |
| 131 | + | |
| 132 | + | |
| 133 | + | |
| 134 | + | |
| 135 | + | |
| 136 | + | |
| 137 | + | |
| 138 | + | |
| 139 | + | |
| 140 | + | |
| 141 | + | |
| 142 | + | |
| 143 | + | |
| 144 | + | |
| 145 | + | |
| 146 | + | |
| 147 | + | |
| 148 | + | |
| 149 | + | |
| 150 | + | |
| 151 | + | |
| 152 | + | |
| 153 | + | |
| 154 | + | |
| 155 | + | |
| 156 | + | |
| 157 | + | |
| 158 | + | |
| 159 | + | |
| 160 | + | |
| 161 | + | |
| 162 | + | |
| 163 | + | |
| 164 | + | |
| 165 | + | |
| 166 | + | |
| 167 | + | |
| 168 | + | |
| 169 | + | |
| 170 | + | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
140 | 140 | | |
141 | 141 | | |
142 | 142 | | |
143 | | - | |
| 143 | + | |
144 | 144 | | |
145 | 145 | | |
146 | 146 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
7 | 7 | | |
8 | 8 | | |
9 | 9 | | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
10 | 13 | | |
11 | 14 | | |
12 | 15 | | |
| |||
25 | 28 | | |
26 | 29 | | |
27 | 30 | | |
| 31 | + | |
| 32 | + | |
| 33 | + | |
| 34 | + | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
| 39 | + | |
| 40 | + | |
| 41 | + | |
| 42 | + | |
| 43 | + | |
| 44 | + | |
| 45 | + | |
| 46 | + | |
| 47 | + | |
| 48 | + | |
| 49 | + | |
| 50 | + | |
| 51 | + | |
| 52 | + | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
| 1 | + | |
| 2 | + | |
| 3 | + | |
| 4 | + | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| 15 | + | |
| 16 | + | |
| 17 | + | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
| 23 | + | |
| 24 | + | |
| 25 | + | |
| 26 | + | |
| 27 | + | |
| 28 | + | |
| 29 | + | |
| 30 | + | |
| 31 | + | |
| 32 | + | |
| 33 | + | |
| 34 | + | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
| 39 | + | |
| 40 | + | |
| 41 | + | |
| 42 | + | |
| 43 | + | |
| 44 | + | |
| 45 | + | |
| 46 | + | |
| 47 | + | |
| 48 | + | |
| 49 | + | |
| 50 | + | |
| 51 | + | |
| 52 | + | |
| 53 | + | |
| 54 | + | |
| 55 | + | |
| 56 | + | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
| 1 | + | |
| 2 | + | |
| 3 | + | |
| 4 | + | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| 15 | + | |
| 16 | + | |
| 17 | + | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
| 23 | + | |
| 24 | + | |
| 25 | + | |
| 26 | + | |
| 27 | + | |
| 28 | + | |
| 29 | + | |
| 30 | + | |
| 31 | + | |
| 32 | + | |
| 33 | + | |
| 34 | + | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
| 39 | + | |
| 40 | + | |
| 41 | + | |
| 42 | + | |
| 43 | + | |
| 44 | + | |
| 45 | + | |
| 46 | + | |
| 47 | + | |
| 48 | + | |
| 49 | + | |
| 50 | + | |
| 51 | + | |
| 52 | + | |
| 53 | + | |
| 54 | + | |
| 55 | + | |
| 56 | + | |
| 57 | + | |
| 58 | + | |
| 59 | + | |
| 60 | + | |
| 61 | + | |
| 62 | + | |
| 63 | + | |
| 64 | + | |
| 65 | + | |
| 66 | + | |
| 67 | + | |
| 68 | + | |
| 69 | + | |
| 70 | + | |
| 71 | + | |
| 72 | + | |
| 73 | + | |
| 74 | + | |
| 75 | + | |
| 76 | + | |
| 77 | + | |
| 78 | + | |
| 79 | + | |
| 80 | + | |
| 81 | + | |
| 82 | + | |
| 83 | + | |
| 84 | + | |
| 85 | + | |
| 86 | + | |
| 87 | + | |
| 88 | + | |
| 89 | + | |
| 90 | + | |
| 91 | + | |
| 92 | + | |
| 93 | + | |
| 94 | + | |
| 95 | + | |
| 96 | + | |
| 97 | + | |
| 98 | + | |
| 99 | + | |
| 100 | + | |
| 101 | + | |
| 102 | + | |
| 103 | + | |
| 104 | + | |
| 105 | + | |
| 106 | + | |
| 107 | + | |
| 108 | + | |
| 109 | + | |
| 110 | + | |
| 111 | + | |
| 112 | + | |
| 113 | + | |
| 114 | + | |
| 115 | + | |
0 commit comments