vibe-coding-master 0.0.9 → 0.0.10

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.
@@ -0,0 +1,32 @@
1
+ /**
2
+ * Copyright (c) 2014 The xterm.js authors. All rights reserved.
3
+ * Copyright (c) 2012-2013, Christopher Jeffrey (MIT License)
4
+ * https://github.com/chjj/term.js
5
+ * @license MIT
6
+ *
7
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
8
+ * of this software and associated documentation files (the "Software"), to deal
9
+ * in the Software without restriction, including without limitation the rights
10
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11
+ * copies of the Software, and to permit persons to whom the Software is
12
+ * furnished to do so, subject to the following conditions:
13
+ *
14
+ * The above copyright notice and this permission notice shall be included in
15
+ * all copies or substantial portions of the Software.
16
+ *
17
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
23
+ * THE SOFTWARE.
24
+ *
25
+ * Originally forked from (with the author's permission):
26
+ * Fabrice Bellard's javascript vt100 for jslinux:
27
+ * http://bellard.org/jslinux/
28
+ * Copyright (c) 2011 Fabrice Bellard
29
+ * The original design remains. The terminal itself
30
+ * has been extended to include xterm CSI codes, among
31
+ * other features.
32
+ */.xterm{cursor:text;position:relative;user-select:none;-ms-user-select:none;-webkit-user-select:none}.xterm.focus,.xterm:focus{outline:none}.xterm .xterm-helpers{position:absolute;top:0;z-index:5}.xterm .xterm-helper-textarea{padding:0;border:0;margin:0;position:absolute;opacity:0;left:-9999em;top:0;width:0;height:0;z-index:-5;white-space:nowrap;overflow:hidden;resize:none}.xterm .composition-view{background:#000;color:#fff;display:none;position:absolute;white-space:nowrap;z-index:1}.xterm .composition-view.active{display:block}.xterm .xterm-viewport{background-color:#000;overflow-y:scroll;cursor:default;position:absolute;right:0;left:0;top:0;bottom:0}.xterm .xterm-screen{position:relative}.xterm .xterm-screen canvas{position:absolute;left:0;top:0}.xterm .xterm-scroll-area{visibility:hidden}.xterm-char-measure-element{display:inline-block;visibility:hidden;position:absolute;top:0;left:-9999em;line-height:normal}.xterm.enable-mouse-events{cursor:default}.xterm.xterm-cursor-pointer,.xterm .xterm-cursor-pointer{cursor:pointer}.xterm.column-select.focus{cursor:crosshair}.xterm .xterm-accessibility:not(.debug),.xterm .xterm-message{position:absolute;left:0;top:0;bottom:0;right:0;z-index:10;color:transparent;pointer-events:none}.xterm .xterm-accessibility-tree:not(.debug) *::selection{color:transparent}.xterm .xterm-accessibility-tree{-webkit-user-select:text;user-select:text;white-space:pre}.xterm .live-region{position:absolute;left:-9999px;width:1px;height:1px;overflow:hidden}.xterm-dim{opacity:1!important}.xterm-underline-1{text-decoration:underline}.xterm-underline-2{text-decoration:double underline}.xterm-underline-3{text-decoration:wavy underline}.xterm-underline-4{text-decoration:dotted underline}.xterm-underline-5{text-decoration:dashed underline}.xterm-overline{text-decoration:overline}.xterm-overline.xterm-underline-1{text-decoration:overline underline}.xterm-overline.xterm-underline-2{text-decoration:overline double underline}.xterm-overline.xterm-underline-3{text-decoration:overline wavy underline}.xterm-overline.xterm-underline-4{text-decoration:overline dotted underline}.xterm-overline.xterm-underline-5{text-decoration:overline dashed underline}.xterm-strikethrough{text-decoration:line-through}.xterm-screen .xterm-decoration-container .xterm-decoration{z-index:6;position:absolute}.xterm-screen .xterm-decoration-container .xterm-decoration.xterm-decoration-top-layer{z-index:7}.xterm-decoration-overview-ruler{z-index:8;position:absolute;top:0;right:0;pointer-events:none}.xterm-decoration-top{z-index:2;position:relative}:root{color-scheme:light;font-family:Inter,ui-sans-serif,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,sans-serif;background:#f5f2ea;color:#1c2024;line-height:1.5}html,body,#root{height:100%}*{box-sizing:border-box}body{margin:0;min-width:320px;min-height:100vh;background:#f5f2ea}button,input,select,textarea{font:inherit}button{border:1px solid #9ba6ad;background:#f8f7f2;color:#1d252b;border-radius:6px;min-height:34px;padding:6px 10px;cursor:pointer}button:hover:not(:disabled){background:#eef4f2;border-color:#607d74}button:disabled{cursor:not-allowed;opacity:.55}.danger-button{border-color:#b84a45;background:#fff1ee;color:#8d211d;font-weight:750}.danger-button:hover:not(:disabled){border-color:#8d211d;background:#ffe2dc}input,select,textarea:not(.xterm-helper-textarea){width:100%;border:1px solid #b9b0a1;border-radius:6px;background:#fffdf8;color:#202326;padding:8px 10px}textarea:not(.xterm-helper-textarea){min-height:240px;resize:vertical;font-family:Menlo,Monaco,Consolas,monospace;font-size:12px}h1,h2,p{margin-top:0}h1{margin-bottom:4px;font-size:26px;line-height:1.15}h2{margin-bottom:10px;font-size:14px;letter-spacing:0}.app-shell{display:grid;grid-template-columns:minmax(280px,320px) minmax(0,1fr);height:100vh;min-height:0;overflow:hidden}.app-shell.is-sidebar-collapsed{grid-template-columns:46px minmax(0,1fr)}.app-sidebar{position:relative;min-width:0;border-right:1px solid #d3c9b8;background:#fbfaf6;padding:14px;overflow:auto}.app-shell.is-sidebar-collapsed .app-sidebar{overflow:hidden;padding:8px}.sidebar-toggle{position:absolute;top:10px;right:10px;z-index:2;display:grid;place-items:center;width:28px;min-height:28px;padding:0;background:#fffdf8}.sidebar-toggle:before{width:8px;height:8px;border-color:currentColor;border-style:solid;border-width:0 2px 2px 0;content:"";transform:translate(2px) rotate(135deg)}.app-shell.is-sidebar-collapsed .sidebar-toggle{left:9px;right:auto}.app-shell.is-sidebar-collapsed .sidebar-toggle:before{transform:translate(-2px) rotate(-45deg)}.sidebar-content{min-width:0}.app-shell.is-sidebar-collapsed .sidebar-content{width:0;opacity:0;pointer-events:none}.app-main{min-width:0;height:100%;padding:14px 16px;overflow:auto}.brand-header{display:flex;gap:12px;align-items:baseline;margin-bottom:10px;padding-right:34px}.brand-header strong{font-size:18px}.brand-header span,.muted,.workspace-branch,.workspace-worktree{color:#667071;font-size:13px}.sidebar-section{margin-bottom:8px;border:1px solid #e0d6c7;border-radius:8px;background:#fffdfa;overflow:hidden}.sidebar-section-toggle{display:grid;grid-template-columns:minmax(0,1fr) auto;gap:8px;align-items:center;width:100%;min-height:34px;border:0;border-radius:0;background:transparent;color:#1c2024;font-size:13px;font-weight:750;text-align:left}.sidebar-section-toggle:hover{background:#f5f1e8}.sidebar-section-toggle[aria-expanded=true]{border-bottom:1px solid #ece5d9}.sidebar-section-chevron{width:8px;height:8px;border-color:currentColor;border-style:solid;border-width:0 2px 2px 0;transform:rotate(45deg)}.sidebar-section-toggle[aria-expanded=true] .sidebar-section-chevron{transform:rotate(-135deg)}.sidebar-section-content{padding:8px}.repo-connect,.project-summary,.harness-panel,.task-create{margin:0}.inline-form{display:grid;grid-template-columns:minmax(0,1fr);gap:8px}.inline-form.has-recent-paths{grid-template-columns:minmax(0,1fr) auto}.inline-form>input{grid-column:1 / -1}.inline-form>button{justify-self:end}.inline-form.has-recent-paths>button{justify-self:auto}.repo-recent-select{min-width:0;max-width:none}.project-summary dl{display:grid;gap:8px;margin:0}.project-summary div{min-width:0}.project-summary dt{color:#6c6255;font-size:12px}.project-summary dd{margin:0;overflow-wrap:anywhere;font-size:13px}.warnings,.error-banner{border:1px solid #c87b54;background:#fff4ed;color:#6f3218;border-radius:6px;padding:10px 12px}.warnings{margin:12px 0 0;padding-left:26px;font-size:13px}.harness-panel{display:grid;gap:8px}.harness-panel-header{display:flex;justify-content:space-between;gap:8px;align-items:center}.harness-panel-header h2,.harness-panel-header p,.harness-result p{margin-bottom:0}.harness-actions{display:flex;flex-wrap:wrap;gap:6px;justify-content:flex-end}.harness-file-list{display:grid;gap:6px;margin:0;padding:0;list-style:none}.harness-file-list li{display:grid;grid-template-columns:minmax(0,1fr) auto;gap:8px;align-items:center;border:1px solid #ece5d9;border-radius:6px;padding:6px 8px;background:#fffdfa}.harness-file-list span{overflow:hidden;font-size:12px;font-weight:650;text-overflow:ellipsis;white-space:nowrap}.harness-changes,.harness-result{border:1px solid #e0d6c7;border-radius:6px;padding:8px;background:#f8f7f2;font-size:12px}.harness-changes h3{margin:0 0 4px;font-size:12px}.harness-changes ul,.harness-result ul{margin:0;padding-left:18px}.task-create form{display:grid;gap:8px}.task-create-preview{display:grid;gap:2px;border:1px solid #e0d6c7;border-radius:6px;background:#f8f7f2;padding:6px 8px}.task-create-option{display:flex;align-items:center;gap:8px;color:#1f242b;font-size:13px;font-weight:700}.task-create-option input{width:16px;height:16px;margin:0}.task-create-preview span{color:#255f3d;font-size:12px;font-weight:700}.task-create-preview small{overflow:hidden;color:#687273;font-size:11px;text-overflow:ellipsis;white-space:nowrap}.task-nav{display:grid;gap:8px}.task-nav-item{display:grid;grid-template-columns:minmax(0,1fr) auto;gap:8px;align-items:center;text-align:left}.task-nav-item.is-active,.role-tab.is-active{border-color:#2f6f73;background:#e8f1ef}.sidebar-settings{display:grid;gap:8px}.sidebar-settings button{display:grid;grid-template-columns:minmax(0,1fr) auto;gap:8px;align-items:center;width:100%;text-align:left}.sidebar-settings .settings-toggle.is-active{border-color:#2f6f73;background:#e8f1ef}.sidebar-settings .theme-mode-toggle span:last-child{font-weight:750}.workspace-header{display:grid;grid-template-columns:minmax(180px,auto) minmax(420px,1fr) auto auto;gap:16px;align-items:center;margin-bottom:6px}.workspace-title-line{display:flex;flex-wrap:wrap;gap:10px;align-items:baseline;min-width:0}.workspace-title-line h1{margin-bottom:0;font-size:18px;line-height:1.15}.workspace-branch{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.workspace-worktree{max-width:260px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.eyebrow{color:#7a5c2f;font-size:12px;font-weight:700;text-transform:uppercase}.role-tabs{display:grid;grid-template-columns:repeat(4,minmax(0,1fr));gap:6px;margin-bottom:8px;min-width:0}.workspace-header .role-tabs{margin-bottom:0}.role-tab{display:grid;grid-template-columns:minmax(0,1fr) auto;gap:6px;align-items:center;min-height:30px;padding:4px 8px;text-align:left}.workflow-panel{display:grid;gap:8px;margin:0}.workflow-summary p{margin-bottom:0}.workflow-summary p{color:#4f5558;font-size:13px}.workflow-steps{display:grid;grid-template-columns:minmax(0,1fr);gap:6px;margin:0;padding:0;list-style:none}.workflow-steps li{display:grid;grid-template-columns:minmax(0,1fr) auto;gap:6px;align-items:center;min-height:28px;border:1px solid #ece5d9;border-radius:6px;padding:4px 6px;background:#fffdfa}.workflow-steps li.is-current{border-color:#2f6f73;background:#e8f1ef}.workflow-steps span{overflow:hidden;color:#394246;font-size:12px;font-weight:650;text-overflow:ellipsis;white-space:nowrap}.workspace-grid{display:grid;grid-template-columns:minmax(0,1fr);flex:1;gap:10px;align-items:stretch;min-height:0}.workspace-main{min-width:0;min-height:0;display:flex;flex-direction:column;gap:8px}.role-console-stack{min-width:0;min-height:0;flex:1;display:flex;flex-direction:column}.role-console-panel{min-width:0;min-height:0;flex:1;display:none}.role-console-panel.is-active{display:flex;flex-direction:column}.session-console,.message-panel,.event-log,.empty-workspace{border:1px solid #d6d0c6;border-radius:8px;background:#fffdf8;padding:10px}.task-workspace{display:flex;flex-direction:column;gap:8px;height:100%;min-height:0}.session-console{display:grid;grid-template-rows:auto minmax(0,1fr);gap:8px;flex:1;height:100%;min-height:0}.session-console-top{display:flex;gap:10px;align-items:center;justify-content:space-between}.session-controls{display:flex;flex-wrap:wrap;gap:8px;align-items:center;justify-content:space-between;margin:0 0 8px}.permission-mode-field{display:grid;grid-template-columns:auto minmax(180px,260px);gap:8px;align-items:center;width:fit-content;max-width:100%}.permission-mode-field span{color:#5f6a6c;font-size:13px;font-weight:650}.permission-mode-field small{display:block;color:#7b8587;font-size:11px;font-weight:500;line-height:1.2}.permission-mode-field select{width:100%;min-height:30px;border:1px solid #b9b0a1;border-radius:6px;background:#fffdf8;color:#202326;padding:4px 8px}.session-toolbar{display:flex;flex-wrap:wrap;gap:6px;justify-content:flex-end}.session-toolbar button{min-height:30px;padding:4px 9px}.translation-toggle{display:inline-flex;align-items:center;justify-content:center;min-height:28px;border:1px solid #b5bec4;border-radius:6px;background:#fffefa;color:#4f5558;font-size:12px;font-weight:650;padding:3px 10px;white-space:nowrap}.translation-toggle.is-active{border-color:#2f7e84;background:#e8f4f2;color:#145e64}.translation-settings-grid input[type=checkbox]{width:auto}.session-console-body{display:grid;grid-template-columns:minmax(0,1fr);min-width:0;min-height:0;height:100%}.session-console-body.has-translation{display:grid;grid-template-columns:minmax(0,1fr) minmax(0,1fr);gap:10px;align-items:stretch}.terminal-pane,.translation-pane{display:grid;min-width:0;min-height:0;height:100%}.terminal-frame,.terminal-empty{width:100%;height:100%;min-height:0;border-radius:6px;overflow:hidden;background:#111316}.terminal-empty{display:grid;place-items:center;align-content:center;gap:8px;color:#d6d0c6;border:1px solid #292d31}.translation-panel{display:grid;grid-template-rows:auto minmax(0,1fr) auto;gap:8px;height:100%;min-height:0;border:1px solid #292d31;border-radius:6px;background:#0d1117;color:#d6deeb;padding:8px;min-width:0;width:100%;overflow:hidden;font-family:Menlo,Monaco,Consolas,monospace}.translation-panel-header{display:grid;gap:3px}.translation-panel-titlebar,.translation-panel-actions,.translation-status-row{display:flex;flex-wrap:wrap;gap:6px;align-items:center;justify-content:space-between}.translation-panel-header h2,.translation-panel-header p{margin-bottom:0}.translation-panel-titlebar h2{font-size:16px}.translation-panel-header p,.translation-composer span{color:#8b949e;font-size:12px}.translation-panel-actions button{border-color:#3a4149;background:#161b22;color:#d6deeb;min-height:26px;padding:2px 8px;font-size:12px}.translation-panel-actions button:hover:not(:disabled),.translation-composer-actions button:hover:not(:disabled){border-color:#58a6ff;background:#1f2937}.translation-panel-actions .auto-send-toggle.is-active{border-color:#56d364;background:#12261a;color:#d6deeb}.translation-panel-actions{justify-content:flex-end}.translation-status-row{flex-wrap:nowrap}.translation-status-row p:last-child{flex:0 0 auto;text-align:right}.translation-entry-list{display:grid;align-content:start;gap:8px;min-height:0;min-width:0;overflow-x:hidden;overflow-y:auto;scrollbar-color:#4b5563 #0d1117}.translation-entry{border:0;border-radius:0;background:transparent;min-width:0;max-width:100%;padding:0}.translation-entry pre{box-sizing:border-box;margin:0;max-height:none;max-width:100%;min-width:0;overflow:visible;white-space:pre-wrap;overflow-wrap:anywhere;font-family:Menlo,Monaco,Consolas,monospace;font-size:12px;line-height:1.45;color:#d6deeb}.translation-markdown{max-width:100%;min-width:0;color:#d6deeb;font-size:12px;line-height:1.55;overflow-wrap:anywhere}.translation-markdown>:first-child{margin-top:0}.translation-markdown>:last-child{margin-bottom:0}.translation-markdown p,.translation-markdown ul,.translation-markdown ol,.translation-markdown blockquote,.translation-markdown pre,.translation-markdown table{margin:0 0 8px}.translation-markdown h1,.translation-markdown h2,.translation-markdown h3,.translation-markdown h4,.translation-markdown h5,.translation-markdown h6{margin:10px 0 6px;color:#f0f6fc;font-weight:700;line-height:1.25}.translation-markdown h1{font-size:17px}.translation-markdown h2{font-size:15px}.translation-markdown h3,.translation-markdown h4,.translation-markdown h5,.translation-markdown h6{font-size:13px}.translation-markdown ul,.translation-markdown ol{padding-left:22px}.translation-markdown li{margin:2px 0}.translation-markdown .task-list-item{list-style:none}.translation-markdown input[type=checkbox]{width:13px;height:13px;margin:0 6px 0 0;accent-color:#56d364}.translation-markdown blockquote{border-left:3px solid #3a4149;color:#b7c0ca;padding-left:10px}.translation-markdown a{color:#79c0ff}.translation-markdown code{border-radius:4px;background:#161b22;color:#f0f6fc;padding:1px 4px;font-family:Menlo,Monaco,Consolas,monospace;font-size:.95em}.translation-markdown pre{overflow-x:auto;border:1px solid #292d31;border-radius:6px;background:#111316;padding:8px;white-space:pre}.translation-markdown pre code{background:transparent;padding:0}.translation-markdown table{display:block;max-width:100%;overflow-x:auto;border-collapse:collapse}.translation-markdown img{max-width:100%;border-radius:4px}.translation-markdown th,.translation-markdown td{border:1px solid #30363d;padding:4px 6px;text-align:left;vertical-align:top}.translation-markdown hr{border:0;border-top:1px solid #292d31;margin:10px 0}.translation-entry.is-tool-output pre{display:block;overflow:hidden;color:#7d8590;text-overflow:ellipsis;white-space:nowrap;width:100%}.translation-entry-note{margin:2px 0 0;color:#6e7681;font-size:10px;line-height:1.35}.translation-entry-note.is-error{color:#a3715f}.translation-composer{display:grid;gap:6px;border-top:1px solid #292d31;padding-top:8px}.translation-composer-row{display:grid;grid-template-columns:minmax(0,1fr) auto;gap:8px;align-items:stretch}.translation-composer textarea{width:100%;min-height:38px;max-height:88px;border-color:#3a4149;background:#0d1117;color:#d6deeb;font-family:inherit;font-size:12px;line-height:1.35;resize:vertical}.translation-composer textarea::placeholder{color:#7d8590}.translation-composer textarea::selection{background:#8b949e59;color:#fff}.translation-composer textarea:focus,.translation-composer textarea:focus-visible{border-color:#4b5563;outline:none;box-shadow:none}.translation-composer-actions{display:grid;align-content:start;gap:6px;min-width:104px}.translation-composer-actions button{border-color:#3a4149;background:#161b22;color:#d6deeb;width:100%;min-height:38px;padding:4px 9px;font-size:12px}.translation-panel .muted{color:#8b949e}.translation-panel .error-banner{border-color:#da7b72;background:#2d1518;color:#ffdcd7}.modal-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:20;display:grid;place-items:center;background:#181c1f61;padding:18px}.translation-settings-modal{display:grid;gap:12px;width:min(980px,100%);max-height:min(760px,92vh);overflow:auto;border:1px solid #d6d0c6;border-radius:8px;background:#fffdf8;padding:14px}.message-modal,.event-modal{display:grid;grid-template-rows:auto minmax(0,1fr);gap:12px;width:min(980px,100%);max-height:min(760px,92vh);overflow:hidden;border:1px solid #d6d0c6;border-radius:8px;background:#fffdf8;padding:14px}.translation-settings-modal header,.message-modal header,.event-modal header,.translation-settings-modal footer{display:flex;gap:8px;align-items:center;justify-content:space-between}.translation-prompt-settings{display:grid;gap:10px;border-top:1px solid #ece5d9;padding-top:12px}.translation-prompt-settings header{display:flex;gap:10px;align-items:end;justify-content:space-between}.translation-prompt-settings h3,.translation-prompt-settings p{margin-bottom:0}.translation-prompt-settings h3{font-size:13px}.translation-prompt-settings textarea{min-height:120px;max-height:260px;font-family:Menlo,Monaco,Consolas,monospace;font-size:12px}.translation-prompt-stack{display:grid;gap:10px}.translation-prompt-stack label{display:grid;gap:4px}.translation-prompt-stack span{color:#4f5558;font-size:12px;font-weight:650}.translation-settings-modal h2,.message-modal h2,.message-modal p,.event-modal h2,.event-modal p,.translation-settings-modal p{margin-bottom:0}.translation-settings-grid{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:10px}.translation-settings-grid label{display:grid;gap:4px}.translation-settings-grid span{color:#4f5558;font-size:12px;font-weight:650}.translation-settings-grid select,.translation-prompt-settings select{min-height:34px;border:1px solid #b9b0a1;border-radius:6px;background:#fffdf8;color:#202326;padding:6px 10px}.translation-test-result{border-radius:6px;padding:8px;font-size:13px}.translation-test-result.is-ok{border:1px solid #6ea77e;background:#e6f3e9;color:#245334}.translation-test-result.is-error{border:1px solid #c46e5f;background:#fae9e6;color:#6f2b21}.message-panel{display:grid;gap:8px}.message-modal .message-panel,.event-modal .event-log{min-height:0;overflow:auto;border:0;background:transparent;padding:0}.message-panel-header{display:flex;justify-content:space-between;gap:12px;align-items:center}.message-panel-header h2,.message-panel-header p{margin-bottom:0}.message-controls,.message-mode-toggle,.message-actions{display:flex;flex-wrap:wrap;gap:8px;align-items:center}.message-mode-toggle{color:#4f5558;font-size:13px;font-weight:650}.message-mode-toggle input{width:auto}.message-list{display:grid;gap:8px;margin:0;padding:0;list-style:none}.message-item{display:grid;grid-template-columns:minmax(0,1fr) auto;gap:10px;align-items:start;border:1px solid #ece5d9;border-radius:6px;padding:8px;background:#fffdfa}.message-meta{display:flex;flex-wrap:wrap;gap:8px;align-items:center;margin-bottom:4px}.message-meta time,.message-meta span:not(.status-badge),.message-path{color:#667071;font-size:12px}.message-sequence{min-width:32px;color:#1f242b;font-weight:800}.message-actions button{min-height:30px;padding:4px 10px}.message-item p{display:-webkit-box;margin-bottom:4px;overflow:hidden;-webkit-box-orient:vertical;-webkit-line-clamp:2}.message-path{display:block;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.event-log ol{margin:0;padding-left:22px;font-size:13px}.event-log{max-height:92px;overflow:auto}.event-log h2{margin-bottom:4px;font-size:13px}.event-log p{margin-bottom:0}.event-log li{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.status-badge{display:inline-flex;align-items:center;justify-content:center;min-width:66px;min-height:20px;border-radius:999px;padding:2px 8px;border:1px solid #c7c1b8;background:#f2eee7;color:#4f5558;font-size:11px;white-space:nowrap}.status-running,.status-ok{border-color:#6ea77e;background:#e6f3e9;color:#245334}.status-blocked,.status-crashed,.status-missing,.status-empty{border-color:#c46e5f;background:#fae9e6;color:#6f2b21}.status-waiting,.status-starting,.status-incomplete{border-color:#c4a34e;background:#f7efcf;color:#604e16}.status-exited,.status-done,.status-resumable,.status-staged,.status-delivered,.status-acknowledged{border-color:#7b98b8;background:#e9f0f8;color:#2e4e70}.status-pending_approval,.status-queued,.status-translating,.status-ready,.status-create,.status-insert,.status-update{border-color:#c4a34e;background:#f7efcf;color:#604e16}.status-rejected,.status-failed,.status-cancelled,.status-blocked{border-color:#c46e5f;background:#fae9e6;color:#6f2b21}.status-pending{border-color:#c7c1b8;background:#f2eee7;color:#4f5558}.status-translated,.status-preserved{border-color:#7b98b8;background:#e9f0f8;color:#2e4e70}.empty-workspace{max-width:680px}@media(max-width:980px){.app-shell,.workspace-grid{grid-template-columns:1fr}.app-sidebar{border-right:0;border-bottom:1px solid #d3c9b8}.role-tabs{grid-template-columns:repeat(2,minmax(0,1fr))}.workflow-panel,.workflow-steps,.session-console-body.has-translation,.translation-settings-grid{grid-template-columns:1fr}}@media(max-width:560px){.app-main,.app-sidebar{padding:12px}.workspace-header,.inline-form,.inline-form.has-recent-paths{grid-template-columns:1fr;display:grid}.role-tabs{grid-template-columns:1fr}.terminal-frame,.terminal-empty{min-height:300px;height:54vh}.permission-mode-field{grid-template-columns:1fr;width:100%}}:root[data-theme=dark]{color-scheme:dark;background:#0d1117;color:#e6edf3}:root[data-theme=dark] body,:root[data-theme=dark] .app-main{background:#0d1117;color:#e6edf3}:root[data-theme=dark] button{border-color:#3d4652;background:#161b22;color:#e6edf3}:root[data-theme=dark] button:hover:not(:disabled){border-color:#58a6ff;background:#1f2937}:root[data-theme=dark] input,:root[data-theme=dark] select,:root[data-theme=dark] textarea:not(.xterm-helper-textarea){border-color:#3d4652;background:#0d1117;color:#e6edf3}:root[data-theme=dark] input::placeholder,:root[data-theme=dark] textarea::placeholder{color:#7d8590}:root[data-theme=dark] .danger-button{border-color:#da7b72;background:#2d1518;color:#ffdcd7}:root[data-theme=dark] .danger-button:hover:not(:disabled){border-color:#ffa198;background:#3d1f23}:root[data-theme=dark] .app-sidebar{border-color:#30363d;background:#0f141b}:root[data-theme=dark] .sidebar-toggle{background:#161b22}:root[data-theme=dark] .brand-header span,:root[data-theme=dark] .muted,:root[data-theme=dark] .workspace-branch,:root[data-theme=dark] .workspace-worktree,:root[data-theme=dark] .message-meta time,:root[data-theme=dark] .message-meta span:not(.status-badge),:root[data-theme=dark] .message-path{color:#8b949e}:root[data-theme=dark] .sidebar-section,:root[data-theme=dark] .session-console,:root[data-theme=dark] .message-panel,:root[data-theme=dark] .event-log,:root[data-theme=dark] .empty-workspace,:root[data-theme=dark] .translation-settings-modal,:root[data-theme=dark] .message-modal,:root[data-theme=dark] .event-modal{border-color:#30363d;background:#11161d}:root[data-theme=dark] .sidebar-section-toggle{color:#e6edf3}:root[data-theme=dark] .sidebar-section-toggle:hover{background:#161b22}:root[data-theme=dark] .sidebar-section-toggle[aria-expanded=true],:root[data-theme=dark] .translation-prompt-settings{border-color:#30363d}:root[data-theme=dark] .project-summary dt,:root[data-theme=dark] .permission-mode-field span,:root[data-theme=dark] .translation-settings-grid span,:root[data-theme=dark] .translation-prompt-stack span,:root[data-theme=dark] .message-mode-toggle,:root[data-theme=dark] .workflow-summary p{color:#b7c0ca}:root[data-theme=dark] .permission-mode-field small,:root[data-theme=dark] .task-create-preview small{color:#8b949e}:root[data-theme=dark] .warnings,:root[data-theme=dark] .error-banner{border-color:#da7b72;background:#2d1518;color:#ffdcd7}:root[data-theme=dark] .harness-file-list li,:root[data-theme=dark] .harness-changes,:root[data-theme=dark] .harness-result,:root[data-theme=dark] .task-create-preview,:root[data-theme=dark] .workflow-steps li,:root[data-theme=dark] .message-item{border-color:#30363d;background:#0d1117}:root[data-theme=dark] .task-create-option{color:#e6edf3}:root[data-theme=dark] .task-create-preview span{color:#7ee787}:root[data-theme=dark] .workflow-steps span{color:#d6deeb}:root[data-theme=dark] .message-sequence{color:#f0f6fc}:root[data-theme=dark] .eyebrow{color:#d29922}:root[data-theme=dark] .task-nav-item.is-active,:root[data-theme=dark] .role-tab.is-active,:root[data-theme=dark] .workflow-steps li.is-current,:root[data-theme=dark] .sidebar-settings .settings-toggle.is-active,:root[data-theme=dark] .translation-toggle.is-active{border-color:#56d4dd;background:#10262b;color:#d6fbff}:root[data-theme=dark] .translation-toggle{border-color:#3d4652;background:#161b22;color:#b7c0ca}:root[data-theme=dark] .permission-mode-field select,:root[data-theme=dark] .translation-settings-grid select,:root[data-theme=dark] .translation-prompt-settings select{border-color:#3d4652;background:#0d1117;color:#e6edf3}:root[data-theme=dark] .terminal-empty{border-color:#30363d}:root[data-theme=dark] .modal-backdrop{background:#010409b8}:root[data-theme=dark] .message-modal .message-panel,:root[data-theme=dark] .event-modal .event-log{background:transparent}:root[data-theme=dark] .status-badge{border-color:#3d4652;background:#161b22;color:#d6deeb}:root[data-theme=dark] .translation-test-result.is-ok,:root[data-theme=dark] .status-running,:root[data-theme=dark] .status-ok{border-color:#3fb950;background:#12261a;color:#aff5b4}:root[data-theme=dark] .translation-test-result.is-error,:root[data-theme=dark] .status-blocked,:root[data-theme=dark] .status-crashed,:root[data-theme=dark] .status-missing,:root[data-theme=dark] .status-empty,:root[data-theme=dark] .status-rejected,:root[data-theme=dark] .status-failed,:root[data-theme=dark] .status-cancelled{border-color:#f85149;background:#2d1518;color:#ffdcd7}:root[data-theme=dark] .status-waiting,:root[data-theme=dark] .status-starting,:root[data-theme=dark] .status-incomplete,:root[data-theme=dark] .status-pending_approval,:root[data-theme=dark] .status-queued,:root[data-theme=dark] .status-translating,:root[data-theme=dark] .status-ready,:root[data-theme=dark] .status-create,:root[data-theme=dark] .status-insert,:root[data-theme=dark] .status-update{border-color:#d29922;background:#2d2208;color:#f8e3a1}:root[data-theme=dark] .status-exited,:root[data-theme=dark] .status-done,:root[data-theme=dark] .status-resumable,:root[data-theme=dark] .status-staged,:root[data-theme=dark] .status-delivered,:root[data-theme=dark] .status-acknowledged,:root[data-theme=dark] .status-translated,:root[data-theme=dark] .status-preserved{border-color:#388bfd;background:#10223a;color:#c9e2ff}:root[data-theme=dark] .status-pending{border-color:#3d4652;background:#161b22;color:#d6deeb}
@@ -4,8 +4,8 @@
4
4
  <meta charset="UTF-8" />
5
5
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
6
6
  <title>VibeCodingMaster</title>
7
- <script type="module" crossorigin src="/assets/index-D59GuHCR.js"></script>
8
- <link rel="stylesheet" crossorigin href="/assets/index-CuiNNOzj.css">
7
+ <script type="module" crossorigin src="/assets/index-B1vIIwLq.js"></script>
8
+ <link rel="stylesheet" crossorigin href="/assets/index-DPyKuEOz.css">
9
9
  </head>
10
10
  <body>
11
11
  <div id="root"></div>
@@ -1486,11 +1486,11 @@ Branch rules:
1486
1486
  - large work should use phase commits on the same task branch unless phases are independently releasable
1487
1487
  - if a task becomes too large, split it into child tasks with explicit branch and PR ownership
1488
1488
 
1489
- Cleanup rules:
1489
+ Close Task rules:
1490
1490
 
1491
- - after task completion, remove the task worktree only after role sessions are stopped and uncommitted work is handled
1492
- - remove VCM task/session/message/orchestration metadata with the worktree cleanup
1493
- - keep the task branch by default until PR merge; delete it only with explicit confirmation
1491
+ - after task completion, use VCM `Close Task` only when the user is ready to delete task-local state
1492
+ - for worktree-backed tasks, `Close Task` deletes the task worktree, deletes the task branch by default, and removes VCM task/session/message/orchestration metadata
1493
+ - `Close Task` does not check running role sessions or uncommitted changes; finish, commit, or preserve anything important before using it
1494
1494
 
1495
1495
  Small commits:
1496
1496
 
@@ -66,7 +66,7 @@ The workflow is a soft guide in V1. VCM computes readiness from handoff artifact
66
66
 
67
67
  ### 4.1 Task Worktree Model
68
68
 
69
- Task-level worktree management is the current model for multi-task parallelism:
69
+ Task-level worktree management is the recommended default model for multi-task parallelism:
70
70
 
71
71
  ```text
72
72
  one task
@@ -78,7 +78,9 @@ one task
78
78
 
79
79
  VCM must not create worktrees per role. `project-manager`, `architect`, `coder`, and `reviewer` for the same task all run in the same task worktree and hand off sequentially.
80
80
 
81
- When the user creates a task, VCM creates the branch and worktree immediately. There is no separate later button named `Create task worktree`, and a task cannot be switched to another worktree after creation.
81
+ When the user creates a task, `Create worktree and branch` is selected by default. With that option selected, VCM creates the branch and worktree immediately. If the user clears the option, VCM creates the task in the currently connected repository path and records the current branch.
82
+
83
+ There is no separate later button named `Create task worktree`, and a task cannot be switched between worktree and non-worktree mode after creation.
82
84
 
83
85
  Branch naming:
84
86
 
@@ -108,27 +110,33 @@ Task creation flow:
108
110
  ```text
109
111
  New Task submit
110
112
  -> validate task name
111
- -> derive branch feature/<task-name>
112
- -> derive worktree path .ai/vcm/worktrees/<task-name>
113
- -> verify .ai/vcm/ is ignored and the base repo is clean
114
- -> git worktree add -b feature/<task-name> .ai/vcm/worktrees/<task-name> <base-ref>
113
+ -> verify .ai/vcm/ is ignored
114
+ -> if Create worktree and branch is selected:
115
+ -> derive branch feature/<task-name>
116
+ -> derive worktree path .ai/vcm/worktrees/<task-name>
117
+ -> verify the base repo is clean
118
+ -> git worktree add -b feature/<task-name> .ai/vcm/worktrees/<task-name> <base-ref>
119
+ -> otherwise:
120
+ -> use the connected repo path and current branch
115
121
  -> create task metadata
116
- -> create handoff structure inside the task worktree
117
- -> open the task workspace with role session cwd = task worktree
122
+ -> create handoff structure inside the task runtime repo
123
+ -> open the task workspace with role session cwd = task runtime repo
118
124
  ```
119
125
 
120
- Task cleanup flow:
126
+ Task close flow:
121
127
 
122
128
  ```text
123
- task complete
124
- -> stop running role sessions
125
- -> verify task worktree is safe to remove
126
- -> remove git worktree
127
- -> remove VCM task/session/message/orchestration metadata
128
- -> keep or delete branch according to guarded branch cleanup policy
129
+ user clicks red Close Task
130
+ -> show destructive confirmation
131
+ -> explain that VCM deletes the task worktree and task branch
132
+ -> explain that VCM does not check running sessions or uncommitted changes
133
+ -> remove git worktree when the task owns one
134
+ -> delete the task branch by default when the task owns one
135
+ -> remove VCM task metadata from the base repo
136
+ -> remove task runtime metadata from the task runtime repo
129
137
  ```
130
138
 
131
- Branch deletion should be a separate guarded confirmation, ideally only after the branch is merged or the user explicitly confirms deletion. Worktree cleanup itself removes the local working directory and task metadata.
139
+ Tasks created without a worktree do not own a separate branch/worktree, so Close Task removes only VCM metadata for those tasks.
132
140
 
133
141
  ## 5. Roles
134
142
 
@@ -242,10 +250,13 @@ The old `Dirty: yes/no` label is not used. The UI uses `Working tree: clean` or
242
250
 
243
251
  `Settings` contains:
244
252
 
253
+ - `Theme` button, cycling through `System`, `Light`, and `Dark`.
245
254
  - `Messages` button, opening a modal list of role messages.
246
255
  - `Events` button, opening a modal list of runtime UI events for the current task.
247
256
  - `Auto orchestration` on/off toggle.
248
257
 
258
+ The default theme mode is `System`, which follows the OS/browser color-scheme preference. The entire application chrome, sidebar, forms, modals, status badges, and workspace panels must support both light and dark rendering. Embedded terminals keep their terminal-native dark styling.
259
+
249
260
  There is no separate `Pause orchestration` or `Resume orchestration` control in the GUI. The current product model is one on/off toggle.
250
261
 
251
262
  `VCM Harness` shows whether VCM managed blocks are installed/up to date in the project rules files and `.gitignore`.
@@ -253,13 +264,14 @@ There is no separate `Pause orchestration` or `Resume orchestration` control in
253
264
  `New Task` contains:
254
265
 
255
266
  - `task name`
256
- - a checked, non-optional `Create worktree and branch` indicator
257
- - generated branch preview: `feature/<task-name>`
258
- - generated worktree preview: `.ai/vcm/worktrees/<task-name>`
267
+ - a `Create worktree and branch` checkbox, selected by default
268
+ - generated branch preview when selected: `feature/<task-name>`
269
+ - generated worktree preview when selected: `.ai/vcm/worktrees/<task-name>`
270
+ - current repository/current branch note when cleared
259
271
 
260
272
  There is no optional title input in the current UI.
261
273
 
262
- The worktree/branch path is the normal VCM task model, not a separate mode users toggle later. The checked indicator is shown so the user understands what will happen; VCM should not require a separate worktree creation action later.
274
+ The worktree/branch path is the recommended VCM task model, but the user may clear the checkbox for an inline task. VCM should not require a separate worktree creation action later.
263
275
 
264
276
  ### Task Workspace
265
277
 
@@ -367,7 +379,7 @@ For `.gitignore`, VCM uses hash comments:
367
379
  # VCM:END
368
380
  ```
369
381
 
370
- `.ai/vcm/` is the active VCM local control area for task state, session state, orchestration state, and task worktrees.
382
+ `.ai/vcm/` is the active VCM local control area. The base repo keeps the task index and nested worktrees; each task runtime repo keeps its own session, message, orchestration, and translation state.
371
383
 
372
384
  VCM must preserve all user-authored content outside the managed block.
373
385
 
@@ -468,7 +480,7 @@ Prompt slots:
468
480
  - `zh-to-en-with-context`
469
481
  - `en-to-zh`
470
482
 
471
- The settings modal shows the default prompt for each slot and allows a user override. Empty override means use the default prompt.
483
+ The settings modal shows all three prompt slots as direct editors. `Reset prompts` restores every prompt to its built-in default. The modal does not include separate enable/output/input-mode switches; opening the role toolbar `Translate` panel is the translation on/off control, and the panel-level `Auto-send` toggle controls whether translated user input is submitted automatically.
472
484
 
473
485
  ### Claude Output Translation
474
486
 
@@ -482,6 +494,16 @@ VCM tails Claude Code transcript JSONL files under:
482
494
 
483
495
  The transcript path is persisted in the role session record. If that path is missing, VCM falls back to resolving by current working directory and then scanning `~/.claude/projects` for the newest file with the session id.
484
496
 
497
+ VCM owns transcript listening in the backend. Opening the translation panel starts or confirms the backend tailer for the active role session. Closing the panel does not stop that tailer; it keeps collecting Claude output until the role session is stopped/restarted or the task is closed. This keeps translation capture independent from frontend rendering.
498
+
499
+ Backend translation cache lives under:
500
+
501
+ ```text
502
+ <taskRepoRoot>/.ai/vcm/translation/<task>/<role>/<session-id>.jsonl
503
+ ```
504
+
505
+ The frontend does not subscribe through WebSocket. It polls the backend with a cursor and receives new cached events. The cursor means "next expected seq": `after=18` confirms that seq `1..17` have already been displayed, so the backend can remove those cached events and return seq `18` and later. If the cursor is older than the retained cache, VCM still returns whatever newer events remain; it does not use a snapshot error mode.
506
+
485
507
  Transcript event handling:
486
508
 
487
509
  - assistant text -> `prose` -> translated
@@ -496,9 +518,12 @@ Display behavior:
496
518
  - `prose` starts by showing the English source.
497
519
  - while translating, panel status shows `translating <elapsed>`.
498
520
  - when translation succeeds, the English source is replaced by Chinese translated text.
521
+ - `prose` content is rendered as Markdown, including headings, lists, code fences, tables, and links.
499
522
  - when translation fails, panel status shows `error` and the entry keeps the visible source plus an error.
500
523
  - `tool-output` is dim, one-line, truncated by CSS, and not translated.
501
524
 
525
+ Long translations do not block capture. Prose entries are pushed to the panel before provider translation starts. `tool_use` and `tool_result` entries are never added to the translation queue; they are displayed immediately.
526
+
502
527
  There is no keyword classifier that drops assistant text. A previous design skipped permission-looking or log-looking text; that is removed.
503
528
 
504
529
  ### User Input Translation
@@ -512,7 +537,7 @@ Keyboard behavior:
512
537
 
513
538
  After translation succeeds, the English draft replaces the original Chinese text in the same textarea.
514
539
 
515
- `Send English` writes the current English text to the active role terminal and submits Enter.
540
+ `Send English` pastes the current English text into the active role terminal, then sends Enter as a separate terminal input event.
516
541
 
517
542
  Translation panel `Auto-send` is separate from task `Auto orchestration`:
518
543
 
@@ -527,13 +552,16 @@ App-level settings:
527
552
  ~/.vcm/settings.json
528
553
  ```
529
554
 
555
+ Stored app-level settings include:
556
+
557
+ - UI theme mode: `system`, `light`, or `dark`
558
+ - translation provider settings and API key
559
+ - recent repository paths
560
+
530
561
  Repository-level VCM state:
531
562
 
532
563
  ```text
533
564
  .ai/vcm/tasks/<task>.json
534
- .ai/vcm/sessions/<task>.json
535
- .ai/vcm/messages/<task>.jsonl
536
- .ai/vcm/orchestration/<task>.json
537
565
  .ai/vcm/worktrees/<task>/
538
566
  ```
539
567
 
@@ -544,14 +572,20 @@ Project config:
544
572
  ~/.vcm/projects/index.json
545
573
  ```
546
574
 
547
- The base repository's `.ai/vcm/` directory is the repository-local runtime control area. Long-lived project config is stored under `~/.vcm` so it survives outside Git-ignored repo state. Task source changes and handoff artifacts live inside the task worktree at `.ai/vcm/worktrees/<task>/`.
575
+ The base repository's `.ai/vcm/` directory stores the task index and nested task worktrees. Long-lived project config is stored under `~/.vcm` so it survives outside Git-ignored repo state.
548
576
 
549
577
  Task worktree local files:
550
578
 
551
579
  ```text
580
+ .ai/vcm/worktrees/<task>/.ai/vcm/sessions/<task>.json
581
+ .ai/vcm/worktrees/<task>/.ai/vcm/messages/<task>.jsonl
582
+ .ai/vcm/worktrees/<task>/.ai/vcm/orchestration/<task>.json
583
+ .ai/vcm/worktrees/<task>/.ai/vcm/translation/<task>/
552
584
  .ai/vcm/worktrees/<task>/.ai/handoffs/<task>/
553
585
  ```
554
586
 
587
+ For tasks created without a worktree, the task runtime repo is the connected base repo, so the runtime state resolves under the base repo's `.ai/vcm/`.
588
+
555
589
  External Claude transcripts:
556
590
 
557
591
  ```text
@@ -583,8 +617,9 @@ This protects against publishing raw TypeScript bin files or missing frontend as
583
617
  VCM V1 is successful when:
584
618
 
585
619
  - A user can connect a repo without global Git safe-directory setup.
586
- - A user can create a task, which creates `feature/<task>` and `.ai/vcm/worktrees/<task>`.
587
- - A user can start all four role sessions in that task worktree.
620
+ - A user can create a default task, which creates `feature/<task>` and `.ai/vcm/worktrees/<task>`.
621
+ - A user can clear `Create worktree and branch` and create a task in the connected repo/current branch.
622
+ - A user can start all four role sessions in the task runtime repo.
588
623
  - Switching roles never loses the embedded terminal.
589
624
  - Restart creates a fresh Claude session; Resume reconnects to the persisted one.
590
625
  - Permission modes are reflected in the Claude command.
@@ -21,7 +21,7 @@ Runtime shape:
21
21
  ```text
22
22
  browser
23
23
  -> React GUI
24
- -> HTTP API + WebSocket
24
+ -> HTTP API + terminal WebSocket
25
25
  -> Fastify backend
26
26
  -> services
27
27
  -> node-pty
@@ -94,9 +94,9 @@ Responsibilities:
94
94
  - Render repository connect form.
95
95
  - Render repository summary.
96
96
  - Render workflow panel.
97
- - Render settings section with Messages, Events, Auto orchestration.
97
+ - Render settings section with Theme, Messages, Events, Auto orchestration.
98
98
  - Render harness status/actions.
99
- - Render task creation form with one task-name field, a checked non-optional worktree/branch indicator, and generated branch/path previews.
99
+ - Render task creation form with one task-name field, a `Create worktree and branch` checkbox selected by default, and generated branch/path previews when selected.
100
100
  - Render task list.
101
101
  - Render Messages and Events modals.
102
102
 
@@ -140,11 +140,12 @@ File:
140
140
  Responsibilities:
141
141
 
142
142
  - Load translation settings and prompt previews.
143
- - Open translation WebSocket for the current terminal runtime session id.
143
+ - Start backend transcript listening for the current terminal runtime session id.
144
+ - Poll backend translation events with a cursor.
144
145
  - Render dark translation output panel.
145
146
  - Render translation status: `ready`, `translating <elapsed>`, or `error`.
146
147
  - Render preserved tool output as dim one-line rows.
147
- - Render prose source while translating, then translated text after completion.
148
+ - Render prose source while translating, then translated text after completion, using Markdown rendering for prose.
148
149
  - Render user composer.
149
150
  - Translate on `Enter`; newline on `Shift+Enter`.
150
151
  - Replace Chinese input with English draft after translation.
@@ -186,7 +187,6 @@ Fastify registers:
186
187
  - message routes
187
188
  - translation routes
188
189
  - terminal WebSocket
189
- - translation WebSocket
190
190
 
191
191
  ## 5. Repository Connection
192
192
 
@@ -224,12 +224,12 @@ VCM does not require global `safe.directory` configuration.
224
224
 
225
225
  ## 6. Task Worktree Architecture
226
226
 
227
- Task-level worktree management is the current architecture for multi-task parallelism.
227
+ Task-level worktree management is the default architecture for multi-task parallelism.
228
228
 
229
229
  Rule:
230
230
 
231
231
  ```text
232
- one VCM task = one branch + one git worktree + one handoff directory + one role-session set
232
+ default VCM task = one branch + one git worktree + one handoff directory + one role-session set
233
233
  ```
234
234
 
235
235
  Branch name:
@@ -244,7 +244,15 @@ Worktree path:
244
244
  <baseRepoRoot>/.ai/vcm/worktrees/<taskSlug>
245
245
  ```
246
246
 
247
- VCM does not support switching a task to another branch or worktree after creation. If the user needs a different branch/worktree, they should create a new task.
247
+ VCM does not support switching a task to another branch or worktree mode after creation. If the user needs a different branch/worktree choice, they should create a new task.
248
+
249
+ When `Create worktree and branch` is cleared, the task uses:
250
+
251
+ ```text
252
+ branch: current connected-repo branch
253
+ runtime repo root: <baseRepoRoot>
254
+ worktreePath: undefined
255
+ ```
248
256
 
249
257
  VCM does not create worktrees by role. All four role sessions for a task share the same task worktree:
250
258
 
@@ -265,13 +273,10 @@ VCM distinguishes:
265
273
  - `branch`: `feature/<taskSlug>`.
266
274
  - `worktreePath`: same as `taskRepoRoot`.
267
275
 
268
- Project-level VCM control state stays under the base repo:
276
+ Base repo state is only the task index and the container for nested task worktrees:
269
277
 
270
278
  ```text
271
279
  <baseRepoRoot>/.ai/vcm/tasks/<task>.json
272
- <baseRepoRoot>/.ai/vcm/sessions/<task>.json
273
- <baseRepoRoot>/.ai/vcm/messages/<task>.jsonl
274
- <baseRepoRoot>/.ai/vcm/orchestration/<task>.json
275
280
  <baseRepoRoot>/.ai/vcm/worktrees/<task>/
276
281
  ```
277
282
 
@@ -282,13 +287,19 @@ Project configuration is app-local and stored outside the repository:
282
287
  ~/.vcm/projects/index.json
283
288
  ```
284
289
 
285
- Task source changes and handoff artifacts live in the task worktree:
290
+ Task runtime state, source changes, and handoff artifacts live in the task runtime repo. For worktree-backed tasks this is the nested task worktree:
286
291
 
287
292
  ```text
293
+ <baseRepoRoot>/.ai/vcm/worktrees/<task>/.ai/vcm/sessions/<task>.json
294
+ <baseRepoRoot>/.ai/vcm/worktrees/<task>/.ai/vcm/messages/<task>.jsonl
295
+ <baseRepoRoot>/.ai/vcm/worktrees/<task>/.ai/vcm/orchestration/<task>.json
296
+ <baseRepoRoot>/.ai/vcm/worktrees/<task>/.ai/vcm/translation/<task>/
288
297
  <baseRepoRoot>/.ai/vcm/worktrees/<task>/.ai/handoffs/<task>/
289
298
  ```
290
299
 
291
- This central base-state model lets VCM list and manage multiple tasks while each task's code changes happen in a separate worktree.
300
+ For inline tasks, `taskRepoRoot` is the connected base repo, so these same runtime paths resolve under the connected repo's `.ai/vcm/`.
301
+
302
+ This split lets VCM list tasks from the base repo after worktrees are created, while each task's runtime state follows the same root as the role sessions.
292
303
 
293
304
  ### 6.2 Git Ignore Requirement
294
305
 
@@ -307,37 +318,36 @@ The VCM harness manages a `.gitignore` block that ignores `.ai/vcm/` before task
307
318
  ```text
308
319
  POST /api/tasks
309
320
  -> validate taskSlug
310
- -> compute branch feature/<taskSlug>
311
- -> compute worktreePath <baseRepoRoot>/.ai/vcm/worktrees/<taskSlug>
312
- -> assert branch does not already exist
313
- -> assert worktreePath does not already exist
314
321
  -> assert .ai/vcm/ is ignored by Git
315
- -> assert base repo has no uncommitted changes
316
- -> git worktree add -b feature/<taskSlug> <worktreePath> <baseRef>
322
+ -> if createWorktree is not false:
323
+ -> compute branch feature/<taskSlug>
324
+ -> compute worktreePath <baseRepoRoot>/.ai/vcm/worktrees/<taskSlug>
325
+ -> assert branch does not already exist
326
+ -> assert worktreePath does not already exist
327
+ -> assert base repo has no uncommitted changes
328
+ -> git worktree add -b feature/<taskSlug> <worktreePath> <baseRef>
329
+ -> otherwise:
330
+ -> read current base repo branch
331
+ -> leave worktreePath undefined
317
332
  -> create handoff structure in taskRepoRoot
318
333
  -> write central task metadata under baseRepoRoot/.ai/vcm/tasks/<task>.json
319
334
  ```
320
335
 
321
336
  The default `baseRef` is the connected repo's current `HEAD`.
322
337
 
323
- ### 6.4 Task Cleanup Flow
338
+ ### 6.4 Task Close Flow
324
339
 
325
340
  ```text
326
341
  POST /api/tasks/:taskSlug/cleanup
327
- -> require no running role sessions
328
342
  -> load task metadata
329
- -> verify worktree path belongs under <baseRepoRoot>/.ai/vcm/worktrees/
330
- -> check worktree status
331
- -> refuse cleanup when uncommitted work exists unless force is explicitly requested
332
- -> git worktree remove <worktreePath>
333
- -> delete central task/session/message/orchestration metadata
343
+ -> when worktreePath exists, verify it belongs under <baseRepoRoot>/.ai/vcm/worktrees/
344
+ -> when worktreePath exists, git worktree remove --force <worktreePath>
345
+ -> when worktreePath exists, delete the task branch by default
346
+ -> delete base task metadata
347
+ -> delete task runtime session/message/orchestration/translation metadata
334
348
  ```
335
349
 
336
- Branch deletion is intentionally separate:
337
-
338
- - Keep `feature/<taskSlug>` by default.
339
- - Allow branch deletion only with explicit confirmation.
340
- - Prefer allowing deletion only when the branch has been merged, or when the user force-confirms.
350
+ Close Task is intentionally destructive after user confirmation. It does not preflight running role sessions or uncommitted worktree changes. Tasks created without a worktree remove VCM metadata only because there is no VCM-owned branch/worktree to delete.
341
351
 
342
352
  ## 7. Task And Artifact Model
343
353
 
@@ -480,7 +490,7 @@ Permission flags:
480
490
  Session persistence:
481
491
 
482
492
  ```text
483
- <baseRepoRoot>/.ai/vcm/sessions/<task>.json
493
+ <taskRepoRoot>/.ai/vcm/sessions/<task>.json
484
494
  ```
485
495
 
486
496
  The persisted record includes:
@@ -545,9 +555,9 @@ Files:
545
555
  State:
546
556
 
547
557
  ```text
548
- .ai/vcm/messages/<task>.jsonl
549
- .ai/vcm/orchestration/<task>.json
550
- .ai/handoffs/<task>/messages/<message-id>.md
558
+ <taskRepoRoot>/.ai/vcm/messages/<task>.jsonl
559
+ <taskRepoRoot>/.ai/vcm/orchestration/<task>.json
560
+ <taskRepoRoot>/.ai/handoffs/<task>/messages/<message-id>.md
551
561
  ```
552
562
 
553
563
  Policy:
@@ -576,11 +586,12 @@ Auto mode:
576
586
  send -> delivered
577
587
  ```
578
588
 
579
- The backend writes a `[VCM MESSAGE]` envelope to the target terminal and appends Enter.
589
+ The backend pastes a `[VCM MESSAGE]` envelope into the target terminal, then sends Enter as a separate terminal input event.
580
590
 
581
591
  The backend still exposes pause/resume orchestration API routes and stores `paused` for compatibility. The current GUI only toggles `mode` between `manual` and `auto`.
582
592
 
583
- Messages and orchestration snapshots are central project state under `baseRepoRoot/.ai/vcm`. Message body markdown lives in the task worktree handoff directory.
593
+ Messages and orchestration snapshots are task runtime state under `taskRepoRoot/.ai/vcm`. Message body markdown also lives in the task worktree handoff directory.
594
+ Messages and orchestration snapshots are task runtime state under `taskRepoRoot/.ai/vcm`. Message body markdown also lives in the task worktree handoff directory.
584
595
 
585
596
  ## 12. Role Command Compatibility
586
597
 
@@ -608,7 +619,7 @@ The dispatcher:
608
619
  2. Reads the role command artifact.
609
620
  3. Rejects missing, empty, or placeholder role commands.
610
621
  4. Resolves primary command path `role-commands/<role>.md`, with legacy fallback `<role>-command.md`.
611
- 5. Writes `Please read and execute the role command at: <path>` to the target terminal and submits Enter.
622
+ 5. Pastes `Please read and execute the role command at: <path>` to the target terminal, then sends Enter as a separate terminal input event.
612
623
 
613
624
  This is a compatibility path. The preferred V1 coordination path is `vcmctl` message bus.
614
625
 
@@ -664,7 +675,6 @@ Files:
664
675
  - `src/backend/services/translation-prompts.ts`
665
676
  - `src/backend/services/claude-transcript-service.ts`
666
677
  - `src/backend/adapters/translation-provider.ts`
667
- - `src/backend/ws/translation-ws.ts`
668
678
  - `src/backend/api/translation-routes.ts`
669
679
  - `src/frontend/components/translation-panel.tsx`
670
680
  - `src/frontend/components/translation-settings-modal.tsx`
@@ -683,6 +693,7 @@ Storage:
683
693
 
684
694
  Stored data:
685
695
 
696
+ - UI theme preference: `system`, `light`, or `dark`
686
697
  - translation settings
687
698
  - translation secrets
688
699
  - recent repository paths, max 5
@@ -718,8 +729,11 @@ Tailer:
718
729
  - validates file exists
719
730
  - can replay history since session start minus a grace window
720
731
  - uses `fs.watch`
721
- - also polls every 500ms
732
+ - also polls every 200ms
722
733
  - parses only complete newline-delimited JSON records
734
+ - is owned by the backend translation service, not the frontend panel
735
+ - stays running after the panel closes
736
+ - stops only when the role session is stopped/restarted or the task is closed
723
737
 
724
738
  Parsed transcript events:
725
739
 
@@ -736,9 +750,21 @@ Translation service behavior:
736
750
  - ignores thinking
737
751
  - translates text/question/todo/agent as prose
738
752
  - preserves tool_use/tool_result as tool-output
739
- - queues translation per runtime session id
740
- - emits WebSocket `translation-entry`
741
- - emits WebSocket `translation-status`
753
+ - queues provider translation per runtime session id
754
+ - pushes prose entries before provider translation starts
755
+ - pushes tool_use/tool_result immediately without entering the translation queue
756
+ - writes translation events to `<taskRepoRoot>/.ai/vcm/translation/<task>/<role>/<session-id>.jsonl`
757
+ - exposes HTTP polling for frontend rendering
758
+
759
+ Polling protocol:
760
+
761
+ - `seq` starts at 1 for each translation session cache.
762
+ - the frontend calls `GET /api/translation/sessions/:sessionId/events?after=<cursor>`.
763
+ - `after` is the next expected seq, not the last displayed seq.
764
+ - `after=18` lets the backend delete cached events with `seq < 18` and return events with `seq >= 18`.
765
+ - if `after` is older than the retained cache, the backend returns whatever newer events still exist.
766
+ - no snapshot mismatch error is used.
767
+ - translated prose replacement is a later `entry` event with the same translation entry id and a newer `seq`.
742
768
 
743
769
  ### User Input Path
744
770
 
@@ -749,10 +775,10 @@ textarea -> POST translation/input -> provider -> English draft in the same text
749
775
  Send path:
750
776
 
751
777
  ```text
752
- POST translation/send -> runtime.write(session.id, englishText + "\r")
778
+ POST translation/send -> bracketed paste English text -> short delay -> runtime.write(session.id, "\r")
753
779
  ```
754
780
 
755
- The backend strips trailing newlines before appending `\r`.
781
+ The backend strips trailing newlines before pasting and sends Enter separately. This avoids Claude Code TUI cases where a single large PTY write containing both text and `\r` fills the input line but does not submit it.
756
782
 
757
783
  ## 15. API Surface
758
784
 
@@ -819,6 +845,13 @@ POST /api/tasks/:taskSlug/orchestration/pause
819
845
  POST /api/tasks/:taskSlug/orchestration/resume
820
846
  ```
821
847
 
848
+ App settings:
849
+
850
+ ```text
851
+ GET /api/settings/preferences
852
+ PUT /api/settings/preferences
853
+ ```
854
+
822
855
  Translation:
823
856
 
824
857
  ```text
@@ -826,6 +859,8 @@ GET /api/translation/settings
826
859
  PUT /api/translation/settings
827
860
  GET /api/translation/prompts
828
861
  POST /api/translation/test
862
+ POST /api/tasks/:taskSlug/sessions/:role/translation/start
863
+ GET /api/translation/sessions/:sessionId/events?after=<cursor>&limit=<n>
829
864
  POST /api/tasks/:taskSlug/sessions/:role/translation/input
830
865
  POST /api/tasks/:taskSlug/sessions/:role/translation/send
831
866
  POST /api/translation/sessions/:sessionId/clear
@@ -836,7 +871,6 @@ WebSockets:
836
871
 
837
872
  ```text
838
873
  /ws/terminal/:sessionId
839
- /ws/translation/:sessionId
840
874
  ```
841
875
 
842
876
  ## 16. Error Handling