@wendongfly/myhi 1.3.197 → 1.3.198

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.min.js CHANGED
@@ -388,7 +388,7 @@ Content-Length: `+C+`\r
388
388
  `)}),this._checkDeathLoop({type:"stderr",_raw:n.join(`
389
389
  `)}))})),this._proc.on("close",(s=>{if(f()){console.log(`[agent] \u65E7\u8FDB\u7A0B\u9000\u51FA (code ${s})\uFF0C\u5DF2\u88AB\u65B0\u8FDB\u7A0B\u66FF\u6362\uFF0C\u5FFD\u7565`);return}if(!this._interrupted&&this._buffer.trim())try{const o=JSON.parse(this._buffer.trim());this._handleMessage(o)}catch{}if(this._keepAliveTimer&&(clearInterval(this._keepAliveTimer),this._keepAliveTimer=null),this._stopStallWatchdog(),this._proc=null,this._buffer="",this._dropInteractions(),this._dropInjected("Claude \u8FDB\u7A0B\u5DF2\u9000\u51FA\uFF0C\u8FD9\u6761\u63D2\u8BDD\u6CA1\u6709\u9001\u8FBE"),console.log(`[agent] \u8FDB\u7A0B\u9000\u51FA (code ${s}), \u4F1A\u8BDD: ${this.claudeSessionId||"?"}`),this._busy&&(this._busy=!1,this._interrupted=!1,this.emit("agent:busy",!1),this._pendingReject&&(this._pendingReject(new Error(`Claude \u8FDB\u7A0B\u9000\u51FA (code ${s})`)),this._pendingResolve=null,this._pendingReject=null)),this._flushPendingSteer(),this._spawnFailed){this._spawnFailed=!1;return}if(this._expectExit){this._expectExit=!1;return}this.alive&&s!==0&&s!==null&&this.emit("agent:error",{message:`Claude \u8FDB\u7A0B\u5F02\u5E38\u9000\u51FA (code ${s})\uFF0C\u4E0B\u6B21\u67E5\u8BE2\u5C06\u81EA\u52A8\u91CD\u542F`})})),this._proc.on("error",(s=>{f()||(this._keepAliveTimer&&(clearInterval(this._keepAliveTimer),this._keepAliveTimer=null),this._stopStallWatchdog(),this._proc=null,this._busy=!1,this.emit("agent:busy",!1),this._spawnFailed=!0,this.emit("agent:error",{message:s.code==="ENOENT"?CLAUDE_MISSING_MSG:`\u542F\u52A8 Claude \u5931\u8D25: ${s.message}`}),s.reported=!0,this._pendingReject&&(this._pendingReject(s),this._pendingResolve=null,this._pendingReject=null))})),this._keepAliveTimer=setInterval((()=>{this._writeStdin({type:"keep_alive"})}),3e4)}async query(c,{internal:i=!1,from:r=null,display:e=null,actor:a=null}={}){if(this._busy){this.emit("agent:error",{message:"\u6B63\u5728\u5904\u7406\u4E2D\uFF0C\u8BF7\u7B49\u5F85\u5B8C\u6210"});return}if(i||(this._followCount=0,this._followStopSignal=!1,this._cancelFollowUp()),c==="/clear"){this.reset();const s=[CLEAR_WHERE[a?.where],a?.device].filter(Boolean).join(" \xB7 "),o=a?.via==="button"?"\u70B9\u4E86\u300C\u6E05\u9664\u300D":"\u53D1\u9001\u4E86 /clear",t=a?`${a.name||"\u7528\u6237"}${s?`\uFF08${s}\uFF09`:""}${o}\uFF0C`:"";console.log(`[clear] \u4F1A\u8BDD ${this.id}\u300C${this.title||""}\u300D\u88AB\u6E05\u9664\uFF1A${a?`${a.name||"?"} / ${CLEAR_WHERE[a.where]||"\u672A\u77E5\u9875\u9762"} / ${a.device||"?"} / ${a.via}`:"\u5185\u90E8\u8C03\u7528"}`),this.emit("agent:message",{type:"system",subtype:"info",cleared:!0,message:`${t}\u5DF2\u5F00\u59CB\u65B0\u5BF9\u8BDD\uFF1AAI \u4E0D\u518D\u8BB0\u5F97\u4E4B\u524D\u804A\u8FC7\u7684\u5185\u5BB9\uFF08\u9879\u76EE\u6587\u4EF6\u4E0D\u53D7\u5F71\u54CD\uFF09`});return}const p=c.match(/^\/resume\s+(\S+)/);if(p){if(this._proc){this._expectExit=!0;try{this._proc.kill("SIGTERM")}catch{}this._proc=null}this.claudeSessionId=p[1],this._history=[],this._buffer="",this._loadResumedHistory(),this.emit("agent:message",{type:"system",subtype:"info",message:`\u5DF2\u5207\u6362\u5230\u4F1A\u8BDD ${p[1].slice(0,8)}...\uFF0C\u4E0B\u6B21\u63D0\u95EE\u5C06\u6062\u590D\u8BE5\u5BF9\u8BDD`});return}const f=c.match(/^\/model\s+(\S+)/);if(f){if(this.modelId=f[1],this._proc){this._expectExit=!0;try{this._proc.kill("SIGTERM")}catch{}this._proc=null}this.emit("agent:message",{type:"system",subtype:"info",message:`\u6A21\u578B\u5DF2\u5207\u6362\u4E3A ${f[1]}`});return}if(c==="/plan"||c.startsWith("/plan ")){if(this.permissionMode==="plan"){if(this.permissionMode=normalizePermissionMode(this._prePlanMode),this._prePlanMode=null,this._proc){this._expectExit=!0;try{this._proc.kill("SIGTERM")}catch{}this._proc=null}this.emit("agent:message",{type:"system",subtype:"info",message:"\u5DF2\u9000\u51FA\u8BA1\u5212\u6A21\u5F0F"})}else{if(this._prePlanMode=this.permissionMode,this.permissionMode="plan",this._proc){this._expectExit=!0;try{this._proc.kill("SIGTERM")}catch{}this._proc=null}this.emit("agent:message",{type:"system",subtype:"info",message:"\u5DF2\u8FDB\u5165\u8BA1\u5212\u6A21\u5F0F\uFF08\u53EA\u89C4\u5212\u4E0D\u6267\u884C\uFF09"});const o=c.slice(5).trim();if(o){setTimeout((()=>this.query(o)),500);return}}return}if(c.startsWith("/rename")){this.emit("agent:message",{type:"system",subtype:"info",message:"\u4F1A\u8BDD\u5DF2\u547D\u540D"});return}this._busy=!0,this._interrupted=!1,this.emit("agent:busy",!0),this._loopSigCounts.clear(),this._loopPoisonHits=0,this._loopTurnToolCalls=0,this._loopTripped=!1,i||(this._loopAutoRecover=0),this._redactor=buildRedactor(),this._pseudoMap||(this._pseudoMap=loadMap(this.claudeSessionId||this.id)),this._pseudo=buildPseudonymizer(this.cwd,this._pseudoMap),this._lastActivityAt=Date.now(),this._awaitingTool=!1,this._startStallWatchdog();const l=redactDeep(typeof e=="string"&&e.trim()?e.trim().slice(0,500):c,this._redactor);return this._history.push({type:"user",content:l,timestamp:Date.now()}),r&&this.emit("agent:message",{type:"user",content:l,timestamp:Date.now(),from:r}),!this.firstUserText&&typeof l=="string"&&!l.startsWith("/")&&(this.firstUserText=l.trim().slice(0,160)),this._proc||(_interactiveCap===null&&await probeInteractive(),this._spawnProcess()),new Promise(((s,o)=>{this._pendingResolve=s,this._pendingReject=o,c.startsWith("/")&&(this._slashTimeout=setTimeout((()=>{this._busy&&(this._busy=!1,this._interrupted=!1,this.emit("agent:busy",!1),this.emit("agent:message",{type:"system",subtype:"info",message:`\u547D\u4EE4 ${c} \u5DF2\u53D1\u9001`}),this._pendingResolve&&(this._pendingResolve(0),this._pendingResolve=null,this._pendingReject=null))}),3e4));let t=c;if(this._pseudo?.enabled){const d=this._pseudo.pseudonymize(c);t=d.text;const h=this.claudeSessionId||this.id;saveMap(h,this._pseudoMap),d.count>0&&(appendAudit(h,{ts:Date.now(),level:this._pseudo.level,maskedCount:d.count,byType:d.byType,sentToModel:d.text}),this.emit("agent:message",{type:"system",subtype:"info",message:`\u{1F6E1} \u9690\u79C1\u62A4\u680F\uFF1A\u672C\u8F6E\u5DF2\u8131\u654F ${d.count} \u5904\u654F\u611F\u4FE1\u606F\uFF0C\u6A21\u578B\u53EA\u770B\u5230\u5360\u4F4D\u7B26\uFF08\u6620\u5C04\u8868\u7559\u672C\u673A\u3001\u53EF\u9006\u8FD8\u539F\uFF09\u3002`}))}this._writeStdin({type:"user",uuid:(0,external_crypto_.randomUUID)(),message:{role:"user",content:t}})||(this._busy=!1,this.emit("agent:busy",!1),this._pendingResolve=null,this._pendingReject=null,o(new Error("Claude \u8FDB\u7A0B\u4E0D\u53EF\u5199")))}))}_handleMessage(c){const i=!!this.claudeSessionId;if(this._lastActivityAt=Date.now(),c.type==="assistant"&&Array.isArray(c.message?.content)?c.message.content.some((l=>l.type==="tool_use"))&&(this._awaitingTool=!0):c.type==="user"&&(this._awaitingTool=!1),c.type==="control_request"){this._onControlRequest(c);return}if(c.type==="control_response")return;if(c.type==="user"&&c.isReplay){this._onReplay(c);return}if(c.type==="system"&&c.subtype==="status"&&c.permissionMode){const l=normalizePermissionMode(c.permissionMode);VALID_PERMISSION_MODES.has(c.permissionMode)&&l!==this.permissionMode&&(this.permissionMode=l,l!=="plan"&&(this._prePlanMode=null),this.emit("mode-changed",l));return}if(c.session_id&&!this.claudeSessionId&&(this.claudeSessionId=c.session_id),c.type==="system"&&c.subtype==="init"&&c.session_id&&(this.claudeSessionId=c.session_id),!i&&this.claudeSessionId&&this.emit("session-id",this.claudeSessionId),c.type==="system"&&c.subtype==="init"&&this.permissionMode==="bypassPermissions"&&c.permissionMode&&c.permissionMode!=="bypassPermissions"){const l=c.permissionMode;this.reset(),this.emit("agent:message",{type:"system",subtype:"warning",message:`\u26A0\uFE0F \u8FD9\u4E2A\u4F1A\u8BDD\u88AB --resume \u5E26\u56DE\u4E86\u300C${l}\u300D\u6A21\u5F0F\uFF08\u975E bypass\uFF0C\u4F1A\u62E6\u5199/\u5220\u4E14\u65E0\u6CD5\u8FD0\u884C\u65F6\u63D0\u6743\uFF0C\u70B9\u300C\u9000\u51FA\u8BA1\u5212\u300D\u4E5F\u9003\u4E0D\u6389\uFF09\u3002\u5DF2\u81EA\u52A8\u65AD\u5F00\u65E7\u4F1A\u8BDD\u94FE\u3001\u91CD\u5F00\u4E3A\u5E72\u51C0\u7684 bypass \u4F1A\u8BDD\u2014\u2014\u8BF7\u91CD\u53D1\u4F60\u521A\u624D\u7684\u6307\u4EE4\uFF0C\u8FD9\u6B21\u4F1A\u76F4\u63A5\u6267\u884C\u3002`});return}const r=this._pseudo?.enabled?redactDeep(c,this._pseudo.restore):c,e=redactDeep(r,this._redactor),a=stripHeavyPayload({...e,timestamp:Date.now()}),p=JSON.stringify(a);this._followEnabled&&p.includes("[\u8DDF\u8FDB\u5B8C\u6210]")&&(this._followStopSignal=!0),p.length>10240&&(a._truncated=!0),this._history.push(a);const f=500;if(this._history.length>f&&(this._history=this._history.slice(-f)),this._trackImagePressure(p),this._checkDeathLoop(c,p),c.type==="rate_limit_event"&&c.rate_limit_info&&(this._usage.rateLimitInfo=c.rate_limit_info),c.type==="result"){const l=this._usageBase;if(this._procQueryCount=(this._procQueryCount||0)+1,this._usage.queryCount=l.queryCount+this._procQueryCount,c.total_cost_usd&&(this._usage.totalCostUSD=l.totalCostUSD+c.total_cost_usd),c.usage&&(this._usage.totalInputTokens=l.totalInputTokens+(c.usage.input_tokens||0),this._usage.totalOutputTokens=l.totalOutputTokens+(c.usage.output_tokens||0),this._usage.totalCacheReadTokens=l.totalCacheReadTokens+(c.usage.cache_read_input_tokens||0),this._usage.totalCacheCreationTokens=l.totalCacheCreationTokens+(c.usage.cache_creation_input_tokens||0)),c.modelUsage)for(const[s,o]of Object.entries(c.modelUsage)){const t=l.modelUsage[s]||{inputTokens:0,outputTokens:0,costUSD:0};this._usage.modelUsage[s]={inputTokens:t.inputTokens+(o.inputTokens||0),outputTokens:t.outputTokens+(o.outputTokens||0),costUSD:t.costUSD+(o.costUSD||0)}}}{let l=c.type==="assistant"?c.message?.usage:null;if(c.type==="result"&&(l=this._readTranscriptCtx()||l),l){const s=(l.input_tokens||0)+(l.cache_read_input_tokens||0)+(l.cache_creation_input_tokens||0);(s>this._contextTokens||this._contextTokens>0&&s<this._contextTokens*.5)&&(this._contextTokens=s)}}if(c.type==="result"&&(e.ctxTokens=this._contextTokens),c.type==="result"&&this._injected?.size&&(e.injectPending=!0),this.emit("agent:message",e),c.type==="result"){this._slashTimeout&&(clearTimeout(this._slashTimeout),this._slashTimeout=null),this._stopStallWatchdog();const l=!this._interrupted&&!c.is_error;if(this._pendingResolve&&(this._pendingResolve(0),this._pendingResolve=null,this._pendingReject=null),this._lastResultAt=Date.now(),this._injected?.size){this._interrupted=!1,this._lastActivityAt=Date.now(),this._startStallWatchdog(),clearTimeout(this._injectWaitTimer),this._injectWaitTimer=setTimeout((()=>{!this._injected?.size||!this._busy||(this._dropInjected("AI \u6CA1\u6709\u63A5\u6536\u8FD9\u6761\u63D2\u8BDD\uFF0C\u8BF7\u91CD\u65B0\u53D1\u9001"),this._busy=!1,this.emit("agent:busy",!1))}),INJECT_FOLLOW_WAIT_MS);return}this._busy=!1,this._interrupted=!1,this.emit("agent:busy",!1),this._skillsDirty&&setTimeout((()=>{this._busy||this.refreshSkills()}),0),this._flushPendingSteer(),l&&this._maybeRelayDraft(),this._maybeScheduleFollowUp()}}_trackImagePressure(c){const i=(c.match(/"type":"image"/g)||[]).length;i&&(this._imageBlockCount+=i,this._imageBlockCount>=this._imageNudgeAt&&(this._imageNudgeAt+=IMAGE_NUDGE_STEP,this.emit("agent:message",{type:"system",subtype:"warning",message:`\u2139\uFE0F \u672C\u4F1A\u8BDD\u5DF2\u7D2F\u79EF\u7EA6 ${this._imageBlockCount} \u5F20\u56FE\u7247\u3002\u56FE\u7247\u8D8A\u591A\u8D8A\u5BB9\u6613\u89E6\u53D1 API \u56FE\u7247\u5904\u7406\u9519\u8BEF\u5E76\u62D6\u6162/\u6D88\u8017\u989D\u5EA6\uFF0C\u5EFA\u8BAE\u7528 /clear \u91CD\u5F00\u4E00\u4E2A\u5E72\u51C0\u4F1A\u8BDD\uFF0C\u6216\u51CF\u5C11\u540E\u7EED\u622A\u56FE\u3002`})))}_checkDeathLoop(c,i){if(this._loopTripped)return;let r=!1;try{const e=i||JSON.stringify(c);if(LOOP_POISON_PHRASES.some((a=>e.includes(a)))){const a=c.type==="assistant",p=e.includes('"type":"image"'),f=e.length<=POISON_MAX_NOTICE_LEN;r=!a&&(p||f)}}catch{}if(r&&(this._loopPoisonHits++,this._loopPoisonHits>=LOOP_MAX_POISON_HITS)){this._tripLoopBreaker("\u8BE5\u56FE\u7247/\u5185\u5BB9 API \u53CD\u590D\u65E0\u6CD5\u5904\u7406\u5E76\u5DF2\u88AB\u79FB\u9664\uFF0C\u8BF7\u4E0D\u8981\u518D\u7528 Read \u91CD\u65B0\u8BFB\u53D6\u5B83\u2014\u2014\u5B83\u5DF2\u4E0D\u53EF\u7528\u3002\u8BF7\u57FA\u4E8E\u73B0\u6709\u6587\u5B57\u4FE1\u606F\u7EE7\u7EED\uFF1B\u82E5\u786E\u5B9E\u9700\u8981\u8BE5\u56FE\uFF0C\u8BF7\u63D0\u793A\u7528\u6237\u91CD\u65B0\u4E0A\u4F20\u4E00\u5F20\u66F4\u5C0F\u7684\u622A\u56FE\u3002");return}if(c.type==="assistant"&&Array.isArray(c.message?.content)){const e=!!c.parent_tool_use_id,a=c.parent_tool_use_id||"main";for(const p of c.message.content){if(p.type!=="tool_use")continue;if(!e&&(this._loopTurnToolCalls++,this._loopTurnToolCalls>LOOP_MAX_TURN_TOOLCALLS)){this._tripLoopBreaker(`\u672C\u8F6E\u5DE5\u5177\u8C03\u7528\u5DF2\u8FBE ${this._loopTurnToolCalls} \u6B21\u5E76\u63D2\u5165\u68C0\u67E5\u70B9\u3002\u82E5\u4ECD\u5728\u6B63\u5E38\u63A8\u8FDB\uFF0C\u8BF7\u6982\u8FF0\u5F53\u524D\u8FDB\u5C55\u540E\u7EE7\u7EED\uFF1B\u82E5\u5728\u91CD\u590D\u540C\u7C7B\u64CD\u4F5C\u800C\u6CA1\u6709\u8FDB\u5C55\uFF0C\u8BF7\u6362\u4E00\u79CD\u601D\u8DEF\uFF0C\u6216\u5148\u5411\u7528\u6237\u6C47\u62A5\u518D\u7B49\u5F85\u6307\u793A\u3002`);return}const f=`${a}:${p.name}:${this._hashInput(p.input)}`,l=(this._loopSigCounts.get(f)||0)+1;if(this._loopSigCounts.set(f,l),l>=LOOP_MAX_IDENTICAL_CALLS){this._tripLoopBreaker(`\u5DE5\u5177\u300C${p.name}\u300D\u5DF2\u7528\u5B8C\u5168\u76F8\u540C\u7684\u53C2\u6570\u8C03\u7528 ${l} \u6B21\uFF0C\u7591\u4F3C\u9677\u5165\u6B7B\u5FAA\u73AF\u3002\u8BF7\u505C\u6B62\u91CD\u590D\u8BE5\u8C03\u7528\uFF0C\u6539\u7528\u4E0D\u540C\u53C2\u6570/\u4E0D\u540C\u5DE5\u5177\uFF0C\u6216\u8DF3\u8FC7\u8FD9\u4E00\u6B65\u7EE7\u7EED\u3002`);return}}}}_hashInput(c){let i;try{i=JSON.stringify(stripHeavyPayload(c))}catch{i=String(c)}i.length>4096&&(i=i.slice(0,4096));let r=5381;for(let e=0;e<i.length;e++)r=(r<<5)+r+i.charCodeAt(e)|0;return r.toString(36)}_tripLoopBreaker(c){if(this._loopTripped=!0,console.warn("[agent] \u{1F50C} \u6B7B\u5FAA\u73AF\u7194\u65AD:",c),this._loopAutoRecover>=LOOP_MAX_AUTO_RECOVER){this._pendingSteer=null,this.emit("agent:message",{type:"system",subtype:"warning",message:"\u26A0\uFE0F \u591A\u6B21\u81EA\u52A8\u7EA0\u504F\u4ECD\u672A\u8DF3\u51FA\u5FAA\u73AF\uFF0C\u5DF2\u505C\u6B62\u4EE5\u4FDD\u62A4 session \u989D\u5EA6\u3002\u8BF7 /clear \u91CD\u5F00\u6216\u6362\u4E2A\u95EE\u6CD5\u3002"}),this.interrupt();return}this._loopAutoRecover++,this._pendingSteer=c,this.emit("agent:message",{type:"system",subtype:"warning",message:`\u26A0\uFE0F \u7194\u65AD\u4FDD\u62A4\uFF08\u7B2C ${this._loopAutoRecover} \u6B21\u81EA\u52A8\u7EA0\u504F\uFF09\uFF1A${c}`}),this.interrupt()}_flushPendingSteer(){if(!this._pendingSteer)return;const c=this._pendingSteer;this._pendingSteer=null,setTimeout((()=>{!this._busy&&this.alive&&this.query(c,{internal:!0}).catch((()=>{}))}),600)}setFollowUp({enabled:c,intervalMinutes:i}={}){if(typeof c=="boolean"&&(this._followEnabled=c),i!=null){const r=Math.max(1,Math.min(180,Number(i)||15));this._followIntervalMs=Math.round(r*60*1e3)}return this._followEnabled?this._busy||this._maybeScheduleFollowUp():(this._cancelFollowUp(),this._followCount=0),this.emit("agent:message",{type:"system",subtype:"info",message:this._followEnabled?`\u{1F504} \u81EA\u52A8\u8DDF\u8FDB\u5DF2\u5F00\u542F\uFF1A\u6BCF ${Math.round(this._followIntervalMs/6e4)} \u5206\u949F\u81EA\u52A8\u67E5\u4E00\u6B21\u8FDB\u5EA6\u5E76\u6C47\u62A5\uFF08\u6700\u591A ${this._followMax} \u6B21\uFF1BAI \u5224\u65AD\u5168\u90E8\u5B8C\u6210\u4F1A\u81EA\u52A8\u505C\uFF09\u3002`:"\u{1F504} \u81EA\u52A8\u8DDF\u8FDB\u5DF2\u5173\u95ED\u3002"}),this.followUpState()}followUpState(){return{enabled:this._followEnabled,intervalMinutes:Math.round(this._followIntervalMs/6e4),max:this._followMax,count:this._followCount}}_cancelFollowUp(){this._followTimer&&(clearTimeout(this._followTimer),this._followTimer=null)}_cancelRelay(){this._relayTimer&&(clearTimeout(this._relayTimer),this._relayTimer=null)}_maybeRelayDraft(){!this.alive||this._relayTimer||(this._relayTimer=setTimeout((()=>{if(this._relayTimer=null,this._busy||!this.alive)return;let c=null;try{c=nextAutoSendDraft(this.id)}catch{return}if(!c)return;try{removeDraft(c.id)}catch{}const i=buildDraftPrompt(c);i.trim()&&(this.emit("agent:message",{type:"system",subtype:"info",message:"\u{1F4E5} \u81EA\u52A8\u63A5\u529B\uFF1A\u4E0A\u4E00\u8F6E\u5DF2\u5B8C\u6210\uFF0C\u53D1\u51FA\u4E0B\u9762\u8FD9\u6761\u8349\u7A3F"}),this.emit("agent:message",{type:"user",content:draftDisplayText(c)||i,timestamp:Date.now()}),this.emit("draft-relayed",{id:c.id,sessionId:this.id}),this.lastInputTime=Date.now(),this.query(i).catch((()=>{})))}),RELAY_DELAY_MS),this._relayTimer.unref&&this._relayTimer.unref())}_maybeScheduleFollowUp(){if(this._cancelFollowUp(),!(!this._followEnabled||!this.alive)){if(this._followStopSignal){this._followStopSignal=!1,this._followCount=0,this.emit("agent:message",{type:"system",subtype:"info",message:"\u{1F504} AI \u5DF2\u786E\u8BA4\u4EFB\u52A1\u5168\u90E8\u5B8C\u6210\uFF0C\u81EA\u52A8\u8DDF\u8FDB\u505C\u6B62\u3002"});return}if(this._followCount>=this._followMax){this.emit("agent:message",{type:"system",subtype:"info",message:`\u{1F504} \u81EA\u52A8\u8DDF\u8FDB\u5DF2\u8FDE\u7EED ${this._followMax} \u6B21\uFF0C\u6682\u505C\uFF08\u9632\u7A7A\u8F6C\u70E7\u989D\u5EA6\uFF09\u3002\u9700\u8981\u7EE7\u7EED\u53EF\u624B\u52A8\u95EE\u4E00\u53E5\u6216\u91CD\u5F00\u3002`});return}this._followTimer=setTimeout((()=>{this._followTimer=null,!(this._busy||!this.alive||!this._followEnabled)&&(this._followCount++,this.emit("agent:message",{type:"system",subtype:"info",message:`\u{1F504} \u81EA\u52A8\u8DDF\u8FDB\uFF08\u7B2C ${this._followCount}/${this._followMax} \u6B21\uFF09\uFF1A\u8BA9 AI \u67E5\u770B\u8FDB\u5EA6\u2026`}),this.query(FOLLOW_UP_PROMPT,{internal:!0}).catch((()=>{})))}),this._followIntervalMs)}}_startStallWatchdog(){this._stopStallWatchdog(),this._watchdogTimer=setInterval((()=>{if(!this._busy){this._stopStallWatchdog();return}if(this._awaitingTool)return;const c=Date.now()-this._lastActivityAt;if(c>=STALL_WATCHDOG_MS){const i=Math.round(c/1e3);console.warn(`[agent] \u23F1 \u505C\u6446\u770B\u95E8\u72D7\u89E6\u53D1\uFF1A\u7B49\u5F85\u6A21\u578B\u54CD\u5E94\u5DF2 ${i}s \u65E0\u4EFB\u4F55\u6D88\u606F\uFF0C\u5F3A\u5236\u4E2D\u65AD`),this.emit("agent:message",{type:"system",subtype:"warning",message:`\u23F1 \u68C0\u6D4B\u5230\u4F1A\u8BDD\u505C\u6446\uFF08\u7B49\u5F85\u6A21\u578B\u54CD\u5E94 ${i}s \u65E0\u54CD\u5E94\uFF0C\u7591\u4F3C API \u4F20\u8F93\u5C42\u91CD\u8BD5\u5361\u4F4F\uFF09\uFF0C\u5DF2\u5F3A\u5236\u4E2D\u65AD\u672C\u56DE\u5408\u3002\u8BF7\u91CD\u8BD5\u6216\u7A0D\u540E\u518D\u8BD5\u3002`}),this._stopStallWatchdog(),this.interrupt()}}),STALL_CHECK_INTERVAL_MS),this._watchdogTimer.unref&&this._watchdogTimer.unref()}_stopStallWatchdog(){this._watchdogTimer&&(clearInterval(this._watchdogTimer),this._watchdogTimer=null)}_onControlRequest(c){const i=c.request||{},r=c.request_id;if(i.subtype!=="can_use_tool"){this._writeStdin({type:"control_response",response:{subtype:"error",request_id:r,error:`myhi \u4E0D\u652F\u6301 ${i.subtype}`}});return}if(i.tool_name==="AskUserQuestion"||i.tool_name==="ExitPlanMode")return this._openInteraction({id:r,kind:i.tool_name==="AskUserQuestion"?"ask":"plan",input:i.input||{},toolUseId:i.tool_use_id});this._ctlReply(r,{behavior:"deny",message:"\u5F53\u524D\u6743\u9650\u6A21\u5F0F\u4E0D\u5141\u8BB8\u6B64\u64CD\u4F5C\uFF08myhi \u65E0\u4EBA\u503C\u5B88\uFF0C\u65E0\u6CD5\u9010\u9879\u6388\u6743\uFF09\u3002\u8BF7\u57FA\u4E8E\u73B0\u72B6\u7EE7\u7EED\uFF0C\u6216\u5728\u56DE\u590D\u91CC\u8BF4\u660E\u9700\u8981\u7528\u6237\u5207\u6362\u5230\u81EA\u52A8\u6267\u884C\u3002"})}_ctlReply(c,i){return this._writeStdin({type:"control_response",response:{subtype:"success",request_id:c,response:i}})}get pendingInteractions(){return[...this._interactions?.values()||[]].map((c=>c.view))}_openInteraction(c){this._interactions||(this._interactions=new Map);const i=redactDeep(this._pseudo?.enabled?redactDeep(c.input,this._pseudo.restore):c.input,this._redactor);c.view={id:c.id,kind:c.kind,toolUseId:c.toolUseId,at:Date.now(),questions:c.kind==="ask"?i.questions||[]:void 0,plan:c.kind==="plan"?String(i.plan||""):void 0};const r=this._followEnabled?INTERACTION_WAIT_FOLLOW_MS:INTERACTION_WAIT_MS;c.view.deadline=Date.now()+r,c.timer=setTimeout((()=>this.respondInteraction(c.id,{skip:!0,timeout:!0},"\u7CFB\u7EDF")),r),c.timer.unref&&c.timer.unref(),this._interactions.set(c.id,c),this.emit("agent:interaction",c.view)}respondInteraction(c,i={},r=""){const e=this._interactions?.get(c);if(!e)return{ok:!1,error:"\u8FD9\u4E2A\u63D0\u95EE\u5DF2\u7ECF\u5904\u7406\u8FC7\u4E86"};clearTimeout(e.timer),this._interactions.delete(c);const a=f=>this._pseudo?.enabled?this._pseudo.pseudonymize(String(f)).text:String(f);let p;if(e.kind==="ask")if(i.skip||!i.answers||!Object.keys(i.answers).length)this._ctlReply(c,{behavior:"deny",message:i.timeout?"\u7528\u6237\u8F83\u957F\u65F6\u95F4\u6CA1\u6709\u4F5C\u7B54\u3002\u8BF7\u6309\u4F60\u7684\u6700\u4F73\u5224\u65AD\u7EE7\u7EED\uFF0C\u5E76\u5728\u56DE\u590D\u91CC\u8BF4\u660E\u4F60\u505A\u4E86\u54EA\u4E9B\u5047\u8BBE\u3002":"\u7528\u6237\u9009\u62E9\u4E0D\u56DE\u7B54\u8FD9\u4E2A\u95EE\u9898\u3002\u8BF7\u6309\u4F60\u7684\u6700\u4F73\u5224\u65AD\u7EE7\u7EED\uFF0C\u5E76\u5728\u56DE\u590D\u91CC\u8BF4\u660E\u4F60\u505A\u4E86\u54EA\u4E9B\u5047\u8BBE\u3002"}),p=i.timeout?"\u23ED \u63D0\u95EE\u7B49\u5F85\u8D85\u65F6\uFF0CAI \u5C06\u6309\u6700\u4F73\u5224\u65AD\u7EE7\u7EED":`\u23ED ${r} \u8DF3\u8FC7\u4E86\u63D0\u95EE\uFF0CAI \u5C06\u6309\u6700\u4F73\u5224\u65AD\u7EE7\u7EED`;else{const f={},l=e.input.questions||[],s=e.view.questions||[];s.forEach(((o,t)=>{const n=i.answers[o.question];n!==void 0&&l[t]&&(f[l[t].question]=a(n))})),this._ctlReply(c,{behavior:"allow",updatedInput:{...e.input,answers:f}}),p=`\u{1F4DD} ${r} \u5DF2\u56DE\u7B54\uFF1A`+s.map((o=>`${o.header||o.question}\uFF1D${i.answers[o.question]??"\uFF08\u672A\u7B54\uFF09"}`)).join("\uFF1B")}else if(i.approve)this._ctlReply(c,{behavior:"allow",updatedInput:e.input,updatedPermissions:[{type:"setMode",mode:"bypassPermissions",destination:"session"}]}),p=`\u2705 ${r} \u6279\u51C6\u4E86\u65B9\u6848\uFF0CAI \u5F00\u59CB\u6267\u884C`;else{const f=String(i.feedback||"").trim();this._ctlReply(c,{behavior:"deny",message:i.timeout?"\u7528\u6237\u8F83\u957F\u65F6\u95F4\u6CA1\u6709\u5BA1\u6279\u65B9\u6848\uFF0C\u6682\u4E0D\u6267\u884C\u3002\u4FDD\u6301\u8BA1\u5212\u6A21\u5F0F\uFF0C\u7B49\u5F85\u7528\u6237\u56DE\u590D\u3002":`\u7528\u6237\u5E0C\u671B\u4FEE\u6539\u65B9\u6848${f?"\uFF1A"+a(f):""}\u3002\u8BF7\u6309\u610F\u89C1\u4FEE\u6539\u540E\u91CD\u65B0\u7528 ExitPlanMode \u63D0\u4EA4\u3002`}),p=i.timeout?"\u23ED \u65B9\u6848\u5BA1\u6279\u7B49\u5F85\u8D85\u65F6\uFF0C\u6682\u4E0D\u6267\u884C":`\u270F\uFE0F ${r} \u8981\u6C42\u4FEE\u6539\u65B9\u6848${f?"\uFF1A"+f:""}`}return this.emit("agent:interaction-closed",{id:c,kind:e.kind}),this.emit("agent:message",{type:"system",subtype:"info",message:p}),{ok:!0}}_dropInteractions(){if(this._interactions?.size){for(const c of this._interactions.values())clearTimeout(c.timer),this.emit("agent:interaction-closed",{id:c.id,kind:c.kind});this._interactions.clear()}}_hardKillTree(c){if(c)try{if(process.platform==="win32")(0,external_child_process_namespaceObject.execSync)(`taskkill /PID ${c} /F /T`,{stdio:"pipe",timeout:5e3});else{try{process.kill(c,"SIGTERM")}catch{}setTimeout((()=>{try{process.kill(c,0)}catch{return}try{process.kill(c,"SIGKILL")}catch{}}),1e3)}}catch{}}get canInject(){return!!this._injectable&&!!this._proc&&this._busy}inject(c,{display:i}={}){if(!this._injectable)return{ok:!1,error:"\u5F53\u524D Claude \u7248\u672C\u4E0D\u652F\u6301\u63D2\u8BDD\uFF0C\u8BF7\u5347\u7EA7 Claude Code \u540E\u91CD\u8BD5"};if(!this._proc||!this._busy)return{ok:!1,error:"AI \u73B0\u5728\u6CA1\u5728\u5E72\u6D3B\uFF0C\u76F4\u63A5\u53D1\u9001\u5C31\u884C"};if(this._interactions?.size)return{ok:!1,error:"AI \u6B63\u5728\u7B49\u4F60\u56DE\u7B54\u63D0\u95EE / \u5BA1\u6279\u65B9\u6848\uFF0C\u8BF7\u5148\u5728\u5F39\u7A97\u91CC\u5904\u7406"};if(c=typeof c=="string"?c.trim():"",!c)return{ok:!1,error:"\u63D2\u8BDD\u5185\u5BB9\u662F\u7A7A\u7684"};if(c.startsWith("/"))return{ok:!1,error:"\u63D2\u8BDD\u4E0D\u652F\u6301 / \u547D\u4EE4\uFF0C\u8BF7\u7B49 AI \u5E72\u5B8C\u518D\u53D1"};let r=c;if(this._pseudo?.enabled){const l=this._pseudo.pseudonymize(c);r=l.text;const s=this.claudeSessionId||this.id;saveMap(s,this._pseudoMap),l.count>0&&appendAudit(s,{ts:Date.now(),level:this._pseudo.level,maskedCount:l.count,byType:l.byType,sentToModel:l.text,inject:!0})}const e=(0,external_crypto_.randomUUID)();if(!this._writeStdin({type:"user",uuid:e,message:{role:"user",content:r}}))return{ok:!1,error:"Claude \u8FDB\u7A0B\u4E0D\u53EF\u5199\uFF0C\u8BF7\u7A0D\u540E\u518D\u8BD5"};this._injected||(this._injected=new Map);const a=Date.now(),p=redactDeep(i||c,this._redactor),f={type:"user",content:p,timestamp:a,inject:{id:e,state:"pending"}};return this._injected.set(e,f),this._history.push(f),this.emit("agent:message",{type:"user",content:p,timestamp:a,inject:{id:e,state:"pending"}}),this.lastInputTime=a,{ok:!0,id:e}}_onReplay(c){const i=c.uuid&&this._injected?.get(c.uuid);i&&(this._injected.delete(c.uuid),i.inject.state="seen",this.emit("agent:message",{type:"system",subtype:"inject_state",id:c.uuid,state:"seen"}),this._injected.size||clearTimeout(this._injectWaitTimer)),this._busy||(this._busy=!0,this._interrupted=!1,this.emit("agent:busy",!0),this._lastActivityAt=Date.now(),this._awaitingTool=!1,this._startStallWatchdog())}refreshSkills(){if(!this._proc)return!1;if(this._busy)return this._skillsDirty=!0,!0;this._skillsDirty=!1,this._expectExit=!0;const c=this._proc.pid;return this._proc=null,this._keepAliveTimer&&(clearInterval(this._keepAliveTimer),this._keepAliveTimer=null),this._hardKillTree(c),this.emit("agent:message",{type:"system",subtype:"info",message:"\u{1F9E0} \u6280\u80FD\u6709\u53D8\u5316\uFF1A\u4E0B\u4E00\u8F6E AI \u4F1A\u91CD\u65B0\u52A0\u8F7D\u6280\u80FD\uFF08\u63A5\u7740\u539F\u6765\u7684\u5BF9\u8BDD\uFF09"}),!0}_dropInjected(c){if(clearTimeout(this._injectWaitTimer),!!this._injected?.size){for(const[i,r]of this._injected)r.inject.state="dropped",this.emit("agent:message",{type:"system",subtype:"inject_state",id:i,state:"dropped",reason:c});this._injected.clear()}}interrupt(){if(this._dropInteractions(),!this._proc||!this._busy)return;this._interrupted=!0;const c=this._proc.pid,i=this._proc,r=Date.now();this._injected?.size&&this.emit("agent:message",{type:"system",subtype:"info",message:"\u26A1 \u4F60\u521A\u63D2\u7684\u8BDD\u5DF2\u7ECF\u6392\u8FDB AI \u7684\u961F\u5217\uFF0C\u4E2D\u65AD\u540E\u5B83\u4F1A\u63A5\u7740\u5904\u7406\uFF1B\u4E0D\u9700\u8981\u7684\u8BDD\u7B49\u5B83\u5F00\u59CB\u540E\u518D\u70B9\u4E00\u6B21\u505C\u6B62"});const a=this._writeStdin({type:"control_request",request_id:`interrupt-${Date.now()}-${Math.random().toString(36).slice(2,8)}`,request:{subtype:"interrupt"}})?1500:0;setTimeout((()=>{this._busy&&this._proc===i&&((this._lastResultAt||0)>=r||(console.log(`[agent] graceful interrupt \u8D85\u65F6\uFF0C\u5F3A\u5236\u7ED3\u675F\u8FDB\u7A0B\u6811 PID ${c}`),this._hardKillTree(c)))}),a),this.emit("agent:message",{type:"system",subtype:"interrupted",message:"\u67E5\u8BE2\u5DF2\u4E2D\u65AD"})}kill(){if(this._dropInteractions(),this._dropInjected("\u4F1A\u8BDD\u5DF2\u7EC8\u6B62"),this.alive=!1,this._cancelRelay(),this._cancelFollowUp(),this._keepAliveTimer&&(clearInterval(this._keepAliveTimer),this._keepAliveTimer=null),this._proc&&(this._hardKillTree(this._proc.pid),this._proc=null),this._pendingReject){try{this._pendingReject(new Error("\u4F1A\u8BDD\u5DF2\u7EC8\u6B62"))}catch{}this._pendingResolve=null,this._pendingReject=null}this._busy=!1}_readTranscriptCtx(){if(!this.claudeSessionId)return null;try{const c=(0,external_path_.join)((0,external_os_.homedir)(),".claude","projects");if(!(0,external_fs_.existsSync)(c))return null;for(const i of(0,external_fs_.readdirSync)(c,{withFileTypes:!0})){if(!i.isDirectory())continue;const r=(0,external_path_.join)(c,i.name,this.claudeSessionId+".jsonl");if(!(0,external_fs_.existsSync)(r))continue;const e=(0,external_fs_.statSync)(r).size,a=Math.min(e,65536),p=Buffer.alloc(a),f=(0,external_fs_.openSync)(r,"r");try{(0,external_fs_.readSync)(f,p,0,a,e-a)}finally{(0,external_fs_.closeSync)(f)}const l=p.toString("utf8").split(`
390
390
  `).filter(Boolean);for(let s=l.length-1;s>=0;s--)try{const o=JSON.parse(l[s]),t=o.type==="assistant"?o.message?.usage:null;if(t&&(t.input_tokens||0)+(t.cache_read_input_tokens||0)+(t.cache_creation_input_tokens||0)>0)return t}catch{}}}catch{}return null}_loadResumedHistory(){try{const c=(0,external_path_.join)((0,external_os_.homedir)(),".claude","projects");if(!(0,external_fs_.existsSync)(c))return;for(const i of(0,external_fs_.readdirSync)(c,{withFileTypes:!0})){if(!i.isDirectory())continue;const r=(0,external_path_.join)(c,i.name,this.claudeSessionId+".jsonl");if(!(0,external_fs_.existsSync)(r))continue;const e=(0,external_fs_.readFileSync)(r,"utf8").split(`
391
- `).filter(Boolean),a=e.slice(-200);if(!this.firstUserText)for(const p of e.slice(0,40))try{const f=JSON.parse(p);if(f.type!=="user"&&f.type!=="human")continue;const l=f.message?.content,s=(typeof l=="string"?l:l?.find?.((o=>o.type==="text"))?.text||"").trim();if(!s||s.startsWith("/")||/^(Caveat:|<command-name>|<system-reminder>|<local-command)/.test(s))continue;this.firstUserText=s.slice(0,160);break}catch{}for(const p of a)try{const f=JSON.parse(p);if(f.isSidechain)continue;if(f.type==="human"||f.type==="user"&&f.message?.content){const l=typeof f.message.content=="string"?f.message.content:f.message.content.find((s=>s.type==="text"))?.text||"";l&&this._history.push({type:"user",content:l,timestamp:f.timestamp})}else if(f.type==="assistant"&&f.message?.content){this._history.push({type:"assistant",message:f.message,timestamp:f.timestamp});const l=f.message.usage;if(l){const s=(l.input_tokens||0)+(l.cache_read_input_tokens||0)+(l.cache_creation_input_tokens||0);this._contextTokens=s}}else f.type==="result"&&this._history.push({type:"result",total_cost_usd:f.costUSD||f.total_cost_usd,timestamp:f.timestamp})}catch{}try{const p=(0,external_fs_.statSync)(r).mtimeMs;p>0&&(this._lastActivityAt=Math.max(this._lastActivityAt,p))}catch{}return}}catch(c){console.warn("[agent] \u52A0\u8F7D\u6062\u590D\u4F1A\u8BDD\u5386\u53F2\u5931\u8D25:",c.message)}}get isBusy(){return this._busy}getRecentHistory(c=20){return this._history.slice(-c)}getUsage(){return{...this._usage}}addViewer(c,i){this._viewers.add(c),i&&this._viewerNames.set(c,i)}removeViewer(c){this._viewers.delete(c),this._viewerNames.delete(c)}get viewerCount(){return new Set(this._viewerNames.values()).size||this._viewers.size}takeControl(c,i){this.controlHolder=c,this.controlHolderName=i||null,this.lastInputTime=Date.now()}releaseControl(){this.controlHolder=null,this.controlHolderName=null,this.lastInputTime=null}isController(c){return this.controlHolder===c}setPermissionMode(c){this.permissionMode=normalizePermissionMode(c),this._proc&&(this._expectExit=!0,this.kill(),this.alive=!0)}reset(){this._dropInteractions(),this._dropInjected("\u5DF2\u5F00\u59CB\u65B0\u5BF9\u8BDD"),this._proc&&(this._expectExit=!0,this._hardKillTree(this._proc.pid),this._proc=null),this.claudeSessionId=null,this._history=[],this._contextTokens=0,this._buffer="",this._imageBlockCount=0,this._imageNudgeAt=IMAGE_NUDGE_STEP,this._cancelFollowUp(),this._followCount=0,this._followStopSignal=!1,this._cancelRelay(),this.permissionMode="bypassPermissions"}toJSON(){return{id:this.id,title:this.title,firstUserText:this.firstUserText||"",cwd:this.cwd,tags:this.tags,createdAt:this.createdAt,lastActivityAt:this._lastActivityAt||null,mode:"agent",alive:this.alive,viewers:this.viewerCount,controlHolder:this.controlHolder,controlHolderName:this.controlHolderName,permissionMode:this.permissionMode,owner:this.owner,claudeSessionId:this.claudeSessionId,busy:this._busy,interactive:!!this._interactive,injectable:_replayCap,usage:this._usage,contextTokens:this._contextTokens,followUp:this.followUpState()}}}function getSessionHealth(b){const c={found:!1,persistedMode:null,poisoned:!1,messageCount:0,transcriptKB:0,imageCount:0,updatedAt:null};if(!b)return c;try{const i=(0,external_path_.join)((0,external_os_.homedir)(),".claude","projects");if(!(0,external_fs_.existsSync)(i))return c;for(const r of(0,external_fs_.readdirSync)(i,{withFileTypes:!0})){if(!r.isDirectory())continue;const e=(0,external_path_.join)(i,r.name,b+".jsonl");if(!(0,external_fs_.existsSync)(e))continue;const a=(0,external_fs_.readFileSync)(e,"utf8"),p=a.split(`
391
+ `).filter(Boolean),a=e.slice(-200);if(!this.firstUserText)for(const p of e.slice(0,40))try{const f=JSON.parse(p);if(f.type!=="user"&&f.type!=="human")continue;const l=f.message?.content,s=(typeof l=="string"?l:l?.find?.((o=>o.type==="text"))?.text||"").trim();if(!s||s.startsWith("/")||/^(Caveat:|<command-name>|<system-reminder>|<local-command)/.test(s))continue;this.firstUserText=s.slice(0,160);break}catch{}for(const p of a)try{const f=JSON.parse(p);if(f.isSidechain)continue;if(f.type==="human"||f.type==="user"&&f.message?.content){const l=typeof f.message.content=="string"?f.message.content:f.message.content.find((s=>s.type==="text"))?.text||"";l&&this._history.push({type:"user",content:l,timestamp:f.timestamp})}else if(f.type==="assistant"&&f.message?.content){this._history.push({type:"assistant",message:f.message,timestamp:f.timestamp});const l=f.message.usage;if(l){const s=(l.input_tokens||0)+(l.cache_read_input_tokens||0)+(l.cache_creation_input_tokens||0);this._contextTokens=s}}else f.type==="result"&&this._history.push({type:"result",total_cost_usd:f.costUSD||f.total_cost_usd,timestamp:f.timestamp})}catch{}try{const p=(0,external_fs_.statSync)(r).mtimeMs;p>0&&(this._lastActivityAt=Math.max(this._lastActivityAt,p))}catch{}return}}catch(c){console.warn("[agent] \u52A0\u8F7D\u6062\u590D\u4F1A\u8BDD\u5386\u53F2\u5931\u8D25:",c.message)}}get isBusy(){return this._busy}getRecentHistory(c=20){return this._history.slice(-c)}getUsage(){return{...this._usage}}addViewer(c,i){this._viewers.add(c),i&&this._viewerNames.set(c,i)}removeViewer(c){this._viewers.delete(c),this._viewerNames.delete(c)}get viewerCount(){return new Set(this._viewerNames.values()).size||this._viewers.size}takeControl(c,i){this.controlHolder=c,this.controlHolderName=i||null,this.lastInputTime=Date.now()}releaseControl(){this.controlHolder=null,this.controlHolderName=null,this.lastInputTime=null}isController(c){return this.controlHolder===c}setPermissionMode(c){this.permissionMode=normalizePermissionMode(c),this._proc&&(this._expectExit=!0,this.kill(),this.alive=!0)}reset(){this._dropInteractions(),this._dropInjected("\u5DF2\u5F00\u59CB\u65B0\u5BF9\u8BDD"),this._proc&&(this._expectExit=!0,this._hardKillTree(this._proc.pid),this._proc=null),this.claudeSessionId=null,this._history=[],this._contextTokens=0,this._buffer="",this._imageBlockCount=0,this._imageNudgeAt=IMAGE_NUDGE_STEP,this._cancelFollowUp(),this._followCount=0,this._followStopSignal=!1,this._cancelRelay(),this.permissionMode="bypassPermissions"}_lastAssistantText(){for(let c=this._history.length-1,i=0;c>=0&&i<80;c--,i++){const r=this._history[c];if(r?.type!=="assistant"||r.parent_tool_use_id)continue;const a=(r.message?.content||[]).filter((p=>p?.type==="text")).map((p=>p.text)).join(" ").replace(/[#*`>|_~\-]+/g," ").replace(/\s+/g," ").trim();if(a)return a.slice(0,80)}return""}toJSON(){return{id:this.id,title:this.title,firstUserText:this.firstUserText||"",cwd:this.cwd,tags:this.tags,createdAt:this.createdAt,lastActivityAt:this._lastActivityAt||null,mode:"agent",alive:this.alive,viewers:this.viewerCount,controlHolder:this.controlHolder,controlHolderName:this.controlHolderName,permissionMode:this.permissionMode,owner:this.owner,claudeSessionId:this.claudeSessionId,busy:this._busy,pending:this._interactions?.size||0,lastText:this._lastAssistantText(),interactive:!!this._interactive,injectable:_replayCap,usage:this._usage,contextTokens:this._contextTokens,followUp:this.followUpState()}}}function getSessionHealth(b){const c={found:!1,persistedMode:null,poisoned:!1,messageCount:0,transcriptKB:0,imageCount:0,updatedAt:null};if(!b)return c;try{const i=(0,external_path_.join)((0,external_os_.homedir)(),".claude","projects");if(!(0,external_fs_.existsSync)(i))return c;for(const r of(0,external_fs_.readdirSync)(i,{withFileTypes:!0})){if(!r.isDirectory())continue;const e=(0,external_path_.join)(i,r.name,b+".jsonl");if(!(0,external_fs_.existsSync)(e))continue;const a=(0,external_fs_.readFileSync)(e,"utf8"),p=a.split(`
392
392
  `).filter(Boolean);let f=null,l=null,s=0;for(const o of p){const t=o.match(/"type":"image"/g);if(t&&(s+=t.length),o.includes("permissionMode"))try{const n=JSON.parse(o);n.type==="user"&&n.permissionMode&&(f=n.permissionMode)}catch{}}try{const o=JSON.parse(p[p.length-1]);o.timestamp&&(l=o.timestamp)}catch{}return{found:!0,persistedMode:f,poisoned:!!(f&&f!=="bypassPermissions"),messageCount:p.length,transcriptKB:Math.round(a.length/1024),imageCount:s,updatedAt:l}}}catch{}return c}let _claudeSessionsCache=null,_claudeSessionsCacheTime=0;const CLAUDE_SESSIONS_CACHE_TTL=3e4;function listLocalClaudeSessions(b){const c=Date.now();if(_claudeSessionsCache&&c-_claudeSessionsCacheTime<CLAUDE_SESSIONS_CACHE_TTL){if(!b)return _claudeSessionsCache;const a=(0,external_path_.resolve)((0,external_path_.normalize)(b)).replace(/[\\/]+$/,"");return _claudeSessionsCache.filter((p=>(0,external_path_.resolve)((0,external_path_.normalize)(p.projectPath)).replace(/[\\/]+$/,"").startsWith(a)))}const i=[],r=b?(0,external_path_.resolve)((0,external_path_.normalize)(b)).replace(/[\\/]+$/,""):null;try{const a=(0,external_path_.join)((0,external_os_.homedir)(),".claude","projects");if(!(0,external_fs_.existsSync)(a))return i;for(const p of(0,external_fs_.readdirSync)(a,{withFileTypes:!0})){if(!p.isDirectory())continue;const f=(0,external_path_.join)(a,p.name);try{for(const l of(0,external_fs_.readdirSync)(f)){if(!l.endsWith(".jsonl"))continue;const s=l.replace(".jsonl",""),o=(0,external_path_.join)(f,l);try{const t=(0,external_fs_.readFileSync)(o,"utf8").split(`
393
393
  `).filter(Boolean);let n=null,d=null,h=0,u="";for(const m of t)try{const _=JSON.parse(m);if(n||(n=_),d=_,h++,!u&&_.type==="human"||_.type==="user"&&_.message?.content){const w=_.message.content;if(typeof w=="string")u=w.slice(0,120);else if(Array.isArray(w)){const g=w.find((S=>S.type==="text"));g&&(u=g.text?.slice(0,120)||"")}}}catch{}let v=p.name;if(process.platform==="win32"&&/^[A-Za-z]--/.test(v)?v=v[0]+":\\"+v.slice(3).replace(/-/g,"\\"):v.startsWith("-")&&(v=v.replace(/-/g,"/")),r&&!(0,external_path_.resolve)((0,external_path_.normalize)(v)).replace(/[\\/]+$/,"").startsWith(r))continue;i.push({sessionId:s,projectDir:p.name,projectPath:v,messageCount:h,summary:u,createdAt:n?.timestamp||null,updatedAt:d?.timestamp||null})}catch{}}}catch{}}}catch{}i.sort(((a,p)=>new Date(p.updatedAt||0).getTime()-new Date(a.updatedAt||0).getTime()));const e=i.slice(0,50);return _claudeSessionsCache=e,_claudeSessionsCacheTime=Date.now(),e.slice(0,20)}const DEFAULT_SHELL=process.platform==="win32"?process.env.SHELL||"powershell.exe":process.env.SHELL||"/bin/bash",sessions_CONFIG_DIR=(0,external_path_.join)((0,external_os_.homedir)(),".myhi"),SESSIONS_FILE=(0,external_path_.join)(sessions_CONFIG_DIR,"sessions.json"),savePath=null;function loadSavedConfigs(){let b;try{b=(0,external_fs_.readFileSync)(SESSIONS_FILE,"utf8")}catch{return[]}try{const c=JSON.parse(b);if(!Array.isArray(c))throw new Error("\u5185\u5BB9\u4E0D\u662F\u6570\u7EC4");return c}catch{const c=new Date().toISOString().replace(/[:.]/g,"-");try{(0,external_fs_.copyFileSync)(SESSIONS_FILE,SESSIONS_FILE+".corrupt-"+c)}catch{}console.error(`[sessions] \u26A0 sessions.json \u635F\u574F\uFF08\u65AD\u7535\u6495\u88C2\u5199/\u88AB\u6539\u574F\uFF09\uFF0C\u5DF2\u7559\u8BC1 sessions.json.corrupt-${c}`);try{const i=JSON.parse((0,external_fs_.readFileSync)(SESSIONS_FILE+".bak","utf8"));if(Array.isArray(i)&&i.length)return console.log(`[sessions] \u2714 \u5DF2\u4ECE .bak \u6062\u590D ${i.length} \u6761\u4F1A\u8BDD\u914D\u7F6E`),i}catch{}return console.error("[sessions] \u26A0 \u65E0 .bak \u53EF\u6062\u590D\uFF0C\u672C\u6B21\u542F\u52A8\u4F1A\u8BDD\u5217\u8868\u4E3A\u7A7A\uFF08\u78C1\u76D8\u8BC1\u636E\u5DF2\u7559\u6863\uFF09"),[]}}function writeSavedConfigs(b){try{(0,external_fs_.mkdirSync)(sessions_CONFIG_DIR,{recursive:!0});try{const i=(0,external_fs_.readFileSync)(SESSIONS_FILE,"utf8").trim();(!b||!b.length)&&i&&i!=="[]"&&console.error(`[sessions] \u26A0 \u5373\u5C06\u7528\u7A7A\u5217\u8868\u8986\u76D6 ${i.length} \u5B57\u8282\u7684\u5B58\u91CF\u4F1A\u8BDD\u6570\u636E\uFF08\u82E5\u975E\u672C\u4EBA\u6E05\u7A7A\u4F1A\u8BDD\uFF0C\u7ACB\u5373\u505C\u6B62 myhi \u5E76\u627E\u56DE .bak\uFF09`)}catch{}try{(0,external_fs_.copyFileSync)(SESSIONS_FILE,SESSIONS_FILE+".bak")}catch{}const c=SESSIONS_FILE+".tmp";(0,external_fs_.writeFileSync)(c,JSON.stringify(b,null,2),{mode:384});try{(0,external_fs_.renameSync)(c,SESSIONS_FILE)}catch{(0,external_fs_.copyFileSync)(c,SESSIONS_FILE);try{(0,external_fs_.rmSync)(c,{force:!0})}catch{}}}catch(c){console.error("[sessions] \u6301\u4E45\u5316\u5199\u5165\u5931\u8D25:",c.message)}}class Session extends external_events_.EventEmitter{constructor(c,i={}){super(),this.id=c,this.createdAt=i.createdAt||new Date().toISOString(),this.title=i.title||DEFAULT_SHELL,this.cwd=i.cwd||process.env.MYHI_CWD||process.cwd(),this.tags=Array.isArray(i.tags)?i.tags:[],this.initCmd=i.initCmd||null,this.owner=i.owner||null,this.cols=i.cols||120,this.rows=i.rows||30,this._lastActivityAt=i.lastActivityAt||0,this._viewers=new Set,this._viewerNames=new Map,this.controlHolder=null,this.controlHolderName=null,this.lastInputTime=null;const r={...process.env};if(delete r.CLAUDECODE,delete r.CLAUDE_CODE_ENTRYPOINT,delete r.CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC,i.userDir){const a=(0,external_path_.join)(i.userDir,".gitconfig");(0,external_fs_.existsSync)(a)&&(r.GIT_CONFIG_GLOBAL=a)}this._pty=external_node_pty_namespaceObject.spawn(DEFAULT_SHELL,[],{name:"xterm-256color",cols:this.cols,rows:this.rows,cwd:this.cwd,env:r,useConpty:!1}),this._scrollback="";const e=100*1024;if(this._pty.onData((a=>{this.emit("data",a),this._scrollback+=a,this._scrollback.length>e&&(this._scrollback=this._scrollback.slice(this._scrollback.length-e))})),this._pty.onExit((({exitCode:a})=>{this.exitCode=a,this.emit("exit",a)})),i.initCmd){const a=i.initCmd;let p=!1;const f=l=>{!p&&/[$>#\]]\s*$/.test(l.trimEnd())&&(p=!0,this._pty.off("data",f),setTimeout((()=>this._pty.write(a+"\r")),120))};this._pty.onData(f),setTimeout((()=>{p||(p=!0,this._pty.write(a+"\r"))}),3e3)}}write(c){c!=null&&(this._lastActivityAt=Date.now(),this._pty.write(c))}resize(c,i){this.cols=c,this.rows=i,this._pty.resize(c,i)}kill(){try{this._pty.kill()}catch{}}addViewer(c,i){this._viewers.add(c),i&&this._viewerNames.set(c,i)}removeViewer(c){this._viewers.delete(c),this._viewerNames.delete(c)}get viewerCount(){return new Set(this._viewerNames.values()).size||this._viewers.size}takeControl(c,i){this.controlHolder=c,this.controlHolderName=i||null,this.lastInputTime=Date.now()}releaseControl(){this.controlHolder=null,this.controlHolderName=null,this.lastInputTime=null}isController(c){return this.controlHolder===c}toJSON(){return{id:this.id,title:this.title,cwd:this.cwd,tags:this.tags,createdAt:this.createdAt,lastActivityAt:this._lastActivityAt||null,cols:this.cols,rows:this.rows,viewers:this.viewerCount,alive:this.exitCode===void 0,controlHolder:this.controlHolder,controlHolderName:this.controlHolderName,owner:this.owner}}}class SessionManager{constructor(){this._sessions=new Map,this._agentSessions=new Map;const c=loadSavedConfigs();let i=0;for(const r of c)try{if(r.mode==="agent"){const e=this._restoreId(r.id),a=new AgentSession(e,{...r,resumeSessionId:r.claudeSessionId});a.on("session-id",(()=>this._persist())),this._agentSessions.set(e,a),i++,console.log(r.claudeSessionId?`[\u4F1A\u8BDD] \u6062\u590D Agent "${r.title}" (claude: ${r.claudeSessionId.slice(0,8)}...)`:`[\u4F1A\u8BDD] \u6062\u590D Agent "${r.title}" (\u65B0\u4E0A\u4E0B\u6587\u2014\u2014\u6B64\u524D\u5DF2\u6E05\u9664/\u672A\u53D1\u8D77\u8FC7\u67E5\u8BE2)`)}else this._spawn(this._restoreId(r.id),r,!1),i++}catch(e){console.warn(`[\u4F1A\u8BDD] \u6062\u590D "${r.title}" \u5931\u8D25:`,e.message)}c.length&&!i&&console.error(`[\u4F1A\u8BDD] \u26A0 \u78C1\u76D8\u4E0A\u6709 ${c.length} \u6761\u4F1A\u8BDD\u914D\u7F6E\u4F46\u4E00\u6761\u90FD\u6CA1\u6062\u590D\u6210\u529F \u2014\u2014 \u68C0\u67E5\u4E0A\u65B9\u65E5\u5FD7\uFF1Bsessions.json.bak \u91CC\u6709\u4E00\u4EFD\u597D\u6570\u636E`)}_restoreId(c){return typeof c=="string"&&/^[0-9a-f-]{8,64}$/i.test(c)&&!this.get(c)?c:(0,external_crypto_.randomUUID)()}_spawn(c,i,r=!0){const e=new Session(c,i);return this._sessions.set(c,e),e.on("exit",(()=>{setTimeout((()=>this._sessions.delete(c)),300*1e3)})),r&&this._persist(),e}create(c={}){return this._spawn((0,external_crypto_.randomUUID)(),c,!0)}createAgent(c={}){const i=(0,external_crypto_.randomUUID)(),r=new AgentSession(i,c);return this._agentSessions.set(i,r),r.on("session-id",(()=>this._persist())),this._persist(),r}get(c){return this._sessions.get(c)||this._agentSessions.get(c)}list(c,i=!1){let r=[...this._sessions.values()].map((a=>({...a.toJSON(),mode:"pty"}))),e=[...this._agentSessions.values()].map((a=>a.toJSON()));return c&&!i&&(r=r.filter((a=>!a.owner||a.owner===c)),e=e.filter((a=>!a.owner||a.owner===c))),[...r,...e]}listSessions(){return[...this._sessions.values(),...this._agentSessions.values()]}kill(c){const i=this._sessions.get(c);if(i){i.kill(),this._sessions.delete(c),this._persist();return}const r=this._agentSessions.get(c);r&&(r.kill(),this._agentSessions.delete(c),this._persist())}persist(){this._persist()}_persist(){const c=[...this._sessions.values()].filter((r=>r.exitCode===void 0)).map((r=>({id:r.id,mode:"pty",title:r.title,cwd:r.cwd,tags:r.tags?.length?r.tags:void 0,createdAt:r.createdAt||void 0,lastActivityAt:r._lastActivityAt||void 0,initCmd:r.initCmd||void 0,owner:r.owner||void 0}))),i=[...this._agentSessions.values()].filter((r=>r.alive)).map((r=>({id:r.id,mode:"agent",title:r.title,firstUserText:r.firstUserText||void 0,cwd:r.cwd,tags:r.tags?.length?r.tags:void 0,createdAt:r.createdAt||void 0,lastActivityAt:r._lastActivityAt||void 0,owner:r.owner||void 0,userDir:r.userDir||void 0,claudeSessionId:r.claudeSessionId||void 0})));writeSavedConfigs([...c,...i])}}const MYHI_NAME=/^(\d{13})-[0-9a-f]{6}/,norm=b=>(0,external_path_.resolve)(b).replace(/\\/g,"/");function sweepUploads(b,c){if(!(c>0))return 0;const i=Date.now()-c*864e5,r=new Set;for(const a of loadDrafts())for(const p of[...a.images||[],...a.files||[]])p?.path&&r.add(norm(p.path));let e=0;for(const a of new Set(b)){let p;try{p=(0,external_fs_.readdirSync)(a)}catch{continue}for(const f of p){const l=MYHI_NAME.exec(f);if(!l||Number(l[1])>=i)continue;const s=(0,external_path_.join)(a,f);if(!r.has(norm(s)))try{(0,external_fs_.unlinkSync)(s),e++}catch{}}}return e}const roles_CONFIG_DIR=(0,external_path_.join)((0,external_os_.homedir)(),".myhi"),ROLES_FILE=(0,external_path_.join)(roles_CONFIG_DIR,"roles.json"),USERS_FILE=(0,external_path_.join)(roles_CONFIG_DIR,"users.json"),ROLE_LEVELS={admin:3,operator:2,viewer:1};let rolesConfig=null,usersConfig=null;function loadRoles(){try{if((0,external_fs_.existsSync)(ROLES_FILE))return rolesConfig=JSON.parse((0,external_fs_.readFileSync)(ROLES_FILE,"utf8")),rolesConfig}catch(b){console.warn("[\u89D2\u8272] \u52A0\u8F7D roles.json \u5931\u8D25:",b.message)}return rolesConfig=null,null}function lookupPassword(b){if(!rolesConfig?.passwords)return null;const c=rolesConfig.passwords[b];return c?{name:c.name||"\u7528\u6237",role:c.role||"viewer"}:null}function hasPermission(b,c){return(ROLE_LEVELS[b]||0)>=(ROLE_LEVELS[c]||0)}function isMultiUserMode(){return rolesConfig!==null&&rolesConfig.passwords&&Object.keys(rolesConfig.passwords).length>0}function getDefaultRole(){return rolesConfig?.defaultRole||"admin"}function loadUsers(){try{if((0,external_fs_.existsSync)(USERS_FILE))return usersConfig=JSON.parse((0,external_fs_.readFileSync)(USERS_FILE,"utf8")),usersConfig}catch(b){console.warn("[\u7528\u6237] \u52A0\u8F7D users.json \u5931\u8D25:",b.message)}return usersConfig=null,null}function hasUsers(){return usersConfig!==null&&usersConfig.users&&Object.keys(usersConfig.users).length>0}function isExclusiveMode(){return hasUsers()&&usersConfig.exclusive===!0}function setExclusiveMode(b){usersConfig||(usersConfig={users:{}}),usersConfig.exclusive=!!b,_writeUsers()}function lookupUser(b){if(!usersConfig?.users)return null;const c=usersConfig.users[b];return c?{name:c.name||"\u7528\u6237",dir:c.dir}:null}function listUsers(){return usersConfig?.users?Object.entries(usersConfig.users).map((([b,c])=>({password:b.slice(0,2)+"*".repeat(b.length-2),name:c.name,dir:c.dir}))):[]}function addUser(b,c,i){usersConfig||(usersConfig={users:{}}),usersConfig.users||(usersConfig.users={}),usersConfig.users[b]={name:c,dir:i},_writeUsers()}function removeUser(b){return!usersConfig?.users||!usersConfig.users[b]?!1:(delete usersConfig.users[b],_writeUsers(),!0)}function changeUserPassword(b,c,i){if(!usersConfig?.users||!Object.keys(usersConfig.users).length)return{ok:!1,error:"\u672A\u914D\u7F6E\u6210\u5458\u7528\u6237"};const r=usersConfig.users,e=r[b];if(!e||i&&e.name!==i)return{ok:!1,error:"\u539F\u5BC6\u7801\u4E0D\u6B63\u786E"};if(b===c)return{ok:!1,error:"\u65B0\u5BC6\u7801\u4E0D\u80FD\u4E0E\u539F\u5BC6\u7801\u76F8\u540C"};for(const[a,p]of Object.entries(r))if(a!==b&&a===c)return{ok:!1,error:`\u65B0\u5BC6\u7801\u4E0E\u7528\u6237\u300C${p.name||"\u672A\u547D\u540D"}\u300D\u7684\u5BC6\u7801\u91CD\u590D\uFF0C\u8BF7\u6362\u4E00\u4E2A`};return delete r[b],r[c]=e,_writeUsers(),{ok:!0}}function _writeUsers(){(0,external_fs_.mkdirSync)(roles_CONFIG_DIR,{recursive:!0}),(0,external_fs_.writeFileSync)(USERS_FILE,JSON.stringify(usersConfig,null,2),{mode:384})}const ASIDE_SYSTEM_PROMPT=["\u4F60\u662F myhi \u7684\u8BB2\u89E3\u52A9\u624B\u3002\u7528\u6237\u6B63\u5728\u8BA9\u53E6\u4E00\u4E2A AI \u5E2E\u4ED6\u5B8C\u6210\u4EFB\u52A1\uFF0C\u770B\u5230\u90A3\u4E2A AI \u56DE\u590D\u91CC\u7684\u67D0\u6BB5\u5185\u5BB9\u4E0D\u592A\u7406\u89E3\uFF08\u53EF\u80FD\u5728\u5B66\u4E60\u4E2D\uFF09\uFF0C\u6765\u95EE\u4F60\u3002","\u8BF7\u7528\u7B80\u4F53\u4E2D\u6587\u3001\u901A\u4FD7\u6613\u61C2\u5730\u56DE\u7B54\uFF1A\u5148\u7528\u4E00\u4E24\u53E5\u8BDD\u76F4\u63A5\u8BF4\u6E05\u5B83\u662F\u4EC0\u4E48 / \u4EC0\u4E48\u610F\u601D\uFF0C\u518D\u7ED3\u5408\u7528\u6237\u5F53\u524D\u7684\u4EFB\u52A1\u573A\u666F\u8BF4\u660E\u5B83\u5728\u8FD9\u91CC\u8D77\u4EC0\u4E48\u4F5C\u7528\uFF0C\u5FC5\u8981\u65F6\u4E3E\u4E00\u4E2A\u751F\u6D3B\u5316\u7684\u5C0F\u4F8B\u5B50\uFF1B","\u56DE\u7B54\u91CC\u51FA\u73B0\u7684\u672F\u8BED\u987A\u5E26\u89E3\u91CA\uFF1B\u7BC7\u5E45\u9002\u4E2D\uFF0C\u4E00\u822C\u4E0D\u8D85\u8FC7 300 \u5B57\uFF0C\u7528\u6237\u8981\u6C42\u8BE6\u7EC6\u65F6\u518D\u5C55\u5F00\u3002","\u4F60\u53EA\u80FD\u89E3\u91CA\u548C\u56DE\u7B54\uFF0C\u4E0D\u80FD\u8BFB\u6587\u4EF6\u3001\u4E0D\u80FD\u6267\u884C\u547D\u4EE4\uFF0C\u4E5F\u770B\u4E0D\u5230\u5B8C\u6574\u7684\u5BF9\u8BDD\uFF1B\u4FE1\u606F\u4E0D\u591F\u65F6\u8BF4\u660E\u8FD9\u662F\u4F60\u7684\u63A8\u6D4B\u3002","\u4E0D\u8981\u66FF\u7528\u6237\u6539\u4EFB\u52A1\u3001\u4E5F\u4E0D\u8981\u5047\u88C5\u4F60\u5C31\u662F\u90A3\u4E2A\u5E72\u6D3B\u7684 AI\uFF1B\u9664\u975E\u7528\u6237\u95EE\uFF0C\u5426\u5219\u4E0D\u8981\u7ED9\u51FA\u64CD\u4F5C\u5EFA\u8BAE\u3002"].join(""),MAX_CTX=3e3,MAX_SEL=2e3,MAX_Q=1e3,MAX_HISTORY=6,TIMEOUT_MS=180*1e3,clip=(b,c)=>(b=String(b||"").trim(),b.length>c?b.slice(0,c)+"\u2026":b);function buildPrompt({title:b,userAsk:c,context:i,selection:r,question:e,history:a}){const p=[];b&&p.push(`\u3010\u4EFB\u52A1\u3011${clip(b,100)}`),c&&p.push(`\u3010\u7528\u6237\u5F53\u65F6\u7ED9\u90A3\u4E2A AI \u7684\u9700\u6C42\u3011
394
394
  ${clip(c,1e3)}`),i&&p.push(`\u3010\u90A3\u4E2A AI \u7684\u56DE\u590D\uFF08\u8282\u9009\uFF09\u3011
@@ -0,0 +1,46 @@
1
+ // 任务「要不要你看一眼」的判定,首页卡片 / 会话页切换面板 / 其他任务提醒共用。
2
+ // wait:AI 在等你回答提问 / 审批方案(最优先)
3
+ // busy:正在执行
4
+ // done:你上次看过之后又有了新动静(本设备未读)
5
+ // 「看过」记在本机 localStorage(myhi_seen:{会话id: 毫秒}),不跨设备同步——手机上看过不代表电脑上看过。
6
+ (function () {
7
+ const KEY = 'myhi_seen';
8
+ let seen = null;
9
+ function load() {
10
+ if (seen) return seen;
11
+ try { seen = JSON.parse(localStorage.getItem(KEY) || 'null'); } catch { seen = null; }
12
+ return seen;
13
+ }
14
+ function save() { try { localStorage.setItem(KEY, JSON.stringify(seen)); } catch {} }
15
+ const ts = (s) => {
16
+ const v = s.lastActivityAt || 0;
17
+ return typeof v === 'number' ? v : (new Date(v).getTime() || 0);
18
+ };
19
+
20
+ window.myhiAttn = {
21
+ // 首次使用(本机还没有记录):把现有任务全当已读,免得一上来满屏未读
22
+ init(list) {
23
+ if (load() || !(list && list.length)) return;
24
+ seen = {};
25
+ for (const s of list || []) seen[s.id] = Date.now();
26
+ save();
27
+ },
28
+ markSeen(id) {
29
+ load(); if (!seen) seen = {};
30
+ seen[id] = Date.now();
31
+ // 顺手清掉早已不存在的老记录(只留最近 200 个)
32
+ const ids = Object.keys(seen);
33
+ if (ids.length > 200) ids.sort((a, b) => seen[a] - seen[b]).slice(0, ids.length - 200).forEach((k) => delete seen[k]);
34
+ save();
35
+ },
36
+ of(s) {
37
+ if (s.pending > 0) return 'wait';
38
+ if (s.busy) return 'busy';
39
+ const t = ts(s); const v = (load() || {})[s.id];
40
+ return v != null && t > v + 1000 ? 'done' : '';
41
+ },
42
+ rank(a) { return { wait: 0, busy: 1, done: 2 }[a] ?? 3; },
43
+ label: { wait: '等你回复', busy: '执行中', done: '新完成' },
44
+ color: { wait: 'var(--orange, #db6d28)', busy: 'var(--blue, #2f81f7)', done: 'var(--green, #3fb950)' },
45
+ };
46
+ })();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@wendongfly/myhi",
3
- "version": "1.3.197",
3
+ "version": "1.3.198",
4
4
  "description": "Web-based terminal sharing with chat UI — control your terminal from phone via LAN/Tailscale",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",