@vitos-pizza/vitos-pizza 0.1.0 → 0.2.0

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.
Files changed (259) hide show
  1. package/AGENTS.md +158 -158
  2. package/CHANGELOG.md +42 -24
  3. package/LICENSE +21 -21
  4. package/README.md +237 -234
  5. package/assets/logo.svg +28 -28
  6. package/node_modules/@vitos-pizza/agent-mode/extensions/index.ts +138 -117
  7. package/node_modules/@vitos-pizza/agent-mode/package.json +3 -3
  8. package/node_modules/@vitos-pizza/agent-mode/src/apply-mode.ts +60 -60
  9. package/node_modules/@vitos-pizza/agent-mode/src/mode-events.ts +102 -102
  10. package/node_modules/@vitos-pizza/agent-mode/src/modes.ts +43 -43
  11. package/node_modules/@vitos-pizza/agent-mode/src/plan-instructions.ts +85 -44
  12. package/node_modules/@vitos-pizza/agent-mode/tests/apply-mode.test.ts +36 -36
  13. package/node_modules/@vitos-pizza/agent-mode/tests/mode-events.test.ts +22 -22
  14. package/node_modules/@vitos-pizza/agent-mode/tests/modes.test.ts +38 -38
  15. package/node_modules/@vitos-pizza/agent-mode/tests/plan-instructions.test.ts +68 -45
  16. package/node_modules/@vitos-pizza/agent-mode/tsconfig.json +13 -13
  17. package/node_modules/@vitos-pizza/agent-mode/vitest.config.ts +8 -8
  18. package/node_modules/@vitos-pizza/keybindings/extensions/index.ts +104 -104
  19. package/node_modules/@vitos-pizza/keybindings/package.json +1 -1
  20. package/node_modules/@vitos-pizza/keybindings/presets/shortcuts.json +3 -3
  21. package/node_modules/@vitos-pizza/keybindings/src/bind.ts +57 -57
  22. package/node_modules/@vitos-pizza/keybindings/src/config.ts +84 -84
  23. package/node_modules/@vitos-pizza/keybindings/src/registry.ts +43 -43
  24. package/node_modules/@vitos-pizza/keybindings/src/types.ts +54 -54
  25. package/node_modules/@vitos-pizza/keybindings/tests/config.test.ts +83 -83
  26. package/node_modules/@vitos-pizza/keybindings/tests/registry.test.ts +142 -142
  27. package/node_modules/@vitos-pizza/keybindings/tsconfig.json +13 -13
  28. package/node_modules/@vitos-pizza/keybindings/vitest.config.ts +8 -8
  29. package/node_modules/@vitos-pizza/permission-system/extensions/index.ts +162 -162
  30. package/node_modules/@vitos-pizza/permission-system/package.json +2 -2
  31. package/node_modules/@vitos-pizza/permission-system/src/bash/matcher.ts +54 -51
  32. package/node_modules/@vitos-pizza/permission-system/src/bash/parser.ts +40 -40
  33. package/node_modules/@vitos-pizza/permission-system/src/config-paths.ts +23 -23
  34. package/node_modules/@vitos-pizza/permission-system/src/detect-preset-mode.ts +61 -61
  35. package/node_modules/@vitos-pizza/permission-system/src/expand-home.ts +12 -12
  36. package/node_modules/@vitos-pizza/permission-system/src/forwarding/forwarder.ts +224 -224
  37. package/node_modules/@vitos-pizza/permission-system/src/forwarding/subagent-registry.ts +61 -61
  38. package/node_modules/@vitos-pizza/permission-system/src/gates/path-utils.ts +66 -66
  39. package/node_modules/@vitos-pizza/permission-system/src/gates/pipeline.ts +151 -155
  40. package/node_modules/@vitos-pizza/permission-system/src/handlers/before-agent-start.ts +86 -65
  41. package/node_modules/@vitos-pizza/permission-system/src/handlers/skill-input.ts +1 -1
  42. package/node_modules/@vitos-pizza/permission-system/src/handlers/tool-call-gate.ts +204 -199
  43. package/node_modules/@vitos-pizza/permission-system/src/mode-api.ts +44 -44
  44. package/node_modules/@vitos-pizza/permission-system/src/permission-evaluator.ts +233 -216
  45. package/node_modules/@vitos-pizza/permission-system/src/permission-session.ts +62 -62
  46. package/node_modules/@vitos-pizza/permission-system/src/policy-loader.ts +211 -211
  47. package/node_modules/@vitos-pizza/permission-system/src/sanitizers/skill-prompt.ts +99 -99
  48. package/node_modules/@vitos-pizza/permission-system/src/sanitizers/system-prompt.ts +221 -221
  49. package/node_modules/@vitos-pizza/permission-system/src/service.ts +66 -66
  50. package/node_modules/@vitos-pizza/permission-system/src/session-approvals.ts +4 -1
  51. package/node_modules/@vitos-pizza/permission-system/src/types.ts +80 -80
  52. package/node_modules/@vitos-pizza/permission-system/src/ui/approval-summary.ts +43 -43
  53. package/node_modules/@vitos-pizza/permission-system/src/ui/config-modal.ts +36 -36
  54. package/node_modules/@vitos-pizza/permission-system/src/ui/permission-dialog.ts +52 -52
  55. package/node_modules/@vitos-pizza/permission-system/src/wildcard-matcher.ts +81 -81
  56. package/node_modules/@vitos-pizza/permission-system/src/yaml-frontmatter.ts +84 -84
  57. package/node_modules/@vitos-pizza/permission-system/src/yolo/runtime-api.ts +49 -49
  58. package/node_modules/@vitos-pizza/permission-system/tests/bash-parser.test.ts +32 -32
  59. package/node_modules/@vitos-pizza/permission-system/tests/before-agent-start.test.ts +61 -0
  60. package/node_modules/@vitos-pizza/permission-system/tests/detect-preset-mode.test.ts +68 -68
  61. package/node_modules/@vitos-pizza/permission-system/tests/forwarder.test.ts +55 -55
  62. package/node_modules/@vitos-pizza/permission-system/tests/gates.test.ts +170 -61
  63. package/node_modules/@vitos-pizza/permission-system/tests/path-utils.test.ts +68 -68
  64. package/node_modules/@vitos-pizza/permission-system/tests/permission-evaluator.test.ts +82 -55
  65. package/node_modules/@vitos-pizza/permission-system/tests/policy-loader.test.ts +25 -25
  66. package/node_modules/@vitos-pizza/permission-system/tests/system-prompt-sanitizer.test.ts +22 -22
  67. package/node_modules/@vitos-pizza/permission-system/tests/wildcard-matcher.test.ts +27 -27
  68. package/node_modules/@vitos-pizza/permission-system/tsconfig.json +13 -13
  69. package/node_modules/@vitos-pizza/permission-system/vitest.config.ts +8 -8
  70. package/node_modules/@vitos-pizza/question/package.json +1 -1
  71. package/node_modules/@vitos-pizza/question/src/question-ui.ts +5 -1
  72. package/node_modules/@vitos-pizza/question/src/register-tool.ts +1 -4
  73. package/node_modules/@vitos-pizza/question/tests/question-ui-width-cache.test.ts +45 -0
  74. package/node_modules/@vitos-pizza/question/tests/register-tool-render.test.ts +48 -45
  75. package/node_modules/@vitos-pizza/session-title/extensions/index.ts +137 -137
  76. package/node_modules/@vitos-pizza/session-title/package.json +3 -3
  77. package/node_modules/@vitos-pizza/session-title/src/build-title-prompt.ts +16 -16
  78. package/node_modules/@vitos-pizza/session-title/src/extract-title-context.ts +55 -55
  79. package/node_modules/@vitos-pizza/session-title/src/fast-rules.ts +48 -48
  80. package/node_modules/@vitos-pizza/session-title/src/load-settings.ts +70 -70
  81. package/node_modules/@vitos-pizza/session-title/src/normalize-title.ts +20 -20
  82. package/node_modules/@vitos-pizza/session-title/src/parse-title-response.ts +6 -6
  83. package/node_modules/@vitos-pizza/session-title/src/resolve-title-model.ts +33 -33
  84. package/node_modules/@vitos-pizza/session-title/src/schedule-title-job.ts +53 -53
  85. package/node_modules/@vitos-pizza/session-title/src/should-schedule.ts +30 -30
  86. package/node_modules/@vitos-pizza/session-title/src/title-agent.ts +60 -60
  87. package/node_modules/@vitos-pizza/session-title/src/truncate-input.ts +10 -10
  88. package/node_modules/@vitos-pizza/session-title/src/types.ts +29 -29
  89. package/node_modules/@vitos-pizza/session-title/tests/build-title-prompt.test.ts +34 -34
  90. package/node_modules/@vitos-pizza/session-title/tests/extension.test.ts +198 -198
  91. package/node_modules/@vitos-pizza/session-title/tests/extract-title-context.test.ts +48 -48
  92. package/node_modules/@vitos-pizza/session-title/tests/fast-rules.test.ts +43 -43
  93. package/node_modules/@vitos-pizza/session-title/tests/parse-title-response.test.ts +34 -34
  94. package/node_modules/@vitos-pizza/session-title/tests/should-schedule.test.ts +30 -30
  95. package/node_modules/@vitos-pizza/session-title/tests/title-agent.test.ts +154 -154
  96. package/node_modules/@vitos-pizza/session-title/tests/truncate-input.test.ts +15 -15
  97. package/node_modules/@vitos-pizza/session-title/tsconfig.json +13 -13
  98. package/node_modules/@vitos-pizza/session-title/vitest.config.ts +8 -8
  99. package/node_modules/@vitos-pizza/subagents/agents/planner.md +46 -43
  100. package/node_modules/@vitos-pizza/subagents/agents/scout.md +40 -40
  101. package/node_modules/@vitos-pizza/subagents/agents/title.md +13 -13
  102. package/node_modules/@vitos-pizza/subagents/agents/worker.md +36 -36
  103. package/node_modules/@vitos-pizza/subagents/extensions/index.ts +164 -164
  104. package/node_modules/@vitos-pizza/subagents/package.json +1 -1
  105. package/node_modules/@vitos-pizza/subagents/skills/subagents/SKILL.md +86 -80
  106. package/node_modules/@vitos-pizza/subagents/src/agents.ts +166 -166
  107. package/node_modules/@vitos-pizza/subagents/src/async/job-tracker.ts +71 -71
  108. package/node_modules/@vitos-pizza/subagents/src/async/spawn-async.ts +220 -220
  109. package/node_modules/@vitos-pizza/subagents/src/async/storage.ts +57 -57
  110. package/node_modules/@vitos-pizza/subagents/src/env.ts +4 -4
  111. package/node_modules/@vitos-pizza/subagents/src/execute-subagent.ts +285 -285
  112. package/node_modules/@vitos-pizza/subagents/src/progress.ts +187 -187
  113. package/node_modules/@vitos-pizza/subagents/src/render-animation.ts +40 -40
  114. package/node_modules/@vitos-pizza/subagents/src/render.ts +428 -428
  115. package/node_modules/@vitos-pizza/subagents/src/rpc/channels.ts +21 -21
  116. package/node_modules/@vitos-pizza/subagents/src/rpc/client.ts +144 -144
  117. package/node_modules/@vitos-pizza/subagents/src/rpc/server.ts +11 -11
  118. package/node_modules/@vitos-pizza/subagents/src/run-agent.ts +313 -313
  119. package/node_modules/@vitos-pizza/subagents/src/runtime.ts +102 -102
  120. package/node_modules/@vitos-pizza/subagents/src/schema.ts +62 -62
  121. package/node_modules/@vitos-pizza/subagents/src/spawn.ts +104 -104
  122. package/node_modules/@vitos-pizza/subagents/src/types.ts +92 -92
  123. package/node_modules/@vitos-pizza/subagents/src/utils.ts +100 -100
  124. package/node_modules/@vitos-pizza/subagents/src/wait.ts +159 -159
  125. package/node_modules/@vitos-pizza/subagents/tests/agents.test.ts +19 -19
  126. package/node_modules/@vitos-pizza/subagents/tests/execute-subagent.test.ts +96 -96
  127. package/node_modules/@vitos-pizza/subagents/tests/extension.test.ts +42 -42
  128. package/node_modules/@vitos-pizza/subagents/tests/progress.test.ts +206 -206
  129. package/node_modules/@vitos-pizza/subagents/tests/rpc.test.ts +74 -74
  130. package/node_modules/@vitos-pizza/subagents/tsconfig.json +13 -13
  131. package/node_modules/@vitos-pizza/subagents/vitest.config.ts +8 -8
  132. package/node_modules/@vitos-pizza/ui-enhancements/package.json +1 -1
  133. package/node_modules/@vitos-pizza/ui-enhancements/src/chrome/agent-mode-badge.ts +60 -60
  134. package/node_modules/@vitos-pizza/ui-enhancements/src/chrome/border-status.ts +14 -1
  135. package/node_modules/@vitos-pizza/ui-enhancements/src/chrome/resize-recovery.ts +63 -0
  136. package/node_modules/@vitos-pizza/ui-enhancements/tests/agent-mode-badge.test.ts +35 -35
  137. package/node_modules/@vitos-pizza/ui-enhancements/tests/resize-recovery.test.ts +135 -0
  138. package/node_modules/@vitos-pizza/websearch/package.json +1 -1
  139. package/node_modules/node-addon-api/tools/conversion.js +0 -0
  140. package/node_modules/node-gyp-build/bin.js +0 -0
  141. package/node_modules/node-gyp-build/build-test.js +0 -0
  142. package/node_modules/node-gyp-build/optional.js +0 -0
  143. package/package.json +11 -9
  144. package/packages/agent-mode/extensions/index.ts +138 -117
  145. package/packages/agent-mode/package.json +3 -3
  146. package/packages/agent-mode/src/apply-mode.ts +60 -60
  147. package/packages/agent-mode/src/mode-events.ts +102 -102
  148. package/packages/agent-mode/src/modes.ts +43 -43
  149. package/packages/agent-mode/src/plan-instructions.ts +85 -44
  150. package/packages/agent-mode/tsconfig.json +13 -13
  151. package/packages/agent-mode/vitest.config.ts +8 -8
  152. package/packages/keybindings/extensions/index.ts +104 -104
  153. package/packages/keybindings/package.json +1 -1
  154. package/packages/keybindings/presets/shortcuts.json +3 -3
  155. package/packages/keybindings/src/bind.ts +57 -57
  156. package/packages/keybindings/src/config.ts +84 -84
  157. package/packages/keybindings/src/registry.ts +43 -43
  158. package/packages/keybindings/src/types.ts +54 -54
  159. package/packages/keybindings/tsconfig.json +13 -13
  160. package/packages/keybindings/vitest.config.ts +8 -8
  161. package/packages/permission-system/extensions/index.ts +162 -162
  162. package/packages/permission-system/node_modules/web-tree-sitter/debug/tree-sitter.wasm +0 -0
  163. package/packages/permission-system/node_modules/web-tree-sitter/tree-sitter.wasm +0 -0
  164. package/packages/permission-system/package.json +2 -2
  165. package/packages/permission-system/src/bash/matcher.ts +54 -51
  166. package/packages/permission-system/src/bash/parser.ts +40 -40
  167. package/packages/permission-system/src/config-paths.ts +23 -23
  168. package/packages/permission-system/src/detect-preset-mode.ts +61 -61
  169. package/packages/permission-system/src/expand-home.ts +12 -12
  170. package/packages/permission-system/src/forwarding/forwarder.ts +224 -224
  171. package/packages/permission-system/src/forwarding/subagent-registry.ts +61 -61
  172. package/packages/permission-system/src/gates/path-utils.ts +66 -66
  173. package/packages/permission-system/src/gates/pipeline.ts +151 -155
  174. package/packages/permission-system/src/handlers/before-agent-start.ts +86 -65
  175. package/packages/permission-system/src/handlers/skill-input.ts +1 -1
  176. package/packages/permission-system/src/handlers/tool-call-gate.ts +204 -199
  177. package/packages/permission-system/src/mode-api.ts +44 -44
  178. package/packages/permission-system/src/permission-evaluator.ts +233 -216
  179. package/packages/permission-system/src/permission-session.ts +62 -62
  180. package/packages/permission-system/src/policy-loader.ts +211 -211
  181. package/packages/permission-system/src/sanitizers/skill-prompt.ts +99 -99
  182. package/packages/permission-system/src/sanitizers/system-prompt.ts +221 -221
  183. package/packages/permission-system/src/service.ts +66 -66
  184. package/packages/permission-system/src/session-approvals.ts +4 -1
  185. package/packages/permission-system/src/types.ts +80 -80
  186. package/packages/permission-system/src/ui/approval-summary.ts +43 -43
  187. package/packages/permission-system/src/ui/config-modal.ts +36 -36
  188. package/packages/permission-system/src/ui/permission-dialog.ts +52 -52
  189. package/packages/permission-system/src/wildcard-matcher.ts +81 -81
  190. package/packages/permission-system/src/yaml-frontmatter.ts +84 -84
  191. package/packages/permission-system/src/yolo/runtime-api.ts +49 -49
  192. package/packages/permission-system/tsconfig.json +13 -13
  193. package/packages/permission-system/vitest.config.ts +8 -8
  194. package/packages/question/package.json +1 -1
  195. package/packages/question/src/question-ui.ts +5 -1
  196. package/packages/question/src/register-tool.ts +1 -4
  197. package/packages/session-title/extensions/index.ts +137 -137
  198. package/packages/session-title/package.json +3 -3
  199. package/packages/session-title/src/build-title-prompt.ts +16 -16
  200. package/packages/session-title/src/extract-title-context.ts +55 -55
  201. package/packages/session-title/src/fast-rules.ts +48 -48
  202. package/packages/session-title/src/load-settings.ts +70 -70
  203. package/packages/session-title/src/normalize-title.ts +20 -20
  204. package/packages/session-title/src/parse-title-response.ts +6 -6
  205. package/packages/session-title/src/resolve-title-model.ts +33 -33
  206. package/packages/session-title/src/schedule-title-job.ts +53 -53
  207. package/packages/session-title/src/should-schedule.ts +30 -30
  208. package/packages/session-title/src/title-agent.ts +60 -60
  209. package/packages/session-title/src/truncate-input.ts +10 -10
  210. package/packages/session-title/src/types.ts +29 -29
  211. package/packages/session-title/tsconfig.json +13 -13
  212. package/packages/session-title/vitest.config.ts +8 -8
  213. package/packages/subagents/agents/planner.md +46 -43
  214. package/packages/subagents/agents/scout.md +40 -40
  215. package/packages/subagents/agents/title.md +13 -13
  216. package/packages/subagents/agents/worker.md +36 -36
  217. package/packages/subagents/extensions/index.ts +164 -164
  218. package/packages/subagents/package.json +1 -1
  219. package/packages/subagents/skills/subagents/SKILL.md +86 -80
  220. package/packages/subagents/src/agents.ts +166 -166
  221. package/packages/subagents/src/async/job-tracker.ts +71 -71
  222. package/packages/subagents/src/async/spawn-async.ts +220 -220
  223. package/packages/subagents/src/async/storage.ts +57 -57
  224. package/packages/subagents/src/env.ts +4 -4
  225. package/packages/subagents/src/execute-subagent.ts +285 -285
  226. package/packages/subagents/src/progress.ts +187 -187
  227. package/packages/subagents/src/render-animation.ts +40 -40
  228. package/packages/subagents/src/render.ts +428 -428
  229. package/packages/subagents/src/rpc/channels.ts +21 -21
  230. package/packages/subagents/src/rpc/client.ts +144 -144
  231. package/packages/subagents/src/rpc/server.ts +11 -11
  232. package/packages/subagents/src/run-agent.ts +313 -313
  233. package/packages/subagents/src/runtime.ts +102 -102
  234. package/packages/subagents/src/schema.ts +62 -62
  235. package/packages/subagents/src/spawn.ts +104 -104
  236. package/packages/subagents/src/types.ts +92 -92
  237. package/packages/subagents/src/utils.ts +100 -100
  238. package/packages/subagents/src/wait.ts +159 -159
  239. package/packages/subagents/tsconfig.json +13 -13
  240. package/packages/subagents/vitest.config.ts +8 -8
  241. package/packages/todoist/extensions/index.ts +163 -0
  242. package/packages/todoist/package.json +34 -0
  243. package/packages/todoist/src/events.ts +7 -0
  244. package/packages/todoist/src/silent-render.ts +8 -0
  245. package/packages/todoist/src/state.ts +147 -0
  246. package/packages/todoist/src/tools.ts +175 -0
  247. package/packages/todoist/src/types.ts +34 -0
  248. package/packages/todoist/src/widget.ts +109 -0
  249. package/packages/todoist/tsconfig.json +13 -0
  250. package/packages/todoist/vitest.config.ts +8 -0
  251. package/packages/ui-enhancements/package.json +1 -1
  252. package/packages/ui-enhancements/src/chrome/agent-mode-badge.ts +60 -60
  253. package/packages/ui-enhancements/src/chrome/border-status.ts +14 -1
  254. package/packages/ui-enhancements/src/chrome/resize-recovery.ts +63 -0
  255. package/packages/websearch/package.json +1 -1
  256. package/scripts/sync-pi-manifest.mjs +1 -1
  257. package/packages/permission-system/node_modules/web-tree-sitter/lib/tree-sitter.cjs +0 -2988
  258. package/packages/permission-system/node_modules/web-tree-sitter/lib/tree-sitter.wasm +0 -0
  259. package/packages/permission-system/node_modules/web-tree-sitter/lib/tree-sitter.wasm.map +0 -1
@@ -1,60 +1,60 @@
1
- import type { ExtensionAPI, Theme } from "@earendil-works/pi-coding-agent";
2
-
3
- export const AGENT_MODE_CHANGED = "agent-mode:changed";
4
-
5
- export type AgentModeDisplayColor = "dim" | "accent" | "warning";
6
-
7
- export interface AgentModeChangedPayload {
8
- mode: "agent" | "plan" | "execute";
9
- label: string;
10
- color: AgentModeDisplayColor;
11
- }
12
-
13
- let currentAgentMode: AgentModeChangedPayload | null = null;
14
-
15
- function isPayload(value: unknown): value is AgentModeChangedPayload {
16
- if (!value || typeof value !== "object") return false;
17
- const payload = value as Partial<AgentModeChangedPayload>;
18
- return (
19
- (payload.mode === "agent" ||
20
- payload.mode === "plan" ||
21
- payload.mode === "execute") &&
22
- typeof payload.label === "string" &&
23
- (payload.color === "dim" ||
24
- payload.color === "accent" ||
25
- payload.color === "warning")
26
- );
27
- }
28
-
29
- export function getAgentModeBadge(): AgentModeChangedPayload | null {
30
- return currentAgentMode;
31
- }
32
-
33
- export function formatAgentModeSuffix(
34
- payload: AgentModeChangedPayload | null,
35
- theme: Theme,
36
- ): string {
37
- if (!payload || payload.mode === "agent") return "";
38
- return theme.fg(payload.color, ` · ${payload.label}`);
39
- }
40
-
41
- export function registerAgentModeBadge(
42
- pi: ExtensionAPI,
43
- requestRender: () => void,
44
- ): () => void {
45
- const unsubChanged = pi.events.on(AGENT_MODE_CHANGED, (value) => {
46
- if (!isPayload(value)) return;
47
- currentAgentMode = value;
48
- requestRender();
49
- });
50
-
51
- pi.on("session_shutdown", () => {
52
- currentAgentMode = null;
53
- });
54
-
55
- return unsubChanged;
56
- }
57
-
58
- export function resetAgentModeBadgeForTests(): void {
59
- currentAgentMode = null;
60
- }
1
+ import type { ExtensionAPI, Theme } from "@earendil-works/pi-coding-agent";
2
+
3
+ export const AGENT_MODE_CHANGED = "agent-mode:changed";
4
+
5
+ export type AgentModeDisplayColor = "dim" | "accent" | "warning";
6
+
7
+ export interface AgentModeChangedPayload {
8
+ mode: "agent" | "plan" | "execute";
9
+ label: string;
10
+ color: AgentModeDisplayColor;
11
+ }
12
+
13
+ let currentAgentMode: AgentModeChangedPayload | null = null;
14
+
15
+ function isPayload(value: unknown): value is AgentModeChangedPayload {
16
+ if (!value || typeof value !== "object") return false;
17
+ const payload = value as Partial<AgentModeChangedPayload>;
18
+ return (
19
+ (payload.mode === "agent" ||
20
+ payload.mode === "plan" ||
21
+ payload.mode === "execute") &&
22
+ typeof payload.label === "string" &&
23
+ (payload.color === "dim" ||
24
+ payload.color === "accent" ||
25
+ payload.color === "warning")
26
+ );
27
+ }
28
+
29
+ export function getAgentModeBadge(): AgentModeChangedPayload | null {
30
+ return currentAgentMode;
31
+ }
32
+
33
+ export function formatAgentModeSuffix(
34
+ payload: AgentModeChangedPayload | null,
35
+ theme: Theme,
36
+ ): string {
37
+ if (!payload || payload.mode === "agent") return "";
38
+ return theme.fg(payload.color, ` · ${payload.label}`);
39
+ }
40
+
41
+ export function registerAgentModeBadge(
42
+ pi: ExtensionAPI,
43
+ requestRender: () => void,
44
+ ): () => void {
45
+ const unsubChanged = pi.events.on(AGENT_MODE_CHANGED, (value) => {
46
+ if (!isPayload(value)) return;
47
+ currentAgentMode = value;
48
+ requestRender();
49
+ });
50
+
51
+ pi.on("session_shutdown", () => {
52
+ currentAgentMode = null;
53
+ });
54
+
55
+ return unsubChanged;
56
+ }
57
+
58
+ export function resetAgentModeBadgeForTests(): void {
59
+ currentAgentMode = null;
60
+ }
@@ -8,12 +8,13 @@ import type { Component, EditorTheme, TUI } from "@earendil-works/pi-tui";
8
8
  import type { UiEnhancementsSettings } from "../config.ts";
9
9
  import { loadUiEnhancementsSettings } from "../config.ts";
10
10
  import { shortenPath } from "../utils/shorten-path.ts";
11
- import { fitBorder } from "./format-border.ts";
12
11
  import {
13
12
  formatAgentModeSuffix,
14
13
  getAgentModeBadge,
15
14
  registerAgentModeBadge,
16
15
  } from "./agent-mode-badge.ts";
16
+ import { fitBorder } from "./format-border.ts";
17
+ import { attachResizeRecovery } from "./resize-recovery.ts";
17
18
 
18
19
  type GetSettings = () => UiEnhancementsSettings;
19
20
 
@@ -46,6 +47,7 @@ export function registerBorderStatusBar(
46
47
  let spinnerIndex = 0;
47
48
  let spinnerTimer: ReturnType<typeof setInterval> | undefined;
48
49
  let activeTui: TUI | undefined;
50
+ let detachResizeRecovery: (() => void) | undefined;
49
51
  const spinnerFrames = ["⠋", "⠙", "⠹", "⠸", "⠼", "⠴", "⠦", "⠧", "⠇", "⠏"];
50
52
 
51
53
  const stopSpinner = () => {
@@ -55,6 +57,11 @@ export function registerBorderStatusBar(
55
57
  }
56
58
  };
57
59
 
60
+ const stopResizeRecovery = () => {
61
+ detachResizeRecovery?.();
62
+ detachResizeRecovery = undefined;
63
+ };
64
+
58
65
  pi.on("agent_start", () => {
59
66
  isWorking = true;
60
67
  stopSpinner();
@@ -73,6 +80,7 @@ export function registerBorderStatusBar(
73
80
 
74
81
  pi.on("session_shutdown", () => {
75
82
  stopSpinner();
83
+ stopResizeRecovery();
76
84
  activeTui = undefined;
77
85
  });
78
86
 
@@ -84,6 +92,11 @@ export function registerBorderStatusBar(
84
92
  const settings = loadUiEnhancementsSettings(ctx.cwd);
85
93
  if (!settings.borderStatusBar || !ctx.hasUI || ctx.mode !== "tui") return;
86
94
 
95
+ stopResizeRecovery();
96
+ detachResizeRecovery = attachResizeRecovery({
97
+ getTarget: () => activeTui,
98
+ });
99
+
87
100
  ctx.ui.setWorkingVisible(false);
88
101
  ctx.ui.setFooter(() => new EmptyFooter());
89
102
 
@@ -0,0 +1,63 @@
1
+ /** Debounce window after the last resize event before forcing a full redraw. */
2
+ export const RESIZE_RECOVERY_DEBOUNCE_MS = 150;
3
+
4
+ export type ResizeRecoveryTarget = {
5
+ invalidate(): void;
6
+ requestRender(force?: boolean): void;
7
+ };
8
+
9
+ export type ResizeRecoveryOptions = {
10
+ debounceMs?: number;
11
+ getColumns?: () => number | undefined;
12
+ getRows?: () => number | undefined;
13
+ getTarget?: () => ResizeRecoveryTarget | undefined;
14
+ on?: (event: "resize", listener: () => void) => void;
15
+ off?: (event: "resize", listener: () => void) => void;
16
+ };
17
+
18
+ /**
19
+ * After terminal resize settles, force a full TUI invalidate+redraw.
20
+ * Skips frames where columns/rows are falsy (Windows can briefly report 0).
21
+ */
22
+ export function attachResizeRecovery(
23
+ options: ResizeRecoveryOptions = {},
24
+ ): () => void {
25
+ const debounceMs = options.debounceMs ?? RESIZE_RECOVERY_DEBOUNCE_MS;
26
+ const getColumns = options.getColumns ?? (() => process.stdout.columns);
27
+ const getRows = options.getRows ?? (() => process.stdout.rows);
28
+ const getTarget = options.getTarget ?? (() => undefined);
29
+ const on =
30
+ options.on ??
31
+ ((event, listener) => {
32
+ process.stdout.on(event, listener);
33
+ });
34
+ const off =
35
+ options.off ??
36
+ ((event, listener) => {
37
+ process.stdout.off(event, listener);
38
+ });
39
+
40
+ let timer: ReturnType<typeof setTimeout> | undefined;
41
+
42
+ const onResize = () => {
43
+ if (timer) clearTimeout(timer);
44
+ timer = setTimeout(() => {
45
+ timer = undefined;
46
+ const cols = getColumns();
47
+ const rows = getRows();
48
+ if (!cols || !rows) return;
49
+ const target = getTarget();
50
+ if (!target) return;
51
+ target.invalidate();
52
+ target.requestRender(true);
53
+ }, debounceMs);
54
+ };
55
+
56
+ on("resize", onResize);
57
+
58
+ return () => {
59
+ if (timer) clearTimeout(timer);
60
+ timer = undefined;
61
+ off("resize", onResize);
62
+ };
63
+ }
@@ -1,35 +1,35 @@
1
- import { describe, expect, it } from "vitest";
2
- import {
3
- formatAgentModeSuffix,
4
- getAgentModeBadge,
5
- resetAgentModeBadgeForTests,
6
- } from "../src/chrome/agent-mode-badge.ts";
7
-
8
- describe("agent-mode-badge", () => {
9
- it("omits suffix for agent mode", () => {
10
- resetAgentModeBadgeForTests();
11
- expect(getAgentModeBadge()).toBeNull();
12
- const theme = {
13
- fg: (_color: string, text: string) => text,
14
- };
15
- expect(formatAgentModeSuffix(null, theme as never)).toBe("");
16
- });
17
-
18
- it("formats plan and execute suffixes", () => {
19
- const theme = {
20
- fg: (_color: string, text: string) => text,
21
- };
22
- expect(
23
- formatAgentModeSuffix(
24
- { mode: "plan", label: "plan", color: "accent" },
25
- theme as never,
26
- ),
27
- ).toBe(" · plan");
28
- expect(
29
- formatAgentModeSuffix(
30
- { mode: "execute", label: "execute", color: "warning" },
31
- theme as never,
32
- ),
33
- ).toBe(" · execute");
34
- });
35
- });
1
+ import { describe, expect, it } from "vitest";
2
+ import {
3
+ formatAgentModeSuffix,
4
+ getAgentModeBadge,
5
+ resetAgentModeBadgeForTests,
6
+ } from "../src/chrome/agent-mode-badge.ts";
7
+
8
+ describe("agent-mode-badge", () => {
9
+ it("omits suffix for agent mode", () => {
10
+ resetAgentModeBadgeForTests();
11
+ expect(getAgentModeBadge()).toBeNull();
12
+ const theme = {
13
+ fg: (_color: string, text: string) => text,
14
+ };
15
+ expect(formatAgentModeSuffix(null, theme as never)).toBe("");
16
+ });
17
+
18
+ it("formats plan and execute suffixes", () => {
19
+ const theme = {
20
+ fg: (_color: string, text: string) => text,
21
+ };
22
+ expect(
23
+ formatAgentModeSuffix(
24
+ { mode: "plan", label: "plan", color: "accent" },
25
+ theme as never,
26
+ ),
27
+ ).toBe(" · plan");
28
+ expect(
29
+ formatAgentModeSuffix(
30
+ { mode: "execute", label: "execute", color: "warning" },
31
+ theme as never,
32
+ ),
33
+ ).toBe(" · execute");
34
+ });
35
+ });
@@ -0,0 +1,135 @@
1
+ import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
2
+ import {
3
+ attachResizeRecovery,
4
+ RESIZE_RECOVERY_DEBOUNCE_MS,
5
+ } from "../src/chrome/resize-recovery.ts";
6
+
7
+ describe("attachResizeRecovery", () => {
8
+ beforeEach(() => {
9
+ vi.useFakeTimers();
10
+ });
11
+
12
+ afterEach(() => {
13
+ vi.useRealTimers();
14
+ });
15
+
16
+ it("debounces resize and forces invalidate + full render", () => {
17
+ const listeners = new Map<string, Set<() => void>>();
18
+ const target = {
19
+ invalidate: vi.fn(),
20
+ requestRender: vi.fn(),
21
+ };
22
+ const columns = 120;
23
+ const rows = 40;
24
+
25
+ const detach = attachResizeRecovery({
26
+ getColumns: () => columns,
27
+ getRows: () => rows,
28
+ getTarget: () => target,
29
+ on: (event, listener) => {
30
+ const set = listeners.get(event) ?? new Set();
31
+ set.add(listener);
32
+ listeners.set(event, set);
33
+ },
34
+ off: (event, listener) => {
35
+ listeners.get(event)?.delete(listener);
36
+ },
37
+ });
38
+
39
+ const fire = () => {
40
+ for (const listener of listeners.get("resize") ?? []) listener();
41
+ };
42
+
43
+ fire();
44
+ fire();
45
+ expect(target.invalidate).not.toHaveBeenCalled();
46
+
47
+ vi.advanceTimersByTime(RESIZE_RECOVERY_DEBOUNCE_MS - 1);
48
+ expect(target.invalidate).not.toHaveBeenCalled();
49
+
50
+ vi.advanceTimersByTime(1);
51
+ expect(target.invalidate).toHaveBeenCalledOnce();
52
+ expect(target.requestRender).toHaveBeenCalledOnce();
53
+ expect(target.requestRender).toHaveBeenCalledWith(true);
54
+
55
+ detach();
56
+ });
57
+
58
+ it("skips recovery when columns or rows are falsy", () => {
59
+ const listeners = new Map<string, Set<() => void>>();
60
+ const target = {
61
+ invalidate: vi.fn(),
62
+ requestRender: vi.fn(),
63
+ };
64
+ let columns: number | undefined = 0;
65
+ let rows: number | undefined = 40;
66
+
67
+ attachResizeRecovery({
68
+ getColumns: () => columns,
69
+ getRows: () => rows,
70
+ getTarget: () => target,
71
+ on: (event, listener) => {
72
+ const set = listeners.get(event) ?? new Set();
73
+ set.add(listener);
74
+ listeners.set(event, set);
75
+ },
76
+ off: (event, listener) => {
77
+ listeners.get(event)?.delete(listener);
78
+ },
79
+ });
80
+
81
+ const fire = () => {
82
+ for (const listener of listeners.get("resize") ?? []) listener();
83
+ };
84
+
85
+ fire();
86
+ vi.advanceTimersByTime(RESIZE_RECOVERY_DEBOUNCE_MS);
87
+ expect(target.invalidate).not.toHaveBeenCalled();
88
+
89
+ columns = 100;
90
+ rows = undefined;
91
+ fire();
92
+ vi.advanceTimersByTime(RESIZE_RECOVERY_DEBOUNCE_MS);
93
+ expect(target.invalidate).not.toHaveBeenCalled();
94
+
95
+ columns = 100;
96
+ rows = 30;
97
+ fire();
98
+ vi.advanceTimersByTime(RESIZE_RECOVERY_DEBOUNCE_MS);
99
+ expect(target.invalidate).toHaveBeenCalledOnce();
100
+ expect(target.requestRender).toHaveBeenCalledWith(true);
101
+ });
102
+
103
+ it("removes the listener and cancels pending timers on detach", () => {
104
+ const listeners = new Map<string, Set<() => void>>();
105
+ const target = {
106
+ invalidate: vi.fn(),
107
+ requestRender: vi.fn(),
108
+ };
109
+
110
+ const detach = attachResizeRecovery({
111
+ getColumns: () => 80,
112
+ getRows: () => 24,
113
+ getTarget: () => target,
114
+ on: (event, listener) => {
115
+ const set = listeners.get(event) ?? new Set();
116
+ set.add(listener);
117
+ listeners.set(event, set);
118
+ },
119
+ off: (event, listener) => {
120
+ listeners.get(event)?.delete(listener);
121
+ },
122
+ });
123
+
124
+ const fire = () => {
125
+ for (const listener of listeners.get("resize") ?? []) listener();
126
+ };
127
+
128
+ fire();
129
+ detach();
130
+ expect(listeners.get("resize")?.size ?? 0).toBe(0);
131
+
132
+ vi.advanceTimersByTime(RESIZE_RECOVERY_DEBOUNCE_MS);
133
+ expect(target.invalidate).not.toHaveBeenCalled();
134
+ });
135
+ });
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vitos-pizza/websearch",
3
- "version": "0.1.0",
3
+ "version": "0.2.0",
4
4
  "description": "Web search and URL reading for Vito's Pizzeria Pi distribution",
5
5
  "type": "module",
6
6
  "license": "MIT",
File without changes
File without changes
File without changes
File without changes
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vitos-pizza/vitos-pizza",
3
- "version": "0.1.0",
3
+ "version": "0.2.0",
4
4
  "description": "Vito's Pizzeria — a Pi distribution (Garfield-approved)",
5
5
  "publishConfig": {
6
6
  "access": "public",
@@ -37,14 +37,15 @@
37
37
  "typescript": "^5.8.0"
38
38
  },
39
39
  "dependencies": {
40
- "@vitos-pizza/agent-mode": "0.1.0",
41
- "@vitos-pizza/keybindings": "0.1.0",
42
- "@vitos-pizza/permission-system": "0.1.0",
43
- "@vitos-pizza/question": "0.1.0",
44
- "@vitos-pizza/session-title": "0.1.0",
45
- "@vitos-pizza/subagents": "0.1.0",
46
- "@vitos-pizza/ui-enhancements": "0.1.0",
47
- "@vitos-pizza/websearch": "0.1.0"
40
+ "@vitos-pizza/agent-mode": "0.2.0",
41
+ "@vitos-pizza/keybindings": "0.2.0",
42
+ "@vitos-pizza/permission-system": "0.2.0",
43
+ "@vitos-pizza/question": "0.2.0",
44
+ "@vitos-pizza/session-title": "0.2.0",
45
+ "@vitos-pizza/subagents": "0.2.0",
46
+ "@vitos-pizza/todoist": "0.2.0",
47
+ "@vitos-pizza/ui-enhancements": "0.2.0",
48
+ "@vitos-pizza/websearch": "0.2.0"
48
49
  },
49
50
  "bundledDependencies": [
50
51
  "@vitos-pizza/agent-mode",
@@ -66,6 +67,7 @@
66
67
  "node_modules/@vitos-pizza/subagents/extensions",
67
68
  "node_modules/@vitos-pizza/websearch/extensions",
68
69
  "node_modules/@vitos-pizza/session-title/extensions",
70
+ "node_modules/@vitos-pizza/todoist/extensions",
69
71
  "node_modules/@vitos-pizza/keybindings/extensions"
70
72
  ],
71
73
  "skills": [