hjworktree-cli 2.1.0 โ†’ 2.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.
@@ -1,14 +1,10 @@
1
1
  {
2
2
  "permissions": {
3
3
  "allow": [
4
- "Bash(lsof:*)",
5
- "Bash(netstat:*)",
6
- "Bash(ss:*)",
7
- "Bash(kill:*)",
4
+ "Bash(git worktree list:*)",
8
5
  "mcp__sequential-thinking__sequentialthinking",
9
6
  "Bash(npm run build:*)",
10
- "Bash(git add:*)",
11
- "Bash(git commit -m \"$\\(cat <<''EOF''\nfeat: improve LNB with session management and always-visible navigation\n\n- Add always-visible LNB that persists during running state\n- Implement session grouping by branch with collapsible sections\n- Add individual and bulk session selection/deletion\n- Create AddWorktreeModal for adding sessions while running\n- Create ConfirmDeleteModal for safe deletion confirmation\n- Add REST API endpoints: POST /worktrees/single, DELETE /worktrees/batch\n- Remove \"Back to Setup\" button, enable free navigation\n- Add README.md for npm package documentation\n- Bump version to 2.1.0\n\n๐Ÿค– Generated with [Claude Code]\\(https://claude.com/claude-code\\)\n\nCo-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>\nEOF\n\\)\")"
7
+ "Bash(npm install:*)"
12
8
  ]
13
9
  }
14
10
  }
@@ -0,0 +1,108 @@
1
+ # Context Snapshot
2
+
3
+ ## Session Metadata
4
+ - **Created**: 2026-01-06T18:00:00+09:00
5
+ - **CLI**: Claude Code
6
+ - **Project**: /root/workspace/work/new/utils/hjWorktree-cli
7
+
8
+ ## Conversation Summary
9
+
10
+ ### User Requests
11
+ - Delete ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ ํ”„๋กœ์ ํŠธ์˜ `.git` ํด๋”๊ฐ€ ์‚ญ์ œ๋˜๋Š” ์น˜๋ช…์  ๋ฒ„๊ทธ ์ˆ˜์ •
12
+ - Close All ๋ฒ„ํŠผ ๊ฒ€์ˆ˜
13
+ - ํ”„๋กœ๋•์…˜ ๋นŒ๋“œ์—์„œ๋„ ๋™์ผํ•œ ๋ฌธ์ œ๊ฐ€ ์žˆ๋Š”์ง€ ํ™•์ธ
14
+ - Plan mode๋กœ ๋ถ„์„ ํ›„ ์ˆ˜์ •
15
+
16
+ ### Completed Tasks
17
+ 1. **์ทจ์•ฝ์  ๋ถ„์„**: 4๊ฐœ์˜ ์น˜๋ช…์  ๋ณด์•ˆ ์ทจ์•ฝ์  ๋ฐœ๊ฒฌ
18
+ - V1: ๊ฒฝ๋กœ ๋น„๊ต ์‹œ ์ •๊ทœํ™” ๋ฏธ์ ์šฉ (`worktreeService.ts:156`)
19
+ - V2: ์‹ฌ๋ณผ๋ฆญ ๋งํฌ ๋ฏธํ•ด๊ฒฐ (`path.resolve()` ์‚ฌ์šฉ)
20
+ - V3: ์œ„ํ—˜ํ•œ `fs.rm()` ํด๋ฐฑ (git ์‹คํŒจ ์‹œ ๊ฐ•์ œ ์‚ญ์ œ)
21
+ - V4: ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ ์‹๋ณ„์ž ๋ถ€์žฌ
22
+
23
+ 2. **6๊ฒน ๋ฐฉ์–ด ์‹œ์Šคํ…œ ๊ตฌํ˜„**:
24
+ - Layer 1: `realpathSync()` ์‹ฌ๋ณผ๋ฆญ ๋งํฌ ํ•ด๊ฒฐ
25
+ - Layer 2: `.git` ํŒŒ์ผ vs ๋””๋ ‰ํ† ๋ฆฌ ๊ฒ€์ฆ
26
+ - Layer 3: ๊ฒฝ๋กœ ์ •ํ™•ํžˆ ์ผ์น˜ ์ฒดํฌ
27
+ - Layer 4: ๋‚ด๋ถ€ ๊ฒฝ๋กœ ์ฒดํฌ
28
+ - Layer 5: ๋ถ€๋ชจ ๊ฒฝ๋กœ ์ฒดํฌ (์žฌ์•™ ๋ฐฉ์ง€)
29
+ - Layer 6: `fs.rm()` ํด๋ฐฑ ์™„์ „ ์ œ๊ฑฐ
30
+
31
+ 3. **`isMainWorktree` ํ”Œ๋ž˜๊ทธ ์ถ”๊ฐ€**: ๋ฐ์ดํ„ฐ ๋ชจ๋ธ์— ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ ๋ช…์‹œ์  ์‹๋ณ„์ž ์ถ”๊ฐ€
32
+
33
+ 4. **API ๋ ˆ๋ฒจ 403 ๋ณดํ˜ธ**: ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ ์‚ญ์ œ ์‹œ๋„ ์‹œ ์ฆ‰์‹œ ๊ฑฐ๋ถ€
34
+
35
+ 5. **๋นŒ๋“œ ๊ฒ€์ฆ**: TypeScript ์ปดํŒŒ์ผ ๋ฐ Vite ๋นŒ๋“œ ์„ฑ๊ณต
36
+
37
+ ### Modified Files
38
+ - `shared/types/index.ts`
39
+ - `server/services/worktreeService.ts`
40
+ - `server/routes/api.ts`
41
+
42
+ ## Technical Context
43
+
44
+ ### Key Concepts
45
+ - **Git Worktree**: ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ vs ๋งํฌ๋“œ ์›ŒํฌํŠธ๋ฆฌ ๊ตฌ๋ถ„
46
+ - ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ: `.git` ๋””๋ ‰ํ† ๋ฆฌ ๋ณด์œ 
47
+ - ๋งํฌ๋“œ ์›ŒํฌํŠธ๋ฆฌ: `.git` ํŒŒ์ผ (๋ฉ”์ธ .git ๊ฒฝ๋กœ ํฌํ•จ)
48
+ - **์‹ฌ๋ณผ๋ฆญ ๋งํฌ ํ•ด๊ฒฐ**: `path.resolve()` vs `realpathSync()`
49
+ - **Defense in Depth**: ๋‹ค์ค‘ ๋ ˆ์ด์–ด ๋ณด์•ˆ ๋ฐฉ์–ด ์ „๋žต
50
+
51
+ ### Important Changes
52
+
53
+ **shared/types/index.ts**
54
+ ```typescript
55
+ export interface Worktree {
56
+ path: string;
57
+ branch: string;
58
+ name: string;
59
+ isMainWorktree: boolean; // NEW
60
+ }
61
+ ```
62
+
63
+ **server/services/worktreeService.ts**
64
+ - `safeRealpath()`: ์‹ฌ๋ณผ๋ฆญ ๋งํฌ๋ฅผ ์•ˆ์ „ํ•˜๊ฒŒ ํ•ด๊ฒฐํ•˜๋Š” ํ—ฌํผ ๋ฉ”์„œ๋“œ
65
+ - `isLinkedWorktree()`: `.git` ํŒŒ์ผ ์กด์žฌ ์—ฌ๋ถ€๋กœ ๋งํฌ๋“œ ์›ŒํฌํŠธ๋ฆฌ ํŒ๋ณ„
66
+ - `isMainRepository()`: ๋ฉ”์ธ ์ €์žฅ์†Œ ์—ฌ๋ถ€ ํ™•์ธ
67
+ - `listWorktrees()`: `isMainWorktree` ํ”Œ๋ž˜๊ทธ ์„ค์ • ์ถ”๊ฐ€
68
+ - `removeWorktree()`: 5๊ฐœ ๋ณด์•ˆ ๊ฐ€๋“œ + `fs.rm()` ํด๋ฐฑ ์ œ๊ฑฐ
69
+ - `removeAllWorktrees()`: ์ด์ค‘ ํ•„ํ„ฐ๋ง (flag + realpath)
70
+ - `removeWorktreesByNames()`: ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ ์‚ญ์ œ ์ฐจ๋‹จ
71
+
72
+ **server/routes/api.ts**
73
+ - `DELETE /worktrees/:name`: ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ ์‚ญ์ œ ์‹œ 403 ๋ฐ˜ํ™˜
74
+
75
+ ### Issues Discovered & Resolved
76
+
77
+ | ์ทจ์•ฝ์  | ์‹ฌ๊ฐ๋„ | ํ•ด๊ฒฐ ๋ฐฉ๋ฒ• |
78
+ |--------|--------|-----------|
79
+ | ๊ฒฝ๋กœ ์ •๊ทœํ™” ๋ฏธ์ ์šฉ | CRITICAL | `realpathSync()` ์‚ฌ์šฉ |
80
+ | ์‹ฌ๋ณผ๋ฆญ ๋งํฌ ๋ฏธํ•ด๊ฒฐ | CRITICAL | `realpathSync()` ์‚ฌ์šฉ |
81
+ | `fs.rm()` ํด๋ฐฑ | CRITICAL | ์™„์ „ ์ œ๊ฑฐ, ์—๋Ÿฌ throw |
82
+ | ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ ๋ฏธ์‹๋ณ„ | HIGH | `isMainWorktree` ํ”Œ๋ž˜๊ทธ ์ถ”๊ฐ€ |
83
+
84
+ ## Next Steps
85
+
86
+ ### Completed
87
+ - [x] ๋ณด์•ˆ ์ˆ˜์ • ๊ตฌํ˜„
88
+ - [x] TypeScript ๋นŒ๋“œ ๊ฒ€์ฆ
89
+
90
+ ### Recommendations
91
+ 1. **์ˆ˜๋™ ํ…Œ์ŠคํŠธ ๊ถŒ์žฅ**:
92
+ - ์‹ฌ๋ณผ๋ฆญ ๋งํฌ๋กœ ์ ‘๊ทผํ•œ ํ”„๋กœ์ ํŠธ์—์„œ ํ…Œ์ŠคํŠธ
93
+ - Close All ๋ฒ„ํŠผ ๋™์ž‘ ํ™•์ธ
94
+ - ๋‹จ์ผ ์„ธ์…˜ ์‚ญ์ œ ๋™์ž‘ ํ™•์ธ
95
+
96
+ 2. **๋ฒ„์ „ ์—…๋ฐ์ดํŠธ**: ๋ณด์•ˆ ์ˆ˜์ •์ด๋ฏ€๋กœ `v2.3.0` ๋ฆด๋ฆฌ์Šค ๊ถŒ์žฅ
97
+
98
+ 3. **ํ…Œ์ŠคํŠธ ์ผ€์ด์Šค ์ถ”๊ฐ€ ๊ณ ๋ ค**:
99
+ - ๋ฉ”์ธ ์›ŒํฌํŠธ๋ฆฌ ์‚ญ์ œ ์‹œ๋„ ์‹œ 403 ๋ฐ˜ํ™˜ ํ™•์ธ
100
+ - ์‹ฌ๋ณผ๋ฆญ ๋งํฌ ํ”„๋กœ์ ํŠธ์—์„œ ๊ฒฝ๋กœ ํ•ด๊ฒฐ ํ™•์ธ
101
+ - `.git` ๋””๋ ‰ํ† ๋ฆฌ vs ํŒŒ์ผ ๊ตฌ๋ถ„ ํ™•์ธ
102
+
103
+ ### Caution
104
+ - `fs.rm()` ํด๋ฐฑ์ด ์ œ๊ฑฐ๋˜์—ˆ์œผ๋ฏ€๋กœ, `git worktree remove` ์‹คํŒจ ์‹œ ์—๋Ÿฌ๊ฐ€ throw๋จ
105
+ - ์ด์ „์—๋Š” silentํ•˜๊ฒŒ ๋ฌด์‹œ๋˜๋˜ ์—๋Ÿฌ๊ฐ€ ์ด์ œ ๋ช…์‹œ์ ์œผ๋กœ ๋ณด๊ณ ๋จ
106
+
107
+ ## Plan File Reference
108
+ - `/root/.claude/plans/encapsulated-swimming-pine.md`
@@ -0,0 +1,108 @@
1
+ # Context Snapshot
2
+
3
+ ## Session Metadata
4
+ - **Created**: 2026-01-06T23:55:00+09:00
5
+ - **CLI**: Claude Code
6
+ - **Project**: /root/workspace/work/new/utils/hjWorktree-cli
7
+
8
+ ## Conversation Summary
9
+
10
+ ### User Requests
11
+ 1. npm์— hjWorktree-cli ํ”„๋กœ์ ํŠธ ๋ฐฐํฌํ•˜๊ธฐ ์œ„ํ•œ ์•ˆ๋‚ด
12
+ 2. package.json์— author ํ•„๋“œ ์ถ”๊ฐ€
13
+ 3. ํฌํŠธ ์ถฉ๋Œ ๋ฌธ์ œ ํ•ด๊ฒฐ (EADDRINUSE)
14
+ 4. LNB(Left Navigation Bar) UX ๋Œ€ํญ ๊ฐœ์„ 
15
+ - LNB๊ฐ€ running ๋‹จ๊ณ„์—์„œ๋„ ํ•ญ์ƒ ํ‘œ์‹œ
16
+ - ์„ธ์…˜ ๋„ค๋น„๊ฒŒ์ด์…˜์„ LNB๋ฅผ ํ†ตํ•ด ํด๋ฆญ์œผ๋กœ ์ด๋™
17
+ - ๋ธŒ๋žœ์น˜๋ณ„ ์„ธ์…˜ ๊ทธ๋ฃนํ•‘
18
+ - ๊ฐœ๋ณ„/๋Œ€๋Ÿ‰ ์„ธ์…˜ ์‚ญ์ œ ๊ธฐ๋Šฅ
19
+ - ์‹คํ–‰ ์ค‘ ์ƒˆ ์›ŒํฌํŠธ๋ฆฌ ์ถ”๊ฐ€ ๊ธฐ๋Šฅ
20
+ 5. npm publish๋ฅผ ์œ„ํ•œ version ์—…๊ทธ๋ ˆ์ด๋“œ ๋ฐ README.md ์ž‘์„ฑ
21
+ 6. ๋ณ€๊ฒฝ์‚ฌํ•ญ ์ปค๋ฐ‹
22
+
23
+ ### Completed Tasks
24
+ 1. npm publish ํ”„๋กœ์„ธ์Šค ์•ˆ๋‚ด (2FA, OTP, Access Token ์„ค๋ช…)
25
+ 2. author ํ•„๋“œ ์ถ”๊ฐ€: "hyungju-lee <beegizee1220@gmail.com>"
26
+ 3. ํฌํŠธ 3847 ์‚ฌ์šฉ ์ค‘์ธ ํ”„๋กœ์„ธ์Šค ์ข…๋ฃŒ (PID 4442)
27
+ 4. LNB ๊ฐœ์„  ๊ตฌํ˜„ (์ด 9๊ฐœ ํƒœ์Šคํฌ)
28
+ - ํƒ€์ž… ์ •์˜ ์ถ”๊ฐ€ (WorktreeSession, SessionGroup, ModalType ๋“ฑ)
29
+ - REST API ์—”๋“œํฌ์ธํŠธ ์ถ”๊ฐ€ (POST /worktrees/single, DELETE /worktrees/batch)
30
+ - WorktreeService ๋ฉ”์„œ๋“œ ์ถ”๊ฐ€ (createSingleWorktree, removeWorktreesByNames)
31
+ - Zustand ์Šคํ† ์–ด ํ™•์žฅ (์„ธ์…˜ ๊ด€๋ฆฌ, LNB ์ƒํƒœ, ๋ชจ๋‹ฌ ์ƒํƒœ)
32
+ - LeftNavBar ์™„์ „ ์žฌ์ž‘์„ฑ (SetupSection, SessionsSection, BulkActionsBar)
33
+ - MainLayout ์ˆ˜์ • (LNB ํ•ญ์ƒ ํ‘œ์‹œ)
34
+ - TerminalPanel ์ˆ˜์ • ("Back to Setup" ์ œ๊ฑฐ, sessionId ๊ธฐ๋ฐ˜ ์ „ํ™˜)
35
+ - ๋ชจ๋‹ฌ ์ปดํฌ๋„ŒํŠธ ์ƒ์„ฑ (AddWorktreeModal, ConfirmDeleteModal, ModalContainer)
36
+ - CSS ์Šคํƒ€์ผ ์ถ”๊ฐ€ (~500์ค„)
37
+ 5. package.json version 2.0.0 โ†’ 2.1.0 ์—…๊ทธ๋ ˆ์ด๋“œ
38
+ 6. README.md ์ž‘์„ฑ
39
+ 7. Git ์ปค๋ฐ‹ ์™„๋ฃŒ (1d4476fc)
40
+
41
+ ### Modified Files
42
+ - `shared/types/index.ts` - ์„ธ์…˜ ๊ด€๋ฆฌ์šฉ ํƒ€์ž… ์ •์˜ ์ถ”๊ฐ€
43
+ - `server/routes/api.ts` - 2๊ฐœ์˜ ์ƒˆ API ์—”๋“œํฌ์ธํŠธ ์ถ”๊ฐ€
44
+ - `server/services/worktreeService.ts` - 2๊ฐœ์˜ ์ƒˆ ๋ฉ”์„œ๋“œ ์ถ”๊ฐ€
45
+ - `web/src/stores/useAppStore.ts` - ์ƒํƒœ ๋ฐ ์•ก์…˜ ๋Œ€ํญ ํ™•์žฅ
46
+ - `web/src/components/Layout/LeftNavBar.tsx` - ์™„์ „ ์žฌ์ž‘์„ฑ
47
+ - `web/src/components/Layout/MainLayout.tsx` - LNB ํ•ญ์ƒ ํ‘œ์‹œ ๋กœ์ง
48
+ - `web/src/components/Terminal/TerminalPanel.tsx` - sessionId ๊ธฐ๋ฐ˜ ์ „ํ™˜
49
+ - `web/src/components/Modals/AddWorktreeModal.tsx` - ์‹ ๊ทœ ์ƒ์„ฑ
50
+ - `web/src/components/Modals/ConfirmDeleteModal.tsx` - ์‹ ๊ทœ ์ƒ์„ฑ
51
+ - `web/src/components/Modals/ModalContainer.tsx` - ์‹ ๊ทœ ์ƒ์„ฑ
52
+ - `web/src/App.tsx` - ModalContainer ์ถ”๊ฐ€
53
+ - `web/src/styles/global.css` - LNB, ์„ธ์…˜, ๋ชจ๋‹ฌ ์Šคํƒ€์ผ ์ถ”๊ฐ€
54
+ - `package.json` - version 2.1.0, author ์ถ”๊ฐ€
55
+ - `README.md` - ์‹ ๊ทœ ์ƒ์„ฑ
56
+
57
+ ## Technical Context
58
+
59
+ ### Key Concepts
60
+ - **Git Worktree**: ๋‹จ์ผ ์ €์žฅ์†Œ์—์„œ ์—ฌ๋Ÿฌ ๋ธŒ๋žœ์น˜๋ฅผ ๋™์‹œ์— ์ฒดํฌ์•„์›ƒ
61
+ - **Socket.IO + node-pty**: ์‹ค์‹œ๊ฐ„ ํ„ฐ๋ฏธ๋„ ์—๋ฎฌ๋ ˆ์ด์…˜
62
+ - **Zustand**: React ์ƒํƒœ ๊ด€๋ฆฌ
63
+ - **xterm.js**: ์›น ๊ธฐ๋ฐ˜ ํ„ฐ๋ฏธ๋„ ๋ Œ๋”๋ง
64
+ - **REST API ์„ค๊ณ„**: ๋‹จ์ผ/๋ฐฐ์น˜ CRUD ์—”๋“œํฌ์ธํŠธ
65
+
66
+ ### Important Changes
67
+
68
+ **shared/types/index.ts**
69
+ ```typescript
70
+ // ์ƒˆ ํƒ€์ž… ์ •์˜
71
+ export interface CreateSingleWorktreeRequest { branch: string; agentType: AgentId; }
72
+ export interface BatchDeleteRequest { names: string[]; }
73
+ export interface WorktreeSession extends TerminalInfo { id: string; createdAt: number; }
74
+ export interface SessionGroup { branchName: string; sessions: WorktreeSession[]; isCollapsed: boolean; }
75
+ export type ModalType = 'addWorktree' | 'confirmDelete' | null;
76
+ ```
77
+
78
+ **server/routes/api.ts**
79
+ ```typescript
80
+ // POST /worktrees/single - ๋‹จ์ผ ์›ŒํฌํŠธ๋ฆฌ ์ƒ์„ฑ
81
+ // DELETE /worktrees/batch - ๋ฐฐ์น˜ ์‚ญ์ œ
82
+ ```
83
+
84
+ **web/src/stores/useAppStore.ts**
85
+ - ์ƒˆ ์ƒํƒœ: activeSessionId, selectedSessionIds, isSetupCollapsed, collapsedBranches, modalType, modalData
86
+ - ์ƒˆ ์•ก์…˜: setActiveSession, toggleSessionSelection, selectAllSessions, clearSessionSelection, removeSelectedSessions, getSessionGroups, toggleSetupCollapse, toggleBranchCollapse, openModal, closeModal, createSingleWorktree
87
+
88
+ **web/src/components/Layout/LeftNavBar.tsx**
89
+ - SetupSection: ์ ‘์„ ์ˆ˜ ์žˆ๋Š” ์„ค์ • ์„น์…˜
90
+ - SessionsSection: ๋ธŒ๋žœ์น˜๋ณ„ ๊ทธ๋ฃนํ•‘๋œ ์„ธ์…˜ ๋ชฉ๋ก
91
+ - SessionItem: ์ฒดํฌ๋ฐ•์Šค, ์ƒํƒœ ํ‘œ์‹œ, ์‚ญ์ œ ๋ฒ„ํŠผ
92
+ - BulkActionsBar: ๋Œ€๋Ÿ‰ ์„ ํƒ/์‚ญ์ œ ๊ธฐ๋Šฅ
93
+
94
+ ### Issues Resolved
95
+ 1. **npm publish E403 (2FA required)**: 2FA ๋˜๋Š” Automation Token ํ•„์š” ์„ค๋ช…
96
+ 2. **OTP vs Access Token ํ˜ผ๋™**: ์ฐจ์ด์  ์„ค๋ช… (6์ž๋ฆฌ ์ˆซ์ž vs ํ† ํฐ)
97
+ 3. **EADDRINUSE :3847**: `lsof -i :3847` โ†’ `kill 4442`๋กœ ํ•ด๊ฒฐ
98
+ 4. **LNB๊ฐ€ running ์ƒํƒœ์—์„œ ์ˆจ๊ฒจ์ง**: MainLayout์—์„œ ์กฐ๊ฑด๋ถ€ ๋ Œ๋”๋ง ์ œ๊ฑฐ
99
+ 5. **Back to Setup์ด ๋ชจ๋“  ์›ŒํฌํŠธ๋ฆฌ ์‚ญ์ œ**: ๋ฒ„ํŠผ ์ œ๊ฑฐ, ์ž์œ  ๋„ค๋น„๊ฒŒ์ด์…˜ ๊ตฌํ˜„
100
+
101
+ ## Next Steps
102
+ - `git push`๋กœ ์›๊ฒฉ ์ €์žฅ์†Œ์— ํ‘ธ์‹œ
103
+ - `npm publish --access public`๋กœ npm ๋ฐฐํฌ
104
+ - ๋ฐฐํฌ ํ›„ `npm i hjworktree-cli -g`๋กœ ์„ค์น˜ ํ…Œ์ŠคํŠธ
105
+
106
+ ## Notes
107
+ - npm ํ† ํฐ์ด ์ฑ„ํŒ…์— ๋…ธ์ถœ๋˜์—ˆ์œผ๋ฏ€๋กœ revoke ํ›„ ์žฌ์ƒ์„ฑ ํ•„์š” (์ด๋ฏธ ์ฒ˜๋ฆฌ๋จ)
108
+ - ํ˜„์žฌ ๋ธŒ๋žœ์น˜๋Š” `origin/main`๋ณด๋‹ค 1 commit ์•ž์„œ ์žˆ์Œ
package/README.md CHANGED
@@ -112,6 +112,19 @@ hjWorktree-cli/
112
112
  | DELETE | /api/worktrees/batch | Batch delete worktrees |
113
113
  | DELETE | /api/worktrees | Delete all worktrees |
114
114
 
115
+ ## Changelog
116
+
117
+ ### v2.2.0
118
+ - **Security Fix**: Added critical protection guards to prevent accidental deletion of main repository's `.git` folder during worktree cleanup
119
+ - **Session Reliability**: Added path and shell validation before PTY spawn
120
+ - **PTY Stability**: Added retry logic with exponential backoff for PTY spawn failures
121
+ - **Resource Protection**: Added spawn interval control (150ms minimum) to prevent resource contention when creating multiple terminals
122
+
123
+ ### v2.1.0
124
+ - Improved LNB with session management and always-visible navigation
125
+ - Implemented 4-step wizard navigation with LNB
126
+ - Rebuilt as web-based application
127
+
115
128
  ## License
116
129
 
117
130
  MIT
@@ -1 +1 @@
1
- {"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../../../server/routes/api.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAqB,MAAM,SAAS,CAAC;AAKpD,wBAAgB,SAAS,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAgJ7C"}
1
+ {"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../../../server/routes/api.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAqB,MAAM,SAAS,CAAC;AAKpD,wBAAgB,SAAS,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAuJ7C"}
@@ -113,6 +113,12 @@ export function apiRouter(cwd) {
113
113
  res.status(404).json({ error: 'Worktree not found' });
114
114
  return;
115
115
  }
116
+ // SECURITY: Never delete main worktree
117
+ if (worktree.isMainWorktree) {
118
+ console.warn(`[SECURITY] API blocked attempt to delete main worktree: ${name}`);
119
+ res.status(403).json({ error: 'Cannot delete main worktree' });
120
+ return;
121
+ }
116
122
  await worktreeService.removeWorktree(worktree.path);
117
123
  res.json({ success: true });
118
124
  }
@@ -1 +1 @@
1
- {"version":3,"file":"api.js","sourceRoot":"","sources":["../../../server/routes/api.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"api.js","sourceRoot":"","sources":["../../../server/routes/api.ts"],"names":[],"mappings":"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"}
@@ -4,6 +4,21 @@ export declare class WorktreeService {
4
4
  private rootDir;
5
5
  private createdWorktrees;
6
6
  constructor(cwd?: string);
7
+ /**
8
+ * Safely resolves a path to its real path, handling symlinks.
9
+ * Returns null if path cannot be resolved.
10
+ */
11
+ private safeRealpath;
12
+ /**
13
+ * Checks if a path is a linked worktree (has .git file) vs main repo (has .git directory).
14
+ * Linked worktrees have a .git FILE that points to the main .git directory.
15
+ * Main repo has a .git DIRECTORY.
16
+ */
17
+ private isLinkedWorktree;
18
+ /**
19
+ * Checks if the given path is the main repository.
20
+ */
21
+ private isMainRepository;
7
22
  listWorktrees(): Promise<Worktree[]>;
8
23
  createWorktree(baseBranch: string, index: number): Promise<Worktree>;
9
24
  createMultipleWorktrees(baseBranch: string, count: number): Promise<Worktree[]>;
@@ -1 +1 @@
1
- {"version":3,"file":"worktreeService.d.ts","sourceRoot":"","sources":["../../../server/services/worktreeService.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,6BAA6B,CAAC;AAE5D,qBAAa,eAAe;IAC1B,OAAO,CAAC,GAAG,CAAY;IACvB,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,gBAAgB,CAA0B;gBAEtC,GAAG,GAAE,MAAsB;IAKjC,aAAa,IAAI,OAAO,CAAC,QAAQ,EAAE,CAAC;IAwBpC,cAAc,CAAC,UAAU,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC;IAsCpE,uBAAuB,CAAC,UAAU,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,QAAQ,EAAE,CAAC;IA2B/E,cAAc,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAgCnD,kBAAkB,IAAI,OAAO,CAAC,IAAI,CAAC;IAenC,oBAAoB,CAAC,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC;IAqB3D,sBAAsB,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC;QACrD,OAAO,EAAE,MAAM,EAAE,CAAC;QAClB,MAAM,EAAE;YAAE,IAAI,EAAE,MAAM,CAAC;YAAC,KAAK,EAAE,MAAM,CAAA;SAAE,EAAE,CAAC;KAC3C,CAAC;IA4BI,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAY9B,mBAAmB,IAAI,MAAM,EAAE;IAI/B,UAAU,IAAI,MAAM;CAGrB;AAKD,wBAAgB,kBAAkB,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,eAAe,CAKhE"}
1
+ {"version":3,"file":"worktreeService.d.ts","sourceRoot":"","sources":["../../../server/services/worktreeService.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,6BAA6B,CAAC;AAE5D,qBAAa,eAAe;IAC1B,OAAO,CAAC,GAAG,CAAY;IACvB,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,gBAAgB,CAA0B;gBAEtC,GAAG,GAAE,MAAsB;IAKvC;;;OAGG;IACH,OAAO,CAAC,YAAY;IAQpB;;;;OAIG;IACH,OAAO,CAAC,gBAAgB;IAYxB;;OAEG;IACH,OAAO,CAAC,gBAAgB;IAYlB,aAAa,IAAI,OAAO,CAAC,QAAQ,EAAE,CAAC;IAgCpC,cAAc,CAAC,UAAU,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC;IAuCpE,uBAAuB,CAAC,UAAU,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,QAAQ,EAAE,CAAC;IA2B/E,cAAc,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAsEnD,kBAAkB,IAAI,OAAO,CAAC,IAAI,CAAC;IAgCnC,oBAAoB,CAAC,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC;IAqB3D,sBAAsB,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC;QACrD,OAAO,EAAE,MAAM,EAAE,CAAC;QAClB,MAAM,EAAE;YAAE,IAAI,EAAE,MAAM,CAAC;YAAC,KAAK,EAAE,MAAM,CAAA;SAAE,EAAE,CAAC;KAC3C,CAAC;IAmCI,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAY9B,mBAAmB,IAAI,MAAM,EAAE;IAI/B,UAAU,IAAI,MAAM;CAGrB;AAKD,wBAAgB,kBAAkB,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,eAAe,CAKhE"}
@@ -1,6 +1,7 @@
1
1
  import { simpleGit } from 'simple-git';
2
2
  import path from 'path';
3
3
  import fs from 'fs/promises';
4
+ import { realpathSync, statSync } from 'fs';
4
5
  export class WorktreeService {
5
6
  git;
6
7
  rootDir;
@@ -9,20 +10,68 @@ export class WorktreeService {
9
10
  this.rootDir = cwd;
10
11
  this.git = simpleGit(cwd);
11
12
  }
13
+ /**
14
+ * Safely resolves a path to its real path, handling symlinks.
15
+ * Returns null if path cannot be resolved.
16
+ */
17
+ safeRealpath(targetPath) {
18
+ try {
19
+ return realpathSync(targetPath);
20
+ }
21
+ catch {
22
+ return null;
23
+ }
24
+ }
25
+ /**
26
+ * Checks if a path is a linked worktree (has .git file) vs main repo (has .git directory).
27
+ * Linked worktrees have a .git FILE that points to the main .git directory.
28
+ * Main repo has a .git DIRECTORY.
29
+ */
30
+ isLinkedWorktree(worktreePath) {
31
+ const gitPath = path.join(worktreePath, '.git');
32
+ try {
33
+ const stat = statSync(gitPath);
34
+ // .git is a directory = main repository
35
+ // .git is a file = linked worktree
36
+ return !stat.isDirectory();
37
+ }
38
+ catch {
39
+ return false;
40
+ }
41
+ }
42
+ /**
43
+ * Checks if the given path is the main repository.
44
+ */
45
+ isMainRepository(targetPath) {
46
+ const resolvedTarget = this.safeRealpath(targetPath);
47
+ const resolvedRoot = this.safeRealpath(this.rootDir);
48
+ if (!resolvedTarget || !resolvedRoot) {
49
+ // If we can't resolve paths, assume it might be main repo (fail safe)
50
+ return true;
51
+ }
52
+ return resolvedTarget === resolvedRoot;
53
+ }
12
54
  async listWorktrees() {
13
55
  const result = await this.git.raw(['worktree', 'list', '--porcelain']);
14
56
  const worktrees = [];
15
57
  const entries = result.trim().split('\n\n').filter(Boolean);
58
+ const resolvedRootDir = this.safeRealpath(this.rootDir);
16
59
  for (const entry of entries) {
17
60
  const lines = entry.split('\n');
18
61
  const worktreePath = lines.find((l) => l.startsWith('worktree '))?.replace('worktree ', '');
19
62
  const branchLine = lines.find((l) => l.startsWith('branch '));
20
63
  const branch = branchLine?.replace('branch refs/heads/', '');
21
64
  if (worktreePath) {
65
+ // Determine if this is the main worktree using realpath comparison
66
+ const resolvedWorktreePath = this.safeRealpath(worktreePath);
67
+ const isMainWorktree = resolvedWorktreePath !== null &&
68
+ resolvedRootDir !== null &&
69
+ resolvedWorktreePath === resolvedRootDir;
22
70
  worktrees.push({
23
71
  path: worktreePath,
24
72
  branch: branch || 'detached',
25
73
  name: path.basename(worktreePath),
74
+ isMainWorktree,
26
75
  });
27
76
  }
28
77
  }
@@ -60,6 +109,7 @@ export class WorktreeService {
60
109
  path: worktreePath,
61
110
  branch: newBranchName,
62
111
  name: worktreeName,
112
+ isMainWorktree: false, // Created worktrees are always linked, not main
63
113
  };
64
114
  }
65
115
  async createMultipleWorktrees(baseBranch, count) {
@@ -88,28 +138,58 @@ export class WorktreeService {
88
138
  }
89
139
  }
90
140
  async removeWorktree(worktreePath) {
141
+ // SECURITY GUARD 1: Use realpathSync for symlink resolution
142
+ const resolvedWorktreePath = this.safeRealpath(worktreePath);
143
+ const resolvedRootDir = this.safeRealpath(this.rootDir);
144
+ // If we cannot resolve paths, abort for safety
145
+ if (!resolvedWorktreePath) {
146
+ console.warn(`[SECURITY] Cannot resolve worktree path: ${worktreePath}. Aborting deletion.`);
147
+ return;
148
+ }
149
+ if (!resolvedRootDir) {
150
+ console.warn(`[SECURITY] Cannot resolve root directory path. Aborting deletion.`);
151
+ return;
152
+ }
153
+ // SECURITY GUARD 2: Check exact match with main repo
154
+ if (resolvedWorktreePath === resolvedRootDir) {
155
+ console.warn(`[SECURITY] Attempted to remove main repository: ${worktreePath}. Ignoring.`);
156
+ return;
157
+ }
158
+ // SECURITY GUARD 3: Check if path is inside main repo
159
+ if (resolvedWorktreePath.startsWith(resolvedRootDir + path.sep)) {
160
+ console.warn(`[SECURITY] Attempted to remove path inside main repository: ${worktreePath}. Ignoring.`);
161
+ return;
162
+ }
163
+ // SECURITY GUARD 4: Check if main repo is inside target path (catastrophic prevention)
164
+ if (resolvedRootDir.startsWith(resolvedWorktreePath + path.sep)) {
165
+ console.warn(`[SECURITY] Attempted to remove parent of main repository: ${worktreePath}. Ignoring.`);
166
+ return;
167
+ }
168
+ // SECURITY GUARD 5: Verify it's actually a linked worktree (has .git FILE, not directory)
169
+ const isLinked = this.isLinkedWorktree(worktreePath);
170
+ if (!isLinked) {
171
+ console.warn(`[SECURITY] Path is not a linked worktree (missing .git file or has .git directory): ${worktreePath}. Ignoring.`);
172
+ return;
173
+ }
91
174
  const branchName = path.basename(worktreePath);
175
+ // CRITICAL: Only use git worktree remove - NEVER use fs.rm() as fallback
92
176
  try {
93
- // 1. Force remove worktree
94
177
  await this.git.raw(['worktree', 'remove', worktreePath, '--force']);
95
178
  }
96
- catch {
97
- // 2. If worktree remove fails, try to remove directory manually
98
- try {
99
- await fs.rm(worktreePath, { recursive: true, force: true });
100
- }
101
- catch {
102
- // Ignore errors
103
- }
179
+ catch (error) {
180
+ // Log the error but DO NOT fall back to fs.rm
181
+ console.error(`[SECURITY] Failed to remove worktree via git: ${worktreePath}`, error);
182
+ // Propagate error instead of dangerous fallback
183
+ throw new Error(`Failed to remove worktree: ${error instanceof Error ? error.message : 'Unknown error'}`);
104
184
  }
105
- // 3. CRITICAL: Prune orphan worktree references
185
+ // Prune orphan worktree references
106
186
  try {
107
187
  await this.git.raw(['worktree', 'prune']);
108
188
  }
109
189
  catch {
110
- // Ignore prune errors
190
+ // Ignore prune errors - non-critical
111
191
  }
112
- // 4. Now we can safely delete the branch
192
+ // Delete the branch
113
193
  try {
114
194
  await this.git.branch(['-D', branchName]);
115
195
  }
@@ -120,8 +200,22 @@ export class WorktreeService {
120
200
  }
121
201
  async removeAllWorktrees() {
122
202
  const worktrees = await this.listWorktrees();
123
- // Filter out the main worktree (usually the first one / the main repo)
124
- const additionalWorktrees = worktrees.filter(wt => wt.path !== this.rootDir);
203
+ // Filter out the main worktree using the isMainWorktree flag and path comparison
204
+ const additionalWorktrees = worktrees.filter(wt => {
205
+ // Primary check: use isMainWorktree flag
206
+ if (wt.isMainWorktree) {
207
+ console.log(`[SECURITY] Skipping main worktree in removeAll: ${wt.path}`);
208
+ return false;
209
+ }
210
+ // Secondary check: realpath comparison as defense in depth
211
+ const resolvedPath = this.safeRealpath(wt.path);
212
+ const resolvedRoot = this.safeRealpath(this.rootDir);
213
+ if (resolvedPath && resolvedRoot && resolvedPath === resolvedRoot) {
214
+ console.warn(`[SECURITY] Detected main worktree via realpath (flag was false): ${wt.path}`);
215
+ return false;
216
+ }
217
+ return true;
218
+ });
125
219
  for (const worktree of additionalWorktrees) {
126
220
  try {
127
221
  await this.removeWorktree(worktree.path);
@@ -160,6 +254,12 @@ export class WorktreeService {
160
254
  results.failed.push({ name, error: 'Worktree not found' });
161
255
  continue;
162
256
  }
257
+ // SECURITY: Never delete main worktree
258
+ if (worktree.isMainWorktree) {
259
+ console.warn(`[SECURITY] Blocked attempt to delete main worktree by name: ${name}`);
260
+ results.failed.push({ name, error: 'Cannot delete main worktree' });
261
+ continue;
262
+ }
163
263
  try {
164
264
  await this.removeWorktree(worktree.path);
165
265
  results.deleted.push(name);
@@ -1 +1 @@
1
- {"version":3,"file":"worktreeService.js","sourceRoot":"","sources":["../../../server/services/worktreeService.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"worktreeService.js","sourceRoot":"","sources":["../../../server/services/worktreeService.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"socketHandlers.d.ts","sourceRoot":"","sources":["../../server/socketHandlers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAU,MAAM,WAAW,CAAC;AA8B3C,wBAAgB,mBAAmB,CAAC,EAAE,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,QAsH1D;AAED,wBAAgB,eAAe,IAAI,IAAI,CAMtC"}
1
+ {"version":3,"file":"socketHandlers.d.ts","sourceRoot":"","sources":["../../server/socketHandlers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAU,MAAM,WAAW,CAAC;AAwG3C,wBAAgB,mBAAmB,CAAC,EAAE,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,QAqI1D;AAED,wBAAgB,eAAe,IAAI,IAAI,CAMtC"}
@@ -1,5 +1,66 @@
1
1
  import * as pty from 'node-pty';
2
2
  import { AI_AGENTS } from '../shared/constants.js';
3
+ import fs from 'fs';
4
+ import { promisify } from 'util';
5
+ const access = promisify(fs.access);
6
+ // Validation utilities
7
+ async function validatePath(pathToCheck) {
8
+ try {
9
+ await access(pathToCheck, fs.constants.R_OK | fs.constants.X_OK);
10
+ return { valid: true };
11
+ }
12
+ catch (error) {
13
+ return {
14
+ valid: false,
15
+ error: error instanceof Error ? error.message : 'Path not accessible'
16
+ };
17
+ }
18
+ }
19
+ async function validateShell(shell) {
20
+ if (process.platform === 'win32') {
21
+ return { valid: true };
22
+ }
23
+ try {
24
+ await access(shell, fs.constants.X_OK);
25
+ return { valid: true };
26
+ }
27
+ catch (error) {
28
+ return {
29
+ valid: false,
30
+ error: `Shell not executable: ${shell}`
31
+ };
32
+ }
33
+ }
34
+ // PTY spawn with retry logic
35
+ async function spawnWithRetry(shell, args, options, maxRetries = 3) {
36
+ let lastError = null;
37
+ for (let attempt = 0; attempt < maxRetries; attempt++) {
38
+ try {
39
+ const ptyProcess = pty.spawn(shell, args, options);
40
+ return ptyProcess;
41
+ }
42
+ catch (error) {
43
+ lastError = error instanceof Error ? error : new Error(String(error));
44
+ console.error(`[PTY] Spawn attempt ${attempt + 1}/${maxRetries} failed:`, lastError.message);
45
+ if (attempt < maxRetries - 1) {
46
+ const delay = Math.pow(2, attempt) * 100;
47
+ await new Promise(resolve => setTimeout(resolve, delay));
48
+ }
49
+ }
50
+ }
51
+ throw lastError || new Error('Failed to spawn PTY after retries');
52
+ }
53
+ // Spawn interval control to prevent resource contention
54
+ let lastSpawnTime = 0;
55
+ const MIN_SPAWN_INTERVAL = 150;
56
+ async function waitForSpawnInterval() {
57
+ const now = Date.now();
58
+ const elapsed = now - lastSpawnTime;
59
+ if (elapsed < MIN_SPAWN_INTERVAL) {
60
+ await new Promise(resolve => setTimeout(resolve, MIN_SPAWN_INTERVAL - elapsed));
61
+ }
62
+ lastSpawnTime = Date.now();
63
+ }
3
64
  const sessions = new Map();
4
65
  function getAgentCommand(agentType) {
5
66
  const agent = AI_AGENTS.find(a => a.id === agentType);
@@ -18,7 +79,19 @@ export function setupSocketHandlers(io, cwd) {
18
79
  try {
19
80
  const shell = getShell();
20
81
  const agentCommand = getAgentCommand(agentType);
21
- const ptyProcess = pty.spawn(shell, [], {
82
+ // Validate path before spawning
83
+ const pathValidation = await validatePath(worktreePath);
84
+ if (!pathValidation.valid) {
85
+ throw new Error(`Invalid worktree path: ${pathValidation.error}`);
86
+ }
87
+ // Validate shell before spawning
88
+ const shellValidation = await validateShell(shell);
89
+ if (!shellValidation.valid) {
90
+ throw new Error(`Invalid shell: ${shellValidation.error}`);
91
+ }
92
+ // Wait for spawn interval to prevent resource contention
93
+ await waitForSpawnInterval();
94
+ const ptyProcess = await spawnWithRetry(shell, [], {
22
95
  name: 'xterm-256color',
23
96
  cols: 120,
24
97
  rows: 30,