gencode-ai 0.1.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 (274) hide show
  1. package/.env.example +11 -0
  2. package/CLAUDE.md +70 -0
  3. package/LICENSE +21 -0
  4. package/README.md +117 -0
  5. package/dist/agent/agent.d.ts +84 -0
  6. package/dist/agent/agent.d.ts.map +1 -0
  7. package/dist/agent/agent.js +233 -0
  8. package/dist/agent/agent.js.map +1 -0
  9. package/dist/agent/index.d.ts +6 -0
  10. package/dist/agent/index.d.ts.map +1 -0
  11. package/dist/agent/index.js +6 -0
  12. package/dist/agent/index.js.map +1 -0
  13. package/dist/agent/types.d.ts +47 -0
  14. package/dist/agent/types.d.ts.map +1 -0
  15. package/dist/agent/types.js +5 -0
  16. package/dist/agent/types.js.map +1 -0
  17. package/dist/cli/components/App.d.ts +14 -0
  18. package/dist/cli/components/App.d.ts.map +1 -0
  19. package/dist/cli/components/App.js +395 -0
  20. package/dist/cli/components/App.js.map +1 -0
  21. package/dist/cli/components/CommandSuggestions.d.ts +13 -0
  22. package/dist/cli/components/CommandSuggestions.d.ts.map +1 -0
  23. package/dist/cli/components/CommandSuggestions.js +32 -0
  24. package/dist/cli/components/CommandSuggestions.js.map +1 -0
  25. package/dist/cli/components/Header.d.ts +9 -0
  26. package/dist/cli/components/Header.d.ts.map +1 -0
  27. package/dist/cli/components/Header.js +13 -0
  28. package/dist/cli/components/Header.js.map +1 -0
  29. package/dist/cli/components/Input.d.ts +13 -0
  30. package/dist/cli/components/Input.d.ts.map +1 -0
  31. package/dist/cli/components/Input.js +27 -0
  32. package/dist/cli/components/Input.js.map +1 -0
  33. package/dist/cli/components/Logo.d.ts +2 -0
  34. package/dist/cli/components/Logo.d.ts.map +1 -0
  35. package/dist/cli/components/Logo.js +8 -0
  36. package/dist/cli/components/Logo.js.map +1 -0
  37. package/dist/cli/components/Messages.d.ts +37 -0
  38. package/dist/cli/components/Messages.d.ts.map +1 -0
  39. package/dist/cli/components/Messages.js +106 -0
  40. package/dist/cli/components/Messages.js.map +1 -0
  41. package/dist/cli/components/ModelSelector.d.ts +13 -0
  42. package/dist/cli/components/ModelSelector.d.ts.map +1 -0
  43. package/dist/cli/components/ModelSelector.js +72 -0
  44. package/dist/cli/components/ModelSelector.js.map +1 -0
  45. package/dist/cli/components/Spinner.d.ts +12 -0
  46. package/dist/cli/components/Spinner.d.ts.map +1 -0
  47. package/dist/cli/components/Spinner.js +45 -0
  48. package/dist/cli/components/Spinner.js.map +1 -0
  49. package/dist/cli/components/index.d.ts +12 -0
  50. package/dist/cli/components/index.d.ts.map +1 -0
  51. package/dist/cli/components/index.js +12 -0
  52. package/dist/cli/components/index.js.map +1 -0
  53. package/dist/cli/components/theme.d.ts +31 -0
  54. package/dist/cli/components/theme.d.ts.map +1 -0
  55. package/dist/cli/components/theme.js +36 -0
  56. package/dist/cli/components/theme.js.map +1 -0
  57. package/dist/cli/index-legacy.d.ts +7 -0
  58. package/dist/cli/index-legacy.d.ts.map +1 -0
  59. package/dist/cli/index-legacy.js +431 -0
  60. package/dist/cli/index-legacy.js.map +1 -0
  61. package/dist/cli/index.d.ts +7 -0
  62. package/dist/cli/index.d.ts.map +1 -0
  63. package/dist/cli/index.js +116 -0
  64. package/dist/cli/index.js.map +1 -0
  65. package/dist/cli/ink-cli.d.ts +7 -0
  66. package/dist/cli/ink-cli.d.ts.map +1 -0
  67. package/dist/cli/ink-cli.js +105 -0
  68. package/dist/cli/ink-cli.js.map +1 -0
  69. package/dist/cli/session-picker.d.ts +16 -0
  70. package/dist/cli/session-picker.d.ts.map +1 -0
  71. package/dist/cli/session-picker.js +280 -0
  72. package/dist/cli/session-picker.js.map +1 -0
  73. package/dist/cli/ui.d.ts +61 -0
  74. package/dist/cli/ui.d.ts.map +1 -0
  75. package/dist/cli/ui.js +364 -0
  76. package/dist/cli/ui.js.map +1 -0
  77. package/dist/config/index.d.ts +7 -0
  78. package/dist/config/index.d.ts.map +1 -0
  79. package/dist/config/index.js +6 -0
  80. package/dist/config/index.js.map +1 -0
  81. package/dist/config/manager.d.ts +31 -0
  82. package/dist/config/manager.d.ts.map +1 -0
  83. package/dist/config/manager.js +65 -0
  84. package/dist/config/manager.js.map +1 -0
  85. package/dist/config/types.d.ts +22 -0
  86. package/dist/config/types.d.ts.map +1 -0
  87. package/dist/config/types.js +6 -0
  88. package/dist/config/types.js.map +1 -0
  89. package/dist/index.d.ts +12 -0
  90. package/dist/index.d.ts.map +1 -0
  91. package/dist/index.js +21 -0
  92. package/dist/index.js.map +1 -0
  93. package/dist/memory/index.d.ts +10 -0
  94. package/dist/memory/index.d.ts.map +1 -0
  95. package/dist/memory/index.js +9 -0
  96. package/dist/memory/index.js.map +1 -0
  97. package/dist/memory/init.d.ts +20 -0
  98. package/dist/memory/init.d.ts.map +1 -0
  99. package/dist/memory/init.js +332 -0
  100. package/dist/memory/init.js.map +1 -0
  101. package/dist/memory/manager.d.ts +85 -0
  102. package/dist/memory/manager.d.ts.map +1 -0
  103. package/dist/memory/manager.js +234 -0
  104. package/dist/memory/manager.js.map +1 -0
  105. package/dist/memory/types.d.ts +74 -0
  106. package/dist/memory/types.d.ts.map +1 -0
  107. package/dist/memory/types.js +6 -0
  108. package/dist/memory/types.js.map +1 -0
  109. package/dist/permissions/index.d.ts +7 -0
  110. package/dist/permissions/index.d.ts.map +1 -0
  111. package/dist/permissions/index.js +6 -0
  112. package/dist/permissions/index.js.map +1 -0
  113. package/dist/permissions/manager.d.ts +32 -0
  114. package/dist/permissions/manager.d.ts.map +1 -0
  115. package/dist/permissions/manager.js +79 -0
  116. package/dist/permissions/manager.js.map +1 -0
  117. package/dist/permissions/types.d.ts +14 -0
  118. package/dist/permissions/types.d.ts.map +1 -0
  119. package/dist/permissions/types.js +17 -0
  120. package/dist/permissions/types.js.map +1 -0
  121. package/dist/providers/anthropic.d.ts +20 -0
  122. package/dist/providers/anthropic.d.ts.map +1 -0
  123. package/dist/providers/anthropic.js +185 -0
  124. package/dist/providers/anthropic.js.map +1 -0
  125. package/dist/providers/gemini.d.ts +21 -0
  126. package/dist/providers/gemini.d.ts.map +1 -0
  127. package/dist/providers/gemini.js +241 -0
  128. package/dist/providers/gemini.js.map +1 -0
  129. package/dist/providers/index.d.ts +34 -0
  130. package/dist/providers/index.d.ts.map +1 -0
  131. package/dist/providers/index.js +72 -0
  132. package/dist/providers/index.js.map +1 -0
  133. package/dist/providers/openai.d.ts +19 -0
  134. package/dist/providers/openai.d.ts.map +1 -0
  135. package/dist/providers/openai.js +221 -0
  136. package/dist/providers/openai.js.map +1 -0
  137. package/dist/providers/types.d.ts +125 -0
  138. package/dist/providers/types.d.ts.map +1 -0
  139. package/dist/providers/types.js +6 -0
  140. package/dist/providers/types.js.map +1 -0
  141. package/dist/session/index.d.ts +6 -0
  142. package/dist/session/index.d.ts.map +1 -0
  143. package/dist/session/index.js +6 -0
  144. package/dist/session/index.js.map +1 -0
  145. package/dist/session/manager.d.ts +101 -0
  146. package/dist/session/manager.d.ts.map +1 -0
  147. package/dist/session/manager.js +295 -0
  148. package/dist/session/manager.js.map +1 -0
  149. package/dist/session/types.d.ts +39 -0
  150. package/dist/session/types.d.ts.map +1 -0
  151. package/dist/session/types.js +10 -0
  152. package/dist/session/types.js.map +1 -0
  153. package/dist/tools/builtin/bash.d.ts +7 -0
  154. package/dist/tools/builtin/bash.d.ts.map +1 -0
  155. package/dist/tools/builtin/bash.js +80 -0
  156. package/dist/tools/builtin/bash.js.map +1 -0
  157. package/dist/tools/builtin/edit.d.ts +7 -0
  158. package/dist/tools/builtin/edit.d.ts.map +1 -0
  159. package/dist/tools/builtin/edit.js +32 -0
  160. package/dist/tools/builtin/edit.js.map +1 -0
  161. package/dist/tools/builtin/glob.d.ts +7 -0
  162. package/dist/tools/builtin/glob.d.ts.map +1 -0
  163. package/dist/tools/builtin/glob.js +36 -0
  164. package/dist/tools/builtin/glob.js.map +1 -0
  165. package/dist/tools/builtin/grep.d.ts +7 -0
  166. package/dist/tools/builtin/grep.d.ts.map +1 -0
  167. package/dist/tools/builtin/grep.js +59 -0
  168. package/dist/tools/builtin/grep.js.map +1 -0
  169. package/dist/tools/builtin/read.d.ts +7 -0
  170. package/dist/tools/builtin/read.d.ts.map +1 -0
  171. package/dist/tools/builtin/read.js +29 -0
  172. package/dist/tools/builtin/read.js.map +1 -0
  173. package/dist/tools/builtin/write.d.ts +7 -0
  174. package/dist/tools/builtin/write.d.ts.map +1 -0
  175. package/dist/tools/builtin/write.js +24 -0
  176. package/dist/tools/builtin/write.js.map +1 -0
  177. package/dist/tools/index.d.ts +38 -0
  178. package/dist/tools/index.d.ts.map +1 -0
  179. package/dist/tools/index.js +32 -0
  180. package/dist/tools/index.js.map +1 -0
  181. package/dist/tools/registry.d.ts +22 -0
  182. package/dist/tools/registry.d.ts.map +1 -0
  183. package/dist/tools/registry.js +71 -0
  184. package/dist/tools/registry.js.map +1 -0
  185. package/dist/tools/types.d.ts +62 -0
  186. package/dist/tools/types.d.ts.map +1 -0
  187. package/dist/tools/types.js +126 -0
  188. package/dist/tools/types.js.map +1 -0
  189. package/docs/README.md +16 -0
  190. package/docs/proposals/0001-web-fetch-tool.md +293 -0
  191. package/docs/proposals/0002-web-search-tool.md +306 -0
  192. package/docs/proposals/0003-task-subagents.md +333 -0
  193. package/docs/proposals/0004-plan-mode.md +338 -0
  194. package/docs/proposals/0005-todo-system.md +299 -0
  195. package/docs/proposals/0006-memory-system.md +539 -0
  196. package/docs/proposals/0007-context-management.md +429 -0
  197. package/docs/proposals/0008-checkpointing.md +327 -0
  198. package/docs/proposals/0009-hooks-system.md +343 -0
  199. package/docs/proposals/0010-mcp-integration.md +382 -0
  200. package/docs/proposals/0011-custom-commands.md +374 -0
  201. package/docs/proposals/0012-ask-user-question.md +317 -0
  202. package/docs/proposals/0013-multi-edit-tool.md +345 -0
  203. package/docs/proposals/0014-lsp-tool.md +478 -0
  204. package/docs/proposals/0015-ls-tool.md +407 -0
  205. package/docs/proposals/0016-kill-shell-tool.md +455 -0
  206. package/docs/proposals/0017-background-tasks.md +489 -0
  207. package/docs/proposals/0018-parallel-tool-execution.md +415 -0
  208. package/docs/proposals/0019-session-enhancements.md +462 -0
  209. package/docs/proposals/0020-session-summarization.md +447 -0
  210. package/docs/proposals/0021-skills-system.md +409 -0
  211. package/docs/proposals/0022-plugin-system.md +467 -0
  212. package/docs/proposals/0023-permission-enhancements.md +470 -0
  213. package/docs/proposals/0024-keyboard-shortcuts.md +443 -0
  214. package/docs/proposals/0025-cost-tracking.md +447 -0
  215. package/docs/proposals/0026-git-integration.md +475 -0
  216. package/docs/proposals/0027-enhanced-read-tool.md +514 -0
  217. package/docs/proposals/0028-enhanced-bash-tool.md +511 -0
  218. package/docs/proposals/0029-notebook-edit-tool.md +413 -0
  219. package/docs/proposals/0030-plugin-marketplace.md +360 -0
  220. package/docs/proposals/0031-command-suggestions.md +295 -0
  221. package/docs/proposals/0032-ide-integrations.md +328 -0
  222. package/docs/proposals/0033-enterprise-deployment.md +221 -0
  223. package/docs/proposals/0034-sandboxing.md +273 -0
  224. package/docs/proposals/0035-auto-updater.md +311 -0
  225. package/docs/proposals/0036-enhanced-glob-tool.md +267 -0
  226. package/docs/proposals/0037-enhanced-grep-tool.md +360 -0
  227. package/docs/proposals/0038-interactive-cli-ui.md +373 -0
  228. package/docs/proposals/0039-streaming-enhancements.md +359 -0
  229. package/docs/proposals/0040-multi-provider-enhancements.md +369 -0
  230. package/docs/proposals/README.md +84 -0
  231. package/docs/proposals/TEMPLATE.md +57 -0
  232. package/docs/proposals/research/claude-code-research.md +307 -0
  233. package/examples/agent-demo.ts +115 -0
  234. package/examples/basic.ts +166 -0
  235. package/package.json +50 -0
  236. package/src/agent/agent.ts +276 -0
  237. package/src/agent/index.ts +6 -0
  238. package/src/agent/types.ts +62 -0
  239. package/src/cli/components/App.tsx +565 -0
  240. package/src/cli/components/CommandSuggestions.tsx +58 -0
  241. package/src/cli/components/Header.tsx +36 -0
  242. package/src/cli/components/Input.tsx +60 -0
  243. package/src/cli/components/Logo.tsx +16 -0
  244. package/src/cli/components/Messages.tsx +210 -0
  245. package/src/cli/components/ModelSelector.tsx +135 -0
  246. package/src/cli/components/Spinner.tsx +72 -0
  247. package/src/cli/components/index.ts +21 -0
  248. package/src/cli/components/theme.ts +36 -0
  249. package/src/cli/index.tsx +136 -0
  250. package/src/config/index.ts +7 -0
  251. package/src/config/manager.ts +77 -0
  252. package/src/config/types.ts +25 -0
  253. package/src/index.ts +86 -0
  254. package/src/permissions/index.ts +7 -0
  255. package/src/permissions/manager.ts +97 -0
  256. package/src/permissions/types.ts +29 -0
  257. package/src/providers/anthropic.ts +224 -0
  258. package/src/providers/gemini.ts +295 -0
  259. package/src/providers/index.ts +97 -0
  260. package/src/providers/openai.ts +261 -0
  261. package/src/providers/types.ts +181 -0
  262. package/src/session/index.ts +6 -0
  263. package/src/session/manager.ts +354 -0
  264. package/src/session/types.ts +49 -0
  265. package/src/tools/builtin/bash.ts +92 -0
  266. package/src/tools/builtin/edit.ts +37 -0
  267. package/src/tools/builtin/glob.ts +42 -0
  268. package/src/tools/builtin/grep.ts +67 -0
  269. package/src/tools/builtin/read.ts +34 -0
  270. package/src/tools/builtin/write.ts +27 -0
  271. package/src/tools/index.ts +36 -0
  272. package/src/tools/registry.ts +83 -0
  273. package/src/tools/types.ts +172 -0
  274. package/tsconfig.json +21 -0
@@ -0,0 +1,327 @@
1
+ # Proposal: Checkpointing (Edit Undo/Rewind)
2
+
3
+ - **Proposal ID**: 0008
4
+ - **Author**: mycode team
5
+ - **Status**: Draft
6
+ - **Created**: 2025-01-15
7
+ - **Updated**: 2025-01-15
8
+
9
+ ## Summary
10
+
11
+ Implement a checkpointing system that tracks all file changes made by the agent and enables users to rewind/undo unwanted modifications. This provides a safety net for experimentation and quick recovery from undesired changes.
12
+
13
+ ## Motivation
14
+
15
+ Currently, mycode makes irreversible file changes. This leads to:
16
+
17
+ 1. **Fear of damage**: Users hesitant to let agent modify files
18
+ 2. **Manual recovery**: Must use git or backups to undo changes
19
+ 3. **Lost work**: Accidental overwrites can't be recovered
20
+ 4. **No visibility**: Can't see what files were changed
21
+ 5. **No experimentation**: Can't easily try approaches and revert
22
+
23
+ A checkpointing system enables safe experimentation with easy rollback.
24
+
25
+ ## Claude Code Reference
26
+
27
+ Claude Code provides automatic checkpointing:
28
+
29
+ ### Key Features
30
+ - Automatic tracking of all file edits
31
+ - `/rewind` command to undo changes
32
+ - Change history visible in session
33
+ - Per-file and bulk rollback options
34
+ - Integration with git (commits as checkpoints)
35
+
36
+ ### Example Usage
37
+ ```
38
+ Agent: [Makes several file changes]
39
+ - Modified src/auth.ts
40
+ - Created src/middleware.ts
41
+ - Modified package.json
42
+
43
+ User: Actually, I don't like that approach. Undo those changes.
44
+
45
+ Agent: I'll rewind the file changes.
46
+ [Reverting 3 file changes...]
47
+ - Reverted src/auth.ts
48
+ - Deleted src/middleware.ts
49
+ - Reverted package.json
50
+
51
+ Changes have been undone.
52
+ ```
53
+
54
+ ### Change Tracking Display
55
+ ```
56
+ Session Changes:
57
+ [1] src/auth.ts (modified) - 10 minutes ago
58
+ [2] src/middleware.ts (created) - 8 minutes ago
59
+ [3] package.json (modified) - 5 minutes ago
60
+
61
+ Use /rewind [number] to undo specific changes
62
+ Use /rewind all to undo all changes
63
+ ```
64
+
65
+ ## Detailed Design
66
+
67
+ ### API Design
68
+
69
+ ```typescript
70
+ // src/checkpointing/types.ts
71
+ type ChangeType = 'create' | 'modify' | 'delete';
72
+
73
+ interface FileCheckpoint {
74
+ id: string;
75
+ path: string;
76
+ changeType: ChangeType;
77
+ timestamp: Date;
78
+ previousContent: string | null; // null for create
79
+ newContent: string | null; // null for delete
80
+ toolName: string; // Which tool made the change
81
+ }
82
+
83
+ interface CheckpointSession {
84
+ id: string;
85
+ sessionId: string;
86
+ checkpoints: FileCheckpoint[];
87
+ createdAt: Date;
88
+ }
89
+
90
+ interface RewindOptions {
91
+ checkpointId?: string; // Specific checkpoint
92
+ path?: string; // Specific file
93
+ all?: boolean; // All changes
94
+ count?: number; // Last N changes
95
+ }
96
+
97
+ interface RewindResult {
98
+ success: boolean;
99
+ revertedFiles: string[];
100
+ errors: Array<{ path: string; error: string }>;
101
+ }
102
+ ```
103
+
104
+ ```typescript
105
+ // src/checkpointing/checkpoint-manager.ts
106
+ class CheckpointManager {
107
+ private session: CheckpointSession;
108
+
109
+ constructor(sessionId: string);
110
+
111
+ // Record a file change
112
+ recordChange(change: Omit<FileCheckpoint, 'id' | 'timestamp'>): void;
113
+
114
+ // Get all checkpoints
115
+ getCheckpoints(): FileCheckpoint[];
116
+
117
+ // Get changes for a specific file
118
+ getFileHistory(path: string): FileCheckpoint[];
119
+
120
+ // Rewind changes
121
+ async rewind(options: RewindOptions): Promise<RewindResult>;
122
+
123
+ // Get summary of changes
124
+ getSummary(): { created: number; modified: number; deleted: number };
125
+
126
+ // Clear checkpoints (e.g., after git commit)
127
+ clearCheckpoints(): void;
128
+ }
129
+ ```
130
+
131
+ ### Implementation Approach
132
+
133
+ 1. **Tool Hooking**: Intercept Write and Edit tool executions
134
+ 2. **Pre-Change Capture**: Store file content before modification
135
+ 3. **Change Recording**: Log all changes with metadata
136
+ 4. **Rewind Logic**: Apply inverse operations to restore state
137
+ 5. **Persistence**: Store checkpoints in session data
138
+ 6. **Git Integration**: Option to use git for versioning
139
+
140
+ ```typescript
141
+ // Wrapping tools with checkpoint tracking
142
+ function withCheckpointing(tool: Tool, checkpointManager: CheckpointManager): Tool {
143
+ return {
144
+ ...tool,
145
+ execute: async (input, context) => {
146
+ // Capture pre-change state
147
+ let previousContent: string | null = null;
148
+ if (tool.name === 'Write' || tool.name === 'Edit') {
149
+ previousContent = await safeReadFile(input.file_path);
150
+ }
151
+
152
+ // Execute original tool
153
+ const result = await tool.execute(input, context);
154
+
155
+ // Record checkpoint on success
156
+ if (result.success) {
157
+ const newContent = await safeReadFile(input.file_path);
158
+ checkpointManager.recordChange({
159
+ path: input.file_path,
160
+ changeType: previousContent === null ? 'create' : 'modify',
161
+ previousContent,
162
+ newContent,
163
+ toolName: tool.name
164
+ });
165
+ }
166
+
167
+ return result;
168
+ }
169
+ };
170
+ }
171
+ ```
172
+
173
+ ### Rewind Command
174
+
175
+ ```typescript
176
+ // src/commands/rewind-command.ts
177
+ async function rewindCommand(args: string[], context: CommandContext): Promise<void> {
178
+ const { checkpointManager, ui } = context;
179
+
180
+ if (args[0] === 'all') {
181
+ const result = await checkpointManager.rewind({ all: true });
182
+ ui.showMessage(`Reverted ${result.revertedFiles.length} files`);
183
+ } else if (args[0]) {
184
+ const checkpointId = args[0];
185
+ const result = await checkpointManager.rewind({ checkpointId });
186
+ ui.showMessage(`Reverted: ${result.revertedFiles.join(', ')}`);
187
+ } else {
188
+ // Show change list
189
+ const checkpoints = checkpointManager.getCheckpoints();
190
+ ui.showChangeList(checkpoints);
191
+ }
192
+ }
193
+ ```
194
+
195
+ ### File Changes
196
+
197
+ | File | Action | Description |
198
+ |------|--------|-------------|
199
+ | `src/checkpointing/types.ts` | Create | Checkpoint type definitions |
200
+ | `src/checkpointing/checkpoint-manager.ts` | Create | Core checkpoint management |
201
+ | `src/checkpointing/tool-wrapper.ts` | Create | Tool wrapping for tracking |
202
+ | `src/checkpointing/index.ts` | Create | Module exports |
203
+ | `src/commands/rewind-command.ts` | Create | /rewind command |
204
+ | `src/tools/write.ts` | Modify | Add checkpoint integration |
205
+ | `src/tools/edit.ts` | Modify | Add checkpoint integration |
206
+ | `src/session/types.ts` | Modify | Add checkpoint data |
207
+
208
+ ## User Experience
209
+
210
+ ### Change Tracking Display
211
+ ```
212
+ ┌─ File Changes This Session ───────────────────┐
213
+ │ │
214
+ │ [1] 5 min ago src/auth.ts (modified) │
215
+ │ [2] 4 min ago src/middleware.ts (created) │
216
+ │ [3] 2 min ago package.json (modified) │
217
+ │ │
218
+ │ Total: 2 modified, 1 created, 0 deleted │
219
+ └───────────────────────────────────────────────┘
220
+ ```
221
+
222
+ ### Rewind Command
223
+ ```
224
+ > /rewind
225
+
226
+ Session has 3 file changes:
227
+ [1] src/auth.ts (modified) - 5 min ago
228
+ [2] src/middleware.ts (created) - 4 min ago
229
+ [3] package.json (modified) - 2 min ago
230
+
231
+ Usage:
232
+ /rewind 1 - Revert specific change
233
+ /rewind all - Revert all changes
234
+ /rewind last 2 - Revert last 2 changes
235
+ ```
236
+
237
+ ### Rewind Confirmation
238
+ ```
239
+ > /rewind all
240
+
241
+ Are you sure you want to revert 3 file changes?
242
+ - src/auth.ts (restore previous)
243
+ - src/middleware.ts (delete)
244
+ - package.json (restore previous)
245
+
246
+ [Confirm] [Cancel]
247
+ ```
248
+
249
+ ### Rewind Success
250
+ ```
251
+ ✓ Reverted 3 files:
252
+ • src/auth.ts - restored
253
+ • src/middleware.ts - deleted
254
+ • package.json - restored
255
+
256
+ Checkpoints cleared.
257
+ ```
258
+
259
+ ### Inline Change Indicator
260
+ After each file modification:
261
+ ```
262
+ Agent: [Edit] Modified src/auth.ts
263
+ (checkpoint saved - use /rewind to undo)
264
+ ```
265
+
266
+ ## Alternatives Considered
267
+
268
+ ### Alternative 1: Git-Only Versioning
269
+ Rely solely on git for undo.
270
+
271
+ **Pros**: No extra storage, standard workflow
272
+ **Cons**: Requires git, must commit to checkpoint
273
+ **Decision**: Rejected as primary - git integration as optional enhancement
274
+
275
+ ### Alternative 2: Full File Backups
276
+ Store complete file copies.
277
+
278
+ **Pros**: Simple, reliable
279
+ **Cons**: Storage intensive for large files
280
+ **Decision**: Partially adopted - store content for reasonable sizes
281
+
282
+ ### Alternative 3: Diff-Based Storage
283
+ Store only diffs between versions.
284
+
285
+ **Pros**: Space efficient
286
+ **Cons**: Complex, harder to apply reverts
287
+ **Decision**: Deferred - start simple, optimize later
288
+
289
+ ## Security Considerations
290
+
291
+ 1. **Sensitive Data**: Checkpoints may contain sensitive content
292
+ 2. **Storage Limits**: Limit total checkpoint size
293
+ 3. **Cleanup**: Clear checkpoints on session end
294
+ 4. **File Permissions**: Respect file permissions when reverting
295
+ 5. **Concurrent Access**: Handle external file modifications
296
+
297
+ ## Testing Strategy
298
+
299
+ 1. **Unit Tests**:
300
+ - Change recording
301
+ - Rewind logic for each change type
302
+ - Multiple file reverts
303
+
304
+ 2. **Integration Tests**:
305
+ - Tool wrapping
306
+ - Session persistence
307
+ - Command handling
308
+
309
+ 3. **Manual Testing**:
310
+ - Various file operations
311
+ - Partial reverts
312
+ - Edge cases (binary files, permissions)
313
+
314
+ ## Migration Path
315
+
316
+ 1. **Phase 1**: Basic Write/Edit tracking and rewind
317
+ 2. **Phase 2**: /rewind command with UI
318
+ 3. **Phase 3**: Git integration (optional)
319
+ 4. **Phase 4**: Selective rewind (by file, by time range)
320
+ 5. **Phase 5**: Checkpoint browsing and diff viewing
321
+
322
+ No breaking changes to existing functionality.
323
+
324
+ ## References
325
+
326
+ - [Claude Code Checkpointing](https://code.claude.com/docs/en/checkpointing)
327
+ - [Git Reset and Revert](https://git-scm.com/docs/git-reset)
@@ -0,0 +1,343 @@
1
+ # Proposal: Hooks System
2
+
3
+ - **Proposal ID**: 0009
4
+ - **Author**: mycode team
5
+ - **Status**: Draft
6
+ - **Created**: 2025-01-15
7
+ - **Updated**: 2025-01-15
8
+
9
+ ## Summary
10
+
11
+ Implement an event-driven hooks system that allows users to register shell commands or scripts to run automatically in response to specific events (tool execution, prompt submission, session events). This enables automated workflows, quality gates, and custom integrations.
12
+
13
+ ## Motivation
14
+
15
+ Currently, mycode has no extensibility for automated actions. This limits:
16
+
17
+ 1. **Quality enforcement**: Can't auto-run linters after edits
18
+ 2. **Notifications**: Can't alert users on completion
19
+ 3. **Integration**: Can't trigger external systems
20
+ 4. **Automation**: Can't enforce coding standards automatically
21
+ 5. **Customization**: No way to extend agent behavior
22
+
23
+ A hooks system enables powerful automation and customization.
24
+
25
+ ## Claude Code Reference
26
+
27
+ Claude Code provides a comprehensive hooks system:
28
+
29
+ ### Configuration
30
+ ```json
31
+ // .claude/settings.json
32
+ {
33
+ "hooks": {
34
+ "PostToolUse": [
35
+ {
36
+ "matcher": "Edit|Write",
37
+ "type": "command",
38
+ "command": ".claude/hooks/run-linter.sh $FILE_PATH"
39
+ }
40
+ ],
41
+ "Notification": [
42
+ {
43
+ "type": "command",
44
+ "command": "afplay ~/.claude/sounds/notify.mp3"
45
+ }
46
+ ]
47
+ }
48
+ }
49
+ ```
50
+
51
+ ### Available Events
52
+ | Event | Description | Context |
53
+ |-------|-------------|---------|
54
+ | `PreToolUse` | Before tool execution | Tool name, inputs |
55
+ | `PostToolUse` | After tool execution | Tool name, inputs, result |
56
+ | `UserPromptSubmit` | User sends message | Prompt text |
57
+ | `Notification` | Agent needs attention | Message |
58
+ | `Stop` | Agent stops working | Reason |
59
+ | `SessionStart` | Session begins | Session info |
60
+
61
+ ### Hook Types
62
+ 1. **Command Mode**: Run shell command directly
63
+ 2. **Prompt Mode**: Let LLM decide actions (advanced)
64
+
65
+ ### Matcher Patterns
66
+ - Simple string: `"Edit"` - matches Edit tool
67
+ - Regex: `"Edit|Write"` - matches Edit or Write
68
+ - Wildcard: `"*"` - matches all
69
+
70
+ ### Environment Variables
71
+ Hooks receive context via environment:
72
+ - `$TOOL_NAME` - Name of the tool
73
+ - `$FILE_PATH` - Path of affected file
74
+ - `$EXIT_CODE` - Tool exit code
75
+ - `$SESSION_ID` - Current session
76
+
77
+ ## Detailed Design
78
+
79
+ ### API Design
80
+
81
+ ```typescript
82
+ // src/hooks/types.ts
83
+ type HookEvent =
84
+ | 'PreToolUse'
85
+ | 'PostToolUse'
86
+ | 'UserPromptSubmit'
87
+ | 'Notification'
88
+ | 'Stop'
89
+ | 'SessionStart'
90
+ | 'SubagentStop';
91
+
92
+ type HookType = 'command' | 'prompt';
93
+
94
+ interface HookDefinition {
95
+ matcher?: string | RegExp; // For tool events
96
+ type: HookType;
97
+ command?: string; // For command type
98
+ prompt?: string; // For prompt type
99
+ timeout?: number; // Max execution time
100
+ blocking?: boolean; // Wait for completion
101
+ }
102
+
103
+ interface HooksConfig {
104
+ [event: string]: HookDefinition[];
105
+ }
106
+
107
+ interface HookContext {
108
+ event: HookEvent;
109
+ toolName?: string;
110
+ toolInput?: Record<string, any>;
111
+ toolResult?: any;
112
+ prompt?: string;
113
+ sessionId: string;
114
+ cwd: string;
115
+ }
116
+
117
+ interface HookResult {
118
+ success: boolean;
119
+ output?: string;
120
+ error?: string;
121
+ blocked?: boolean; // Hook blocked the action
122
+ message?: string; // Message to show user
123
+ }
124
+ ```
125
+
126
+ ```typescript
127
+ // src/hooks/hooks-manager.ts
128
+ class HooksManager {
129
+ private config: HooksConfig;
130
+
131
+ constructor(config: HooksConfig);
132
+
133
+ // Register hooks from settings
134
+ loadFromSettings(settings: Settings): void;
135
+
136
+ // Trigger hooks for an event
137
+ async trigger(event: HookEvent, context: HookContext): Promise<HookResult[]>;
138
+
139
+ // Check if event has hooks
140
+ hasHooks(event: HookEvent): boolean;
141
+
142
+ // Get hooks for event
143
+ getHooks(event: HookEvent): HookDefinition[];
144
+
145
+ // Add hook programmatically
146
+ addHook(event: HookEvent, hook: HookDefinition): void;
147
+
148
+ // Remove hook
149
+ removeHook(event: HookEvent, index: number): void;
150
+ }
151
+ ```
152
+
153
+ ### Implementation Approach
154
+
155
+ 1. **Configuration Loading**: Parse hooks from settings.json
156
+ 2. **Event Integration**: Hook into tool execution, prompts, etc.
157
+ 3. **Matcher Evaluation**: Match hooks to relevant events
158
+ 4. **Command Execution**: Run shell commands with context
159
+ 5. **Environment Setup**: Pass context via environment variables
160
+ 6. **Result Handling**: Process hook output and blocking
161
+
162
+ ```typescript
163
+ // Hook execution
164
+ async function executeHook(hook: HookDefinition, context: HookContext): Promise<HookResult> {
165
+ if (hook.type === 'command') {
166
+ // Build environment
167
+ const env = {
168
+ ...process.env,
169
+ TOOL_NAME: context.toolName || '',
170
+ FILE_PATH: context.toolInput?.file_path || '',
171
+ SESSION_ID: context.sessionId,
172
+ CWD: context.cwd,
173
+ };
174
+
175
+ // Expand variables in command
176
+ const command = expandVariables(hook.command, context);
177
+
178
+ // Execute with timeout
179
+ const result = await execWithTimeout(command, {
180
+ env,
181
+ cwd: context.cwd,
182
+ timeout: hook.timeout || 30000
183
+ });
184
+
185
+ return {
186
+ success: result.exitCode === 0,
187
+ output: result.stdout,
188
+ error: result.stderr,
189
+ blocked: result.exitCode !== 0 && hook.blocking
190
+ };
191
+ }
192
+
193
+ // Prompt mode - more complex, uses LLM
194
+ // ...
195
+ }
196
+ ```
197
+
198
+ ### File Changes
199
+
200
+ | File | Action | Description |
201
+ |------|--------|-------------|
202
+ | `src/hooks/types.ts` | Create | Hook type definitions |
203
+ | `src/hooks/hooks-manager.ts` | Create | Core hooks management |
204
+ | `src/hooks/executor.ts` | Create | Hook execution logic |
205
+ | `src/hooks/index.ts` | Create | Module exports |
206
+ | `src/agent/agent.ts` | Modify | Integrate hook triggers |
207
+ | `src/tools/registry.ts` | Modify | Tool execution hooks |
208
+ | `src/config/settings-manager.ts` | Modify | Load hooks config |
209
+
210
+ ## User Experience
211
+
212
+ ### Configuration
213
+ Users configure hooks in `.mycode/settings.json`:
214
+
215
+ ```json
216
+ {
217
+ "hooks": {
218
+ "PostToolUse": [
219
+ {
220
+ "matcher": "Write|Edit",
221
+ "type": "command",
222
+ "command": "npm run lint:fix $FILE_PATH",
223
+ "blocking": false
224
+ }
225
+ ],
226
+ "Stop": [
227
+ {
228
+ "type": "command",
229
+ "command": "afplay ~/.mycode/sounds/done.mp3"
230
+ }
231
+ ]
232
+ }
233
+ }
234
+ ```
235
+
236
+ ### Hook Execution Display
237
+ ```
238
+ Agent: [Write] Created src/component.tsx
239
+
240
+ Running hooks...
241
+ ▶ PostToolUse: npm run lint:fix src/component.tsx
242
+ ✓ Lint completed (2 issues fixed)
243
+ ```
244
+
245
+ ### Blocking Hook
246
+ ```
247
+ Agent: [Edit] Modified src/auth.ts
248
+
249
+ Running hooks...
250
+ ▶ PostToolUse: npm test -- --related src/auth.ts
251
+ ✗ Tests failed (2 failures)
252
+
253
+ Hook blocked further execution. Please fix the failing tests.
254
+ ```
255
+
256
+ ### Hook Status
257
+ ```
258
+ > /hooks
259
+
260
+ Active Hooks:
261
+ ┌────────────────────┬─────────────────────────────────────┐
262
+ │ Event │ Action │
263
+ ├────────────────────┼─────────────────────────────────────┤
264
+ │ PostToolUse │ npm run lint:fix (Edit|Write) │
265
+ │ Stop │ afplay done.mp3 │
266
+ │ SessionStart │ echo "Welcome!" │
267
+ └────────────────────┴─────────────────────────────────────┘
268
+ ```
269
+
270
+ ## Alternatives Considered
271
+
272
+ ### Alternative 1: Plugin-Based Hooks
273
+ Hooks as JavaScript/TypeScript modules.
274
+
275
+ **Pros**: More powerful, type-safe
276
+ **Cons**: Requires JS knowledge, security concerns
277
+ **Decision**: Deferred - start with shell commands
278
+
279
+ ### Alternative 2: Built-in Actions Only
280
+ Predefined hook actions (lint, test, notify).
281
+
282
+ **Pros**: Simpler, safer
283
+ **Cons**: Limited flexibility
284
+ **Decision**: Rejected - custom commands are essential
285
+
286
+ ### Alternative 3: Webhook-Based
287
+ HTTP webhooks instead of shell commands.
288
+
289
+ **Pros**: Remote integration
290
+ **Cons**: Complexity, security, network dependency
291
+ **Decision**: Deferred - can add alongside shell hooks
292
+
293
+ ## Security Considerations
294
+
295
+ 1. **Command Injection**: Sanitize context values in commands
296
+ 2. **Timeout Enforcement**: Prevent runaway hooks
297
+ 3. **Resource Limits**: Limit concurrent hook executions
298
+ 4. **Path Restrictions**: Consider limiting executable paths
299
+ 5. **Output Limits**: Truncate large hook outputs
300
+ 6. **Privilege Escalation**: Hooks run with user's permissions
301
+
302
+ ```typescript
303
+ // Safe variable expansion
304
+ function expandVariables(command: string, context: HookContext): string {
305
+ return command
306
+ .replace(/\$FILE_PATH/g, shellescape([context.toolInput?.file_path || '']))
307
+ .replace(/\$TOOL_NAME/g, shellescape([context.toolName || '']))
308
+ // ... etc
309
+ }
310
+ ```
311
+
312
+ ## Testing Strategy
313
+
314
+ 1. **Unit Tests**:
315
+ - Matcher evaluation
316
+ - Environment building
317
+ - Variable expansion
318
+
319
+ 2. **Integration Tests**:
320
+ - Hook triggering from tools
321
+ - Blocking behavior
322
+ - Multiple hooks
323
+
324
+ 3. **Manual Testing**:
325
+ - Various hook configurations
326
+ - Error handling
327
+ - Timeout behavior
328
+
329
+ ## Migration Path
330
+
331
+ 1. **Phase 1**: Basic PostToolUse and Stop hooks
332
+ 2. **Phase 2**: All event types
333
+ 3. **Phase 3**: Blocking hooks
334
+ 4. **Phase 4**: /hooks command and UI
335
+ 5. **Phase 5**: Prompt-mode hooks
336
+
337
+ No breaking changes to existing functionality.
338
+
339
+ ## References
340
+
341
+ - [Claude Code Hooks Documentation](https://code.claude.com/docs/en/hooks)
342
+ - [Understanding Claude Code Full Stack](https://alexop.dev/posts/understanding-claude-code-full-stack/)
343
+ - [Git Hooks](https://git-scm.com/docs/githooks) (similar concept)