@saadnvd1/agent-os 0.3.792 → 0.3.799
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/app/api/busy/route.ts +2 -2
- package/app/api/tips/route.test.ts +56 -0
- package/app/api/tips/route.ts +45 -0
- package/app/api/updates/health/route.ts +22 -0
- package/app/api/updates/route.test.ts +53 -0
- package/app/api/updates/settings/route.ts +37 -10
- package/components/Chat/ChatPanel.tsx +28 -0
- package/components/Chat/needs-more-history.test.ts +28 -0
- package/components/Chat/needs-more-history.ts +14 -0
- package/components/Recipes/TimerFields.tsx +2 -1
- package/components/Schedules/ScheduleForm.tsx +1 -1
- package/components/Settings/SettingsDialog.tsx +1 -1
- package/components/SidebarFooter.tsx +2 -0
- package/components/Tips/TipButton.tsx +39 -0
- package/components/Tips/TipDialog.tsx +148 -0
- package/components/Tips/TipHost.tsx +14 -0
- package/components/Tips/TipMedia.tsx +71 -0
- package/components/Tips/index.ts +2 -0
- package/components/Updates/AutoUpdates.tsx +141 -0
- package/components/Updates/UpdateBanner.test.ts +39 -1
- package/components/Updates/UpdateBanner.tsx +31 -5
- package/components/Updates/UpdatesSection.tsx +24 -3
- package/content/tips.json +456 -0
- package/content/whats-new.json +32 -0
- package/data/tips/index.ts +49 -0
- package/data/updates/index.ts +5 -0
- package/hooks/useReloadWhenUpdated.ts +5 -1
- package/lib/busy.ts +23 -1
- package/lib/chat/drivers/copilot-approvals.ts +2 -0
- package/lib/chat/drivers/copilot-ask.ts +232 -0
- package/lib/chat/drivers/copilot-mapper.ts +9 -0
- package/lib/chat/drivers/copilot.ts +18 -4
- package/lib/db/migrations.ts +21 -0
- package/lib/recipes/timer.ts +3 -1
- package/lib/schedules/cron.ts +14 -5
- package/lib/schedules/store.ts +3 -2
- package/lib/security/demo.ts +2 -0
- package/lib/tasks/finish.ts +5 -5
- package/lib/tips/conditions.ts +38 -0
- package/lib/tips/index.ts +2 -0
- package/lib/tips/load.ts +26 -0
- package/lib/tips/media.ts +101 -0
- package/lib/tips/pick.ts +35 -0
- package/lib/tips/schema.ts +82 -0
- package/lib/tips/state.ts +26 -0
- package/lib/tips/view.ts +60 -0
- package/lib/updates/auto.ts +149 -0
- package/lib/updates/banner.ts +78 -3
- package/lib/updates/check.ts +64 -8
- package/lib/updates/history.ts +99 -0
- package/lib/updates/run.ts +334 -23
- package/lib/updates/settings.ts +66 -0
- package/lib/updates/view.ts +14 -3
- package/package.json +2 -2
- package/public/tips/.gitkeep +0 -0
- package/public/tips/chat-slash-menu-poster.webp +0 -0
- package/public/tips/chat-slash-menu.mp4 +0 -0
- package/scripts/autodeploy +4 -0
- package/scripts/autodeploy.test.ts +12 -0
- package/scripts/docs-links.test.ts +1 -25
- package/scripts/lib/commands.sh +32 -1
- package/scripts/lib/deps-swap.sh +8 -6
- package/scripts/lib/heading-slugs.ts +26 -0
- package/scripts/lib/update-verify.mjs +90 -0
- package/scripts/redeploy +31 -2
- package/scripts/redeploy.test.ts +94 -3
- package/scripts/tips-lint.test.ts +77 -0
- package/scripts/tips-media.ts +31 -0
- package/scripts/update-e2e.test.ts +215 -0
- package/scripts/update-recover.mjs +130 -0
- package/scripts/update-recover.test.ts +144 -0
- package/scripts/update-run.mjs +182 -40
- package/scripts/update-run.test.ts +208 -2
- package/server.ts +3 -2
- package/stores/tips.ts +14 -0
|
@@ -0,0 +1,456 @@
|
|
|
1
|
+
{
|
|
2
|
+
"v": 1,
|
|
3
|
+
"tips": [
|
|
4
|
+
{
|
|
5
|
+
"id": "chat-enter-sends",
|
|
6
|
+
"title": "Enter sends, Shift+Enter adds a line",
|
|
7
|
+
"body": "Cmd/Ctrl+Enter always sends. On a phone, Enter is a new line.",
|
|
8
|
+
"guide": {
|
|
9
|
+
"file": "chat"
|
|
10
|
+
},
|
|
11
|
+
"added": "2026-10-31"
|
|
12
|
+
},
|
|
13
|
+
{
|
|
14
|
+
"id": "chat-plan-mode",
|
|
15
|
+
"title": "Plan before anything changes",
|
|
16
|
+
"body": "Turn on Plan under the composer, or press Shift+Tab, and the agent reads and plans without editing. It stays on for that session.",
|
|
17
|
+
"guide": {
|
|
18
|
+
"file": "chat"
|
|
19
|
+
},
|
|
20
|
+
"added": "2026-10-31",
|
|
21
|
+
"mediaBrief": {
|
|
22
|
+
"kind": "crop",
|
|
23
|
+
"shot": "Composer bottom bar with Plan switched on, the agent's reply a plan checklist above it."
|
|
24
|
+
}
|
|
25
|
+
},
|
|
26
|
+
{
|
|
27
|
+
"id": "chat-attach-files",
|
|
28
|
+
"title": "Attach PDFs, spreadsheets and documents",
|
|
29
|
+
"body": "The paperclip, a paste or a drag takes up to 8 files a message, 25 MB each. Big photos are shrunk for you.",
|
|
30
|
+
"guide": {
|
|
31
|
+
"file": "chat"
|
|
32
|
+
},
|
|
33
|
+
"added": "2026-10-31",
|
|
34
|
+
"mediaBrief": {
|
|
35
|
+
"kind": "clip",
|
|
36
|
+
"shot": "A PDF dragged onto the composer; its chip appears; one more pasted; send."
|
|
37
|
+
}
|
|
38
|
+
},
|
|
39
|
+
{
|
|
40
|
+
"id": "chat-slash-menu",
|
|
41
|
+
"title": "Type / for commands and skills",
|
|
42
|
+
"body": "/ in the composer lists every command and skill the agent knows, filtered as you type.",
|
|
43
|
+
"guide": {
|
|
44
|
+
"file": "chat"
|
|
45
|
+
},
|
|
46
|
+
"added": "2026-10-31",
|
|
47
|
+
"media": {
|
|
48
|
+
"kind": "video",
|
|
49
|
+
"src": "/tips/chat-slash-menu.mp4",
|
|
50
|
+
"poster": "/tips/chat-slash-menu-poster.webp",
|
|
51
|
+
"alt": "Typing a slash in the composer opens a menu of commands and skills that narrows as you type.",
|
|
52
|
+
"width": 768,
|
|
53
|
+
"height": 480,
|
|
54
|
+
"durationMs": 6367
|
|
55
|
+
}
|
|
56
|
+
},
|
|
57
|
+
{
|
|
58
|
+
"id": "chat-tab-suggestion",
|
|
59
|
+
"title": "Tab takes the suggested reply",
|
|
60
|
+
"body": "After the first turn, a guess at your next message shows in the empty composer. Tab or → takes it; typing sets it aside.",
|
|
61
|
+
"guide": {
|
|
62
|
+
"file": "chat"
|
|
63
|
+
},
|
|
64
|
+
"added": "2026-10-31",
|
|
65
|
+
"mediaBrief": {
|
|
66
|
+
"kind": "clip",
|
|
67
|
+
"shot": "Empty composer shows a grey suggested reply; Tab fills it in."
|
|
68
|
+
}
|
|
69
|
+
},
|
|
70
|
+
{
|
|
71
|
+
"id": "chat-access-picker",
|
|
72
|
+
"title": "Choose what the agent may do",
|
|
73
|
+
"body": "The access picker under the composer has Ask first, Accept edits and Full access. Ask first shows an approval card for anything not already allowed.",
|
|
74
|
+
"guide": {
|
|
75
|
+
"file": "chat"
|
|
76
|
+
},
|
|
77
|
+
"added": "2026-10-31",
|
|
78
|
+
"mediaBrief": {
|
|
79
|
+
"kind": "crop",
|
|
80
|
+
"shot": "The access picker open, showing Ask first, Accept edits, Full access."
|
|
81
|
+
}
|
|
82
|
+
},
|
|
83
|
+
{
|
|
84
|
+
"id": "chat-undo",
|
|
85
|
+
"title": "Undo a message and its edits",
|
|
86
|
+
"body": "Undo on a message puts back the files the agent edited since and returns the message to the composer. Shell command changes aren't tracked.",
|
|
87
|
+
"guide": {
|
|
88
|
+
"file": "chat"
|
|
89
|
+
},
|
|
90
|
+
"added": "2026-10-31",
|
|
91
|
+
"mediaBrief": {
|
|
92
|
+
"kind": "crop",
|
|
93
|
+
"shot": "A user message with its Undo action visible on hover."
|
|
94
|
+
}
|
|
95
|
+
},
|
|
96
|
+
{
|
|
97
|
+
"id": "chat-terminal-handoff",
|
|
98
|
+
"title": "Hand a chat to the terminal",
|
|
99
|
+
"body": "The Chat / Terminal switch in the tab bar resumes the same conversation in the agent's own terminal, and back.",
|
|
100
|
+
"guide": {
|
|
101
|
+
"file": "chat"
|
|
102
|
+
},
|
|
103
|
+
"added": "2026-10-31",
|
|
104
|
+
"mediaBrief": {
|
|
105
|
+
"kind": "clip",
|
|
106
|
+
"shot": "Click Terminal in the Chat / Terminal switch; the same conversation resumes in the terminal."
|
|
107
|
+
}
|
|
108
|
+
},
|
|
109
|
+
{
|
|
110
|
+
"id": "chat-bookmark",
|
|
111
|
+
"title": "Star a message to find it later",
|
|
112
|
+
"body": "Star a message, a step or a whole turn. The star in the chat header lists them and jumps to one.",
|
|
113
|
+
"guide": {
|
|
114
|
+
"file": "chat"
|
|
115
|
+
},
|
|
116
|
+
"when": ["no-bookmarks"],
|
|
117
|
+
"added": "2026-10-31",
|
|
118
|
+
"mediaBrief": {
|
|
119
|
+
"kind": "crop",
|
|
120
|
+
"shot": "Chat header's star list open with three bookmarks."
|
|
121
|
+
}
|
|
122
|
+
},
|
|
123
|
+
{
|
|
124
|
+
"id": "chat-search",
|
|
125
|
+
"title": "⌘K searches every conversation",
|
|
126
|
+
"body": "Type in ⌘K for matching chats, or Tab for a full search of what you and the agents said.",
|
|
127
|
+
"guide": {
|
|
128
|
+
"file": "chat"
|
|
129
|
+
},
|
|
130
|
+
"added": "2026-10-31",
|
|
131
|
+
"mediaBrief": {
|
|
132
|
+
"kind": "clip",
|
|
133
|
+
"shot": "⌘K, type two words, matching chats appear, Tab switches to the full search."
|
|
134
|
+
}
|
|
135
|
+
},
|
|
136
|
+
{
|
|
137
|
+
"id": "sidebar-draft",
|
|
138
|
+
"title": "⌥N opens a draft",
|
|
139
|
+
"body": "A draft in the project you're in. Nothing starts until you send, and unsent drafts wait under Drafts.",
|
|
140
|
+
"guide": {
|
|
141
|
+
"file": "sessions",
|
|
142
|
+
"anchor": "new-sessions"
|
|
143
|
+
},
|
|
144
|
+
"added": "2026-10-31",
|
|
145
|
+
"mediaBrief": {
|
|
146
|
+
"kind": "clip",
|
|
147
|
+
"shot": "⌥N opens a draft with project, agent and worktree chips; type a line."
|
|
148
|
+
}
|
|
149
|
+
},
|
|
150
|
+
{
|
|
151
|
+
"id": "sidebar-open-pr",
|
|
152
|
+
"title": "Make a session a task",
|
|
153
|
+
"body": "Tick Open a PR when done on a draft and it runs in its own worktree and ends in a pull request.",
|
|
154
|
+
"guide": {
|
|
155
|
+
"file": "sessions",
|
|
156
|
+
"anchor": "new-sessions"
|
|
157
|
+
},
|
|
158
|
+
"added": "2026-10-31"
|
|
159
|
+
},
|
|
160
|
+
{
|
|
161
|
+
"id": "sidebar-pin",
|
|
162
|
+
"title": "Pin a session",
|
|
163
|
+
"body": "Pin in a row's ⋯ menu keeps it on the Pinned shelf, and a pinned session never settles on its own.",
|
|
164
|
+
"guide": {
|
|
165
|
+
"file": "sessions",
|
|
166
|
+
"anchor": "the-sidebar"
|
|
167
|
+
},
|
|
168
|
+
"added": "2026-10-31"
|
|
169
|
+
},
|
|
170
|
+
{
|
|
171
|
+
"id": "sidebar-snooze",
|
|
172
|
+
"title": "Snooze until tomorrow",
|
|
173
|
+
"body": "Snooze in a row's ⋯ menu hides it until 9 AM tomorrow or next Monday. It wakes early if it needs you.",
|
|
174
|
+
"guide": {
|
|
175
|
+
"file": "sessions",
|
|
176
|
+
"anchor": "the-sidebar"
|
|
177
|
+
},
|
|
178
|
+
"added": "2026-10-31",
|
|
179
|
+
"mediaBrief": {
|
|
180
|
+
"kind": "crop",
|
|
181
|
+
"shot": "A row's ⋯ menu open on Snooze with Tomorrow and Next week."
|
|
182
|
+
}
|
|
183
|
+
},
|
|
184
|
+
{
|
|
185
|
+
"id": "sidebar-groups",
|
|
186
|
+
"title": "Put sessions in a group",
|
|
187
|
+
"body": "Move to group → New group… in a row's ⋯ menu gives them their own shelf. Select moves many at once.",
|
|
188
|
+
"guide": {
|
|
189
|
+
"file": "sessions",
|
|
190
|
+
"anchor": "groups"
|
|
191
|
+
},
|
|
192
|
+
"when": ["no-groups"],
|
|
193
|
+
"added": "2026-10-31",
|
|
194
|
+
"mediaBrief": {
|
|
195
|
+
"kind": "screenshot",
|
|
196
|
+
"shot": "Sidebar with a named group shelf holding three sessions."
|
|
197
|
+
}
|
|
198
|
+
},
|
|
199
|
+
{
|
|
200
|
+
"id": "sidebar-load",
|
|
201
|
+
"title": "The dot that shows machine load",
|
|
202
|
+
"body": "The dot in the sidebar header turns amber or red when the machine is busy. Tap it to see which sessions use the most CPU.",
|
|
203
|
+
"guide": {
|
|
204
|
+
"file": "sessions",
|
|
205
|
+
"anchor": "machine-load"
|
|
206
|
+
},
|
|
207
|
+
"added": "2026-10-31",
|
|
208
|
+
"mediaBrief": {
|
|
209
|
+
"kind": "crop",
|
|
210
|
+
"shot": "The machine load popover: the dot amber, the top CPU sessions listed."
|
|
211
|
+
}
|
|
212
|
+
},
|
|
213
|
+
{
|
|
214
|
+
"id": "tasks-sign-off",
|
|
215
|
+
"title": "Sign off and merge from the app",
|
|
216
|
+
"body": "Sign off & merge merges a task's PR once CI is green, then removes its worktree and branches.",
|
|
217
|
+
"guide": {
|
|
218
|
+
"file": "tasks"
|
|
219
|
+
},
|
|
220
|
+
"added": "2026-10-31",
|
|
221
|
+
"mediaBrief": {
|
|
222
|
+
"kind": "crop",
|
|
223
|
+
"shot": "A task in review with CI green and the Sign off & merge button."
|
|
224
|
+
}
|
|
225
|
+
},
|
|
226
|
+
{
|
|
227
|
+
"id": "tasks-queue",
|
|
228
|
+
"title": "Cap how many tasks run at once",
|
|
229
|
+
"body": "Settings → Workspaces sets a running limit. Extra tasks wait under Queued and start in order.",
|
|
230
|
+
"guide": {
|
|
231
|
+
"file": "tasks"
|
|
232
|
+
},
|
|
233
|
+
"added": "2026-10-31"
|
|
234
|
+
},
|
|
235
|
+
{
|
|
236
|
+
"id": "tasks-pause",
|
|
237
|
+
"title": "Pause a task for a while",
|
|
238
|
+
"body": "A running task's row menu pauses it for an hour, until tomorrow, or until you resume it.",
|
|
239
|
+
"guide": {
|
|
240
|
+
"file": "tasks"
|
|
241
|
+
},
|
|
242
|
+
"added": "2026-10-31"
|
|
243
|
+
},
|
|
244
|
+
{
|
|
245
|
+
"id": "tasks-plan-pieces",
|
|
246
|
+
"title": "Approve a plan piece by piece",
|
|
247
|
+
"body": "A plan waiting on you lists its pieces, each with Merge into ① or Drop, and Approve with note… for the whole plan.",
|
|
248
|
+
"guide": {
|
|
249
|
+
"file": "tasks",
|
|
250
|
+
"anchor": "plans-in-pieces"
|
|
251
|
+
},
|
|
252
|
+
"added": "2026-10-31",
|
|
253
|
+
"mediaBrief": {
|
|
254
|
+
"kind": "screenshot",
|
|
255
|
+
"shot": "A plan awaiting approval with two pieces, Merge into ① and Drop on the second."
|
|
256
|
+
}
|
|
257
|
+
},
|
|
258
|
+
{
|
|
259
|
+
"id": "tasks-linked-machines",
|
|
260
|
+
"title": "Run tasks on another machine",
|
|
261
|
+
"body": "Link a second machine and queued tasks start there when this one is busy. Linking more than one machine with Connect needs Pro.",
|
|
262
|
+
"guide": {
|
|
263
|
+
"file": "install",
|
|
264
|
+
"anchor": "with-agentos-connect-any-network-free-for-one-machine-pro-to-link-several"
|
|
265
|
+
},
|
|
266
|
+
"added": "2026-10-31"
|
|
267
|
+
},
|
|
268
|
+
{
|
|
269
|
+
"id": "tasks-stacks",
|
|
270
|
+
"title": "Run a board as a stack",
|
|
271
|
+
"body": "In a project linked to a board, Run as stack starts the cards as stacked PRs, and Land merges them in order.",
|
|
272
|
+
"guide": {
|
|
273
|
+
"file": "tasks",
|
|
274
|
+
"anchor": "stacks"
|
|
275
|
+
},
|
|
276
|
+
"added": "2026-10-31",
|
|
277
|
+
"mediaBrief": {
|
|
278
|
+
"kind": "screenshot",
|
|
279
|
+
"shot": "A stack of three tasks with their PR states and Land."
|
|
280
|
+
}
|
|
281
|
+
},
|
|
282
|
+
{
|
|
283
|
+
"id": "schedule-first",
|
|
284
|
+
"title": "Start work on a timer",
|
|
285
|
+
"body": "Schedules in the sidebar's ⋯ menu runs a prompt every day, every few hours, or once.",
|
|
286
|
+
"guide": {
|
|
287
|
+
"file": "schedules",
|
|
288
|
+
"anchor": "schedules"
|
|
289
|
+
},
|
|
290
|
+
"when": ["no-schedules"],
|
|
291
|
+
"added": "2026-10-31",
|
|
292
|
+
"mediaBrief": {
|
|
293
|
+
"kind": "screenshot",
|
|
294
|
+
"shot": "The Schedules form filled in: daily at 9 AM, a prompt, a project."
|
|
295
|
+
}
|
|
296
|
+
},
|
|
297
|
+
{
|
|
298
|
+
"id": "schedule-check-in",
|
|
299
|
+
"title": "Check in on a long session",
|
|
300
|
+
"body": "Schedule check-ins in a session's ⋯ menu sends it a message on a timer.",
|
|
301
|
+
"guide": {
|
|
302
|
+
"file": "schedules",
|
|
303
|
+
"anchor": "schedules"
|
|
304
|
+
},
|
|
305
|
+
"added": "2026-10-31"
|
|
306
|
+
},
|
|
307
|
+
{
|
|
308
|
+
"id": "recipe-save",
|
|
309
|
+
"title": "Save a job you'll do again",
|
|
310
|
+
"body": "Save as recipe on a finished session or task fills in a recipe from what it did. Each run starts fresh.",
|
|
311
|
+
"guide": {
|
|
312
|
+
"file": "schedules",
|
|
313
|
+
"anchor": "recipes"
|
|
314
|
+
},
|
|
315
|
+
"when": ["no-recipes"],
|
|
316
|
+
"added": "2026-10-31",
|
|
317
|
+
"mediaBrief": {
|
|
318
|
+
"kind": "crop",
|
|
319
|
+
"shot": "The recipe form prefilled from a finished session."
|
|
320
|
+
}
|
|
321
|
+
},
|
|
322
|
+
{
|
|
323
|
+
"id": "net-peers",
|
|
324
|
+
"title": "Sessions can talk to each other",
|
|
325
|
+
"body": "Agents run aos peers to see other sessions and aos send to message one.",
|
|
326
|
+
"guide": {
|
|
327
|
+
"file": "agent-network"
|
|
328
|
+
},
|
|
329
|
+
"added": "2026-10-31"
|
|
330
|
+
},
|
|
331
|
+
{
|
|
332
|
+
"id": "net-await",
|
|
333
|
+
"title": "Wait for a reply without polling",
|
|
334
|
+
"body": "aos send <session> --await ends the agent's turn and wakes it with the answer.",
|
|
335
|
+
"guide": {
|
|
336
|
+
"file": "agent-network",
|
|
337
|
+
"anchor": "waiting-on-a-peer"
|
|
338
|
+
},
|
|
339
|
+
"added": "2026-10-31"
|
|
340
|
+
},
|
|
341
|
+
{
|
|
342
|
+
"id": "net-messages",
|
|
343
|
+
"title": "Read what your agents say to each other",
|
|
344
|
+
"body": "Messages shows every conversation between sessions, and you can join any of them.",
|
|
345
|
+
"guide": {
|
|
346
|
+
"file": "agent-network"
|
|
347
|
+
},
|
|
348
|
+
"added": "2026-10-31",
|
|
349
|
+
"mediaBrief": {
|
|
350
|
+
"kind": "screenshot",
|
|
351
|
+
"shot": "Messages with two sessions talking, one waiting on a reply."
|
|
352
|
+
}
|
|
353
|
+
},
|
|
354
|
+
{
|
|
355
|
+
"id": "phone-pair",
|
|
356
|
+
"title": "Use AgentOS from your phone",
|
|
357
|
+
"body": "Settings → Devices & access → Add a device shows a code to scan. Each code works once.",
|
|
358
|
+
"guide": {
|
|
359
|
+
"file": "phone",
|
|
360
|
+
"anchor": "pair-the-phone"
|
|
361
|
+
},
|
|
362
|
+
"when": ["no-paired-device"],
|
|
363
|
+
"added": "2026-10-31"
|
|
364
|
+
},
|
|
365
|
+
{
|
|
366
|
+
"id": "phone-connect",
|
|
367
|
+
"title": "Reach this machine from anywhere",
|
|
368
|
+
"body": "Connect gives it a private address that works off your home network, free for one machine.",
|
|
369
|
+
"guide": {
|
|
370
|
+
"file": "phone",
|
|
371
|
+
"anchor": "from-anywhere-with-connect"
|
|
372
|
+
},
|
|
373
|
+
"when": ["connect-not-linked"],
|
|
374
|
+
"added": "2026-10-31"
|
|
375
|
+
},
|
|
376
|
+
{
|
|
377
|
+
"id": "phone-push",
|
|
378
|
+
"title": "Get pushes when an agent needs you",
|
|
379
|
+
"body": "Settings → Notifications → Your phone sends a test push to check it works.",
|
|
380
|
+
"guide": {
|
|
381
|
+
"file": "phone",
|
|
382
|
+
"anchor": "notifications"
|
|
383
|
+
},
|
|
384
|
+
"when": ["no-push-device"],
|
|
385
|
+
"added": "2026-10-31"
|
|
386
|
+
},
|
|
387
|
+
{
|
|
388
|
+
"id": "share-check",
|
|
389
|
+
"title": "Shares are masked before upload",
|
|
390
|
+
"body": "The Share dialog shows exactly what goes up, with secrets, addresses and emails masked. Nothing leaves until Create link.",
|
|
391
|
+
"guide": {
|
|
392
|
+
"file": "sharing",
|
|
393
|
+
"anchor": "check-it-first"
|
|
394
|
+
},
|
|
395
|
+
"when": ["no-shares"],
|
|
396
|
+
"added": "2026-10-31",
|
|
397
|
+
"mediaBrief": {
|
|
398
|
+
"kind": "screenshot",
|
|
399
|
+
"shot": "The Share dialog preview with masked values highlighted, before Create link."
|
|
400
|
+
}
|
|
401
|
+
},
|
|
402
|
+
{
|
|
403
|
+
"id": "share-expiry",
|
|
404
|
+
"title": "Links can expire",
|
|
405
|
+
"body": "Create link lasts 1, 7 or 30 days, or never. Revoke one in Settings → Shared links.",
|
|
406
|
+
"guide": {
|
|
407
|
+
"file": "sharing",
|
|
408
|
+
"anchor": "create-the-link"
|
|
409
|
+
},
|
|
410
|
+
"added": "2026-10-31"
|
|
411
|
+
},
|
|
412
|
+
{
|
|
413
|
+
"id": "export-ai",
|
|
414
|
+
"title": "Hand a chat to another AI",
|
|
415
|
+
"body": "Export for AI… in the ⋯ menu saves the chat as Markdown, JSON or HTML, with secrets masked.",
|
|
416
|
+
"guide": {
|
|
417
|
+
"file": "export"
|
|
418
|
+
},
|
|
419
|
+
"added": "2026-10-31",
|
|
420
|
+
"mediaBrief": {
|
|
421
|
+
"kind": "crop",
|
|
422
|
+
"shot": "The Export for AI sheet: format, Compact selected, the size estimate."
|
|
423
|
+
}
|
|
424
|
+
},
|
|
425
|
+
{
|
|
426
|
+
"id": "export-compact",
|
|
427
|
+
"title": "Compact export for long chats",
|
|
428
|
+
"body": "Compact drops thinking and trims tool output, and the sheet warns when a file is too big for most models.",
|
|
429
|
+
"guide": {
|
|
430
|
+
"file": "export",
|
|
431
|
+
"anchor": "what-you-choose"
|
|
432
|
+
},
|
|
433
|
+
"added": "2026-10-31"
|
|
434
|
+
},
|
|
435
|
+
{
|
|
436
|
+
"id": "update-when-idle",
|
|
437
|
+
"title": "Update without interrupting work",
|
|
438
|
+
"body": "Update when idle in the update banner waits until nothing is working.",
|
|
439
|
+
"guide": {
|
|
440
|
+
"file": "install",
|
|
441
|
+
"anchor": "update-from-the-app"
|
|
442
|
+
},
|
|
443
|
+
"added": "2026-10-31"
|
|
444
|
+
},
|
|
445
|
+
{
|
|
446
|
+
"id": "tips-whats-new",
|
|
447
|
+
"title": "See what changed in each update",
|
|
448
|
+
"body": "The sparkle next to the lightbulb lists every change. A dot on it means something new since you last looked.",
|
|
449
|
+
"guide": {
|
|
450
|
+
"file": "tips",
|
|
451
|
+
"anchor": "whats-new"
|
|
452
|
+
},
|
|
453
|
+
"added": "2026-10-31"
|
|
454
|
+
}
|
|
455
|
+
]
|
|
456
|
+
}
|
package/content/whats-new.json
CHANGED
|
@@ -1785,6 +1785,38 @@
|
|
|
1785
1785
|
"area": "Chat",
|
|
1786
1786
|
"text": "Large photos from your phone now attach to a chat instead of being refused.",
|
|
1787
1787
|
"url": "https://github.com/saadnvd1/agent-os/pull/529"
|
|
1788
|
+
},
|
|
1789
|
+
{
|
|
1790
|
+
"id": 530,
|
|
1791
|
+
"date": "2026-10-31",
|
|
1792
|
+
"kind": "new",
|
|
1793
|
+
"area": "Chat",
|
|
1794
|
+
"text": "GitHub Copilot chats can now ask you questions with clickable answer cards, like Claude chats do.",
|
|
1795
|
+
"url": "https://github.com/saadnvd1/agent-os/pull/530"
|
|
1796
|
+
},
|
|
1797
|
+
{
|
|
1798
|
+
"id": 531,
|
|
1799
|
+
"date": "2026-10-31",
|
|
1800
|
+
"kind": "new",
|
|
1801
|
+
"area": "Updates",
|
|
1802
|
+
"text": "AgentOS now keeps itself up to date once nothing is working, and goes back to the previous version on its own if an update doesn't start cleanly.",
|
|
1803
|
+
"url": "https://github.com/saadnvd1/agent-os/pull/531"
|
|
1804
|
+
},
|
|
1805
|
+
{
|
|
1806
|
+
"id": 532,
|
|
1807
|
+
"date": "2026-10-31",
|
|
1808
|
+
"kind": "new",
|
|
1809
|
+
"area": "AgentOS",
|
|
1810
|
+
"text": "A lightbulb in the sidebar shows one short tip a day about a feature you may have missed, and you can turn tips off in Settings.",
|
|
1811
|
+
"url": "https://github.com/saadnvd1/agent-os/pull/532"
|
|
1812
|
+
},
|
|
1813
|
+
{
|
|
1814
|
+
"id": 533,
|
|
1815
|
+
"date": "2026-10-31",
|
|
1816
|
+
"kind": "fixed",
|
|
1817
|
+
"area": "Chat",
|
|
1818
|
+
"text": "Chats now fill the screen with earlier messages on open instead of showing a nearly empty view with a \"Show earlier messages\" button.",
|
|
1819
|
+
"url": "https://github.com/saadnvd1/agent-os/pull/533"
|
|
1788
1820
|
}
|
|
1789
1821
|
]
|
|
1790
1822
|
}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query";
|
|
2
|
+
import type { TipsView } from "@/lib/tips/schema";
|
|
3
|
+
|
|
4
|
+
export const tipsKeys = { all: ["tips"] as const };
|
|
5
|
+
|
|
6
|
+
// The browser's own date: the tip changes at the user's midnight.
|
|
7
|
+
const localDay = () => new Date().toLocaleDateString("sv");
|
|
8
|
+
|
|
9
|
+
async function send(init?: { body: object }): Promise<TipsView> {
|
|
10
|
+
const res = await fetch(
|
|
11
|
+
init ? "/api/tips" : `/api/tips?day=${localDay()}`,
|
|
12
|
+
init && {
|
|
13
|
+
method: "POST",
|
|
14
|
+
headers: { "Content-Type": "application/json" },
|
|
15
|
+
body: JSON.stringify(init.body),
|
|
16
|
+
}
|
|
17
|
+
).catch(() => {
|
|
18
|
+
throw new Error("Couldn't reach AgentOS. Try again.");
|
|
19
|
+
});
|
|
20
|
+
if (!res.ok) throw new Error(`Tips failed (${res.status})`);
|
|
21
|
+
return res.json();
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
// The tips file only changes with an update; the day can change under an open tab.
|
|
25
|
+
export const useTips = () =>
|
|
26
|
+
useQuery({
|
|
27
|
+
queryKey: tipsKeys.all,
|
|
28
|
+
queryFn: () => send(),
|
|
29
|
+
staleTime: 10 * 60_000,
|
|
30
|
+
refetchOnWindowFocus: true,
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
function useTipsMutation<V>(body: (v: V) => object) {
|
|
34
|
+
const queryClient = useQueryClient();
|
|
35
|
+
return useMutation({
|
|
36
|
+
mutationFn: (v: V) => send({ body: body(v) }),
|
|
37
|
+
onSuccess: (view) => queryClient.setQueryData(tipsKeys.all, view),
|
|
38
|
+
});
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export const useMarkTipSeen = () =>
|
|
42
|
+
useTipsMutation<string>((id) => ({
|
|
43
|
+
action: "seen",
|
|
44
|
+
ids: [id],
|
|
45
|
+
day: localDay(),
|
|
46
|
+
}));
|
|
47
|
+
|
|
48
|
+
export const useSetTipsOff = () =>
|
|
49
|
+
useTipsMutation<boolean>((off) => ({ action: "off", off }));
|
package/data/updates/index.ts
CHANGED
|
@@ -61,3 +61,8 @@ export const useUpdateBannerSetting = () =>
|
|
|
61
61
|
useUpdateMutation<boolean>((banner) =>
|
|
62
62
|
send("PUT", "/api/updates/settings", { banner })
|
|
63
63
|
);
|
|
64
|
+
|
|
65
|
+
export const useAutoUpdateSetting = () =>
|
|
66
|
+
useUpdateMutation<{ auto?: boolean; idleMinutes?: number }>((patch) =>
|
|
67
|
+
send("PUT", "/api/updates/settings", patch)
|
|
68
|
+
);
|
|
@@ -13,7 +13,11 @@ export function useReloadWhenUpdated(view: UpdateView | undefined) {
|
|
|
13
13
|
useEffect(() => {
|
|
14
14
|
if (!run) return;
|
|
15
15
|
if (isActivePhase(run.phase)) watched.current = run.id;
|
|
16
|
-
|
|
16
|
+
// A rollback restarted the server onto the old build: reload onto it too.
|
|
17
|
+
else if (
|
|
18
|
+
(run.phase === "done" || run.phase === "rolled_back") &&
|
|
19
|
+
watched.current === run.id
|
|
20
|
+
)
|
|
17
21
|
window.location.reload();
|
|
18
22
|
}, [run]);
|
|
19
23
|
}
|
package/lib/busy.ts
CHANGED
|
@@ -2,12 +2,14 @@ import { db } from "./db";
|
|
|
2
2
|
import { runningStarts } from "./simulator";
|
|
3
3
|
|
|
4
4
|
// What a restart would cut off and have to start over: reviews, task
|
|
5
|
-
// setups
|
|
5
|
+
// setups, simulator starts, merges and stack landings run in the server. (Chat turns run in their own workers and
|
|
6
6
|
// outlive it.) Older than half an hour is stuck, not in flight.
|
|
7
7
|
export function inFlight(): {
|
|
8
8
|
reviews: number;
|
|
9
9
|
setups: number;
|
|
10
10
|
simulatorStarts: number;
|
|
11
|
+
merges: number;
|
|
12
|
+
landings: number;
|
|
11
13
|
} {
|
|
12
14
|
const count = (sql: string) => (db.prepare(sql).get() as { n: number }).n;
|
|
13
15
|
return {
|
|
@@ -22,5 +24,25 @@ export function inFlight(): {
|
|
|
22
24
|
AND created_at > datetime('now', '-30 minutes')`
|
|
23
25
|
),
|
|
24
26
|
simulatorStarts: runningStarts(),
|
|
27
|
+
merges: mergesInFlight(),
|
|
28
|
+
landings: count(
|
|
29
|
+
`SELECT COUNT(*) AS n FROM stacks WHERE status = 'landing'`
|
|
30
|
+
),
|
|
25
31
|
};
|
|
26
32
|
}
|
|
33
|
+
|
|
34
|
+
// Between `gh pr merge` and the tidying after it (lib/tasks/finish.ts keeps
|
|
35
|
+
// both on globalThis, so every bundle sees the same ones).
|
|
36
|
+
function mergesInFlight(): number {
|
|
37
|
+
const g = globalThis as unknown as {
|
|
38
|
+
__agentosSigningOff?: Set<string>;
|
|
39
|
+
__agentosAfterMerge?: Map<string, unknown>;
|
|
40
|
+
};
|
|
41
|
+
return new Set([
|
|
42
|
+
...(g.__agentosSigningOff ?? []),
|
|
43
|
+
...(g.__agentosAfterMerge?.keys() ?? []),
|
|
44
|
+
]).size;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
export const inFlightTotal = (w: ReturnType<typeof inFlight>): number =>
|
|
48
|
+
w.reviews + w.setups + w.simulatorStarts + w.merges + w.landings;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import type { ChatAccess, DriverEvent, FileDiff } from "../events";
|
|
2
2
|
import { unifiedToDiff } from "../diff";
|
|
3
3
|
import { toolTitle } from "../tools";
|
|
4
|
+
import { isAskUserCall } from "./copilot-ask";
|
|
4
5
|
import { PendingApprovals } from "./pending-approvals";
|
|
5
6
|
|
|
6
7
|
type P = Record<string, unknown>;
|
|
@@ -71,6 +72,7 @@ export class CopilotApprovals {
|
|
|
71
72
|
: { outcome: { outcome: "cancelled" } };
|
|
72
73
|
|
|
73
74
|
if (
|
|
75
|
+
isAskUserCall(call) ||
|
|
74
76
|
this.access === "full" ||
|
|
75
77
|
(this.access === "edits" && EDITS_KINDS.has(kind))
|
|
76
78
|
)
|