openclaw-code-agent 4.5.3 → 4.5.5

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.js CHANGED
@@ -1,45 +1,45 @@
1
- var Tu=Object.defineProperty;var H=(t,e,n)=>()=>{if(n)throw n[0];try{return t&&(e=t(t=0)),e}catch(r){throw n=[r],r}};var Cu=(t,e)=>{for(var n in e)Tu(t,n,{get:e[n],enumerable:!0})};function Ht(t,e){return e?{...e,...t}:t}function Mu(t){return{...t,[Uo]:!0}}function _u(t){return{const:t,type:typeof t}}var Uo,g,te=H(()=>{Uo=Symbol("optionalSchema");g={Object(t,e){let n=Object.entries(t).filter(([,o])=>!o[Uo]).map(([o])=>o),r=Object.fromEntries(Object.entries(t).map(([o,i])=>{let{[Uo]:s,...l}=i;return[o,l]}));return{...e,type:"object",...n.length>0?{required:n}:{},properties:r}},String(t){return Ht({type:"string"},t)},Number(t){return Ht({type:"number"},t)},Boolean(t){return Ht({type:"boolean"},t)},Array(t,e){return Ht({type:"array",items:t},e)},Literal:_u,Union(t,e){return Ht({anyOf:t},e)},Optional:Mu}});function Ko(t){S=t}function Vo(t){z=t}var S,z,N=H(()=>{S=null,z=null});function xs(t){let e=t.chatId.trim(),n=t.topicId.trim();return!/^-?\d+$/.test(e)||!/^\d+$/.test(n)?null:`${e}:topic:${n}`}function Wu(t){let e=t.conversationId.trim(),n=e.match(/^(-?\d+):topic:(\d+)$/i);if(n?.[1]&&n[2]){let i=xs({chatId:n[1],topicId:n[2]});return i?{chatId:n[1],topicId:n[2],canonicalConversationId:i}:null}if(!/^\d+$/.test(e))return null;let r=t.parentConversationId?.trim();if(!r||!/^-?\d+$/.test(r))return null;let o=xs({chatId:r,topicId:e});return o?{chatId:r,topicId:e,canonicalConversationId:o}:null}function Nu(t){if(!t)return;let e=t.match(/^agent:[^:]+:discord:(direct|dm|channel|group):/i);if(!e?.[1])return;let n=e[1].toLowerCase();return n==="direct"||n==="dm"?"user":"channel"}function Lu(t,e){if(!/^\d+$/.test(t))return t;let n=Nu(e);return n?`${n}:${t}`:`channel:${t}`}function Fu(t){if(!(!t?.provider||!t.target)&&!(t.provider==="system"||t.target==="system"))return t.accountId?`${t.provider}|${t.accountId}|${t.target}`:`${t.provider}|${t.target}`}function Bu(t){let e=t.toLowerCase(),n=[":thread:",":topic:"];for(let r of n){let o=e.lastIndexOf(r);if(o===-1)continue;let i=t.slice(0,o).trim(),s=t.slice(o+r.length).trim()||void 0;return{id:i||t,threadId:s}}return{id:t}}function qu(t){let e=t?.trim();if(!e)return;let n=e.split(":").filter(Boolean);if(n[0]?.trim().toLowerCase()==="agent")for(let r=2;r<=n.length-3;r+=1){let o=n[r]?.trim().toLowerCase();if(!o||!Ou.has(o))continue;let i=n[r+1]?.trim().toLowerCase(),s=n.slice(r+2).join(":").trim();if(!(!i||!s))return{provider:o,kind:i,rawId:s}}}function Uu(t,e=Wu){try{return e({conversationId:t})}catch{return null}}function Go(t){return{provider:"system",target:"system",sessionKey:t?.trim()||void 0}}function jo(t,e){return{...t,threadId:e??t.threadId}}function Vu(t,e,n){return t==="telegram"&&n?.provider==="telegram"&&!!n.target&&e!==n.target}function Gu(t){let e=t?.trim();if(!e)return;let n=qu(e);if(!n)return;let{provider:r,kind:o,rawId:i}=n,s=Bu(i),l=null;if(r==="telegram")try{l=Ku.safeParseTelegramTopicConversation(i)}catch{l=null}let a=l?.chatId??s.id,d=l?.topicId??s.threadId,u=r==="discord"?o==="direct"||o==="dm"?`user:${a}`:`channel:${a}`:a;return{provider:r,target:u,threadId:d,sessionKey:e}}function Ho(t){let e=t?.match(/:topic:(\d+)$/i);return e?parseInt(e[1],10):void 0}function Ts(t){return!!(t?.provider&&t.target&&t.provider!=="system"&&t.target!=="system")}function zt(t,e,n){let r=Gu(n),o=e!=null?String(e):void 0,i=t?.trim();if(!i||i.toLowerCase()==="unknown")return r?jo(r,o):Go(n);let s=i.split("|").map(f=>f.trim());if(s.length<2)return r?jo(r,o):Go(n);let[l,a,d]=s,u=s.length>=3?d:a,c=s.length>=3?a:void 0,m=l?.toLowerCase();if(!m||!u)return r?jo(r,o):Go(n);let p=m==="discord"?Lu(u,n):u;return Vu(m,p,r)?{provider:m,accountId:c,target:r.target,threadId:o??r.threadId,sessionKey:n?.trim()||void 0}:{provider:m,accountId:c,target:p,threadId:o??(r?.provider===m?r.threadId:void 0),sessionKey:n?.trim()||void 0}}function Qe(t){return zt(Fu(t.route)??t.originChannel,t.route?.threadId??t.originThreadId,t.route?.sessionKey??t.originSessionKey)??t.route}function _e(t){let e=Qe(t);return Ts(e)?e:void 0}function ju(t){return Object.fromEntries(Object.entries(t).filter(e=>!!e[1]))}function Qt(t){let e=Qe(t);if(!Ts(e))return"";let n=ju({provider:e?.provider,accountId:e?.accountId,target:e?.target,threadId:e?.threadId??(t.originThreadId!=null?String(t.originThreadId):void 0),sessionKey:e?.sessionKey??t.originSessionKey});return Object.keys(n).length===0?"":["Session origin route (authoritative for human follow-ups):",`originRoute: ${JSON.stringify(n)}`,"Routing rule: Send any human follow-up for this wake to originRoute. If originRoute differs from the current chat, do not use a plain final assistant reply; use a routed send path that preserves provider/target/threadId."].join(`
2
- `)}var Ou,Ku,be=H(()=>{Ou=new Set(["telegram","discord","slack","system","mattermost","feishu","line","whatsapp","signal","matrix","googlechat","bluebubbles","imessage","msteams"]);Ku={safeParseTelegramTopicConversation:Uu}});import{readFileSync as Hu}from"fs";import{homedir as zu}from"os";import{join as Qu}from"path";function Ms(){if(Jt!==void 0)return Jt;try{let t=Hu(Qu(zu(),".claude.json"),"utf-8");Jt=JSON.parse(t).mcpServers??{}}catch{Jt={}}return Jt}function _s(t){let e=t.defaultHarness??Cs,n={};for(let[r,o]of Object.entries(Yt)){let i={...o};o.allowedModels&&(i.allowedModels=[...o.allowedModels]),n[r]=i}for(let[r,o]of Object.entries(t.harnesses??{})){let i=n[r]??{},s={...i,defaultModel:o.defaultModel??i.defaultModel,reasoningEffort:o.reasoningEffort??i.reasoningEffort,fastMode:o.fastMode??i.fastMode};o.allowedModels!==void 0?s.allowedModels=o.allowedModels?[...o.allowedModels]:o.allowedModels:o.defaultModel!==void 0&&(s.allowedModels=void 0),n[r]=s}if(t.defaultModel!==void 0){let r=n[e]??{};n[e]={...r,defaultModel:t.harnesses?.[e]?.defaultModel??t.defaultModel,allowedModels:t.harnesses?.[e]?.allowedModels!==void 0?r.allowedModels:t.allowedModels},`${e}`}if(t.model!==void 0){let r=n.codex??{};n.codex={...r,defaultModel:t.harnesses?.codex?.defaultModel??t.model,allowedModels:t.harnesses?.codex?.allowedModels!==void 0?r.allowedModels:t.allowedModels}}if(t.reasoningEffort!==void 0){let r=n.codex??{};n.codex={...r,reasoningEffort:t.harnesses?.codex?.reasoningEffort??t.reasoningEffort}}if(t.allowedModels!==void 0)for(let[r,o]of Object.entries(n))t.harnesses?.[r]?.allowedModels===void 0&&(n[r]={...o,allowedModels:void 0});D={maxSessions:t.maxSessions??20,defaultWorkdir:t.defaultWorkdir,idleTimeoutMinutes:t.idleTimeoutMinutes??15,sessionGcAgeMinutes:t.sessionGcAgeMinutes??1440,maxPersistedSessions:t.maxPersistedSessions??1e4,fallbackChannel:t.fallbackChannel,agentChannels:t.agentChannels,maxAutoResponds:t.maxAutoResponds??10,permissionMode:t.permissionMode??"plan",planApproval:t.planApproval??"delegate",defaultHarness:e,harnesses:n,allowedModels:t.allowedModels,defaultWorktreeStrategy:t.defaultWorktreeStrategy??"delegate",worktreeDir:t.worktreeDir}}function ae(){return D.defaultHarness??Cs}function Jo(t){let e=Yt[t],n=D.harnesses[t];return{...e,...n,allowedModels:n?.allowedModels??e?.allowedModels}}function ut(t){return Jo(t).defaultModel}function _n(t){return D.harnesses[t]?.allowedModels??D.allowedModels}function Be(t){return Jo(t).reasoningEffort}function ct(t){return t==="codex"?Jo(t).fastMode:void 0}function Se(t){return t==null?void 0:String(t).trim()||void 0}function Yo(t){return{channel:Se(t?.deliveryContext?.channel),to:Se(t?.deliveryContext?.to),accountId:Se(t?.deliveryContext?.accountId),threadId:Se(t?.deliveryContext?.threadId)}}function $s(t,e,n){if(!(!t||!e))return n?`${t}|${n}|${e}`:`${t}|${e}`}function zo(t){return Se(t?.requesterSenderId??t?.senderId)}function Qo(t){return(Se(t.deliveryContext?.channel)??t.messageChannel??t.channel)?.toLowerCase()!=="telegram"?!1:!!(Ho(t.sessionKey)||Se(t.messageThreadId)||Se(t.deliveryContext?.threadId))}function $n(t){let e=Yo(t),n=$s(e.channel,e.to,e.accountId);if(n)return n;if(t.messageChannel){let r=t.messageChannel.split("|");if(r.length>=3)return t.messageChannel;if(t.agentAccountId&&r.length>=2)return`${r[0]}|${t.agentAccountId}|${r.slice(1).join("|")}`;let o=Se(t.chatId);if(r.length===1&&o)return`${r[0]}|${o}`;let i=zo(t);if(r.length===1&&i&&!Qo(t))return`${r[0]}|${i}`}if(t.workspaceDir){let r=Je(t.workspaceDir);if(r)return r}if(t.messageChannel&&t.messageChannel.includes("|"))return t.messageChannel}function Zt(t,e){if(e&&String(e).includes("|"))return String(e);let n=Yo(t),r=$s(n.channel,n.to,n.accountId);if(r)return r;if(t?.channelId&&String(t.channelId).includes("|"))return String(t.channelId);if(t?.messageChannel){let l=String(t.messageChannel);if(l.includes("|"))return l;let a=Se(t.chatId);if(a)return`${l}|${a}`;let d=zo(t);if(d&&!Qo(t))return`${l}|${d}`}let o=Se(t?.channel),i=Se(t?.chatId);if(o&&i)return`${o}|${i}`;let s=zo(t);return o&&s&&!Qo(t)?`${o}|${s}`:t?.id&&/^-?\d+$/.test(String(t.id))?`telegram|${t.id}`:D.fallbackChannel??"unknown"}function Zo(t){return Yo(t).threadId??t?.messageThreadId??void 0}function pt(t,e,n){return zt(Zt(t,e),Zo(t),n??t?.sessionKey)}function Je(t){let e=D.agentChannels;if(!e)return;let n=i=>i.replace(/\/+$/,""),r=n(t),o=Object.entries(e).sort((i,s)=>s[0].length-i[0].length);for(let[i,s]of o)if(r===n(i)||r.startsWith(n(i)+"/"))return s}function Es(t){return Ho(t)}var Jt,Cs,Yt,D,ie=H(()=>{be();Cs="claude-code",Yt={"claude-code":{defaultModel:"anthropic/claude-sonnet-4-7",allowedModels:["sonnet","opus"]},codex:{defaultModel:"gpt-5.5",allowedModels:["gpt-5.5","gpt-5.5-pro"],reasoningEffort:"medium"},opencode:{}};D={maxSessions:20,idleTimeoutMinutes:15,sessionGcAgeMinutes:1440,maxPersistedSessions:1e4,maxAutoResponds:10,permissionMode:"plan",planApproval:"delegate",defaultWorktreeStrategy:"delegate",harnesses:{"claude-code":{...Yt["claude-code"]},codex:{...Yt.codex},opencode:{...Yt.opencode}}}});function q(t){return t&&typeof t=="object"&&!Array.isArray(t)?t:null}function G(t,e,n){for(let r of e){let o=t?.[r];if(typeof o!="string")continue;let i=n?.trim===!1?o:o.trim();if(i)return i}}function Ds(t,e){return e&&typeof e.recommended=="boolean"?e.recommended:e&&typeof e.isRecommended=="boolean"?e.isRecommended:/\b(?:not\s+(?:a\s+)?|non[-\s]?|un)recommended\b/i.test(t)?!1:/\brecommended\b/i.test(t)}function Os(t){if(typeof t=="string"){let s=t.trim();return s?{label:s,value:s,recommended:Ds(s)}:void 0}let e=q(t);if(!e)return;let n=G(e,["label","title","text","value","name","id"])?.trim();if(!n)return;let r=G(e,["description","preview","detail","details"]),o=G(e,["value","id","name"]),i=e.isOther===!0||e.is_other===!0||e.other===!0;return{label:n,...r?{description:r}:{},...o?{value:o}:{},...i?{isOther:!0}:{},recommended:Ds(n,e)}}function En(t){let e=q(t);if(!e)return[];let n=e.options??e.choices??e.availableDecisions??e.decisions;return Array.isArray(n)?n.map(Os).filter(r=>!!r):[]}function ft(t){let e=q(t);return(Array.isArray(e?.questions)?e.questions:[]).map((r,o)=>Ju(r,o)).filter(r=>!!r)}function Ju(t,e=0){let n=q(t);if(!n)return;let r=G(n,["question","prompt","message","text","summary"])?.trim();if(!r)return;let o=G(n,["id","questionId","question_id","name"]),i=G(n,["header","title","label"]),l=(Array.isArray(n.options)?n.options:Array.isArray(n.choices)?n.choices:[]).map(Os).filter(u=>!!u),a=n.multiSelect===!0||n.multi_select===!0,d=n.isOther===!0||n.is_other===!0||n.allowFreeText===!0||n.allowsFreeText===!0||a||l.some(u=>u.isOther);return{id:o??`question_${e+1}`,...i?{header:i}:{},question:r,options:l,...a?{multiSelect:!0}:{},...d?{allowsFreeText:!0}:{},...n.isSecret===!0||n.is_secret===!0?{isSecret:!0}:{}}}function Ws(t,e,n){let r=[n>1?`Question ${e+1}`:void 0,t.header].filter(Boolean).join(" - "),o=[...r?[r]:[],t.question];return t.options.length>0&&o.push("Options:",...t.options.map((i,s)=>{let l=i.recommended&&!/\brecommended\b/i.test(i.label)?" (recommended)":"",a=i.description?` - ${i.description}`:"",d=i.isOther?" (free text)":"";return` ${s+1}. ${i.label}${l}${d}${a}`})),t.allowsFreeText&&!t.options.some(i=>i.isOther)&&o.push(t.multiSelect?"Reply with one or more option labels.":"Free-form answer is allowed."),o}function Dn(t){if(t.length===0)return;let e=t.flatMap((n,r)=>[...r>0?[""]:[],...Ws(n,r,t.length)]);return t.length>1&&e.push("","Reply with answers by question, for example: Q1: ..., Q2: ..."),e.join(`
3
- `)}function $e(t,e,n){return Ws(t,e,n).join(`
4
- `)}var Xt=H(()=>{});function gt(t){return{type:"backend_ref",ref:t}}function ht(t){return{type:"run_started",...t?{runId:t}:{}}}function Ye(t){return{type:"text_delta",text:t}}function On(t,e){return{type:"tool_call",name:t,input:e}}function Te(t){return{type:"pending_input",state:t}}function Ue(t){return t?{type:"pending_input_resolved",requestId:t}:{type:"pending_input_resolved"}}function Wn(t,e){return{type:"plan_artifact",artifact:t,finalized:e}}function yt(t){return t?{type:"settings_changed",permissionMode:t}:{type:"settings_changed"}}function Ee(t){return{type:"run_completed",data:t}}var qe,Nn=H(()=>{qe=class{queue=[];resolvePending=null;done=!1;enqueue(e){this.queue.push(e),this.flush()}close(){this.done=!0,this.flush()}flush(){this.resolvePending&&(this.resolvePending(),this.resolvePending=null)}messages(){let e=this;return(async function*(){for(;;){for(;e.queue.length>0;)yield e.queue.shift();if(e.done)return;await new Promise(n=>{e.resolvePending=n})}})()}}});import*as Fn from"@anthropic-ai/claude-agent-sdk";function Yu(t){if(typeof t.result=="string"&&t.result.length>0)return t.result;if(Array.isArray(t.errors)){let e=t.errors.filter(n=>typeof n=="string"&&n.length>0);if(e.length>0)return e.join(`
5
- `)}}function Zu(t,e,n){let r=ft(n),o=r.length>0?0:void 0,i=o!=null?r[o]:void 0,s=i?.options.map(a=>a.label)??[],l=i?$e(i,o,r.length):Dn(r);return{requestId:`${t||"claude"}-ask-${e}`,kind:"question",promptText:l,options:s,...r.length>0?{questions:r}:{},...o!=null?{activeQuestionIndex:o}:{},allowsFreeText:i?.allowsFreeText===!0||s.length===0}}var Ln,Ns=H(()=>{Xt();Nn();Ln=class{constructor(e={}){this.deps=e}deps;name="claude-code";backendKind="claude-code";supportedPermissionModes=["default","plan","bypassPermissions"];capabilities={nativePendingInput:!1,nativePlanArtifacts:!1,worktrees:"plugin-managed"};launch(e){let n=new qe,r=!1,o="",i=!1,s=0,l=e.resumeSessionId??"",a=e.canUseTool,d={cwd:e.cwd,model:e.model,...e.reasoningEffort?{effort:e.reasoningEffort}:{},permissionMode:e.permissionMode,allowDangerouslySkipPermissions:!0,allowedTools:e.allowedTools,systemPrompt:e.systemPrompt,includePartialMessages:!0,abortController:e.abortController,mcpServers:e.mcpServers,...a?{canUseTool:async(f,h)=>{if(f!=="AskUserQuestion")return{behavior:"allow"};let k=Zu(l,++s,h);n.enqueue(Te(k));try{let v=await a(f,h);return n.enqueue(Ue(k.requestId)),v}catch(v){throw n.enqueue(Ue(k.requestId)),v}}}:{}};e.resumeSessionId&&(d.resume=e.resumeSessionId,d.forkSession=e.forkSession??!1);let u=e.prompt,c=this.deps.query??Fn.query,m=this.deps.startup??Fn.startup,p=(async()=>{if(typeof m!="function")return c({prompt:u,options:d});let f=await m({options:d});try{return f.query(u)}catch(h){throw await f.close?.(),h}})();return(async()=>{try{let f=await p;for await(let h of f){let k=h;if(k.type==="system"&&k.subtype==="init"){l=k.session_id??l,n.enqueue(gt({kind:"claude-code",conversationId:l}));continue}if(k.type==="system"&&k.subtype==="status"&&k.permissionMode){n.enqueue(yt(k.permissionMode));continue}if(k.type==="assistant"){r||(r=!0,n.enqueue(ht()));for(let v of k.message?.content??[]){if(v.type==="text"){o+=o?`
6
- ${v.text}`:v.text,n.enqueue(Ye(v.text));continue}v.type==="tool_use"&&((v.name==="ExitPlanMode"||v.name==="set_permission_mode")&&(i=!0),v.name!=="AskUserQuestion"&&n.enqueue(On(v.name,v.input)))}continue}if(k.type==="result"){let v=o.trim();if(v&&(e.permissionMode==="plan"||i)){let I={explanation:void 0,steps:[],markdown:v};n.enqueue(Wn(I,!0))}n.enqueue(Ee({success:k.subtype==="success",duration_ms:k.duration_ms??0,total_cost_usd:k.total_cost_usd??0,num_turns:k.num_turns??0,result:Yu(k),session_id:k.session_id??l})),o="",i=!1,r=!1}}}finally{n.close()}})().catch(f=>{n.enqueue(Ee({success:!1,duration_ms:0,total_cost_usd:0,num_turns:0,result:f instanceof Error?f.message:String(f),session_id:l})),n.close()}),{messages:n.messages(),async setPermissionMode(f){let h=await p;typeof h.setPermissionMode=="function"&&await h.setPermissionMode(f)},async streamInput(f){let h=await p;typeof h.streamInput=="function"&&await h.streamInput(f)},async interrupt(){let f=await p;typeof f.interrupt=="function"&&await f.interrupt()}}}buildUserMessage(e,n){return{type:"user",message:{role:"user",content:e},parent_tool_use_id:null,session_id:n}}}});import{spawn as Xu}from"node:child_process";import ec from"node:readline";function tc(t){return t instanceof Error?t.message:String(t)}function nc(t){try{let e=JSON.parse(t);return!e||typeof e!="object"||Array.isArray(e)?null:e}catch{return null}}async function rc(t,e){if(t.id!=null&&(Object.hasOwn(t,"result")||Object.hasOwn(t,"error"))){let r=String(t.id),o=e.pending.get(r);if(!o)return;if(clearTimeout(o.timer),e.pending.delete(r),t.error){o.reject(new Error(`codex app server rpc error (${t.error.code??"unknown"}): ${t.error.message??"unknown error"}`));return}o.resolve(t.result);return}let n=t.method?.trim();if(n){if(t.id==null){await e.onNotification(n,t.params);return}try{let r=await e.onRequest(n,t.params);e.respond({jsonrpc:"2.0",id:t.id,result:r??{}})}catch(r){e.respond({jsonrpc:"2.0",id:t.id,error:{code:-32603,message:tc(r)}})}}}function oc(t){return t.replace(/\b([a-z][a-z0-9+.-]*:\/\/)[^\s/?#@]+@/gi,"$1[redacted credential]@").replace(/\b(authorization\s*[:=]\s*)[^\r\n,;}]+/gi,"$1[redacted credential]").replace(/\b(Bearer\s+)[^\s]+/gi,"$1[redacted credential]").replace(/(["'][A-Za-z0-9_.-]*(?:api[_-]?key|token|secret|password|authorization)[A-Za-z0-9_.-]*["']\s*:\s*["'])[^"']+(["'])/gi,"$1[redacted credential]$2").replace(/\b([A-Za-z0-9_.-]*(?:api[_-]?key|token|secret|password|authorization)[A-Za-z0-9_.-]*\s*[:=]\s*)[^\s,}]+/gi,"$1[redacted credential]").replace(/\b(?:sk-[A-Za-z0-9_-]{8,}|gh[opsru]_[A-Za-z0-9_]{8,}|[A-Za-z0-9_-]{32,})\b/g,"[redacted token]").replace(/(?:\/Users|\/home)\/[^\s]+/g,"[redacted path]").replace(/\s+/g," ").slice(-1e3)}var Bn,Ls=H(()=>{Bn=class{constructor(e,n,r){this.command=e;this.args=n;this.requestTimeoutMs=r}command;args;requestTimeoutMs;process=null;pending=new Map;stderrTail="";counter=0;onNotification=()=>{};onRequest=async()=>({});setNotificationHandler(e){this.onNotification=e}setRequestHandler(e){this.onRequest=e}async connect(){if(this.process)return;let e=Xu(this.command,["app-server",...this.args],{stdio:["pipe","pipe","pipe"],env:process.env});if(!e.stdin||!e.stdout||!e.stderr)throw new Error("codex app server stdio pipes unavailable");this.process=e,ec.createInterface({input:e.stdout}).on("line",r=>{this.handleLine(r)}),e.stderr.on("data",r=>{this.stderrTail=`${this.stderrTail}${r.toString("utf8")}`.slice(-4e3)}),e.on("close",()=>{this.flushPending(new Error("codex app server stdio closed")),this.process=null})}async close(){this.flushPending(new Error("codex app server stdio closed"));let e=this.process;this.process=null,e&&e.kill()}async notify(e,n){this.write({jsonrpc:"2.0",method:e,params:n??{}})}async request(e,n,r){let o=`rpc-${++this.counter}`,i=new Promise((s,l)=>{let a=Math.max(100,r??this.requestTimeoutMs),d=setTimeout(()=>{this.pending.delete(o),l(new Error(this.buildTimeoutErrorMessage(e,a)))},a);d.unref?.(),this.pending.set(o,{resolve:s,reject:l,timer:d})});return this.write({jsonrpc:"2.0",id:o,method:e,params:n??{}}),await i}write(e){if(!this.process?.stdin)throw new Error("codex app server stdio not connected");this.process.stdin.write(`${JSON.stringify(e)}
7
- `)}async handleLine(e){let n=nc(e);n&&await rc(n,{pending:this.pending,onNotification:this.onNotification,onRequest:this.onRequest,respond:r=>this.write(r)})}flushPending(e){for(let[n,r]of this.pending)clearTimeout(r.timer),r.reject(e),this.pending.delete(n)}buildTimeoutErrorMessage(e,n){let r=this.stderrTail.trim(),o=r?`; recent stderr: ${oc(r)}`:"";return`codex app server timeout after ${n}ms: ${e}${o}`}}});function Fs(t,e){if(!e||e.length===0)return!0;if(!t)return!1;let n=t.toLowerCase();return e.some(r=>n.includes(r.toLowerCase()))}var Bs=H(()=>{});function De(t,e){let n=e?.trim();if(!n)return;if(t!=="codex")return n;let[r,...o]=n.split("/");return r?.toLowerCase()==="openai"&&o.length===1&&o[0]?.trim()?o[0].trim():n}function ic(t,e){if(!e||e.length===0)return!0;if(!t)return!1;let n=t.toLowerCase();return e.some(r=>De("codex",r)?.toLowerCase()===n)}function qn(t,e,n){return t==="codex"?ic(e,n):Fs(e,n)}function kt(t,e){return t!=="codex"||!e?!0:!e.includes("/")}function Un(t,e,n){if(t!=="codex"||!e||!n||n.length===0)return e;let r=e.toLowerCase(),o=n.find(i=>De("codex",i)?.toLowerCase()===r);return De("codex",o)??e}var Kn=H(()=>{Bs()});function sc(t){return t instanceof Error?t.message:String(t)}function qs(t){return t?t.split(",").map(e=>e.trim()).filter(Boolean):[]}function Ke(t){if(typeof t=="string")return t;if(Array.isArray(t))return t.map(n=>Ke(n)).join("");let e=q(t);if(!e)return"";for(let n of["delta","text","content","message","input","output","parts"]){let r=Ke(e[n]);if(r)return r}for(let n of["item","turn","thread","response","result","data"]){let r=Ke(e[n]);if(r)return r}return""}function en(t){let e=q(t);if(!e)return{};let n=q(e.thread)??q(e.session),r=q(e.turn)??q(e.run),o=q(e.item),i=q(e.serverRequest);return{threadId:G(e,["threadId","thread_id","conversationId","conversation_id"])??G(n,["id","threadId","thread_id","conversationId"]),runId:G(e,["turnId","turn_id","runId","run_id"])??G(r,["id","turnId","turn_id","runId","run_id"]),requestId:G(e,["requestId","request_id","serverRequestId"])??G(i,["id","requestId","request_id"]),itemId:G(e,["itemId","item_id"])??G(o,["id","itemId","item_id"])}}function Vn(t,e,n=0){if(n>6)return;if(Array.isArray(t)){for(let i of t){let s=Vn(i,e,n+1);if(s)return s}return}let r=q(t);if(!r)return;let o=G(r,e);if(o)return o;for(let i of Object.values(r)){let s=Vn(i,e,n+1);if(s)return s}}function tn(t){return{threadId:en(t).threadId,cwd:Vn(t,["cwd","workdir","directory"])}}function Us(t){let e=t?.trim();return!!(e&&/[/\\]worktrees[/\\][^/\\]+[/\\][^/\\]+/.test(e))}function Ks(t){let e=t?.trim();if(!e)return;let n=e.split(/[/\\]+/).filter(Boolean),r=n.lastIndexOf("worktrees");if(!(r<0||r+1>=n.length))return n[r+1]}function Gn(t){let e=q(t);if(!e)return;let n=q(e.item)??e;return G(n,["id","itemId","item_id","messageId","message_id"])}function ac(t,e=!1){let n=q(t);if(!n)return"";let r=q(n.item)??n;return G(r,["type"])?.toLowerCase()!=="agentmessage"?"":e?Ke(r):G(r,["text"],{trim:!1})??Ke(r)}function Vs(t,e){let n=t.trim().toLowerCase();return n==="item/agentmessage/delta"?{mode:"delta",text:Ke(e),itemId:Gn(e)}:n==="item/completed"?{mode:"snapshot",text:ac(e),itemId:Gn(e)}:{mode:"ignore",text:""}}function Gs(t){return{itemId:Gn(t),delta:Ke(t)}}function js(t){let e=q(t),n=q(e?.plan),o=(Array.isArray(e?.plan)?e.plan:Array.isArray(n?.steps)?n.steps:[]).map(i=>{let s=q(i),l=G(s,["step","title","text"]);if(!l)return null;let a=G(s,["status"])?.toLowerCase()??"pending";return{step:l,status:a==="inprogress"||a==="in_progress"?"inProgress":a==="completed"?"completed":"pending"}}).filter(Boolean);return{explanation:G(n,["explanation"])??G(e,["explanation"]),steps:o}}function Hs(t){let e=q(t);if(!e)return{};let n=q(e.item)??e;return G(n,["type"])?.toLowerCase()!=="plan"?{}:{itemId:Gn(n),text:G(n,["text"],{trim:!1})??Ke(n)}}function zs(t,e){let n=t.trim().toLowerCase();if(n==="turn/failed")return"failed";if(n==="turn/cancelled")return"interrupted";let r=q(e)??{},o=q(r.turn)??r,i=G(o,["status"])?.toLowerCase();return i==="failed"?"failed":i==="interrupted"||i==="cancelled"?"interrupted":"completed"}function Qs(t,e){let n=q(e)??{},r=q(n.turn)??n,o=q(r.error)??q(n.error);if(o)return G(o,["message","text","summary","reason"])}function lc(t,e){let n=sc(t).toLowerCase();return n.includes("method not found")||n.includes("unknown method")?!0:n.includes("unknown variant")?e?n.includes(`unknown variant \`${e.toLowerCase()}\``):!0:!1}function uc(t){return dc.has(t.trim().toLowerCase())}function cc(t){let e=q(t);return e?!!G(e,["threadId","thread_id"]):!1}async function nn(t){if(t.payloads.length===0)throw new Error(`codex app server request skipped: no payloads for ${t.methods.join(", ")||"<none>"}`);let e;for(let n of t.methods)for(let r of t.payloads){if(uc(n)&&!cc(r))throw new Error(`codex app server request missing threadId: ${n}`);try{return await t.client.request(n,r,t.timeoutMs)}catch(o){if(e=o,!lc(o,n))continue}}throw e instanceof Error?e:new Error(String(e))}function Js(t){let e={cwd:t.cwd};return t.model?.trim()&&(e.model=t.model.trim()),t.reasoningEffort?.trim()&&(e.reasoningEffort=t.reasoningEffort.trim()),t.fastMode===!0&&(e.service_tier="fast"),t.approvalPolicy?.trim()&&(e.approvalPolicy=t.approvalPolicy.trim()),t.sandbox?.trim()&&(e.sandbox=t.sandbox.trim()),[e]}function Ys(t){let e={threadId:t.threadId,persistExtendedHistory:!1};return t.model?.trim()&&(e.model=t.model.trim()),t.reasoningEffort?.trim()&&(e.reasoningEffort=t.reasoningEffort.trim()),t.fastMode===!0&&(e.service_tier="fast"),t.cwd?.trim()&&(e.cwd=t.cwd.trim()),t.approvalPolicy?.trim()&&(e.approvalPolicy=t.approvalPolicy.trim()),t.sandbox?.trim()&&(e.sandbox=t.sandbox.trim()),[e]}function pc(t){return[{type:"text",text:t}]}function mc(t,e,n,r){let o=e?.trim(),i=n?.trim(),s=r?.trim();if(t!=="plan")return o||i||s?{mode:"default",settings:{...o?{model:o}:{},...i?{reasoningEffort:i}:{},developerInstructions:s??null}}:void 0;if(!(!o&&!i&&!s))return{mode:"plan",settings:{...o?{model:o}:{},...i?{reasoningEffort:i}:{},developerInstructions:s??null}}}function Zs(t){let e={threadId:t.threadId,input:pc(t.prompt)};t.model?.trim()&&(e.model=t.model.trim()),t.fastMode===!0&&(e.service_tier="fast"),t.approvalPolicy?.trim()&&(e.approvalPolicy=t.approvalPolicy.trim()),t.sandbox?.trim()&&(e.sandbox=t.sandbox.trim());let n=mc(t.permissionMode??"default",t.model,t.reasoningEffort,t.systemPrompt);return n?[{...e,collaborationMode:n}]:[e]}function Xs(t){return[{threadId:t.threadId,turnId:t.turnId}]}function fc(t){let e=t.trim().toLowerCase();return e.includes("session")?"acceptForSession":/cancel|abort|stop/.test(e)?"cancel":/deny|decline|reject|block|no/.test(e)?"decline":/approve|allow|accept|yes/.test(e)?"accept":t.trim()}function ea(t,e,n){let r=t.trim().toLowerCase(),o=r.includes("requestapproval"),i=r.includes("requestuserinput"),s=ft(n);if(i&&s.length===0)throw new Error(`Malformed Codex request_user_input payload for ${e}: expected non-empty questions[]`);let l=o?En(n):[],a=s.length>0?0:void 0,d=a!=null?s[a]:void 0,u=d?d.options:[],m=(o&&u.length===0?l:u).map(h=>h.label),p=(d?$e(d,a??0,s.length):Dn(s))??(o?Vn(n,["question","prompt","message","text","summary","reason"]):void 0)??void 0,f=o?m.map(h=>({kind:"approval",label:h,decision:fc(h),responseDecision:h})):m.map(h=>({kind:"option",label:h,value:h}));return{requestId:e,kind:o?"approval":"question",promptText:p,options:m,...s.length>0?{questions:s}:{},...a!=null?{activeQuestionIndex:a}:{},actions:f,allowsFreeText:!0}}function ta(t){let e=t.trim().toLowerCase();return e.includes("requestuserinput")||e.includes("requestapproval")}function Xo(t,e){let n=t==="bypassPermissions"?"never":e?.trim()||"never";return{approvalPolicy:n,sandbox:n==="never"?"danger-full-access":void 0}}var dc,na=H(()=>{Xt();dc=new Set(["thread/resume","turn/start","turn/steer","turn/interrupt"])});function vc(t){let e=t?.trim();return e&&Sc.test(e)?e:void 0}function Pc(t){let e=t?.trim();if(!e||!/^\d+$/.test(e))return ei;let n=Number(e);return Number.isSafeInteger(n)&&n>0?n:ei}function ti(t){return t instanceof Error?t.message:String(t)}function wc(t){if(typeof t=="string")return t;if(!t||typeof t!="object")return String(t);let e=t;return typeof e.message?.content=="string"?e.message.content:typeof e.text=="string"?e.text:String(t)}function oa(t,e,n){let r=t.questions??[],o=r[e];return o?{...t,promptText:$e(o,e,r.length),options:o.options.map(i=>i.label),activeQuestionIndex:e,answers:n}:t}function bc(t){if(t===void 0)return ra;let e=qs(t);return e.length>0?e:ra}var gc,ei,ra,hc,yc,kc,Sc,jn,ia=H(()=>{Ls();Nn();Xt();Kn();na();gc="1.0",ei=12e4,ra=["--listen","stdio://"],hc="OPENCLAW_CODEX_APP_SERVER_COMMAND",yc="OPENCLAW_CODEX_APP_SERVER_ARGS",kc="OPENCLAW_CODEX_APP_SERVER_TIMEOUT_MS",Sc=/^(?:urn:uuid:)?[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}$/;jn=class{constructor(e={}){this.deps=e}deps;name="codex";backendKind="codex-app-server";supportedPermissionModes=["default","plan","bypassPermissions"];capabilities={nativePendingInput:!0,nativePlanArtifacts:!0,worktrees:"native-restore"};launch(e){let n={command:process.env[hc]?.trim()||"codex",args:bc(process.env[yc]),requestTimeoutMs:Pc(process.env[kc])},r=this.deps.createClient?.(n)??new Bn(n.command,n.args,n.requestTimeoutMs),o=new qe,i=vc(e.resumeSessionId);e.resumeSessionId&&!i&&`${e.resumeSessionId}`;let s,l=e.backendRef?.worktreePath,a=e.backendRef?.worktreeId,d=e.permissionMode??"default",u=De(this.name,e.model);if(!kt(this.name,u))throw new Error(`Codex model "${e.model}" is not supported. Use a bare Codex model id such as "gpt-5.5".`);let c,m=0,p="",f=[],h,k=new Map,v=new Set,I=E=>{let T=E?.trim();if(!T)return;let C=e.originalWorkdir?.trim()||e.cwd.trim();e.worktreeStrategy&&e.worktreeStrategy!=="off"&&T!==C&&Us(T)&&(l=T,a=Ks(T))},x=()=>{i&&o.enqueue(gt({kind:"codex-app-server",conversationId:i,...s?{runId:s}:{},...a?{worktreeId:a}:{},...l?{worktreePath:l}:{}}))};r.setNotificationHandler(async(E,T)=>{let C=E.trim().toLowerCase(),B=en(T),j=tn(T);if(B.threadId&&i&&B.threadId!==i)return;if(B.threadId&&(i=B.threadId),B.runId&&(s=B.runId),I(j.cwd),(B.threadId||B.runId||j.cwd)&&x(),C==="serverrequest/resolved"){c&&(o.enqueue(Ue(c.requestId)),c=void 0);return}if(C==="turn/plan/updated"){let V=js(T);p=V.explanation??p,V.steps.length>0&&(f=V.steps);return}if(C==="item/plan/delta"){let V=Gs(T);if(V.itemId&&V.delta){let oe=k.get(V.itemId)??"";k.set(V.itemId,`${oe}${V.delta}`)}return}if(C==="item/completed"){let V=Hs(T);if(V.text?.trim()){let oe={explanation:p||void 0,steps:f,markdown:V.text.trim()};o.enqueue(Wn(oe,!0));return}}let W=Vs(C,T);if(W.mode==="delta"&&W.text){W.itemId&&v.add(W.itemId),o.enqueue(Ye(W.text));return}W.mode==="snapshot"&&W.text&&(!W.itemId||!v.has(W.itemId))&&o.enqueue(Ye(W.text)),(C==="turn/completed"||C==="turn/failed"||C==="turn/cancelled")&&h&&(h.method=E,h.params=T,h.resolve())}),r.setRequestHandler(async(E,T)=>{if(!ta(E))return{};let C=en(T),B=tn(T);if(C.threadId&&i&&C.threadId!==i)return{};C.threadId&&(i=C.threadId),C.runId&&(s=C.runId),I(B.cwd),(C.threadId||C.runId||B.cwd)&&x();let j=C.requestId??`${i??"codex"}-${Date.now().toString(36)}`,W;try{W=ea(E,j,T)}catch(Vt){let Gt=ti(Vt);return`${Gt}`,{error:Gt}}let V=E.trim().toLowerCase(),oe=W.options,Ie=W.actions??[],lt=await new Promise(Vt=>{c={requestId:j,methodLower:V,state:W,options:oe,actions:Ie,answers:{...W.answers??{}},resolveResponse:Vt},o.enqueue(Te(W))});return c=void 0,o.enqueue(Ue(j)),lt});let b=async()=>{await r.connect(),await r.request("initialize",{protocolVersion:gc,clientInfo:{name:"openclaw-code-agent",version:"3.1.0"},capabilities:{experimentalApi:!0}},n.requestTimeoutMs),await r.notify("initialized",{})},A=async()=>{let E=Xo(d,e.codexApprovalPolicy);if(i){let B=await nn({client:r,methods:["thread/resume"],payloads:Ys({threadId:i,model:u,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,approvalPolicy:E.approvalPolicy,sandbox:E.sandbox}),timeoutMs:n.requestTimeoutMs}),j=tn(B);i=j.threadId??i,I(j.cwd),x();return}let T=await nn({client:r,methods:["thread/start","thread/new"],payloads:Js({cwd:e.cwd,model:u,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,approvalPolicy:E.approvalPolicy,sandbox:E.sandbox}),timeoutMs:n.requestTimeoutMs}),C=tn(T);if(i=C.threadId,!i)throw new Error("Codex App Server did not return a thread id.");I(C.cwd),x()},y=async E=>{await A(),o.enqueue(ht()),m+=1,p="",f=[],k.clear(),v.clear();let T="",C,B,j=new Promise(W=>{B=W});h={resolve:B};try{let W=Xo(d,e.codexApprovalPolicy),V=await nn({client:r,methods:["turn/start"],payloads:Zs({threadId:i,prompt:E,model:u,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,systemPrompt:e.systemPrompt,permissionMode:d,approvalPolicy:W.approvalPolicy,sandbox:W.sandbox}),timeoutMs:n.requestTimeoutMs}),oe=en(V);oe.runId&&(s=oe.runId,x()),await j,T=h?.method??"turn/failed",C=h?.params;let Ie=zs(T,C);o.enqueue(Ee({success:Ie==="completed",outcome:Ie,duration_ms:0,total_cost_usd:0,num_turns:m,result:Qs(T,C),session_id:i}))}catch(W){o.enqueue(Ee({success:!1,duration_ms:0,total_cost_usd:0,num_turns:m,result:ti(W),session_id:i??""}))}finally{h=void 0}},w=async E=>{let T=c;if(!T)return!1;let C=E.trim();if(T.methodLower.includes("requestapproval"))return T.resolveResponse({decision:C||"decline"}),!0;let B=T.state.questions??[];if(B.length>0){if(!C)return!1;let j=T.state.activeQuestionIndex??0,W=B[j];if(!W)return!1;T.answers={...T.answers,[W.id]:{answers:[C]}};let V=j+1;if(V<B.length)return T.state=oa(T.state,V,T.answers),T.options=T.state.options,o.enqueue(Te(T.state)),!0;T.resolveResponse({answers:T.answers})}else T.resolveResponse({text:C});return!0},F=async(E,T={})=>{let C=c;if(!C||T.requestId&&T.requestId!==C.state.requestId)return!1;let B=C.actions[E];if(B?.kind==="approval")return C.resolveResponse({decision:B.responseDecision,...B.proposedExecpolicyAmendment?{proposedExecpolicyAmendment:B.proposedExecpolicyAmendment}:{}}),!0;let j=C.state.questions??[],W=C.state.activeQuestionIndex??0,V=j.length>0?j[W]:void 0;if(T.questionId&&T.questionId!==V?.id)return!1;let oe=V?.options[E];if(V&&oe){C.answers={...C.answers,[V.id]:{answers:[oe.value??oe.label]}};let lt=W+1;return lt<j.length?(C.state=oa(C.state,lt,C.answers),C.options=C.state.options,o.enqueue(Te(C.state)),!0):(C.resolveResponse({answers:C.answers}),!0)}let Ie=C.options[E];return Ie?(C.methodLower.includes("requestapproval")?C.resolveResponse({decision:Ie}):C.resolveResponse({option:Ie,index:E}),!0):!1},ce=typeof e.prompt=="string"?(async function*(){yield{type:"user",text:e.prompt,session_id:e.resumeSessionId??""}})():e.prompt;return(async()=>{try{await b();for await(let E of ce){let T=wc(E).trim();!T||await w(T)||await y(T)}}catch(E){o.enqueue(Ee({success:!1,duration_ms:0,total_cost_usd:0,num_turns:m,result:ti(E),session_id:i??e.resumeSessionId??""}))}finally{await r.close().catch(()=>{}),o.close()}})(),{messages:o.messages(),async setPermissionMode(E){d=E,o.enqueue(yt(E))},async submitPendingInputOption(E,T){return F(E,T)},async submitPendingInputText(E){return w(E)},async interrupt(){!i||!s||await nn({client:r,methods:["turn/interrupt"],payloads:Xs({threadId:i,turnId:s}),timeoutMs:n.requestTimeoutMs}).catch(()=>{})}}}buildUserMessage(e,n){return{type:"user",text:e,session_id:n}}}});import{spawn as Rc}from"node:child_process";import{constants as Ac,accessSync as Ic}from"node:fs";import{createServer as xc}from"node:net";import{delimiter as Tc,dirname as ni,join as la,sep as Cc}from"node:path";function vt(t){return t instanceof Error?t.message:String(t)}function Dc(t){try{return Ic(t,Ac.X_OK),!0}catch{return!1}}function Oc(t){return t.includes("/")||Cc==="\\"&&t.includes("\\")}function Wc(t){let e=(t??"").split(Tc).map(r=>r.trim()).filter(Boolean),n=[...e];for(let r of e)r.replaceAll("\\","/").endsWith("/opt/node/bin")&&n.push(la(ni(ni(ni(r))),"bin"));return n.push("/home/linuxbrew/.linuxbrew/bin","/opt/homebrew/bin","/usr/local/bin","/usr/bin","/bin"),[...new Set(n)]}function Nc(t,e=process.env.PATH){if(Oc(t))return t;for(let n of Wc(e)){let r=la(n,t);if(Dc(r))return r}return t}function ne(t){return!!t&&typeof t=="object"&&!Array.isArray(t)}function Lc(t){if(typeof t=="string")return t;if(!ne(t))return String(t);if(typeof t.text=="string")return t.text;let e=ne(t.message)?t.message:void 0;return typeof e?.content=="string"?e.content:String(t)}function da(t){let e=t?.trim();if(!e)return;let n=e.indexOf("/");if(!(n<=0||n===e.length-1))return{providerID:e.slice(0,n),modelID:e.slice(n+1)}}function Fc(t){let e=da(t);return e?{id:e.modelID,providerID:e.providerID}:void 0}function sa(t){let e=t??"default",n=e==="plan"?"deny":e==="bypassPermissions"?"allow":"ask";return Ec.map(r=>({permission:r,pattern:"*",action:n}))}function ri(){let t=process.env.OPENCODE_SERVER_PASSWORD;if(!t)return{};let e=process.env.OPENCODE_SERVER_USERNAME||"opencode";return{Authorization:`Basic ${Buffer.from(`${e}:${t}`).toString("base64")}`}}async function Bc(){return new Promise((t,e)=>{let n=xc();n.once("error",e),n.listen(0,"127.0.0.1",()=>{let r=n.address();n.close(()=>{r&&typeof r=="object"?t(r.port):e(new Error("Could not allocate local OpenCode server port."))})})})}async function ua(t){await new Promise(e=>setTimeout(e,t))}async function Hn(t,e){if(e.signal?.aborted)throw new Error(e.abortMessage??"Operation was aborted.");return await new Promise((n,r)=>{let o=!1,i=()=>{clearTimeout(a),e.signal?.removeEventListener("abort",l)},s=d=>{o||(o=!0,i(),d())},l=()=>{s(()=>r(new Error(e.abortMessage??"Operation was aborted.")))},a=setTimeout(()=>{s(()=>{e.onTimeout?.(),r(new Error(e.timeoutMessage))})},e.timeoutMs);e.signal?.addEventListener("abort",l,{once:!0}),t.then(d=>s(()=>n(d)),d=>s(()=>r(d)))})}async function St(t){t.exitCode===null&&await new Promise(e=>{let n,r=setTimeout(()=>{t.exitCode===null&&t.kill("SIGKILL"),n=setTimeout(e,1e3)},2e3);t.once("exit",()=>{clearTimeout(r),n&&clearTimeout(n),e()}),t.kill("SIGTERM")})}function qc(t){return t.headers.get("content-type")?.toLowerCase()??""}function ii(t){return t.replace(/\s+/g," ").trim().slice(0,300)}function Uc(t,e){return t.includes("text/html")||/^\s*<!doctype html\b/i.test(e)||/^\s*<html[\s>]/i.test(e)}function Kc(t,e,n,r){let o=n?`content-type ${n}`:"missing content-type",i=ii(r),s=Uc(n,r)?" (looks like the OpenCode web UI HTML app shell)":"";return`OpenCode ${t} ${e} expected JSON API response but received ${o}${s}${i?`: ${i}`:""}`}function Vc(t,e,n){let r=da(e);return{...r?{model:{providerID:r.providerID,modelID:r.modelID}}:{},...n?.trim()?{system:n.trim()}:{},parts:[{type:"text",text:t}]}}function Gc(t,e){if(!ne(t))return!1;if(!(e in t))return!0;let n=t[e];return ne(n)&&n.type==="idle"}function jc(t){return t.type==="session.idle"?!0:t.type!=="session.status"?!1:(t.properties.status??t.properties.type)==="idle"}function Hc(t){return new Promise((e,n)=>{aa=aa.then(()=>t().then(e,n)).catch(()=>{})})}async function zc(t){return Hc(async()=>{let e=await Bc(),n=process.env[Mc]?.trim()||"opencode",r=Nc(n),o=["serve","--hostname","127.0.0.1","--port",String(e),"--print-logs"],i=t.fetch??fetch,s=Math.min(t.requestTimeoutMs??li,1e4),l=t.startupTimeoutMs??_c,a=Rc(r,o,{cwd:t.cwd,stdio:["ignore","pipe","pipe"]}),d=`http://127.0.0.1:${e}`,u="",c="",m,p=(v,I)=>{let x=v+String(I);return x.length>8e3?x.slice(-8e3):x};a.stdout.on("data",v=>{u=p(u,v)}),a.stderr.on("data",v=>{c=p(c,v)}),a.once("error",v=>{m=v});let f=()=>` Command: ${n===r?r:`${r} (resolved from ${n})`} ${o.join(" ")}. Cwd: ${t.cwd}. Port: ${e}. PATH: ${process.env.PATH??""}.`,h=()=>{let v=[u.trim(),c.trim()].filter(Boolean).join(`
8
- `).trim();return`${f()}${v?` Output:
9
- ${v}`:""}`},k=()=>{St(a)};if(t.signal?.aborted)throw await St(a),new Error(`OpenCode server startup aborted before readiness.${h()}`);t.signal?.addEventListener("abort",k,{once:!0});try{let v=Date.now();for(;Date.now()-v<l;){if(t.signal?.aborted)throw await St(a),new Error(`OpenCode server startup aborted before readiness.${h()}`);if(m)throw new Error(`OpenCode server failed to start: ${m.message}${h()}`);if(a.exitCode!==null)throw new Error(`OpenCode server exited before readiness.${h()}`);try{if(await Jc({baseUrl:d,fetchImpl:i,requestTimeoutMs:s,startupSignal:t.signal,timeoutMessage:`OpenCode GET /api/health timed out after ${s}ms during server readiness.${h()}`,abortMessage:`OpenCode server startup aborted before readiness.${h()}`}))return{baseUrl:d,close:async()=>{await St(a)}}}catch{if(t.signal?.aborted)throw await St(a),new Error(`OpenCode server startup aborted before readiness.${h()}`)}await ua(100)}throw await St(a),new Error(`Timed out waiting for OpenCode server readiness.${h()}`)}finally{t.signal?.removeEventListener("abort",k)}})}async function Qc(t){for(let e=1;;e+=1)try{return await zc(t)}catch(n){if(e>=3||!/EADDRINUSE|address already in use|bind: address already in use/i.test(vt(n)))throw n}}async function Jc(t){let e=new AbortController,n=()=>e.abort();t.startupSignal?.aborted?e.abort():t.startupSignal?.addEventListener("abort",n,{once:!0});try{return(await Hn(t.fetchImpl(`${t.baseUrl}/api/health`,{headers:ri(),signal:e.signal}),{timeoutMs:t.requestTimeoutMs,timeoutMessage:t.timeoutMessage,signal:t.startupSignal,abortMessage:t.abortMessage,onTimeout:()=>e.abort()})).ok}finally{t.startupSignal?.removeEventListener("abort",n)}}function Yc(t){let e=ne(t)&&ne(t.payload)?t.payload:t;return ne(e)?e.type==="sync"?{type:typeof e.name=="string"?e.name.replace(/\.\d+$/,""):void 0,properties:ne(e.data)?e.data:{}}:{type:typeof e.type=="string"?e.type:void 0,properties:ne(e.properties)?e.properties:e}:{properties:{}}}function Zc(t){return typeof t.sessionID=="string"?t.sessionID:void 0}function Xc(t){let e=typeof t.id=="string"?t.id:"opencode-permission",n=typeof t.permission=="string"?t.permission:"permission",r=Array.isArray(t.patterns)?t.patterns.filter(s=>typeof s=="string"):[],o=r.length>0?`OpenCode requests ${n} permission for ${r.join(", ")}.`:`OpenCode requests ${n} permission.`,i=[{kind:"approval",label:"Allow once",decision:"accept",responseDecision:"once"},{kind:"approval",label:"Always allow",decision:"acceptForSession",responseDecision:"always"},{kind:"approval",label:"Reject",decision:"decline",responseDecision:"reject"}];return{requestId:e,kind:"approval",promptText:o,options:i.map(s=>s.label),actions:i,responseMode:"structured"}}function ep(t){let e=typeof t.id=="string"?t.id:"opencode-question",n=typeof t.question=="string"?t.question:typeof t.prompt=="string"?t.prompt:"OpenCode is asking for input.",r=ft(t),o=En(t),i=r.length>0?r:[{id:e,question:n,options:o,allowsFreeText:!0}],s=i.length>0?0:void 0,l=s!=null?i[s]:void 0,a=l?.options.map(d=>d.label)??o.map(d=>d.label);return{requestId:e,kind:"question",promptText:l?$e(l,s??0,i.length):n,options:a,...i.length>0?{questions:i}:{},...s!=null?{activeQuestionIndex:s}:{},allowsFreeText:!0}}function tp(t,e,n){let r=t.questions??[],o=r[e],i=o?.options.map(s=>s.label)??[];return{...t,promptText:o?$e(o,e,r.length):t.promptText,options:i,activeQuestionIndex:e,answers:n}}function np(t,e){return t.length===1?e[t[0].id]?.answers.join(", ")??"":t.map((n,r)=>{let o=e[n.id]?.answers.join(", ")??"";return`Q${r+1}: ${n.question}
1
+ var Fu=Object.defineProperty;var H=(t,e,n)=>()=>{if(n)throw n[0];try{return t&&(e=t(t=0)),e}catch(r){throw n=[r],r}};var qu=(t,e)=>{for(var n in e)Fu(t,n,{get:e[n],enumerable:!0})};function zt(t,e){return e?{...e,...t}:t}function Ku(t){return{...t,[jo]:!0}}function Uu(t){return{const:t,type:typeof t}}var jo,h,ne=H(()=>{jo=Symbol("optionalSchema");h={Object(t,e){let n=Object.entries(t).filter(([,o])=>!o[jo]).map(([o])=>o),r=Object.fromEntries(Object.entries(t).map(([o,i])=>{let{[jo]:s,...a}=i;return[o,a]}));return{...e,type:"object",...n.length>0?{required:n}:{},properties:r}},String(t){return zt({type:"string"},t)},Number(t){return zt({type:"number"},t)},Boolean(t){return zt({type:"boolean"},t)},Array(t,e){return zt({type:"array",items:t},e)},Literal:Uu,Union(t,e){return zt({anyOf:t},e)},Optional:Ku}});function Ho(t){v=t}function zo(t){z=t}var v,z,B=H(()=>{v=null,z=null});function Ds(t){let e=t.chatId.trim(),n=t.topicId.trim();return!/^-?\d+$/.test(e)||!/^\d+$/.test(n)?null:`${e}:topic:${n}`}function zu(t){let e=t.conversationId.trim(),n=e.match(/^(-?\d+):topic:(\d+)$/i);if(n?.[1]&&n[2]){let i=Ds({chatId:n[1],topicId:n[2]});return i?{chatId:n[1],topicId:n[2],canonicalConversationId:i}:null}if(!/^\d+$/.test(e))return null;let r=t.parentConversationId?.trim();if(!r||!/^-?\d+$/.test(r))return null;let o=Ds({chatId:r,topicId:e});return o?{chatId:r,topicId:e,canonicalConversationId:o}:null}function Qu(t){if(!t)return;let e=t.match(/^agent:[^:]+:discord:(direct|dm|channel|group):/i);if(!e?.[1])return;let n=e[1].toLowerCase();return n==="direct"||n==="dm"?"user":"channel"}function Ju(t,e){if(!/^\d+$/.test(t))return t;let n=Qu(e);return n?`${n}:${t}`:`channel:${t}`}function Yu(t){if(!(!t?.provider||!t.target)&&!(t.provider==="system"||t.target==="system"))return t.accountId?`${t.provider}|${t.accountId}|${t.target}`:`${t.provider}|${t.target}`}function Zu(t){let e=t.toLowerCase(),n=[":thread:",":topic:"];for(let r of n){let o=e.lastIndexOf(r);if(o===-1)continue;let i=t.slice(0,o).trim(),s=t.slice(o+r.length).trim()||void 0;return{id:i||t,threadId:s}}return{id:t}}function Xu(t){let e=t?.trim();if(!e)return;let n=e.split(":").filter(Boolean);if(n[0]?.trim().toLowerCase()==="agent")for(let r=2;r<=n.length-3;r+=1){let o=n[r]?.trim().toLowerCase();if(!o||!Hu.has(o))continue;let i=n[r+1]?.trim().toLowerCase(),s=n.slice(r+2).join(":").trim();if(!(!i||!s))return{provider:o,kind:i,rawId:s}}}function ec(t,e=zu){try{return e({conversationId:t})}catch{return null}}function Qo(t){return{provider:"system",target:"system",sessionKey:t?.trim()||void 0}}function Jo(t,e){return{...t,threadId:e??t.threadId}}function nc(t,e,n){return t==="telegram"&&n?.provider==="telegram"&&!!n.target&&e!==n.target}function rc(t){let e=t?.trim();if(!e)return;let n=Xu(e);if(!n)return;let{provider:r,kind:o,rawId:i}=n,s=Zu(i),a=null;if(r==="telegram")try{a=tc.safeParseTelegramTopicConversation(i)}catch{a=null}let l=a?.chatId??s.id,d=a?.topicId??s.threadId,u=r==="discord"?o==="direct"||o==="dm"?`user:${l}`:`channel:${l}`:l;return{provider:r,target:u,threadId:d,sessionKey:e}}function Yo(t){let e=t?.match(/:topic:(\d+)$/i);return e?parseInt(e[1],10):void 0}function Os(t){return!!(t?.provider&&t.target&&t.provider!=="system"&&t.target!=="system")}function Qt(t,e,n){let r=rc(n),o=e!=null?String(e):void 0,i=t?.trim();if(!i||i.toLowerCase()==="unknown")return r?Jo(r,o):Qo(n);let s=i.split("|").map(m=>m.trim());if(s.length<2)return r?Jo(r,o):Qo(n);let[a,l,d]=s,u=s.length>=3?d:l,c=s.length>=3?l:void 0,p=a?.toLowerCase();if(!p||!u)return r?Jo(r,o):Qo(n);let g=p==="discord"?Ju(u,n):u;return nc(p,g,r)?{provider:p,accountId:c,target:r.target,threadId:o??r.threadId,sessionKey:n?.trim()||void 0}:{provider:p,accountId:c,target:g,threadId:o??(r?.provider===p?r.threadId:void 0),sessionKey:n?.trim()||void 0}}function Ye(t){return Qt(Yu(t.route)??t.originChannel,t.route?.threadId??t.originThreadId,t.route?.sessionKey??t.originSessionKey)??t.route}function $e(t){let e=Ye(t);return Os(e)?e:void 0}function oc(t){return Object.fromEntries(Object.entries(t).filter(e=>!!e[1]))}function Jt(t){let e=Ye(t);if(!Os(e))return"";let n=oc({provider:e?.provider,accountId:e?.accountId,target:e?.target,threadId:e?.threadId??(t.originThreadId!=null?String(t.originThreadId):void 0),sessionKey:e?.sessionKey??t.originSessionKey});return Object.keys(n).length===0?"":["Session origin route (authoritative for human follow-ups):",`originRoute: ${JSON.stringify(n)}`,"Routing rule: Send any human follow-up for this wake to originRoute. If originRoute differs from the current chat, do not use a plain final assistant reply; use a routed send path that preserves provider/target/threadId."].join(`
2
+ `)}var Hu,tc,Re=H(()=>{Hu=new Set(["telegram","discord","slack","system","mattermost","feishu","line","whatsapp","signal","matrix","googlechat","bluebubbles","imessage","msteams"]);tc={safeParseTelegramTopicConversation:ec}});import{readFileSync as ic}from"fs";import{homedir as sc}from"os";import{join as ac}from"path";function Ns(){if(Yt!==void 0)return Yt;try{let t=ic(ac(sc(),".claude.json"),"utf-8");Yt=JSON.parse(t).mcpServers??{}}catch{Yt={}}return Yt}function Ls(t){let e=t.defaultHarness??Ws,n={};for(let[r,o]of Object.entries(Zt)){let i={...o};o.allowedModels&&(i.allowedModels=[...o.allowedModels]),n[r]=i}for(let[r,o]of Object.entries(t.harnesses??{})){let i=n[r]??{},s={...i,defaultModel:o.defaultModel??i.defaultModel,reasoningEffort:o.reasoningEffort??i.reasoningEffort,fastMode:o.fastMode??i.fastMode};o.allowedModels!==void 0?s.allowedModels=o.allowedModels?[...o.allowedModels]:o.allowedModels:o.defaultModel!==void 0&&(s.allowedModels=void 0),n[r]=s}if(t.defaultModel!==void 0){let r=n[e]??{};n[e]={...r,defaultModel:t.harnesses?.[e]?.defaultModel??t.defaultModel,allowedModels:t.harnesses?.[e]?.allowedModels!==void 0?r.allowedModels:t.allowedModels},`${e}`}if(t.model!==void 0){let r=n.codex??{};n.codex={...r,defaultModel:t.harnesses?.codex?.defaultModel??t.model,allowedModels:t.harnesses?.codex?.allowedModels!==void 0?r.allowedModels:t.allowedModels}}if(t.reasoningEffort!==void 0){let r=n.codex??{};n.codex={...r,reasoningEffort:t.harnesses?.codex?.reasoningEffort??t.reasoningEffort}}if(t.allowedModels!==void 0)for(let[r,o]of Object.entries(n))t.harnesses?.[r]?.allowedModels===void 0&&(n[r]={...o,allowedModels:void 0});D={maxSessions:t.maxSessions??20,defaultWorkdir:t.defaultWorkdir,idleTimeoutMinutes:t.idleTimeoutMinutes??15,sessionGcAgeMinutes:t.sessionGcAgeMinutes??1440,maxPersistedSessions:t.maxPersistedSessions??1e4,fallbackChannel:t.fallbackChannel,agentChannels:t.agentChannels,maxAutoResponds:t.maxAutoResponds??10,permissionMode:t.permissionMode??"plan",planApproval:t.planApproval??"delegate",defaultHarness:e,harnesses:n,allowedModels:t.allowedModels,defaultWorktreeStrategy:t.defaultWorktreeStrategy??"delegate",worktreeDir:t.worktreeDir}}function le(){return D.defaultHarness??Ws}function ei(t){let e=Zt[t],n=D.harnesses[t];return{...e,...n,allowedModels:n?.allowedModels??e?.allowedModels}}function pt(t){return ei(t).defaultModel}function En(t){return D.harnesses[t]?.allowedModels??D.allowedModels}function Ke(t){return ei(t).reasoningEffort}function mt(t){return t==="codex"?ei(t).fastMode:void 0}function Se(t){return t==null?void 0:String(t).trim()||void 0}function ti(t){return{channel:Se(t?.deliveryContext?.channel),to:Se(t?.deliveryContext?.to),accountId:Se(t?.deliveryContext?.accountId),threadId:Se(t?.deliveryContext?.threadId)}}function Bs(t,e,n){if(!(!t||!e))return n?`${t}|${n}|${e}`:`${t}|${e}`}function Zo(t){return Se(t?.requesterSenderId??t?.senderId)}function Xo(t){return(Se(t.deliveryContext?.channel)??t.messageChannel??t.channel)?.toLowerCase()!=="telegram"?!1:!!(Yo(t.sessionKey)||Se(t.messageThreadId)||Se(t.deliveryContext?.threadId))}function Dn(t){let e=ti(t),n=Bs(e.channel,e.to,e.accountId);if(n)return n;if(t.messageChannel){let r=t.messageChannel.split("|");if(r.length>=3)return t.messageChannel;if(t.agentAccountId&&r.length>=2)return`${r[0]}|${t.agentAccountId}|${r.slice(1).join("|")}`;let o=Se(t.chatId);if(r.length===1&&o)return`${r[0]}|${o}`;let i=Zo(t);if(r.length===1&&i&&!Xo(t))return`${r[0]}|${i}`}if(t.workspaceDir){let r=Ze(t.workspaceDir);if(r)return r}if(t.messageChannel&&t.messageChannel.includes("|"))return t.messageChannel}function Xt(t,e){if(e&&String(e).includes("|"))return String(e);let n=ti(t),r=Bs(n.channel,n.to,n.accountId);if(r)return r;if(t?.channelId&&String(t.channelId).includes("|"))return String(t.channelId);if(t?.messageChannel){let a=String(t.messageChannel);if(a.includes("|"))return a;let l=Se(t.chatId);if(l)return`${a}|${l}`;let d=Zo(t);if(d&&!Xo(t))return`${a}|${d}`}let o=Se(t?.channel),i=Se(t?.chatId);if(o&&i)return`${o}|${i}`;let s=Zo(t);return o&&s&&!Xo(t)?`${o}|${s}`:t?.id&&/^-?\d+$/.test(String(t.id))?`telegram|${t.id}`:D.fallbackChannel??"unknown"}function ni(t){return ti(t).threadId??t?.messageThreadId??void 0}function ft(t,e,n){return Qt(Xt(t,e),ni(t),n??t?.sessionKey)}function Ze(t){let e=D.agentChannels;if(!e)return;let n=i=>i.replace(/\/+$/,""),r=n(t),o=Object.entries(e).sort((i,s)=>s[0].length-i[0].length);for(let[i,s]of o)if(r===n(i)||r.startsWith(n(i)+"/"))return s}function Fs(t){return Yo(t)}var Yt,Ws,Zt,D,se=H(()=>{Re();Ws="claude-code",Zt={"claude-code":{defaultModel:"anthropic/claude-sonnet-4-7",allowedModels:["sonnet","opus"]},codex:{defaultModel:"gpt-5.5",allowedModels:["gpt-5.5","gpt-5.5-pro"],reasoningEffort:"medium"},opencode:{}};D={maxSessions:20,idleTimeoutMinutes:15,sessionGcAgeMinutes:1440,maxPersistedSessions:1e4,maxAutoResponds:10,permissionMode:"plan",planApproval:"delegate",defaultWorktreeStrategy:"delegate",harnesses:{"claude-code":{...Zt["claude-code"]},codex:{...Zt.codex},opencode:{...Zt.opencode}}}});function K(t){return t&&typeof t=="object"&&!Array.isArray(t)?t:null}function G(t,e,n){for(let r of e){let o=t?.[r];if(typeof o!="string")continue;let i=n?.trim===!1?o:o.trim();if(i)return i}}function qs(t,e){return e&&typeof e.recommended=="boolean"?e.recommended:e&&typeof e.isRecommended=="boolean"?e.isRecommended:/\b(?:not\s+(?:a\s+)?|non[-\s]?|un)recommended\b/i.test(t)?!1:/\brecommended\b/i.test(t)}function Ks(t){if(typeof t=="string"){let s=t.trim();return s?{label:s,value:s,recommended:qs(s)}:void 0}let e=K(t);if(!e)return;let n=G(e,["label","title","text","value","name","id"])?.trim();if(!n)return;let r=G(e,["description","preview","detail","details"]),o=G(e,["value","id","name"]),i=e.isOther===!0||e.is_other===!0||e.other===!0;return{label:n,...r?{description:r}:{},...o?{value:o}:{},...i?{isOther:!0}:{},recommended:qs(n,e)}}function On(t){let e=K(t);if(!e)return[];let n=e.options??e.choices??e.availableDecisions??e.decisions;return Array.isArray(n)?n.map(Ks).filter(r=>!!r):[]}function ht(t){let e=K(t);return(Array.isArray(e?.questions)?e.questions:[]).map((r,o)=>lc(r,o)).filter(r=>!!r)}function lc(t,e=0){let n=K(t);if(!n)return;let r=G(n,["question","prompt","message","text","summary"])?.trim();if(!r)return;let o=G(n,["id","questionId","question_id","name"]),i=G(n,["header","title","label"]),a=(Array.isArray(n.options)?n.options:Array.isArray(n.choices)?n.choices:[]).map(Ks).filter(u=>!!u),l=n.multiSelect===!0||n.multi_select===!0,d=n.isOther===!0||n.is_other===!0||n.allowFreeText===!0||n.allowsFreeText===!0||l||a.some(u=>u.isOther);return{id:o??`question_${e+1}`,...i?{header:i}:{},question:r,options:a,...l?{multiSelect:!0}:{},...d?{allowsFreeText:!0}:{},...n.isSecret===!0||n.is_secret===!0?{isSecret:!0}:{}}}function Us(t,e,n){let r=[n>1?`Question ${e+1}`:void 0,t.header].filter(Boolean).join(" - "),o=[...r?[r]:[],t.question];return t.options.length>0&&o.push("Options:",...t.options.map((i,s)=>{let a=i.recommended&&!/\brecommended\b/i.test(i.label)?" (recommended)":"",l=i.description?` - ${i.description}`:"",d=i.isOther?" (free text)":"";return` ${s+1}. ${i.label}${a}${d}${l}`})),t.allowsFreeText&&!t.options.some(i=>i.isOther)&&o.push(t.multiSelect?"Reply with one or more option labels.":"Free-form answer is allowed."),o}function Wn(t){if(t.length===0)return;let e=t.flatMap((n,r)=>[...r>0?[""]:[],...Us(n,r,t.length)]);return t.length>1&&e.push("","Reply with answers by question, for example: Q1: ..., Q2: ..."),e.join(`
3
+ `)}function Ee(t,e,n){return Us(t,e,n).join(`
4
+ `)}var en=H(()=>{});function yt(t){return{type:"backend_ref",ref:t}}function kt(t){return{type:"run_started",...t?{runId:t}:{}}}function Xe(t){return{type:"text_delta",text:t}}function Nn(t,e){return{type:"tool_call",name:t,input:e}}function Ce(t){return{type:"pending_input",state:t}}function Ve(t){return t?{type:"pending_input_resolved",requestId:t}:{type:"pending_input_resolved"}}function Ln(t,e){return{type:"plan_artifact",artifact:t,finalized:e}}function St(t){return t?{type:"settings_changed",permissionMode:t}:{type:"settings_changed"}}function De(t){return{type:"run_completed",data:t}}var Ue,Bn=H(()=>{Ue=class{queue=[];resolvePending=null;done=!1;enqueue(e){this.queue.push(e),this.flush()}close(){this.done=!0,this.flush()}flush(){this.resolvePending&&(this.resolvePending(),this.resolvePending=null)}messages(){let e=this;return(async function*(){for(;;){for(;e.queue.length>0;)yield e.queue.shift();if(e.done)return;await new Promise(n=>{e.resolvePending=n})}})()}}});import*as qn from"@anthropic-ai/claude-agent-sdk";function dc(t){if(typeof t.result=="string"&&t.result.length>0)return t.result;if(Array.isArray(t.errors)){let e=t.errors.filter(n=>typeof n=="string"&&n.length>0);if(e.length>0)return e.join(`
5
+ `)}}function uc(t,e,n){let r=ht(n),o=r.length>0?0:void 0,i=o!=null?r[o]:void 0,s=i?.options.map(l=>l.label)??[],a=i?Ee(i,o,r.length):Wn(r);return{requestId:`${t||"claude"}-ask-${e}`,kind:"question",promptText:a,options:s,...r.length>0?{questions:r}:{},...o!=null?{activeQuestionIndex:o}:{},allowsFreeText:i?.allowsFreeText===!0||s.length===0}}var Fn,Vs=H(()=>{en();Bn();Fn=class{constructor(e={}){this.deps=e}deps;name="claude-code";backendKind="claude-code";supportedPermissionModes=["default","plan","bypassPermissions"];capabilities={nativePendingInput:!1,nativePlanArtifacts:!1,worktrees:"plugin-managed"};launch(e){let n=new Ue,r=!1,o="",i=!1,s=0,a=e.resumeSessionId??"",l=e.canUseTool,d={cwd:e.cwd,model:e.model,...e.reasoningEffort?{effort:e.reasoningEffort}:{},permissionMode:e.permissionMode,allowDangerouslySkipPermissions:!0,allowedTools:e.allowedTools,systemPrompt:e.systemPrompt,includePartialMessages:!0,abortController:e.abortController,mcpServers:e.mcpServers,...l?{canUseTool:async(m,f)=>{if(m!=="AskUserQuestion")return{behavior:"allow"};let y=uc(a,++s,f);n.enqueue(Ce(y));try{let S=await l(m,f);return n.enqueue(Ve(y.requestId)),S}catch(S){throw n.enqueue(Ve(y.requestId)),S}}}:{}};e.resumeSessionId&&(d.resume=e.resumeSessionId,d.forkSession=e.forkSession??!1);let u=e.prompt,c=this.deps.query??qn.query,p=this.deps.startup??qn.startup,g=(async()=>{if(typeof p!="function")return c({prompt:u,options:d});let m=await p({options:d});try{return m.query(u)}catch(f){throw await m.close?.(),f}})();return(async()=>{try{let m=await g;for await(let f of m){let y=f;if(y.type==="system"&&y.subtype==="init"){a=y.session_id??a,n.enqueue(yt({kind:"claude-code",conversationId:a}));continue}if(y.type==="system"&&y.subtype==="status"&&y.permissionMode){n.enqueue(St(y.permissionMode));continue}if(y.type==="assistant"){r||(r=!0,n.enqueue(kt()));for(let S of y.message?.content??[]){if(S.type==="text"){o+=o?`
6
+ ${S.text}`:S.text,n.enqueue(Xe(S.text));continue}S.type==="tool_use"&&((S.name==="ExitPlanMode"||S.name==="set_permission_mode")&&(i=!0),S.name!=="AskUserQuestion"&&n.enqueue(Nn(S.name,S.input)))}continue}if(y.type==="result"){let S=o.trim();if(S&&(e.permissionMode==="plan"||i)){let R={explanation:void 0,steps:[],markdown:S};n.enqueue(Ln(R,!0))}n.enqueue(De({success:y.subtype==="success",duration_ms:y.duration_ms??0,total_cost_usd:y.total_cost_usd??0,num_turns:y.num_turns??0,result:dc(y),session_id:y.session_id??a})),o="",i=!1,r=!1}}}finally{n.close()}})().catch(m=>{n.enqueue(De({success:!1,duration_ms:0,total_cost_usd:0,num_turns:0,result:m instanceof Error?m.message:String(m),session_id:a})),n.close()}),{messages:n.messages(),async setPermissionMode(m){let f=await g;typeof f.setPermissionMode=="function"&&await f.setPermissionMode(m)},async streamInput(m){let f=await g;typeof f.streamInput=="function"&&await f.streamInput(m)},async interrupt(){let m=await g;typeof m.interrupt=="function"&&await m.interrupt()}}}buildUserMessage(e,n){return{type:"user",message:{role:"user",content:e},parent_tool_use_id:null,session_id:n}}}});import{spawn as cc}from"node:child_process";import pc from"node:readline";function mc(t){return t instanceof Error?t.message:String(t)}function fc(t){try{let e=JSON.parse(t);return!e||typeof e!="object"||Array.isArray(e)?null:e}catch{return null}}async function gc(t,e){if(t.id!=null&&(Object.hasOwn(t,"result")||Object.hasOwn(t,"error"))){let r=String(t.id),o=e.pending.get(r);if(!o)return;if(clearTimeout(o.timer),e.pending.delete(r),t.error){o.reject(new Error(`codex app server rpc error (${t.error.code??"unknown"}): ${t.error.message??"unknown error"}`));return}o.resolve(t.result);return}let n=t.method?.trim();if(n){if(t.id==null){await e.onNotification(n,t.params);return}try{let r=await e.onRequest(n,t.params);e.respond({jsonrpc:"2.0",id:t.id,result:r??{}})}catch(r){e.respond({jsonrpc:"2.0",id:t.id,error:{code:-32603,message:mc(r)}})}}}function hc(t){return t.replace(/\b([a-z][a-z0-9+.-]*:\/\/)[^\s/?#@]+@/gi,"$1[redacted credential]@").replace(/\b(authorization\s*[:=]\s*)[^\r\n,;}]+/gi,"$1[redacted credential]").replace(/\b(Bearer\s+)[^\s]+/gi,"$1[redacted credential]").replace(/(["'][A-Za-z0-9_.-]*(?:api[_-]?key|token|secret|password|authorization)[A-Za-z0-9_.-]*["']\s*:\s*["'])[^"']+(["'])/gi,"$1[redacted credential]$2").replace(/\b([A-Za-z0-9_.-]*(?:api[_-]?key|token|secret|password|authorization)[A-Za-z0-9_.-]*\s*[:=]\s*)[^\s,}]+/gi,"$1[redacted credential]").replace(/\b(?:sk-[A-Za-z0-9_-]{8,}|gh[opsru]_[A-Za-z0-9_]{8,}|[A-Za-z0-9_-]{32,})\b/g,"[redacted token]").replace(/(?:\/Users|\/home)\/[^\s]+/g,"[redacted path]").replace(/\s+/g," ").slice(-1e3)}var Kn,Gs=H(()=>{Kn=class{constructor(e,n,r){this.command=e;this.args=n;this.requestTimeoutMs=r}command;args;requestTimeoutMs;process=null;pending=new Map;stderrTail="";counter=0;onNotification=()=>{};onRequest=async()=>({});setNotificationHandler(e){this.onNotification=e}setRequestHandler(e){this.onRequest=e}async connect(){if(this.process)return;let e=cc(this.command,["app-server",...this.args],{stdio:["pipe","pipe","pipe"],env:process.env});if(!e.stdin||!e.stdout||!e.stderr)throw new Error("codex app server stdio pipes unavailable");this.process=e,pc.createInterface({input:e.stdout}).on("line",r=>{this.handleLine(r)}),e.stderr.on("data",r=>{this.stderrTail=`${this.stderrTail}${r.toString("utf8")}`.slice(-4e3)}),e.on("close",()=>{this.flushPending(new Error("codex app server stdio closed")),this.process=null})}async close(){this.flushPending(new Error("codex app server stdio closed"));let e=this.process;this.process=null,e&&e.kill()}async notify(e,n){this.write({jsonrpc:"2.0",method:e,params:n??{}})}async request(e,n,r){let o=`rpc-${++this.counter}`,i=new Promise((s,a)=>{let l=Math.max(100,r??this.requestTimeoutMs),d=setTimeout(()=>{this.pending.delete(o),a(new Error(this.buildTimeoutErrorMessage(e,l)))},l);d.unref?.(),this.pending.set(o,{resolve:s,reject:a,timer:d})});return this.write({jsonrpc:"2.0",id:o,method:e,params:n??{}}),await i}write(e){if(!this.process?.stdin)throw new Error("codex app server stdio not connected");this.process.stdin.write(`${JSON.stringify(e)}
7
+ `)}async handleLine(e){let n=fc(e);n&&await gc(n,{pending:this.pending,onNotification:this.onNotification,onRequest:this.onRequest,respond:r=>this.write(r)})}flushPending(e){for(let[n,r]of this.pending)clearTimeout(r.timer),r.reject(e),this.pending.delete(n)}buildTimeoutErrorMessage(e,n){let r=this.stderrTail.trim(),o=r?`; recent stderr: ${hc(r)}`:"";return`codex app server timeout after ${n}ms: ${e}${o}`}}});function js(t,e){if(!e||e.length===0)return!0;if(!t)return!1;let n=t.toLowerCase();return e.some(r=>n.includes(r.toLowerCase()))}var Hs=H(()=>{});function Oe(t,e){let n=e?.trim();if(!n)return;if(t!=="codex")return n;let[r,...o]=n.split("/");return r?.toLowerCase()==="openai"&&o.length===1&&o[0]?.trim()?o[0].trim():n}function yc(t,e){if(!e||e.length===0)return!0;if(!t)return!1;let n=t.toLowerCase();return e.some(r=>Oe("codex",r)?.toLowerCase()===n)}function Un(t,e,n){return t==="codex"?yc(e,n):js(e,n)}function vt(t,e){return t!=="codex"||!e?!0:!e.includes("/")}function Vn(t,e,n){if(t!=="codex"||!e||!n||n.length===0)return e;let r=e.toLowerCase(),o=n.find(i=>Oe("codex",i)?.toLowerCase()===r);return Oe("codex",o)??e}var Gn=H(()=>{Hs()});function kc(t){return t instanceof Error?t.message:String(t)}function zs(t){return t?t.split(",").map(e=>e.trim()).filter(Boolean):[]}function Ge(t){if(typeof t=="string")return t;if(Array.isArray(t))return t.map(n=>Ge(n)).join("");let e=K(t);if(!e)return"";for(let n of["delta","text","content","message","input","output","parts"]){let r=Ge(e[n]);if(r)return r}for(let n of["item","turn","thread","response","result","data"]){let r=Ge(e[n]);if(r)return r}return""}function tn(t){let e=K(t);if(!e)return{};let n=K(e.thread)??K(e.session),r=K(e.turn)??K(e.run),o=K(e.item),i=K(e.serverRequest);return{threadId:G(e,["threadId","thread_id","conversationId","conversation_id"])??G(n,["id","threadId","thread_id","conversationId"]),runId:G(e,["turnId","turn_id","runId","run_id"])??G(r,["id","turnId","turn_id","runId","run_id"]),requestId:G(e,["requestId","request_id","serverRequestId"])??G(i,["id","requestId","request_id"]),itemId:G(e,["itemId","item_id"])??G(o,["id","itemId","item_id"])}}function jn(t,e,n=0){if(n>6)return;if(Array.isArray(t)){for(let i of t){let s=jn(i,e,n+1);if(s)return s}return}let r=K(t);if(!r)return;let o=G(r,e);if(o)return o;for(let i of Object.values(r)){let s=jn(i,e,n+1);if(s)return s}}function nn(t){return{threadId:tn(t).threadId,cwd:jn(t,["cwd","workdir","directory"])}}function Qs(t){let e=t?.trim();return!!(e&&/[/\\]worktrees[/\\][^/\\]+[/\\][^/\\]+/.test(e))}function Js(t){let e=t?.trim();if(!e)return;let n=e.split(/[/\\]+/).filter(Boolean),r=n.lastIndexOf("worktrees");if(!(r<0||r+1>=n.length))return n[r+1]}function Hn(t){let e=K(t);if(!e)return;let n=K(e.item)??e;return G(n,["id","itemId","item_id","messageId","message_id"])}function Sc(t,e=!1){let n=K(t);if(!n)return"";let r=K(n.item)??n;return G(r,["type"])?.toLowerCase()!=="agentmessage"?"":e?Ge(r):G(r,["text"],{trim:!1})??Ge(r)}function Ys(t,e){let n=t.trim().toLowerCase();return n==="item/agentmessage/delta"?{mode:"delta",text:Ge(e),itemId:Hn(e)}:n==="item/completed"?{mode:"snapshot",text:Sc(e),itemId:Hn(e)}:{mode:"ignore",text:""}}function Zs(t){return{itemId:Hn(t),delta:Ge(t)}}function Xs(t){let e=K(t),n=K(e?.plan),o=(Array.isArray(e?.plan)?e.plan:Array.isArray(n?.steps)?n.steps:[]).map(i=>{let s=K(i),a=G(s,["step","title","text"]);if(!a)return null;let l=G(s,["status"])?.toLowerCase()??"pending";return{step:a,status:l==="inprogress"||l==="in_progress"?"inProgress":l==="completed"?"completed":"pending"}}).filter(Boolean);return{explanation:G(n,["explanation"])??G(e,["explanation"]),steps:o}}function ea(t){let e=K(t);if(!e)return{};let n=K(e.item)??e;return G(n,["type"])?.toLowerCase()!=="plan"?{}:{itemId:Hn(n),text:G(n,["text"],{trim:!1})??Ge(n)}}function ta(t,e){let n=t.trim().toLowerCase();if(n==="turn/failed")return"failed";if(n==="turn/cancelled")return"interrupted";let r=K(e)??{},o=K(r.turn)??r,i=G(o,["status"])?.toLowerCase();return i==="failed"?"failed":i==="interrupted"||i==="cancelled"?"interrupted":"completed"}function na(t,e){let n=K(e)??{},r=K(n.turn)??n,o=K(r.error)??K(n.error);if(o)return G(o,["message","text","summary","reason"])}function vc(t,e){let n=kc(t).toLowerCase();return n.includes("method not found")||n.includes("unknown method")?!0:n.includes("unknown variant")?e?n.includes(`unknown variant \`${e.toLowerCase()}\``):!0:!1}function Pc(t){return wc.has(t.trim().toLowerCase())}function bc(t){let e=K(t);return e?!!G(e,["threadId","thread_id"]):!1}async function rn(t){if(t.payloads.length===0)throw new Error(`codex app server request skipped: no payloads for ${t.methods.join(", ")||"<none>"}`);let e;for(let n of t.methods)for(let r of t.payloads){if(Pc(n)&&!bc(r))throw new Error(`codex app server request missing threadId: ${n}`);try{return await t.client.request(n,r,t.timeoutMs)}catch(o){if(e=o,!vc(o,n))continue}}throw e instanceof Error?e:new Error(String(e))}function ra(t){let e={cwd:t.cwd};return t.model?.trim()&&(e.model=t.model.trim()),t.reasoningEffort?.trim()&&(e.reasoningEffort=t.reasoningEffort.trim()),t.fastMode===!0&&(e.service_tier="fast"),t.approvalPolicy?.trim()&&(e.approvalPolicy=t.approvalPolicy.trim()),t.sandbox?.trim()&&(e.sandbox=t.sandbox.trim()),[e]}function oa(t){let e={threadId:t.threadId,persistExtendedHistory:!1};return t.model?.trim()&&(e.model=t.model.trim()),t.reasoningEffort?.trim()&&(e.reasoningEffort=t.reasoningEffort.trim()),t.fastMode===!0&&(e.service_tier="fast"),t.cwd?.trim()&&(e.cwd=t.cwd.trim()),t.approvalPolicy?.trim()&&(e.approvalPolicy=t.approvalPolicy.trim()),t.sandbox?.trim()&&(e.sandbox=t.sandbox.trim()),[e]}function Rc(t){return[{type:"text",text:t}]}function Ac(t,e,n,r){let o=e?.trim(),i=n?.trim(),s=r?.trim();if(t!=="plan")return o||i||s?{mode:"default",settings:{...o?{model:o}:{},...i?{reasoningEffort:i}:{},developerInstructions:s??null}}:void 0;if(!(!o&&!i&&!s))return{mode:"plan",settings:{...o?{model:o}:{},...i?{reasoningEffort:i}:{},developerInstructions:s??null}}}function ia(t){let e={threadId:t.threadId,input:Rc(t.prompt)};t.model?.trim()&&(e.model=t.model.trim()),t.fastMode===!0&&(e.service_tier="fast"),t.approvalPolicy?.trim()&&(e.approvalPolicy=t.approvalPolicy.trim()),t.sandbox?.trim()&&(e.sandbox=t.sandbox.trim());let n=Ac(t.permissionMode??"default",t.model,t.reasoningEffort,t.systemPrompt);return n?[{...e,collaborationMode:n}]:[e]}function sa(t){return[{threadId:t.threadId,turnId:t.turnId}]}function Ic(t){let e=t.trim().toLowerCase();return e.includes("session")?"acceptForSession":/cancel|abort|stop/.test(e)?"cancel":/deny|decline|reject|block|no/.test(e)?"decline":/approve|allow|accept|yes/.test(e)?"accept":t.trim()}function aa(t,e,n){let r=t.trim().toLowerCase(),o=r.includes("requestapproval"),i=r.includes("requestuserinput"),s=ht(n);if(i&&s.length===0)throw new Error(`Malformed Codex request_user_input payload for ${e}: expected non-empty questions[]`);let a=o?On(n):[],l=s.length>0?0:void 0,d=l!=null?s[l]:void 0,u=d?d.options:[],p=(o&&u.length===0?a:u).map(f=>f.label),g=(d?Ee(d,l??0,s.length):Wn(s))??(o?jn(n,["question","prompt","message","text","summary","reason"]):void 0)??void 0,m=o?p.map(f=>({kind:"approval",label:f,decision:Ic(f),responseDecision:f})):p.map(f=>({kind:"option",label:f,value:f}));return{requestId:e,kind:o?"approval":"question",promptText:g,options:p,...s.length>0?{questions:s}:{},...l!=null?{activeQuestionIndex:l}:{},actions:m,allowsFreeText:!0}}function la(t){let e=t.trim().toLowerCase();return e.includes("requestuserinput")||e.includes("requestapproval")}function ri(t,e){let n=t==="bypassPermissions"?"never":e?.trim()||"never";return{approvalPolicy:n,sandbox:n==="never"?"danger-full-access":void 0}}var wc,da=H(()=>{en();wc=new Set(["thread/resume","turn/start","turn/steer","turn/interrupt"])});function $c(t){let e=t?.trim();return e&&_c.test(e)?e:void 0}function Ec(t){let e=t?.trim();if(!e||!/^\d+$/.test(e))return oi;let n=Number(e);return Number.isSafeInteger(n)&&n>0?n:oi}function ii(t){return t instanceof Error?t.message:String(t)}function Dc(t){if(typeof t=="string")return t;if(!t||typeof t!="object")return String(t);let e=t;return typeof e.message?.content=="string"?e.message.content:typeof e.text=="string"?e.text:String(t)}function ca(t,e,n){let r=t.questions??[],o=r[e];return o?{...t,promptText:Ee(o,e,r.length),options:o.options.map(i=>i.label),activeQuestionIndex:e,answers:n}:t}function Oc(t){if(t===void 0)return ua;let e=zs(t);return e.length>0?e:ua}var xc,oi,ua,Tc,Cc,Mc,_c,zn,pa=H(()=>{Gs();Bn();en();Gn();da();xc="1.0",oi=12e4,ua=["--listen","stdio://"],Tc="OPENCLAW_CODEX_APP_SERVER_COMMAND",Cc="OPENCLAW_CODEX_APP_SERVER_ARGS",Mc="OPENCLAW_CODEX_APP_SERVER_TIMEOUT_MS",_c=/^(?:urn:uuid:)?[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}$/;zn=class{constructor(e={}){this.deps=e}deps;name="codex";backendKind="codex-app-server";supportedPermissionModes=["default","plan","bypassPermissions"];capabilities={nativePendingInput:!0,nativePlanArtifacts:!0,worktrees:"native-restore"};launch(e){let n={command:process.env[Tc]?.trim()||"codex",args:Oc(process.env[Cc]),requestTimeoutMs:Ec(process.env[Mc])},r=this.deps.createClient?.(n)??new Kn(n.command,n.args,n.requestTimeoutMs),o=new Ue,i=$c(e.resumeSessionId);e.resumeSessionId&&!i&&`${e.resumeSessionId}`;let s,a=e.backendRef?.worktreePath,l=e.backendRef?.worktreeId,d=e.permissionMode??"default",u=Oe(this.name,e.model);if(!vt(this.name,u))throw new Error(`Codex model "${e.model}" is not supported. Use a bare Codex model id such as "gpt-5.5".`);let c,p=0,g="",m=[],f,y=new Map,S=new Set,R=E=>{let T=E?.trim();if(!T)return;let C=e.originalWorkdir?.trim()||e.cwd.trim();e.worktreeStrategy&&e.worktreeStrategy!=="off"&&T!==C&&Qs(T)&&(a=T,l=Js(T))},I=()=>{i&&o.enqueue(yt({kind:"codex-app-server",conversationId:i,...s?{runId:s}:{},...l?{worktreeId:l}:{},...a?{worktreePath:a}:{}}))};r.setNotificationHandler(async(E,T)=>{let C=E.trim().toLowerCase(),q=tn(T),j=nn(T);if(q.threadId&&i&&q.threadId!==i)return;if(q.threadId&&(i=q.threadId),q.runId&&(s=q.runId),R(j.cwd),(q.threadId||q.runId||j.cwd)&&I(),C==="serverrequest/resolved"){c&&(o.enqueue(Ve(c.requestId)),c=void 0);return}if(C==="turn/plan/updated"){let V=Xs(T);g=V.explanation??g,V.steps.length>0&&(m=V.steps);return}if(C==="item/plan/delta"){let V=Zs(T);if(V.itemId&&V.delta){let ie=y.get(V.itemId)??"";y.set(V.itemId,`${ie}${V.delta}`)}return}if(C==="item/completed"){let V=ea(T);if(V.text?.trim()){let ie={explanation:g||void 0,steps:m,markdown:V.text.trim()};o.enqueue(Ln(ie,!0));return}}let N=Ys(C,T);if(N.mode==="delta"&&N.text){N.itemId&&S.add(N.itemId),o.enqueue(Xe(N.text));return}N.mode==="snapshot"&&N.text&&(!N.itemId||!S.has(N.itemId))&&o.enqueue(Xe(N.text)),(C==="turn/completed"||C==="turn/failed"||C==="turn/cancelled")&&f&&(f.method=E,f.params=T,f.resolve())}),r.setRequestHandler(async(E,T)=>{if(!la(E))return{};let C=tn(T),q=nn(T);if(C.threadId&&i&&C.threadId!==i)return{};C.threadId&&(i=C.threadId),C.runId&&(s=C.runId),R(q.cwd),(C.threadId||C.runId||q.cwd)&&I();let j=C.requestId??`${i??"codex"}-${Date.now().toString(36)}`,N;try{N=aa(E,j,T)}catch(Gt){let jt=ii(Gt);return`${jt}`,{error:jt}}let V=E.trim().toLowerCase(),ie=N.options,xe=N.actions??[],ut=await new Promise(Gt=>{c={requestId:j,methodLower:V,state:N,options:ie,actions:xe,answers:{...N.answers??{}},resolveResponse:Gt},o.enqueue(Ce(N))});return c=void 0,o.enqueue(Ve(j)),ut});let b=async()=>{await r.connect(),await r.request("initialize",{protocolVersion:xc,clientInfo:{name:"openclaw-code-agent",version:"3.1.0"},capabilities:{experimentalApi:!0}},n.requestTimeoutMs),await r.notify("initialized",{})},A=async()=>{let E=ri(d,e.codexApprovalPolicy);if(i){let q=await rn({client:r,methods:["thread/resume"],payloads:oa({threadId:i,model:u,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,approvalPolicy:E.approvalPolicy,sandbox:E.sandbox}),timeoutMs:n.requestTimeoutMs}),j=nn(q);i=j.threadId??i,R(j.cwd),I();return}let T=await rn({client:r,methods:["thread/start","thread/new"],payloads:ra({cwd:e.cwd,model:u,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,approvalPolicy:E.approvalPolicy,sandbox:E.sandbox}),timeoutMs:n.requestTimeoutMs}),C=nn(T);if(i=C.threadId,!i)throw new Error("Codex App Server did not return a thread id.");R(C.cwd),I()},k=async E=>{await A(),o.enqueue(kt()),p+=1,g="",m=[],y.clear(),S.clear();let T="",C,q,j=new Promise(N=>{q=N});f={resolve:q};try{let N=ri(d,e.codexApprovalPolicy),V=await rn({client:r,methods:["turn/start"],payloads:ia({threadId:i,prompt:E,model:u,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,systemPrompt:e.systemPrompt,permissionMode:d,approvalPolicy:N.approvalPolicy,sandbox:N.sandbox}),timeoutMs:n.requestTimeoutMs}),ie=tn(V);ie.runId&&(s=ie.runId,I()),await j,T=f?.method??"turn/failed",C=f?.params;let xe=ta(T,C);o.enqueue(De({success:xe==="completed",outcome:xe,duration_ms:0,total_cost_usd:0,num_turns:p,result:na(T,C),session_id:i}))}catch(N){o.enqueue(De({success:!1,duration_ms:0,total_cost_usd:0,num_turns:p,result:ii(N),session_id:i??""}))}finally{f=void 0}},P=async E=>{let T=c;if(!T)return!1;let C=E.trim();if(T.methodLower.includes("requestapproval"))return T.resolveResponse({decision:C||"decline"}),!0;let q=T.state.questions??[];if(q.length>0){if(!C)return!1;let j=T.state.activeQuestionIndex??0,N=q[j];if(!N)return!1;T.answers={...T.answers,[N.id]:{answers:[C]}};let V=j+1;if(V<q.length)return T.state=ca(T.state,V,T.answers),T.options=T.state.options,o.enqueue(Ce(T.state)),!0;T.resolveResponse({answers:T.answers})}else T.resolveResponse({text:C});return!0},F=async(E,T={})=>{let C=c;if(!C||T.requestId&&T.requestId!==C.state.requestId)return!1;let q=C.actions[E];if(q?.kind==="approval")return C.resolveResponse({decision:q.responseDecision,...q.proposedExecpolicyAmendment?{proposedExecpolicyAmendment:q.proposedExecpolicyAmendment}:{}}),!0;let j=C.state.questions??[],N=C.state.activeQuestionIndex??0,V=j.length>0?j[N]:void 0;if(T.questionId&&T.questionId!==V?.id)return!1;let ie=V?.options[E];if(V&&ie){C.answers={...C.answers,[V.id]:{answers:[ie.value??ie.label]}};let ut=N+1;return ut<j.length?(C.state=ca(C.state,ut,C.answers),C.options=C.state.options,o.enqueue(Ce(C.state)),!0):(C.resolveResponse({answers:C.answers}),!0)}let xe=C.options[E];return xe?(C.methodLower.includes("requestapproval")?C.resolveResponse({decision:xe}):C.resolveResponse({option:xe,index:E}),!0):!1},pe=typeof e.prompt=="string"?(async function*(){yield{type:"user",text:e.prompt,session_id:e.resumeSessionId??""}})():e.prompt;return(async()=>{try{await b();for await(let E of pe){let T=Dc(E).trim();!T||await P(T)||await k(T)}}catch(E){o.enqueue(De({success:!1,duration_ms:0,total_cost_usd:0,num_turns:p,result:ii(E),session_id:i??e.resumeSessionId??""}))}finally{await r.close().catch(()=>{}),o.close()}})(),{messages:o.messages(),async setPermissionMode(E){d=E,o.enqueue(St(E))},async submitPendingInputOption(E,T){return F(E,T)},async submitPendingInputText(E){return P(E)},async interrupt(){!i||!s||await rn({client:r,methods:["turn/interrupt"],payloads:sa({threadId:i,turnId:s}),timeoutMs:n.requestTimeoutMs}).catch(()=>{})}}}buildUserMessage(e,n){return{type:"user",text:e,session_id:n}}}});import{spawn as Wc}from"node:child_process";import{constants as Nc,accessSync as Lc}from"node:fs";import{createServer as Bc}from"node:net";import{delimiter as Fc,dirname as si,join as ga,sep as qc}from"node:path";function Pt(t){return t instanceof Error?t.message:String(t)}function jc(t){try{return Lc(t,Nc.X_OK),!0}catch{return!1}}function Hc(t){return t.includes("/")||qc==="\\"&&t.includes("\\")}function zc(t){let e=(t??"").split(Fc).map(r=>r.trim()).filter(Boolean),n=[...e];for(let r of e)r.replaceAll("\\","/").endsWith("/opt/node/bin")&&n.push(ga(si(si(si(r))),"bin"));return n.push("/home/linuxbrew/.linuxbrew/bin","/opt/homebrew/bin","/usr/local/bin","/usr/bin","/bin"),[...new Set(n)]}function Qc(t,e=process.env.PATH){if(Hc(t))return t;for(let n of zc(e)){let r=ga(n,t);if(jc(r))return r}return t}function re(t){return!!t&&typeof t=="object"&&!Array.isArray(t)}function Jc(t){if(typeof t=="string")return t;if(!re(t))return String(t);if(typeof t.text=="string")return t.text;let e=re(t.message)?t.message:void 0;return typeof e?.content=="string"?e.content:String(t)}function ha(t){let e=t?.trim();if(!e)return;let n=e.indexOf("/");if(!(n<=0||n===e.length-1))return{providerID:e.slice(0,n),modelID:e.slice(n+1)}}function Yc(t){let e=ha(t);return e?{id:e.modelID,providerID:e.providerID}:void 0}function ma(t){let e=t??"default",n=e==="plan"?"deny":e==="bypassPermissions"?"allow":"ask";return Gc.map(r=>({permission:r,pattern:"*",action:n}))}function ai(){let t=process.env.OPENCODE_SERVER_PASSWORD;if(!t)return{};let e=process.env.OPENCODE_SERVER_USERNAME||"opencode";return{Authorization:`Basic ${Buffer.from(`${e}:${t}`).toString("base64")}`}}async function Zc(){return new Promise((t,e)=>{let n=Bc();n.once("error",e),n.listen(0,"127.0.0.1",()=>{let r=n.address();n.close(()=>{r&&typeof r=="object"?t(r.port):e(new Error("Could not allocate local OpenCode server port."))})})})}async function ya(t){await new Promise(e=>setTimeout(e,t))}async function Qn(t,e){if(e.signal?.aborted)throw new Error(e.abortMessage??"Operation was aborted.");return await new Promise((n,r)=>{let o=!1,i=()=>{clearTimeout(l),e.signal?.removeEventListener("abort",a)},s=d=>{o||(o=!0,i(),d())},a=()=>{s(()=>r(new Error(e.abortMessage??"Operation was aborted.")))},l=setTimeout(()=>{s(()=>{e.onTimeout?.(),r(new Error(e.timeoutMessage))})},e.timeoutMs);e.signal?.addEventListener("abort",a,{once:!0}),t.then(d=>s(()=>n(d)),d=>s(()=>r(d)))})}async function wt(t){t.exitCode===null&&await new Promise(e=>{let n,r=setTimeout(()=>{t.exitCode===null&&t.kill("SIGKILL"),n=setTimeout(e,1e3)},2e3);t.once("exit",()=>{clearTimeout(r),n&&clearTimeout(n),e()}),t.kill("SIGTERM")})}function Xc(t){return t.headers.get("content-type")?.toLowerCase()??""}function di(t){return t.replace(/\s+/g," ").trim().slice(0,300)}function ep(t,e){return t.includes("text/html")||/^\s*<!doctype html\b/i.test(e)||/^\s*<html[\s>]/i.test(e)}function tp(t,e,n,r){let o=n?`content-type ${n}`:"missing content-type",i=di(r),s=ep(n,r)?" (looks like the OpenCode web UI HTML app shell)":"";return`OpenCode ${t} ${e} expected JSON API response but received ${o}${s}${i?`: ${i}`:""}`}function np(t,e,n){let r=ha(e);return{...r?{model:{providerID:r.providerID,modelID:r.modelID}}:{},...n?.trim()?{system:n.trim()}:{},parts:[{type:"text",text:t}]}}function rp(t,e){if(!re(t))return!1;if(!(e in t))return!0;let n=t[e];return re(n)&&n.type==="idle"}function op(t){return t.type==="session.idle"?!0:t.type!=="session.status"?!1:(t.properties.status??t.properties.type)==="idle"}function ip(t){return new Promise((e,n)=>{fa=fa.then(()=>t().then(e,n)).catch(()=>{})})}async function sp(t){return ip(async()=>{let e=await Zc(),n=process.env[Kc]?.trim()||"opencode",r=Qc(n),o=["serve","--hostname","127.0.0.1","--port",String(e),"--print-logs"],i=t.fetch??fetch,s=Math.min(t.requestTimeoutMs??pi,1e4),a=t.startupTimeoutMs??Uc,l=Wc(r,o,{cwd:t.cwd,stdio:["ignore","pipe","pipe"]}),d=`http://127.0.0.1:${e}`,u="",c="",p,g=(S,R)=>{let I=S+String(R);return I.length>8e3?I.slice(-8e3):I};l.stdout.on("data",S=>{u=g(u,S)}),l.stderr.on("data",S=>{c=g(c,S)}),l.once("error",S=>{p=S});let m=()=>` Command: ${n===r?r:`${r} (resolved from ${n})`} ${o.join(" ")}. Cwd: ${t.cwd}. Port: ${e}. PATH: ${process.env.PATH??""}.`,f=()=>{let S=[u.trim(),c.trim()].filter(Boolean).join(`
8
+ `).trim();return`${m()}${S?` Output:
9
+ ${S}`:""}`},y=()=>{wt(l)};if(t.signal?.aborted)throw await wt(l),new Error(`OpenCode server startup aborted before readiness.${f()}`);t.signal?.addEventListener("abort",y,{once:!0});try{let S=Date.now();for(;Date.now()-S<a;){if(t.signal?.aborted)throw await wt(l),new Error(`OpenCode server startup aborted before readiness.${f()}`);if(p)throw new Error(`OpenCode server failed to start: ${p.message}${f()}`);if(l.exitCode!==null)throw new Error(`OpenCode server exited before readiness.${f()}`);try{if(await lp({baseUrl:d,fetchImpl:i,requestTimeoutMs:s,startupSignal:t.signal,timeoutMessage:`OpenCode GET /api/health timed out after ${s}ms during server readiness.${f()}`,abortMessage:`OpenCode server startup aborted before readiness.${f()}`}))return{baseUrl:d,close:async()=>{await wt(l)}}}catch{if(t.signal?.aborted)throw await wt(l),new Error(`OpenCode server startup aborted before readiness.${f()}`)}await ya(100)}throw await wt(l),new Error(`Timed out waiting for OpenCode server readiness.${f()}`)}finally{t.signal?.removeEventListener("abort",y)}})}async function ap(t){for(let e=1;;e+=1)try{return await sp(t)}catch(n){if(e>=3||!/EADDRINUSE|address already in use|bind: address already in use/i.test(Pt(n)))throw n}}async function lp(t){let e=new AbortController,n=()=>e.abort();t.startupSignal?.aborted?e.abort():t.startupSignal?.addEventListener("abort",n,{once:!0});try{return(await Qn(t.fetchImpl(`${t.baseUrl}/api/health`,{headers:ai(),signal:e.signal}),{timeoutMs:t.requestTimeoutMs,timeoutMessage:t.timeoutMessage,signal:t.startupSignal,abortMessage:t.abortMessage,onTimeout:()=>e.abort()})).ok}finally{t.startupSignal?.removeEventListener("abort",n)}}function dp(t){let e=re(t)&&re(t.payload)?t.payload:t;return re(e)?e.type==="sync"?{type:typeof e.name=="string"?e.name.replace(/\.\d+$/,""):void 0,properties:re(e.data)?e.data:{}}:{type:typeof e.type=="string"?e.type:void 0,properties:re(e.properties)?e.properties:e}:{properties:{}}}function up(t){return typeof t.sessionID=="string"?t.sessionID:void 0}function cp(t){let e=typeof t.id=="string"?t.id:"opencode-permission",n=typeof t.permission=="string"?t.permission:"permission",r=Array.isArray(t.patterns)?t.patterns.filter(s=>typeof s=="string"):[],o=r.length>0?`OpenCode requests ${n} permission for ${r.join(", ")}.`:`OpenCode requests ${n} permission.`,i=[{kind:"approval",label:"Allow once",decision:"accept",responseDecision:"once"},{kind:"approval",label:"Always allow",decision:"acceptForSession",responseDecision:"always"},{kind:"approval",label:"Reject",decision:"decline",responseDecision:"reject"}];return{requestId:e,kind:"approval",promptText:o,options:i.map(s=>s.label),actions:i,responseMode:"structured"}}function pp(t){let e=typeof t.id=="string"?t.id:"opencode-question",n=typeof t.question=="string"?t.question:typeof t.prompt=="string"?t.prompt:"OpenCode is asking for input.",r=ht(t),o=On(t),i=r.length>0?r:[{id:e,question:n,options:o,allowsFreeText:!0}],s=i.length>0?0:void 0,a=s!=null?i[s]:void 0,l=a?.options.map(d=>d.label)??o.map(d=>d.label);return{requestId:e,kind:"question",promptText:a?Ee(a,s??0,i.length):n,options:l,...i.length>0?{questions:i}:{},...s!=null?{activeQuestionIndex:s}:{},allowsFreeText:!0}}function mp(t,e,n){let r=t.questions??[],o=r[e],i=o?.options.map(s=>s.label)??[];return{...t,promptText:o?Ee(o,e,r.length):t.promptText,options:i,activeQuestionIndex:e,answers:n}}function fp(t,e){return t.length===1?e[t[0].id]?.answers.join(", ")??"":t.map((n,r)=>{let o=e[n.id]?.answers.join(", ")??"";return`Q${r+1}: ${n.question}
10
10
  A${r+1}: ${o}`}).join(`
11
11
 
12
- `)}function rp(t){return ai(t).result}function ai(t){let e=Array.isArray(t)?t:ne(t)&&Array.isArray(t.messages)?t.messages:ne(t)&&Array.isArray(t.items)?t.items:[],n=[];for(let r of e){let o=ne(r)&&ne(r.info)?r.info:r;if(!ne(o)||(typeof o.role=="string"?o.role:o.type)!=="assistant")continue;let s=Array.isArray(o.content)?o.content:[],l=ne(r)&&Array.isArray(r.parts)?r.parts:[];for(let a of[...s,...l])ne(a)&&a.type==="text"&&typeof a.text=="string"&&n.push(a.text)}return{count:n.length,result:n.at(-1)}}var Mc,_c,li,$c,Ec,oi,aa,si,zn,ca=H(()=>{Xt();Nn();Mc="OPENCLAW_OPENCODE_COMMAND",_c=15e3,li=6e4,$c=15*6e4,Ec=["edit","bash","task","todowrite","external_directory"];oi=class extends Error{constructor(n,r,o,i){super(`OpenCode ${n} ${r} failed with ${o}${i?`: ${i}`:""}`);this.method=n;this.path=r;this.status=o;this.body=i}method;path;status;body};aa=Promise.resolve();si=class{constructor(e,n,r=li){this.baseUrl=e;this.fetchImpl=n;this.requestTimeoutMs=r}baseUrl;fetchImpl;requestTimeoutMs;async request(e,n,r,o={}){let i=new AbortController,s=!1,l=!1,a=o.timeoutMs??this.requestTimeoutMs,d=`OpenCode ${e} ${n} timed out after ${a}ms.`,u=`OpenCode ${e} ${n} was aborted.`,c=()=>{s=!0,i.abort()};o.signal?.aborted?(s=!0,i.abort()):o.signal?.addEventListener("abort",c,{once:!0});try{let m=await Hn(this.fetchImpl(`${this.baseUrl}${n}`,{method:e,headers:{...ri(),...r===void 0?{}:{"content-type":"application/json"}},body:r===void 0?void 0:JSON.stringify(r),signal:i.signal}),{timeoutMs:a,timeoutMessage:d,signal:o.signal,abortMessage:u,onTimeout:()=>{l=!0,i.abort()}});if(!m.ok){let h=await Hn(m.text(),{timeoutMs:a,timeoutMessage:d,signal:o.signal,abortMessage:u,onTimeout:()=>{l=!0,i.abort()}}).catch(()=>"");throw new oi(e,n,m.status,ii(h))}if(m.status===204)return;let p=await Hn(m.text(),{timeoutMs:a,timeoutMessage:d,signal:o.signal,abortMessage:u,onTimeout:()=>{l=!0,i.abort()}});if(!p)return;let f=qc(m);if(!f.includes("application/json")&&!f.includes("+json"))throw new Error(Kc(e,n,f,p));try{return JSON.parse(p)}catch(h){let k=ii(p);throw new Error(`OpenCode ${e} ${n} returned invalid JSON: ${vt(h)}${k?`: ${k}`:""}`)}}catch(m){if(i.signal.aborted){if(l)throw new Error(`OpenCode ${e} ${n} timed out after ${a}ms.`);if(s)throw new Error(`OpenCode ${e} ${n} was aborted.`)}throw m}finally{o.signal?.removeEventListener("abort",c)}}async streamEvents(e,n){let r=await this.fetchImpl(`${this.baseUrl}/event`,{headers:ri(),signal:n});if(!r.ok)throw new Error(`OpenCode event stream failed with ${r.status}`);if(!r.body)return;let o=r.body.getReader(),i=new TextDecoder,s="",l=async d=>{let u=d.split(/\r?\n/).filter(c=>c.startsWith("data:")).map(c=>c.slice(5).trimStart()).join(`
13
- `).trim();!u||u==="[DONE]"||await e(JSON.parse(u))};for(;;){let{done:d,value:u}=await o.read();if(d)break;s+=i.decode(u,{stream:!0});let c=/\r?\n\r?\n/.exec(s);for(;c;){let m=s.slice(0,c.index);s=s.slice(c.index+c[0].length),await l(m),c=/\r?\n\r?\n/.exec(s)}}let a=s.trim();a&&await l(a)}};zn=class{constructor(e={}){this.deps=e}deps;name="opencode";backendKind="opencode-server";supportedPermissionModes=["default","plan","bypassPermissions"];capabilities={nativePendingInput:!0,nativePlanArtifacts:!1,worktrees:"plugin-managed"};launch(e){let n=new qe,r=this.deps.fetch??fetch,o,i,s,l=e.resumeSessionId,a=0,d=e.permissionMode??"default",u,c=!e.resumeSessionId,m=!1,p=!1,f=new AbortController,h,k=!1,v=!1,I=!1,x=!1,b=!1,A=!1,y,w=new Set,F=M=>x?!1:(x=!0,n.enqueue(Ee(M)),!0),ce=(M,R,_)=>F({success:M,outcome:R,duration_ms:0,total_cost_usd:0,num_turns:a,result:_,session_id:l??""}),E=()=>{l&&y!==l&&(y=l,n.enqueue(gt({kind:"opencode-server",conversationId:l})))},T=M=>{M&&w.has(M)||(M&&w.add(M),n.enqueue(Ue(M)),M&&u?.requestId===M&&(u=void 0))},C=async()=>{if(i)return i;s??=(async()=>{let M=await(this.deps.createServer??Qc)({cwd:e.cwd,signal:e.abortController?.signal,fetch:r,requestTimeoutMs:this.deps.requestTimeoutMs,startupTimeoutMs:this.deps.startupTimeoutMs});if(b||e.abortController?.signal.aborted)throw await M.close().catch(()=>{}),new Error("OpenCode startup was interrupted before session creation.");return o=M,i=new si(M.baseUrl,r,this.deps.requestTimeoutMs),i})();try{return await s}catch(M){throw s=void 0,M}},B=async(M,R)=>{!i||!l||await i.request("POST",`/permission/${encodeURIComponent(M)}/reply`,{reply:R})},j=async(M,R)=>{!i||!l||await i.request("POST",`/question/${encodeURIComponent(M)}/reply`,{answers:[[R]]})},W=async M=>{let R=Yc(M),_=Zc(R.properties);if(!(_&&_!==l)){if((R.type==="session.next.text.delta"||R.type==="message.part.delta")&&R.properties.field!=="reasoning"&&typeof R.properties.delta=="string"){n.enqueue(Ye(R.properties.delta));return}if(R.type==="session.next.tool.called"||R.type==="message.part.updated"){let O=ne(R.properties.part)?R.properties.part:void 0;if(R.type==="message.part.updated"&&O?.type!=="tool"){n.enqueue({type:"activity"});return}let ee=typeof R.properties.tool=="string"?R.properties.tool:typeof O?.tool=="string"?O.tool:"tool";n.enqueue(On(ee,R.properties.input));return}if(R.type==="session.next.step.failed"||R.type==="session.error"){let O=ne(R.properties.error)&&typeof R.properties.error.message=="string"?R.properties.error.message:`${R.type} failed`;v&&!I&&(h?.abort(),ce(!1,"failed",O));return}if(R.type==="permission.asked"){if(d==="bypassPermissions"){let ee=typeof R.properties.id=="string"?R.properties.id:void 0;ee&&(await B(ee,"once").catch(()=>{}),T(ee));return}let O=Xc(R.properties);u={requestId:O.requestId,kind:"approval",options:O.options,actions:O.actions??[],state:O},n.enqueue(Te(O));return}if(R.type==="permission.replied"){let O=typeof R.properties.requestID=="string"?R.properties.requestID:void 0;T(O);return}if(R.type==="question.asked"){let O=ep(R.properties);u={requestId:O.requestId,kind:"question",options:O.options,actions:[],state:O},n.enqueue(Te(O));return}if(R.type==="question.replied"||R.type==="question.rejected"){let O=typeof R.properties.requestID=="string"?R.properties.requestID:void 0;T(O);return}(R.type?.startsWith("session.next.")||R.type?.startsWith("message.")||R.type==="session.status"||R.type==="session.idle")&&(jc(R)&&(A=!0),n.enqueue({type:"activity"}))}},V=()=>{k||!i||(k=!0,i.streamEvents(W,f.signal).catch(M=>{!f.signal.aborted&&v&&!I&&(h?.abort(),ce(!1,"failed",vt(M)))}).finally(()=>{k=!1}))},oe=async(M,R)=>await M.request("GET",`/session/${encodeURIComponent(R)}/message`),Ie=async(M,R,_,O,ee)=>{await M.request("POST",`/session/${encodeURIComponent(R)}/prompt_async`,Vc(_,e.model,O),{signal:ee})},lt=async(M,R,_,O)=>{let ee=Date.now(),xe=!1,ge=_,Ne,dt=0,Le,As=this.deps.turnTimeoutMs??$c;for(;;){if(O.aborted)throw new Error("wait aborted");let xu=await oe(M,R).catch(()=>{}),Fe=ai(xu),Is=Fe.count>_&&!!Fe.result;Is&&Fe.count===ge&&Fe.result===Ne?dt+=1:(dt=Is?1:0,ge=Fe.count,Ne=Fe.result);let qo=!1;try{let jt=await M.request("GET","/session/status",void 0,{signal:O,timeoutMs:Math.min(this.deps.requestTimeoutMs??li,1e4)});qo=Gc(jt,R),Le=void 0,qo||(xe=!0)}catch(jt){if(O.aborted)throw new Error("wait aborted");Le=vt(jt)}if(qo&&(xe||Fe.count>_)||A&&Fe.count>_||dt>=2&&Le)return;if(Date.now()-ee>As){let jt=Le?` Last status error: ${Le}`:"";throw new Error(`Timed out waiting for OpenCode session ${R} to become idle after ${As}ms.${jt}`)}await ua(250)}},Vt=async()=>{let M=await C();if(l){if(e.forkSession&&!m){let O=await M.request("POST",`/session/${encodeURIComponent(l)}/fork`,{});if(!O.id)throw new Error("OpenCode fork did not return a session id.");l=O.id,m=!0,c=!0}else c||(await oe(M,l),c=!0);return E(),V(),l}let R=Fc(e.model),_=await M.request("POST","/session",{...R?{model:R}:{},metadata:{client:"openclaw-code-agent"},permission:sa(d)});if(!_.id)throw new Error("OpenCode did not return a session id.");return l=_.id,c=!0,E(),V(),l},Gt=async(M,R,_=M?"completed":"failed")=>{let O=R;if(M&&i&&l){let ee=await oe(i,l).catch(()=>{});O=O??rp(ee)}ce(M,_,O)},Au=async M=>{v=!0,I=!1,x=!1,A=!1;try{let R=await C();if(b)return;let _=await Vt();if(b)return;n.enqueue(ht()),a+=1;let O=p?void 0:e.systemPrompt,ee=await oe(R,_).catch(()=>{}),xe=ai(ee).count,ge=new AbortController;h=ge,await Ie(R,_,M,O,ge.signal),p=!0,await lt(R,_,xe,ge.signal),h=void 0,I=!0,await Gt(!0)}catch(R){h=void 0,await Gt(!1,vt(R))}finally{v=!1,I=!1}},Bo=async(M,R={})=>{let _=u;if(!_||_.kind!=="question"||R.requestId&&R.requestId!==_.requestId)return!1;let O=M.trim();if(!O)return!1;let ee=_.state?.questions??[];if(ee.length>0){let xe=_.state?.activeQuestionIndex??0,ge=ee[xe];if(!ge||R.questionId&&R.questionId!==ge.id)return!1;_.answers={..._.answers,[ge.id]:{answers:[O]}};let Ne=xe+1;return Ne<ee.length?(_.state=tp(_.state,Ne,_.answers),_.options=_.state.options,n.enqueue(Te(_.state)),!0):(await j(_.requestId,np(ee,_.answers)),T(_.requestId),!0)}return await j(_.requestId,O),T(_.requestId),!0},Iu=typeof e.prompt=="string"?(async function*(){yield{type:"user",text:e.prompt,session_id:e.resumeSessionId??""}})():e.prompt;return(async()=>{try{for await(let M of Iu){if(b)break;let R=Lc(M).trim();if(R){if(u?.kind==="question"){await Bo(R);continue}if(await Au(R),b)break}}}catch(M){b||(v||(x=!1),ce(!1,"failed",vt(M)))}finally{f.abort(),await o?.close().catch(()=>{}),n.close()}})(),{messages:n.messages(),async setPermissionMode(M){l&&await(await C()).request("PATCH",`/session/${encodeURIComponent(l)}`,{permission:sa(M)}),d=M,n.enqueue(yt(M))},async submitPendingInputOption(M,R={}){let _=u;if(!_||R.requestId&&R.requestId!==_.requestId)return!1;if(_.kind==="approval"){let dt=_.actions[M],Le=dt?.kind==="approval"?dt.responseDecision:void 0;return Le?(await B(_.requestId,Le),T(_.requestId),!0):!1}let O=_.state?.questions??[],ee=_.state?.activeQuestionIndex??0,xe=O[ee];if(R.questionId&&R.questionId!==xe?.id)return!1;let ge=xe?.options[M],Ne=ge?.value??ge?.label??_.options[M];return Ne?await Bo(Ne,R):!1},async submitPendingInputText(M){return await Bo(M)},async interrupt(){if(b=!0,f.abort(),h?.abort(),v||(x=!1),ce(!1,"interrupted"),!i){await o?.close().catch(()=>{});return}if(!l)return;await i.request("POST",`/session/${encodeURIComponent(l)}/abort`).catch(()=>{})}}}buildUserMessage(e,n){return{type:"user",text:e,session_id:n}}}});function ui(t){di.set(t.name,t)}function rn(t){let e=di.get(t);if(!e)throw new Error(`Unknown agent harness: "${t}". Available: ${[...di.keys()].join(", ")}`);return e}function pa(){return rn(ae())}var di,ci=H(()=>{Ns();ia();ca();ie();di=new Map;ui(new Ln);ui(new jn);ui(new zn)});function $(t){return t.backendRef?.conversationId??t.harnessSessionId}function U(t){return t.id??t.sessionId??t.name??$(t)??t.harnessSessionId}function op(t){return t.harnessSessionId}function pe(t){let e=[U(t),$(t),op(t)].filter(n=>!!n);return[...new Set(e)]}function pi(t){return t.harnessName??t.persistedHarness??ae()}function on(t){if(t.backendRef?.kind==="codex-app-server")return"native-restore";try{return rn(pi(t)).capabilities.worktrees}catch{return"plugin-managed"}}function mi(t){return t==="native-execution"}function Qn(t){return t==="native-restore"}function ip(t){return!!(t.backendRef?.worktreePath||t.backendRef?.worktreeId)}function le(t){let e=on(t);return(mi(e)||Qn(e))&&ip(t)}var Z=H(()=>{ie();ci()});import{execFileSync as re}from"child_process";import*as ur from"fs";import{tmpdir as Op}from"os";import{dirname as Oa,join as Wp}from"path";function Np(t){try{return re("git",["rev-parse","--show-toplevel"],{cwd:t,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch{return}}function cr(t){if(process.env.OPENCLAW_WORKTREE_DIR)return process.env.OPENCLAW_WORKTREE_DIR;if(D.worktreeDir)return D.worktreeDir;if(t){let e=Np(t);if(e)return Wp(e,".worktrees")}return Op()}function Wa(t){return t.replace(/[^a-zA-Z0-9._-]/g,"-").replace(/\.{2,}/g,"-").replace(/^[-.]|[-.]$/g,"").slice(0,100).replace(/[-.]+$/,"")||"session"}function pr(t){try{let e=re("git",["-C",t,"rev-parse","--git-common-dir"],{cwd:t,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();return e&&e.endsWith("/.git")?Oa(e):void 0}catch{return}}function Lp(){if(lr!==void 0)return lr;try{return re("git",["--version"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),lr=!0,!0}catch{return lr=!1,!1}}function Ae(){if(dr!==void 0)return dr;try{return re("gh",["--version"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),dr=!0,!0}catch{return dr=!1,!1}}function ki(t){if(!Lp())return!1;try{return re("git",["rev-parse","--git-dir"],{cwd:t,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch{return!1}}function Na(t){try{let e=Bp(t);if(!e)return`${cr(t)}`,!0;let n=ur.statfsSync(e),r=n.bavail*n.bsize;return qp(r)}catch(e){return`${e instanceof Error?e.message:String(e)}`,!0}}function un(t,e){try{return re("git",["-C",t,"rev-parse","--verify",e],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch{return!1}}function Fp(t){let e=t;for(;;){if(ur.existsSync(e))return e;let n=Oa(e);if(n===e)return;e=n}}function Bp(t){return Fp(cr(t))}function qp(t){return t>=104857600}function Ce(t){let e=process.env.OPENCLAW_WORKTREE_BASE_BRANCH?.trim();if(e)return e;try{let r=re("git",["-C",t,"rev-parse","--abbrev-ref","origin/HEAD"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim().replace(/^origin\//,"");if(r)return r}catch{}try{return re("git",["-C",t,"rev-parse","--verify","main"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),"main"}catch{}try{return re("git",["-C",t,"rev-parse","--verify","master"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),"master"}catch{return"main"}}function At(t){try{let n=re("git",["-C",t,"rev-parse","--abbrev-ref","HEAD"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();if(n==="HEAD"){`${t}`;return}return n||void 0}catch{return}}function cn(t,e,n){try{let r=re("git",["-C",t,"rev-list","--count",`${n}..${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),o=parseInt(r.trim(),10);return Number.isFinite(o)?o:void 0}catch{return}}function La(t,e,n){try{let r=re("git",["-C",t,"rev-list","--left-right","--count",`${e}...${n}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim(),[o,i]=r.split(/\s+/);return{ahead:parseInt(o??"0",10)||0,behind:parseInt(i??"0",10)||0}}catch{return}}function It(t,e,n){try{return re("git",["-C",t,"merge-base","--is-ancestor",e,n],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch{return!1}}function mr(t,e,n){try{let r=re("git",["-C",t,"merge-tree","--write-tree",n,e],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim(),o=re("git",["-C",t,"rev-parse",`${n}^{tree}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();return!!r&&r===o}catch{return!1}}function he(t,e){try{return re("git",["-C",t,"branch","-D",e],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch(n){return`${e}${n instanceof Error?n.message:String(n)}`,!1}}function Fa(t,e){if(e)return e;let n;try{n=re("git",["-C",t,"remote","get-url","origin"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch{}try{let r=re("git",["-C",t,"remote","get-url","upstream"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();if(r&&r!==n){let o=r.match(/[:/]([^/]+\/[^/]+?)(?:\.git)?$/);if(o)return o[1]}}catch{}}var lr,dr,xt=H(()=>{ie()});import{execFileSync as Tt}from"child_process";import{randomBytes as Up}from"crypto";import{appendFileSync as Kp,existsSync as Ua,mkdirSync as Ba,readFileSync as Vp,rmSync as Si}from"fs";import{relative as Gp,sep as qa}from"path";function jp(t,e){return!!(t&&typeof t=="object"&&"code"in t&&t.code===e)}function Hp(t){try{return Tt("git",["-C",t,"rev-parse","--show-toplevel"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch{return}}function zp(t){return t===0?"":`-${t}-${Up(8).toString("hex")}`}function Qp(t,e){let n=Hp(t);if(!n)return;let r=Gp(n,e);if(!r||r.startsWith("..")||r.includes(`..${qa}`))return;let o=`${n}/.git/info/exclude`,i=`${r.split(qa).join("/").replace(/\/$/,"")}/`;try{let s=Ua(o)?Vp(o,"utf-8"):"";s.split(/\r?\n/).map(a=>a.trim()).some(a=>a===i||a===`/${i}`)||Kp(o,`${s.endsWith(`
12
+ `)}function gp(t){return ci(t).result}function ci(t){let e=Array.isArray(t)?t:re(t)&&Array.isArray(t.messages)?t.messages:re(t)&&Array.isArray(t.items)?t.items:[],n=[];for(let r of e){let o=re(r)&&re(r.info)?r.info:r;if(!re(o)||(typeof o.role=="string"?o.role:o.type)!=="assistant")continue;let s=Array.isArray(o.content)?o.content:[],a=re(r)&&Array.isArray(r.parts)?r.parts:[];for(let l of[...s,...a])re(l)&&l.type==="text"&&typeof l.text=="string"&&n.push(l.text)}return{count:n.length,result:n.at(-1)}}var Kc,Uc,pi,Vc,Gc,li,fa,ui,Jn,ka=H(()=>{en();Bn();Kc="OPENCLAW_OPENCODE_COMMAND",Uc=15e3,pi=6e4,Vc=15*6e4,Gc=["edit","bash","task","todowrite","external_directory"];li=class extends Error{constructor(n,r,o,i){super(`OpenCode ${n} ${r} failed with ${o}${i?`: ${i}`:""}`);this.method=n;this.path=r;this.status=o;this.body=i}method;path;status;body};fa=Promise.resolve();ui=class{constructor(e,n,r=pi){this.baseUrl=e;this.fetchImpl=n;this.requestTimeoutMs=r}baseUrl;fetchImpl;requestTimeoutMs;async request(e,n,r,o={}){let i=new AbortController,s=!1,a=!1,l=o.timeoutMs??this.requestTimeoutMs,d=`OpenCode ${e} ${n} timed out after ${l}ms.`,u=`OpenCode ${e} ${n} was aborted.`,c=()=>{s=!0,i.abort()};o.signal?.aborted?(s=!0,i.abort()):o.signal?.addEventListener("abort",c,{once:!0});try{let p=await Qn(this.fetchImpl(`${this.baseUrl}${n}`,{method:e,headers:{...ai(),...r===void 0?{}:{"content-type":"application/json"}},body:r===void 0?void 0:JSON.stringify(r),signal:i.signal}),{timeoutMs:l,timeoutMessage:d,signal:o.signal,abortMessage:u,onTimeout:()=>{a=!0,i.abort()}});if(!p.ok){let f=await Qn(p.text(),{timeoutMs:l,timeoutMessage:d,signal:o.signal,abortMessage:u,onTimeout:()=>{a=!0,i.abort()}}).catch(()=>"");throw new li(e,n,p.status,di(f))}if(p.status===204)return;let g=await Qn(p.text(),{timeoutMs:l,timeoutMessage:d,signal:o.signal,abortMessage:u,onTimeout:()=>{a=!0,i.abort()}});if(!g)return;let m=Xc(p);if(!m.includes("application/json")&&!m.includes("+json"))throw new Error(tp(e,n,m,g));try{return JSON.parse(g)}catch(f){let y=di(g);throw new Error(`OpenCode ${e} ${n} returned invalid JSON: ${Pt(f)}${y?`: ${y}`:""}`)}}catch(p){if(i.signal.aborted){if(a)throw new Error(`OpenCode ${e} ${n} timed out after ${l}ms.`);if(s)throw new Error(`OpenCode ${e} ${n} was aborted.`)}throw p}finally{o.signal?.removeEventListener("abort",c)}}async streamEvents(e,n){let r=await this.fetchImpl(`${this.baseUrl}/event`,{headers:ai(),signal:n});if(!r.ok)throw new Error(`OpenCode event stream failed with ${r.status}`);if(!r.body)return;let o=r.body.getReader(),i=new TextDecoder,s="",a=async d=>{let u=d.split(/\r?\n/).filter(c=>c.startsWith("data:")).map(c=>c.slice(5).trimStart()).join(`
13
+ `).trim();!u||u==="[DONE]"||await e(JSON.parse(u))};for(;;){let{done:d,value:u}=await o.read();if(d)break;s+=i.decode(u,{stream:!0});let c=/\r?\n\r?\n/.exec(s);for(;c;){let p=s.slice(0,c.index);s=s.slice(c.index+c[0].length),await a(p),c=/\r?\n\r?\n/.exec(s)}}let l=s.trim();l&&await a(l)}};Jn=class{constructor(e={}){this.deps=e}deps;name="opencode";backendKind="opencode-server";supportedPermissionModes=["default","plan","bypassPermissions"];capabilities={nativePendingInput:!0,nativePlanArtifacts:!1,worktrees:"plugin-managed"};launch(e){let n=new Ue,r=this.deps.fetch??fetch,o,i,s,a=e.resumeSessionId,l=0,d=e.permissionMode??"default",u,c=!e.resumeSessionId,p=!1,g=!1,m=new AbortController,f,y=!1,S=!1,R=!1,I=!1,b=!1,A=!1,k,P=new Set,F=M=>I?!1:(I=!0,n.enqueue(De(M)),!0),pe=(M,x,_)=>F({success:M,outcome:x,duration_ms:0,total_cost_usd:0,num_turns:l,result:_,session_id:a??""}),E=()=>{a&&k!==a&&(k=a,n.enqueue(yt({kind:"opencode-server",conversationId:a})))},T=M=>{M&&P.has(M)||(M&&P.add(M),n.enqueue(Ve(M)),M&&u?.requestId===M&&(u=void 0))},C=async()=>{if(i)return i;s??=(async()=>{let M=await(this.deps.createServer??ap)({cwd:e.cwd,signal:e.abortController?.signal,fetch:r,requestTimeoutMs:this.deps.requestTimeoutMs,startupTimeoutMs:this.deps.startupTimeoutMs});if(b||e.abortController?.signal.aborted)throw await M.close().catch(()=>{}),new Error("OpenCode startup was interrupted before session creation.");return o=M,i=new ui(M.baseUrl,r,this.deps.requestTimeoutMs),i})();try{return await s}catch(M){throw s=void 0,M}},q=async(M,x)=>{!i||!a||await i.request("POST",`/permission/${encodeURIComponent(M)}/reply`,{reply:x})},j=async(M,x)=>{!i||!a||await i.request("POST",`/question/${encodeURIComponent(M)}/reply`,{answers:[[x]]})},N=async M=>{let x=dp(M),_=up(x.properties);if(!(_&&_!==a)){if((x.type==="session.next.text.delta"||x.type==="message.part.delta")&&x.properties.field!=="reasoning"&&typeof x.properties.delta=="string"){n.enqueue(Xe(x.properties.delta));return}if(x.type==="session.next.tool.called"||x.type==="message.part.updated"){let W=re(x.properties.part)?x.properties.part:void 0;if(x.type==="message.part.updated"&&W?.type!=="tool"){n.enqueue({type:"activity"});return}let te=typeof x.properties.tool=="string"?x.properties.tool:typeof W?.tool=="string"?W.tool:"tool";n.enqueue(Nn(te,x.properties.input));return}if(x.type==="session.next.step.failed"||x.type==="session.error"){let W=re(x.properties.error)&&typeof x.properties.error.message=="string"?x.properties.error.message:`${x.type} failed`;S&&!R&&(f?.abort(),pe(!1,"failed",W));return}if(x.type==="permission.asked"){if(d==="bypassPermissions"){let te=typeof x.properties.id=="string"?x.properties.id:void 0;te&&(await q(te,"once").catch(()=>{}),T(te));return}let W=cp(x.properties);u={requestId:W.requestId,kind:"approval",options:W.options,actions:W.actions??[],state:W},n.enqueue(Ce(W));return}if(x.type==="permission.replied"){let W=typeof x.properties.requestID=="string"?x.properties.requestID:void 0;T(W);return}if(x.type==="question.asked"){let W=pp(x.properties);u={requestId:W.requestId,kind:"question",options:W.options,actions:[],state:W},n.enqueue(Ce(W));return}if(x.type==="question.replied"||x.type==="question.rejected"){let W=typeof x.properties.requestID=="string"?x.properties.requestID:void 0;T(W);return}(x.type?.startsWith("session.next.")||x.type?.startsWith("message.")||x.type==="session.status"||x.type==="session.idle")&&(op(x)&&(A=!0),n.enqueue({type:"activity"}))}},V=()=>{y||!i||(y=!0,i.streamEvents(N,m.signal).catch(M=>{!m.signal.aborted&&S&&!R&&(f?.abort(),pe(!1,"failed",Pt(M)))}).finally(()=>{y=!1}))},ie=async(M,x)=>await M.request("GET",`/session/${encodeURIComponent(x)}/message`),xe=async(M,x,_,W,te)=>{await M.request("POST",`/session/${encodeURIComponent(x)}/prompt_async`,np(_,e.model,W),{signal:te})},ut=async(M,x,_,W)=>{let te=Date.now(),Te=!1,he=_,Be,ct=0,Fe,$s=this.deps.turnTimeoutMs??Vc;for(;;){if(W.aborted)throw new Error("wait aborted");let Bu=await ie(M,x).catch(()=>{}),qe=ci(Bu),Es=qe.count>_&&!!qe.result;Es&&qe.count===he&&qe.result===Be?ct+=1:(ct=Es?1:0,he=qe.count,Be=qe.result);let Go=!1;try{let Ht=await M.request("GET","/session/status",void 0,{signal:W,timeoutMs:Math.min(this.deps.requestTimeoutMs??pi,1e4)});Go=rp(Ht,x),Fe=void 0,Go||(Te=!0)}catch(Ht){if(W.aborted)throw new Error("wait aborted");Fe=Pt(Ht)}if(Go&&(Te||qe.count>_)||A&&qe.count>_||ct>=2&&Fe)return;if(Date.now()-te>$s){let Ht=Fe?` Last status error: ${Fe}`:"";throw new Error(`Timed out waiting for OpenCode session ${x} to become idle after ${$s}ms.${Ht}`)}await ya(250)}},Gt=async()=>{let M=await C();if(a){if(e.forkSession&&!p){let W=await M.request("POST",`/session/${encodeURIComponent(a)}/fork`,{});if(!W.id)throw new Error("OpenCode fork did not return a session id.");a=W.id,p=!0,c=!0}else c||(await ie(M,a),c=!0);return E(),V(),a}let x=Yc(e.model),_=await M.request("POST","/session",{...x?{model:x}:{},metadata:{client:"openclaw-code-agent"},permission:ma(d)});if(!_.id)throw new Error("OpenCode did not return a session id.");return a=_.id,c=!0,E(),V(),a},jt=async(M,x,_=M?"completed":"failed")=>{let W=x;if(M&&i&&a){let te=await ie(i,a).catch(()=>{});W=W??gp(te)}pe(M,_,W)},Nu=async M=>{S=!0,R=!1,I=!1,A=!1;try{let x=await C();if(b)return;let _=await Gt();if(b)return;n.enqueue(kt()),l+=1;let W=g?void 0:e.systemPrompt,te=await ie(x,_).catch(()=>{}),Te=ci(te).count,he=new AbortController;f=he,await xe(x,_,M,W,he.signal),g=!0,await ut(x,_,Te,he.signal),f=void 0,R=!0,await jt(!0)}catch(x){f=void 0,await jt(!1,Pt(x))}finally{S=!1,R=!1}},Vo=async(M,x={})=>{let _=u;if(!_||_.kind!=="question"||x.requestId&&x.requestId!==_.requestId)return!1;let W=M.trim();if(!W)return!1;let te=_.state?.questions??[];if(te.length>0){let Te=_.state?.activeQuestionIndex??0,he=te[Te];if(!he||x.questionId&&x.questionId!==he.id)return!1;_.answers={..._.answers,[he.id]:{answers:[W]}};let Be=Te+1;return Be<te.length?(_.state=mp(_.state,Be,_.answers),_.options=_.state.options,n.enqueue(Ce(_.state)),!0):(await j(_.requestId,fp(te,_.answers)),T(_.requestId),!0)}return await j(_.requestId,W),T(_.requestId),!0},Lu=typeof e.prompt=="string"?(async function*(){yield{type:"user",text:e.prompt,session_id:e.resumeSessionId??""}})():e.prompt;return(async()=>{try{for await(let M of Lu){if(b)break;let x=Jc(M).trim();if(x){if(u?.kind==="question"){await Vo(x);continue}if(await Nu(x),b)break}}}catch(M){b||(S||(I=!1),pe(!1,"failed",Pt(M)))}finally{m.abort(),await o?.close().catch(()=>{}),n.close()}})(),{messages:n.messages(),async setPermissionMode(M){a&&await(await C()).request("PATCH",`/session/${encodeURIComponent(a)}`,{permission:ma(M)}),d=M,n.enqueue(St(M))},async submitPendingInputOption(M,x={}){let _=u;if(!_||x.requestId&&x.requestId!==_.requestId)return!1;if(_.kind==="approval"){let ct=_.actions[M],Fe=ct?.kind==="approval"?ct.responseDecision:void 0;return Fe?(await q(_.requestId,Fe),T(_.requestId),!0):!1}let W=_.state?.questions??[],te=_.state?.activeQuestionIndex??0,Te=W[te];if(x.questionId&&x.questionId!==Te?.id)return!1;let he=Te?.options[M],Be=he?.value??he?.label??_.options[M];return Be?await Vo(Be,x):!1},async submitPendingInputText(M){return await Vo(M)},async interrupt(){if(b=!0,m.abort(),f?.abort(),S||(I=!1),pe(!1,"interrupted"),!i){await o?.close().catch(()=>{});return}if(!a)return;await i.request("POST",`/session/${encodeURIComponent(a)}/abort`).catch(()=>{})}}}buildUserMessage(e,n){return{type:"user",text:e,session_id:n}}}});function fi(t){mi.set(t.name,t)}function on(t){let e=mi.get(t);if(!e)throw new Error(`Unknown agent harness: "${t}". Available: ${[...mi.keys()].join(", ")}`);return e}function Sa(){return on(le())}var mi,gi=H(()=>{Vs();pa();ka();se();mi=new Map;fi(new Fn);fi(new zn);fi(new Jn)});function $(t){return t.backendRef?.conversationId??t.harnessSessionId}function U(t){return t.id??t.sessionId??t.name??$(t)??t.harnessSessionId}function hp(t){return t.harnessSessionId}function me(t){let e=[U(t),$(t),hp(t)].filter(n=>!!n);return[...new Set(e)]}function hi(t){return t.harnessName??t.persistedHarness??le()}function sn(t){if(t.backendRef?.kind==="codex-app-server")return"native-restore";try{return on(hi(t)).capabilities.worktrees}catch{return"plugin-managed"}}function yi(t){return t==="native-execution"}function Yn(t){return t==="native-restore"}function yp(t){return!!(t.backendRef?.worktreePath||t.backendRef?.worktreeId)}function de(t){let e=sn(t);return(yi(e)||Yn(e))&&yp(t)}var X=H(()=>{se();gi()});import{execFileSync as oe}from"child_process";import*as pr from"fs";import{tmpdir as Hp}from"os";import{dirname as Ka,join as zp}from"path";function Qp(t){try{return oe("git",["rev-parse","--show-toplevel"],{cwd:t,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch{return}}function mr(t){if(process.env.OPENCLAW_WORKTREE_DIR)return process.env.OPENCLAW_WORKTREE_DIR;if(D.worktreeDir)return D.worktreeDir;if(t){let e=Qp(t);if(e)return zp(e,".worktrees")}return Hp()}function Ua(t){return t.replace(/[^a-zA-Z0-9._-]/g,"-").replace(/\.{2,}/g,"-").replace(/^[-.]|[-.]$/g,"").slice(0,100).replace(/[-.]+$/,"")||"session"}function fr(t){try{let e=oe("git",["-C",t,"rev-parse","--git-common-dir"],{cwd:t,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();return e&&e.endsWith("/.git")?Ka(e):void 0}catch{return}}function Jp(){if(ur!==void 0)return ur;try{return oe("git",["--version"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),ur=!0,!0}catch{return ur=!1,!1}}function Ie(){if(cr!==void 0)return cr;try{return oe("gh",["--version"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),cr=!0,!0}catch{return cr=!1,!1}}function Pi(t){if(!Jp())return!1;try{return oe("git",["rev-parse","--git-dir"],{cwd:t,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch{return!1}}function Va(t){try{let e=Zp(t);if(!e)return`${mr(t)}`,!0;let n=pr.statfsSync(e),r=n.bavail*n.bsize;return Xp(r)}catch(e){return`${e instanceof Error?e.message:String(e)}`,!0}}function cn(t,e){try{return oe("git",["-C",t,"rev-parse","--verify",e],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch{return!1}}function Yp(t){let e=t;for(;;){if(pr.existsSync(e))return e;let n=Ka(e);if(n===e)return;e=n}}function Zp(t){return Yp(mr(t))}function Xp(t){return t>=104857600}function Me(t){let e=process.env.OPENCLAW_WORKTREE_BASE_BRANCH?.trim();if(e)return e;try{let r=oe("git",["-C",t,"rev-parse","--abbrev-ref","origin/HEAD"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim().replace(/^origin\//,"");if(r)return r}catch{}try{return oe("git",["-C",t,"rev-parse","--verify","main"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),"main"}catch{}try{return oe("git",["-C",t,"rev-parse","--verify","master"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),"master"}catch{return"main"}}function xt(t){try{let n=oe("git",["-C",t,"rev-parse","--abbrev-ref","HEAD"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();if(n==="HEAD"){`${t}`;return}return n||void 0}catch{return}}function pn(t,e,n){try{let r=oe("git",["-C",t,"rev-list","--count",`${n}..${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),o=parseInt(r.trim(),10);return Number.isFinite(o)?o:void 0}catch{return}}function Ga(t,e,n){try{let r=oe("git",["-C",t,"rev-list","--left-right","--count",`${e}...${n}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim(),[o,i]=r.split(/\s+/);return{ahead:parseInt(o??"0",10)||0,behind:parseInt(i??"0",10)||0}}catch{return}}function Tt(t,e,n){try{return oe("git",["-C",t,"merge-base","--is-ancestor",e,n],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch{return!1}}function gr(t,e,n){try{let r=oe("git",["-C",t,"merge-tree","--write-tree",n,e],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim(),o=oe("git",["-C",t,"rev-parse",`${n}^{tree}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();return!!r&&r===o}catch{return!1}}function ye(t,e){try{return oe("git",["-C",t,"branch","-D",e],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch(n){return`${e}${n instanceof Error?n.message:String(n)}`,!1}}function ja(t,e){if(e)return e;let n;try{n=oe("git",["-C",t,"remote","get-url","origin"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch{}try{let r=oe("git",["-C",t,"remote","get-url","upstream"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();if(r&&r!==n){let o=r.match(/[:/]([^/]+\/[^/]+?)(?:\.git)?$/);if(o)return o[1]}}catch{}}var ur,cr,Ct=H(()=>{se()});import{execFileSync as Mt}from"child_process";import{randomBytes as em}from"crypto";import{appendFileSync as tm,existsSync as Qa,mkdirSync as Ha,readFileSync as nm,rmSync as bi}from"fs";import{relative as rm,sep as za}from"path";function om(t,e){return!!(t&&typeof t=="object"&&"code"in t&&t.code===e)}function im(t){try{return Mt("git",["-C",t,"rev-parse","--show-toplevel"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch{return}}function sm(t){return t===0?"":`-${t}-${em(8).toString("hex")}`}function am(t,e){let n=im(t);if(!n)return;let r=rm(n,e);if(!r||r.startsWith("..")||r.includes(`..${za}`))return;let o=`${n}/.git/info/exclude`,i=`${r.split(za).join("/").replace(/\/$/,"")}/`;try{let s=Qa(o)?nm(o,"utf-8"):"";s.split(/\r?\n/).map(l=>l.trim()).some(l=>l===i||l===`/${i}`)||tm(o,`${s.endsWith(`
14
14
  `)||s.length===0?"":`
15
15
  `}${i}
16
- `,"utf-8")}catch(s){`${i}${o}${s instanceof Error?s.message:String(s)}`}}function vi(t,e,n={}){let r=Wa(e),o=cr(t);Qp(t,o),Ba(o,{recursive:!0});let i=n.allowExistingBranch===!0,s,l,a=10,d=!1;for(let c=0;c<a;c++){let m=zp(c),p=`${o}/openclaw-worktree-${r}${m}`,f=`agent/${r}${m}`;if(!i&&un(t,f))continue;let h=!1;do{h=!1;try{Ba(p,{recursive:!1}),s=p,l=f;break}catch(k){if(jp(k,"EEXIST")){if(i&&c===0&&!d)try{Si(p,{recursive:!0,force:!0}),d=!0,h=!0}catch(v){throw new Error(`Failed to recreate existing worktree branch ${f}: could not clear blocked path ${p}: ${v instanceof Error?v.message:String(v)}`)}else if(i&&c===0)throw new Error(`Failed to recreate existing worktree branch ${f}: path ${p} remains blocked after one cleanup attempt`);continue}throw k}}while(h);if(s&&l)break}if(!s||!l)throw new Error(`Failed to create unique worktree directory and branch after ${a} attempts`);let u=un(t,l);try{u?Tt("git",["-C",t,"worktree","add",s,l],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}):Tt("git",["-C",t,"worktree","add","-b",l,s],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(c){try{Si(s,{recursive:!0,force:!0})}catch{}throw c}return s}function tt(t){if(!Ua(t))return[];try{let e=Tt("git",["-C",t,"status","--porcelain","--untracked-files=all"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();return e?e.split(`
17
- `).map(n=>n.trim()).filter(Boolean):[]}catch{return[]}}function nt(t){return tt(t).length>0}function ue(t,e,n={}){let r=n.destructive===!0,o=tt(e);if(o.length>0&&!r)return`${e}${o[0]}`,!1;try{return Tt("git",["-C",t,"worktree","remove",...r?["--force"]:[],e],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch(i){if(`${e}${i instanceof Error?i.message:String(i)}`,!r)return!1;try{return Si(e,{recursive:!0,force:!0}),`${e}`,!0}catch(s){return console.error(`[worktree] Both git worktree remove and rmSync failed for ${e}: ${s instanceof Error?s.message:String(s)}`),!1}}}function fr(t){try{Tt("git",["-C",t,"worktree","prune"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(e){let n=e instanceof Error?e.message.split(/\r?\n/,1)[0]:String(e);`${t}${n}`}}var Pi=H(()=>{xt()});import{execFileSync as Q}from"child_process";import{existsSync as Jp}from"fs";function Ct(t){return(t.warnings??[]).filter(e=>!(t.stashPopConflict&&e.startsWith("Failed to pop auto-stash after merge"))).map(e=>`Recovery warning: ${e}`)}function Me(t,e){let n=Ct(e);return n.length===0?t:`${t}
16
+ `,"utf-8")}catch(s){`${i}${o}${s instanceof Error?s.message:String(s)}`}}function Ri(t,e,n={}){let r=Ua(e),o=mr(t);am(t,o),Ha(o,{recursive:!0});let i=n.allowExistingBranch===!0,s,a,l=10,d=!1;for(let c=0;c<l;c++){let p=sm(c),g=`${o}/openclaw-worktree-${r}${p}`,m=`agent/${r}${p}`;if(!i&&cn(t,m))continue;let f=!1;do{f=!1;try{Ha(g,{recursive:!1}),s=g,a=m;break}catch(y){if(om(y,"EEXIST")){if(i&&c===0&&!d)try{bi(g,{recursive:!0,force:!0}),d=!0,f=!0}catch(S){throw new Error(`Failed to recreate existing worktree branch ${m}: could not clear blocked path ${g}: ${S instanceof Error?S.message:String(S)}`)}else if(i&&c===0)throw new Error(`Failed to recreate existing worktree branch ${m}: path ${g} remains blocked after one cleanup attempt`);continue}throw y}}while(f);if(s&&a)break}if(!s||!a)throw new Error(`Failed to create unique worktree directory and branch after ${l} attempts`);let u=cn(t,a);try{u?Mt("git",["-C",t,"worktree","add",s,a],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}):Mt("git",["-C",t,"worktree","add","-b",a,s],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(c){try{bi(s,{recursive:!0,force:!0})}catch{}throw c}return s}function rt(t){if(!Qa(t))return[];try{let e=Mt("git",["-C",t,"status","--porcelain","--untracked-files=all"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();return e?e.split(`
17
+ `).map(n=>n.trim()).filter(Boolean):[]}catch{return[]}}function ot(t){return rt(t).length>0}function ce(t,e,n={}){let r=n.destructive===!0,o=rt(e);if(o.length>0&&!r)return`${e}${o[0]}`,!1;try{return Mt("git",["-C",t,"worktree","remove",...r?["--force"]:[],e],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch(i){if(`${e}${i instanceof Error?i.message:String(i)}`,!r)return!1;try{return bi(e,{recursive:!0,force:!0}),`${e}`,!0}catch(s){return console.error(`[worktree] Both git worktree remove and rmSync failed for ${e}: ${s instanceof Error?s.message:String(s)}`),!1}}}function hr(t){try{Mt("git",["-C",t,"worktree","prune"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(e){let n=e instanceof Error?e.message.split(/\r?\n/,1)[0]:String(e);`${t}${n}`}}var Ai=H(()=>{Ct()});import{execFileSync as Q}from"child_process";import{existsSync as lm}from"fs";function _t(t){return(t.warnings??[]).filter(e=>!(t.stashPopConflict&&e.startsWith("Failed to pop auto-stash after merge"))).map(e=>`Recovery warning: ${e}`)}function _e(t,e){let n=_t(e);return n.length===0?t:`${t}
18
18
  ${n.map(r=>`⚠️ ${r}`).join(`
19
- `)}`}function gr(t){return t instanceof Error?t.message:String(t)}function Oe(t,e,n){try{let r=Q("git",["-C",t,"rev-list","--count",`${n}..${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),o=parseInt(r.trim(),10),s=Q("git",["-C",t,"diff","--shortstat",`${n}...${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim(),l=0,a=0,d=0,u=s.match(/(\d+)\s+files?\s+changed/);u&&(l=parseInt(u[1],10));let c=s.match(/(\d+)\s+insertions?\(/);c&&(a=parseInt(c[1],10));let m=s.match(/(\d+)\s+deletions?\(/);m&&(d=parseInt(m[1],10));let f=Q("git",["-C",t,"diff","--name-only","--diff-filter=ACMR",`${n}...${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim().split(`
20
- `).map(v=>v.trim()).filter(Boolean),k=Q("git",["-C",t,"log",`${n}..${e}`,"--format=%h|%s|%an","-n","5"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim().split(`
21
- `).filter(Boolean).map(v=>{let[I,x,b]=v.split("|");return{hash:I||"",message:x||"",author:b||""}});return{commits:o,filesChanged:l,insertions:a,deletions:d,changedFiles:f,commitMessages:k}}catch(r){`${r instanceof Error?r.message:String(r)}`;return}}function hr(t,e,n="origin"){try{return Q("git",["-C",t,"push",n,e],{timeout:6e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch(r){return`${e}${r instanceof Error?r.message:String(r)}`,!1}}function Ka(t){try{return Q("git",["-C",t,"status","--porcelain"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).split(`
22
- `).some(n=>n.length>0&&!n.startsWith("??")&&!n.startsWith("!!"))}catch{return!1}}function yr(t,e,n,r="merge",o){let i=!1,s,l=[],a=c=>l.length>0?{...c,warnings:[...l]}:c,d=(c,m)=>{l.push(`${c}: ${gr(m)}`)},u=c=>{if(i)try{Q("git",["-C",c,"stash","pop"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(m){d("Failed to pop auto-stash during recovery",m)}};try{if(r==="squash"){if(Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),Ka(t)){let h;try{h=Q("git",["-C",t,"stash","push","-m",`pre-merge stash before ${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(k){return a({success:!1,dirtyError:!0,error:`Auto-stash failed: ${gr(k)}. Commit or stash changes manually, then retry.`})}if(!h.includes("No local changes to save")){i=!0;try{s=Q("git",["-C",t,"stash","list","--format=%gd","-n","1"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch(k){d("Failed to determine auto-stash ref",k)}}}Q("git",["-C",t,"merge","--squash",e],{timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),Q("git",["-C",t,"commit","-m",`Squash merge ${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]});let f=!1;if(i)try{Q("git",["-C",t,"stash","pop"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(h){f=!0,d("Failed to pop auto-stash after merge",h)}return a({success:!0,stashed:i||void 0,stashRef:s,stashPopConflict:f||void 0})}let c=o&&Jp(o),m=c?o:t;if(c||Q("git",["-C",t,"checkout",e],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),Ka(t)){let f;try{f=Q("git",["-C",t,"stash","push","-m",`pre-merge stash before ${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(h){try{Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(k){d(`Failed to check out ${n} after auto-stash failure`,k)}return a({success:!1,dirtyError:!0,error:`Auto-stash failed: ${gr(h)}. Commit or stash changes manually, then retry.`})}if(!f.includes("No local changes to save")){i=!0;try{s=Q("git",["-C",t,"stash","list","--format=%gd","-n","1"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch(h){d("Failed to determine auto-stash ref",h)}}}try{Q("git",["-C",m,"rebase",n],{timeout:6e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch{try{Q("git",["-C",m,"rebase","--abort"],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(f){d("Failed to abort rebase during recovery",f)}try{Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(f){d(`Failed to check out ${n} during recovery`,f)}return u(t),a({success:!1,rebaseConflict:!0,stashed:i||void 0,stashRef:s,error:[`Rebase of ${e} onto ${n} hit conflicts.`,"To resolve manually:",` cd ${m}`,` git rebase ${n}`," # resolve conflicts in each file, then:"," git add <file>"," git rebase --continue"," # repeat until rebase finishes, then re-run agent_merge."].join(`
23
- `)})}Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),Q("git",["-C",t,"merge","--ff-only",e],{timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]});let p=!1;if(i)try{Q("git",["-C",t,"stash","pop"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(f){p=!0,d("Failed to pop auto-stash after merge",f)}return a({success:!0,fastForward:!0,stashed:i||void 0,stashRef:s,stashPopConflict:p||void 0})}catch(c){try{Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(m){d(`Failed to check out ${n} during recovery`,m)}return u(t),a({success:!1,error:gr(c),stashed:i||void 0,stashRef:s})}}var Va=H(()=>{});import{execFileSync as pn}from"child_process";function Ga(t){return/pull request already exists/i.test(t)||/createPullRequest/i.test(t)&&/already exists/i.test(t)}function ja(t,e,n){let r=Mt(t,e,n);if(r.exists&&r.state==="open"&&r.url)return{success:!0,prUrl:r.url,warnings:["A PR already exists for this branch; reused the existing open PR."]};if(r.exists&&r.url)return{success:!1,error:`A PR already exists for ${e}, but it is ${r.state}: ${r.url}`}}function Ha(t){try{return pn("git",["-C",t,"remote","get-url","origin"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim().match(/[:/]([^/]+)\/[^/]+(?:\.git)?$/)?.[1]}catch{return}}function Yp(t,e,n){if(!n)return e;let r=Ha(t);return r?`${r}:${e}`:e}function za(t,e,n,r,o,i,s={}){if(!Ae())return{success:!1,error:"GitHub CLI (gh) is not available"};let l;try{return l=["pr","create","--base",n],(s.draft??!0)&&l.push("--draft"),i&&l.push("--repo",i),l.push("--head",Yp(t,e,i)),r&&o?l.push("--title",r,"--body",o):l.push("--fill-verbose"),{success:!0,prUrl:pn("gh",l,{cwd:t,timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()}}catch(a){let d=a instanceof Error?a.message:String(a);if(Ga(d))return ja(t,e,i)??{success:!1,error:d};if((s.draft??!0)&&l&&/draft/i.test(d))try{let u=l.filter(p=>p!=="--draft");return{success:!0,prUrl:pn("gh",u,{cwd:t,timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim(),warnings:["Target repo does not support draft PRs; created as regular (non-draft) PR instead."]}}catch(u){let c=u instanceof Error?u.message:String(u);return Ga(c)?ja(t,e,i)??{success:!1,error:`Draft PR creation failed (${d}); non-draft retry also failed: ${c}`}:{success:!1,error:`Draft PR creation failed (${d}); non-draft retry also failed: ${c}`}}return{success:!1,error:d}}}function Mt(t,e,n){if(!Ae())return{exists:!1,state:"none"};try{let r=["pr","list","--head",e,"--state","all","--json","url,number,title,state,headRepositoryOwner,headRefName"];n&&r.push("--repo",n);let i=pn("gh",r,{cwd:t,timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();if(!i)return{exists:!1,state:"none"};let s=JSON.parse(i),l=n?Ha(t)?.toLowerCase():void 0,a=l?s.find(c=>c.headRefName===e&&c.headRepositoryOwner?.login?.toLowerCase()===l):s[0];if(!a)return{exists:!1,state:"none"};let d=a.state.toLowerCase();return{exists:!0,state:d==="open"?"open":d==="merged"?"merged":d==="closed"?"closed":"none",url:a.url,number:a.number,title:a.title}}catch(r){return`${e}${r instanceof Error?r.message:String(r)}`,{exists:!1,state:"none"}}}function Qa(t,e,n,r){if(!Ae())return!1;try{let o=["pr","comment",String(e),"--body",n];return r&&o.push("--repo",r),pn("gh",o,{cwd:t,timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch(o){return`${e}${o instanceof Error?o.message:String(o)}`,!1}}function rt(t){if(t.kind==="merge"){let e=t.filesChanged!==void 0?` (${t.filesChanged} files, +${t.insertions??0}/-${t.deletions??0})`:"";return`✅ Merged: ${t.branch} → ${t.base??"main"}${e}`}return t.kind==="pr-updated"?`✅ PR updated: ${t.prUrl??""}`:t.targetRepo?`✅ PR opened against ${t.targetRepo}: ${t.prUrl??""}`:`✅ PR opened: ${t.prUrl??""}`}var wi=H(()=>{xt()});import{existsSync as bi}from"fs";function Ja(){return new Date().toISOString()}function Zp(t){return t.worktreeLifecycle??{state:t.worktreePath||t.worktreeBranch?"provisioned":"none",updatedAt:Ja(),baseBranch:t.worktreeBaseBranch,targetRepo:t.worktreePrTargetRepo,pushRemote:t.worktreePushRemote}}function Xp(t){let e=Ya(t);return t.worktreeLifecycle?.baseBranch??t.worktreeBaseBranch??(e&&bi(e)?Ce(e):void 0)}function Ya(t){return typeof t.workdir=="string"&&t.workdir.length>0?t.workdir:void 0}function Ve(t,e={}){let n=Zp(t),r=Ja(),o=new Set,i=Ya(t),s=!!(i&&bi(i)),l=!!(t.worktreePath&&bi(t.worktreePath)),a=t.worktreeBranch,d=Xp(t),u=!1,c=!1,m=!1,p=!1,f,h,k=t.worktreePrUrl?"open":"none",v=t.worktreePrUrl,I=t.worktreePrNumber;if(s||o.add("repo_missing"),a||o.add("branch_missing"),!l&&t.worktreePath&&o.add("worktree_missing"),e.activeSession&&o.add("active_session"),n.state==="pending_decision"&&o.add("pending_decision"),n.state==="merge_conflict_resolving"&&o.add("merge_conflict_resolving"),s&&i&&a&&(u=un(i,a),u||o.add("branch_missing")),l&&t.worktreePath&&(c=nt(t.worktreePath),c&&o.add("dirty_worktree_entries")),s&&i&&u&&a&&d){let E=La(i,a,d);f=E?.ahead,h=E?.behind,m=It(i,a,d),m?o.add("topology_merged"):(p=mr(i,a,d),p&&o.add("merge_noop_content_already_on_base"),!p&&(f??0)>0&&o.add("unique_content"))}else d||o.add("base_branch_missing");if(e.includePrSync&&s&&i&&a){let E=Mt(i,a,t.worktreePrTargetRepo??n.targetRepo);k=E.state,v=E.url??v,I=E.number??I}k==="open"&&o.add("pr_open"),k==="merged"&&!m&&!p&&o.add("pr_merged_not_reflected_locally");let x;m?x="merged":p&&(x="released");let b=e.activeSession||c,A=n.state;!b&&x?A=x:!u&&n.state==="pending_decision"&&(A="cleanup_failed");let y=A==="merged"||A==="released",w=e.activeSession||c||!y&&n.state==="pending_decision"||n.state==="merge_conflict_resolving"||n.state==="pr_open"||k==="open"||o.has("pr_merged_not_reflected_locally"),F=!w&&(A==="merged"||A==="released"||n.state==="dismissed"||n.state==="no_change"),ce={checkedAt:r,repoExists:s,branchExists:u,worktreeExists:l,activeSession:e.activeSession===!0,dirtyTracked:c,topologyMerged:m,releaseNoopMerge:p,branchAheadCount:f,baseAheadCount:h,prState:k,prUrl:v,prNumber:I,reasons:[...o]};return{lifecycle:n,evidence:ce,derivedState:A,cleanupSafe:F,preserve:w,reasons:[...o]}}var mn=H(()=>{xt();wi();Pi()});var ye=H(()=>{xt();Pi();Va();wi();mn()});function xr(t,e){return{...e,baseBranch:e.baseBranch??t.worktreeBaseBranch,targetRepo:e.targetRepo??t.worktreePrTargetRepo,pushRemote:e.pushRemote??t.worktreePushRemote}}function Tr(t,e={}){let n=e.updatedAt??new Date().toISOString(),r={pendingWorktreeDecisionSince:e.pendingSince??n,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,lifecycle:"awaiting_worktree_decision",worktreeState:"pending_decision",worktreeLifecycle:xr(t,{state:"pending_decision",updatedAt:n,notes:e.notes})};return e.clearResolverSessionId&&(r.autoMergeResolverSessionId=void 0),r}function Pl(t,e,n,r={}){let o=r.updatedAt??new Date().toISOString();return{autoMergeConflictResolutionAttemptCount:n,autoMergeResolverSessionId:e,pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,lifecycle:"terminal",worktreeState:"merge_conflict_resolving",worktreeLifecycle:xr(t,{state:"merge_conflict_resolving",updatedAt:o,notes:r.notes})}}function $t(t,e={}){let n=e.updatedAt??new Date().toISOString(),r=e.resolvedAt??n,o={worktreeMerged:!0,worktreeMergedAt:e.mergedAt??r,lifecycle:"terminal",worktreeState:"merged",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeLifecycle:xr(t,{state:"merged",updatedAt:n,resolvedAt:r,resolutionSource:e.resolutionSource??"agent_merge"})};return e.clearResolverSessionId&&(o.autoMergeResolverSessionId=void 0),o}function wl(t,e){let n=e.updatedAt??new Date().toISOString(),r={worktreePrUrl:e.prUrl,lifecycle:"terminal",worktreeState:"pr_open",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeLifecycle:xr(t,{state:"pr_open",updatedAt:n,resolutionSource:"agent_pr",baseBranch:e.baseBranch,targetRepo:e.targetRepo})};return e.prNumber!==void 0&&(r.worktreePrNumber=e.prNumber),e.disposition!==void 0&&(r.worktreeDisposition=e.disposition),r}var kn=H(()=>{});function Et(t,e){let n=t.resolve(e),r=t.getPersistedSession(e),o=n?U(n):r?U(r):void 0;return{activeSession:n,persistedSession:r,persistedRef:o,sessionName:n?.name??r?.name??e,prompt:n?.prompt??r?.prompt,worktreePath:n?.worktreePath??r?.worktreePath,originalWorkdir:n?.originalWorkdir??r?.workdir,branchName:n?.worktreeBranch??r?.worktreeBranch,notificationTarget:n??(r?{id:o??e,name:r.name,harnessSessionId:r.harnessSessionId,backendRef:r.backendRef,route:r.route,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey,goalTaskId:r.goalTaskId}:void 0)}}function Sn(t){return[...t.persistedSession?pe(t.persistedSession):[],...t.activeSession?pe(t.activeSession):[]].filter((e,n,r)=>r.indexOf(e)===n)}function Km(t,e){let n=[e.id,e.backendConversationId,e.harnessSessionId,e.name],r,o;for(let i of n)if(i&&(r??=t.resolve(i),o??=t.getPersistedSession(i),r&&o))break;return{activeSession:r,persistedSession:o}}function Cr(t,e,n={}){let{activeSession:r,persistedSession:o}=Km(t,e),i=Ve({workdir:e.workdir,worktreePath:e.worktreePath,worktreeBranch:e.worktreeBranch,worktreeBaseBranch:n.baseBranch??o?.worktreeBaseBranch,worktreePrTargetRepo:o?.worktreePrTargetRepo,worktreePushRemote:o?.worktreePushRemote,worktreePrUrl:o?.worktreePrUrl,worktreePrNumber:o?.worktreePrNumber,worktreeLifecycle:o?.worktreeLifecycle},{activeSession:!!(r&&(r.status==="starting"||r.status==="running")),includePrSync:!!(o?.worktreeLifecycle?.state==="pr_open"||o?.worktreePrUrl)});return{activeSession:r,persistedSession:o,resolvedLifecycle:i}}function Mr(t){let e=t.list("all").filter(o=>o.worktreePath),n=t.listPersistedSessions().filter(o=>o.worktreePath),r=new Map;for(let o of n){if(!o.worktreePath)continue;let i=$(o),s=o.sessionId??i??o.harnessSessionId;s&&r.set(s,{id:o.sessionId??i??o.harnessSessionId,name:o.name,worktreePath:o.worktreePath,worktreeBranch:o.worktreeBranch,worktreeStrategy:o.worktreeStrategy,workdir:o.workdir,worktreeMerged:o.worktreeMerged,worktreeMergedAt:o.worktreeMergedAt,worktreePrUrl:o.worktreePrUrl,backendConversationId:i,harnessSessionId:o.harnessSessionId})}for(let o of e)o.worktreePath&&r.set(o.id,{id:o.id,name:o.name,worktreePath:o.worktreePath,worktreeBranch:o.worktreeBranch,worktreeStrategy:o.worktreeStrategy,workdir:o.originalWorkdir??o.workdir,worktreeMerged:void 0,worktreeMergedAt:void 0,worktreePrUrl:void 0,backendConversationId:$(o),harnessSessionId:o.harnessSessionId});return Array.from(r.values())}function _r(t,e){return t.id===e||t.name===e||t.backendConversationId===e||t.harnessSessionId===e}function it(t){switch(t){case"none":return"none";case"provisioned":return"active";case"pending_decision":return"needs decision";case"merge_conflict_resolving":return"conflict resolving";case"pr_open":return"pr open";case"merged":return"merged";case"released":return"released";case"dismissed":return"dismissed";case"no_change":return"no change";case"cleanup_failed":return"cleanup failed";default:return t}}function $r(t){switch(t){case"active_session":return"active session";case"pending_decision":return"pending decision";case"merge_conflict_resolving":return"conflict resolving";case"dirty_tracked_changes":case"dirty_worktree_entries":return"dirty worktree";case"unique_content":return"still has unique content";case"topology_merged":return"merged by ancestry";case"merge_noop_content_already_on_base":return"content already on base";case"pr_open":return"PR open";case"pr_merged_not_reflected_locally":return"merged PR not reflected locally";case"repo_missing":return"repo missing";case"branch_missing":return"branch missing";case"worktree_missing":return"worktree missing";case"base_branch_missing":return"base branch missing";default:return t.replaceAll("_"," ")}}var vn=H(()=>{Z();mn()});function Rl(t,e={preserveBlankLines:!0}){return t?.replace(/\r\n/g,`
19
+ `)}`}function yr(t){return t instanceof Error?t.message:String(t)}function We(t,e,n){try{let r=Q("git",["-C",t,"rev-list","--count",`${n}..${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),o=parseInt(r.trim(),10),s=Q("git",["-C",t,"diff","--shortstat",`${n}...${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim(),a=0,l=0,d=0,u=s.match(/(\d+)\s+files?\s+changed/);u&&(a=parseInt(u[1],10));let c=s.match(/(\d+)\s+insertions?\(/);c&&(l=parseInt(c[1],10));let p=s.match(/(\d+)\s+deletions?\(/);p&&(d=parseInt(p[1],10));let m=Q("git",["-C",t,"diff","--name-only","--diff-filter=ACMR",`${n}...${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim().split(`
20
+ `).map(S=>S.trim()).filter(Boolean),y=Q("git",["-C",t,"log",`${n}..${e}`,"--format=%h|%s|%an","-n","5"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim().split(`
21
+ `).filter(Boolean).map(S=>{let[R,I,b]=S.split("|");return{hash:R||"",message:I||"",author:b||""}});return{commits:o,filesChanged:a,insertions:l,deletions:d,changedFiles:m,commitMessages:y}}catch(r){`${r instanceof Error?r.message:String(r)}`;return}}function kr(t,e,n="origin"){try{return Q("git",["-C",t,"push",n,e],{timeout:6e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch(r){return`${e}${r instanceof Error?r.message:String(r)}`,!1}}function Ja(t){try{return Q("git",["-C",t,"status","--porcelain"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).split(`
22
+ `).some(n=>n.length>0&&!n.startsWith("??")&&!n.startsWith("!!"))}catch{return!1}}function Sr(t,e,n,r="merge",o){let i=!1,s,a=[],l=c=>a.length>0?{...c,warnings:[...a]}:c,d=(c,p)=>{a.push(`${c}: ${yr(p)}`)},u=c=>{if(i)try{Q("git",["-C",c,"stash","pop"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(p){d("Failed to pop auto-stash during recovery",p)}};try{if(r==="squash"){if(Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),Ja(t)){let f;try{f=Q("git",["-C",t,"stash","push","-m",`pre-merge stash before ${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(y){return l({success:!1,dirtyError:!0,error:`Auto-stash failed: ${yr(y)}. Commit or stash changes manually, then retry.`})}if(!f.includes("No local changes to save")){i=!0;try{s=Q("git",["-C",t,"stash","list","--format=%gd","-n","1"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch(y){d("Failed to determine auto-stash ref",y)}}}Q("git",["-C",t,"merge","--squash",e],{timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),Q("git",["-C",t,"commit","-m",`Squash merge ${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]});let m=!1;if(i)try{Q("git",["-C",t,"stash","pop"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(f){m=!0,d("Failed to pop auto-stash after merge",f)}return l({success:!0,stashed:i||void 0,stashRef:s,stashPopConflict:m||void 0})}let c=o&&lm(o),p=c?o:t;if(c||Q("git",["-C",t,"checkout",e],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),Ja(t)){let m;try{m=Q("git",["-C",t,"stash","push","-m",`pre-merge stash before ${e}`],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(f){try{Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(y){d(`Failed to check out ${n} after auto-stash failure`,y)}return l({success:!1,dirtyError:!0,error:`Auto-stash failed: ${yr(f)}. Commit or stash changes manually, then retry.`})}if(!m.includes("No local changes to save")){i=!0;try{s=Q("git",["-C",t,"stash","list","--format=%gd","-n","1"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch(f){d("Failed to determine auto-stash ref",f)}}}try{Q("git",["-C",p,"rebase",n],{timeout:6e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch{try{Q("git",["-C",p,"rebase","--abort"],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(m){d("Failed to abort rebase during recovery",m)}try{Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(m){d(`Failed to check out ${n} during recovery`,m)}return u(t),l({success:!1,rebaseConflict:!0,stashed:i||void 0,stashRef:s,error:[`Rebase of ${e} onto ${n} hit conflicts.`,"To resolve manually:",` cd ${p}`,` git rebase ${n}`," # resolve conflicts in each file, then:"," git add <file>"," git rebase --continue"," # repeat until rebase finishes, then re-run agent_merge."].join(`
23
+ `)})}Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),Q("git",["-C",t,"merge","--ff-only",e],{timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]});let g=!1;if(i)try{Q("git",["-C",t,"stash","pop"],{timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(m){g=!0,d("Failed to pop auto-stash after merge",m)}return l({success:!0,fastForward:!0,stashed:i||void 0,stashRef:s,stashPopConflict:g||void 0})}catch(c){try{Q("git",["-C",t,"checkout",n],{timeout:15e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]})}catch(p){d(`Failed to check out ${n} during recovery`,p)}return u(t),l({success:!1,error:yr(c),stashed:i||void 0,stashRef:s})}}var Ya=H(()=>{});import{execFileSync as mn}from"child_process";function Za(t){return/pull request already exists/i.test(t)||/createPullRequest/i.test(t)&&/already exists/i.test(t)}function Xa(t,e,n){let r=$t(t,e,n);if(r.exists&&r.state==="open"&&r.url)return{success:!0,prUrl:r.url,warnings:["A PR already exists for this branch; reused the existing open PR."]};if(r.exists&&r.url)return{success:!1,error:`A PR already exists for ${e}, but it is ${r.state}: ${r.url}`}}function el(t){try{return mn("git",["-C",t,"remote","get-url","origin"],{timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim().match(/[:/]([^/]+)\/[^/]+(?:\.git)?$/)?.[1]}catch{return}}function dm(t,e,n){if(!n)return e;let r=el(t);return r?`${r}:${e}`:e}function tl(t,e,n,r,o,i,s={}){if(!Ie())return{success:!1,error:"GitHub CLI (gh) is not available"};let a;try{return a=["pr","create","--base",n],(s.draft??!0)&&a.push("--draft"),i&&a.push("--repo",i),a.push("--head",dm(t,e,i)),r&&o?a.push("--title",r,"--body",o):a.push("--fill-verbose"),{success:!0,prUrl:mn("gh",a,{cwd:t,timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()}}catch(l){let d=l instanceof Error?l.message:String(l);if(Za(d))return Xa(t,e,i)??{success:!1,error:d};if((s.draft??!0)&&a&&/draft/i.test(d))try{let u=a.filter(g=>g!=="--draft");return{success:!0,prUrl:mn("gh",u,{cwd:t,timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim(),warnings:["Target repo does not support draft PRs; created as regular (non-draft) PR instead."]}}catch(u){let c=u instanceof Error?u.message:String(u);return Za(c)?Xa(t,e,i)??{success:!1,error:`Draft PR creation failed (${d}); non-draft retry also failed: ${c}`}:{success:!1,error:`Draft PR creation failed (${d}); non-draft retry also failed: ${c}`}}return{success:!1,error:d}}}function $t(t,e,n){if(!Ie())return{exists:!1,state:"none"};try{let r=["pr","list","--head",e,"--state","all","--json","url,number,title,state,headRepositoryOwner,headRefName"];n&&r.push("--repo",n);let i=mn("gh",r,{cwd:t,timeout:1e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();if(!i)return{exists:!1,state:"none"};let s=JSON.parse(i),a=n?el(t)?.toLowerCase():void 0,l=a?s.find(c=>c.headRefName===e&&c.headRepositoryOwner?.login?.toLowerCase()===a):s[0];if(!l)return{exists:!1,state:"none"};let d=l.state.toLowerCase();return{exists:!0,state:d==="open"?"open":d==="merged"?"merged":d==="closed"?"closed":"none",url:l.url,number:l.number,title:l.title}}catch(r){return`${e}${r instanceof Error?r.message:String(r)}`,{exists:!1,state:"none"}}}function nl(t,e,n,r){if(!Ie())return!1;try{let o=["pr","comment",String(e),"--body",n];return r&&o.push("--repo",r),mn("gh",o,{cwd:t,timeout:3e4,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}),!0}catch(o){return`${e}${o instanceof Error?o.message:String(o)}`,!1}}function it(t){if(t.kind==="merge"){let e=t.filesChanged!==void 0?` (${t.filesChanged} files, +${t.insertions??0}/-${t.deletions??0})`:"";return`✅ Merged: ${t.branch} → ${t.base??"main"}${e}`}return t.kind==="pr-updated"?`✅ PR updated: ${t.prUrl??""}`:t.targetRepo?`✅ PR opened against ${t.targetRepo}: ${t.prUrl??""}`:`✅ PR opened: ${t.prUrl??""}`}var Ii=H(()=>{Ct()});import{existsSync as xi}from"fs";function rl(){return new Date().toISOString()}function um(t){return t.worktreeLifecycle??{state:t.worktreePath||t.worktreeBranch?"provisioned":"none",updatedAt:rl(),baseBranch:t.worktreeBaseBranch,targetRepo:t.worktreePrTargetRepo,pushRemote:t.worktreePushRemote}}function cm(t){let e=ol(t);return t.worktreeLifecycle?.baseBranch??t.worktreeBaseBranch??(e&&xi(e)?Me(e):void 0)}function ol(t){return typeof t.workdir=="string"&&t.workdir.length>0?t.workdir:void 0}function je(t,e={}){let n=um(t),r=rl(),o=new Set,i=ol(t),s=!!(i&&xi(i)),a=!!(t.worktreePath&&xi(t.worktreePath)),l=t.worktreeBranch,d=cm(t),u=!1,c=!1,p=!1,g=!1,m,f,y=t.worktreePrUrl?"open":"none",S=t.worktreePrUrl,R=t.worktreePrNumber;if(s||o.add("repo_missing"),l||o.add("branch_missing"),!a&&t.worktreePath&&o.add("worktree_missing"),e.activeSession&&o.add("active_session"),n.state==="pending_decision"&&o.add("pending_decision"),n.state==="merge_conflict_resolving"&&o.add("merge_conflict_resolving"),s&&i&&l&&(u=cn(i,l),u||o.add("branch_missing")),a&&t.worktreePath&&(c=ot(t.worktreePath),c&&o.add("dirty_worktree_entries")),s&&i&&u&&l&&d){let E=Ga(i,l,d);m=E?.ahead,f=E?.behind,p=Tt(i,l,d),p?o.add("topology_merged"):(g=gr(i,l,d),g&&o.add("merge_noop_content_already_on_base"),!g&&(m??0)>0&&o.add("unique_content"))}else d||o.add("base_branch_missing");if(e.includePrSync&&s&&i&&l){let E=$t(i,l,t.worktreePrTargetRepo??n.targetRepo);y=E.state,S=E.url??S,R=E.number??R}y==="open"&&o.add("pr_open"),y==="merged"&&!p&&!g&&o.add("pr_merged_not_reflected_locally");let I;p?I="merged":g&&(I="released");let b=e.activeSession||c,A=n.state;!b&&I?A=I:!u&&n.state==="pending_decision"&&(A="cleanup_failed");let k=A==="merged"||A==="released",P=e.activeSession||c||!k&&n.state==="pending_decision"||n.state==="merge_conflict_resolving"||n.state==="pr_open"||y==="open"||o.has("pr_merged_not_reflected_locally"),F=!P&&(A==="merged"||A==="released"||n.state==="dismissed"||n.state==="no_change"),pe={checkedAt:r,repoExists:s,branchExists:u,worktreeExists:a,activeSession:e.activeSession===!0,dirtyTracked:c,topologyMerged:p,releaseNoopMerge:g,branchAheadCount:m,baseAheadCount:f,prState:y,prUrl:S,prNumber:R,reasons:[...o]};return{lifecycle:n,evidence:pe,derivedState:A,cleanupSafe:F,preserve:P,reasons:[...o]}}var fn=H(()=>{Ct();Ii();Ai()});var ke=H(()=>{Ct();Ai();Ya();Ii();fn()});function Cr(t,e){return{...e,baseBranch:e.baseBranch??t.worktreeBaseBranch,targetRepo:e.targetRepo??t.worktreePrTargetRepo,pushRemote:e.pushRemote??t.worktreePushRemote}}function Mr(t,e={}){let n=e.updatedAt??new Date().toISOString(),r={pendingWorktreeDecisionSince:e.pendingSince??n,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,lifecycle:"awaiting_worktree_decision",worktreeState:"pending_decision",worktreeLifecycle:Cr(t,{state:"pending_decision",updatedAt:n,notes:e.notes})};return e.clearResolverSessionId&&(r.autoMergeResolverSessionId=void 0),r}function Tl(t,e,n,r={}){let o=r.updatedAt??new Date().toISOString();return{autoMergeConflictResolutionAttemptCount:n,autoMergeResolverSessionId:e,pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,lifecycle:"terminal",worktreeState:"merge_conflict_resolving",worktreeLifecycle:Cr(t,{state:"merge_conflict_resolving",updatedAt:o,notes:r.notes})}}function Dt(t,e={}){let n=e.updatedAt??new Date().toISOString(),r=e.resolvedAt??n,o={worktreeMerged:!0,worktreeMergedAt:e.mergedAt??r,lifecycle:"terminal",worktreeState:"merged",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeLifecycle:Cr(t,{state:"merged",updatedAt:n,resolvedAt:r,resolutionSource:e.resolutionSource??"agent_merge"})};return e.clearResolverSessionId&&(o.autoMergeResolverSessionId=void 0),o}function Cl(t,e){let n=e.updatedAt??new Date().toISOString(),r={worktreePrUrl:e.prUrl,lifecycle:"terminal",worktreeState:"pr_open",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeLifecycle:Cr(t,{state:"pr_open",updatedAt:n,resolutionSource:"agent_pr",baseBranch:e.baseBranch,targetRepo:e.targetRepo})};return e.prNumber!==void 0&&(r.worktreePrNumber=e.prNumber),e.disposition!==void 0&&(r.worktreeDisposition=e.disposition),r}var Sn=H(()=>{});function Ot(t,e){let n=t.resolve(e),r=t.getPersistedSession(e),o=n?U(n):r?U(r):void 0;return{activeSession:n,persistedSession:r,persistedRef:o,sessionName:n?.name??r?.name??e,prompt:n?.prompt??r?.prompt,worktreePath:n?.worktreePath??r?.worktreePath,originalWorkdir:n?.originalWorkdir??r?.workdir,branchName:n?.worktreeBranch??r?.worktreeBranch,notificationTarget:n??(r?{id:o??e,name:r.name,harnessSessionId:r.harnessSessionId,backendRef:r.backendRef,route:r.route,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey,goalTaskId:r.goalTaskId}:void 0)}}function vn(t){return[...t.persistedSession?me(t.persistedSession):[],...t.activeSession?me(t.activeSession):[]].filter((e,n,r)=>r.indexOf(e)===n)}function tf(t,e){let n=[e.id,e.backendConversationId,e.harnessSessionId,e.name],r,o;for(let i of n)if(i&&(r??=t.resolve(i),o??=t.getPersistedSession(i),r&&o))break;return{activeSession:r,persistedSession:o}}function _r(t,e,n={}){let{activeSession:r,persistedSession:o}=tf(t,e),i=je({workdir:e.workdir,worktreePath:e.worktreePath,worktreeBranch:e.worktreeBranch,worktreeBaseBranch:n.baseBranch??o?.worktreeBaseBranch,worktreePrTargetRepo:o?.worktreePrTargetRepo,worktreePushRemote:o?.worktreePushRemote,worktreePrUrl:o?.worktreePrUrl,worktreePrNumber:o?.worktreePrNumber,worktreeLifecycle:o?.worktreeLifecycle},{activeSession:!!(r&&(r.status==="starting"||r.status==="running")),includePrSync:!!(o?.worktreeLifecycle?.state==="pr_open"||o?.worktreePrUrl)});return{activeSession:r,persistedSession:o,resolvedLifecycle:i}}function $r(t){let e=t.list("all").filter(o=>o.worktreePath),n=t.listPersistedSessions().filter(o=>o.worktreePath),r=new Map;for(let o of n){if(!o.worktreePath)continue;let i=$(o),s=o.sessionId??i??o.harnessSessionId;s&&r.set(s,{id:o.sessionId??i??o.harnessSessionId,name:o.name,worktreePath:o.worktreePath,worktreeBranch:o.worktreeBranch,worktreeStrategy:o.worktreeStrategy,workdir:o.workdir,worktreeMerged:o.worktreeMerged,worktreeMergedAt:o.worktreeMergedAt,worktreePrUrl:o.worktreePrUrl,backendConversationId:i,harnessSessionId:o.harnessSessionId})}for(let o of e)o.worktreePath&&r.set(o.id,{id:o.id,name:o.name,worktreePath:o.worktreePath,worktreeBranch:o.worktreeBranch,worktreeStrategy:o.worktreeStrategy,workdir:o.originalWorkdir??o.workdir,worktreeMerged:void 0,worktreeMergedAt:void 0,worktreePrUrl:void 0,backendConversationId:$(o),harnessSessionId:o.harnessSessionId});return Array.from(r.values())}function Er(t,e){return t.id===e||t.name===e||t.backendConversationId===e||t.harnessSessionId===e}function at(t){switch(t){case"none":return"none";case"provisioned":return"active";case"pending_decision":return"needs decision";case"merge_conflict_resolving":return"conflict resolving";case"pr_open":return"pr open";case"merged":return"merged";case"released":return"released";case"dismissed":return"dismissed";case"no_change":return"no change";case"cleanup_failed":return"cleanup failed";default:return t}}function Dr(t){switch(t){case"active_session":return"active session";case"pending_decision":return"pending decision";case"merge_conflict_resolving":return"conflict resolving";case"dirty_tracked_changes":case"dirty_worktree_entries":return"dirty worktree";case"unique_content":return"still has unique content";case"topology_merged":return"merged by ancestry";case"merge_noop_content_already_on_base":return"content already on base";case"pr_open":return"PR open";case"pr_merged_not_reflected_locally":return"merged PR not reflected locally";case"repo_missing":return"repo missing";case"branch_missing":return"branch missing";case"worktree_missing":return"worktree missing";case"base_branch_missing":return"base branch missing";default:return t.replaceAll("_"," ")}}var wn=H(()=>{X();fn()});function _l(t,e={preserveBlankLines:!0}){return t?.replace(/\r\n/g,`
24
24
  `).split(`
25
25
  `).map(r=>r.trim()).reduce((r,o)=>o?(r.push(o),r):(e.preserveBlankLines&&r[r.length-1]!==""&&r.push(o),r),[]).join(e.preserveBlankLines?`
26
- `:" ").replace(/[ \t]+/g," ").trim()||void 0}function Dt(t,e){return t.length<=e?t:`${t.slice(0,Math.max(0,e-3)).trimEnd()}...`}function wn(t){return t.replace(/\b[A-Za-z0-9_-]*(?:api[_-]?key|token|secret|password|passwd|pwd|credential|credentials|authorization|auth)[A-Za-z0-9_-]*\b\s*[:=]\s*["']?[^"'\s,;)]+/gi,"[redacted credential]").replace(/\b(?:api key|token|secret|password|credential|credentials)\s+\[redacted credential\]/gi,"[redacted credential]").replace(/\b(?:ghp|gho|ghu|ghs|ghr)_[A-Za-z0-9_]{16,}\b/g,"[redacted token]").replace(/\bgithub_pat_[A-Za-z0-9_]{20,}\b/g,"[redacted token]").replace(/\bsk-[A-Za-z0-9_-]{20,}\b/g,"[redacted token]").replace(/\bxox[baprs]-[A-Za-z0-9-]{20,}\b/g,"[redacted token]").replace(/\bAKIA[0-9A-Z]{16}\b/g,"[redacted token]").replace(/\beyJ[A-Za-z0-9_-]{20,}\.[A-Za-z0-9_-]{20,}\.[A-Za-z0-9_-]{10,}\b/g,"[redacted token]").replace(/\bhttps?:\/\/\S+/gi,"[redacted link]").replace(/\b[A-Z]:\\(?:Users|Documents and Settings)\\[^\s`'")]+/gi,"[redacted path]").replace(/(?:^|[\s(])\/(?:home|Users|var|etc|private|tmp)\/[^\s`'").]+/g,e=>`${e.startsWith(" ")||e.startsWith("(")?e[0]:""}[redacted path]`).replace(new RegExp("\\b[A-Za-z0-9_-]{32,}\\b","g"),"[redacted token]")}function Wr(t){return/\b[A-Za-z0-9_-]*(?:api[_-]?key|token|secret|password|passwd|pwd|credential|credentials|authorization|auth)[A-Za-z0-9_-]*\b\s*[:=]\s*["']?[^"'\s,;)]+/i.test(t)||/\b(?:ghp|gho|ghu|ghs|ghr)_[A-Za-z0-9_]{16,}\b/.test(t)||/\bgithub_pat_[A-Za-z0-9_]{20,}\b/.test(t)||/\bsk-[A-Za-z0-9_-]{20,}\b/.test(t)||/\bxox[baprs]-[A-Za-z0-9-]{20,}\b/.test(t)||/\bAKIA[0-9A-Z]{16}\b/.test(t)||/\beyJ[A-Za-z0-9_-]{20,}\.[A-Za-z0-9_-]{20,}\.[A-Za-z0-9_-]{10,}\b/.test(t)||/\bhttps?:\/\/\S+/i.test(t)||/\b[A-Z]:\\(?:Users|Documents and Settings)\\[^\s`'")]+/i.test(t)||/(?:^|[\s(])\/(?:home|Users|var|etc|private|tmp)\/[^\s`'").]+/.test(t)||new RegExp("\\b[A-Za-z0-9_-]{32,}\\b").test(t)}function Hm(t){let e=Rl(t);if(!e)return;let n=e.match(/^[^.!?]+[.!?]/)?.[0]??e,r=wn(n).replace(/\s+/g," ").trim();return r?Dt(r,180):void 0}function Al(t){return wn(t.trim()).replace(/\s+/g," ").trim()}function zm(t,e){return t?.commitMessages.map(n=>Al(n.message)).filter(Boolean).slice(0,e)??[]}function Ni(){return["Not recorded by agent_pr. Review CI/checks and session output before merging."]}function Il(){return["Generated PR metadata omits full task prompts and redacts sensitive-looking prompt details.","Review touched areas for behavior, security, and privacy impact."]}function Qm(t){let e=Hm(t.prompt),n=t.diffSummary;return{sessionName:t.sessionName,branchName:t.branchName,objective:e,stats:n?{commits:n.commits,filesChanged:n.filesChanged,insertions:n.insertions,deletions:n.deletions}:void 0,changedFiles:n?.changedFiles??[],commitSubjects:zm(n,5),validation:Ni(),notes:Il()}}function Or(t,e,n){return Array.isArray(t)&&t.length>0&&t.length<=e&&t.every(r=>typeof r=="string"&&r.trim().length>0&&r.length<=n)}function xl(t,e){let n=Rl(t);if(!n)return[];let r=e?.toLowerCase();return n.split(/[.!?\n]/).map(o=>o.trim()).filter(o=>o.length>=24).filter(o=>!r||o.toLowerCase()!==r.replace(/[.!?]$/,"")).map(o=>o.toLowerCase())}function Pn(t,e,n){let r=t.toLowerCase();return xl(e,n.objective).some(o=>r.includes(o))}function bl(t){return/^(?:node|next|nuxt|vue|express|nest|three|d3|chart|ember|backbone|require)\.js$/i.test(t)}function Li(t,e){let n=new Set(e.changedFiles);if([...t.matchAll(/(?:^|[^\w.-])((?:\.?[\w-][\w.-]*\/)+(?:\.?[\w-][\w.-]*))(?![\w.-])/g)].map(m=>m[1]).some(m=>/\.[A-Za-z0-9]+$/.test(m)&&!n.has(m)))return!0;let o=new Set(e.changedFiles.filter(m=>!m.includes("/"))),i=String.raw`\.[a-z0-9][\w.-]*`,s=t.matchAll(new RegExp(`[\\\`"'](${i})[\\\`"']`,"g"));for(let m of s)if(!o.has(m[1]))return!0;let l=t.matchAll(new RegExp(String.raw`\b(?:file|files|path|paths|changed|changes|updated?|updates?|modified?|modifies|touched?|touches|added?|adds?|removed?|removes?|deleted?|deletes?)\s+(?:the\s+)?(${i})(?![\w.-])`,"gi"));for(let m of l)if(!o.has(m[1]))return!0;if(o.size===0)return!1;let a=new Set([...o].map(m=>m.match(/\.([A-Za-z0-9]+)$/)?.[1]?.toLowerCase()).filter(m=>!!m)),d=String.raw`[A-Za-z0-9][\w.-]*\.([A-Za-z0-9]+)`,u=t.matchAll(new RegExp(`[\\\`"'](${d})[\\\`"']`,"g"));for(let m of u){let p=m[1],f=m[2]?.toLowerCase();if(f!==void 0&&a.has(f)&&!o.has(p)&&!bl(p))return!0}return[...t.matchAll(new RegExp(String.raw`\b(?:file|files|path|paths|changed|changes|updated?|updates?|modified?|modifies|touched?|touches|added?|adds?|removed?|removes?|deleted?|deletes?)\s+(?:the\s+)?(${d})\b`,"gi"))].some(m=>{let p=m[1],f=m[2]?.toLowerCase();return f!==void 0&&a.has(f)&&!o.has(p)&&!bl(p)})}function We(t){return wn(t).replace(/\s+/g," ").trim()}function Jm(t,e,n){if(!t||typeof t!="object")return;let r=t;if(typeof r.title!="string"||r.title.trim().length===0||r.title.length>90||!Or(r.summary,5,180)||!Or(r.changes,10,160)||!Or(r.validation,5,160)||!Or(r.notes,5,180)||[r.title,...r.summary,...r.changes,...r.validation,...r.notes].some(l=>Wr(l)||Pn(l,n,e)))return;let i={title:We(r.title),summary:r.summary.map(We),changes:r.changes.map(We),validation:r.validation.map(We),notes:r.notes.map(We)},s=[i.title,...i.summary,...i.changes,...i.validation,...i.notes];if(!s.some(l=>!l||Wr(l)||Pn(l,n,e))&&!s.some(l=>Li(l,e)))return i}function Ym(t,e){let n=Dt(wn(t.sessionName).replace(/[-_]+/g," ").replace(/\s+/g," ").trim()||"agent worktree",80),r=Dt(`OpenClaw agent changes: ${n}`,90),o=["Deterministic fallback metadata generated because no LLM PR metadata provider is configured.",`Session: ${n}.`,...t.objective?[`Objective: ${t.objective}`]:[],...t.stats?[`Scope: ${t.stats.commits} commits, ${t.stats.filesChanged} files changed (+${t.stats.insertions} / -${t.stats.deletions}).`]:["Scope: Diff summary was unavailable when the PR body was generated."]],i=t.changedFiles.length>0?t.changedFiles.slice(0,10).map(p=>`\`${p}\``):["Review the pushed worktree branch for the full set of changes."],s=t.changedFiles.length>10?[`...and ${t.changedFiles.length-10} more changed files.`]:[],l=["Fallback metadata is conservative; review the diff and CI/checks before marking the draft PR ready.",...t.notes],a={title:r,summary:o,changes:[...i,...s],validation:t.validation,notes:l},d=!1,u=!1,c=p=>{let f=We(p);if(Pn(f,e,t)){d=!0;let h=xl(e,t.objective);for(let k of h){let v=new RegExp(k.replace(/[.*+?^${}()|[\]\\]/g,"\\$&"),"gi");f=f.replace(v,"[redacted prompt detail]")}f=We(f)}return Li(f,t)&&(u=!0,f="[redacted file reference outside change set]"),f=We(f),(Pn(f,e,t)||Wr(f))&&(d=!0,f="[redacted prompt detail]"),f};if(a={title:c(a.title)||Dt(`OpenClaw agent changes: ${n}`,90),summary:a.summary.map(c).filter(p=>p&&p.length>0),changes:a.changes.map(c).filter(p=>p&&p.length>0),validation:a.validation.map(c).filter(p=>p&&p.length>0),notes:a.notes.map(c).filter(p=>p&&p.length>0)},a.summary.length===0&&(a.summary=["Deterministic fallback metadata generated because no LLM PR metadata provider is configured."]),a.changes.length===0&&(a.changes=["Review the pushed worktree branch for the full set of changes."]),a.validation.length===0&&(a.validation=Ni()),a.notes.length===0&&(a.notes=Il()),d||u){let p="Some content was stripped from fallback metadata due to safety checks (prompt leak guard or references to files outside the diff).";a.notes.some(f=>f.toLowerCase().includes("stripped")||f.toLowerCase().includes("sanitized"))||(a.notes=[...a.notes,p])}let m=[a.title,...a.summary,...a.changes,...a.validation,...a.notes];if(m.some(p=>!p)||m.some(p=>Wr(p)||Pn(p,e,t))||m.some(p=>Li(p,t))){let p=Dt(wn(t.sessionName).replace(/[-_]+/g," ").trim()||"session",60);a={title:Dt(`OpenClaw agent changes: ${p}`,90),summary:["Deterministic fallback metadata (sanitized for safety)."],changes:t.changedFiles.length>0?t.changedFiles.slice(0,5).map(f=>`\`${f}\``):["See the worktree branch diff for the full set of changes."],validation:Ni(),notes:["Fallback metadata was hardened because prompt-leak or unknown-file checks were triggered after initial construction.","Review the actual diff, session output, and CI before merging."]}}if(t.branchName){let p=We(t.branchName);a.notes.some(f=>f.toLowerCase().includes(p.toLowerCase()))||(a.notes=[...a.notes,`Branch: ${p}`])}return a}async function Nr(t){let e=Qm({sessionName:t.sessionName,branchName:t.branchName,prompt:t.prompt,diffSummary:t.diffSummary});if(!t.provider)return{ok:!0,metadata:Ym(e,t.prompt),evidence:e};try{let n=await t.provider.generatePrMetadata(e),r=Jm(n,e,t.prompt);return r?{ok:!0,metadata:r,evidence:e}:{ok:!1,error:"LLM-generated PR metadata failed schema or safety validation. Pass explicit title/body or retry after correcting the provider output.",evidence:e}}catch(n){return`${n instanceof Error?n.message:String(n)}`,{ok:!1,error:"PR metadata provider failed. Pass explicit title/body or retry after the provider is healthy.",evidence:e}}}function Lr(t){let e=[`OpenClaw Code Agent session: ${t.sessionName}`,"","## Summary",...t.metadata.summary.map(n=>`- ${n}`),"","## Changes",...t.metadata.changes.map(n=>`- ${n}`),""];if(t.diffSummary){let n=t.diffSummary.commitMessages.slice(0,5).map(o=>`- ${o.hash} ${Al(o.message)} (${o.author})`),r=t.diffSummary.commits>5?[`- ...and ${t.diffSummary.commits-5} more`]:[];n.length>0&&e.push("## Commits",...n,...r,"")}return e.push("## Validation",...t.metadata.validation.map(n=>`- ${n}`),"","## Notes / Risks",...t.metadata.notes.map(n=>`- ${n}`),""),e.push("---","Generated with [openclaw-code-agent](https://github.com/goldmar/openclaw-code-agent)"),e.join(`
27
- `)}var Fi=H(()=>{});var Tl={};Cu(Tl,{buildPrCompletionWakeOutcomeKey:()=>qi,buildPrMetadata:()=>Nr,buildPrOutcomeDetailLines:()=>Bi,formatPrBody:()=>Lr,makeAgentPrTool:()=>bn});import{existsSync as Zm}from"fs";function Xm(t){return!t||typeof t!="object"?!1:typeof t.session=="string"}function Bi(t){return[t.action==="opened"?`Opened PR for branch ${t.branchName} into ${t.baseBranch}.`:`Updated PR for branch ${t.branchName} into ${t.baseBranch}.`,...t.prUrl?[`PR URL: ${t.prUrl}.`]:[],...t.prNumber?[`PR number: #${t.prNumber}.`]:[],...t.targetRepo?[`Target repository: ${t.targetRepo}.`]:[],...t.commits!==void 0?[`Pushed ${t.commits} new commits (+${t.insertions??0}/-${t.deletions??0}).`]:[]]}function qi(t){let e=t.prNumber!==void 0?`#${t.prNumber}`:t.prUrl??"unknown-pr",n=t.diffSummary?.commitMessages.map(o=>o.hash.trim()).filter(Boolean).join(","),r=t.action==="updated"?n||[`commits:${t.diffSummary?.commits??"unknown"}`,`insertions:${t.diffSummary?.insertions??"unknown"}`,`deletions:${t.diffSummary?.deletions??"unknown"}`].join(","):"created";return["worktree-pr",t.action,t.targetRepo??"default-repo",e,t.branchName,r].join(":")}function bn(t,e={}){return{name:"agent_pr",description:"Create or update a GitHub PR for a worktree branch. Handles full PR lifecycle: creates new PRs, updates existing open PRs with comments, and handles merged/closed PRs. Pushes the branch, syncs PR state, and persists metadata.",parameters:g.Object({session:g.String({description:"Session name or ID to create/update PR for"}),title:g.Optional(g.String({description:"PR title (default: auto-generated from session name)"})),body:g.Optional(g.String({description:"PR body (default: auto-generated from commit summary)"})),base_branch:g.Optional(g.String({description:"Base branch for the PR (default: detected from repo)"})),force_new:g.Optional(g.Boolean({description:"Force creation of a new PR even if one exists (default: false)"})),target_repo:g.Optional(g.String({description:"Target repository for cross-repo PRs (e.g. 'openai/codex'). Auto-detected from 'upstream' remote if not set."}))}),async execute(n,r){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}],meta:{success:!1,state:"error"}};if(!Xm(r))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, title?, body?, base_branch?, force_new? }."}],meta:{success:!1,state:"error"}};if(!Ae())return{content:[{type:"text",text:"Error: GitHub CLI (gh) is not available. Install it and authenticate to create PRs."}],meta:{success:!1,state:"error"}};let o=Et(S,r.session),i=o.activeSession,s=o.persistedSession;if(!i&&!s)return{content:[{type:"text",text:`Error: Session "${r.session}" not found.`}],meta:{success:!1,state:"error"}};let{worktreePath:l,originalWorkdir:a,sessionName:d,branchName:u}=o;if(!l||!a)return{content:[{type:"text",text:`Error: Session "${r.session}" does not have a worktree.`}],meta:{success:!1,state:"error"}};if(!u)return{content:[{type:"text",text:`Error: Cannot determine branch name for worktree ${l}. The worktree may have been removed and no persisted branch name is available.`}],meta:{success:!1,state:"error"}};Zm(l)||`${l}${u}${a}`;let c=r.base_branch??Ce(a),m=S.resolveRepoPolicy(a);if(m?.policy==="never-pr")return{content:[{type:"text",text:`Error: Repo policy forbids PR creation for ${m.identity?.repoRoot??a}.`}],meta:{success:!1,state:"error"}};if(m&&!m.prAvailable)return{content:[{type:"text",text:`Error: PR automation is unavailable for ${m.identity?.repoRoot??a}. Provider: ${m.provider}.`}],meta:{success:!1,state:"error"}};let p=k=>{let v=wl({worktreeBaseBranch:s?.worktreeBaseBranch??i?.worktreeBaseBranch??c,worktreePrTargetRepo:s?.worktreePrTargetRepo??i?.worktreePrTargetRepo,worktreePushRemote:s?.worktreePushRemote??i?.worktreePushRemote},{prUrl:k.prUrl,prNumber:k.prNumber,baseBranch:c,targetRepo:k.targetRepo,disposition:k.disposition});for(let I of Sn(o))S.updatePersistedSession(I,v)},f=Fa(a,r.target_repo??s?.worktreePrTargetRepo);if(!hr(a,u))return{content:[{type:"text",text:`❌ Failed to push ${u} — cannot create/update PR`}],meta:{success:!1,state:"error"}};let h=Mt(a,u,f);if(r.force_new&&h.exists)return{content:[{type:"text",text:`⚠️ Cannot create new PR: A PR already exists for ${u} (${h.state}).
26
+ `:" ").replace(/[ \t]+/g," ").trim()||void 0}function Wt(t,e){return t.length<=e?t:`${t.slice(0,Math.max(0,e-3)).trimEnd()}...`}function bn(t){return t.replace(/\b[A-Za-z0-9_-]*(?:api[_-]?key|token|secret|password|passwd|pwd|credential|credentials|authorization|auth)[A-Za-z0-9_-]*\b\s*[:=]\s*["']?[^"'\s,;)]+/gi,"[redacted credential]").replace(/\b(?:api key|token|secret|password|credential|credentials)\s+\[redacted credential\]/gi,"[redacted credential]").replace(/\b(?:ghp|gho|ghu|ghs|ghr)_[A-Za-z0-9_]{16,}\b/g,"[redacted token]").replace(/\bgithub_pat_[A-Za-z0-9_]{20,}\b/g,"[redacted token]").replace(/\bsk-[A-Za-z0-9_-]{20,}\b/g,"[redacted token]").replace(/\bxox[baprs]-[A-Za-z0-9-]{20,}\b/g,"[redacted token]").replace(/\bAKIA[0-9A-Z]{16}\b/g,"[redacted token]").replace(/\beyJ[A-Za-z0-9_-]{20,}\.[A-Za-z0-9_-]{20,}\.[A-Za-z0-9_-]{10,}\b/g,"[redacted token]").replace(/\bhttps?:\/\/\S+/gi,"[redacted link]").replace(/\b[A-Z]:\\(?:Users|Documents and Settings)\\[^\s`'")]+/gi,"[redacted path]").replace(/(?:^|[\s(])\/(?:home|Users|var|etc|private|tmp)\/[^\s`'").]+/g,e=>`${e.startsWith(" ")||e.startsWith("(")?e[0]:""}[redacted path]`).replace(new RegExp("\\b[A-Za-z0-9_-]{32,}\\b","g"),"[redacted token]")}function Lr(t){return/\b[A-Za-z0-9_-]*(?:api[_-]?key|token|secret|password|passwd|pwd|credential|credentials|authorization|auth)[A-Za-z0-9_-]*\b\s*[:=]\s*["']?[^"'\s,;)]+/i.test(t)||/\b(?:ghp|gho|ghu|ghs|ghr)_[A-Za-z0-9_]{16,}\b/.test(t)||/\bgithub_pat_[A-Za-z0-9_]{20,}\b/.test(t)||/\bsk-[A-Za-z0-9_-]{20,}\b/.test(t)||/\bxox[baprs]-[A-Za-z0-9-]{20,}\b/.test(t)||/\bAKIA[0-9A-Z]{16}\b/.test(t)||/\beyJ[A-Za-z0-9_-]{20,}\.[A-Za-z0-9_-]{20,}\.[A-Za-z0-9_-]{10,}\b/.test(t)||/\bhttps?:\/\/\S+/i.test(t)||/\b[A-Z]:\\(?:Users|Documents and Settings)\\[^\s`'")]+/i.test(t)||/(?:^|[\s(])\/(?:home|Users|var|etc|private|tmp)\/[^\s`'").]+/.test(t)||new RegExp("\\b[A-Za-z0-9_-]{32,}\\b").test(t)}function sf(t){let e=_l(t);if(!e)return;let n=e.match(/^[^.!?]+[.!?]/)?.[0]??e,r=bn(n).replace(/\s+/g," ").trim();return r?Wt(r,180):void 0}function $l(t){return bn(t.trim()).replace(/\s+/g," ").trim()}function af(t,e){return t?.commitMessages.map(n=>$l(n.message)).filter(Boolean).slice(0,e)??[]}function qi(){return["Not recorded by agent_pr. Review CI/checks and session output before merging."]}function El(){return["Generated PR metadata omits full task prompts and redacts sensitive-looking prompt details.","Review touched areas for behavior, security, and privacy impact."]}function lf(t){let e=sf(t.prompt),n=t.diffSummary;return{sessionName:t.sessionName,branchName:t.branchName,objective:e,stats:n?{commits:n.commits,filesChanged:n.filesChanged,insertions:n.insertions,deletions:n.deletions}:void 0,changedFiles:n?.changedFiles??[],commitSubjects:af(n,5),validation:qi(),notes:El()}}function Nr(t,e,n){return Array.isArray(t)&&t.length>0&&t.length<=e&&t.every(r=>typeof r=="string"&&r.trim().length>0&&r.length<=n)}function Dl(t,e){let n=_l(t);if(!n)return[];let r=e?.toLowerCase();return n.split(/[.!?\n]/).map(o=>o.trim()).filter(o=>o.length>=24).filter(o=>!r||o.toLowerCase()!==r.replace(/[.!?]$/,"")).map(o=>o.toLowerCase())}function Pn(t,e,n){let r=t.toLowerCase();return Dl(e,n.objective).some(o=>r.includes(o))}function Ml(t){return/^(?:node|next|nuxt|vue|express|nest|three|d3|chart|ember|backbone|require)\.js$/i.test(t)}function Ki(t,e){let n=new Set(e.changedFiles);if([...t.matchAll(/(?:^|[^\w.-])((?:\.?[\w-][\w.-]*\/)+(?:\.?[\w-][\w.-]*))(?![\w.-])/g)].map(p=>p[1]).some(p=>/\.[A-Za-z0-9]+$/.test(p)&&!n.has(p)))return!0;let o=new Set(e.changedFiles.filter(p=>!p.includes("/"))),i=String.raw`\.[a-z0-9][\w.-]*`,s=t.matchAll(new RegExp(`[\\\`"'](${i})[\\\`"']`,"g"));for(let p of s)if(!o.has(p[1]))return!0;let a=t.matchAll(new RegExp(String.raw`\b(?:file|files|path|paths|changed|changes|updated?|updates?|modified?|modifies|touched?|touches|added?|adds?|removed?|removes?|deleted?|deletes?)\s+(?:the\s+)?(${i})(?![\w.-])`,"gi"));for(let p of a)if(!o.has(p[1]))return!0;if(o.size===0)return!1;let l=new Set([...o].map(p=>p.match(/\.([A-Za-z0-9]+)$/)?.[1]?.toLowerCase()).filter(p=>!!p)),d=String.raw`[A-Za-z0-9][\w.-]*\.([A-Za-z0-9]+)`,u=t.matchAll(new RegExp(`[\\\`"'](${d})[\\\`"']`,"g"));for(let p of u){let g=p[1],m=p[2]?.toLowerCase();if(m!==void 0&&l.has(m)&&!o.has(g)&&!Ml(g))return!0}return[...t.matchAll(new RegExp(String.raw`\b(?:file|files|path|paths|changed|changes|updated?|updates?|modified?|modifies|touched?|touches|added?|adds?|removed?|removes?|deleted?|deletes?)\s+(?:the\s+)?(${d})\b`,"gi"))].some(p=>{let g=p[1],m=p[2]?.toLowerCase();return m!==void 0&&l.has(m)&&!o.has(g)&&!Ml(g)})}function Ne(t){return bn(t).replace(/\s+/g," ").trim()}function df(t,e,n){if(!t||typeof t!="object")return;let r=t;if(typeof r.title!="string"||r.title.trim().length===0||r.title.length>90||!Nr(r.summary,5,180)||!Nr(r.changes,10,160)||!Nr(r.validation,5,160)||!Nr(r.notes,5,180)||[r.title,...r.summary,...r.changes,...r.validation,...r.notes].some(a=>Lr(a)||Pn(a,n,e)))return;let i={title:Ne(r.title),summary:r.summary.map(Ne),changes:r.changes.map(Ne),validation:r.validation.map(Ne),notes:r.notes.map(Ne)},s=[i.title,...i.summary,...i.changes,...i.validation,...i.notes];if(!s.some(a=>!a||Lr(a)||Pn(a,n,e))&&!s.some(a=>Ki(a,e)))return i}function uf(t,e){let n=Wt(bn(t.sessionName).replace(/[-_]+/g," ").replace(/\s+/g," ").trim()||"agent worktree",80),r=Wt(`OpenClaw agent changes: ${n}`,90),o=["Deterministic fallback metadata generated because no LLM PR metadata provider is configured.",`Session: ${n}.`,...t.objective?[`Objective: ${t.objective}`]:[],...t.stats?[`Scope: ${t.stats.commits} commits, ${t.stats.filesChanged} files changed (+${t.stats.insertions} / -${t.stats.deletions}).`]:["Scope: Diff summary was unavailable when the PR body was generated."]],i=t.changedFiles.length>0?t.changedFiles.slice(0,10).map(g=>`\`${g}\``):["Review the pushed worktree branch for the full set of changes."],s=t.changedFiles.length>10?[`...and ${t.changedFiles.length-10} more changed files.`]:[],a=["Fallback metadata is conservative; review the diff and CI/checks before marking the draft PR ready.",...t.notes],l={title:r,summary:o,changes:[...i,...s],validation:t.validation,notes:a},d=!1,u=!1,c=g=>{let m=Ne(g);if(Pn(m,e,t)){d=!0;let f=Dl(e,t.objective);for(let y of f){let S=new RegExp(y.replace(/[.*+?^${}()|[\]\\]/g,"\\$&"),"gi");m=m.replace(S,"[redacted prompt detail]")}m=Ne(m)}return Ki(m,t)&&(u=!0,m="[redacted file reference outside change set]"),m=Ne(m),(Pn(m,e,t)||Lr(m))&&(d=!0,m="[redacted prompt detail]"),m};if(l={title:c(l.title)||Wt(`OpenClaw agent changes: ${n}`,90),summary:l.summary.map(c).filter(g=>g&&g.length>0),changes:l.changes.map(c).filter(g=>g&&g.length>0),validation:l.validation.map(c).filter(g=>g&&g.length>0),notes:l.notes.map(c).filter(g=>g&&g.length>0)},l.summary.length===0&&(l.summary=["Deterministic fallback metadata generated because no LLM PR metadata provider is configured."]),l.changes.length===0&&(l.changes=["Review the pushed worktree branch for the full set of changes."]),l.validation.length===0&&(l.validation=qi()),l.notes.length===0&&(l.notes=El()),d||u){let g="Some content was stripped from fallback metadata due to safety checks (prompt leak guard or references to files outside the diff).";l.notes.some(m=>m.toLowerCase().includes("stripped")||m.toLowerCase().includes("sanitized"))||(l.notes=[...l.notes,g])}let p=[l.title,...l.summary,...l.changes,...l.validation,...l.notes];if(p.some(g=>!g)||p.some(g=>Lr(g)||Pn(g,e,t))||p.some(g=>Ki(g,t))){let g=Wt(bn(t.sessionName).replace(/[-_]+/g," ").trim()||"session",60);l={title:Wt(`OpenClaw agent changes: ${g}`,90),summary:["Deterministic fallback metadata (sanitized for safety)."],changes:t.changedFiles.length>0?t.changedFiles.slice(0,5).map(m=>`\`${m}\``):["See the worktree branch diff for the full set of changes."],validation:qi(),notes:["Fallback metadata was hardened because prompt-leak or unknown-file checks were triggered after initial construction.","Review the actual diff, session output, and CI before merging."]}}if(t.branchName){let g=Ne(t.branchName);l.notes.some(m=>m.toLowerCase().includes(g.toLowerCase()))||(l.notes=[...l.notes,`Branch: ${g}`])}return l}async function Br(t){let e=lf({sessionName:t.sessionName,branchName:t.branchName,prompt:t.prompt,diffSummary:t.diffSummary});if(!t.provider)return{ok:!0,metadata:uf(e,t.prompt),evidence:e};try{let n=await t.provider.generatePrMetadata(e),r=df(n,e,t.prompt);return r?{ok:!0,metadata:r,evidence:e}:{ok:!1,error:"LLM-generated PR metadata failed schema or safety validation. Pass explicit title/body or retry after correcting the provider output.",evidence:e}}catch(n){return`${n instanceof Error?n.message:String(n)}`,{ok:!1,error:"PR metadata provider failed. Pass explicit title/body or retry after the provider is healthy.",evidence:e}}}function Fr(t){let e=[`OpenClaw Code Agent session: ${t.sessionName}`,"","## Summary",...t.metadata.summary.map(n=>`- ${n}`),"","## Changes",...t.metadata.changes.map(n=>`- ${n}`),""];if(t.diffSummary){let n=t.diffSummary.commitMessages.slice(0,5).map(o=>`- ${o.hash} ${$l(o.message)} (${o.author})`),r=t.diffSummary.commits>5?[`- ...and ${t.diffSummary.commits-5} more`]:[];n.length>0&&e.push("## Commits",...n,...r,"")}return e.push("## Validation",...t.metadata.validation.map(n=>`- ${n}`),"","## Notes / Risks",...t.metadata.notes.map(n=>`- ${n}`),""),e.push("---","Generated with [openclaw-code-agent](https://github.com/goldmar/openclaw-code-agent)"),e.join(`
27
+ `)}var Ui=H(()=>{});var Ol={};qu(Ol,{buildPrCompletionWakeOutcomeKey:()=>Gi,buildPrMetadata:()=>Br,buildPrOutcomeDetailLines:()=>Vi,formatPrBody:()=>Fr,makeAgentPrTool:()=>Rn});import{existsSync as cf}from"fs";function pf(t){return!t||typeof t!="object"?!1:typeof t.session=="string"}function Vi(t){return[t.action==="opened"?`Opened PR for branch ${t.branchName} into ${t.baseBranch}.`:`Updated PR for branch ${t.branchName} into ${t.baseBranch}.`,...t.prUrl?[`PR URL: ${t.prUrl}.`]:[],...t.prNumber?[`PR number: #${t.prNumber}.`]:[],...t.targetRepo?[`Target repository: ${t.targetRepo}.`]:[],...t.commits!==void 0?[`Pushed ${t.commits} new commits (+${t.insertions??0}/-${t.deletions??0}).`]:[]]}function Gi(t){let e=t.prNumber!==void 0?`#${t.prNumber}`:t.prUrl??"unknown-pr",n=t.diffSummary?.commitMessages.map(o=>o.hash.trim()).filter(Boolean).join(","),r=t.action==="updated"?n||[`commits:${t.diffSummary?.commits??"unknown"}`,`insertions:${t.diffSummary?.insertions??"unknown"}`,`deletions:${t.diffSummary?.deletions??"unknown"}`].join(","):"created";return["worktree-pr",t.action,t.targetRepo??"default-repo",e,t.branchName,r].join(":")}function Rn(t,e={}){return{name:"agent_pr",description:"Create or update a GitHub PR for a worktree branch. Handles full PR lifecycle: creates new PRs, updates existing open PRs with comments, and handles merged/closed PRs. Pushes the branch, syncs PR state, and persists metadata.",parameters:h.Object({session:h.String({description:"Session name or ID to create/update PR for"}),title:h.Optional(h.String({description:"PR title (default: auto-generated from session name)"})),body:h.Optional(h.String({description:"PR body (default: auto-generated from commit summary)"})),base_branch:h.Optional(h.String({description:"Base branch for the PR (default: detected from repo)"})),force_new:h.Optional(h.Boolean({description:"Force creation of a new PR even if one exists (default: false)"})),target_repo:h.Optional(h.String({description:"Target repository for cross-repo PRs (e.g. 'openai/codex'). Auto-detected from 'upstream' remote if not set."}))}),async execute(n,r){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}],meta:{success:!1,state:"error"}};if(!pf(r))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, title?, body?, base_branch?, force_new? }."}],meta:{success:!1,state:"error"}};if(!Ie())return{content:[{type:"text",text:"Error: GitHub CLI (gh) is not available. Install it and authenticate to create PRs."}],meta:{success:!1,state:"error"}};let o=Ot(v,r.session),i=o.activeSession,s=o.persistedSession;if(!i&&!s)return{content:[{type:"text",text:`Error: Session "${r.session}" not found.`}],meta:{success:!1,state:"error"}};let{worktreePath:a,originalWorkdir:l,sessionName:d,branchName:u}=o;if(!a||!l)return{content:[{type:"text",text:`Error: Session "${r.session}" does not have a worktree.`}],meta:{success:!1,state:"error"}};if(!u)return{content:[{type:"text",text:`Error: Cannot determine branch name for worktree ${a}. The worktree may have been removed and no persisted branch name is available.`}],meta:{success:!1,state:"error"}};cf(a)||`${a}${u}${l}`;let c=r.base_branch??Me(l),p=v.resolveRepoPolicy(l);if(p?.policy==="never-pr")return{content:[{type:"text",text:`Error: Repo policy forbids PR creation for ${p.identity?.repoRoot??l}.`}],meta:{success:!1,state:"error"}};if(p&&!p.prAvailable)return{content:[{type:"text",text:`Error: PR automation is unavailable for ${p.identity?.repoRoot??l}. Provider: ${p.provider}.`}],meta:{success:!1,state:"error"}};let g=y=>{let S=Cl({worktreeBaseBranch:s?.worktreeBaseBranch??i?.worktreeBaseBranch??c,worktreePrTargetRepo:s?.worktreePrTargetRepo??i?.worktreePrTargetRepo,worktreePushRemote:s?.worktreePushRemote??i?.worktreePushRemote},{prUrl:y.prUrl,prNumber:y.prNumber,baseBranch:c,targetRepo:y.targetRepo,disposition:y.disposition});for(let R of vn(o))v.updatePersistedSession(R,S)},m=ja(l,r.target_repo??s?.worktreePrTargetRepo);if(!kr(l,u))return{content:[{type:"text",text:`❌ Failed to push ${u} — cannot create/update PR`}],meta:{success:!1,state:"error"}};let f=$t(l,u,m);if(r.force_new&&f.exists)return{content:[{type:"text",text:`⚠️ Cannot create new PR: A PR already exists for ${u} (${f.state}).
28
28
 
29
- Existing PR: ${h.url}
29
+ Existing PR: ${f.url}
30
30
 
31
- To create a new PR, you must first close/merge the existing PR manually or use a different branch.`}],meta:{success:!1,state:"error"}};if(h.exists&&h.state==="open"){let k=Oe(a,u,c);if(k&&k.commits>0){let v=k.commitMessages.slice(0,5).map(A=>`• ${A.hash} ${A.message} (${A.author})`).join(`
32
- `),I=k.commits>5?`
33
- ...and ${k.commits-5} more commits`:"",x=["🔄 **New commits pushed**","",`${k.commits} new commits (+${k.insertions} / -${k.deletions})`,"","### Latest commits:",v+I,"","---","🤖 [openclaw-code-agent](https://github.com/goldmar/openclaw-code-agent)"].join(`
34
- `);if(Qa(a,h.number,x,f)){p({prUrl:h.url,prNumber:h.number,targetRepo:f});let A=rt({kind:"pr-updated",branch:u,prUrl:h.url});return S.notifyWorktreeOutcome(o.notificationTarget,A,{completionWakeOutcomeKey:qi({action:"updated",branchName:u,prUrl:h.url,prNumber:h.number,targetRepo:f,diffSummary:k}),detailLines:Bi({action:"updated",branchName:u,baseBranch:c,prUrl:h.url,prNumber:h.number,targetRepo:f,commits:k.commits,insertions:k.insertions,deletions:k.deletions})}),{content:[{type:"text",text:`${A}
31
+ To create a new PR, you must first close/merge the existing PR manually or use a different branch.`}],meta:{success:!1,state:"error"}};if(f.exists&&f.state==="open"){let y=We(l,u,c);if(y&&y.commits>0){let S=y.commitMessages.slice(0,5).map(A=>`• ${A.hash} ${A.message} (${A.author})`).join(`
32
+ `),R=y.commits>5?`
33
+ ...and ${y.commits-5} more commits`:"",I=["🔄 **New commits pushed**","",`${y.commits} new commits (+${y.insertions} / -${y.deletions})`,"","### Latest commits:",S+R,"","---","🤖 [openclaw-code-agent](https://github.com/goldmar/openclaw-code-agent)"].join(`
34
+ `);if(nl(l,f.number,I,m)){g({prUrl:f.url,prNumber:f.number,targetRepo:m});let A=it({kind:"pr-updated",branch:u,prUrl:f.url});return v.notifyWorktreeOutcome(o.notificationTarget,A,{completionWakeOutcomeKey:Gi({action:"updated",branchName:u,prUrl:f.url,prNumber:f.number,targetRepo:m,diffSummary:y}),detailLines:Vi({action:"updated",branchName:u,baseBranch:c,prUrl:f.url,prNumber:f.number,targetRepo:m,commits:y.commits,insertions:y.insertions,deletions:y.deletions})}),{content:[{type:"text",text:`${A}
35
35
 
36
- 📝 Added comment detailing ${k.commits} new commits (+${k.insertions} / -${k.deletions})`}],meta:{success:!0,state:"pr_updated"}}}else return{content:[{type:"text",text:`⚠️ Pushed to ${h.url} but failed to add comment.
36
+ 📝 Added comment detailing ${y.commits} new commits (+${y.insertions} / -${y.deletions})`}],meta:{success:!0,state:"pr_updated"}}}else return{content:[{type:"text",text:`⚠️ Pushed to ${f.url} but failed to add comment.
37
37
 
38
- ${k.commits} new commits (+${k.insertions} / -${k.deletions})`}],meta:{success:!0,state:"pr_open"}}}else return p({prUrl:h.url,prNumber:h.number,targetRepo:f}),{content:[{type:"text",text:`ℹ️ PR already exists and is up to date: ${h.url}
38
+ ${y.commits} new commits (+${y.insertions} / -${y.deletions})`}],meta:{success:!0,state:"pr_open"}}}else return g({prUrl:f.url,prNumber:f.number,targetRepo:m}),{content:[{type:"text",text:`ℹ️ PR already exists and is up to date: ${f.url}
39
39
 
40
- No new commits to push.`}],meta:{success:!0,state:"pr_open"}}}else if(h.exists&&h.state==="merged"){let k={...$t({worktreeBaseBranch:s?.worktreeBaseBranch??i?.worktreeBaseBranch??c,worktreePrTargetRepo:s?.worktreePrTargetRepo??i?.worktreePrTargetRepo,worktreePushRemote:s?.worktreePushRemote??i?.worktreePushRemote},{resolutionSource:"agent_pr",clearResolverSessionId:!0}),worktreePrUrl:h.url,worktreePrNumber:h.number,worktreeDisposition:"merged",worktreeDecisionSnoozedUntil:void 0};for(let v of Sn(o))S.updatePersistedSession(v,k);return{content:[{type:"text",text:`✅ PR was already merged: ${h.url}
40
+ No new commits to push.`}],meta:{success:!0,state:"pr_open"}}}else if(f.exists&&f.state==="merged"){let y={...Dt({worktreeBaseBranch:s?.worktreeBaseBranch??i?.worktreeBaseBranch??c,worktreePrTargetRepo:s?.worktreePrTargetRepo??i?.worktreePrTargetRepo,worktreePushRemote:s?.worktreePushRemote??i?.worktreePushRemote},{resolutionSource:"agent_pr",clearResolverSessionId:!0}),worktreePrUrl:f.url,worktreePrNumber:f.number,worktreeDisposition:"merged",worktreeDecisionSnoozedUntil:void 0};for(let S of vn(o))v.updatePersistedSession(S,y);return{content:[{type:"text",text:`✅ PR was already merged: ${f.url}
41
41
 
42
- The worktree branch ${u} can be cleaned up with agent_merge(delete_branch=true).`}],meta:{success:!0,state:"merged"}}}else{if(h.exists&&h.state==="closed")return{content:[{type:"text",text:`⚠️ A PR exists but was closed without merging: ${h.url}
42
+ The worktree branch ${u} can be cleaned up with agent_merge(delete_branch=true).`}],meta:{success:!0,state:"merged"}}}else{if(f.exists&&f.state==="closed")return{content:[{type:"text",text:`⚠️ A PR exists but was closed without merging: ${f.url}
43
43
 
44
44
  What would you like to do?
45
45
 
@@ -47,227 +47,229 @@ What would you like to do?
47
47
  2. Close and delete the branch with agent_merge(delete_branch=true), then start a new session/worktree
48
48
  3. Manually delete the closed PR on GitHub, then call agent_pr(force_new=true) to create a fresh PR
49
49
 
50
- (This tool cannot automatically reopen or recreate PRs to avoid unintended actions.)`}],meta:{success:!1,state:"closed"}};{let k=!r.title||!r.body?Oe(a,u,c):void 0,v;if(!r.title||!r.body){let A=await Nr({sessionName:d,branchName:u,prompt:o.prompt,diffSummary:k,provider:e.metadataProvider});if(A.ok===!1)return{content:[{type:"text",text:`❌ ${A.error}`}],meta:{success:!1,state:"error"}};v=A.metadata}let I=r.title??v.title,x=r.body;x||(x=Lr({sessionName:d,metadata:v,diffSummary:k}));let b=za(a,u,c,I,x,f,{draft:!0});if(b.success&&b.prUrl){let A=Mt(a,u,f);p({prUrl:b.prUrl,prNumber:A.number,targetRepo:f,disposition:"pr-opened"});let y=rt({kind:"pr-opened",branch:u,targetRepo:f,prUrl:b.prUrl});return S.notifyWorktreeOutcome(o.notificationTarget,y,{completionWakeOutcomeKey:qi({action:"opened",branchName:u,prUrl:b.prUrl,prNumber:A.number,targetRepo:f}),detailLines:Bi({action:"opened",branchName:u,baseBranch:c,prUrl:b.prUrl,prNumber:A.number,targetRepo:f})}),{content:[{type:"text",text:b.warnings&&b.warnings.length>0?`${y}
50
+ (This tool cannot automatically reopen or recreate PRs to avoid unintended actions.)`}],meta:{success:!1,state:"closed"}};{let y=!r.title||!r.body?We(l,u,c):void 0,S;if(!r.title||!r.body){let A=await Br({sessionName:d,branchName:u,prompt:o.prompt,diffSummary:y,provider:e.metadataProvider});if(A.ok===!1)return{content:[{type:"text",text:`❌ ${A.error}`}],meta:{success:!1,state:"error"}};S=A.metadata}let R=r.title??S.title,I=r.body;I||(I=Fr({sessionName:d,metadata:S,diffSummary:y}));let b=tl(l,u,c,R,I,m,{draft:!0});if(b.success&&b.prUrl){let A=$t(l,u,m);g({prUrl:b.prUrl,prNumber:A.number,targetRepo:m,disposition:"pr-opened"});let k=it({kind:"pr-opened",branch:u,targetRepo:m,prUrl:b.prUrl});return v.notifyWorktreeOutcome(o.notificationTarget,k,{completionWakeOutcomeKey:Gi({action:"opened",branchName:u,prUrl:b.prUrl,prNumber:A.number,targetRepo:m}),detailLines:Vi({action:"opened",branchName:u,baseBranch:c,prUrl:b.prUrl,prNumber:A.number,targetRepo:m})}),{content:[{type:"text",text:b.warnings&&b.warnings.length>0?`${k}
51
51
 
52
- ⚠️ ${b.warnings.join("; ")}`:y}],meta:{success:!0,state:"created"}}}else return{content:[{type:"text",text:`❌ Failed to create PR: ${b.error??"unknown error"}`}],meta:{success:!1,state:"error"}}}}}}}var Fr=H(()=>{te();N();ye();Fi();kn();vn();Fi()});import{readdirSync as Vy,statSync as Gy,rmSync as jy}from"fs";import{execFileSync as Hy}from"child_process";import{join as Ru}from"path";te();N();function $u(t){return t.length>80?`${t.slice(0,80)}...`:t}function Eu(t){return t.worktreePath?!t.originalWorkdir||t.originalWorkdir===t.worktreePath?`${t.worktreePath} (worktree)`:`${t.worktreePath} (worktree of ${t.originalWorkdir})`:t.workdir}function Du(t){let e=["Session launched successfully.",` Name: ${t.sessionName}`,` ID: ${t.sessionId}`,` Harness: ${t.harness}`,` Permission mode: ${t.permissionMode}`,` Plan approval: ${t.planApproval}`,` Worktree strategy: ${t.worktreeStrategy??"off"}`,...t.repoIntegrationPolicy?[` Repo policy: ${t.repoIntegrationPolicy}${t.repoProvider?` (${t.repoProvider})`:""}`]:[],` Resolved workdir: ${Eu(t)}`,` Model: ${t.model??"default"}`,` Prompt: "${$u(t.prompt)}"`];return t.reasoningEffort&&e.push(` Reasoning effort: ${t.reasoningEffort}`),t.fastMode&&e.push(" Fast mode: enabled"),t.resumeSessionId?e.push(` Resume: ${t.resumeSessionId}${t.forkSession?" (forked)":""}`):t.forceNewSession&&e.push(" Force new session: true"),t.clearedPersistedCodexResume&&e.push(" Thread state: historical Codex state cleared; starting a fresh thread."),e.push(" Mode: multi-turn (use agent_respond to send follow-up messages)"),e.push("","Use agent_sessions to check status, agent_output to see output."),e.join(`
53
- `)}function Mn(t,e){return Du({...t,sessionId:e.id,sessionName:e.name,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,worktreeStrategy:e.worktreeStrategy??"off",repoIntegrationPolicy:e.repoIntegrationPolicy,repoProvider:e.repoProvider,worktreePath:e.worktreePath,originalWorkdir:e.originalWorkdir})}ie();function mt(t){let{requestedResumeSessionId:e,activeSession:n,persistedSession:r}=t;return e?n?{resumeSessionId:e,clearedPersistedCodexResume:!1}:r?.harness==="codex"&&r.backendRef?.kind!=="codex-app-server"?{resumeSessionId:void 0,clearedPersistedCodexResume:!0}:{resumeSessionId:e,clearedPersistedCodexResume:!1}:{resumeSessionId:void 0,clearedPersistedCodexResume:!1}}Z();function Jn(t){return"id"in t?t.id:t.sessionId}function sn(t){return t.status==="completed"||t.killReason==="done"}function sp(t){return!sn(t)||!$(t)?!1:t.backendRef?.kind==="codex-app-server"||t.backendRef?.kind==="opencode-server"}function ap(t){return(t.killReason==="shutdown"||t.killReason==="startup-timeout")&&!$(t)}function an(t){if(t.status==="running")return{kind:"direct",reason:"already_running"};let e=Jn(t);if(sn(t)&&!sp(t))return{kind:"unavailable",reason:"completed",stableSessionId:e};let n=$(t);if(n){let r="harnessName"in t?void 0:t,{resumeSessionId:o,clearedPersistedCodexResume:i}=mt({requestedResumeSessionId:n,activeSession:"harnessName"in t?{harnessSessionId:n}:void 0,persistedSession:r?{harness:r.harness,backendRef:r.backendRef}:void 0});return o?{kind:"resume",resumeSessionId:o,stableSessionId:e,clearedPersistedCodexResume:i}:{kind:"unavailable",reason:"legacy_non_resumable",stableSessionId:e,clearedPersistedCodexResume:i}}return ap(t)?{kind:"relaunch",stableSessionId:e}:{kind:"unavailable",reason:"missing_backend_state",stableSessionId:e}}ie();Kn();import{existsSync as ha}from"fs";Z();function ma(t){return t==null?void 0:String(t).trim()||void 0}function lp(t){return t.trim().replace(/^['"`](.*)['"`]$/s,"$1").trim()}function dp(t){let e=t.split(/\n\s*\n/,1)[0]?.split(`
54
- `).map(n=>n.trim()).filter(Boolean)??[];if(e.length!==0)for(let n of e){let r=n.match(/^(Workdir|Repo):\s*(.+)$/),o=lp(r?.[2]??"");if(o.startsWith("/")&&ha(o))return o}}function fa(t,e){return t.workdir!==e.workdir?!1:e.originSessionKey&&t.originSessionKey?t.originSessionKey===e.originSessionKey:!e.originChannel||!t.originChannel?!1:t.originChannel===e.originChannel&&ma(t.originThreadId)===ma(e.originThreadId)}function ga(t){return t.slice(0,3).map(e=>` - ${e.name} [${e.ref}] | status=${e.status}${e.lifecycle?` | lifecycle=${e.lifecycle}`:""}`).join(`
55
- `)}function up(t,e){let n=[],r=[],o=new Set;for(let i of t.list?.("all")??[]){if(!fa(i,e))continue;let s=i.id;if(!o.has(s)){if(o.add(s),i.isExplicitlyResumable){n.push({ref:i.id,name:i.name,status:i.status,lifecycle:i.lifecycle,resumable:!0});continue}(i.status==="starting"||i.status==="running")&&r.push({ref:i.id,name:i.name,status:i.status,lifecycle:i.lifecycle,resumable:!1})}}for(let i of t.listPersistedSessions?.()??[]){if(!i.resumable||!fa(i,e))continue;let s=U(i)??i.harnessSessionId,l=i.sessionId??$(i)??i.harnessSessionId;!s||!l||o.has(l)||(o.add(l),n.push({ref:s,name:i.name,status:i.status,lifecycle:i.lifecycle,resumable:!0}))}return{resumable:n,active:r}}function Yn(t,e,n){let r=t.workdir||dp(t.prompt)||e.workspaceDir||D.defaultWorkdir||process.cwd();if(!ha(r))return{kind:"error",text:`Error: Working directory does not exist: ${r}`};let o=t.harness??ae(),i=ut(o),s=t.model??i,l=De(o,s),a=t.model!==void 0,d=_n(o);if(!l&&(o!=="opencode"||d&&d.length>0))return{kind:"error",text:`Error: No default model configured for harness "${o}". Set plugins.entries["openclaw-code-agent"].config.harnesses.${o}.defaultModel or pass model explicitly.`};if(l&&!kt(o,l))return{kind:"error",text:`Error: Model "${s}" is not supported for harness "${o}". Use a bare Codex model id such as "gpt-5.5".`};if(l&&d&&d.length>0&&!qn(o,l,d))return{kind:"error",text:a?`Error: Model "${s}" is not allowed. Permitted models: ${d.join(", ")}`:`Error: Default model "${s||"undefined"}" is not in allowedModels (${d.join(", ")}). Update your plugin config to set a compatible defaultModel.`};let u=Un(o,l,d),c=$n(e),m=Zt(e,c||Je(r)),p=e.sessionKey||void 0,f=Es(p)??Zo(e);if(!t.resume_session_id&&!t.force_new_session){let y=up(n,{workdir:r,originSessionKey:p,originChannel:m,originThreadId:f});if(y.resumable.length>0||y.active.length>0){let w=y.resumable.length>0?["Linked resumable session(s) already exist for this thread/workdir:",ga(y.resumable),"","Resume the latest one with:",` agent_respond(session='${y.resumable[0].ref}', message='<next instruction>')`,"Fork from it with:",` agent_launch(prompt='<new task>', resume_session_id='${y.resumable[0].ref}', fork_session=true)`].join(`
56
- `):"",F=y.active.length>0?[y.resumable.length>0?"Linked active session(s):":"Linked active session(s) already exist for this thread/workdir:",ga(y.active),"","Send a follow-up instead of launching a duplicate:",` agent_respond(session='${y.active[0].ref}', message='<next instruction>')`].join(`
57
- `):"";return{kind:"blocked",text:["Resume-first protection blocked a fresh launch.","",w,F,["If you intentionally want a brand-new independent session here, call:"," agent_launch(prompt='<new task>', force_new_session=true)"].join(`
52
+ ⚠️ ${b.warnings.join("; ")}`:k}],meta:{success:!0,state:"created"}}}else return{content:[{type:"text",text:`❌ Failed to create PR: ${b.error??"unknown error"}`}],meta:{success:!1,state:"error"}}}}}}}var qr=H(()=>{ne();B();ke();Ui();Sn();wn();Ui()});import{readdirSync as ak,statSync as lk,rmSync as dk}from"fs";import{execFileSync as uk}from"child_process";import{join as Wu}from"path";ne();B();function Vu(t){return t.length>80?`${t.slice(0,80)}...`:t}function Gu(t){return t.worktreePath?!t.originalWorkdir||t.originalWorkdir===t.worktreePath?`${t.worktreePath} (worktree)`:`${t.worktreePath} (worktree of ${t.originalWorkdir})`:t.workdir}function ju(t){let e=["Session launched successfully.",` Name: ${t.sessionName}`,` ID: ${t.sessionId}`,` Harness: ${t.harness}`,` Permission mode: ${t.permissionMode}`,` Plan approval: ${t.planApproval}`,` Worktree strategy: ${t.worktreeStrategy??"off"}`,...t.repoIntegrationPolicy?[` Repo policy: ${t.repoIntegrationPolicy}${t.repoProvider?` (${t.repoProvider})`:""}`]:[],` Resolved workdir: ${Gu(t)}`,` Model: ${t.model??"default"}`,` Prompt: "${Vu(t.prompt)}"`];return t.reasoningEffort&&e.push(` Reasoning effort: ${t.reasoningEffort}`),t.fastMode&&e.push(" Fast mode: enabled"),t.resumeSessionId?e.push(` Resume: ${t.resumeSessionId}${t.forkSession?" (forked)":""}`):t.forceNewSession&&e.push(" Force new session: true"),t.clearedPersistedCodexResume&&e.push(" Thread state: historical Codex state cleared; starting a fresh thread."),e.push(" Mode: multi-turn (use agent_respond to send follow-up messages)"),e.push("","Use agent_sessions to check status, agent_output to see output."),e.join(`
53
+ `)}function $n(t,e){return ju({...t,sessionId:e.id,sessionName:e.name,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,worktreeStrategy:e.worktreeStrategy??"off",repoIntegrationPolicy:e.repoIntegrationPolicy,repoProvider:e.repoProvider,worktreePath:e.worktreePath,originalWorkdir:e.originalWorkdir})}se();function gt(t){let{requestedResumeSessionId:e,activeSession:n,persistedSession:r}=t;return e?n?{resumeSessionId:e,clearedPersistedCodexResume:!1}:r?.harness==="codex"&&r.backendRef?.kind!=="codex-app-server"?{resumeSessionId:void 0,clearedPersistedCodexResume:!0}:{resumeSessionId:e,clearedPersistedCodexResume:!1}:{resumeSessionId:void 0,clearedPersistedCodexResume:!1}}X();function Zn(t){return"id"in t?t.id:t.sessionId}function an(t){return t.status==="completed"||t.killReason==="done"}function kp(t){return!an(t)||!$(t)?!1:t.backendRef?.kind==="codex-app-server"||t.backendRef?.kind==="opencode-server"}function Sp(t){return(t.killReason==="shutdown"||t.killReason==="startup-timeout")&&!$(t)}function ln(t){if(t.status==="running")return{kind:"direct",reason:"already_running"};let e=Zn(t);if(an(t)&&!kp(t))return{kind:"unavailable",reason:"completed",stableSessionId:e};let n=$(t);if(n){let r="harnessName"in t?void 0:t,{resumeSessionId:o,clearedPersistedCodexResume:i}=gt({requestedResumeSessionId:n,activeSession:"harnessName"in t?{harnessSessionId:n}:void 0,persistedSession:r?{harness:r.harness,backendRef:r.backendRef}:void 0});return o?{kind:"resume",resumeSessionId:o,stableSessionId:e,clearedPersistedCodexResume:i}:{kind:"unavailable",reason:"legacy_non_resumable",stableSessionId:e,clearedPersistedCodexResume:i}}return Sp(t)?{kind:"relaunch",stableSessionId:e}:{kind:"unavailable",reason:"missing_backend_state",stableSessionId:e}}se();Gn();import{existsSync as ba}from"fs";X();function va(t){return t==null?void 0:String(t).trim()||void 0}function vp(t){return t.trim().replace(/^['"`](.*)['"`]$/s,"$1").trim()}function wp(t){let e=t.split(/\n\s*\n/,1)[0]?.split(`
54
+ `).map(n=>n.trim()).filter(Boolean)??[];if(e.length!==0)for(let n of e){let r=n.match(/^(Workdir|Repo):\s*(.+)$/),o=vp(r?.[2]??"");if(o.startsWith("/")&&ba(o))return o}}function wa(t,e){return t.workdir!==e.workdir?!1:e.originSessionKey&&t.originSessionKey?t.originSessionKey===e.originSessionKey:!e.originChannel||!t.originChannel?!1:t.originChannel===e.originChannel&&va(t.originThreadId)===va(e.originThreadId)}function Pa(t){return t.slice(0,3).map(e=>` - ${e.name} [${e.ref}] | status=${e.status}${e.lifecycle?` | lifecycle=${e.lifecycle}`:""}`).join(`
55
+ `)}function Pp(t,e){let n=[],r=[],o=new Set;for(let i of t.list?.("all")??[]){if(!wa(i,e))continue;let s=i.id;if(!o.has(s)){if(o.add(s),i.isExplicitlyResumable){n.push({ref:i.id,name:i.name,status:i.status,lifecycle:i.lifecycle,resumable:!0});continue}(i.status==="starting"||i.status==="running")&&r.push({ref:i.id,name:i.name,status:i.status,lifecycle:i.lifecycle,resumable:!1})}}for(let i of t.listPersistedSessions?.()??[]){if(!i.resumable||!wa(i,e))continue;let s=U(i)??i.harnessSessionId,a=i.sessionId??$(i)??i.harnessSessionId;!s||!a||o.has(a)||(o.add(a),n.push({ref:s,name:i.name,status:i.status,lifecycle:i.lifecycle,resumable:!0}))}return{resumable:n,active:r}}function Xn(t,e,n){let r=t.workdir||wp(t.prompt)||e.workspaceDir||D.defaultWorkdir||process.cwd();if(!ba(r))return{kind:"error",text:`Error: Working directory does not exist: ${r}`};let o=t.harness??le(),i=pt(o),s=t.model??i,a=Oe(o,s),l=t.model!==void 0,d=En(o);if(!a&&(o!=="opencode"||d&&d.length>0))return{kind:"error",text:`Error: No default model configured for harness "${o}". Set plugins.entries["openclaw-code-agent"].config.harnesses.${o}.defaultModel or pass model explicitly.`};if(a&&!vt(o,a))return{kind:"error",text:`Error: Model "${s}" is not supported for harness "${o}". Use a bare Codex model id such as "gpt-5.5".`};if(a&&d&&d.length>0&&!Un(o,a,d))return{kind:"error",text:l?`Error: Model "${s}" is not allowed. Permitted models: ${d.join(", ")}`:`Error: Default model "${s||"undefined"}" is not in allowedModels (${d.join(", ")}). Update your plugin config to set a compatible defaultModel.`};let u=Vn(o,a,d),c=Dn(e),p=Xt(e,c||Ze(r)),g=e.sessionKey||void 0,m=Fs(g)??ni(e);if(!t.resume_session_id&&!t.force_new_session){let k=Pp(n,{workdir:r,originSessionKey:g,originChannel:p,originThreadId:m});if(k.resumable.length>0||k.active.length>0){let P=k.resumable.length>0?["Linked resumable session(s) already exist for this thread/workdir:",Pa(k.resumable),"","Resume the latest one with:",` agent_respond(session='${k.resumable[0].ref}', message='<next instruction>')`,"Fork from it with:",` agent_launch(prompt='<new task>', resume_session_id='${k.resumable[0].ref}', fork_session=true)`].join(`
56
+ `):"",F=k.active.length>0?[k.resumable.length>0?"Linked active session(s):":"Linked active session(s) already exist for this thread/workdir:",Pa(k.active),"","Send a follow-up instead of launching a duplicate:",` agent_respond(session='${k.active[0].ref}', message='<next instruction>')`].join(`
57
+ `):"";return{kind:"blocked",text:["Resume-first protection blocked a fresh launch.","",P,F,["If you intentionally want a brand-new independent session here, call:"," agent_launch(prompt='<new task>', force_new_session=true)"].join(`
58
58
  `)].filter(Boolean).join(`
59
59
 
60
- `)}}}let h=t.resume_session_id,k=h?n.resolve?.(h):void 0,v=h?n.getPersistedSession?.(h):void 0;if(h){let y=n.resolveBackendConversationId?.(h)??n.resolveHarnessSessionId?.(h);if(!y)return{kind:"error",text:`Error: Could not resolve resume_session_id "${h}" to a session ID. Use agent_sessions to list available sessions.`};h=y}let{resumeSessionId:I,clearedPersistedCodexResume:x}=mt({requestedResumeSessionId:h,activeSession:k?{harnessSessionId:k.backendConversationId??k.harnessSessionId}:void 0,persistedSession:v?{harness:v.harness,backendRef:v.backendRef}:void 0}),b=t.permission_mode??D.permissionMode,A=t.plan_approval??D.planApproval;return{kind:"resolved",workdir:r,harness:o,resolvedModel:u,permissionMode:b,planApproval:A,originChannel:m,originThreadId:f,originSessionKey:p,route:pt(e,m,p),resumeSessionId:I,resolvedResumeId:h,clearedPersistedCodexResume:x,reasoningEffort:Be(o),fastMode:ct(o)}}Z();function ln(t){let e=t.harness?.trim(),n=t.model?.trim();return e&&n?`${e} | ${n}`:e?`${e} | default`:n}function Zn(t){let e=ln(t);return e?` | ${e}`:""}function Re(t){let e=Math.floor(t/1e3),n=Math.floor(e/60),r=e%60;return n>0?`${n}m${r}s`:`${r}s`}var cp=new Set(["a","an","the","is","are","was","were","be","been","being","have","has","had","do","does","did","will","would","could","should","may","might","shall","can","need","must","i","me","my","we","our","you","your","it","its","he","she","to","of","in","for","on","with","at","by","from","as","into","through","about","that","this","these","those","and","or","but","if","then","so","not","no","please","just","also","very","all","some","any","each","make","write","create","build","implement","add","update"]);function ka(t){let n=t.toLowerCase().replace(/[^a-z0-9\s-]/g," ").split(/\s+/).filter(r=>r.length>1&&!cp.has(r)).slice(0,3);return n.length===0?"session":n.join("-")}var ya={starting:"🟡",running:"🟢",completed:"✅",failed:"❌",killed:"⛔",awaiting_plan_decision:"📋",awaiting_user_input:"❓",awaiting_worktree_decision:"🌿",suspended:"⏸️",terminal:"🏁"};function pp(t){let e=t.worktreeLifecycle?.state??t.worktreeState;return t.worktreeMerged||e==="merged"?"[merged ✓]":e==="released"?"[released]":t.worktreePrUrl?`[PR: ${t.worktreePrUrl}]`:e==="pr_open"?"[PR open]":e==="dismissed"?"[dismissed]":e==="no_change"?"[no change]":"[not merged]"}function Sa(t){let e=ya[t.phase]??ya[t.status]??"❓",n=Re(t.duration),r=t.multiTurn?"multi-turn":"single",o=t.prompt.length>80?t.prompt.slice(0,80)+"...":t.prompt,i=t.costUsd>0?` | $${t.costUsd.toFixed(2)}`:"",s=[`${e} ${t.name} [${t.id}] (${n}${i}) — ${r}`,` 📁 ${t.workdir}`,` 📝 "${o}"`];t.worktreePath&&t.worktreeBranch&&s.push(` 🌿 Worktree: ${t.worktreeBranch} ${pp(t)}`),t.phase!==t.status&&s.push(` ⚙️ Phase: ${t.phase}`),t.lifecycle&&t.lifecycle!==t.phase&&s.push(` 🔄 Lifecycle: ${t.lifecycle}`),(t.requestedPermissionMode||t.currentPermissionMode||t.approvalExecutionState)&&s.push(` 🔐 Approval: ${t.approvalExecutionState??"unknown"} (requested=${t.requestedPermissionMode??"unknown"}, effective=${t.currentPermissionMode??"unknown"})`),t.resumable&&s.push(" ↩️ Resumable: yes"),t.recovered&&s.push(" ♻️ Recovered: persisted metadata only; no live process to kill"),t.harness?s.push(` 🧰 Harness | model: ${ln({harness:t.harness,model:t.model})}`):t.model&&s.push(` 🧰 Harness | model: ${t.model}`);let l=$(t);return l&&s.push(` 🔗 Backend ID: ${l}`),t.resumeSessionId&&s.push(` ↩️ Resumed from: ${t.resumeSessionId}${t.forkSession?" (forked)":""}`),s.join(`
61
- `)}function Xn(t,e){let n=t.sessionsWithDuration>0?t.totalDurationMs/t.sessionsWithDuration:0,{completed:r,failed:o,killed:i}=t.sessionsByStatus,s=["📊 OpenClaw Code Agent Stats","","📋 Sessions",` Launched: ${t.totalLaunched}`,` Running: ${e}`,` Completed: ${r}`,` Failed: ${o}`,` Killed: ${i}`,"",`⏱️ Average duration: ${n>0?Re(n):"n/a"}`];if(t.mostExpensive){let l=t.mostExpensive;s.push("","🏆 Notable session",` ${l.name} [${l.id}]`,` 📝 "${l.prompt}"`)}return s.join(`
62
- `)}function se(t,e){return e<=0?"":t.length<=e?t:e<=3?".".repeat(e):t.slice(0,e-3)+"..."}function va(t,e){let n=t.split(`
60
+ `)}}}let f=t.resume_session_id,y=f?n.resolve?.(f):void 0,S=f?n.getPersistedSession?.(f):void 0;if(f){let k=n.resolveBackendConversationId?.(f)??n.resolveHarnessSessionId?.(f);if(!k)return{kind:"error",text:`Error: Could not resolve resume_session_id "${f}" to a session ID. Use agent_sessions to list available sessions.`};f=k}let{resumeSessionId:R,clearedPersistedCodexResume:I}=gt({requestedResumeSessionId:f,activeSession:y?{harnessSessionId:y.backendConversationId??y.harnessSessionId}:void 0,persistedSession:S?{harness:S.harness,backendRef:S.backendRef}:void 0}),b=t.permission_mode??D.permissionMode,A=t.plan_approval??D.planApproval;return{kind:"resolved",workdir:r,harness:o,resolvedModel:u,permissionMode:b,planApproval:A,originChannel:p,originThreadId:m,originSessionKey:g,route:ft(e,p,g),resumeSessionId:R,resolvedResumeId:f,clearedPersistedCodexResume:I,reasoningEffort:Ke(o),fastMode:mt(o)}}X();function dn(t){let e=t.harness?.trim(),n=t.model?.trim();return e&&n?`${e} | ${n}`:e?`${e} | default`:n}function er(t){let e=dn(t);return e?` | ${e}`:""}function Ae(t){let e=Math.floor(t/1e3),n=Math.floor(e/60),r=e%60;return n>0?`${n}m${r}s`:`${r}s`}var bp=new Set(["a","an","the","is","are","was","were","be","been","being","have","has","had","do","does","did","will","would","could","should","may","might","shall","can","need","must","i","me","my","we","our","you","your","it","its","he","she","to","of","in","for","on","with","at","by","from","as","into","through","about","that","this","these","those","and","or","but","if","then","so","not","no","please","just","also","very","all","some","any","each","make","write","create","build","implement","add","update"]);function Aa(t){let n=t.toLowerCase().replace(/[^a-z0-9\s-]/g," ").split(/\s+/).filter(r=>r.length>1&&!bp.has(r)).slice(0,3);return n.length===0?"session":n.join("-")}var Ra={starting:"🟡",running:"🟢",completed:"✅",failed:"❌",killed:"⛔",awaiting_plan_decision:"📋",awaiting_user_input:"❓",awaiting_worktree_decision:"🌿",suspended:"⏸️",terminal:"🏁"};function Rp(t){let e=t.worktreeLifecycle?.state??t.worktreeState;return t.worktreeMerged||e==="merged"?"[merged ✓]":e==="released"?"[released]":t.worktreePrUrl?`[PR: ${t.worktreePrUrl}]`:e==="pr_open"?"[PR open]":e==="dismissed"?"[dismissed]":e==="no_change"?"[no change]":"[not merged]"}function Ia(t){let e=Ra[t.phase]??Ra[t.status]??"❓",n=Ae(t.duration),r=t.multiTurn?"multi-turn":"single",o=t.prompt.length>80?t.prompt.slice(0,80)+"...":t.prompt,i=t.costUsd>0?` | $${t.costUsd.toFixed(2)}`:"",s=[`${e} ${t.name} [${t.id}] (${n}${i}) — ${r}`,` 📁 ${t.workdir}`,` 📝 "${o}"`];t.worktreePath&&t.worktreeBranch&&s.push(` 🌿 Worktree: ${t.worktreeBranch} ${Rp(t)}`),t.phase!==t.status&&s.push(` ⚙️ Phase: ${t.phase}`),t.lifecycle&&t.lifecycle!==t.phase&&s.push(` 🔄 Lifecycle: ${t.lifecycle}`),(t.requestedPermissionMode||t.currentPermissionMode||t.approvalExecutionState)&&s.push(` 🔐 Approval: ${t.approvalExecutionState??"unknown"} (requested=${t.requestedPermissionMode??"unknown"}, effective=${t.currentPermissionMode??"unknown"})`),t.resumable&&s.push(" ↩️ Resumable: yes"),t.recovered&&s.push(" ♻️ Recovered: persisted metadata only; no live process to kill"),t.harness?s.push(` 🧰 Harness | model: ${dn({harness:t.harness,model:t.model})}`):t.model&&s.push(` 🧰 Harness | model: ${t.model}`);let a=$(t);return a&&s.push(` 🔗 Backend ID: ${a}`),t.resumeSessionId&&s.push(` ↩️ Resumed from: ${t.resumeSessionId}${t.forkSession?" (forked)":""}`),s.join(`
61
+ `)}function tr(t,e){let n=t.sessionsWithDuration>0?t.totalDurationMs/t.sessionsWithDuration:0,{completed:r,failed:o,killed:i}=t.sessionsByStatus,s=["📊 OpenClaw Code Agent Stats","","📋 Sessions",` Launched: ${t.totalLaunched}`,` Running: ${e}`,` Completed: ${r}`,` Failed: ${o}`,` Killed: ${i}`,"",`⏱️ Average duration: ${n>0?Ae(n):"n/a"}`];if(t.mostExpensive){let a=t.mostExpensive;s.push("","🏆 Notable session",` ${a.name} [${a.id}]`,` 📝 "${a.prompt}"`)}return s.join(`
62
+ `)}function ae(t,e){return e<=0?"":t.length<=e?t:e<=3?".".repeat(e):t.slice(0,e-3)+"..."}function xa(t,e){let n=t.split(`
63
63
  `),r=[],o=0;for(let i=n.length-1;i>=0;i--){let s=n[i].length+(r.length>0?1:0);if(o+s>e&&r.length>0)break;r.unshift(n[i]),o+=s}return r.join(`
64
- `)}function Pa(t,e){let n=t.split(`
64
+ `)}function Ta(t,e){let n=t.split(`
65
65
  `),r=[],o=0;for(let i=0;i<n.length;i++){let s=n[i].length+(r.length>0?1:0);if(o+s>e&&r.length>0)break;r.push(n[i]),o+=s}return r.join(`
66
- `)}var Ze,dn,Pt=!1;function wa(t){try{return t?.config?.current?.()}catch{return}}function wt(t,e){if(t&&typeof t=="object"){Ze=t,arguments.length>=2?(dn=e,Pt=!0):Pt||(dn=wa(Ze),Pt=!0);return}Ze=void 0,dn=void 0,Pt=!1}function bt(){return Ze}function ba(){return Ze?.tasks?.managedFlows??Ze?.taskFlow}function Ra(){return Pt||(dn=wa(Ze),Pt=!0),dn}var mp="openclaw-code-agent",fp=160,er={create(){},progress(){},finalize(){}};function tr(t,e){let n=e instanceof Error?e.message:String(e);`${t}${n}`}function gp(t,e){if(e.applied===!1){let n=e.code?` (${e.code})`:"";`${t}${n}`}}function hp(t){let e=t.prompt.trim().replace(/\s+/g," ");return se(e||t.name,fp)}function yp(t){if(t.status==="starting"||t.lifecycle==="starting")return"Starting";if(t.lifecycle==="active")return"Running";if(t.lifecycle==="awaiting_plan_decision")return"Waiting for plan approval";if(t.lifecycle==="awaiting_user_input")return"Waiting for input";if(t.lifecycle==="awaiting_worktree_decision")return"Waiting for worktree decision";if(t.lifecycle==="suspended")return"Suspended after idle timeout"}function kp(t){if(t.status==="completed")return"succeeded";if(t.status==="failed")return"failed";if(t.status==="killed")return t.killReason==="idle-timeout"||t.killReason==="startup-timeout"?"timed_out":"cancelled"}function fi(t,e){return t==="completed"?"Completed":t==="failed"?"Failed":e==="idle-timeout"?"Timed out after idle timeout":e==="startup-timeout"?"Timed out during startup":e==="shutdown"?"Cancelled during shutdown":e==="user"?"Cancelled by user":"Cancelled"}function Sp(t){return t.lifecycle==="awaiting_plan_decision"||t.lifecycle==="awaiting_user_input"||t.lifecycle==="awaiting_worktree_decision"||t.lifecycle==="suspended"}function gi(t,e,n){return{phase:e,integration:"phase-1-managed-task-flow",sessionId:t.id,sessionName:t.name,sessionStatus:t.status,sessionLifecycle:t.lifecycle,summary:n}}function vp(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.createManaged=="function"&&typeof e.resume=="function"&&typeof e.setWaiting=="function"&&typeof e.finish=="function"&&typeof e.fail=="function"}function Aa(t,e){if(e.applied)return e.flow;let n=e.current;return n?.flowId&&typeof n.revision=="number"?n:t}var hi=class{constructor(e){this.taskFlow=e}taskFlow;flow;finalized=!1;lastProgressKey;create(e){if(this.flow||this.finalized)return;let n="Starting",r=Date.now();try{this.flow=this.taskFlow.createManaged({controllerId:mp,goal:hp(e),status:"running",notifyPolicy:"silent",currentStep:n,stateJson:gi(e,"created",n),createdAt:e.startedAt,updatedAt:r}),this.lastProgressKey=this.progressKey(e,n)}catch(o){tr("create",o)}}progress(e){if(!this.flow||this.finalized)return;let n=yp(e);if(!n)return;let r=this.progressKey(e,n);if(r!==this.lastProgressKey)try{let o=gi(e,"progress",n),i=Date.now(),s=Sp(e)?this.taskFlow.setWaiting({flowId:this.flow.flowId,expectedRevision:this.flow.revision,currentStep:n,stateJson:o,waitJson:{reason:n,sessionId:e.id},blockedSummary:n,updatedAt:i}):this.taskFlow.resume({flowId:this.flow.flowId,expectedRevision:this.flow.revision,status:"running",currentStep:n,stateJson:o,updatedAt:i});this.flow=Aa(this.flow,s),this.lastProgressKey=r}catch(o){tr("progress",o)}}finalize(e){if(!this.flow||this.finalized)return;let n=kp(e);if(!n)return;let r=n==="succeeded"?"Completed":n==="failed"?"Failed":fi(e.status,e.killReason);try{let o=e.completedAt??Date.now(),i={...gi(e,"terminal",r),terminalStatus:n,terminalSummary:fi(e.status,e.killReason),...e.status==="failed"&&e.error?{error:e.error}:{}},s=n==="succeeded"?this.taskFlow.finish({flowId:this.flow.flowId,expectedRevision:this.flow.revision,stateJson:i,updatedAt:o,endedAt:o}):this.taskFlow.fail({flowId:this.flow.flowId,expectedRevision:this.flow.revision,stateJson:i,blockedSummary:fi(e.status,e.killReason),updatedAt:o,endedAt:o});gp("finalize",s),this.flow=Aa(this.flow,s),this.finalized=!0}catch(o){tr("finalize",o)}}progressKey(e,n){return`${e.status}:${e.lifecycle}:${n}`}};function nr(t){if(!t.sessionKey?.trim())return er;try{let e=ba()?.fromToolContext;if(typeof e!="function")return er;let n=e(t);return vp(n)?new hi(n):er}catch(e){return tr("resolve",e),er}}function Pp(t){return t instanceof Error?t.message:String(t)}function Ia(t,e){return t?("id"in t?t.id:t.sessionId)??e??"unknown-session":e??"unknown-session"}function wp(t){return!t||typeof t!="object"?!1:typeof t.prompt=="string"}function bp(t){return!!t&&typeof t=="object"&&typeof t.formatLaunchResult=="function"}function Rp(t){return!!t&&typeof t=="object"&&typeof t.checkRepoPolicyForLaunch=="function"&&typeof t.requestRepoPolicyForLaunch=="function"}function xa(t){return{name:"agent_launch",description:"Launch a coding agent session in background to execute a development task. Sessions are multi-turn — they stay open for follow-up messages via agent_respond. Supports resuming previous sessions. Returns a session ID and name for tracking.",parameters:g.Object({prompt:g.String({description:"The task prompt to execute"}),name:g.Optional(g.String({description:"Short human-readable name for the session (kebab-case, e.g. 'fix-auth'). Auto-generated from prompt if omitted."})),workdir:g.Optional(g.String({description:"Working directory (defaults to cwd)"})),model:g.Optional(g.String({description:"Model name to use"})),system_prompt:g.Optional(g.String({description:"Additional system prompt"})),allowed_tools:g.Optional(g.Array(g.String(),{description:"List of allowed tools"})),resume_session_id:g.Optional(g.String({description:"Session reference to continue or fork from. Prefer the plugin session ID shown by agent_launch or agent_sessions; persisted backend conversation IDs also resolve when available."})),fork_session:g.Optional(g.Boolean({description:"When resuming, fork to a new session instead of continuing the existing one. Use with resume_session_id."})),force_new_session:g.Optional(g.Boolean({description:"Bypass resume-first protection and start a brand-new linked session even when a resumable or active linked session already exists."})),permission_mode:g.Optional(g.Union([g.Literal("default"),g.Literal("plan"),g.Literal("bypassPermissions")],{description:"Permission mode: 'default' (plugin-managed interactive execution), 'plan' (present the plan first and block implementation until approval), 'bypassPermissions' (fully autonomous execution). Defaults to plugin config ('plan' by default)."})),plan_approval:g.Optional(g.Union([g.Literal("ask"),g.Literal("delegate"),g.Literal("approve")],{description:"Plan approval policy for this session: 'ask' (send the full plan to the user with Approve/Revise/Reject buttons), 'delegate' (orchestrator must review the full plan, then either approve directly or escalate back to the user with the same buttons), 'approve' (auto-approve after verification). Overrides the plugin-level planApproval setting."})),harness:g.Optional(g.String({description:"Agent harness to use ('claude-code', 'codex', or experimental 'opencode'). Defaults to the plugin defaultHarness."})),worktree_strategy:g.Optional(g.Union([g.Literal("off"),g.Literal("manual"),g.Literal("ask"),g.Literal("delegate"),g.Literal("auto-merge"),g.Literal("auto-pr")],{description:"Worktree strategy: 'off' (no worktree), 'manual' (create worktree but no auto merge-back), 'ask' (prompt user with Merge/Open PR/Later/Discard buttons), 'delegate' (orchestrator decides), 'auto-merge' (merge automatically), 'auto-pr' (open/update a PR automatically). Defaults to the plugin config when unset."})),worktree_base_branch:g.Optional(g.String({description:"Base branch for worktree merge/PR operations (default: auto-detected or 'main')"})),worktree_pr_target_repo:g.Optional(g.String({description:"Target repository for cross-repo PRs (e.g. 'openai/codex' for fork-to-upstream workflow). If not set, auto-detected from 'upstream' remote or defaults to 'origin'."}))}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!wp(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected at least { prompt }."}]};n.agentId&&`${n.agentId}${t.agentId}`;try{let r=Yn(n,t,S);if(r.kind!=="resolved")return{content:[{type:"text",text:r.text}]};let{workdir:o,harness:i,resolvedModel:s,permissionMode:l,planApproval:a,originChannel:d,originThreadId:u,originSessionKey:c,route:m,resumeSessionId:p,resolvedResumeId:f,clearedPersistedCodexResume:h,reasoningEffort:k,fastMode:v}=r,I=n.resume_session_id?S.resolve(n.resume_session_id)??S.getPersistedSession(n.resume_session_id):void 0,x=!n.fork_session&&I?an(I):void 0;if(x?.kind==="direct")return{content:[{type:"text",text:`Session ${I.name} [${Ia(I,n.resume_session_id)}] is already running. Use agent_respond(session='${n.resume_session_id}', message='<next instruction>') instead of agent_launch(resume_session_id=...).`}]};if(x?.kind==="unavailable")return{content:[{type:"text",text:`Resume unavailable for session ${I.name} [${Ia(I,n.resume_session_id)}] (${x.reason}). Use agent_launch(prompt='<new task>') for a fresh session or set fork_session=true to fork from prior context.`}]};let b=n.worktree_strategy??D.defaultWorktreeStrategy??"off",A=n.fork_session?void 0:x?.kind==="resume"||x?.kind==="relaunch"?x.stableSessionId:void 0;if(b!=="off"&&Rp(S)&&S.checkRepoPolicyForLaunch(o,n.worktree_strategy).ok===!1)return{content:[{type:"text",text:S.requestRepoPolicyForLaunch({route:m,prompt:n.prompt,workdir:o,name:n.name,model:s,reasoningEffort:k,fastMode:v,systemPrompt:n.system_prompt,allowedTools:n.allowed_tools,resumeSessionId:x?.kind==="resume"?x.resumeSessionId:p,resumeWorktreeFrom:f,sessionIdOverride:A,clearedPersistedCodexResume:h,forkSession:p?n.fork_session:!1,forceNewSession:n.force_new_session,permissionMode:l,planApproval:a,harness:i,worktreeStrategy:n.worktree_strategy,worktreeBaseBranch:n.worktree_base_branch,worktreePrTargetRepo:n.worktree_pr_target_repo,originAgentId:t.agentId||void 0})}]};let y=S.spawn({prompt:n.prompt,sessionIdOverride:A,name:n.name,workdir:o,model:s,reasoningEffort:k,fastMode:v,systemPrompt:n.system_prompt,allowedTools:n.allowed_tools,resumeSessionId:x?.kind==="resume"?x.resumeSessionId:p,resumeWorktreeFrom:f,forkSession:p?n.fork_session:!1,multiTurn:!0,permissionMode:l,planApproval:a,codexApprovalPolicy:i==="codex"?"never":void 0,originChannel:d,originThreadId:u,originAgentId:t.agentId||void 0,originSessionKey:c,route:m,harness:i,taskLifecycle:nr(t),worktreeStrategy:n.worktree_strategy,worktreeBaseBranch:n.worktree_base_branch,worktreePrTargetRepo:n.worktree_pr_target_repo});return{content:[{type:"text",text:bp(S)?S.formatLaunchResult({prompt:n.prompt,workdir:o,harness:i,permissionMode:l??D.permissionMode,planApproval:a,forceNewSession:n.force_new_session,resumeSessionId:n.resume_session_id,forkSession:n.fork_session,clearedPersistedCodexResume:h},y):Mn({prompt:n.prompt,workdir:o,harness:i,permissionMode:l??D.permissionMode,planApproval:a,resumeSessionId:n.resume_session_id,forkSession:n.fork_session,forceNewSession:n.force_new_session,clearedPersistedCodexResume:h},{id:y.id,name:y.name,model:y.model,reasoningEffort:y.reasoningEffort??Be(i),fastMode:y.fastMode??v,worktreeStrategy:y.worktreeStrategy??n.worktree_strategy??D.defaultWorktreeStrategy??"off",repoIntegrationPolicy:y.repoIntegrationPolicy,repoProvider:y.repoProvider,worktreePath:y.worktreePath,originalWorkdir:y.originalWorkdir})}]}}catch(r){let o=Pp(r),i=o.includes("Max sessions")?"":`
66
+ `)}var et,un,bt=!1;function Ca(t){try{return t?.config?.current?.()}catch{return}}function Rt(t,e){if(t&&typeof t=="object"){et=t,arguments.length>=2?(un=e,bt=!0):bt||(un=Ca(et),bt=!0);return}et=void 0,un=void 0,bt=!1}function At(){return et}function Ma(){return et?.tasks?.managedFlows??et?.taskFlow}function _a(){return bt||(un=Ca(et),bt=!0),un}var Ap="openclaw-code-agent",Ip=160,nr={create(){},progress(){},finalize(){}};function rr(t,e){let n=e instanceof Error?e.message:String(e);`${t}${n}`}function xp(t,e){if(e.applied===!1){let n=e.code?` (${e.code})`:"";`${t}${n}`}}function Tp(t){let e=t.prompt.trim().replace(/\s+/g," ");return ae(e||t.name,Ip)}function Cp(t){if(t.status==="starting"||t.lifecycle==="starting")return"Starting";if(t.lifecycle==="active")return"Running";if(t.lifecycle==="awaiting_plan_decision")return"Waiting for plan approval";if(t.lifecycle==="awaiting_user_input")return"Waiting for input";if(t.lifecycle==="awaiting_worktree_decision")return"Waiting for worktree decision";if(t.lifecycle==="suspended")return"Suspended after idle timeout"}function Mp(t){if(t.status==="completed")return"succeeded";if(t.status==="failed")return"failed";if(t.status==="killed")return t.killReason==="idle-timeout"||t.killReason==="startup-timeout"?"timed_out":"cancelled"}function ki(t,e){return t==="completed"?"Completed":t==="failed"?"Failed":e==="idle-timeout"?"Timed out after idle timeout":e==="startup-timeout"?"Timed out during startup":e==="shutdown"?"Cancelled during shutdown":e==="user"?"Cancelled by user":"Cancelled"}function _p(t){return t.lifecycle==="awaiting_plan_decision"||t.lifecycle==="awaiting_user_input"||t.lifecycle==="awaiting_worktree_decision"||t.lifecycle==="suspended"}function Si(t,e,n){return{phase:e,integration:"phase-1-managed-task-flow",sessionId:t.id,sessionName:t.name,sessionStatus:t.status,sessionLifecycle:t.lifecycle,summary:n}}function $p(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.createManaged=="function"&&typeof e.resume=="function"&&typeof e.setWaiting=="function"&&typeof e.finish=="function"&&typeof e.fail=="function"}function $a(t,e){if(e.applied)return e.flow;let n=e.current;return n?.flowId&&typeof n.revision=="number"?n:t}var vi=class{constructor(e){this.taskFlow=e}taskFlow;flow;finalized=!1;lastProgressKey;create(e){if(this.flow||this.finalized)return;let n="Starting",r=Date.now();try{this.flow=this.taskFlow.createManaged({controllerId:Ap,goal:Tp(e),status:"running",notifyPolicy:"silent",currentStep:n,stateJson:Si(e,"created",n),createdAt:e.startedAt,updatedAt:r}),this.lastProgressKey=this.progressKey(e,n)}catch(o){rr("create",o)}}progress(e){if(!this.flow||this.finalized)return;let n=Cp(e);if(!n)return;let r=this.progressKey(e,n);if(r!==this.lastProgressKey)try{let o=Si(e,"progress",n),i=Date.now(),s=_p(e)?this.taskFlow.setWaiting({flowId:this.flow.flowId,expectedRevision:this.flow.revision,currentStep:n,stateJson:o,waitJson:{reason:n,sessionId:e.id},blockedSummary:n,updatedAt:i}):this.taskFlow.resume({flowId:this.flow.flowId,expectedRevision:this.flow.revision,status:"running",currentStep:n,stateJson:o,updatedAt:i});this.flow=$a(this.flow,s),this.lastProgressKey=r}catch(o){rr("progress",o)}}finalize(e){if(!this.flow||this.finalized)return;let n=Mp(e);if(!n)return;let r=n==="succeeded"?"Completed":n==="failed"?"Failed":ki(e.status,e.killReason);try{let o=e.completedAt??Date.now(),i={...Si(e,"terminal",r),terminalStatus:n,terminalSummary:ki(e.status,e.killReason),...e.status==="failed"&&e.error?{error:e.error}:{}},s=n==="succeeded"?this.taskFlow.finish({flowId:this.flow.flowId,expectedRevision:this.flow.revision,stateJson:i,updatedAt:o,endedAt:o}):this.taskFlow.fail({flowId:this.flow.flowId,expectedRevision:this.flow.revision,stateJson:i,blockedSummary:ki(e.status,e.killReason),updatedAt:o,endedAt:o});xp("finalize",s),this.flow=$a(this.flow,s),this.finalized=!0}catch(o){rr("finalize",o)}}progressKey(e,n){return`${e.status}:${e.lifecycle}:${n}`}};function or(t){if(!t.sessionKey?.trim())return nr;try{let e=Ma()?.fromToolContext;if(typeof e!="function")return nr;let n=e(t);return $p(n)?new vi(n):nr}catch(e){return rr("resolve",e),nr}}function Ep(t){return t instanceof Error?t.message:String(t)}function Ea(t,e){return t?("id"in t?t.id:t.sessionId)??e??"unknown-session":e??"unknown-session"}function Dp(t){return!t||typeof t!="object"?!1:typeof t.prompt=="string"}function Op(t){return!!t&&typeof t=="object"&&typeof t.formatLaunchResult=="function"}function Wp(t){return!!t&&typeof t=="object"&&typeof t.checkRepoPolicyForLaunch=="function"&&typeof t.requestRepoPolicyForLaunch=="function"}function Da(t){return{name:"agent_launch",description:"Launch a coding agent session in background to execute a development task. Sessions are multi-turn — they stay open for follow-up messages via agent_respond. Supports resuming previous sessions. Returns a session ID and name for tracking.",parameters:h.Object({prompt:h.String({description:"The task prompt to execute"}),name:h.Optional(h.String({description:"Short human-readable name for the session (kebab-case, e.g. 'fix-auth'). Auto-generated from prompt if omitted."})),workdir:h.Optional(h.String({description:"Working directory (defaults to cwd)"})),model:h.Optional(h.String({description:"Model name to use"})),system_prompt:h.Optional(h.String({description:"Additional system prompt"})),allowed_tools:h.Optional(h.Array(h.String(),{description:"List of allowed tools"})),resume_session_id:h.Optional(h.String({description:"Session reference to continue or fork from. Prefer the plugin session ID shown by agent_launch or agent_sessions; persisted backend conversation IDs also resolve when available."})),fork_session:h.Optional(h.Boolean({description:"When resuming, fork to a new session instead of continuing the existing one. Use with resume_session_id."})),force_new_session:h.Optional(h.Boolean({description:"Bypass resume-first protection and start a brand-new linked session even when a resumable or active linked session already exists."})),permission_mode:h.Optional(h.Union([h.Literal("default"),h.Literal("plan"),h.Literal("bypassPermissions")],{description:"Permission mode: 'default' (plugin-managed interactive execution), 'plan' (present the plan first and block implementation until approval), 'bypassPermissions' (fully autonomous execution). Defaults to plugin config ('plan' by default)."})),plan_approval:h.Optional(h.Union([h.Literal("ask"),h.Literal("delegate"),h.Literal("approve")],{description:"Plan approval policy for this session: 'ask' (send the full plan to the user with Approve/Revise/Reject buttons), 'delegate' (orchestrator must review the full plan, then either approve directly or escalate back to the user with the same buttons), 'approve' (auto-approve after verification). Overrides the plugin-level planApproval setting."})),harness:h.Optional(h.String({description:"Agent harness to use ('claude-code', 'codex', or experimental 'opencode'). Defaults to the plugin defaultHarness."})),worktree_strategy:h.Optional(h.Union([h.Literal("off"),h.Literal("manual"),h.Literal("ask"),h.Literal("delegate"),h.Literal("auto-merge"),h.Literal("auto-pr")],{description:"Worktree strategy: 'off' (no worktree), 'manual' (create worktree but no auto merge-back), 'ask' (prompt user with Merge/Open PR/Later/Discard buttons), 'delegate' (orchestrator decides), 'auto-merge' (merge automatically), 'auto-pr' (open/update a PR automatically). Defaults to the plugin config when unset."})),worktree_base_branch:h.Optional(h.String({description:"Base branch for worktree merge/PR operations (default: auto-detected or 'main')"})),worktree_pr_target_repo:h.Optional(h.String({description:"Target repository for cross-repo PRs (e.g. 'openai/codex' for fork-to-upstream workflow). If not set, auto-detected from 'upstream' remote or defaults to 'origin'."}))}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!Dp(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected at least { prompt }."}]};n.agentId&&`${n.agentId}${t.agentId}`;try{let r=Xn(n,t,v);if(r.kind!=="resolved")return{content:[{type:"text",text:r.text}]};let{workdir:o,harness:i,resolvedModel:s,permissionMode:a,planApproval:l,originChannel:d,originThreadId:u,originSessionKey:c,route:p,resumeSessionId:g,resolvedResumeId:m,clearedPersistedCodexResume:f,reasoningEffort:y,fastMode:S}=r,R=n.resume_session_id?v.resolve(n.resume_session_id)??v.getPersistedSession(n.resume_session_id):void 0,I=!n.fork_session&&R?ln(R):void 0;if(I?.kind==="direct")return{content:[{type:"text",text:`Session ${R.name} [${Ea(R,n.resume_session_id)}] is already running. Use agent_respond(session='${n.resume_session_id}', message='<next instruction>') instead of agent_launch(resume_session_id=...).`}]};if(I?.kind==="unavailable")return{content:[{type:"text",text:`Resume unavailable for session ${R.name} [${Ea(R,n.resume_session_id)}] (${I.reason}). Use agent_launch(prompt='<new task>') for a fresh session or set fork_session=true to fork from prior context.`}]};let b=n.worktree_strategy??D.defaultWorktreeStrategy??"off",A=n.fork_session?void 0:I?.kind==="resume"||I?.kind==="relaunch"?I.stableSessionId:void 0;if(b!=="off"&&Wp(v)&&v.checkRepoPolicyForLaunch(o,n.worktree_strategy).ok===!1)return{content:[{type:"text",text:v.requestRepoPolicyForLaunch({route:p,prompt:n.prompt,workdir:o,name:n.name,model:s,reasoningEffort:y,fastMode:S,systemPrompt:n.system_prompt,allowedTools:n.allowed_tools,resumeSessionId:I?.kind==="resume"?I.resumeSessionId:g,resumeWorktreeFrom:m,sessionIdOverride:A,clearedPersistedCodexResume:f,forkSession:g?n.fork_session:!1,forceNewSession:n.force_new_session,permissionMode:a,planApproval:l,harness:i,worktreeStrategy:n.worktree_strategy,worktreeBaseBranch:n.worktree_base_branch,worktreePrTargetRepo:n.worktree_pr_target_repo,originAgentId:t.agentId||void 0})}]};let k=v.spawn({prompt:n.prompt,sessionIdOverride:A,name:n.name,workdir:o,model:s,reasoningEffort:y,fastMode:S,systemPrompt:n.system_prompt,allowedTools:n.allowed_tools,resumeSessionId:I?.kind==="resume"?I.resumeSessionId:g,resumeWorktreeFrom:m,forkSession:g?n.fork_session:!1,multiTurn:!0,permissionMode:a,planApproval:l,codexApprovalPolicy:i==="codex"?"never":void 0,originChannel:d,originThreadId:u,originAgentId:t.agentId||void 0,originSessionKey:c,route:p,harness:i,taskLifecycle:or(t),worktreeStrategy:n.worktree_strategy,worktreeBaseBranch:n.worktree_base_branch,worktreePrTargetRepo:n.worktree_pr_target_repo});return{content:[{type:"text",text:Op(v)?v.formatLaunchResult({prompt:n.prompt,workdir:o,harness:i,permissionMode:a??D.permissionMode,planApproval:l,forceNewSession:n.force_new_session,resumeSessionId:n.resume_session_id,forkSession:n.fork_session,clearedPersistedCodexResume:f},k):$n({prompt:n.prompt,workdir:o,harness:i,permissionMode:a??D.permissionMode,planApproval:l,resumeSessionId:n.resume_session_id,forkSession:n.fork_session,forceNewSession:n.force_new_session,clearedPersistedCodexResume:f},{id:k.id,name:k.name,model:k.model,reasoningEffort:k.reasoningEffort??Ke(i),fastMode:k.fastMode??S,worktreeStrategy:k.worktreeStrategy??n.worktree_strategy??D.defaultWorktreeStrategy??"off",repoIntegrationPolicy:k.repoIntegrationPolicy,repoProvider:k.repoProvider,worktreePath:k.worktreePath,originalWorkdir:k.originalWorkdir})}]}}catch(r){let o=Ep(r),i=o.includes("Max sessions")?"":`
67
67
 
68
- Use agent_sessions to see active sessions and their status.`;return{content:[{type:"text",text:`Error launching session: ${o}${i}`}]}}}}}te();N();ie();import{existsSync as Ri,readFileSync as Xa}from"fs";import{EventEmitter as em}from"events";import{webcrypto as Ca}from"node:crypto";var Ta="useandom-26T198340PX75pxJACKVERYMINDBUSHWOLF_GQZbfghjklqvwyzrict";var Ap=128,Xe,Rt;function Ip(t){if(t<0||t>1024)throw new RangeError("Wrong ID size");!Xe||Xe.length<t?(Xe=Buffer.allocUnsafe(t*Ap),Ca.getRandomValues(Xe),Rt=0):Rt+t>Xe.length&&(Ca.getRandomValues(Xe),Rt=0),Rt+=t}function rr(t=21){Ip(t|=0);let e="";for(let n=Rt-t;n<Rt;n++)e+=Ta[Xe[n]&63];return e}ci();ie();Z();var Ma={starting:["running","failed","killed"],running:["completed","failed","killed"],completed:[],failed:[],killed:[]};function Y(t,e){return Object.hasOwn(t,e)}var _a=new Set(["merged","released","pr_open","dismissed","cleanup_failed"]);function xp(t){return t.requestedPermissionMode!=="plan"?"not_plan_gated":t.pendingPlanApproval?"awaiting_approval":t.planModeApproved?"approved_then_implemented":t.currentPermissionMode!=="plan"?"implemented_without_required_approval":"awaiting_plan_output"}function de(t){return{...t,approvalExecutionState:xp(t)}}function yi(t,e){switch(e.type){case"initialize":return de({...t,worktreeState:e.hasWorktree&&t.worktreeState==="none"?"provisioned":t.worktreeState,lifecycle:t.status==="starting"?"starting":t.lifecycle,runtimeState:t.status==="starting"?"live":t.runtimeState});case"status.transition":return e.status==="starting"?de({...t,status:e.status,lifecycle:"starting",runtimeState:"live"}):e.status==="running"?de({...t,status:e.status,lifecycle:t.lifecycle==="starting"||t.lifecycle==="suspended"?"active":t.lifecycle,runtimeState:"live"}):de({...t,status:e.status,runtimeState:"stopped",lifecycle:t.lifecycle==="suspended"?"suspended":"terminal"});case"permission.mode_changed":return de({...t,currentPermissionMode:e.currentPermissionMode});case"turn.started":return de({...t,lifecycle:"active",runtimeState:"live"});case"input.requested":return de({...t,lifecycle:t.pendingPlanApproval?"awaiting_plan_decision":"awaiting_user_input"});case"plan.requested":if(t.planModeApproved)return t;{let n=t.pendingPlanApproval&&t.approvalState==="pending"&&t.planApprovalContext===e.context,r=t.pendingPlanApproval&&t.approvalState==="changes_requested"&&t.planApprovalContext===e.context&&t.planDecisionVersion>0,o=!t.pendingPlanApproval&&t.approvalState==="changes_requested"&&t.planApprovalContext===e.context&&t.planDecisionVersion>0,i=n||r||o?t.planDecisionVersion:t.planDecisionVersion+1;return de({...t,pendingPlanApproval:!0,planApprovalContext:e.context,approvalState:"pending",planDecisionVersion:i,actionablePlanDecisionVersion:i,canonicalPlanPromptVersion:n?t.canonicalPlanPromptVersion:void 0,approvalPromptRequiredVersion:n?t.approvalPromptRequiredVersion:void 0,approvalPromptVersion:n?t.approvalPromptVersion:void 0,approvalPromptStatus:n?t.approvalPromptStatus:"not_sent",approvalPromptTransport:n?t.approvalPromptTransport:"none",approvalPromptMessageKind:n?t.approvalPromptMessageKind:"none",approvalPromptLastAttemptAt:n?t.approvalPromptLastAttemptAt:void 0,approvalPromptDeliveredAt:n?t.approvalPromptDeliveredAt:void 0,approvalPromptFailedAt:n?t.approvalPromptFailedAt:void 0,lifecycle:"awaiting_plan_decision"})}case"plan.cleared":return de({...t,pendingPlanApproval:!1,planApprovalContext:void 0,actionablePlanDecisionVersion:void 0,approvalState:t.approvalState==="pending"?"not_required":t.approvalState});case"plan.approved":return de({...t,pendingPlanApproval:!1,planApprovalContext:void 0,actionablePlanDecisionVersion:void 0,planModeApproved:!0,approvalState:"approved",planDecisionVersion:t.planDecisionVersion+1,approvalPromptVersion:void 0,approvalPromptStatus:"not_sent",lifecycle:t.status==="running"?"active":t.lifecycle});case"plan.changes_requested":return de({...t,pendingPlanApproval:!0,approvalState:"changes_requested",planDecisionVersion:t.planDecisionVersion+1,actionablePlanDecisionVersion:void 0,canonicalPlanPromptVersion:void 0,approvalPromptRequiredVersion:void 0,approvalPromptVersion:void 0,approvalPromptStatus:"not_sent",approvalPromptTransport:"none",approvalPromptMessageKind:"none",approvalPromptLastAttemptAt:void 0,approvalPromptDeliveredAt:void 0,approvalPromptFailedAt:void 0,lifecycle:"awaiting_plan_decision"});case"terminal.entered":return de({...t,lifecycle:e.suspended?"suspended":"terminal",runtimeState:"stopped"});case"worktree.decision_requested":return de({...t,lifecycle:"awaiting_worktree_decision",worktreeState:"pending_decision"});case"worktree.state_set":return de({...t,worktreeState:e.worktreeState,lifecycle:e.worktreeState==="pending_decision"?"awaiting_worktree_decision":_a.has(e.worktreeState)?"terminal":t.lifecycle});case"delivery.state_set":return de({...t,deliveryState:e.deliveryState})}}function $a(t,e){let n={...t,...Y(e,"lifecycle")?{lifecycle:e.lifecycle}:{},...Y(e,"approvalState")?{approvalState:e.approvalState}:{},...Y(e,"approvalExecutionState")?{approvalExecutionState:e.approvalExecutionState}:{},...Y(e,"worktreeState")?{worktreeState:e.worktreeState}:{},...Y(e,"runtimeState")?{runtimeState:e.runtimeState}:{},...Y(e,"deliveryState")?{deliveryState:e.deliveryState}:{},...Y(e,"requestedPermissionMode")?{requestedPermissionMode:e.requestedPermissionMode}:{},...Y(e,"currentPermissionMode")?{currentPermissionMode:e.currentPermissionMode}:{},...Y(e,"pendingPlanApproval")?{pendingPlanApproval:e.pendingPlanApproval}:{},...Y(e,"planApprovalContext")?{planApprovalContext:e.planApprovalContext}:{},...Y(e,"planDecisionVersion")?{planDecisionVersion:e.planDecisionVersion}:{},...Y(e,"actionablePlanDecisionVersion")?{actionablePlanDecisionVersion:e.actionablePlanDecisionVersion}:{},...Y(e,"canonicalPlanPromptVersion")?{canonicalPlanPromptVersion:e.canonicalPlanPromptVersion}:{},...Y(e,"approvalPromptRequiredVersion")?{approvalPromptRequiredVersion:e.approvalPromptRequiredVersion}:{},...Y(e,"approvalPromptVersion")?{approvalPromptVersion:e.approvalPromptVersion}:{},...Y(e,"approvalPromptStatus")?{approvalPromptStatus:e.approvalPromptStatus}:{},...Y(e,"approvalPromptTransport")?{approvalPromptTransport:e.approvalPromptTransport}:{},...Y(e,"approvalPromptMessageKind")?{approvalPromptMessageKind:e.approvalPromptMessageKind}:{},...Y(e,"approvalPromptLastAttemptAt")?{approvalPromptLastAttemptAt:e.approvalPromptLastAttemptAt}:{},...Y(e,"approvalPromptDeliveredAt")?{approvalPromptDeliveredAt:e.approvalPromptDeliveredAt}:{},...Y(e,"approvalPromptFailedAt")?{approvalPromptFailedAt:e.approvalPromptFailedAt}:{},...Y(e,"planModeApproved")?{planModeApproved:e.planModeApproved}:{}};return e.approvalState==="changes_requested"&&e.pendingPlanApproval===void 0&&(n={...n,pendingPlanApproval:!1}),n.pendingPlanApproval?n={...n,approvalState:"pending",actionablePlanDecisionVersion:n.actionablePlanDecisionVersion??n.planDecisionVersion,lifecycle:"awaiting_plan_decision"}:n.approvalState==="changes_requested"&&(n={...n,actionablePlanDecisionVersion:void 0,lifecycle:"awaiting_user_input"}),Y(e,"pendingWorktreeDecisionSince")&&e.pendingWorktreeDecisionSince!==void 0||n.worktreeState==="pending_decision"?n=yi(n,{type:"worktree.decision_requested"}):_a.has(n.worktreeState)&&(n={...n,lifecycle:"terminal"}),de(n)}var or=class{queue=[];resolve=null;done=!1;hasPending(){return this.queue.length>0}push(e){this.queue.push(e),this.resolve&&(this.resolve(),this.resolve=null)}end(){this.done=!0,this.resolve&&(this.resolve(),this.resolve=null)}async*[Symbol.asyncIterator](){for(;;){for(;this.queue.length>0;)yield this.queue.shift();if(this.done)return;await new Promise(e=>{this.resolve=e})}}};import{createHash as Tp}from"crypto";import{appendFileSync as Cp}from"fs";import{tmpdir as Mp}from"os";import{join as _p}from"path";var Ea=2e3,$p=/^[A-Za-z0-9_.-]+$/;function Ep(t){return $p.test(t)?t:`hashed+${Tp("sha256").update(t,"utf8").digest("hex")}`}function et(t){return _p(Mp(),`openclaw-agent-${Ep(t)}.txt`)}function Dp(t,e){if(!e)return;let n=e.split(`
69
- `),[r="",...o]=n;t.length===0?t.push(r):t[t.length-1]+=r;for(let i of o)t.push(i)}function Da(t,e,n){Dp(t,n),t.length>Ea&&t.splice(0,t.length-Ea);try{Cp(et(e),n,"utf-8")}catch{}return t}var ir=class{timers=new Map;get size(){return this.timers.size}set(e,n,r){this.clear(e);let o=setTimeout(()=>{this.timers.get(e)===o&&this.timers.delete(e),r()},n);o.unref?.(),this.timers.set(e,o)}clear(e){let n=this.timers.get(e);n&&(clearTimeout(n),this.timers.delete(e))}clearAll(){for(let e of this.timers.values())clearTimeout(e);this.timers.clear()}};var sr=class{constructor(e){this.deps=e}deps;waitingForInputFired=!1;lastTurnHadQuestion=!1;turnInProgress=!0;currentTurnText="";currentTurnPlanArtifact;beginUserTurn(){this.waitingForInputFired=!1,this.turnInProgress=!0,this.currentTurnText="",this.currentTurnPlanArtifact=void 0,this.lastTurnHadQuestion=!1}noteTextDelta(e,n){this.waitingForInputFired=!1,n||(this.lastTurnHadQuestion=!1),this.deps.appendOutput(e),this.currentTurnText+=this.currentTurnText?`
70
- ${e}`:e,this.deps.emitOutput(e)}noteToolCall(e){let{name:n,input:r,currentPermissionMode:o,permissionMode:i,planModeApproved:s}=e;if(n==="Write"){let l=r;typeof l?.file_path=="string"&&l.file_path.includes("/.claude/plans/")&&this.deps.setPlanFilePath(l.file_path)}n==="AskUserQuestion"?(this.lastTurnHadQuestion=!0,this.deps.applyInputRequested(),(o==="plan"||i==="plan")&&!s&&this.deps.markPendingPlanApproval("plan-mode")):(n==="ExitPlanMode"||n==="set_permission_mode")&&!s&&(this.lastTurnHadQuestion=!0,this.deps.markPendingPlanApproval("plan-mode")),this.deps.emitToolUse(n,r)}notePendingInput(){this.lastTurnHadQuestion=!0,this.deps.applyInputRequested(),this.waitingForInputFired||(this.waitingForInputFired=!0,this.deps.emitTurnEnd(!0))}clearResolvedPendingInput(e,n){if(!(!e||n?.requestId===e))return n}notePlanArtifact(e,n){if(this.currentTurnPlanArtifact=e,this.deps.setLatestPlanArtifact(e),!n)return;let r=e.markdown.trim();!r||this.currentTurnText.trim()===r||(this.deps.appendOutput(r),this.currentTurnText=r,this.deps.emitOutput(r))}noteSettingsChanged(e){let{oldMode:n,permissionMode:r,planModeApproved:o}=e;if(r)return r!=="plan"&&n==="plan"&&!o&&(this.deps.markPendingPlanApproval("plan-mode"),this.lastTurnHadQuestion=!0),r}finishSuccessfulTurn(e){let{currentPermissionMode:n,permissionMode:r,pendingPlanApproval:o,planModeApproved:i,pendingInputState:s,hasPendingMessages:l}=e,a=o;(n==="plan"||r==="plan")&&!a&&!i&&(this.deps.markPendingPlanApproval("plan-mode"),a=!0);let d=a||this.lastTurnHadQuestion||!!s;if(this.turnInProgress=l,d&&!this.waitingForInputFired)this.waitingForInputFired=!0,a||this.deps.markAwaitingUserInput(),this.deps.emitTurnEnd(!0);else if(!l&&!d){if(this.deps.queueWorktreeFinalizationPrompt?.()){this.turnInProgress=!0;return}this.deps.completeTurn(),this.deps.emitTurnEnd(!1)}}finishTerminalTurn(){this.turnInProgress=!1}finishInterruptedTurn(e){this.turnInProgress=e,this.waitingForInputFired=!1,this.lastTurnHadQuestion=!1,this.currentTurnText="",this.currentTurnPlanArtifact=void 0}resetAfterRun(){this.lastTurnHadQuestion=!1,this.currentTurnText="",this.currentTurnPlanArtifact=void 0}};var ar=class{constructor(e){this.deps=e}deps;applyMessage(e,n){if(e.type==="backend_ref"){this.deps.clearStartupTimer(),this.deps.assignBackendRef({...e.ref}),this.deps.transitionRunning();return}if(e.type==="run_started"){e.runId&&this.deps.noteRunStarted(e.runId);return}if(e.type==="text_delta"){this.deps.noteTextDelta(e.text,n.pendingPlanApproval);return}if(e.type==="tool_call"){this.deps.noteToolCall({name:e.name,input:e.input,currentPermissionMode:n.currentPermissionMode,permissionMode:n.permissionMode,planModeApproved:n.planModeApproved});return}if(e.type==="pending_input"){this.deps.setPendingInputState(e.state),this.deps.notePendingInput();return}if(e.type==="pending_input_resolved"){this.deps.setPendingInputState(this.deps.clearResolvedPendingInput(e.requestId,n.pendingInputState));return}if(e.type==="plan_artifact"){this.deps.notePlanArtifact(e);return}if(e.type==="settings_changed"){let r=this.deps.noteSettingsChanged({oldMode:n.currentPermissionMode,permissionMode:e.permissionMode,planModeApproved:n.planModeApproved});r&&this.deps.setCurrentPermissionMode(r);return}if(e.type==="run_completed"){this.deps.handleRunCompleted(e.data);return}e.type}};ye();var tm=120*1e3;function kr(t){return t instanceof Error?t.message:String(t)}var Sr=class extends em{id;name;harnessSessionId;backendRef;harness;harnessHandle;prompt;workdir;model;reasoningEffort;fastMode;systemPrompt;allowedTools;permissionMode;requestedPermissionMode;planApproval;codexApprovalPolicy;currentPermissionMode;pendingModeSwitch;resumeSessionId;forkSession;worktreePath;originalWorkdir;worktreeBranch;worktreeStrategy;repoIntegrationPolicy;repoIntegrationPolicySource;repoProvider;worktreeBaseBranch;worktreePrTargetRepo;autoMergeParentSessionId;autoMergeConflictResolutionAttemptCount;autoMergeResolverSessionId;worktreePushRemote;worktreeDisposition;worktreePrUrl;worktreePrNumber;worktreeMerged;worktreeMergedAt;worktreeLifecycle;worktreeState="none";multiTurn;goalTaskId;messageStream;_status="starting";error;startedAt;completedAt;abortController;outputBuffer=[];result;costUsd=0;originChannel;originThreadId;originAgentId;originSessionKey;route;pendingInputState;pendingPlanApproval=!1;planApprovalContext;planDecisionVersion=0;actionablePlanDecisionVersion;canonicalPlanPromptVersion;approvalPromptRequiredVersion;approvalPromptVersion;approvalPromptStatus="not_sent";approvalPromptTransport="none";approvalPromptMessageKind="none";approvalPromptLastAttemptAt;approvalPromptDeliveredAt;approvalPromptFailedAt;planFilePath;killReason="unknown";planModeApproved=!1;turnRuntime;harnessEvents;worktreeFinalizationPromptIssued=!1;lifecycle="starting";approvalState="not_required";approvalExecutionState="not_plan_gated";approvalRationale;latestPlanArtifact;latestPlanArtifactVersion;runtimeState="live";deliveryState="idle";canUseTool;autoRespondCount=0;timers=new ir;constructor(e,n){super(),this.id=e.sessionIdOverride??rr(8),this.name=n,this.harness=e.harness?rn(e.harness):pa(),this.prompt=e.prompt,this.workdir=e.workdir,this.model=e.model??ut(this.harness.name),this.reasoningEffort=e.reasoningEffort??Be(this.harness.name),this.fastMode=this.harness.name==="codex"?e.fastMode??ct(this.harness.name):void 0,this.systemPrompt=e.systemPrompt,this.allowedTools=e.allowedTools,this.permissionMode=e.permissionMode??D.permissionMode,this.requestedPermissionMode=e.requestedPermissionMode??this.permissionMode,this.planApproval=e.planApproval??D.planApproval,this.codexApprovalPolicy=this.harness.name==="codex"?"never":void 0,this.currentPermissionMode=this.permissionMode,this.originChannel=e.originChannel,this.originThreadId=e.originThreadId,this.originAgentId=e.originAgentId,this.originSessionKey=e.originSessionKey,this.route=e.route?{...e.route}:void 0,this.backendRef=e.backendRef?{...e.backendRef}:void 0,this.resumeSessionId=e.resumeSessionId,this.forkSession=e.forkSession,this.multiTurn=e.multiTurn??!0,this.goalTaskId=e.goalTaskId,this.worktreeStrategy=e.worktreeStrategy,this.repoIntegrationPolicy=e.repoIntegrationPolicy,this.repoIntegrationPolicySource=e.repoIntegrationPolicySource,this.repoProvider=e.repoProvider,this.worktreeBaseBranch=e.worktreeBaseBranch,e.worktreePrTargetRepo&&(this.worktreePrTargetRepo=e.worktreePrTargetRepo),e.autoMergeParentSessionId&&(this.autoMergeParentSessionId=e.autoMergeParentSessionId),e.autoMergeConflictResolutionAttemptCount!==void 0&&(this.autoMergeConflictResolutionAttemptCount=e.autoMergeConflictResolutionAttemptCount),e.autoMergeResolverSessionId&&(this.autoMergeResolverSessionId=e.autoMergeResolverSessionId),this.canUseTool=e.canUseTool,this.startedAt=Date.now(),this.abortController=new AbortController,this.turnRuntime=new sr({appendOutput:r=>Da(this.outputBuffer,this.id,r),emitOutput:r=>this.emit("output",this,r),emitToolUse:(r,o)=>this.emit("toolUse",this,r,o),emitTurnEnd:r=>this.emit("turnEnd",this,r),markPendingPlanApproval:r=>this.markPendingPlanApproval(r),markAwaitingUserInput:()=>this.markAwaitingUserInput(),applyInputRequested:()=>this.applyControlEvent({type:"input.requested"}),completeTurn:()=>{this.applyControlEvent({type:"terminal.entered"}),this.complete("done")},queueWorktreeFinalizationPrompt:()=>this.queueWorktreeFinalizationPrompt(),setPlanFilePath:r=>{this.planFilePath=r},setLatestPlanArtifact:r=>{this.latestPlanArtifact=r;let o=this.pendingPlanApproval?this.actionablePlanDecisionVersion??this.planDecisionVersion:void 0;this.latestPlanArtifactVersion=o&&o>0?o:void 0}}),this.harnessEvents=new ar({clearStartupTimer:()=>this.clearTimer("startup"),assignBackendRef:r=>{this.backendRef=r,this.harnessSessionId=r.conversationId,r.worktreePath&&(this.worktreePath=r.worktreePath,this.originalWorkdir??=this.workdir,this.worktreeBranch??=At(r.worktreePath),this.worktreeStrategy&&this.worktreeStrategy!=="off"&&this.applyControlEvent({type:"worktree.state_set",worktreeState:"provisioned"}))},noteRunStarted:r=>{this.backendRef&&(this.backendRef={...this.backendRef,runId:r})},transitionRunning:()=>{this._status==="starting"&&this.transition("running")},noteTextDelta:(r,o)=>this.turnRuntime.noteTextDelta(r,o),noteToolCall:r=>this.turnRuntime.noteToolCall(r),setPendingInputState:r=>{this.pendingInputState=r},notePendingInput:()=>this.turnRuntime.notePendingInput(),clearResolvedPendingInput:(r,o)=>this.turnRuntime.clearResolvedPendingInput(r,o),notePlanArtifact:r=>this.turnRuntime.notePlanArtifact(r.artifact,r.finalized),noteSettingsChanged:r=>this.turnRuntime.noteSettingsChanged(r),setCurrentPermissionMode:r=>{this.currentPermissionMode=r,this.applyControlEvent({type:"permission.mode_changed",currentPermissionMode:r})},handleRunCompleted:r=>{let o=r.outcome??(r.success?"completed":"failed");this.result={subtype:o==="interrupted"?"interrupted":r.success?"success":"error",duration_ms:r.duration_ms,total_cost_usd:r.total_cost_usd,num_turns:r.num_turns,result:r.result,is_error:o==="failed",session_id:r.session_id},this.costUsd=r.total_cost_usd;let i=this.multiTurn&&this.messageStream&&o==="interrupted",s=this.multiTurn&&this.messageStream&&o==="completed";i?(this.resetIdleTimer(),this.turnRuntime.finishInterruptedTurn(this.messageStream?.hasPending()===!0)):s?(this.resetIdleTimer(),this.turnRuntime.finishSuccessfulTurn({currentPermissionMode:this.currentPermissionMode,permissionMode:this.permissionMode,pendingPlanApproval:this.pendingPlanApproval,planModeApproved:this.planModeApproved,pendingInputState:this.pendingInputState,hasPendingMessages:this.messageStream?.hasPending()===!0})):(this.turnRuntime.finishTerminalTurn(),this.transitionToTerminal(o==="completed"?"completed":"failed")),this.turnRuntime.resetAfterRun(),this.pendingInputState=void 0}}),this.applyControlEvent({type:"initialize",hasWorktree:!!(this.worktreeStrategy&&this.worktreeStrategy!=="off")}),(e.planModeApproved!==void 0||e.approvalState!==void 0||e.approvalExecutionState!==void 0||e.approvalRationale!==void 0||e.pendingPlanApproval!==void 0||e.planApprovalContext!==void 0||e.planDecisionVersion!==void 0||e.actionablePlanDecisionVersion!==void 0||e.canonicalPlanPromptVersion!==void 0||e.approvalPromptRequiredVersion!==void 0||e.approvalPromptVersion!==void 0||e.approvalPromptStatus!==void 0||e.approvalPromptTransport!==void 0||e.approvalPromptMessageKind!==void 0||e.approvalPromptLastAttemptAt!==void 0||e.approvalPromptDeliveredAt!==void 0||e.approvalPromptFailedAt!==void 0)&&this.applyControlPatch({...e.planModeApproved!==void 0?{planModeApproved:e.planModeApproved}:{},...e.approvalState!==void 0?{approvalState:e.approvalState}:{},...e.approvalExecutionState!==void 0?{approvalExecutionState:e.approvalExecutionState}:{},...e.pendingPlanApproval!==void 0?{pendingPlanApproval:e.pendingPlanApproval}:{},...e.planApprovalContext!==void 0?{planApprovalContext:e.planApprovalContext}:{},...e.planDecisionVersion!==void 0?{planDecisionVersion:e.planDecisionVersion}:{},...e.actionablePlanDecisionVersion!==void 0?{actionablePlanDecisionVersion:e.actionablePlanDecisionVersion}:{},...e.canonicalPlanPromptVersion!==void 0?{canonicalPlanPromptVersion:e.canonicalPlanPromptVersion}:{},...e.approvalPromptRequiredVersion!==void 0?{approvalPromptRequiredVersion:e.approvalPromptRequiredVersion}:{},...e.approvalPromptVersion!==void 0?{approvalPromptVersion:e.approvalPromptVersion}:{},...e.approvalPromptStatus!==void 0?{approvalPromptStatus:e.approvalPromptStatus}:{},...e.approvalPromptTransport!==void 0?{approvalPromptTransport:e.approvalPromptTransport}:{},...e.approvalPromptMessageKind!==void 0?{approvalPromptMessageKind:e.approvalPromptMessageKind}:{},...e.approvalPromptLastAttemptAt!==void 0?{approvalPromptLastAttemptAt:e.approvalPromptLastAttemptAt}:{},...e.approvalPromptDeliveredAt!==void 0?{approvalPromptDeliveredAt:e.approvalPromptDeliveredAt}:{},...e.approvalPromptFailedAt!==void 0?{approvalPromptFailedAt:e.approvalPromptFailedAt}:{}}),this.approvalRationale=e.approvalRationale}get status(){return this._status}get harnessName(){return this.harness.name}get backendKind(){return this.harness.backendKind}get backendCapabilities(){return this.harness.capabilities}get backendConversationId(){return $(this)}approvalSnapshot(){return{requestedPermissionMode:this.requestedPermissionMode,currentPermissionMode:this.currentPermissionMode,approvalExecutionState:this.approvalExecutionState,approvalRationale:this.approvalRationale,planModeApproved:this.controlStateSnapshot().planModeApproved,pendingPlanApproval:this.pendingPlanApproval,planApprovalContext:this.planApprovalContext,planDecisionVersion:this.planDecisionVersion,actionablePlanDecisionVersion:this.actionablePlanDecisionVersion,canonicalPlanPromptVersion:this.canonicalPlanPromptVersion,approvalPromptRequiredVersion:this.approvalPromptRequiredVersion,approvalPromptVersion:this.approvalPromptVersion,approvalPromptStatus:this.approvalPromptStatus,approvalPromptTransport:this.approvalPromptTransport,approvalPromptMessageKind:this.approvalPromptMessageKind,approvalPromptLastAttemptAt:this.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:this.approvalPromptDeliveredAt,approvalPromptFailedAt:this.approvalPromptFailedAt,planApproval:this.planApproval,codexApprovalPolicy:this.codexApprovalPolicy}}worktreeSnapshot(){return{worktreePath:this.worktreePath,worktreeBranch:this.worktreeBranch,worktreeStrategy:this.worktreeStrategy,repoIntegrationPolicy:this.repoIntegrationPolicy,repoIntegrationPolicySource:this.repoIntegrationPolicySource,repoProvider:this.repoProvider,worktreeBaseBranch:this.worktreeBaseBranch,worktreePrTargetRepo:this.worktreePrTargetRepo,autoMergeParentSessionId:this.autoMergeParentSessionId,autoMergeConflictResolutionAttemptCount:this.autoMergeConflictResolutionAttemptCount,autoMergeResolverSessionId:this.autoMergeResolverSessionId,worktreeLifecycle:this.worktreeLifecycle}}backendSnapshot(){return{harnessSessionId:this.harnessSessionId,backendRef:this.backendRef,harness:this.harnessName,backendKind:this.backendKind,backendConversationId:this.backendConversationId}}routingSnapshot(){return{route:this.route,originAgentId:this.originAgentId,originChannel:this.originChannel,originThreadId:this.originThreadId,originSessionKey:this.originSessionKey}}get waitingForInputFired(){return this.turnRuntime.waitingForInputFired}set waitingForInputFired(e){this.turnRuntime.waitingForInputFired=e}get turnInProgress(){return this.turnRuntime.turnInProgress}set turnInProgress(e){this.turnRuntime.turnInProgress=e}get currentTurnPlanArtifact(){return this.turnRuntime.currentTurnPlanArtifact}set currentTurnPlanArtifact(e){this.turnRuntime.currentTurnPlanArtifact=e}get duration(){return(this.completedAt??Date.now())-this.startedAt}get phase(){return this.lifecycle}get isExplicitlyResumable(){return this.status!=="running"&&this.status!=="completed"&&this.killReason!=="done"&&!!this.backendConversationId}transition(e){if(!Ma[this._status].includes(e))throw new Error(`Session state error: cannot transition from ${this._status} to ${e}. This is an internal error — please report it.`);let n=this._status;this._status=e,this.applyControlEvent({type:"status.transition",status:e}),this.emit("statusChange",this,e,n)}setTimer(e,n,r){this.timers.set(e,n,r)}clearTimer(e){this.timers.clear(e)}clearAllTimers(){this.timers.clearAll()}markPendingPlanApproval(e){let n=this.latestPlanArtifactVersion;this.approvalRationale=void 0,this.applyControlEvent({type:"plan.requested",context:e});let r=this.actionablePlanDecisionVersion??this.planDecisionVersion;this.currentTurnPlanArtifact&&r>0?(this.latestPlanArtifact=this.currentTurnPlanArtifact,this.latestPlanArtifactVersion=r):n!==r&&(this.latestPlanArtifact=void 0,this.latestPlanArtifactVersion=void 0)}clearPendingPlanApproval(){this.applyControlEvent({type:"plan.cleared"})}markAwaitingUserInput(){this.applyControlEvent({type:"input.requested"})}queueWorktreeFinalizationPrompt(){if(!this.multiTurn||!this.messageStream||!this.worktreePath||!this.worktreeStrategy||this.worktreeStrategy==="off"||this.worktreeFinalizationPromptIssued)return!1;let e=tt(this.worktreePath);if(e.length===0)return!1;this.worktreeFinalizationPromptIssued=!0;let n=e.slice(0,20).map(i=>`- ${i}`).join(`
68
+ Use agent_sessions to see active sessions and their status.`;return{content:[{type:"text",text:`Error launching session: ${o}${i}`}]}}}}}ne();B();se();import{existsSync as Ti,readFileSync as sl}from"fs";import{EventEmitter as pm}from"events";import{webcrypto as Wa}from"node:crypto";var Oa="useandom-26T198340PX75pxJACKVERYMINDBUSHWOLF_GQZbfghjklqvwyzrict";var Np=128,tt,It;function Lp(t){if(t<0||t>1024)throw new RangeError("Wrong ID size");!tt||tt.length<t?(tt=Buffer.allocUnsafe(t*Np),Wa.getRandomValues(tt),It=0):It+t>tt.length&&(Wa.getRandomValues(tt),It=0),It+=t}function ir(t=21){Lp(t|=0);let e="";for(let n=It-t;n<It;n++)e+=Oa[tt[n]&63];return e}gi();se();X();var Na={starting:["running","failed","killed"],running:["completed","failed","killed"],completed:[],failed:[],killed:[]};function Y(t,e){return Object.hasOwn(t,e)}var La=new Set(["merged","released","pr_open","dismissed","cleanup_failed"]);function Bp(t){return t.requestedPermissionMode!=="plan"?"not_plan_gated":t.pendingPlanApproval?"awaiting_approval":t.planModeApproved?"approved_then_implemented":t.currentPermissionMode!=="plan"?"implemented_without_required_approval":"awaiting_plan_output"}function ue(t){return{...t,approvalExecutionState:Bp(t)}}function wi(t,e){switch(e.type){case"initialize":return ue({...t,worktreeState:e.hasWorktree&&t.worktreeState==="none"?"provisioned":t.worktreeState,lifecycle:t.status==="starting"?"starting":t.lifecycle,runtimeState:t.status==="starting"?"live":t.runtimeState});case"status.transition":return e.status==="starting"?ue({...t,status:e.status,lifecycle:"starting",runtimeState:"live"}):e.status==="running"?ue({...t,status:e.status,lifecycle:t.lifecycle==="starting"||t.lifecycle==="suspended"?"active":t.lifecycle,runtimeState:"live"}):ue({...t,status:e.status,runtimeState:"stopped",lifecycle:t.lifecycle==="suspended"?"suspended":"terminal"});case"permission.mode_changed":return ue({...t,currentPermissionMode:e.currentPermissionMode});case"turn.started":return ue({...t,lifecycle:"active",runtimeState:"live"});case"input.requested":return ue({...t,lifecycle:t.pendingPlanApproval?"awaiting_plan_decision":"awaiting_user_input"});case"plan.requested":if(t.planModeApproved)return t;{let n=t.pendingPlanApproval&&t.approvalState==="pending"&&t.planApprovalContext===e.context,r=t.pendingPlanApproval&&t.approvalState==="changes_requested"&&t.planApprovalContext===e.context&&t.planDecisionVersion>0,o=!t.pendingPlanApproval&&t.approvalState==="changes_requested"&&t.planApprovalContext===e.context&&t.planDecisionVersion>0,i=n||r||o?t.planDecisionVersion:t.planDecisionVersion+1;return ue({...t,pendingPlanApproval:!0,planApprovalContext:e.context,approvalState:"pending",planDecisionVersion:i,actionablePlanDecisionVersion:i,canonicalPlanPromptVersion:n?t.canonicalPlanPromptVersion:void 0,approvalPromptRequiredVersion:n?t.approvalPromptRequiredVersion:void 0,approvalPromptVersion:n?t.approvalPromptVersion:void 0,approvalPromptStatus:n?t.approvalPromptStatus:"not_sent",approvalPromptTransport:n?t.approvalPromptTransport:"none",approvalPromptMessageKind:n?t.approvalPromptMessageKind:"none",approvalPromptLastAttemptAt:n?t.approvalPromptLastAttemptAt:void 0,approvalPromptDeliveredAt:n?t.approvalPromptDeliveredAt:void 0,approvalPromptFailedAt:n?t.approvalPromptFailedAt:void 0,lifecycle:"awaiting_plan_decision"})}case"plan.cleared":return ue({...t,pendingPlanApproval:!1,planApprovalContext:void 0,actionablePlanDecisionVersion:void 0,approvalState:t.approvalState==="pending"?"not_required":t.approvalState});case"plan.approved":return ue({...t,pendingPlanApproval:!1,planApprovalContext:void 0,actionablePlanDecisionVersion:void 0,planModeApproved:!0,approvalState:"approved",planDecisionVersion:t.planDecisionVersion+1,approvalPromptVersion:void 0,approvalPromptStatus:"not_sent",lifecycle:t.status==="running"?"active":t.lifecycle});case"plan.changes_requested":return ue({...t,pendingPlanApproval:!0,approvalState:"changes_requested",planDecisionVersion:t.planDecisionVersion+1,actionablePlanDecisionVersion:void 0,canonicalPlanPromptVersion:void 0,approvalPromptRequiredVersion:void 0,approvalPromptVersion:void 0,approvalPromptStatus:"not_sent",approvalPromptTransport:"none",approvalPromptMessageKind:"none",approvalPromptLastAttemptAt:void 0,approvalPromptDeliveredAt:void 0,approvalPromptFailedAt:void 0,lifecycle:"awaiting_plan_decision"});case"terminal.entered":return ue({...t,lifecycle:e.suspended?"suspended":"terminal",runtimeState:"stopped"});case"worktree.decision_requested":return ue({...t,lifecycle:"awaiting_worktree_decision",worktreeState:"pending_decision"});case"worktree.state_set":return ue({...t,worktreeState:e.worktreeState,lifecycle:e.worktreeState==="pending_decision"?"awaiting_worktree_decision":La.has(e.worktreeState)?"terminal":t.lifecycle});case"delivery.state_set":return ue({...t,deliveryState:e.deliveryState})}}function Ba(t,e){let n={...t,...Y(e,"lifecycle")?{lifecycle:e.lifecycle}:{},...Y(e,"approvalState")?{approvalState:e.approvalState}:{},...Y(e,"approvalExecutionState")?{approvalExecutionState:e.approvalExecutionState}:{},...Y(e,"worktreeState")?{worktreeState:e.worktreeState}:{},...Y(e,"runtimeState")?{runtimeState:e.runtimeState}:{},...Y(e,"deliveryState")?{deliveryState:e.deliveryState}:{},...Y(e,"requestedPermissionMode")?{requestedPermissionMode:e.requestedPermissionMode}:{},...Y(e,"currentPermissionMode")?{currentPermissionMode:e.currentPermissionMode}:{},...Y(e,"pendingPlanApproval")?{pendingPlanApproval:e.pendingPlanApproval}:{},...Y(e,"planApprovalContext")?{planApprovalContext:e.planApprovalContext}:{},...Y(e,"planDecisionVersion")?{planDecisionVersion:e.planDecisionVersion}:{},...Y(e,"actionablePlanDecisionVersion")?{actionablePlanDecisionVersion:e.actionablePlanDecisionVersion}:{},...Y(e,"canonicalPlanPromptVersion")?{canonicalPlanPromptVersion:e.canonicalPlanPromptVersion}:{},...Y(e,"approvalPromptRequiredVersion")?{approvalPromptRequiredVersion:e.approvalPromptRequiredVersion}:{},...Y(e,"approvalPromptVersion")?{approvalPromptVersion:e.approvalPromptVersion}:{},...Y(e,"approvalPromptStatus")?{approvalPromptStatus:e.approvalPromptStatus}:{},...Y(e,"approvalPromptTransport")?{approvalPromptTransport:e.approvalPromptTransport}:{},...Y(e,"approvalPromptMessageKind")?{approvalPromptMessageKind:e.approvalPromptMessageKind}:{},...Y(e,"approvalPromptLastAttemptAt")?{approvalPromptLastAttemptAt:e.approvalPromptLastAttemptAt}:{},...Y(e,"approvalPromptDeliveredAt")?{approvalPromptDeliveredAt:e.approvalPromptDeliveredAt}:{},...Y(e,"approvalPromptFailedAt")?{approvalPromptFailedAt:e.approvalPromptFailedAt}:{},...Y(e,"planModeApproved")?{planModeApproved:e.planModeApproved}:{}};return e.approvalState==="changes_requested"&&e.pendingPlanApproval===void 0&&(n={...n,pendingPlanApproval:!1}),n.pendingPlanApproval?n={...n,approvalState:"pending",actionablePlanDecisionVersion:n.actionablePlanDecisionVersion??n.planDecisionVersion,lifecycle:"awaiting_plan_decision"}:n.approvalState==="changes_requested"&&(n={...n,actionablePlanDecisionVersion:void 0,lifecycle:"awaiting_user_input"}),Y(e,"pendingWorktreeDecisionSince")&&e.pendingWorktreeDecisionSince!==void 0||n.worktreeState==="pending_decision"?n=wi(n,{type:"worktree.decision_requested"}):La.has(n.worktreeState)&&(n={...n,lifecycle:"terminal"}),ue(n)}var sr=class{queue=[];resolve=null;done=!1;hasPending(){return this.queue.length>0}push(e){this.queue.push(e),this.resolve&&(this.resolve(),this.resolve=null)}end(){this.done=!0,this.resolve&&(this.resolve(),this.resolve=null)}async*[Symbol.asyncIterator](){for(;;){for(;this.queue.length>0;)yield this.queue.shift();if(this.done)return;await new Promise(e=>{this.resolve=e})}}};import{createHash as Fp}from"crypto";import{appendFileSync as qp}from"fs";import{tmpdir as Kp}from"os";import{join as Up}from"path";var Fa=2e3,Vp=/^[A-Za-z0-9_.-]+$/;function Gp(t){return Vp.test(t)?t:`hashed+${Fp("sha256").update(t,"utf8").digest("hex")}`}function nt(t){return Up(Kp(),`openclaw-agent-${Gp(t)}.txt`)}function jp(t,e){if(!e)return;let n=e.split(`
69
+ `),[r="",...o]=n;t.length===0?t.push(r):t[t.length-1]+=r;for(let i of o)t.push(i)}function qa(t,e,n){jp(t,n),t.length>Fa&&t.splice(0,t.length-Fa);try{qp(nt(e),n,"utf-8")}catch{}return t}var ar=class{timers=new Map;get size(){return this.timers.size}set(e,n,r){this.clear(e);let o=setTimeout(()=>{this.timers.get(e)===o&&this.timers.delete(e),r()},n);o.unref?.(),this.timers.set(e,o)}clear(e){let n=this.timers.get(e);n&&(clearTimeout(n),this.timers.delete(e))}clearAll(){for(let e of this.timers.values())clearTimeout(e);this.timers.clear()}};var lr=class{constructor(e){this.deps=e}deps;waitingForInputFired=!1;lastTurnHadQuestion=!1;turnInProgress=!0;currentTurnText="";currentTurnPlanArtifact;beginUserTurn(){this.waitingForInputFired=!1,this.turnInProgress=!0,this.currentTurnText="",this.currentTurnPlanArtifact=void 0,this.lastTurnHadQuestion=!1}noteTextDelta(e,n){this.waitingForInputFired=!1,n||(this.lastTurnHadQuestion=!1),this.deps.appendOutput(e),this.currentTurnText+=this.currentTurnText?`
70
+ ${e}`:e,this.deps.emitOutput(e)}noteToolCall(e){let{name:n,input:r,currentPermissionMode:o,permissionMode:i,planModeApproved:s}=e;if(n==="Write"){let a=r;typeof a?.file_path=="string"&&a.file_path.includes("/.claude/plans/")&&this.deps.setPlanFilePath(a.file_path)}n==="AskUserQuestion"?(this.lastTurnHadQuestion=!0,this.deps.applyInputRequested(),(o==="plan"||i==="plan")&&!s&&this.deps.markPendingPlanApproval("plan-mode")):(n==="ExitPlanMode"||n==="set_permission_mode")&&!s&&(this.lastTurnHadQuestion=!0,this.deps.markPendingPlanApproval("plan-mode")),this.deps.emitToolUse(n,r)}notePendingInput(){this.lastTurnHadQuestion=!0,this.deps.applyInputRequested(),this.waitingForInputFired||(this.waitingForInputFired=!0,this.deps.emitTurnEnd(!0))}clearResolvedPendingInput(e,n){if(!(!e||n?.requestId===e))return n}notePlanArtifact(e,n){if(this.currentTurnPlanArtifact=e,this.deps.setLatestPlanArtifact(e),!n)return;let r=e.markdown.trim();!r||this.currentTurnText.trim()===r||(this.deps.appendOutput(r),this.currentTurnText=r,this.deps.emitOutput(r))}noteSettingsChanged(e){let{oldMode:n,permissionMode:r,planModeApproved:o}=e;if(r)return r!=="plan"&&n==="plan"&&!o&&(this.deps.markPendingPlanApproval("plan-mode"),this.lastTurnHadQuestion=!0),r}finishSuccessfulTurn(e){let{currentPermissionMode:n,permissionMode:r,pendingPlanApproval:o,planModeApproved:i,pendingInputState:s,hasPendingMessages:a}=e,l=o;(n==="plan"||r==="plan")&&!l&&!i&&(this.deps.markPendingPlanApproval("plan-mode"),l=!0);let d=l||this.lastTurnHadQuestion||!!s;if(this.turnInProgress=a,d&&!this.waitingForInputFired)this.waitingForInputFired=!0,l||this.deps.markAwaitingUserInput(),this.deps.emitTurnEnd(!0);else if(!a&&!d){if(this.deps.queueWorktreeFinalizationPrompt?.()){this.turnInProgress=!0;return}this.deps.completeTurn(),this.deps.emitTurnEnd(!1)}}finishTerminalTurn(){this.turnInProgress=!1}finishInterruptedTurn(e){this.turnInProgress=e,this.waitingForInputFired=!1,this.lastTurnHadQuestion=!1,this.currentTurnText="",this.currentTurnPlanArtifact=void 0}resetAfterRun(){this.lastTurnHadQuestion=!1,this.currentTurnText="",this.currentTurnPlanArtifact=void 0}};var dr=class{constructor(e){this.deps=e}deps;applyMessage(e,n){if(e.type==="backend_ref"){this.deps.clearStartupTimer(),this.deps.assignBackendRef({...e.ref}),this.deps.transitionRunning();return}if(e.type==="run_started"){e.runId&&this.deps.noteRunStarted(e.runId);return}if(e.type==="text_delta"){this.deps.noteTextDelta(e.text,n.pendingPlanApproval);return}if(e.type==="tool_call"){this.deps.noteToolCall({name:e.name,input:e.input,currentPermissionMode:n.currentPermissionMode,permissionMode:n.permissionMode,planModeApproved:n.planModeApproved});return}if(e.type==="pending_input"){this.deps.setPendingInputState(e.state),this.deps.notePendingInput();return}if(e.type==="pending_input_resolved"){this.deps.setPendingInputState(this.deps.clearResolvedPendingInput(e.requestId,n.pendingInputState));return}if(e.type==="plan_artifact"){this.deps.notePlanArtifact(e);return}if(e.type==="settings_changed"){let r=this.deps.noteSettingsChanged({oldMode:n.currentPermissionMode,permissionMode:e.permissionMode,planModeApproved:n.planModeApproved});r&&this.deps.setCurrentPermissionMode(r);return}if(e.type==="run_completed"){this.deps.handleRunCompleted(e.data);return}e.type}};ke();var mm=120*1e3;function vr(t){return t instanceof Error?t.message:String(t)}var wr=class extends pm{id;name;harnessSessionId;backendRef;harness;harnessHandle;prompt;workdir;model;reasoningEffort;fastMode;systemPrompt;allowedTools;permissionMode;requestedPermissionMode;planApproval;codexApprovalPolicy;currentPermissionMode;pendingModeSwitch;resumeSessionId;forkSession;worktreePath;originalWorkdir;worktreeBranch;worktreeStrategy;repoIntegrationPolicy;repoIntegrationPolicySource;repoProvider;worktreeBaseBranch;worktreePrTargetRepo;autoMergeParentSessionId;autoMergeConflictResolutionAttemptCount;autoMergeResolverSessionId;worktreePushRemote;worktreeDisposition;worktreePrUrl;worktreePrNumber;worktreeMerged;worktreeMergedAt;worktreeLifecycle;worktreeState="none";multiTurn;goalTaskId;messageStream;_status="starting";error;startedAt;completedAt;abortController;outputBuffer=[];result;costUsd=0;originChannel;originThreadId;originAgentId;originSessionKey;route;pendingInputState;pendingPlanApproval=!1;planApprovalContext;planDecisionVersion=0;actionablePlanDecisionVersion;canonicalPlanPromptVersion;approvalPromptRequiredVersion;approvalPromptVersion;approvalPromptStatus="not_sent";approvalPromptTransport="none";approvalPromptMessageKind="none";approvalPromptLastAttemptAt;approvalPromptDeliveredAt;approvalPromptFailedAt;planFilePath;killReason="unknown";planModeApproved=!1;turnRuntime;harnessEvents;worktreeFinalizationPromptIssued=!1;lifecycle="starting";approvalState="not_required";approvalExecutionState="not_plan_gated";approvalRationale;latestPlanArtifact;latestPlanArtifactVersion;runtimeState="live";deliveryState="idle";canUseTool;autoRespondCount=0;timers=new ar;constructor(e,n){super(),this.id=e.sessionIdOverride??ir(8),this.name=n,this.harness=e.harness?on(e.harness):Sa(),this.prompt=e.prompt,this.workdir=e.workdir,this.model=e.model??pt(this.harness.name),this.reasoningEffort=e.reasoningEffort??Ke(this.harness.name),this.fastMode=this.harness.name==="codex"?e.fastMode??mt(this.harness.name):void 0,this.systemPrompt=e.systemPrompt,this.allowedTools=e.allowedTools,this.permissionMode=e.permissionMode??D.permissionMode,this.requestedPermissionMode=e.requestedPermissionMode??this.permissionMode,this.planApproval=e.planApproval??D.planApproval,this.codexApprovalPolicy=this.harness.name==="codex"?"never":void 0,this.currentPermissionMode=this.permissionMode,this.originChannel=e.originChannel,this.originThreadId=e.originThreadId,this.originAgentId=e.originAgentId,this.originSessionKey=e.originSessionKey,this.route=e.route?{...e.route}:void 0,this.backendRef=e.backendRef?{...e.backendRef}:void 0,this.resumeSessionId=e.resumeSessionId,this.forkSession=e.forkSession,this.multiTurn=e.multiTurn??!0,this.goalTaskId=e.goalTaskId,this.worktreeStrategy=e.worktreeStrategy,this.repoIntegrationPolicy=e.repoIntegrationPolicy,this.repoIntegrationPolicySource=e.repoIntegrationPolicySource,this.repoProvider=e.repoProvider,this.worktreeBaseBranch=e.worktreeBaseBranch,e.worktreePrTargetRepo&&(this.worktreePrTargetRepo=e.worktreePrTargetRepo),e.autoMergeParentSessionId&&(this.autoMergeParentSessionId=e.autoMergeParentSessionId),e.autoMergeConflictResolutionAttemptCount!==void 0&&(this.autoMergeConflictResolutionAttemptCount=e.autoMergeConflictResolutionAttemptCount),e.autoMergeResolverSessionId&&(this.autoMergeResolverSessionId=e.autoMergeResolverSessionId),this.canUseTool=e.canUseTool,this.startedAt=Date.now(),this.abortController=new AbortController,this.turnRuntime=new lr({appendOutput:r=>qa(this.outputBuffer,this.id,r),emitOutput:r=>this.emit("output",this,r),emitToolUse:(r,o)=>this.emit("toolUse",this,r,o),emitTurnEnd:r=>this.emit("turnEnd",this,r),markPendingPlanApproval:r=>this.markPendingPlanApproval(r),markAwaitingUserInput:()=>this.markAwaitingUserInput(),applyInputRequested:()=>this.applyControlEvent({type:"input.requested"}),completeTurn:()=>{this.applyControlEvent({type:"terminal.entered"}),this.complete("done")},queueWorktreeFinalizationPrompt:()=>this.queueWorktreeFinalizationPrompt(),setPlanFilePath:r=>{this.planFilePath=r},setLatestPlanArtifact:r=>{this.latestPlanArtifact=r;let o=this.pendingPlanApproval?this.actionablePlanDecisionVersion??this.planDecisionVersion:void 0;this.latestPlanArtifactVersion=o&&o>0?o:void 0}}),this.harnessEvents=new dr({clearStartupTimer:()=>this.clearTimer("startup"),assignBackendRef:r=>{this.backendRef=r,this.harnessSessionId=r.conversationId,r.worktreePath&&(this.worktreePath=r.worktreePath,this.originalWorkdir??=this.workdir,this.worktreeBranch??=xt(r.worktreePath),this.worktreeStrategy&&this.worktreeStrategy!=="off"&&this.applyControlEvent({type:"worktree.state_set",worktreeState:"provisioned"}))},noteRunStarted:r=>{this.backendRef&&(this.backendRef={...this.backendRef,runId:r})},transitionRunning:()=>{this._status==="starting"&&this.transition("running")},noteTextDelta:(r,o)=>this.turnRuntime.noteTextDelta(r,o),noteToolCall:r=>this.turnRuntime.noteToolCall(r),setPendingInputState:r=>{this.pendingInputState=r},notePendingInput:()=>this.turnRuntime.notePendingInput(),clearResolvedPendingInput:(r,o)=>this.turnRuntime.clearResolvedPendingInput(r,o),notePlanArtifact:r=>this.turnRuntime.notePlanArtifact(r.artifact,r.finalized),noteSettingsChanged:r=>this.turnRuntime.noteSettingsChanged(r),setCurrentPermissionMode:r=>{this.currentPermissionMode=r,this.applyControlEvent({type:"permission.mode_changed",currentPermissionMode:r})},handleRunCompleted:r=>{let o=r.outcome??(r.success?"completed":"failed");this.result={subtype:o==="interrupted"?"interrupted":r.success?"success":"error",duration_ms:r.duration_ms,total_cost_usd:r.total_cost_usd,num_turns:r.num_turns,result:r.result,is_error:o==="failed",session_id:r.session_id},this.costUsd=r.total_cost_usd;let i=this.multiTurn&&this.messageStream&&o==="interrupted",s=this.multiTurn&&this.messageStream&&o==="completed";i?(this.resetIdleTimer(),this.turnRuntime.finishInterruptedTurn(this.messageStream?.hasPending()===!0)):s?(this.resetIdleTimer(),this.turnRuntime.finishSuccessfulTurn({currentPermissionMode:this.currentPermissionMode,permissionMode:this.permissionMode,pendingPlanApproval:this.pendingPlanApproval,planModeApproved:this.planModeApproved,pendingInputState:this.pendingInputState,hasPendingMessages:this.messageStream?.hasPending()===!0})):(this.turnRuntime.finishTerminalTurn(),this.transitionToTerminal(o==="completed"?"completed":"failed")),this.turnRuntime.resetAfterRun(),this.pendingInputState=void 0}}),this.applyControlEvent({type:"initialize",hasWorktree:!!(this.worktreeStrategy&&this.worktreeStrategy!=="off")}),(e.planModeApproved!==void 0||e.approvalState!==void 0||e.approvalExecutionState!==void 0||e.approvalRationale!==void 0||e.pendingPlanApproval!==void 0||e.planApprovalContext!==void 0||e.planDecisionVersion!==void 0||e.actionablePlanDecisionVersion!==void 0||e.canonicalPlanPromptVersion!==void 0||e.approvalPromptRequiredVersion!==void 0||e.approvalPromptVersion!==void 0||e.approvalPromptStatus!==void 0||e.approvalPromptTransport!==void 0||e.approvalPromptMessageKind!==void 0||e.approvalPromptLastAttemptAt!==void 0||e.approvalPromptDeliveredAt!==void 0||e.approvalPromptFailedAt!==void 0)&&this.applyControlPatch({...e.planModeApproved!==void 0?{planModeApproved:e.planModeApproved}:{},...e.approvalState!==void 0?{approvalState:e.approvalState}:{},...e.approvalExecutionState!==void 0?{approvalExecutionState:e.approvalExecutionState}:{},...e.pendingPlanApproval!==void 0?{pendingPlanApproval:e.pendingPlanApproval}:{},...e.planApprovalContext!==void 0?{planApprovalContext:e.planApprovalContext}:{},...e.planDecisionVersion!==void 0?{planDecisionVersion:e.planDecisionVersion}:{},...e.actionablePlanDecisionVersion!==void 0?{actionablePlanDecisionVersion:e.actionablePlanDecisionVersion}:{},...e.canonicalPlanPromptVersion!==void 0?{canonicalPlanPromptVersion:e.canonicalPlanPromptVersion}:{},...e.approvalPromptRequiredVersion!==void 0?{approvalPromptRequiredVersion:e.approvalPromptRequiredVersion}:{},...e.approvalPromptVersion!==void 0?{approvalPromptVersion:e.approvalPromptVersion}:{},...e.approvalPromptStatus!==void 0?{approvalPromptStatus:e.approvalPromptStatus}:{},...e.approvalPromptTransport!==void 0?{approvalPromptTransport:e.approvalPromptTransport}:{},...e.approvalPromptMessageKind!==void 0?{approvalPromptMessageKind:e.approvalPromptMessageKind}:{},...e.approvalPromptLastAttemptAt!==void 0?{approvalPromptLastAttemptAt:e.approvalPromptLastAttemptAt}:{},...e.approvalPromptDeliveredAt!==void 0?{approvalPromptDeliveredAt:e.approvalPromptDeliveredAt}:{},...e.approvalPromptFailedAt!==void 0?{approvalPromptFailedAt:e.approvalPromptFailedAt}:{}}),this.approvalRationale=e.approvalRationale}get status(){return this._status}get harnessName(){return this.harness.name}get backendKind(){return this.harness.backendKind}get backendCapabilities(){return this.harness.capabilities}get backendConversationId(){return $(this)}approvalSnapshot(){return{requestedPermissionMode:this.requestedPermissionMode,currentPermissionMode:this.currentPermissionMode,approvalExecutionState:this.approvalExecutionState,approvalRationale:this.approvalRationale,planModeApproved:this.controlStateSnapshot().planModeApproved,pendingPlanApproval:this.pendingPlanApproval,planApprovalContext:this.planApprovalContext,planDecisionVersion:this.planDecisionVersion,actionablePlanDecisionVersion:this.actionablePlanDecisionVersion,canonicalPlanPromptVersion:this.canonicalPlanPromptVersion,approvalPromptRequiredVersion:this.approvalPromptRequiredVersion,approvalPromptVersion:this.approvalPromptVersion,approvalPromptStatus:this.approvalPromptStatus,approvalPromptTransport:this.approvalPromptTransport,approvalPromptMessageKind:this.approvalPromptMessageKind,approvalPromptLastAttemptAt:this.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:this.approvalPromptDeliveredAt,approvalPromptFailedAt:this.approvalPromptFailedAt,planApproval:this.planApproval,codexApprovalPolicy:this.codexApprovalPolicy}}worktreeSnapshot(){return{worktreePath:this.worktreePath,worktreeBranch:this.worktreeBranch,worktreeStrategy:this.worktreeStrategy,repoIntegrationPolicy:this.repoIntegrationPolicy,repoIntegrationPolicySource:this.repoIntegrationPolicySource,repoProvider:this.repoProvider,worktreeBaseBranch:this.worktreeBaseBranch,worktreePrTargetRepo:this.worktreePrTargetRepo,autoMergeParentSessionId:this.autoMergeParentSessionId,autoMergeConflictResolutionAttemptCount:this.autoMergeConflictResolutionAttemptCount,autoMergeResolverSessionId:this.autoMergeResolverSessionId,worktreeLifecycle:this.worktreeLifecycle}}backendSnapshot(){return{harnessSessionId:this.harnessSessionId,backendRef:this.backendRef,harness:this.harnessName,backendKind:this.backendKind,backendConversationId:this.backendConversationId}}routingSnapshot(){return{route:this.route,originAgentId:this.originAgentId,originChannel:this.originChannel,originThreadId:this.originThreadId,originSessionKey:this.originSessionKey}}get waitingForInputFired(){return this.turnRuntime.waitingForInputFired}set waitingForInputFired(e){this.turnRuntime.waitingForInputFired=e}get turnInProgress(){return this.turnRuntime.turnInProgress}set turnInProgress(e){this.turnRuntime.turnInProgress=e}get currentTurnPlanArtifact(){return this.turnRuntime.currentTurnPlanArtifact}set currentTurnPlanArtifact(e){this.turnRuntime.currentTurnPlanArtifact=e}get duration(){return(this.completedAt??Date.now())-this.startedAt}get phase(){return this.lifecycle}get isExplicitlyResumable(){return this.status!=="running"&&this.status!=="completed"&&this.killReason!=="done"&&!!this.backendConversationId}transition(e){if(!Na[this._status].includes(e))throw new Error(`Session state error: cannot transition from ${this._status} to ${e}. This is an internal error — please report it.`);let n=this._status;this._status=e,this.applyControlEvent({type:"status.transition",status:e}),this.emit("statusChange",this,e,n)}setTimer(e,n,r){this.timers.set(e,n,r)}clearTimer(e){this.timers.clear(e)}clearAllTimers(){this.timers.clearAll()}markPendingPlanApproval(e){let n=this.latestPlanArtifactVersion;this.approvalRationale=void 0,this.applyControlEvent({type:"plan.requested",context:e});let r=this.actionablePlanDecisionVersion??this.planDecisionVersion;this.currentTurnPlanArtifact&&r>0?(this.latestPlanArtifact=this.currentTurnPlanArtifact,this.latestPlanArtifactVersion=r):n!==r&&(this.latestPlanArtifact=void 0,this.latestPlanArtifactVersion=void 0)}clearPendingPlanApproval(){this.applyControlEvent({type:"plan.cleared"})}markAwaitingUserInput(){this.applyControlEvent({type:"input.requested"})}queueWorktreeFinalizationPrompt(){if(!this.multiTurn||!this.messageStream||!this.worktreePath||!this.worktreeStrategy||this.worktreeStrategy==="off"||this.worktreeFinalizationPromptIssued)return!1;let e=rt(this.worktreePath);if(e.length===0)return!1;this.worktreeFinalizationPromptIssued=!0;let n=e.slice(0,20).map(i=>`- ${i}`).join(`
71
71
  `),r=e.length>20?`
72
72
  - ...and ${e.length-20} more`:"",o=["Your worktree still has uncommitted changes, so this session cannot finish yet.","",`Worktree: ${this.worktreePath}`,`Branch: ${this.worktreeBranch??"(unknown)"}`,"","Dirty entries:",`${n}${r}`,"","Before finishing, run `git status --short` in the worktree and do exactly one of these:","1. If these are real task changes, commit them on the worktree branch with `git add` and `git commit`.","2. If these are temporary or unrelated artifacts, remove or restore them so the worktree is clean.","3. If no repository changes were intended, leave the worktree clean and say that no changes were needed.","","Do not finish again until `git status --short` is clean or all real task changes are committed."].join(`
73
- `);return this.messageStream.push(this.harness.buildUserMessage(o,this.backendConversationId??"")),!0}async start(){try{let e;this.multiTurn?(this.messageStream=new or,this.messageStream.push(this.harness.buildUserMessage(this.prompt,"")),e=this.messageStream):e=this.prompt;let n=this.harness.launch({prompt:e,cwd:this.workdir,model:this.model,reasoningEffort:this.reasoningEffort,fastMode:this.fastMode,permissionMode:this.permissionMode,codexApprovalPolicy:this.codexApprovalPolicy,systemPrompt:this.systemPrompt,allowedTools:this.allowedTools,resumeSessionId:this.resumeSessionId,forkSession:this.forkSession,backendRef:this.backendRef,worktreeStrategy:this.worktreeStrategy,originalWorkdir:this.originalWorkdir??this.workdir,abortController:this.abortController,mcpServers:Ms(),canUseTool:this.canUseTool});this.harnessHandle=n,this.setTimer("startup",tm,()=>{this._status==="starting"&&this.kill("startup-timeout")})}catch(e){let n=e instanceof Error?e.message:String(e);this.transitionToTerminal("failed",{error:n});return}this.consumeMessages(this.harnessHandle.messages).catch(e=>{let n=e instanceof Error?e.message:String(e),r=e instanceof Error?e.stack:void 0;console.error(`[Session ${this.id}] consumeMessages error: ${n}`,r),this.isActive&&this.transitionToTerminal("failed",{error:n})})}async sendMessage(e){if(this._status!=="running")throw new Error(`Session is not running (status: ${this._status})`);this.resetIdleTimer(),this.turnRuntime.beginUserTurn(),this.applyControlEvent({type:"turn.started"});let n=e;if(this.pendingModeSwitch){let r=this.pendingModeSwitch,o=!1,i=!1;if(this.harnessHandle?.setPermissionMode)try{await this.harnessHandle.setPermissionMode(r),this.currentPermissionMode=r,this.applyControlEvent({type:"permission.mode_changed",currentPermissionMode:r}),this.pendingModeSwitch=void 0,i=!0,o=!0}catch(s){throw console.error(`[Session ${this.id}] setPermissionMode(${r}) FAILED: ${kr(s)}`),this.markPendingPlanApproval(this.planApprovalContext??"plan-mode"),new Error(`Failed to switch permission mode to ${r}: ${kr(s)}`)}else this.pendingModeSwitch=void 0,i=!0,o=!0,`${this.id}${this.currentPermissionMode}`;i&&(this.clearPendingPlanApproval(),r!=="plan"&&this.applyControlEvent({type:"plan.approved"})),o&&(n=`[SYSTEM: The user has approved your plan. Exit plan mode immediately and implement the changes with full permissions. Do not ask for further confirmation.]
73
+ `);return this.messageStream.push(this.harness.buildUserMessage(o,this.backendConversationId??"")),!0}async start(){try{let e;this.multiTurn?(this.messageStream=new sr,this.messageStream.push(this.harness.buildUserMessage(this.prompt,"")),e=this.messageStream):e=this.prompt;let n=this.harness.launch({prompt:e,cwd:this.workdir,model:this.model,reasoningEffort:this.reasoningEffort,fastMode:this.fastMode,permissionMode:this.permissionMode,codexApprovalPolicy:this.codexApprovalPolicy,systemPrompt:this.systemPrompt,allowedTools:this.allowedTools,resumeSessionId:this.resumeSessionId,forkSession:this.forkSession,backendRef:this.backendRef,worktreeStrategy:this.worktreeStrategy,originalWorkdir:this.originalWorkdir??this.workdir,abortController:this.abortController,mcpServers:Ns(),canUseTool:this.canUseTool});this.harnessHandle=n,this.setTimer("startup",mm,()=>{this._status==="starting"&&this.kill("startup-timeout")})}catch(e){let n=e instanceof Error?e.message:String(e);this.transitionToTerminal("failed",{error:n});return}this.consumeMessages(this.harnessHandle.messages).catch(e=>{let n=e instanceof Error?e.message:String(e),r=e instanceof Error?e.stack:void 0;console.error(`[Session ${this.id}] consumeMessages error: ${n}`,r),this.isActive&&this.transitionToTerminal("failed",{error:n})})}async sendMessage(e){if(this._status!=="running")throw new Error(`Session is not running (status: ${this._status})`);this.resetIdleTimer(),this.turnRuntime.beginUserTurn(),this.applyControlEvent({type:"turn.started"});let n=e;if(this.pendingModeSwitch){let r=this.pendingModeSwitch,o=!1,i=!1;if(this.harnessHandle?.setPermissionMode)try{await this.harnessHandle.setPermissionMode(r),this.currentPermissionMode=r,this.applyControlEvent({type:"permission.mode_changed",currentPermissionMode:r}),this.pendingModeSwitch=void 0,i=!0,o=!0}catch(s){throw console.error(`[Session ${this.id}] setPermissionMode(${r}) FAILED: ${vr(s)}`),this.markPendingPlanApproval(this.planApprovalContext??"plan-mode"),new Error(`Failed to switch permission mode to ${r}: ${vr(s)}`)}else this.pendingModeSwitch=void 0,i=!0,o=!0,`${this.id}${this.currentPermissionMode}`;i&&(this.clearPendingPlanApproval(),r!=="plan"&&this.applyControlEvent({type:"plan.approved"})),o&&(n=`[SYSTEM: The user has approved your plan. Exit plan mode immediately and implement the changes with full permissions. Do not ask for further confirmation.]
74
74
 
75
75
  ${e}`)}else if((this.pendingPlanApproval||this.approvalState==="changes_requested")&&!this.planModeApproved&&(this.approvalState!=="changes_requested"&&this.applyControlEvent({type:"plan.changes_requested"}),n=`[SYSTEM: The user wants changes to your plan. Revise the plan based on their feedback below, then re-submit your revised plan for approval. Do NOT start implementing yet.]
76
76
 
77
- ${e}`,this.harnessHandle?.setPermissionMode))try{await this.harnessHandle.setPermissionMode("plan"),this.currentPermissionMode="plan",this.applyControlEvent({type:"permission.mode_changed",currentPermissionMode:"plan"})}catch(r){`${this.id}${kr(r)}`}if(this.multiTurn&&this.messageStream)this.messageStream.push(this.harness.buildUserMessage(n,this.backendConversationId??""));else if(this.harnessHandle?.streamInput){let r=this.harness.buildUserMessage(n,this.backendConversationId??"");async function*o(){yield r}await this.harnessHandle.streamInput(o())}else throw new Error("Session does not support follow-up messages (launched in single-turn mode).")}async interrupt(){return!this.turnInProgress||!this.harnessHandle?.interrupt?!1:(await this.harnessHandle.interrupt(),!0)}async submitPendingInputOption(e,n){if(!this.pendingInputState||!this.harnessHandle?.submitPendingInputOption)return!1;let r=await this.harnessHandle.submitPendingInputOption(e,n);return r&&(this.waitingForInputFired=!1),r}canSubmitPendingInputOption(){return!!(this.pendingInputState&&this.harnessHandle?.submitPendingInputOption)}async submitPendingInputText(e){if(!this.pendingInputState||!this.harnessHandle?.submitPendingInputText)return!1;let n=await this.harnessHandle.submitPendingInputText(e);return n&&(this.waitingForInputFired=!1),n}switchPermissionMode(e){this.pendingModeSwitch=e}get isActive(){return this._status==="starting"||this._status==="running"}kill(e){this.transitionToTerminal("killed",{reason:e})}complete(e="done"){this.transitionToTerminal("completed",{reason:e})}incrementAutoRespond(){this.autoRespondCount++}resetAutoRespond(){this.autoRespondCount=0}getOutput(e){return e===void 0?this.outputBuffer.slice():this.outputBuffer.slice(-e)}resetIdleTimer(){if(!this.multiTurn)return;let e=(D.idleTimeoutMinutes??15)*60*1e3;this.setTimer("idle",e,()=>{this._status==="running"&&(this.applyControlEvent({type:"terminal.entered",suspended:!0}),this.kill("idle-timeout"))})}teardown(){this.clearAllTimers(),this.completedAt||(this.completedAt=Date.now()),this.messageStream&&this.messageStream.end(),this.harnessHandle?.interrupt&&this.harnessHandle.interrupt().catch(e=>{`${this.id}${kr(e)}`}),this.abortController.abort(),this.applyControlEvent({type:"terminal.entered",suspended:this.lifecycle==="suspended"})}transitionToTerminal(e,n={}){this.isActive&&(this.turnInProgress=!1,n.reason&&(this.killReason=n.reason),n.error!==void 0&&(this.error=n.error),this.completedAt=Date.now(),this.applyControlEvent({type:"terminal.entered",suspended:e==="killed"&&n.reason==="idle-timeout"}),this.transition(e),this.teardown())}async consumeMessages(e){for await(let n of e){if(!this.isActive)break;this.resetIdleTimer(),this.harnessEvents.applyMessage(n,{pendingPlanApproval:this.pendingPlanApproval,currentPermissionMode:this.currentPermissionMode,permissionMode:this.permissionMode,planModeApproved:this.planModeApproved,pendingInputState:this.pendingInputState})}}controlStateSnapshot(){return{status:this._status,lifecycle:this.lifecycle,approvalState:this.approvalState,approvalExecutionState:this.approvalExecutionState,worktreeState:this.worktreeState,runtimeState:this.runtimeState,deliveryState:this.deliveryState,requestedPermissionMode:this.requestedPermissionMode,currentPermissionMode:this.currentPermissionMode,pendingPlanApproval:this.pendingPlanApproval,planApprovalContext:this.planApprovalContext,planDecisionVersion:this.planDecisionVersion,actionablePlanDecisionVersion:this.actionablePlanDecisionVersion,canonicalPlanPromptVersion:this.canonicalPlanPromptVersion,approvalPromptRequiredVersion:this.approvalPromptRequiredVersion,approvalPromptVersion:this.approvalPromptVersion,approvalPromptStatus:this.approvalPromptStatus,approvalPromptTransport:this.approvalPromptTransport,approvalPromptMessageKind:this.approvalPromptMessageKind,approvalPromptLastAttemptAt:this.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:this.approvalPromptDeliveredAt,approvalPromptFailedAt:this.approvalPromptFailedAt,planModeApproved:this.planModeApproved}}applyControlEvent(e){let n=yi(this.controlStateSnapshot(),e);this.applyControlState(n)}applyControlPatch(e){let n=$a(this.controlStateSnapshot(),e);this.applyControlState(n)}setControlField(e,n){this.applyControlPatch({[e]:n})}applyControlState(e){let n=this.lifecycle;this.lifecycle=e.lifecycle,this.approvalState=e.approvalState,this.approvalExecutionState=e.approvalExecutionState,this.worktreeState=e.worktreeState,this.runtimeState=e.runtimeState,this.deliveryState=e.deliveryState,this.pendingPlanApproval=e.pendingPlanApproval,this.planApprovalContext=e.planApprovalContext,this.planDecisionVersion=e.planDecisionVersion,this.actionablePlanDecisionVersion=e.actionablePlanDecisionVersion,this.canonicalPlanPromptVersion=e.canonicalPlanPromptVersion,this.approvalPromptRequiredVersion=e.approvalPromptRequiredVersion,this.approvalPromptVersion=e.approvalPromptVersion,this.approvalPromptStatus=e.approvalPromptStatus,this.approvalPromptTransport=e.approvalPromptTransport,this.approvalPromptMessageKind=e.approvalPromptMessageKind,this.approvalPromptLastAttemptAt=e.approvalPromptLastAttemptAt,this.approvalPromptDeliveredAt=e.approvalPromptDeliveredAt,this.approvalPromptFailedAt=e.approvalPromptFailedAt,this.planModeApproved=e.planModeApproved,n!==this.lifecycle&&this.emit("lifecycleChange",this,this.lifecycle,n)}};var nm=50,rm=1,om=new Set(["starting","running","completed","failed","killed"]),im=5,sm=1440*60*1e3,vr=new Set(["merged","released","dismissed","no_change"]);function am(t){let e=Number(t);return!Number.isFinite(e)||e<rm?nm:Math.floor(e)}function lm(t){return typeof t=="string"&&om.has(t)}function dm(t){let e=t.split(`
78
- `);return e.at(-1)===""&&e.pop(),e}function Ai(t){return t.backendRef?.conversationId??t.harnessSessionId}function um(t,e){return e&&vr.has(e)&&(!t||!vr.has(t))?e:t??e}function cm(t,e){return e&&vr.has(e.state)&&(!t||!vr.has(t.state))?e:t??e}function el(t,e,n){let r=Xa(t,"utf-8"),o=dm(r);return e.full?o:o.slice(-n)}function pm(t,e,n){if(t.status!=="starting"&&t.status!=="running")return null;let r=et(t.id);if(!Ri(r))return null;try{return el(r,e,n)}catch{return null}}function mm(t){let e=Re(t.duration),n=` | Cost: $${t.costUsd.toFixed(4)}`,r=t.phase?` | Phase: ${t.phase}`:"",o=t.lifecycle&&t.lifecycle!==t.phase?` | Lifecycle: ${t.lifecycle}`:"";return[`Session: ${t.name} [${t.id}] | Status: ${t.status.toUpperCase()}${r}${o}${n} | Duration: ${e}`,`${"─".repeat(60)}`].join(`
79
- `)}function tl(t,e){let n=t.name||t.sessionId||Ai(t)||"unknown",r=t.lifecycle?` | Phase: ${t.lifecycle}`:"";return[`Session: ${n} | Status: ${t.status.toUpperCase()}${r} | Cost: $${t.costUsd.toFixed(4)}`,e,`${"─".repeat(60)}`].join(`
80
- `)}function fm(t){return`(retrieved from ${t.outputPath} — evicted from runtime cache — showing persisted output)`}function gm(t){return t.outputPath?`(persisted session metadata recovered; output file is unavailable at ${t.outputPath})`:"(persisted session metadata recovered; no output file was recorded before the runtime was interrupted)"}function Za(t,e){let n=tl(t,gm(t)),r=Ai(t),o=r?`
77
+ ${e}`,this.harnessHandle?.setPermissionMode))try{await this.harnessHandle.setPermissionMode("plan"),this.currentPermissionMode="plan",this.applyControlEvent({type:"permission.mode_changed",currentPermissionMode:"plan"})}catch(r){`${this.id}${vr(r)}`}if(this.multiTurn&&this.messageStream)this.messageStream.push(this.harness.buildUserMessage(n,this.backendConversationId??""));else if(this.harnessHandle?.streamInput){let r=this.harness.buildUserMessage(n,this.backendConversationId??"");async function*o(){yield r}await this.harnessHandle.streamInput(o())}else throw new Error("Session does not support follow-up messages (launched in single-turn mode).")}async interrupt(){return!this.turnInProgress||!this.harnessHandle?.interrupt?!1:(await this.harnessHandle.interrupt(),!0)}async submitPendingInputOption(e,n){if(!this.pendingInputState||!this.harnessHandle?.submitPendingInputOption)return!1;let r=await this.harnessHandle.submitPendingInputOption(e,n);return r&&(this.waitingForInputFired=!1),r}canSubmitPendingInputOption(){return!!(this.pendingInputState&&this.harnessHandle?.submitPendingInputOption)}async submitPendingInputText(e){if(!this.pendingInputState||!this.harnessHandle?.submitPendingInputText)return!1;let n=await this.harnessHandle.submitPendingInputText(e);return n&&(this.waitingForInputFired=!1),n}switchPermissionMode(e){this.pendingModeSwitch=e}get isActive(){return this._status==="starting"||this._status==="running"}kill(e){this.transitionToTerminal("killed",{reason:e})}complete(e="done"){this.transitionToTerminal("completed",{reason:e})}incrementAutoRespond(){this.autoRespondCount++}resetAutoRespond(){this.autoRespondCount=0}getOutput(e){return e===void 0?this.outputBuffer.slice():this.outputBuffer.slice(-e)}resetIdleTimer(){if(!this.multiTurn)return;let e=(D.idleTimeoutMinutes??15)*60*1e3;this.setTimer("idle",e,()=>{this._status==="running"&&(this.applyControlEvent({type:"terminal.entered",suspended:!0}),this.kill("idle-timeout"))})}teardown(){this.clearAllTimers(),this.completedAt||(this.completedAt=Date.now()),this.messageStream&&this.messageStream.end(),this.harnessHandle?.interrupt&&this.harnessHandle.interrupt().catch(e=>{`${this.id}${vr(e)}`}),this.abortController.abort(),this.applyControlEvent({type:"terminal.entered",suspended:this.lifecycle==="suspended"})}transitionToTerminal(e,n={}){this.isActive&&(this.turnInProgress=!1,n.reason&&(this.killReason=n.reason),n.error!==void 0&&(this.error=n.error),this.completedAt=Date.now(),this.applyControlEvent({type:"terminal.entered",suspended:e==="killed"&&n.reason==="idle-timeout"}),this.transition(e),this.teardown())}async consumeMessages(e){for await(let n of e){if(!this.isActive)break;this.resetIdleTimer(),this.harnessEvents.applyMessage(n,{pendingPlanApproval:this.pendingPlanApproval,currentPermissionMode:this.currentPermissionMode,permissionMode:this.permissionMode,planModeApproved:this.planModeApproved,pendingInputState:this.pendingInputState})}}controlStateSnapshot(){return{status:this._status,lifecycle:this.lifecycle,approvalState:this.approvalState,approvalExecutionState:this.approvalExecutionState,worktreeState:this.worktreeState,runtimeState:this.runtimeState,deliveryState:this.deliveryState,requestedPermissionMode:this.requestedPermissionMode,currentPermissionMode:this.currentPermissionMode,pendingPlanApproval:this.pendingPlanApproval,planApprovalContext:this.planApprovalContext,planDecisionVersion:this.planDecisionVersion,actionablePlanDecisionVersion:this.actionablePlanDecisionVersion,canonicalPlanPromptVersion:this.canonicalPlanPromptVersion,approvalPromptRequiredVersion:this.approvalPromptRequiredVersion,approvalPromptVersion:this.approvalPromptVersion,approvalPromptStatus:this.approvalPromptStatus,approvalPromptTransport:this.approvalPromptTransport,approvalPromptMessageKind:this.approvalPromptMessageKind,approvalPromptLastAttemptAt:this.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:this.approvalPromptDeliveredAt,approvalPromptFailedAt:this.approvalPromptFailedAt,planModeApproved:this.planModeApproved}}applyControlEvent(e){let n=wi(this.controlStateSnapshot(),e);this.applyControlState(n)}applyControlPatch(e){let n=Ba(this.controlStateSnapshot(),e);this.applyControlState(n)}setControlField(e,n){this.applyControlPatch({[e]:n})}applyControlState(e){let n=this.lifecycle;this.lifecycle=e.lifecycle,this.approvalState=e.approvalState,this.approvalExecutionState=e.approvalExecutionState,this.worktreeState=e.worktreeState,this.runtimeState=e.runtimeState,this.deliveryState=e.deliveryState,this.pendingPlanApproval=e.pendingPlanApproval,this.planApprovalContext=e.planApprovalContext,this.planDecisionVersion=e.planDecisionVersion,this.actionablePlanDecisionVersion=e.actionablePlanDecisionVersion,this.canonicalPlanPromptVersion=e.canonicalPlanPromptVersion,this.approvalPromptRequiredVersion=e.approvalPromptRequiredVersion,this.approvalPromptVersion=e.approvalPromptVersion,this.approvalPromptStatus=e.approvalPromptStatus,this.approvalPromptTransport=e.approvalPromptTransport,this.approvalPromptMessageKind=e.approvalPromptMessageKind,this.approvalPromptLastAttemptAt=e.approvalPromptLastAttemptAt,this.approvalPromptDeliveredAt=e.approvalPromptDeliveredAt,this.approvalPromptFailedAt=e.approvalPromptFailedAt,this.planModeApproved=e.planModeApproved,n!==this.lifecycle&&this.emit("lifecycleChange",this,this.lifecycle,n)}};var fm=50,gm=1,hm=new Set(["starting","running","completed","failed","killed"]),ym=5,km=1440*60*1e3,Pr=new Set(["merged","released","dismissed","no_change"]);function Sm(t){let e=Number(t);return!Number.isFinite(e)||e<gm?fm:Math.floor(e)}function vm(t){return typeof t=="string"&&hm.has(t)}function wm(t){let e=t.split(`
78
+ `);return e.at(-1)===""&&e.pop(),e}function Ci(t){return t.backendRef?.conversationId??t.harnessSessionId}function Pm(t,e){return e&&Pr.has(e)&&(!t||!Pr.has(t))?e:t??e}function bm(t,e){return e&&Pr.has(e.state)&&(!t||!Pr.has(t.state))?e:t??e}function al(t,e,n){let r=sl(t,"utf-8"),o=wm(r);return e.full?o:o.slice(-n)}function Rm(t,e,n){if(t.status!=="starting"&&t.status!=="running")return null;let r=nt(t.id);if(!Ti(r))return null;try{return al(r,e,n)}catch{return null}}function Am(t){let e=Ae(t.duration),n=` | Cost: $${t.costUsd.toFixed(4)}`,r=t.phase?` | Phase: ${t.phase}`:"",o=t.lifecycle&&t.lifecycle!==t.phase?` | Lifecycle: ${t.lifecycle}`:"";return[`Session: ${t.name} [${t.id}] | Status: ${t.status.toUpperCase()}${r}${o}${n} | Duration: ${e}`,`${"─".repeat(60)}`].join(`
79
+ `)}function ll(t,e){let n=t.name||t.sessionId||Ci(t)||"unknown",r=t.lifecycle?` | Phase: ${t.lifecycle}`:"";return[`Session: ${n} | Status: ${t.status.toUpperCase()}${r} | Cost: $${t.costUsd.toFixed(4)}`,e,`${"─".repeat(60)}`].join(`
80
+ `)}function Im(t){return`(retrieved from ${t.outputPath} — evicted from runtime cache — showing persisted output)`}function xm(t){return t.outputPath?`(persisted session metadata recovered; output file is unavailable at ${t.outputPath})`:"(persisted session metadata recovered; no output file was recorded before the runtime was interrupted)"}function il(t,e){let n=ll(t,xm(t)),r=Ci(t),o=r?`
81
81
  Backend session: ${r}`:"";return`${n}
82
- (no persisted output available: ${e})${o}`}function hm(t){let e=[];return t.error&&e.push(`Error: ${t.error}`),t.result?.result&&e.push(`Result: ${t.result.result}`),t.result&&e.push(`Result status: ${t.result.subtype}`),e.length>0?`
82
+ (no persisted output available: ${e})${o}`}function Tm(t){let e=[];return t.error&&e.push(`Error: ${t.error}`),t.result?.result&&e.push(`Result: ${t.result.result}`),t.result&&e.push(`Result status: ${t.result.subtype}`),e.length>0?`
83
83
  (no output yet)
84
84
  ${e.join(`
85
85
  `)}`:`
86
- (no output yet)`}function Pr(t,e,n={}){let r=am(n.lines),o=t.resolve(e);if(!o){let d=t.getPersistedSession(e);if(d?.outputPath&&Ri(d.outputPath))try{let u=el(d.outputPath,n,r).join(`
87
- `),c=tl(d,fm(d));return u?`${c}
86
+ (no output yet)`}function br(t,e,n={}){let r=Sm(n.lines),o=t.resolve(e);if(!o){let d=t.getPersistedSession(e);if(d?.outputPath&&Ti(d.outputPath))try{let u=al(d.outputPath,n,r).join(`
87
+ `),c=ll(d,Im(d));return u?`${c}
88
88
  ${u}`:`${c}
89
- (output file was empty)`}catch(u){let c=u instanceof Error?u.message:String(u);return`Error: Session "${e}" was cleaned up (expired) and output file could not be read: ${c}`}return d?.outputPath?Za(d,`output file is missing at ${d.outputPath}`):d?Za(d,"no outputPath is stored for this recovered session"):`Error: Session "${e}" not found.`}let i=pm(o,n,r),s=i&&i.length>0?i:n.full?o.getOutput():o.getOutput(r),l=mm(o),a=s.length===0?`${l}${hm(o)}`:`${l}
89
+ (output file was empty)`}catch(u){let c=u instanceof Error?u.message:String(u);return`Error: Session "${e}" was cleaned up (expired) and output file could not be read: ${c}`}return d?.outputPath?il(d,`output file is missing at ${d.outputPath}`):d?il(d,"no outputPath is stored for this recovered session"):`Error: Session "${e}" not found.`}let i=Rm(o,n,r),s=i&&i.length>0?i:n.full?o.getOutput():o.getOutput(r),a=Am(o),l=s.length===0?`${a}${Tm(o)}`:`${a}
90
90
  ${s.join(`
91
- `)}`;if(o.pendingPlanApproval&&o.planFilePath)try{if(Ri(o.planFilePath)){let d=Xa(o.planFilePath,"utf-8"),u="─".repeat(60);return`${a}
91
+ `)}`;if(o.pendingPlanApproval&&o.planFilePath)try{if(Ti(o.planFilePath)){let d=sl(o.planFilePath,"utf-8"),u="─".repeat(60);return`${l}
92
92
  ${u}
93
93
  Plan file: ${o.planFilePath}
94
94
  ${u}
95
- ${d}`}}catch{}return a}function wr(t,e="all",n,r={}){let o=t.listPersistedSessions()??[],s=ym(t.list("all"),o);if(e!=="all"&&(s=s.filter(l=>l.status===e)),n&&(s=s.filter(l=>l.originChannel===n)),r.full){let l=Date.now()-sm;s=s.filter(a=>(a.startedAt??0)>=l)}else s=s.slice(0,im);return s.length===0?"No sessions found.":s.map(l=>Sa(l)).join(`
96
-
97
- `)}function ym(t,e){let n=new Map;for(let r of e){if(!lm(r.status))continue;let o=r.completedAt??Date.now(),i=r.createdAt??o,s=Ai(r),l=r.sessionId??`persisted:${s??r.harnessSessionId}`;n.set(l,{id:r.sessionId??s??r.harnessSessionId,name:r.name||r.sessionId||s||r.harnessSessionId,status:r.status,startedAt:r.createdAt??0,completedAt:r.completedAt,duration:Math.max(0,o-i),prompt:r.prompt??"",workdir:r.workdir??"(unknown)",costUsd:r.costUsd??0,multiTurn:!0,phase:r.lifecycle??r.status,lifecycle:r.lifecycle,resumable:r.resumable,harness:r.harness,model:r.model,backendRef:r.backendRef,harnessSessionId:r.harnessSessionId,requestedPermissionMode:r.requestedPermissionMode,currentPermissionMode:r.currentPermissionMode,approvalExecutionState:r.approvalExecutionState,originChannel:r.originChannel,originThreadId:r.originThreadId,worktreePath:r.worktreePath,worktreeBranch:r.worktreeBranch,worktreeStrategy:r.worktreeStrategy,worktreeState:r.worktreeState,worktreeLifecycle:r.worktreeLifecycle,worktreeMerged:r.worktreeMerged,worktreeMergedAt:r.worktreeMergedAt,worktreePrUrl:r.worktreePrUrl,recovered:!0})}for(let r of t){let o=n.get(r.id);n.set(r.id,{id:r.id,name:r.name,status:r.status,startedAt:r.startedAt,completedAt:r.completedAt,duration:r.duration,prompt:r.prompt,workdir:r.originalWorkdir??r.workdir,costUsd:r.costUsd,multiTurn:r.multiTurn,phase:r.phase,lifecycle:r.lifecycle,resumable:r.isExplicitlyResumable,harness:r.harnessName,model:r.model,backendRef:r.backendRef,harnessSessionId:r.harnessSessionId,requestedPermissionMode:r.requestedPermissionMode,currentPermissionMode:r.currentPermissionMode,approvalExecutionState:r.approvalExecutionState,originChannel:r.originChannel,originThreadId:r.originThreadId,worktreePath:r.worktreePath,worktreeBranch:r.worktreeBranch,worktreeStrategy:r.worktreeStrategy,worktreeState:um(r.worktreeState,o?.worktreeState),worktreeLifecycle:cm(r.worktreeLifecycle,o?.worktreeLifecycle),worktreeMerged:r.worktreeMerged??o?.worktreeMerged,worktreeMergedAt:r.worktreeMergedAt??o?.worktreeMergedAt,worktreePrUrl:r.worktreePrUrl??o?.worktreePrUrl,recovered:!1})}return[...n.values()].sort((r,o)=>(o.startedAt??0)-(r.startedAt??0))}function km(t){if(!t||typeof t!="object")return"all";let e=t.status;switch(e){case"running":case"completed":case"failed":case"killed":case"all":return e;default:return"all"}}function nl(t){return{name:"agent_sessions",description:"List coding agent sessions with their status and progress. By default, shows the 5 most recent sessions; set `full` to show all sessions from the last 24 hours.",parameters:g.Object({status:g.Optional(g.Union([g.Literal("all"),g.Literal("running"),g.Literal("completed"),g.Literal("failed"),g.Literal("killed")],{description:'Filter by status (default "all")'})),full:g.Optional(g.Boolean({description:"Show all sessions from the last 24h instead of just the most recent 5"}))}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};let r=km(n),o=t?.workspaceDir?Je(t.workspaceDir):void 0,i=!!(n&&typeof n=="object"&&n.full===!0);return{content:[{type:"text",text:wr(S,r,o,{full:i})}]}}}}te();N();function br(t,e,n){let r=t.resolve(e);if(!r){let o=t.getPersistedSession(e);if(!o)return`Error: Session "${e}" not found.`;if(o.status==="killed"&&o.lifecycle==="suspended"){let i=n==="completed";if(t.updatePersistedSession(e,{status:i?"completed":"killed",lifecycle:"terminal",runtimeState:"stopped",resumable:!1,killReason:i?"done":"user"}))return i?`Recovered session ${o.name} [${o.sessionId??o.harnessSessionId}] marked as completed. No live process was running.`:`Recovered session ${o.name} [${o.sessionId??o.harnessSessionId}] dismissed. No live process was running.`}return`Session ${o.name} [${o.sessionId??o.harnessSessionId}] is a persisted ${o.status} record with no live process to kill.`}return r.status==="completed"||r.status==="failed"||r.status==="killed"?`Session ${r.name} [${r.id}] is already ${r.status}. No action needed.`:n==="completed"?(r.complete(),`Session ${r.name} [${r.id}] marked as completed.`):(t.kill(r.id),`Session ${r.name} [${r.id}] has been terminated.`)}function Sm(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.session!="string"?!1:e.reason===void 0?!0:e.reason==="completed"||e.reason==="killed"}function rl(t){return{name:"agent_kill",description:"Terminate or complete a running coding agent session by name or ID. Use reason='completed' to mark a session as successfully completed instead of killed.",parameters:g.Object({session:g.String({description:"Session name or ID to terminate"}),reason:g.Optional(g.Union([g.Literal("completed"),g.Literal("killed")],{description:"Reason for closing the session. 'completed' marks it as successfully done (sends ✅ notification). 'killed' (default) terminates it."}))}),async execute(e,n){return S?Sm(n)?{content:[{type:"text",text:br(S,n.session,n.reason)}]}:{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, reason? }."}]}:{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]}}}}te();N();function vm(t){return!t||typeof t!="object"?!1:typeof t.session=="string"}function Rr(t){return{name:"agent_output",description:"Show recent output from a coding agent session (by name or ID).",parameters:g.Object({session:g.String({description:"Session name or ID to get output from"}),lines:g.Optional(g.Number({description:"Number of recent lines to show (default 50)"})),full:g.Optional(g.Boolean({description:"Show all available output"}))}),async execute(e,n){return S?vm(n)?{content:[{type:"text",text:Pr(S,n.session,{full:n.full,lines:n.lines})}]}:{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, lines?, full? }."}]}:{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]}}}}te();N();ie();Z();var Pm=10;function xi(t){return t instanceof Error?t.message:String(t)}function ot(t){return U(t)??t.harnessSessionId??"unknown-session"}function wm(t){if(!(!t.worktreeStrategy||t.worktreeStrategy==="off"))return Jn(t)??U(t)??$(t)}function ol(t){return t.status!=="running"&&!!t.pendingPlanApproval&&!!$(t)}function bm(t){let e=t.trim().toLowerCase().replace(/[.!?]+$/g,"").trim();if(e==="approve"||e==="approved")return"approve";if(e==="revise"||e==="request changes"||e==="changes requested")return"revise";if(e==="reject"||e==="rejected")return"reject"}function fn(t,e,n){let r=e==="completed"?`This session is closed by default. Launch a fresh session, or fork from prior context with agent_launch(resume_session_id='${ot(t)}', fork_session=true, prompt='<new task>').`:e==="legacy_non_resumable"?`Persisted historical backend state is intentionally non-resumable here. Launch fresh, or fork with agent_launch(resume_session_id='${ot(t)}', fork_session=true, prompt='<new task>').`:e==="missing_backend_state"?`No resumable backend state is available. Launch a fresh session, or fork from prior context with agent_launch(resume_session_id='${ot(t)}', fork_session=true, prompt='<new task>').`:`Use agent_respond(session='${ot(t)}', message='<next instruction>') to continue the running session.`,o=n?` ${n}`:"";return{text:`Resume unavailable for session ${t.name} [${ot(t)}] (${e}).${o} ${r}`,isError:!0}}async function il(t,e,n){try{let r={prompt:e.prompt,sessionIdOverride:Jn(e),workdir:e.workdir,name:e.name,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,worktreeStrategy:e.worktreeStrategy,multiTurn:!0,originChannel:e.originChannel,originThreadId:e.originThreadId,originAgentId:e.originAgentId,originSessionKey:e.originSessionKey,route:e.route,permissionMode:e.currentPermissionMode,requestedPermissionMode:e.requestedPermissionMode??e.currentPermissionMode,planApproval:e.planApproval,codexApprovalPolicy:e.codexApprovalPolicy,harness:"harnessName"in e?e.harnessName:e.harness},o=await t.spawnAndAwaitRunning(r,{notifyLaunch:!1});return t.notifySession(o,`▶️ [${o.name}] Relaunched fresh`),{text:`Session ${e.name} was relaunched fresh — it was killed during startup before the harness initialized. New session: ${o.name} [${o.id}].`}}catch(r){return{text:`Error relaunching session ${e.name} [${ot(e)}]: ${xi(r)}`,isError:!0}}}var Rm=`[SYSTEM: The user has approved your plan. Exit plan mode immediately and implement the changes with full permissions. Do not ask for further confirmation.]
98
-
99
- `;function sl(t){let e=t?.replace(/\s+/g," ").trim();if(e)return se(e,240)}function Ii(t){if(t.approvalState==="changes_requested"&&!Ar(t))return`Plan changes were already requested for session ${t.name}. Wait for the revised plan before approving.`;if(t.approvalState==="rejected")return`Plan for session ${t.name} was already rejected.`}function Ar(t){return t.pendingPlanApproval?(t.approvalState==="changes_requested"?t.actionablePlanDecisionVersion:t.actionablePlanDecisionVersion??t.planDecisionVersion)>0:!1}function Am(t){return Ii(t)?!1:Ar(t)||t.currentPermissionMode==="plan"}function Im(t,e){let n=t.updatePersistedSession;if(typeof n!="function")return;let r=e.controlStateSnapshot();n.call(t,e.id,{lifecycle:r.lifecycle,approvalState:r.approvalState,approvalExecutionState:r.approvalExecutionState,runtimeState:r.runtimeState,requestedPermissionMode:r.requestedPermissionMode,currentPermissionMode:r.currentPermissionMode,pendingPlanApproval:r.pendingPlanApproval,planApprovalContext:r.planApprovalContext,planDecisionVersion:r.planDecisionVersion,actionablePlanDecisionVersion:r.actionablePlanDecisionVersion,planModeApproved:r.planModeApproved,approvalRationale:e.approvalRationale})}function xm(t){return(t.planDecisionVersion??0)+1}function al(t,e){let n={approvalState:e,lifecycle:e==="rejected"?"terminal":"awaiting_user_input",pendingPlanApproval:!1,planApprovalContext:void 0,planDecisionVersion:xm(t),actionablePlanDecisionVersion:void 0,canonicalPlanPromptVersion:void 0,approvalPromptRequiredVersion:void 0,approvalPromptVersion:void 0,approvalPromptStatus:"not_sent",approvalPromptTransport:"none",approvalPromptMessageKind:"none",approvalPromptLastAttemptAt:void 0,approvalPromptDeliveredAt:void 0,approvalPromptFailedAt:void 0};return e==="rejected"&&(n.runtimeState="stopped"),n}function ll(t,e){let n=t;typeof n.applyControlPatch=="function"&&n.applyControlPatch(e),Object.assign(t,e)}function Ti(t,e){let n=t.resolve(e),r=n?void 0:t.getPersistedSession(e),o=n??r,i=o?.name??e;if(t.clearPlanDecisionTokens?.(e),!o)return{text:`Plan rejected for [${i}].`,isError:!1};let s=al(o,"rejected");return n?(ll(n,s),t.updatePersistedSession?.(e,s),t.kill(n.id,"user"),{text:`Plan rejected for [${n.name}]. Session stopped.`}):(t.updatePersistedSession?.(e,s),{text:`Plan rejected for [${i}]. Session remains stopped.`})}function Ci(t,e){let n=t.resolve(e),r=n?void 0:t.getPersistedSession(e),o=n??r,i=o?.name??e;if(t.clearPlanDecisionTokens?.(e),o){let s=al(o,"changes_requested");n&&ll(n,s),t.updatePersistedSession?.(e,s)}return{text:`Type your revision feedback for [${i}] and I'll forward it to the agent.`}}async function Tm(t,e,n,r={}){let o=an(e);if(!(o.kind==="resume"||ol(e)))return;let s=!!(r.approve&&Am(e)),l=s?sl(r.approvalRationale):void 0;try{if(o.kind!=="resume")return o.kind==="relaunch"?il(t,e,n):fn(e,o.reason);let a={prompt:s?Rm+n:n,sessionIdOverride:o.stableSessionId,workdir:e.workdir,name:e.name,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,resumeSessionId:o.resumeSessionId,resumeWorktreeFrom:wm(e),worktreeStrategy:e.worktreeStrategy,worktreeBaseBranch:e.worktreeBaseBranch,worktreePrTargetRepo:e.worktreePrTargetRepo,multiTurn:!0,originChannel:e.originChannel,originThreadId:e.originThreadId,originAgentId:e.originAgentId,originSessionKey:e.originSessionKey,route:e.route,permissionMode:s?"bypassPermissions":e.currentPermissionMode,requestedPermissionMode:e.requestedPermissionMode??e.currentPermissionMode,planApproval:e.planApproval,codexApprovalPolicy:e.codexApprovalPolicy,pendingPlanApproval:s?!1:e.pendingPlanApproval,planApprovalContext:e.planApprovalContext,planDecisionVersion:e.planDecisionVersion,actionablePlanDecisionVersion:s?void 0:e.actionablePlanDecisionVersion,canonicalPlanPromptVersion:e.canonicalPlanPromptVersion,approvalPromptRequiredVersion:e.approvalPromptRequiredVersion,approvalPromptVersion:e.approvalPromptVersion,approvalPromptStatus:e.approvalPromptStatus,approvalPromptTransport:e.approvalPromptTransport,approvalPromptMessageKind:e.approvalPromptMessageKind,approvalPromptLastAttemptAt:e.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:e.approvalPromptDeliveredAt,approvalPromptFailedAt:e.approvalPromptFailedAt,...s?{approvalState:"approved",approvalExecutionState:"approved_then_implemented",approvalRationale:l,planModeApproved:!0}:{},harness:"harnessName"in e?e.harnessName:e.harness},d=await t.spawnAndAwaitRunning(a,{notifyLaunch:!1});return s?(t.notifySession(d,`👍 [${d.name}] Plan approved (resumed)`,"plan-approved"),{text:`Plan approved for session ${d.name} [${d.id}]. Session resumed in bypassPermissions mode. Use agent_output to see the response.`}):(t.notifySession(d,`▶️ [${d.name}] Auto-resumed`),{text:`Auto-resumed session ${d.name} [${d.id}]. Use agent_output to see the response.`})}catch(a){return fn(e,"missing_backend_state",`Backend resume failed: ${xi(a)}`)}}async function ve(t,e){let n=t.resolve(e.session),r=n?void 0:t.getPersistedSession(e.session);if(!n&&!r)return{text:`Error: Session "${e.session}" not found.`,isError:!0};let o=n??r,i=o.status==="running"?{kind:"direct"}:an(o),s=!e.approve&&o.lifecycle==="awaiting_plan_decision"&&o.pendingPlanApproval&&e.userInitiated?bm(e.message):void 0;if(s==="approve")return ve(t,{...e,message:"Approved. Go ahead.",approve:!0});if(s==="revise")return Ci(t,n?.id??r?.sessionId??e.session);if(s==="reject")return Ti(t,n?.id??r?.sessionId??e.session);if(e.approve){let a=Ii(o);if(a)return{text:a,isError:!0}}if(i.kind==="resume"||ol(o)){let a=await Tm(t,o,e.message,{approve:e.approve,approvalRationale:e.approvalRationale});if(a)return a}else{if(i.kind==="relaunch")return il(t,o,e.message);if(i.kind==="unavailable")return fn(o,i.reason)}if(!n)return sn(r)?fn(r,"completed"):{text:`Error: Session ${r.name} [${ot(r)}] is not running (status: ${r.status}). Cannot send a message to a non-running session.`,isError:!0};if(n.status!=="running")return sn(n)?fn(n,"completed"):{text:`Error: Session ${n.name} [${n.id}] is not running (status: ${n.status}). Cannot send a message to a non-running session.`,isError:!0};let l=D.maxAutoResponds??Pm;if(e.userInitiated)n.resetAutoRespond();else if(n.autoRespondCount>=l)return{text:`⚠️ Auto-respond limit reached (${n.autoRespondCount}/${l}). Ask the user to provide the answer for session ${n.name}. Then call agent_respond with their answer and set userInitiated: true to reset the counter.`};try{if(e.approve){let f=Ii(n);if(f)return{text:f,isError:!0}}if(!e.approve&&n.pendingInputState?.allowsFreeText&&await n.submitPendingInputText?.(e.message)===!0){if(e.userInitiated){let h=se(e.message,100);t.notifySession(n,`↪️ [${n.name}] "${h}"`,"agent-respond")}e.userInitiated||n.incrementAutoRespond();let f=se(e.message,80);return{text:[`Pending input answered for session ${n.name} [${n.id}].`,` Message: "${f}"`,"Use agent_output to see the response."].join(`
100
- `)}}let d=!1;e.interrupt&&(d=await n.interrupt());let u=!!(e.approve&&Ar(n)),c=u?sl(e.approvalRationale):void 0,m="";if(e.approve&&Ar(n)?(n.switchPermissionMode("bypassPermissions"),n.approvalRationale=c):e.approve&&n.currentPermissionMode==="default"?n.switchPermissionMode("bypassPermissions"):e.approve&&n.currentPermissionMode==="bypassPermissions"?m=`
101
- ℹ️ approve=true was set but session is already in bypassPermissions mode.`:e.approve?m=`
102
- ⚠️ approve=true was set but session has no pending plan approval.`:(n.pendingPlanApproval||n.approvalState==="changes_requested")&&(m=`
103
- ℹ️ Session has a pending plan — sending as revision feedback. The agent will revise and re-submit. Set approve=true to approve instead.`),await n.sendMessage(e.message),u&&Im(t,n),u)t.notifySession(n,`👍 [${n.name}] Plan approved`,"plan-approved");else if(e.userInitiated){let f=se(e.message,100);t.notifySession(n,`↪️ [${n.name}] "${f}"`,"agent-respond")}e.userInitiated||n.incrementAutoRespond();let p=se(e.message,80);return u?{text:`Plan approved for session ${n.name} [${n.id}]. Use agent_output to see the response.`}:{text:[`Message sent to session ${n.name} [${n.id}].`,d?" (redirected active turn first)":e.interrupt?" (no active turn to interrupt)":"",` Message: "${p}"`,m,"Use agent_output to see the response."].filter(Boolean).join(`
104
- `)}}catch(a){return{text:`Error sending message to session ${n.name} [${n.id}]: ${xi(a)}`,isError:!0}}}function Cm(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.session=="string"&&typeof e.message=="string"&&(e.approval_rationale===void 0||typeof e.approval_rationale=="string")}function dl(t){return{name:"agent_respond",description:"Send a follow-up message to a running coding agent session. The session must be running. All sessions are multi-turn.",parameters:g.Object({session:g.String({description:"Session name or ID to respond to"}),message:g.String({description:"The message to send to the session"}),interrupt:g.Optional(g.Boolean({description:"If true, interrupt the current turn before sending the message. Useful to redirect the session mid-response."})),userInitiated:g.Optional(g.Boolean({description:"Set to true when the message comes from the user (not auto-generated). Resets the auto-respond counter and bypasses the auto-respond limit."})),approve:g.Optional(g.Boolean({description:"Set to true to escalate session permissions to bypassPermissions. Works in two scenarios: (1) approve a pending plan in plan mode, or (2) escalate a default-mode session to skip remaining OpenClaw approval checkpoints. No-op if already in bypassPermissions mode. In plan mode without a pending plan, this flag is ignored."})),approval_rationale:g.Optional(g.String({description:"Optional structured rationale for a direct delegated plan approval. Use this instead of embedding the rationale in message text when approve=true for a pending plan."}))}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!Cm(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, message, interrupt?, userInitiated?, approve?, approval_rationale? }."}]};let r=await ve(S,{session:n.session,message:n.message,interrupt:n.interrupt,userInitiated:n.userInitiated,approve:n.approve,approvalRationale:n.approval_rationale});return{isError:r.isError??!1,content:[{type:"text",text:r.text}]}}}}te();N();function Mm(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.session=="string"&&typeof e.summary=="string"}function ul(t){return{name:"agent_request_plan_approval",description:"Send a plan-approval decision prompt to the user for a session that is already waiting on plan approval. Reuses the plugin's Approve/Revise/Reject buttons so the user can decide directly from the message.",parameters:g.Object({session:g.String({description:"Session name or ID awaiting plan approval"}),summary:g.String({description:"Concise user-facing summary of scope, risk, and any concerns that should accompany the approval buttons"})}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!Mm(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, summary }."}]};let r=S.requestPlanApprovalFromUser(n.session,n.summary);return{isError:r.startsWith("Error:"),content:[{type:"text",text:r}]}}}}te();N();function _m(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.session=="string"&&typeof e.summary=="string"}function cl(t){return{name:"agent_request_worktree_decision",description:"Send a worktree Merge/Open PR/Later/Discard decision prompt to the user for a delegated worktree session that is awaiting human choice.",parameters:g.Object({session:g.String({description:"Delegated session name or ID awaiting a worktree decision"}),summary:g.String({description:"Concise user-facing summary of scope, risk, and why human choice is needed"})}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!_m(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, summary }."}]};let r=S.requestWorktreeDecisionFromUser(n.session,n.summary);return{isError:r.startsWith("Error:"),content:[{type:"text",text:r}]}}}}te();N();ie();var Mi=["off","manual","ask","delegate","auto-merge","auto-pr"],Ir=new Set(Mi),$m=["pr-required","pr-allowed","never-pr","manual"],pl=new Set($m),Em=["low","medium","high","xhigh","max"],ml=new Set(Em);function Dm(t){return typeof t=="string"&&Ir.has(t)}var Om=g.Union(Mi.map(t=>g.Literal(t)),{description:"Optional worktree strategy for the planning session. Use auto-pr when the follow-up should branch and open/update a PR after approved implementation."});function Wm(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.offer_id=="string"&&typeof e.offer_text=="string"&&typeof e.plan_prompt=="string"&&typeof e.plan_workdir=="string"&&(e.plan_worktree_strategy==null||Dm(e.plan_worktree_strategy))&&(e.plan_name==null||typeof e.plan_name=="string")&&(e.target_channel==null||typeof e.target_channel=="string")&&(e.target_thread_id==null||typeof e.target_thread_id=="string"||typeof e.target_thread_id=="number")&&(e.target_session_key==null||typeof e.target_session_key=="string")}function Nm(t,e){let n=pt(t,e.target_channel,e.target_session_key);if(n)return e.target_thread_id!=null&&(n.threadId=String(e.target_thread_id)),n}async function Lm(t,e){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};let n=Nm(t,e);return!n?.provider||!n.target?{content:[{type:"text",text:"Error: Could not resolve a direct delivery route for the plan offer."}]}:(S.sendPlanOffer({offerId:e.offer_id,route:n,text:e.offer_text,planName:e.plan_name??e.offer_id,planPrompt:e.plan_prompt,planWorkdir:e.plan_workdir,planWorktreeStrategy:e.plan_worktree_strategy}),{content:[{type:"text",text:`Interactive plan offer queued for ${n.provider}|${n.target}${n.threadId?`#${n.threadId}`:""}.`}]})}function fl(t){return{name:"agent_send_plan_offer",description:"Post a user-facing message to the current or explicit chat route with human-gated Start Plan and Dismiss inline buttons. Use this when an external workflow wants the user to open a plan-only code-agent session from the message.",parameters:g.Object({offer_id:g.String({description:"Stable offer identifier, for example 'plugin-readiness-v2026.5.5'."}),offer_text:g.String({description:"Final user-facing text to deliver."}),plan_prompt:g.String({description:"Prompt to seed into the plan-only session when the user clicks Start Plan."}),plan_workdir:g.String({description:"Working directory for the planning session."}),plan_worktree_strategy:g.Optional(Om),plan_name:g.Optional(g.String({description:"Optional explicit session name for the planning session."})),target_channel:g.Optional(g.String({description:"Optional explicit route like 'telegram|<chat-id>'."})),target_thread_id:g.Optional(g.Union([g.String(),g.Number()],{description:"Optional explicit topic/thread id."})),target_session_key:g.Optional(g.String({description:"Optional explicit session key for wake routing."}))}),async execute(e,n){return Wm(n)?Lm(t,n):{content:[{type:"text",text:"Error: Invalid parameters. Expected { offer_id, offer_text, plan_prompt, plan_workdir }."}]}}}}te();N();function gl(t){return{name:"agent_stats",description:"Show OpenClaw Code Agent usage metrics: session counts by status, average duration, and notable sessions.",parameters:g.Object({}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};let r=S.getMetrics(),o=S.list("running").length;return{content:[{type:"text",text:Xn(r,o)}]}}}}te();N();xt();import{execFileSync as Fm}from"child_process";var $i=[{policy:"pr-required",label:"Require PR",title:"Require PR",description:"Direct merge is disabled; follow-through must use a pull request."},{policy:"pr-allowed",label:"Merge or PR",title:"Merge or PR",description:"Use the requested strategy; direct merge and pull requests are both allowed."},{policy:"never-pr",label:"No PR",title:"No PR",description:"Do not create pull requests; keep follow-through local/direct."},{policy:"manual",label:"Manual",title:"Manual",description:"Create isolated worktrees, but require an explicit human follow-up decision every time."}],Bm=new Map($i.map(t=>[t.policy,t]));function gn(t){return t?$i:$i.filter(e=>e.policy==="never-pr"||e.policy==="manual")}function hl(t){return Bm.get(t)??{policy:t,label:t,title:t,description:"Custom repo integration policy."}}function _t(t,e){if(!(e||t!=="pr-required"&&t!=="pr-allowed"))return`Policy ${t} requires PR automation, but no supported PR provider is available. Choose never-pr or manual.`}function Ei(t){let{policy:e,prAvailable:n}=t;return{merge:e!=="pr-required"&&e!=="manual",pr:e!=="never-pr"&&e!=="manual"&&n}}function _i(t,e){try{return Fm("git",e,{cwd:t,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch{return}}function yl(t){if(!t)return;let e=t.trim().replace(/\/+$/,"").replace(/\.git$/i,""),n=e.match(/^git@([^:]+):(.+)$/);if(n)return`https://${n[1].toLowerCase()}/${n[2].toLowerCase()}`;let r=e.match(/^https?:\/\/([^/]+)\/(.+)$/i);return r?`https://${r[1].toLowerCase()}/${r[2].toLowerCase()}`:e.toLowerCase()}function qm(t){return yl(t)?.startsWith("https://github.com/")?"github":"unsupported"}function hn(t){let e=_i(t,["rev-parse","--show-toplevel"]);if(!e)return;let n=_i(e,["remote","get-url","origin"])??_i(e,["remote","get-url","upstream"]),r=yl(n),o=qm(r);return{key:r?`${e}|${r}`:e,repoRoot:e,remoteUrl:r,provider:o}}function kl(t){if(t?.remoteUrl)return t.remoteUrl==="https://github.com/goldmar/openclaw-code-agent"?"pr-required":void 0}function Di(t,e,n="stored",r=new Date().toISOString()){return{key:t.key,policy:e,repoRoot:t.repoRoot,remoteUrl:t.remoteUrl,provider:t.provider,createdAt:r,updatedAt:r,source:n}}function Oi(t){return t.provider==="github"&&Ae()}function Sl(t){let e=t.requestedStrategy,n=Ei(t);return!e||e==="off"||e==="manual"?{allowedActions:n}:t.policy?t.policy==="manual"?{strategy:e==="delegate"?"delegate":"ask",reason:"Repo policy requires manual follow-through.",allowedActions:{merge:!1,pr:!1}}:t.policy==="pr-required"?e==="auto-merge"?t.prAvailable?{strategy:"auto-pr",reason:"Repo policy requires a PR; auto-merge was downgraded to auto-pr.",allowedActions:n}:{strategy:"ask",blocked:!0,reason:"Repo policy requires a PR, but no supported PR provider is available.",allowedActions:n}:e==="auto-pr"?t.prAvailable?{strategy:"auto-pr",allowedActions:n}:{strategy:"ask",blocked:!0,reason:"Repo policy requires a PR, but no supported PR provider is available.",allowedActions:n}:{strategy:e,allowedActions:n}:t.policy==="never-pr"?e==="auto-pr"?{strategy:"ask",reason:"Repo policy forbids PR creation; auto-pr was downgraded to an explicit worktree decision.",allowedActions:n}:{strategy:e,allowedActions:n}:e==="auto-pr"&&!t.prAvailable?{strategy:"ask",reason:"No supported PR provider is available; auto-pr was downgraded to an explicit worktree decision.",allowedActions:n}:{strategy:e,allowedActions:n}:{strategy:e==="auto-merge"||e==="auto-pr"?"ask":e,blocked:!0,reason:"Repo integration policy is unknown.",allowedActions:{merge:!1,pr:!1}}}function Wi(t,e,n=t.provider==="github"){let r=gn(n);return[`Repo integration policy is not set for ${t.repoRoot}.`,"","OCA will create isolated worktrees, but it needs one repo policy before worktree follow-through can run.",`Requested worktree strategy: ${e}`,`Provider: ${t.provider}${n?"":" (PR automation unavailable)"}`,"","Choose one available policy:",...r.map(o=>`- ${o.title}: ${o.description}`),"","If buttons are unavailable, set it manually. OCA will continue the pending launch automatically when exactly one matching launch is waiting; otherwise run the intended launch again:",...r.map(o=>`- agent_repo_policy(workdir="${t.repoRoot}", policy="${o.policy}")`)].join(`
105
- `)}function Um(t){return t==="pr-required"||t==="pr-allowed"||t==="never-pr"||t==="manual"}function yn(t){return t?[`Repo policy: ${t.policy}`,`Repo: ${t.repoRoot}`,`Provider: ${t.provider}`,...t.remoteUrl?[`Remote: ${t.remoteUrl}`]:[],`Updated: ${t.updatedAt}`].join(`
106
- `):"No stored repo policy found."}function vl(t){return{name:"agent_repo_policy",description:"Inspect or set the repository integration policy that governs OCA worktree merge/PR follow-through.",parameters:g.Object({workdir:g.Optional(g.String({description:"Repository workdir. Defaults to the current workspace directory."})),policy:g.Optional(g.Union([g.Literal("pr-required"),g.Literal("pr-allowed"),g.Literal("never-pr"),g.Literal("manual")],{description:"Policy to set for this repo."})),reset:g.Optional(g.Boolean({description:"Remove the stored policy for this repo."})),list:g.Optional(g.Boolean({description:"List all stored repo policies."})),cleanup:g.Optional(g.Boolean({description:"Remove stored repo policies whose repoRoot no longer exists on disk."}))}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};let r=n&&typeof n=="object"?n:{};if(r.cleanup===!0){let l=S.cleanupRepoPolicies();return{content:[{type:"text",text:l.length===0?"No stale repo policies found.":[`Removed ${l.length} stale repo ${l.length===1?"policy":"policies"}.`,...l.map(d=>`${d.policy} | ${d.provider} | ${d.repoRoot}`)].join(`
107
- `)}]}}if(r.list===!0){let l=S.listRepoPolicies();return{content:[{type:"text",text:l.length===0?"No stored repo policies.":l.map(d=>`${d.policy} | ${d.provider} | ${d.repoRoot}${d.remoteUrl?` | ${d.remoteUrl}`:""}`).join(`
108
- `)}]}}let o=r.workdir??t?.workspaceDir;if(!o)return{content:[{type:"text",text:"Error: workdir is required when no workspace directory is available."}]};if(r.reset===!0)return{content:[{type:"text",text:S.resetRepoPolicy(o)?`Repo policy reset for ${o}.`:`No stored repo policy found for ${o}.`}]};if(r.policy!==void 0){if(!Um(r.policy))return{content:[{type:"text",text:"Error: policy must be one of pr-required, pr-allowed, never-pr, manual."}]};if(typeof S.resolveRepoPolicy=="function"){let d=S.resolveRepoPolicy(o);if(d.identity){let u=_t(r.policy,d.prAvailable);if(u)return{content:[{type:"text",text:`Error: ${u}`}]}}}let l=S.setRepoPolicy(o,r.policy);if(!l)return{content:[{type:"text",text:`Error: ${o} is not a git repository.`}]};let a;try{a=typeof S.continueLaunchAfterManualRepoPolicy=="function"?S.continueLaunchAfterManualRepoPolicy(l.repoRoot,r.policy):{kind:"none"}}catch(d){let u=d instanceof Error?d.message:String(d);return{content:[{type:"text",text:[yn(l),"",`Repo policy saved, but the deferred launch failed: ${u}`,"The pending launch context was kept so you can retry the same agent_repo_policy call or run the intended launch again."].join(`
109
- `)}]}}return a.kind==="launched"?{content:[{type:"text",text:[yn(l),"",a.text].join(`
110
- `)}]}:a.kind==="ambiguous"?{content:[{type:"text",text:[yn(l),"",`Repo policy saved, but ${a.count} pending launches match this policy. Run the intended launch again to avoid starting the wrong session.`].join(`
111
- `)}]}:{content:[{type:"text",text:yn(l)}]}}let i=S.resolveRepoPolicy(o);if(!i.identity)return{content:[{type:"text",text:`No git repository found for ${o}.`}]};let s=i.record;return s?{content:[{type:"text",text:yn(s)}]}:{content:[{type:"text",text:["Repo policy: unknown",`Repo: ${i.identity.repoRoot}`,`Provider: ${i.provider}${i.prAvailable?"":" (PR automation unavailable)"}`,...i.identity.remoteUrl?[`Remote: ${i.identity.remoteUrl}`]:[]].join(`
112
- `)}]}}}}te();ie();N();ye();kn();vn();import{existsSync as Er}from"fs";function Vm(t){return!t||typeof t!="object"?!1:typeof t.session=="string"}function Gm(t){return t.mergeResult.stashPopConflict?[`Pre-merge stash pop conflicted; run git stash show ${t.mergeResult.stashRef??"stash@{0}"} in ${t.repoDir} to review stashed changes.`]:t.mergeResult.stashed?[`Pre-existing changes on ${t.baseBranch} were auto-stashed and restored.`]:[]}function jm(t){return t.deleteBranchRequested?t.branchDeleted&&t.worktreeCleanedUp&&!t.worktreeAlreadyAbsent?{detailLine:"Branch and worktree cleaned up.",summaryFragment:" Branch and worktree cleaned up."}:t.branchDeleted&&t.worktreeAlreadyAbsent?{detailLine:"Branch deleted; worktree was already absent.",summaryFragment:" Branch deleted; worktree was already absent."}:t.branchDeleted?{detailLine:"Branch deleted; worktree cleanup failed.",summaryFragment:" Branch deleted; worktree cleanup failed."}:t.worktreeAlreadyAbsent?{detailLine:"Worktree was already absent; branch deletion failed.",summaryFragment:" Worktree was already absent; branch deletion failed."}:t.worktreeCleanedUp?{detailLine:"Worktree cleaned up; branch deletion failed.",summaryFragment:" Worktree cleaned up; branch deletion failed."}:{detailLine:"Branch deletion and worktree cleanup failed.",summaryFragment:" Branch deletion and worktree cleanup failed."}:t.worktreeCleanedUp&&!t.worktreeAlreadyAbsent?{detailLine:"Worktree cleaned up; branch deletion was not requested.",summaryFragment:" Worktree cleaned up; branch kept."}:t.worktreeAlreadyAbsent?{detailLine:"Worktree was already absent; branch deletion was not requested.",summaryFragment:" Worktree was already absent; branch kept."}:{detailLine:"Worktree cleanup failed; branch deletion was not requested.",summaryFragment:" Worktree cleanup failed; branch kept."}}function Dr(t){return{name:"agent_merge",description:"Merge a worktree branch back to the base branch. Resolves session (active or persisted), gets worktree path, and performs the merge. On conflict, spawns a conflict-resolver session using the configured default harness.",parameters:g.Object({session:g.String({description:"Session name or ID to merge"}),base_branch:g.Optional(g.String({description:"Base branch to merge into (default: main)"})),strategy:g.Optional(g.Union([g.Literal("merge"),g.Literal("squash")],{description:"Merge strategy: 'merge' (default, fast-forward if possible; merge commit if branches have diverged) or 'squash' (squashes all commits into one)"})),push:g.Optional(g.Boolean({description:"Push the base branch after successful merge (default: false)"})),delete_branch:g.Optional(g.Boolean({description:"Delete the worktree branch after successful merge (default: true)"}))}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!Vm(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, base_branch?, strategy?, push?, delete_branch? }."}]};let r=Et(S,n.session),o=r.activeSession,i=r.persistedSession;if(!o&&!i)return{content:[{type:"text",text:`Error: Session "${n.session}" not found.`}]};let{worktreePath:s,originalWorkdir:l,branchName:a}=r;if(!s||!l)return{content:[{type:"text",text:`Error: Session "${n.session}" does not have a worktree.`}]};if(!a)return{content:[{type:"text",text:`Error: Cannot determine branch name for worktree at ${s}. The worktree may have been removed and no persisted branch name is available.`}]};Er(s)||`${s}${l}`;let d=l;if(!Er(l))return{content:[{type:"text",text:`Error: originalWorkdir "${l}" does not exist.`}]};let u=n.base_branch??Ce(d),c=u,m=n.strategy??"merge",p=n.push===!0,f=n.delete_branch!==!1,h=S.resolveRepoPolicy(d);if(h?.policy==="pr-required")return{content:[{type:"text",text:`❌ Merge blocked: repo policy requires a pull request for ${h.identity?.repoRoot??d}. Use agent_pr if PR automation is available.`}]};if(i?.worktreeLifecycle?.state==="merged"||i?.worktreeMerged)return{content:[{type:"text",text:`ℹ️ Session "${n.session}" is already merged.`}]};if((Er(s)?cn(d,a,c):void 0)===0&&nt(s))return{content:[{type:"text",text:[`❌ Merge blocked: session "${n.session}" has uncommitted worktree changes but branch ${a} has no commits ahead of ${c}.`,`Worktree: ${s}`,"Resume or inspect the session, then commit real task changes or clean temporary files before retrying agent_merge."].join(`
113
- `)}]};let v={content:[{type:"text",text:"❌ Merge did not run (internal error)"}]};return await S.enqueueMerge(d,async()=>{let I=S.getPersistedSession(n.session);if(I?.worktreeLifecycle?.state==="merged"||I?.worktreeMerged){v={content:[{type:"text",text:`ℹ️ Session "${n.session}" was already merged while waiting in queue.`}]};return}let x=Oe(d,a,u),b=yr(d,a,c,m,s),A=Ct(b);if(b.success){let y=Gm({mergeResult:b,repoDir:d,baseBranch:c});if(p&&!hr(d,c)){let W=`⚠️ Merged ${a} → ${c} locally, but failed to push ${c}`;S.notifyWorktreeOutcome(r.notificationTarget,W,{detailLines:[`Branch ${a} was merged into ${c} in the local repository.`,`Pushing ${c} failed; remote state may not include the merge.`,"Cleanup was skipped so the branch/worktree remains available for follow-up.",...y,...A]}),v={content:[{type:"text",text:Me(W,b)}]};return}let w=!1,F=!1,ce=!Er(s);F=ce?!0:ue(d,s),fr(d),f&&(w=he(d,a));let E=jm({deleteBranchRequested:f,branchDeleted:w,worktreeCleanedUp:F,worktreeAlreadyAbsent:ce});if(I){let W=new Date().toISOString();for(let V of Sn({...r,persistedSession:I}))S.updatePersistedSession(V,{...$t({worktreeBaseBranch:u,worktreePrTargetRepo:I.worktreePrTargetRepo,worktreePushRemote:I.worktreePushRemote},{mergedAt:W,updatedAt:W,resolvedAt:W,resolutionSource:"agent_merge"}),worktreeDisposition:"merged"})}let T=rt({kind:"merge",branch:a,base:u,filesChanged:x?.filesChanged,insertions:x?.insertions,deletions:x?.deletions});S.notifyWorktreeOutcome(r.notificationTarget,T,{detailLines:[b.fastForward?"Merge type: fast-forward.":"Merge type: merge commit.",p?`Pushed ${c}.`:`Did not push ${c}; push was not requested.`,E.detailLine,...y,...A]});let j=`✅ ${b.fastForward?"⚡ Fast-forward":"🔀 Merge commit"}: ${a} → ${c}.${p?" Pushed.":""}${E.summaryFragment}`;b.stashPopConflict?j+=`
95
+ ${d}`}}catch{}return l}function Rr(t,e="all",n,r={}){let o=t.listPersistedSessions()??[],s=Cm(t.list("all"),o);if(e!=="all"&&(s=s.filter(a=>a.status===e)),n&&(s=s.filter(a=>a.originChannel===n)),r.full){let a=Date.now()-km;s=s.filter(l=>(l.startedAt??0)>=a)}else s=s.slice(0,ym);return s.length===0?"No sessions found.":s.map(a=>Ia(a)).join(`
96
+
97
+ `)}function Cm(t,e){let n=new Map;for(let r of e){if(!vm(r.status))continue;let o=r.completedAt??Date.now(),i=r.createdAt??o,s=Ci(r),a=r.sessionId??`persisted:${s??r.harnessSessionId}`;n.set(a,{id:r.sessionId??s??r.harnessSessionId,name:r.name||r.sessionId||s||r.harnessSessionId,status:r.status,startedAt:r.createdAt??0,completedAt:r.completedAt,duration:Math.max(0,o-i),prompt:r.prompt??"",workdir:r.workdir??"(unknown)",costUsd:r.costUsd??0,multiTurn:!0,phase:r.lifecycle??r.status,lifecycle:r.lifecycle,resumable:r.resumable,harness:r.harness,model:r.model,backendRef:r.backendRef,harnessSessionId:r.harnessSessionId,requestedPermissionMode:r.requestedPermissionMode,currentPermissionMode:r.currentPermissionMode,approvalExecutionState:r.approvalExecutionState,originChannel:r.originChannel,originThreadId:r.originThreadId,worktreePath:r.worktreePath,worktreeBranch:r.worktreeBranch,worktreeStrategy:r.worktreeStrategy,worktreeState:r.worktreeState,worktreeLifecycle:r.worktreeLifecycle,worktreeMerged:r.worktreeMerged,worktreeMergedAt:r.worktreeMergedAt,worktreePrUrl:r.worktreePrUrl,recovered:!0})}for(let r of t){let o=n.get(r.id);n.set(r.id,{id:r.id,name:r.name,status:r.status,startedAt:r.startedAt,completedAt:r.completedAt,duration:r.duration,prompt:r.prompt,workdir:r.originalWorkdir??r.workdir,costUsd:r.costUsd,multiTurn:r.multiTurn,phase:r.phase,lifecycle:r.lifecycle,resumable:r.isExplicitlyResumable,harness:r.harnessName,model:r.model,backendRef:r.backendRef,harnessSessionId:r.harnessSessionId,requestedPermissionMode:r.requestedPermissionMode,currentPermissionMode:r.currentPermissionMode,approvalExecutionState:r.approvalExecutionState,originChannel:r.originChannel,originThreadId:r.originThreadId,worktreePath:r.worktreePath,worktreeBranch:r.worktreeBranch,worktreeStrategy:r.worktreeStrategy,worktreeState:Pm(r.worktreeState,o?.worktreeState),worktreeLifecycle:bm(r.worktreeLifecycle,o?.worktreeLifecycle),worktreeMerged:r.worktreeMerged??o?.worktreeMerged,worktreeMergedAt:r.worktreeMergedAt??o?.worktreeMergedAt,worktreePrUrl:r.worktreePrUrl??o?.worktreePrUrl,recovered:!1})}return[...n.values()].sort((r,o)=>(o.startedAt??0)-(r.startedAt??0))}function Mm(t){if(!t||typeof t!="object")return"all";let e=t.status;switch(e){case"running":case"completed":case"failed":case"killed":case"all":return e;default:return"all"}}function dl(t){return{name:"agent_sessions",description:"List coding agent sessions with their status and progress. By default, shows the 5 most recent sessions; set `full` to show all sessions from the last 24 hours.",parameters:h.Object({status:h.Optional(h.Union([h.Literal("all"),h.Literal("running"),h.Literal("completed"),h.Literal("failed"),h.Literal("killed")],{description:'Filter by status (default "all")'})),full:h.Optional(h.Boolean({description:"Show all sessions from the last 24h instead of just the most recent 5"}))}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};let r=Mm(n),o=t?.workspaceDir?Ze(t.workspaceDir):void 0,i=!!(n&&typeof n=="object"&&n.full===!0);return{content:[{type:"text",text:Rr(v,r,o,{full:i})}]}}}}ne();B();function Ar(t,e,n){let r=t.resolve(e);if(!r){let o=t.getPersistedSession(e);if(!o)return`Error: Session "${e}" not found.`;if(o.status==="killed"&&o.lifecycle==="suspended"){let i=n==="completed";if(t.updatePersistedSession(e,{status:i?"completed":"killed",lifecycle:"terminal",runtimeState:"stopped",resumable:!1,killReason:i?"done":"user"}))return i?`Recovered session ${o.name} [${o.sessionId??o.harnessSessionId}] marked as completed. No live process was running.`:`Recovered session ${o.name} [${o.sessionId??o.harnessSessionId}] dismissed. No live process was running.`}return`Session ${o.name} [${o.sessionId??o.harnessSessionId}] is a persisted ${o.status} record with no live process to kill.`}return r.status==="completed"||r.status==="failed"||r.status==="killed"?`Session ${r.name} [${r.id}] is already ${r.status}. No action needed.`:n==="completed"?(r.complete(),`Session ${r.name} [${r.id}] marked as completed.`):(t.kill(r.id),`Session ${r.name} [${r.id}] has been terminated.`)}function _m(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.session!="string"?!1:e.reason===void 0?!0:e.reason==="completed"||e.reason==="killed"}function ul(t){return{name:"agent_kill",description:"Terminate or complete a running coding agent session by name or ID. Use reason='completed' to mark a session as successfully completed instead of killed.",parameters:h.Object({session:h.String({description:"Session name or ID to terminate"}),reason:h.Optional(h.Union([h.Literal("completed"),h.Literal("killed")],{description:"Reason for closing the session. 'completed' marks it as successfully done (sends ✅ notification). 'killed' (default) terminates it."}))}),async execute(e,n){return v?_m(n)?{content:[{type:"text",text:Ar(v,n.session,n.reason)}]}:{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, reason? }."}]}:{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]}}}}ne();B();function $m(t){return!t||typeof t!="object"?!1:typeof t.session=="string"}function Ir(t){return{name:"agent_output",description:"Show recent output from a coding agent session (by name or ID).",parameters:h.Object({session:h.String({description:"Session name or ID to get output from"}),lines:h.Optional(h.Number({description:"Number of recent lines to show (default 50)"})),full:h.Optional(h.Boolean({description:"Show all available output"}))}),async execute(e,n){return v?$m(n)?{content:[{type:"text",text:br(v,n.session,{full:n.full,lines:n.lines})}]}:{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, lines?, full? }."}]}:{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]}}}}ne();B();se();X();var Em=10;function _i(t){return t instanceof Error?t.message:String(t)}function st(t){return U(t)??t.harnessSessionId??"unknown-session"}function Dm(t){if(!(!t.worktreeStrategy||t.worktreeStrategy==="off"))return Zn(t)??U(t)??$(t)}function cl(t){return t.status!=="running"&&!!t.pendingPlanApproval&&!!$(t)}function Om(t){let e=t.trim().toLowerCase().replace(/[.!?]+$/g,"").trim();if(e==="approve"||e==="approved")return"approve";if(e==="revise"||e==="request changes"||e==="changes requested")return"revise";if(e==="reject"||e==="rejected")return"reject"}function gn(t,e,n){let r=e==="completed"?`This session is closed by default. Launch a fresh session, or fork from prior context with agent_launch(resume_session_id='${st(t)}', fork_session=true, prompt='<new task>').`:e==="legacy_non_resumable"?`Persisted historical backend state is intentionally non-resumable here. Launch fresh, or fork with agent_launch(resume_session_id='${st(t)}', fork_session=true, prompt='<new task>').`:e==="missing_backend_state"?`No resumable backend state is available. Launch a fresh session, or fork from prior context with agent_launch(resume_session_id='${st(t)}', fork_session=true, prompt='<new task>').`:`Use agent_respond(session='${st(t)}', message='<next instruction>') to continue the running session.`,o=n?` ${n}`:"";return{text:`Resume unavailable for session ${t.name} [${st(t)}] (${e}).${o} ${r}`,isError:!0}}async function pl(t,e,n){try{let r={prompt:e.prompt,sessionIdOverride:Zn(e),workdir:e.workdir,name:e.name,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,worktreeStrategy:e.worktreeStrategy,multiTurn:!0,originChannel:e.originChannel,originThreadId:e.originThreadId,originAgentId:e.originAgentId,originSessionKey:e.originSessionKey,route:e.route,permissionMode:e.currentPermissionMode,requestedPermissionMode:e.requestedPermissionMode??e.currentPermissionMode,planApproval:e.planApproval,codexApprovalPolicy:e.codexApprovalPolicy,harness:"harnessName"in e?e.harnessName:e.harness},o=await t.spawnAndAwaitRunning(r,{notifyLaunch:!1});return t.notifySession(o,`▶️ [${o.name}] Relaunched fresh`),{text:`Session ${e.name} was relaunched fresh — it was killed during startup before the harness initialized. New session: ${o.name} [${o.id}].`}}catch(r){return{text:`Error relaunching session ${e.name} [${st(e)}]: ${_i(r)}`,isError:!0}}}var Wm=`[SYSTEM: The user has approved your plan. Exit plan mode immediately and implement the changes with full permissions. Do not ask for further confirmation.]
98
+
99
+ `;function ml(t){let e=t?.replace(/\s+/g," ").trim();if(e)return ae(e,240)}function Mi(t){if(t.approvalState==="changes_requested"&&!xr(t))return`Plan changes were already requested for session ${t.name}. Wait for the revised plan before approving.`;if(t.approvalState==="rejected")return`Plan for session ${t.name} was already rejected.`}function xr(t){return t.pendingPlanApproval?(t.approvalState==="changes_requested"?t.actionablePlanDecisionVersion:t.actionablePlanDecisionVersion??t.planDecisionVersion)>0:!1}function Nm(t){return Mi(t)?!1:xr(t)||t.currentPermissionMode==="plan"}function Lm(t,e){let n=t.updatePersistedSession;if(typeof n!="function")return;let r=e.controlStateSnapshot();n.call(t,e.id,{lifecycle:r.lifecycle,approvalState:r.approvalState,approvalExecutionState:r.approvalExecutionState,runtimeState:r.runtimeState,requestedPermissionMode:r.requestedPermissionMode,currentPermissionMode:r.currentPermissionMode,pendingPlanApproval:r.pendingPlanApproval,planApprovalContext:r.planApprovalContext,planDecisionVersion:r.planDecisionVersion,actionablePlanDecisionVersion:r.actionablePlanDecisionVersion,planModeApproved:r.planModeApproved,approvalRationale:e.approvalRationale})}function Bm(t){return(t.planDecisionVersion??0)+1}function fl(t,e){let n={approvalState:e,lifecycle:e==="rejected"?"terminal":"awaiting_user_input",pendingPlanApproval:!1,planApprovalContext:void 0,planDecisionVersion:Bm(t),actionablePlanDecisionVersion:void 0,canonicalPlanPromptVersion:void 0,approvalPromptRequiredVersion:void 0,approvalPromptVersion:void 0,approvalPromptStatus:"not_sent",approvalPromptTransport:"none",approvalPromptMessageKind:"none",approvalPromptLastAttemptAt:void 0,approvalPromptDeliveredAt:void 0,approvalPromptFailedAt:void 0};return e==="rejected"&&(n.runtimeState="stopped"),n}function gl(t,e){let n=t;typeof n.applyControlPatch=="function"&&n.applyControlPatch(e),Object.assign(t,e)}function $i(t,e){let n=t.resolve(e),r=n?void 0:t.getPersistedSession(e),o=n??r,i=o?.name??e;if(t.clearPlanDecisionTokens?.(e),!o)return{text:`Plan rejected for [${i}].`,isError:!1};let s=fl(o,"rejected");return n?(gl(n,s),t.updatePersistedSession?.(e,s),t.kill(n.id,"user"),{text:`Plan rejected for [${n.name}]. Session stopped.`}):(t.updatePersistedSession?.(e,s),{text:`Plan rejected for [${i}]. Session remains stopped.`})}function Ei(t,e){let n=t.resolve(e),r=n?void 0:t.getPersistedSession(e),o=n??r,i=o?.name??e;if(t.clearPlanDecisionTokens?.(e),o){let s=fl(o,"changes_requested");n&&gl(n,s),t.updatePersistedSession?.(e,s)}return{text:`Type your revision feedback for [${i}] and I'll forward it to the agent.`}}async function Fm(t,e,n,r={}){let o=ln(e);if(!(o.kind==="resume"||cl(e)))return;let s=!!(r.approve&&Nm(e)),a=s?ml(r.approvalRationale):void 0;try{if(o.kind!=="resume")return o.kind==="relaunch"?pl(t,e,n):gn(e,o.reason);let l={prompt:s?Wm+n:n,sessionIdOverride:o.stableSessionId,workdir:e.workdir,name:e.name,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,resumeSessionId:o.resumeSessionId,resumeWorktreeFrom:Dm(e),worktreeStrategy:e.worktreeStrategy,worktreeBaseBranch:e.worktreeBaseBranch,worktreePrTargetRepo:e.worktreePrTargetRepo,multiTurn:!0,originChannel:e.originChannel,originThreadId:e.originThreadId,originAgentId:e.originAgentId,originSessionKey:e.originSessionKey,route:e.route,permissionMode:s?"bypassPermissions":e.currentPermissionMode,requestedPermissionMode:e.requestedPermissionMode??e.currentPermissionMode,planApproval:e.planApproval,codexApprovalPolicy:e.codexApprovalPolicy,pendingPlanApproval:s?!1:e.pendingPlanApproval,planApprovalContext:e.planApprovalContext,planDecisionVersion:e.planDecisionVersion,actionablePlanDecisionVersion:s?void 0:e.actionablePlanDecisionVersion,canonicalPlanPromptVersion:e.canonicalPlanPromptVersion,approvalPromptRequiredVersion:e.approvalPromptRequiredVersion,approvalPromptVersion:e.approvalPromptVersion,approvalPromptStatus:e.approvalPromptStatus,approvalPromptTransport:e.approvalPromptTransport,approvalPromptMessageKind:e.approvalPromptMessageKind,approvalPromptLastAttemptAt:e.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:e.approvalPromptDeliveredAt,approvalPromptFailedAt:e.approvalPromptFailedAt,...s?{approvalState:"approved",approvalExecutionState:"approved_then_implemented",approvalRationale:a,planModeApproved:!0}:{},harness:"harnessName"in e?e.harnessName:e.harness},d=await t.spawnAndAwaitRunning(l,{notifyLaunch:!1});return s?(t.notifySession(d,`👍 [${d.name}] Plan approved (resumed)`,"plan-approved"),{text:`Plan approved for session ${d.name} [${d.id}]. Session resumed in bypassPermissions mode. Use agent_output to see the response.`}):(t.notifySession(d,`▶️ [${d.name}] Auto-resumed`),{text:`Auto-resumed session ${d.name} [${d.id}]. Use agent_output to see the response.`})}catch(l){return gn(e,"missing_backend_state",`Backend resume failed: ${_i(l)}`)}}async function ve(t,e){let n=t.resolve(e.session),r=n?void 0:t.getPersistedSession(e.session);if(!n&&!r)return{text:`Error: Session "${e.session}" not found.`,isError:!0};let o=n??r,i=o.status==="running"?{kind:"direct"}:ln(o),s=!e.approve&&o.lifecycle==="awaiting_plan_decision"&&o.pendingPlanApproval&&e.userInitiated?Om(e.message):void 0;if(s==="approve")return ve(t,{...e,message:"Approved. Go ahead.",approve:!0});if(s==="revise")return Ei(t,n?.id??r?.sessionId??e.session);if(s==="reject")return $i(t,n?.id??r?.sessionId??e.session);if(e.approve){let l=Mi(o);if(l)return{text:l,isError:!0}}if(i.kind==="resume"||cl(o)){let l=await Fm(t,o,e.message,{approve:e.approve,approvalRationale:e.approvalRationale});if(l)return l}else{if(i.kind==="relaunch")return pl(t,o,e.message);if(i.kind==="unavailable")return gn(o,i.reason)}if(!n)return an(r)?gn(r,"completed"):{text:`Error: Session ${r.name} [${st(r)}] is not running (status: ${r.status}). Cannot send a message to a non-running session.`,isError:!0};if(n.status!=="running")return an(n)?gn(n,"completed"):{text:`Error: Session ${n.name} [${n.id}] is not running (status: ${n.status}). Cannot send a message to a non-running session.`,isError:!0};let a=D.maxAutoResponds??Em;if(e.userInitiated)n.resetAutoRespond();else if(n.autoRespondCount>=a)return{text:`⚠️ Auto-respond limit reached (${n.autoRespondCount}/${a}). Ask the user to provide the answer for session ${n.name}. Then call agent_respond with their answer and set userInitiated: true to reset the counter.`};try{if(e.approve){let m=Mi(n);if(m)return{text:m,isError:!0}}if(!e.approve&&n.pendingInputState?.allowsFreeText&&await n.submitPendingInputText?.(e.message)===!0){if(e.userInitiated){let f=ae(e.message,100);t.notifySession(n,`↪️ [${n.name}] "${f}"`,"agent-respond")}e.userInitiated||n.incrementAutoRespond();let m=ae(e.message,80);return{text:[`Pending input answered for session ${n.name} [${n.id}].`,` Message: "${m}"`,"Use agent_output to see the response."].join(`
100
+ `)}}let d=!1;e.interrupt&&(d=await n.interrupt());let u=!!(e.approve&&xr(n)),c=u?ml(e.approvalRationale):void 0,p="";if(e.approve&&xr(n)?(n.switchPermissionMode("bypassPermissions"),n.approvalRationale=c):e.approve&&n.currentPermissionMode==="default"?n.switchPermissionMode("bypassPermissions"):e.approve&&n.currentPermissionMode==="bypassPermissions"?p=`
101
+ ℹ️ approve=true was set but session is already in bypassPermissions mode.`:e.approve?p=`
102
+ ⚠️ approve=true was set but session has no pending plan approval.`:(n.pendingPlanApproval||n.approvalState==="changes_requested")&&(p=`
103
+ ℹ️ Session has a pending plan — sending as revision feedback. The agent will revise and re-submit. Set approve=true to approve instead.`),await n.sendMessage(e.message),u&&Lm(t,n),u)t.notifySession(n,`👍 [${n.name}] Plan approved`,"plan-approved");else if(e.userInitiated){let m=ae(e.message,100);t.notifySession(n,`↪️ [${n.name}] "${m}"`,"agent-respond")}e.userInitiated||n.incrementAutoRespond();let g=ae(e.message,80);return u?{text:`Plan approved for session ${n.name} [${n.id}]. Use agent_output to see the response.`}:{text:[`Message sent to session ${n.name} [${n.id}].`,d?" (redirected active turn first)":e.interrupt?" (no active turn to interrupt)":"",` Message: "${g}"`,p,"Use agent_output to see the response."].filter(Boolean).join(`
104
+ `)}}catch(l){return{text:`Error sending message to session ${n.name} [${n.id}]: ${_i(l)}`,isError:!0}}}function qm(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.session=="string"&&typeof e.message=="string"&&(e.approval_rationale===void 0||typeof e.approval_rationale=="string")}function hl(t){return{name:"agent_respond",description:"Send a follow-up message to a running coding agent session. The session must be running. All sessions are multi-turn.",parameters:h.Object({session:h.String({description:"Session name or ID to respond to"}),message:h.String({description:"The message to send to the session"}),interrupt:h.Optional(h.Boolean({description:"If true, interrupt the current turn before sending the message. Useful to redirect the session mid-response."})),userInitiated:h.Optional(h.Boolean({description:"Set to true when the message comes from the user (not auto-generated). Resets the auto-respond counter and bypasses the auto-respond limit."})),approve:h.Optional(h.Boolean({description:"Set to true to escalate session permissions to bypassPermissions. Works in two scenarios: (1) approve a pending plan in plan mode, or (2) escalate a default-mode session to skip remaining OpenClaw approval checkpoints. No-op if already in bypassPermissions mode. In plan mode without a pending plan, this flag is ignored."})),approval_rationale:h.Optional(h.String({description:"Optional structured rationale for a direct delegated plan approval. Use this instead of embedding the rationale in message text when approve=true for a pending plan."}))}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!qm(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, message, interrupt?, userInitiated?, approve?, approval_rationale? }."}]};let r=await ve(v,{session:n.session,message:n.message,interrupt:n.interrupt,userInitiated:n.userInitiated,approve:n.approve,approvalRationale:n.approval_rationale});return{isError:r.isError??!1,content:[{type:"text",text:r.text}]}}}}ne();B();function Km(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.session=="string"&&typeof e.summary=="string"}function yl(t){return{name:"agent_request_plan_approval",description:"Send a plan-approval decision prompt to the user for a session that is already waiting on plan approval. Reuses the plugin's Approve/Revise/Reject buttons so the user can decide directly from the message.",parameters:h.Object({session:h.String({description:"Session name or ID awaiting plan approval"}),summary:h.String({description:"Concise user-facing summary of scope, risk, and any concerns that should accompany the approval buttons"})}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!Km(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, summary }."}]};let r=v.requestPlanApprovalFromUser(n.session,n.summary);return{isError:r.startsWith("Error:"),content:[{type:"text",text:r}]}}}}ne();B();function Um(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.session=="string"&&typeof e.summary=="string"}function kl(t){return{name:"agent_request_worktree_decision",description:"Send a worktree Merge/Open PR/Later/Discard decision prompt to the user for a delegated worktree session that is awaiting human choice.",parameters:h.Object({session:h.String({description:"Delegated session name or ID awaiting a worktree decision"}),summary:h.String({description:"Concise user-facing summary of scope, risk, and why human choice is needed"})}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!Um(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, summary }."}]};let r=v.requestWorktreeDecisionFromUser(n.session,n.summary);return{isError:r.startsWith("Error:"),content:[{type:"text",text:r}]}}}}ne();B();se();var Di=["off","manual","ask","delegate","auto-merge","auto-pr"],Tr=new Set(Di),Vm=["pr-required","pr-allowed","never-pr","manual"],Sl=new Set(Vm),Gm=["low","medium","high","xhigh","max"],vl=new Set(Gm);function jm(t){return typeof t=="string"&&Tr.has(t)}var Hm=h.Union(Di.map(t=>h.Literal(t)),{description:"Optional worktree strategy for the planning session. Use auto-pr when the follow-up should branch and open/update a PR after approved implementation."});function zm(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.offer_id=="string"&&typeof e.offer_text=="string"&&typeof e.plan_prompt=="string"&&typeof e.plan_workdir=="string"&&(e.plan_worktree_strategy==null||jm(e.plan_worktree_strategy))&&(e.plan_name==null||typeof e.plan_name=="string")&&(e.target_channel==null||typeof e.target_channel=="string")&&(e.target_thread_id==null||typeof e.target_thread_id=="string"||typeof e.target_thread_id=="number")&&(e.target_session_key==null||typeof e.target_session_key=="string")}function Qm(t,e){let n=ft(t,e.target_channel,e.target_session_key);if(n)return e.target_thread_id!=null&&(n.threadId=String(e.target_thread_id)),n}async function Jm(t,e){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};let n=Qm(t,e);return!n?.provider||!n.target?{content:[{type:"text",text:"Error: Could not resolve a direct delivery route for the plan offer."}]}:(v.sendPlanOffer({offerId:e.offer_id,route:n,text:e.offer_text,planName:e.plan_name??e.offer_id,planPrompt:e.plan_prompt,planWorkdir:e.plan_workdir,planWorktreeStrategy:e.plan_worktree_strategy}),{content:[{type:"text",text:`Interactive plan offer queued for ${n.provider}|${n.target}${n.threadId?`#${n.threadId}`:""}.`}]})}function wl(t){return{name:"agent_send_plan_offer",description:"Post a user-facing message to the current or explicit chat route with human-gated Start Plan and Dismiss inline buttons. Use this when an external workflow wants the user to open a plan-only code-agent session from the message.",parameters:h.Object({offer_id:h.String({description:"Stable offer identifier, for example 'plugin-readiness-v2026.5.5'."}),offer_text:h.String({description:"Final user-facing text to deliver."}),plan_prompt:h.String({description:"Prompt to seed into the plan-only session when the user clicks Start Plan."}),plan_workdir:h.String({description:"Working directory for the planning session."}),plan_worktree_strategy:h.Optional(Hm),plan_name:h.Optional(h.String({description:"Optional explicit session name for the planning session."})),target_channel:h.Optional(h.String({description:"Optional explicit route like 'telegram|<chat-id>'."})),target_thread_id:h.Optional(h.Union([h.String(),h.Number()],{description:"Optional explicit topic/thread id."})),target_session_key:h.Optional(h.String({description:"Optional explicit session key for wake routing."}))}),async execute(e,n){return zm(n)?Jm(t,n):{content:[{type:"text",text:"Error: Invalid parameters. Expected { offer_id, offer_text, plan_prompt, plan_workdir }."}]}}}}ne();B();function Pl(t){return{name:"agent_stats",description:"Show OpenClaw Code Agent usage metrics: session counts by status, average duration, and notable sessions.",parameters:h.Object({}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};let r=v.getMetrics(),o=v.list("running").length;return{content:[{type:"text",text:tr(r,o)}]}}}}ne();B();Ct();import{execFileSync as Ym}from"child_process";var Wi=[{policy:"pr-required",label:"Require PR",title:"Require PR",description:"Direct merge is disabled; follow-through must use a pull request."},{policy:"pr-allowed",label:"Merge or PR",title:"Merge or PR",description:"Use the requested strategy; direct merge and pull requests are both allowed."},{policy:"never-pr",label:"No PR",title:"No PR",description:"Do not create pull requests; keep follow-through local/direct."},{policy:"manual",label:"Manual",title:"Manual",description:"Create isolated worktrees, but require an explicit human follow-up decision every time."}],Zm=new Map(Wi.map(t=>[t.policy,t]));function hn(t){return t?Wi:Wi.filter(e=>e.policy==="never-pr"||e.policy==="manual")}function bl(t){return Zm.get(t)??{policy:t,label:t,title:t,description:"Custom repo integration policy."}}function Et(t,e){if(!(e||t!=="pr-required"&&t!=="pr-allowed"))return`Policy ${t} requires PR automation, but no supported PR provider is available. Choose never-pr or manual.`}function Ni(t){let{policy:e,prAvailable:n}=t;return{merge:e!=="pr-required"&&e!=="manual",pr:e!=="never-pr"&&e!=="manual"&&n}}function Oi(t,e){try{return Ym("git",e,{cwd:t,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim()||void 0}catch{return}}function Rl(t){if(!t)return;let e=t.trim().replace(/\/+$/,"").replace(/\.git$/i,""),n=e.match(/^git@([^:]+):(.+)$/);if(n)return`https://${n[1].toLowerCase()}/${n[2].toLowerCase()}`;let r=e.match(/^https?:\/\/([^/]+)\/(.+)$/i);return r?`https://${r[1].toLowerCase()}/${r[2].toLowerCase()}`:e.toLowerCase()}function Xm(t){return Rl(t)?.startsWith("https://github.com/")?"github":"unsupported"}function yn(t){let e=Oi(t,["rev-parse","--show-toplevel"]);if(!e)return;let n=Oi(e,["remote","get-url","origin"])??Oi(e,["remote","get-url","upstream"]),r=Rl(n),o=Xm(r);return{key:r?`${e}|${r}`:e,repoRoot:e,remoteUrl:r,provider:o}}function Al(t){if(t?.remoteUrl)return t.remoteUrl==="https://github.com/goldmar/openclaw-code-agent"?"pr-required":void 0}function Li(t,e,n="stored",r=new Date().toISOString()){return{key:t.key,policy:e,repoRoot:t.repoRoot,remoteUrl:t.remoteUrl,provider:t.provider,createdAt:r,updatedAt:r,source:n}}function Bi(t){return t.provider==="github"&&Ie()}function Il(t){let e=t.requestedStrategy,n=Ni(t);return!e||e==="off"||e==="manual"?{allowedActions:n}:t.policy?t.policy==="manual"?{strategy:e==="delegate"?"delegate":"ask",reason:"Repo policy requires manual follow-through.",allowedActions:{merge:!1,pr:!1}}:t.policy==="pr-required"?e==="auto-merge"?t.prAvailable?{strategy:"auto-pr",reason:"Repo policy requires a PR; auto-merge was downgraded to auto-pr.",allowedActions:n}:{strategy:"ask",blocked:!0,reason:"Repo policy requires a PR, but no supported PR provider is available.",allowedActions:n}:e==="auto-pr"?t.prAvailable?{strategy:"auto-pr",allowedActions:n}:{strategy:"ask",blocked:!0,reason:"Repo policy requires a PR, but no supported PR provider is available.",allowedActions:n}:{strategy:e,allowedActions:n}:t.policy==="never-pr"?e==="auto-pr"?{strategy:"ask",reason:"Repo policy forbids PR creation; auto-pr was downgraded to an explicit worktree decision.",allowedActions:n}:{strategy:e,allowedActions:n}:e==="auto-pr"&&!t.prAvailable?{strategy:"ask",reason:"No supported PR provider is available; auto-pr was downgraded to an explicit worktree decision.",allowedActions:n}:{strategy:e,allowedActions:n}:{strategy:e==="auto-merge"||e==="auto-pr"?"ask":e,blocked:!0,reason:"Repo integration policy is unknown.",allowedActions:{merge:!1,pr:!1}}}function Fi(t,e,n=t.provider==="github"){let r=hn(n);return[`Repo integration policy is not set for ${t.repoRoot}.`,"","OCA will create isolated worktrees, but it needs one repo policy before worktree follow-through can run.",`Requested worktree strategy: ${e}`,`Provider: ${t.provider}${n?"":" (PR automation unavailable)"}`,"","Choose one available policy:",...r.map(o=>`- ${o.title}: ${o.description}`),"","If buttons are unavailable, set it manually. OCA will continue the pending launch automatically when exactly one matching launch is waiting; otherwise run the intended launch again:",...r.map(o=>`- agent_repo_policy(workdir="${t.repoRoot}", policy="${o.policy}")`)].join(`
105
+ `)}function ef(t){return t==="pr-required"||t==="pr-allowed"||t==="never-pr"||t==="manual"}function kn(t){return t?[`Repo policy: ${t.policy}`,`Repo: ${t.repoRoot}`,`Provider: ${t.provider}`,...t.remoteUrl?[`Remote: ${t.remoteUrl}`]:[],`Updated: ${t.updatedAt}`].join(`
106
+ `):"No stored repo policy found."}function xl(t){return{name:"agent_repo_policy",description:"Inspect or set the repository integration policy that governs OCA worktree merge/PR follow-through.",parameters:h.Object({workdir:h.Optional(h.String({description:"Repository workdir. Defaults to the current workspace directory."})),policy:h.Optional(h.Union([h.Literal("pr-required"),h.Literal("pr-allowed"),h.Literal("never-pr"),h.Literal("manual")],{description:"Policy to set for this repo."})),reset:h.Optional(h.Boolean({description:"Remove the stored policy for this repo."})),list:h.Optional(h.Boolean({description:"List all stored repo policies."})),cleanup:h.Optional(h.Boolean({description:"Remove stored repo policies whose repoRoot no longer exists on disk."}))}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};let r=n&&typeof n=="object"?n:{};if(r.cleanup===!0){let a=v.cleanupRepoPolicies();return{content:[{type:"text",text:a.length===0?"No stale repo policies found.":[`Removed ${a.length} stale repo ${a.length===1?"policy":"policies"}.`,...a.map(d=>`${d.policy} | ${d.provider} | ${d.repoRoot}`)].join(`
107
+ `)}]}}if(r.list===!0){let a=v.listRepoPolicies();return{content:[{type:"text",text:a.length===0?"No stored repo policies.":a.map(d=>`${d.policy} | ${d.provider} | ${d.repoRoot}${d.remoteUrl?` | ${d.remoteUrl}`:""}`).join(`
108
+ `)}]}}let o=r.workdir??t?.workspaceDir;if(!o)return{content:[{type:"text",text:"Error: workdir is required when no workspace directory is available."}]};if(r.reset===!0)return{content:[{type:"text",text:v.resetRepoPolicy(o)?`Repo policy reset for ${o}.`:`No stored repo policy found for ${o}.`}]};if(r.policy!==void 0){if(!ef(r.policy))return{content:[{type:"text",text:"Error: policy must be one of pr-required, pr-allowed, never-pr, manual."}]};if(typeof v.resolveRepoPolicy=="function"){let d=v.resolveRepoPolicy(o);if(d.identity){let u=Et(r.policy,d.prAvailable);if(u)return{content:[{type:"text",text:`Error: ${u}`}]}}}let a=v.setRepoPolicy(o,r.policy);if(!a)return{content:[{type:"text",text:`Error: ${o} is not a git repository.`}]};let l;try{l=typeof v.continueLaunchAfterManualRepoPolicy=="function"?v.continueLaunchAfterManualRepoPolicy(a.repoRoot,r.policy):{kind:"none"}}catch(d){let u=d instanceof Error?d.message:String(d);return{content:[{type:"text",text:[kn(a),"",`Repo policy saved, but the deferred launch failed: ${u}`,"The pending launch context was kept so you can retry the same agent_repo_policy call or run the intended launch again."].join(`
109
+ `)}]}}return l.kind==="launched"?{content:[{type:"text",text:[kn(a),"",l.text].join(`
110
+ `)}]}:l.kind==="ambiguous"?{content:[{type:"text",text:[kn(a),"",`Repo policy saved, but ${l.count} pending launches match this policy. Run the intended launch again to avoid starting the wrong session.`].join(`
111
+ `)}]}:{content:[{type:"text",text:kn(a)}]}}let i=v.resolveRepoPolicy(o);if(!i.identity)return{content:[{type:"text",text:`No git repository found for ${o}.`}]};let s=i.record;return s?{content:[{type:"text",text:kn(s)}]}:{content:[{type:"text",text:["Repo policy: unknown",`Repo: ${i.identity.repoRoot}`,`Provider: ${i.provider}${i.prAvailable?"":" (PR automation unavailable)"}`,...i.identity.remoteUrl?[`Remote: ${i.identity.remoteUrl}`]:[]].join(`
112
+ `)}]}}}}ne();se();B();ke();Sn();wn();import{existsSync as Or}from"fs";function nf(t){return!t||typeof t!="object"?!1:typeof t.session=="string"}function rf(t){return t.mergeResult.stashPopConflict?[`Pre-merge stash pop conflicted; run git stash show ${t.mergeResult.stashRef??"stash@{0}"} in ${t.repoDir} to review stashed changes.`]:t.mergeResult.stashed?[`Pre-existing changes on ${t.baseBranch} were auto-stashed and restored.`]:[]}function of(t){return t.deleteBranchRequested?t.branchDeleted&&t.worktreeCleanedUp&&!t.worktreeAlreadyAbsent?{detailLine:"Branch and worktree cleaned up.",summaryFragment:" Branch and worktree cleaned up."}:t.branchDeleted&&t.worktreeAlreadyAbsent?{detailLine:"Branch deleted; worktree was already absent.",summaryFragment:" Branch deleted; worktree was already absent."}:t.branchDeleted?{detailLine:"Branch deleted; worktree cleanup failed.",summaryFragment:" Branch deleted; worktree cleanup failed."}:t.worktreeAlreadyAbsent?{detailLine:"Worktree was already absent; branch deletion failed.",summaryFragment:" Worktree was already absent; branch deletion failed."}:t.worktreeCleanedUp?{detailLine:"Worktree cleaned up; branch deletion failed.",summaryFragment:" Worktree cleaned up; branch deletion failed."}:{detailLine:"Branch deletion and worktree cleanup failed.",summaryFragment:" Branch deletion and worktree cleanup failed."}:t.worktreeCleanedUp&&!t.worktreeAlreadyAbsent?{detailLine:"Worktree cleaned up; branch deletion was not requested.",summaryFragment:" Worktree cleaned up; branch kept."}:t.worktreeAlreadyAbsent?{detailLine:"Worktree was already absent; branch deletion was not requested.",summaryFragment:" Worktree was already absent; branch kept."}:{detailLine:"Worktree cleanup failed; branch deletion was not requested.",summaryFragment:" Worktree cleanup failed; branch kept."}}function Wr(t){return{name:"agent_merge",description:"Merge a worktree branch back to the base branch. Resolves session (active or persisted), gets worktree path, and performs the merge. On conflict, spawns a conflict-resolver session using the configured default harness.",parameters:h.Object({session:h.String({description:"Session name or ID to merge"}),base_branch:h.Optional(h.String({description:"Base branch to merge into (default: main)"})),strategy:h.Optional(h.Union([h.Literal("merge"),h.Literal("squash")],{description:"Merge strategy: 'merge' (default, fast-forward if possible; merge commit if branches have diverged) or 'squash' (squashes all commits into one)"})),push:h.Optional(h.Boolean({description:"Push the base branch after successful merge (default: false)"})),delete_branch:h.Optional(h.Boolean({description:"Delete the worktree branch after successful merge (default: true)"}))}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!nf(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session, base_branch?, strategy?, push?, delete_branch? }."}]};let r=Ot(v,n.session),o=r.activeSession,i=r.persistedSession;if(!o&&!i)return{content:[{type:"text",text:`Error: Session "${n.session}" not found.`}]};let{worktreePath:s,originalWorkdir:a,branchName:l}=r;if(!s||!a)return{content:[{type:"text",text:`Error: Session "${n.session}" does not have a worktree.`}]};if(!l)return{content:[{type:"text",text:`Error: Cannot determine branch name for worktree at ${s}. The worktree may have been removed and no persisted branch name is available.`}]};Or(s)||`${s}${a}`;let d=a;if(!Or(a))return{content:[{type:"text",text:`Error: originalWorkdir "${a}" does not exist.`}]};let u=n.base_branch??Me(d),c=u,p=n.strategy??"merge",g=n.push===!0,m=n.delete_branch!==!1,f=v.resolveRepoPolicy(d);if(f?.policy==="pr-required")return{content:[{type:"text",text:`❌ Merge blocked: repo policy requires a pull request for ${f.identity?.repoRoot??d}. Use agent_pr if PR automation is available.`}]};if(i?.worktreeLifecycle?.state==="merged"||i?.worktreeMerged)return{content:[{type:"text",text:`ℹ️ Session "${n.session}" is already merged.`}]};if((Or(s)?pn(d,l,c):void 0)===0&&ot(s))return{content:[{type:"text",text:[`❌ Merge blocked: session "${n.session}" has uncommitted worktree changes but branch ${l} has no commits ahead of ${c}.`,`Worktree: ${s}`,"Resume or inspect the session, then commit real task changes or clean temporary files before retrying agent_merge."].join(`
113
+ `)}]};let S={content:[{type:"text",text:"❌ Merge did not run (internal error)"}]};return await v.enqueueMerge(d,async()=>{let R=v.getPersistedSession(n.session);if(R?.worktreeLifecycle?.state==="merged"||R?.worktreeMerged){S={content:[{type:"text",text:`ℹ️ Session "${n.session}" was already merged while waiting in queue.`}]};return}let I=We(d,l,u),b=Sr(d,l,c,p,s),A=_t(b);if(b.success){let k=rf({mergeResult:b,repoDir:d,baseBranch:c});if(g&&!kr(d,c)){let N=`⚠️ Merged ${l} → ${c} locally, but failed to push ${c}`;v.notifyWorktreeOutcome(r.notificationTarget,N,{detailLines:[`Branch ${l} was merged into ${c} in the local repository.`,`Pushing ${c} failed; remote state may not include the merge.`,"Cleanup was skipped so the branch/worktree remains available for follow-up.",...k,...A]}),S={content:[{type:"text",text:_e(N,b)}]};return}let P=!1,F=!1,pe=!Or(s);F=pe?!0:ce(d,s),hr(d),m&&(P=ye(d,l));let E=of({deleteBranchRequested:m,branchDeleted:P,worktreeCleanedUp:F,worktreeAlreadyAbsent:pe});if(R){let N=new Date().toISOString();for(let V of vn({...r,persistedSession:R}))v.updatePersistedSession(V,{...Dt({worktreeBaseBranch:u,worktreePrTargetRepo:R.worktreePrTargetRepo,worktreePushRemote:R.worktreePushRemote},{mergedAt:N,updatedAt:N,resolvedAt:N,resolutionSource:"agent_merge"}),worktreeDisposition:"merged"})}let T=it({kind:"merge",branch:l,base:u,filesChanged:I?.filesChanged,insertions:I?.insertions,deletions:I?.deletions});v.notifyWorktreeOutcome(r.notificationTarget,T,{detailLines:[b.fastForward?"Merge type: fast-forward.":"Merge type: merge commit.",g?`Pushed ${c}.`:`Did not push ${c}; push was not requested.`,E.detailLine,...k,...A]});let j=`✅ ${b.fastForward?"⚡ Fast-forward":"🔀 Merge commit"}: ${l} → ${c}.${g?" Pushed.":""}${E.summaryFragment}`;b.stashPopConflict?j+=`
114
114
  ⚠️ Pre-merge stash pop conflicted — run \`git stash show ${b.stashRef??"stash@{0}"}\` in ${d} to review stashed changes.`:b.stashed&&(j+=`
115
- (Pre-existing changes on ${c} were auto-stashed and restored.)`),j=Me(j,b),v={content:[{type:"text",text:j}]}}else if(b.rebaseConflict)v={content:[{type:"text",text:Me(`⚠️ Rebase conflicts — manual resolution required:
116
-
117
- ${b.error}`,b)}]};else if(b.conflictFiles&&b.conflictFiles.length>0){let y=["Resolve merge conflicts in the following files and commit the resolution:","",...b.conflictFiles.map(w=>`- ${w}`),"",`After resolving, commit with message: "Resolve merge conflicts from ${a}"`].join(`
118
- `);try{let w=S.spawn({prompt:y,workdir:d,name:`${n.session}-conflict-resolver`,harness:ae(),permissionMode:"bypassPermissions",multiTurn:!0,route:o?.route??i?.route,originChannel:o?.originChannel??i?.originChannel,originThreadId:o?.originThreadId??i?.originThreadId,originAgentId:o?.originAgentId??i?.originAgentId,originSessionKey:o?.originSessionKey??i?.originSessionKey});v={content:[{type:"text",text:Me(`⚠️ Merge conflicts in ${b.conflictFiles.length} file(s) — spawned conflict resolver session: ${w.name}`,b)}]}}catch(w){v={content:[{type:"text",text:Me(`❌ Merge conflicts detected, but failed to spawn resolver: ${w instanceof Error?w.message:String(w)}`,b)}]}}}else{let y=b.dirtyError?`❌ Merge blocked: ${b.error}`:`❌ Merge failed: ${b.error??"unknown error"}`;v={content:[{type:"text",text:Me(y,b)}]}}}),v}}}Fr();te();N();Z();ye();vn();function ef(t){return!!t&&typeof t=="object"}function Cl(t){return{name:"agent_worktree_cleanup",description:"Manage worktree cleanup with lifecycle-aware safety rules. Use preview_safe to list what Clean all safe would remove, clean_safe to execute it, or preview_all to see both safe and retained sandboxes with kept reasons.",parameters:g.Object({workdir:g.Optional(g.String({description:"Restrict cleanup to sessions rooted in this repository"})),base_branch:g.Optional(g.String({description:"Override base branch for lifecycle resolution"})),mode:g.Optional(g.Union([g.Literal("preview_safe"),g.Literal("clean_safe"),g.Literal("preview_all")],{description:"Cleanup mode. preview_safe shows what Clean all safe would remove, clean_safe performs that cleanup, preview_all shows both safe and retained worktrees. Defaults to preview_safe when dry_run=true, otherwise clean_safe."})),skip_session_check:g.Optional(g.Boolean({description:"Deprecated. Safe cleanup never removes live sessions."})),force:g.Optional(g.Boolean({description:"Deprecated alias for skip_session_check."})),dry_run:g.Optional(g.Boolean({description:"Show what would be cleaned without deleting anything."})),session:g.Optional(g.String({description:"Session name or ID to clean or dismiss."})),dismiss_session:g.Optional(g.Boolean({description:"When true and session is provided, permanently dismiss the worktree."}))}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!ef(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { workdir?, base_branch?, mode?, dry_run?, session?, dismiss_session? }."}]};let r=n.session,o=n.mode??(n.dry_run===!0?"preview_safe":"clean_safe"),i=o!=="clean_safe",s=o==="preview_all"||o==="clean_safe";if(r&&n.dismiss_session===!0)return{content:[{type:"text",text:await S.dismissWorktree(r)}]};let l=Mr(S);if(r&&(l=l.filter(p=>_r(p,r)),l.length===0)){let p=Et(S,r);if(!p.persistedSession&&!p.activeSession)return{content:[{type:"text",text:`Error: Session "${r}" not found.`}]}}if(n.workdir&&(l=l.filter(p=>p.workdir===n.workdir)),l.length===0)return{content:[{type:"text",text:"No managed worktrees matched the requested scope."}]};let a=[],d=[],u=[],c=[];for(let p of l){let{persistedSession:f,activeSession:h,resolvedLifecycle:k}=Cr(S,p,{baseBranch:n.base_branch});if(!k.cleanupSafe){if(s){let v=k.reasons.length>0?k.reasons.map($r).join(", "):it(k.derivedState);d.push(`${p.name} [kept: ${v}]`)}continue}if(a.push(`${p.name} (${it(k.derivedState)})`),!i)try{let v=p.workdir;if(!((f??h)&&le(f??h))&&p.worktreePath&&ue(v,p.worktreePath,{destructive:!1}),p.worktreeBranch&&he(v,p.worktreeBranch),f){let x=k.derivedState==="merged"||k.derivedState==="released"?k.derivedState:k.lifecycle.state,b=new Date().toISOString(),A=x==="merged"?f.worktreeMergedAt:x==="dismissed"?f.worktreeDismissedAt:void 0;S.updatePersistedSession(p.id,{worktreePath:void 0,worktreeBranch:void 0,lifecycle:"terminal",worktreeState:"none",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeMerged:x==="merged"?!0:f.worktreeMerged,worktreeMergedAt:x==="merged"?f.worktreeMergedAt??b:f.worktreeMergedAt,worktreeLifecycle:{...f.worktreeLifecycle??k.lifecycle,state:x,updatedAt:b,resolvedAt:f.worktreeLifecycle?.resolvedAt??A??b,resolutionSource:f.worktreeLifecycle?.resolutionSource??"maintenance",baseBranch:n.base_branch??k.lifecycle.baseBranch??f.worktreeBaseBranch,targetRepo:f.worktreePrTargetRepo,pushRemote:f.worktreePushRemote,notes:k.reasons}})}u.push(`${p.name} (${it(k.derivedState)})`)}catch(v){c.push(`${p.name}: ${v instanceof Error?v.message:String(v)}`)}}let m=[o==="clean_safe"?"Clean all safe:":o==="preview_all"?"Worktree lifecycle review:":"Clean all safe preview:"];return m.push(` SAFE ${i?"NOW":"FOUND"} (${a.length}): ${a.join(", ")||"(none)"}`),s&&m.push(` KEPT (${d.length}): ${d.join(", ")||"(none)"}`),i||(m.push(` CLEANED (${u.length}): ${u.join(", ")||"(none)"}`),m.push(` FAILURES (${c.length}): ${c.join(", ")||"(none)"}`)),{content:[{type:"text",text:m.join(`
119
- `)}]}}}}te();N();vn();function tf(t){if(t==null)return!0;if(Array.isArray(t)||typeof t!="object")return!1;let e=t.session;return e===void 0||typeof e=="string"}function Ml(t){return{name:"agent_worktree_status",description:"Show lifecycle-first worktree status for coding agent sessions. Displays product-facing lifecycle state, released handling, cleanup safety, and retained reasons.",parameters:g.Object({session:g.Optional(g.String({description:"Session name or ID to show status for (optional, shows all if omitted)"}))}),async execute(e,n){if(!S)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!tf(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session? }."}]};let r=n&&typeof n=="object"?n.session:void 0,o=Mr(S);if(r&&(o=o.filter(s=>_r(s,r)),o.length===0))return{content:[{type:"text",text:`Error: Session "${r}" not found or has no worktree.`}]};if(o.length===0)return{content:[{type:"text",text:"No sessions with worktrees found."}]};let i=[];for(let s of o){let{persistedSession:l,resolvedLifecycle:a}=Cr(S,s),d=a.cleanupSafe?"safe now":a.preserve?"preserve":"blocked";i.push(`Session: ${s.name} [${s.id}]`),i.push(` Branch: ${s.worktreeBranch??"(unknown)"} → ${a.lifecycle.baseBranch??l?.worktreeBaseBranch??"main"}`),i.push(` Repo: ${s.workdir}`),i.push(` Lifecycle:${it(a.lifecycle.state)}`),a.derivedState!==a.lifecycle.state&&i.push(` Derived: ${it(a.derivedState)}`),i.push(` Cleanup: ${d}`),a.evidence.prUrl&&i.push(` PR: ${a.evidence.prUrl} (${a.evidence.prState??"unknown"})`),(a.evidence.branchAheadCount!=null||a.evidence.baseAheadCount!=null)&&i.push(` Ahead: ${a.evidence.branchAheadCount??0} ahead / ${a.evidence.baseAheadCount??0} behind`),i.push(` Reasons: ${a.reasons.length>0?a.reasons.map($r).join(", "):"none"}`),i.push("")}return{content:[{type:"text",text:i.join(`
120
- `).trim()}]}}}}te();N();ie();Kn();import{existsSync as nf}from"fs";function rf(t=[]){return t.map((e,n)=>({label:`check-${n+1}`,command:e.trim()})).filter(e=>e.command.length>0)}function Br(t,e){let n=t.goal.trim();if(!n)return{kind:"error",text:"Error: goal must not be empty."};let r=t.workdir||e.workspaceDir||D.defaultWorkdir||process.cwd();if(!nf(r))return{kind:"error",text:`Error: Working directory does not exist: ${r}`};let o=rf(t.verifierCommands),i=t.goalMode??(o.length>0?"verifier":"ralph");if(i==="verifier"&&o.length===0)return{kind:"error",text:"Error: verifier mode requires at least one non-empty verifier command."};let s=t.harness??ae(),l=t.model??ut(s),a=De(s,l),d=_n(s);if(!a&&(s!=="opencode"||d&&d.length>0))return{kind:"error",text:`Error: No default model configured for harness "${s}". Set plugins.entries["openclaw-code-agent"].config.harnesses.${s}.defaultModel or pass model explicitly.`};if(a&&!kt(s,a))return{kind:"error",text:`Error: Model "${l}" is not supported for harness "${s}". Use a bare Codex model id such as "gpt-5.5".`};if(a&&!qn(s,a,d))return{kind:"error",text:`Error: Model "${l}" is not allowed. Permitted models: ${d?.join(", ")}`};let u=Un(s,a,d),c=e.sessionKey||void 0,m=$n(e),p=Zt(e,m||Je(r)),f=pt(e,p,c);return{kind:"resolved",goal:n,name:t.name,workdir:r,model:u,reasoningEffort:Be(s),fastMode:ct(s),systemPrompt:t.systemPrompt,allowedTools:t.allowedTools,maxIterations:t.maxIterations,permissionMode:t.permissionMode??"bypassPermissions",harness:s,loopMode:i,completionPromise:t.completionPromise,originChannel:p,originThreadId:f?.threadId,originAgentId:e.agentId||void 0,originSessionKey:c,route:f,verifierCommands:o}}function qr(t,e){return["Goal task launched.",` Name: ${t.name}`,` ID: ${t.id}`,` Dir: ${t.workdir}`,` Session: ${t.sessionName} [${t.sessionId}]`,` Harness: ${e.harness}`,` Model: ${e.model??"default"}`,...e.fastMode?[" Fast mode: enabled"]:[],` Loop mode: ${t.loopMode}`,` Max controller iterations: ${t.maxIterations}`,` Goal: "${e.goal.length>100?`${e.goal.slice(0,100)}...`:e.goal}"`,...t.loopMode==="ralph"?[` Completion promise: ${t.completionPromise}`]:[" Verifiers:",...e.verifierCommands.map(r=>` - ${r.command}`)],"","Controller iteration progress advances only when the goal controller starts another agent turn; internal agent review passes are reported in the completion summary.","","Use goal_status to follow progress or goal_stop to terminate the task."].join(`
121
- `)}function of(t){return!t||typeof t!="object"?!1:typeof t.goal=="string"}function _l(t){return{name:"goal_launch",description:"Launch an explicit goal loop. Use this only when the user specifically asks for a goal task, Ralph-style autonomous loop, iterative loop, autonomous repair loop, or keep-going-until-checks-pass workflow. This is not the default session path.",parameters:g.Object({goal:g.String({description:"End goal for the autonomous task"}),verifier_commands:g.Optional(g.Array(g.String({description:"Shell command that must pass for the goal to be considered complete"}),{minItems:1,description:"Verifier commands run after each coding turn"})),name:g.Optional(g.String({description:"Short task name (kebab-case preferred)"})),workdir:g.Optional(g.String({description:"Working directory (defaults to cwd / configured workspace)"})),model:g.Optional(g.String({description:"Model name to use"})),system_prompt:g.Optional(g.String({description:"Additional system prompt"})),allowed_tools:g.Optional(g.Array(g.String(),{description:"Allowed tools for the underlying agent session"})),max_iterations:g.Optional(g.Number({description:"Maximum verifier-driven repair iterations",minimum:1})),goal_mode:g.Optional(g.Union([g.Literal("ralph"),g.Literal("verifier")],{description:"Loop strategy. 'ralph' repeats until a completion promise appears. 'verifier' repeats until verifier commands pass. Defaults to 'ralph' when no verifiers are provided, otherwise 'verifier'."})),completion_promise:g.Optional(g.String({description:"Exact completion promise for Ralph-mode loops. Defaults to 'DONE'."})),permission_mode:g.Optional(g.Union([g.Literal("default"),g.Literal("plan"),g.Literal("bypassPermissions")],{description:"Permission mode for the underlying agent session. Defaults to bypassPermissions for autonomous goal loops."})),harness:g.Optional(g.String({description:"Agent harness to use ('claude-code', 'codex', or experimental 'opencode')."}))}),async execute(e,n){if(!z)return{content:[{type:"text",text:"Error: GoalController not initialized. The code-agent service must be running."}]};if(!of(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected at least { goal }."}]};let r=Br({goal:n.goal,verifierCommands:n.verifier_commands,name:n.name,workdir:n.workdir,model:n.model,systemPrompt:n.system_prompt,allowedTools:n.allowed_tools,maxIterations:n.max_iterations,permissionMode:n.permission_mode,harness:n.harness,goalMode:n.goal_mode,completionPromise:n.completion_promise},t);if(r.kind!=="resolved")return{content:[{type:"text",text:r.text}]};try{let o=await z.launchTask({goal:r.goal,name:r.name,workdir:r.workdir,model:r.model,reasoningEffort:r.reasoningEffort,fastMode:r.fastMode,systemPrompt:r.systemPrompt,allowedTools:r.allowedTools,maxIterations:r.maxIterations,permissionMode:r.permissionMode,loopMode:r.loopMode,completionPromise:r.completionPromise,originChannel:r.originChannel,originThreadId:r.originThreadId,originAgentId:r.originAgentId,originSessionKey:r.originSessionKey,route:r.route,harness:r.harness,verifierCommands:r.verifierCommands});return{content:[{type:"text",text:qr(o,r)}]}}catch(o){return{content:[{type:"text",text:`Error launching goal task: ${o instanceof Error?o.message:String(o)}`}]}}}}}te();function Ui(t,e){return t.split(`
122
- `).map(n=>`${e}${n}`)}function $l(t,e){return t.length<=e?t:`${t.slice(0,e-3).trimEnd()}...`}function sf(t,e=8,n=600){let r=t.map(i=>i.trimEnd()).filter(i=>i.trim().length>0);if(r.length===0)return;let o=r.slice(-e).join(`
123
- `);return o.length<=n?o:`...${o.slice(-(n-3))}`}function af(t,e){let n=e?.trim(),r=(t??"").split(/\r?\n/).map(o=>o.trim().replace(/^[-*]\s+/,"")).filter(o=>o.length>0).filter(o=>!(n&&o===n)).filter(o=>!/^<promise>.*<\/promise>$/.test(o));return r.length===0?[]:r.slice(-3).map(o=>$l(o,180))}function lf(t){let e=(t??"").split(/\r?\n/).map(n=>n.trim()).filter(n=>n.length>0);return e.length===0?[]:e.slice(0,2).map(n=>$l(n,180))}function Ur(t){let e=[],n=lf(t.verifierSummary),r=af(t.output,t.completionPromise);if(n.length===0&&r.length===0)return;t.completionDetected===!0&&e.push("Completion was claimed, but the loop is continuing after verification.");for(let i of n)e.push(`Verifier: ${i}`);let o=Math.max(0,3-e.length);if(o>0)for(let i of r.slice(-o))e.push(`Agent: ${i}`);return["Iteration summary:",...e.map(i=>`- ${i}`)].join(`
124
- `)}function Ki(t){if(t)return{phase:t.phase,awaitingInput:t.isAwaitingInput??!!t.pendingInputState,latestOutput:sf(t.getOutput(20))}}function Vi(t,e,n){let r=t.loopMode??"verifier",o=[`${t.name} [${t.id}]`,` Status: ${t.status}`,...r==="ralph"?[" Loop mode: ralph",` Iteration: ${t.iteration}/${t.maxIterations}`]:[` Repair iteration: ${t.iteration}/${t.maxIterations}`],` Workdir: ${t.workdir}`];return r==="ralph"&&t.completionPromise&&o.push(` Completion promise: ${t.completionPromise}`),t.sessionId&&o.push(` Session: ${t.sessionName??"(unknown)"} [${t.sessionId}]`),e?.phase&&o.push(` Phase: ${e.phase}`),e?.awaitingInput!==void 0&&o.push(` Awaiting input: ${e.awaitingInput?"yes":"no"}`),n&&o.push(...Ui(n," ")),t.lastVerifierSummary&&(o.push(" Last verifier:"),o.push(...Ui(t.lastVerifierSummary," "))),e?.latestOutput&&(o.push(" Latest activity:"),o.push(...Ui(e.latestOutput," "))),t.waitingForUserReason&&o.push(` Waiting on user: ${t.waitingForUserReason}`),t.failureReason&&o.push(` Failure: ${t.failureReason}`),o.join(`
125
- `)}var Pe="Error: GoalController not initialized. The code-agent service must be running.";function Kr(t,e,n){let r=n?.trim();if(r){let i=t.getTask(r);if(!i)return`Error: Goal task "${r}" not found.`;let s=i.sessionId?e(i.sessionId):void 0;return Vi(i,Ki(s))}let o=t.listTasks();return o.length===0?"No goal tasks found.":o.map(i=>{let s=i.sessionId?e(i.sessionId):void 0;return Vi(i,Ki(s))}).join(`
126
-
127
- `)}function Vr(t,e){return t?t.action==="already_terminal"?`Task is already ${t.task.status}.`:`Task "${t.task.name}" (${t.task.id}) stopped.`:`Error: Goal task "${e}" not found.`}function Gr(t,e){switch(t.action){case"updated":return`Task "${t.task.name}" (${t.task.id}) goal updated.`;case"not_found":return`Error: Goal task "${e}" not found.`;case"invalid_goal":return"Error: replacement goal must not be empty.";case"not_editable":return t.task.status!=="waiting_for_user"?`Task is already ${t.task.status}.`:`Error: Goal task "${t.task.name}" is ${t.task.status} and cannot be edited.`}}N();function El(t){return{name:"goal_status",description:"Show status for explicit goal tasks managed by the goal controller. Use this to inspect one goal task or list all goal tasks.",parameters:g.Object({task:g.Optional(g.String({description:"Task name or ID. Omit to list all tasks."}))}),async execute(e,n){if(!z)return{content:[{type:"text",text:Pe}]};let r=n&&typeof n=="object"&&typeof n.task=="string"?n.task:void 0;return{content:[{type:"text",text:Kr(z,o=>S?.resolve(o),r)}]}}}}te();N();function df(t){return!!t&&typeof t=="object"&&typeof t.task=="string"}function Dl(t){return{name:"goal_stop",description:"Stop an explicit goal task and kill its underlying agent session.",parameters:g.Object({task:g.String({description:"Goal task name or ID"})}),async execute(e,n){if(!z)return{content:[{type:"text",text:Pe}]};if(!df(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { task }."}]};let r=z.stopTask(n.task);return{content:[{type:"text",text:Vr(r,n.task)}]}}}}te();N();function uf(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.task=="string"&&typeof e.goal=="string"}function Ol(t){return{name:"goal_edit",description:"Edit the goal text for an active goal task without stopping or relaunching its session.",parameters:g.Object({task:g.String({description:"Goal task name or ID"}),goal:g.String({description:"Replacement goal text"})}),async execute(e,n){if(!z)return{content:[{type:"text",text:Pe}]};if(!uf(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { task, goal }."}]};let r=z.editTask(n.task,n.goal);return{content:[{type:"text",text:Gr(r,n.task)}]}}}}N();Fr();import{createHash as cf}from"crypto";var ke="code-agent";var pf=new Set(["1","true","yes","on"]);function ji(){let t=process.env.OPENCLAW_CODE_AGENT_BUTTON_DIAGNOSTICS?.trim().toLowerCase();return!!(t&&pf.has(t))}function Ot(t){if(!(typeof t!="string"||t.length===0))return cf("sha256").update(t).digest("hex").slice(0,12)}function Wl(t){return typeof t.callbackData=="string"?t.callbackData:typeof t.value=="string"?t.value:void 0}function J(t){let e=(t??[]).filter(r=>Array.isArray(r)&&r.length>0),n=e.flat();return{buttonRows:e.length||void 0,buttonCount:n.length||void 0,buttonLabels:n.length>0?n.map(r=>typeof r.label=="string"?r.label:void 0):void 0,callbackByteLengths:n.length>0?n.map(r=>{let o=Wl(r);return o?Buffer.byteLength(o,"utf8"):void 0}):void 0,callbackHashes:n.length>0?n.map(r=>Ot(Wl(r))):void 0,buttonStyles:n.length>0?n.map(r=>typeof r.style=="string"?r.style:void 0):void 0}}function Ge(t){return t&&typeof t=="object"&&!Array.isArray(t)?t:void 0}function Ll(t){let e=Ge(t),n=Array.isArray(e?.blocks)?e.blocks:void 0;if(n)return n.map(r=>Ge(r)?.type).filter(r=>typeof r=="string"&&r.length>0)}function Fl(t){let e=Ge(t),n=Array.isArray(e?.blocks)?e.blocks:void 0;if(!n)return;let r=n.map(o=>{let i=Ge(o);return i?.type!=="buttons"||!Array.isArray(i.buttons)?[]:i.buttons}).filter(o=>o.length>0);return r.length>0?r:void 0}function Hi(t){let e=Fl(t);return{presentationBlockTypes:Ll(t),...J(e)}}function zi(t){let e=Ge(t),n=e?.interactive,r=Ge(e?.channelData),o=Ge(r?.telegram),i=Array.isArray(o?.buttons)?o.buttons:void 0;return{renderedPayloadKeys:e?Object.keys(e).sort():void 0,interactiveBlockTypes:Ll(n),...Nl("interactive",J(Fl(n))),...Nl("telegramChannelData",J(i)),hasPresentation:!!e?.presentation,hasInteractive:!!n,hasTelegramChannelDataButtons:!!i?.some(s=>s.length>0)}}function Bl(t){let e=Ge(t);return e?{sendResultKeys:Object.keys(e).sort(),messageId:Gi(e.messageId),chatId:Gi(e.chatId),telegramThreadId:Gi(e.messageThreadId??e.threadId),channel:typeof e.channel=="string"?e.channel:void 0}:{sendResultType:typeof t}}function Gi(t){return typeof t=="string"||typeof t=="number"?t:void 0}function Nl(t,e){let n={};for(let[r,o]of Object.entries(e))o!==void 0&&(n[`${t}${r.charAt(0).toUpperCase()}${r.slice(1)}`]=o);return n}function L(t,e){if(!ji())return;let n=Object.fromEntries(Object.entries(e).filter(([,r])=>r!==void 0));`${JSON.stringify({event:t,callbackNamespace:ke,...n})}`}function mf(t){let e=t.trim().replace(new RegExp(`^${ke}:`),"");return e||null}async function jr(t,e=!1){if(t.channel==="telegram")try{return(await X(t,{alreadyAcknowledged:e,forceTelegramMarkupEdit:!0})).textDelivered}catch(r){let o=r instanceof Error?r.message:String(r);return`${o}`,!1}let n=t.respond;if(typeof n.clearComponents=="function")try{return await n.clearComponents(),!1}catch(r){if(Wt(r))return!1;let o=r instanceof Error?r.message:String(r);`${o}`}if(typeof n.clearButtons=="function")try{await n.clearButtons()}catch(r){let o=r instanceof Error?r.message:String(r);`${o}`}else!e&&typeof n.acknowledge=="function"&&await n.acknowledge();return!1}function Hr(t){if(t&&typeof t=="object"&&"content"in t&&Array.isArray(t.content)){let e=t.content[0];return typeof e?.text=="string"?e.text:"(done)"}return"(done)"}function ql(t){if(t&&typeof t=="object"&&"meta"in t){let e=t.meta;if(typeof e?.success=="boolean")return e.success}return Qi(Hr(t))}function Qi(t){return!/^\s*(?:Error\b:?|❌|⚠️)/.test(t)}function ff(t){return t==="plan-approve"||t==="plan-request-changes"||t==="plan-reject"}function gf(...t){let e;for(let n of t)n!=null&&(e=e==null?n:Math.max(e,n));return e}function hf(t){if(t.actionablePlanDecisionVersion!=null)return t.actionablePlanDecisionVersion;let e=gf(t.approvalPromptRequiredVersion,t.approvalPromptVersion);return e??t.canonicalPlanPromptVersion??t.planDecisionVersion}function yf(t,e){if(!ff(t.kind))return;if(!e)return"This plan decision is stale because the session is no longer available.";let n=hf(e);if(t.planDecisionVersion!=null&&n!=null&&t.planDecisionVersion!==n)return"This plan decision is stale because a newer plan review state already exists.";if(!e.pendingPlanApproval)return"This plan is no longer awaiting approval.";if(t.kind==="plan-approve"&&e.approvalState==="changes_requested"&&!e.pendingPlanApproval)return"Changes were already requested for this plan. Wait for the revised plan before approving.";if(t.kind==="plan-request-changes"&&e.approvalState==="changes_requested")return"Changes were already requested for this plan. Send your feedback to the agent instead."}function kf(t){let e="callback"in t?t.callback?.payload??t.callback?.data:void 0,n="interaction"in t?t.interaction?.payload:void 0;return e??n??""}function Wt(t){let e=t instanceof Error?t.message:String(t);return/message is not modified/i.test(e)}function Sf(t){let e=t instanceof Error?t.message:String(t);return/empty message/i.test(e)}async function X(t,e={}){let n=t.respond,{alreadyAcknowledged:r=!1,forceTelegramMarkupEdit:o=!1,text:i}=e;if(t.channel==="telegram"){if(typeof i=="string"&&typeof n.editMessage=="function")try{return await n.editMessage({text:i,buttons:[]}),typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!0}}catch(l){if(Wt(l))return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!0};let a=l instanceof Error?l.message:String(l);`${a}`}if(o&&typeof n.editButtons=="function")try{return await n.editButtons({buttons:[]}),typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}catch(l){if(Wt(l))return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1};let a=l instanceof Error?l.message:String(l);`${a}`}let s="callback"in t&&typeof t.callback?.messageText=="string"?t.callback.messageText:void 0;if(o&&typeof s=="string"&&typeof n.editMessage=="function")try{return await n.editMessage({text:s,buttons:[]}),typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}catch(l){if(Wt(l))return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1};let a=l instanceof Error?l.message:String(l);`${a}`}return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}if(typeof n.clearComponents=="function")try{return await n.clearComponents(typeof i=="string"?{text:i}:void 0),{textDelivered:typeof i=="string"}}catch(s){if(Wt(s))return{textDelivered:typeof i=="string"};if(Sf(s)){if(typeof i!="string"&&r)return{textDelivered:!1};if(typeof i!="string"&&typeof n.acknowledge=="function")return await n.acknowledge(),{textDelivered:!1};typeof i!="string"&&n.acknowledge}else{if(typeof i!="string")throw s;{let l=s instanceof Error?s.message:String(s);`${l}`}}}if(typeof i=="string"&&typeof n.editMessage=="function"){try{await n.editMessage({text:i})}catch(s){if(Wt(s))return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!0};let l=s instanceof Error?s.message:String(s);return`${l}`,typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!0}}return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}async function vf(t){let e=t.respond;if(typeof e.acknowledge!="function")return!1;try{return await e.acknowledge(),!0}catch(n){let r=n instanceof Error?n.message:String(n);return`${r}`,!1}}async function K(t,e){if(t.channel==="telegram"){await t.respond.reply({text:e});return}await t.respond.reply({text:e,ephemeral:!0})}function Ul(t="telegram",e={}){let n=e.makeAgentMergeTool??Dr,r=e.makeAgentPrTool??bn;return L("callback_handler_registered",{channel:t,namespace:ke}),{channel:t,namespace:ke,handler:async o=>{let i=await vf(o);if(!o.auth.isAuthorizedSender)return await K(o,"⛔ Unauthorized."),{handled:!0};let s=kf(o),l=mf(s);if(L("callback_received",{channel:o.channel,namespace:ke,payloadByteLength:Buffer.byteLength(s,"utf8"),tokenHash:Ot(l),isAuthorizedSender:o.auth.isAuthorizedSender}),!l)return await K(o,"⚠️ Unrecognized callback payload."),{handled:!0};if(!S)return await K(o,"⚠️ Code agent service not running."),{handled:!0};let a=S.getActionToken(l);if(L("callback_token_lookup_completed",{channel:o.channel,namespace:ke,tokenHash:Ot(l),tokenFound:!!a,actionKind:a?.kind,sessionId:a?.sessionId,planDecisionVersion:a?.planDecisionVersion}),!a)return await X(o,{alreadyAcknowledged:i}),o.channel!=="telegram"&&await K(o,"⚠️ This action is stale or has already been used."),{handled:!0};let d=a.sessionId,u=S.resolve?.(d)??S.getPersistedSession?.(d),c=u?.name??d,m=yf(a,u);if(L("callback_plan_validation_completed",{channel:o.channel,namespace:ke,tokenHash:Ot(l),actionKind:a.kind,sessionId:d,sessionName:c,planDecisionVersion:a.planDecisionVersion,valid:!m}),m)return await X(o,{alreadyAcknowledged:i}),await K(o,`⚠️ ${m}`),{handled:!0};let p=S.consumeActionToken(l);if(L("callback_token_consume_completed",{channel:o.channel,namespace:ke,tokenHash:Ot(l),consumed:!!p,actionKind:p?.kind,sessionId:p?.sessionId,planDecisionVersion:p?.planDecisionVersion}),!p)return await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:a.kind==="plan-offer-start"||a.kind==="plan-offer-dismiss"}),o.channel!=="telegram"&&await K(o,"⚠️ This action is stale or has already been used."),{handled:!0};switch(p.kind){case"worktree-merge":{let f=await n().execute("callback",{session:d}),h=Hr(f);if(ql(f)){await jr(o,i);break}await K(o,h);break}case"worktree-decide-later":{let f=S.snoozeWorktreeDecision(d,{notifyUser:!1});if(Qi(f)){let k=`⏭️ Snoozed 24h for [${c}]`;await jr(o,i),await K(o,k)}else await K(o,f);break}case"worktree-dismiss":{let f=await S.dismissWorktree(d),h=Qi(f);h&&await jr(o,i),await K(o,h?"✅ Discarded":f);break}case"worktree-create-pr":case"worktree-update-pr":{let f=await r().execute("callback",{session:d}),h=Hr(f);if(ql(f)){await jr(o,i);break}await K(o,h);break}case"worktree-view-pr":{await X(o,{alreadyAcknowledged:i});let f=S.getPersistedSession?.(d),h=a.targetUrl??f?.worktreePrUrl;await K(o,h?`PR: ${h}`:"⚠️ PR URL is no longer available.");break}case"plan-approve":{await X(o,{alreadyAcknowledged:i}),S.clearPlanDecisionTokens(d);let f=await ve(S,{session:d,message:"Approved. Go ahead.",approve:!0,userInitiated:!0});f.isError&&await K(o,`⚠️ ${f.text}`);break}case"plan-reject":{await X(o,{alreadyAcknowledged:i});let f=Ti(S,d);await K(o,`❌ ${f.text}`);break}case"plan-request-changes":{await X(o,{alreadyAcknowledged:i});let f=Ci(S,d);await K(o,`✏️ ${f.text}`);break}case"plan-offer-start":{if(!p.launchPrompt||!p.launchWorkdir){await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,"⚠️ This action is missing the plan launch context.");break}let f;try{f=S.launchPlanOffer({route:p.route,prompt:p.launchPrompt,workdir:p.launchWorkdir,name:p.launchName,worktreeStrategy:p.launchWorktreeStrategy})}catch(h){let k=h instanceof Error?h.message:String(h);await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,`⚠️ Failed to start planning session: ${k}`);break}await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,`▶️ Planning session started: ${f.name} [${f.id}]`);break}case"plan-offer-dismiss":{await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,"✅ Dismissed.");break}case"repo-policy-set":{if(!p.repoPolicy||!p.repoPolicyWorkdir){await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,"⚠️ This action is missing the repo policy context.");break}if(!p.launchPrompt||!p.launchWorkdir){await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,"⚠️ This action is missing the launch context.");break}if(typeof S.resolveRepoPolicy=="function"){let k=S.resolveRepoPolicy(p.repoPolicyWorkdir);if(k.identity){let v=_t(p.repoPolicy,k.prAvailable);if(v){await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,`⚠️ ${v}`);break}}}let f=S.setRepoPolicy(p.repoPolicyWorkdir,p.repoPolicy);if(!f){await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,`⚠️ Could not resolve a git repository for ${p.repoPolicyWorkdir}.`);break}S.clearRepoPolicyChoiceTokens(p.sessionId);let h;try{h=S.launchAfterRepoPolicyChoice({route:p.route,prompt:p.launchPrompt,workdir:p.launchWorkdir,name:p.launchName,model:p.launchModel,reasoningEffort:p.launchReasoningEffort,fastMode:p.launchFastMode,systemPrompt:p.launchSystemPrompt,allowedTools:p.launchAllowedTools,resumeSessionId:p.launchResumeSessionId,resumeWorktreeFrom:p.launchResumeWorktreeFrom,sessionIdOverride:p.launchSessionIdOverride,clearedPersistedCodexResume:p.launchClearedPersistedCodexResume,forkSession:p.launchForkSession,forceNewSession:p.launchForceNewSession,permissionMode:p.launchPermissionMode,planApproval:p.launchPlanApproval,harness:p.launchHarness,worktreeStrategy:p.launchWorktreeStrategy,worktreeBaseBranch:p.launchWorktreeBaseBranch,worktreePrTargetRepo:p.launchWorktreePrTargetRepo,originAgentId:p.launchOriginAgentId}).text}catch(k){let v=k instanceof Error?k.message:String(k);await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,`⚠️ Repo policy saved, but launch failed: ${v}`);break}await X(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await K(o,[`✅ Repo policy saved: ${hl(f.policy).title}.`,"",h].join(`
128
- `));break}case"session-restart":case"session-resume":{await X(o,{alreadyAcknowledged:i});let f=await ve(S,{session:d,message:"Continue where you left off.",userInitiated:!0});await K(o,f.isError?`⚠️ ${f.text}`:`▶️ ${f.text}`);break}case"view-output":{await X(o,{alreadyAcknowledged:i});let f=await Rr().execute("callback",{session:d,lines:50});await K(o,Hr(f));break}case"question-answer":{if(await X(o,{alreadyAcknowledged:i}),a.optionIndex==null){await K(o,"⚠️ Invalid question-answer action.");break}let f=await S.resolvePendingInputOption(d,a.optionIndex,{requestId:a.pendingInputRequestId,questionId:a.pendingInputQuestionId});await K(o,f?"✅ Answer submitted.":"⚠️ That question button is no longer active. Use the latest question prompt.");break}default:{await X(o,{alreadyAcknowledged:i}),await K(o,"⚠️ Unknown callback action.");break}}return{handled:!0}}}}N();ie();function Nt(t){return Kl(t).map(e=>e.value)}function Kl(t){return Array.from(t.matchAll(/"[^"]*"|'[^']*'|\S+/g),e=>{let n=e[0],r=e.index??0;return{value:Pf(n),raw:n,start:r,end:r+n.length}})}function st(t){let[e]=Kl(t);if(e)return{value:e.value,rest:t.slice(e.end).trimStart()}}function Pf(t){return t.length>1&&(t.startsWith('"')&&t.endsWith('"')||t.startsWith("'")&&t.endsWith("'"))?t.slice(1,-1):t}function wf(t){return t instanceof Error?t.message:String(t)}function bf(t){let e=Nt(t),n,r=e;return e[0]==="--name"&&e[1]&&(n=e[1],r=e.slice(2)),{name:n,prompt:r.join(" ").trim()}}function Vl(t){t.registerCommand({name:"agent",description:"Launch a coding agent session. Usage: /agent [--name <name>] <prompt>",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!S)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=(e.args??"").trim();if(!n)return{text:"Usage: /agent [--name <name>] <prompt>"};let{name:r,prompt:o}=bf(n);if(!o)return{text:"Usage: /agent [--name <name>] <prompt>"};try{let i=Yn({prompt:o,name:r},e,S);if(i.kind!=="resolved")return{text:i.text};let s=S.spawn({prompt:o,name:r,workdir:i.workdir,model:i.resolvedModel,reasoningEffort:i.reasoningEffort,fastMode:i.fastMode,codexApprovalPolicy:i.harness==="codex"?"never":void 0,originChannel:i.originChannel,originThreadId:i.originThreadId,originAgentId:e.agentId||void 0,originSessionKey:i.originSessionKey,route:i.route,harness:i.harness,permissionMode:i.permissionMode,planApproval:i.planApproval,taskLifecycle:nr(e)});return{text:S.formatLaunchResult({prompt:o,workdir:i.workdir,harness:i.harness,permissionMode:i.permissionMode??D.permissionMode,planApproval:i.planApproval},s)}}catch(i){let s=wf(i),l=s.includes("Max sessions")?"":`
129
-
130
- Use /agent_sessions to see active sessions.`;return{text:`Error launching session: ${s}${l}`}}}})}N();function Gl(t){t.registerCommand({name:"agent_sessions",description:"List coding agent sessions. Usage: /agent_sessions [--full]",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!S)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=(e.args??"").split(/\s+/).includes("--full");return{text:wr(S,"all",void 0,{full:n})}}})}N();function jl(t){t.registerCommand({name:"agent_kill",description:"Kill a coding agent session by name or ID",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!S)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=e.args?.trim();return n?{text:br(S,n,"killed")}:{text:"Usage: /agent_kill <name-or-id>"}}})}N();function Hl(t){t.registerCommand({name:"agent_respond",description:"Send a follow-up message to a running coding agent session. Usage: /agent_respond <id-or-name> <message>",acceptsArgs:!0,requireAuth:!0,handler:async e=>{if(!S)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=(e.args??"").trim();if(!n)return{text:`Usage: /agent_respond <id-or-name> <message>
131
- /agent_respond --interrupt <id-or-name> <message>`};let r=!1,o=n,i=st(o);i?.value==="--interrupt"&&(r=!0,o=i.rest);let s=st(o);if(!s)return{text:"Error: Missing message. Usage: /agent_respond <id-or-name> <message>"};let l=s.value,a=s.rest;return a.trim()?{text:(await ve(S,{session:l,message:a,interrupt:r,userInitiated:!0})).text}:{text:"Error: Empty message. Usage: /agent_respond <id-or-name> <message>"}}})}N();function zl(t){t.registerCommand({name:"agent_stats",description:"Show OpenClaw Code Agent usage metrics",acceptsArgs:!1,requireAuth:!0,handler:()=>{if(!S)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let e=S.getMetrics(),n=S.list("running").length;return{text:Xn(e,n)}}})}N();function Rf(t){return t==="pr-required"||t==="pr-allowed"||t==="never-pr"||t==="manual"}function Ql(t){t.registerCommand({name:"agent_policy",description:"Inspect or set the current repo integration policy. Usage: /agent_policy [pr-required|pr-allowed|never-pr|manual|reset|list|cleanup]",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!S)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let r=st((e.args??"").trim())?.value;if(r==="list"){let l=S.listRepoPolicies();return{text:l.length===0?"No stored repo policies.":l.map(a=>`${a.policy} | ${a.provider} | ${a.repoRoot}`).join(`
132
- `)}}if(r==="cleanup"){let l=S.cleanupRepoPolicies();return{text:l.length===0?"No stale repo policies found.":[`Removed ${l.length} stale repo ${l.length===1?"policy":"policies"}.`,...l.map(a=>`${a.policy} | ${a.provider} | ${a.repoRoot}`)].join(`
133
- `)}}let o=e.workspaceDir;if(!o)return{text:"Error: workspaceDir is required."};if(r==="reset")return{text:S.resetRepoPolicy(o)?`Repo policy reset for ${o}.`:`No stored repo policy found for ${o}.`};if(r&&Rf(r)){if(typeof S.resolveRepoPolicy=="function"){let d=S.resolveRepoPolicy(o);if(d.identity){let u=_t(r,d.prAvailable);if(u)return{text:`Error: ${u}`}}}let l=S.setRepoPolicy(o,r);if(!l)return{text:`Error: ${o} is not a git repository.`};let a=`Repo policy set to ${l.policy} for ${l.repoRoot}.`;try{if(typeof S.continueLaunchAfterManualRepoPolicy!="function")return{text:a};let d=S.continueLaunchAfterManualRepoPolicy(l.repoRoot,r);if(d.kind==="launched")return{text:[a,"",d.text].join(`
134
- `)};if(d.kind==="ambiguous")return{text:[a,"",`Repo policy saved, but ${d.count} pending launches match this policy. Run the intended launch again to avoid starting the wrong session.`].join(`
135
- `)}}catch(d){let u=d instanceof Error?d.message:String(d);return{text:[a,"",`Repo policy saved, but the deferred launch failed: ${u}`,"The pending launch context was kept so you can retry the same /agent_policy command or run the intended launch again."].join(`
136
- `)}}return{text:a}}let i=S.resolveRepoPolicy(o);if(!i.identity)return{text:`No git repository found for ${o}.`};let s=gn(i.prAvailable).map(l=>l.policy).join(", ");return{text:[`Repo policy: ${i.policy??"unknown"}`,`Repo: ${i.identity.repoRoot}`,`Provider: ${i.provider}${i.prAvailable?"":" (PR automation unavailable)"}`,...i.identity.remoteUrl?[`Remote: ${i.identity.remoteUrl}`]:[],"",`Set with /agent_policy ${s}.`].join(`
137
- `)}}})}N();var Af=50;function Jl(t){t.registerCommand({name:"agent_output",description:"Show recent output from a coding agent session. Usage: /agent_output <id-or-name> [--full] [--lines N]",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!S)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=(e.args??"").trim();if(!n)return{text:"Usage: /agent_output <id-or-name> [--full] [--lines N]"};let r=Nt(n),o="",i=!1,s=Af;for(let a=0;a<r.length;a++)if(r[a]==="--full")i=!0;else if(r[a]==="--lines"&&a+1<r.length){let d=parseInt(r[a+1],10);!isNaN(d)&&d>0&&(s=d),a++}else o||(o=r[a]);return o?{text:Pr(S,o,{full:i,lines:s})}:{text:"Usage: /agent_output <id-or-name> [--full] [--lines N]"}}})}N();var Yl="Usage: /goal [--name <name>] [--workdir <dir>] [--model <model>] [--harness <name>] [--mode <ralph|verifier>] [--completion-promise <text>] [--max-iterations N] [--verify <cmd> ...] <goal>";function Zl(t){t.registerCommand({name:"goal",description:"Launch an explicit goal task (Ralph-style completion loop or verifier-driven loop)",acceptsArgs:!0,requireAuth:!0,handler:async e=>{if(!z)return{text:"Error: GoalController not initialized. The code-agent service must be running."};let n=(e.args??"").trim();if(!n)return{text:Yl};let r=Nt(n),o,i,s,l,a="bypassPermissions",d,u,c,m=[],p=[];for(let k=0;k<r.length;k++){let v=r[k];if(v==="--name"&&k+1<r.length)o=r[++k];else if(v==="--workdir"&&k+1<r.length)i=r[++k];else if(v==="--model"&&k+1<r.length)s=r[++k];else if(v==="--max-iterations"&&k+1<r.length){let I=parseInt(r[++k],10);!Number.isNaN(I)&&I>0&&(l=I)}else if(v==="--permission-mode"&&k+1<r.length){let I=r[++k];if(I==="default"||I==="plan"||I==="bypassPermissions")a=I;else return{text:`Error: Invalid permission mode "${I}".`}}else if(v==="--harness"&&k+1<r.length)d=r[++k];else if(v==="--mode"&&k+1<r.length){let I=r[++k];if(I==="ralph"||I==="verifier")u=I;else return{text:`Error: Invalid goal mode "${I}". Use ralph or verifier.`}}else if(v==="--completion-promise"&&k+1<r.length)c=r[++k];else if(v==="--verify"&&k+1<r.length){let I=r[++k].trim();if(!I)return{text:"Error: --verify commands must not be empty."};m.push(I)}else p.push(v)}let f=p.join(" ").trim();if(!f)return{text:Yl};let h=Br({goal:f,verifierCommands:m,name:o,workdir:i,model:s,maxIterations:l,permissionMode:a,harness:d,goalMode:u,completionPromise:c},e);if(h.kind!=="resolved")return{text:h.text};try{let k=await z.launchTask({goal:h.goal,name:h.name,workdir:h.workdir,model:h.model,reasoningEffort:h.reasoningEffort,fastMode:h.fastMode,maxIterations:h.maxIterations,permissionMode:h.permissionMode,harness:h.harness,loopMode:h.loopMode,completionPromise:h.completionPromise,originChannel:h.originChannel,originThreadId:h.originThreadId,originAgentId:h.originAgentId,originSessionKey:h.originSessionKey,route:h.route,verifierCommands:h.verifierCommands});return{text:qr(k,h)}}catch(k){return{text:`Error launching goal task: ${k instanceof Error?k.message:String(k)}`}}}})}N();function Xl(t){t.registerCommand({name:"goal_status",description:"Show one goal task or list all explicit goal tasks. Usage: /goal_status [<task-id-or-name>]",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!z)return{text:Pe};let n=(e.args??"").trim();return{text:Kr(z,r=>S?.resolve(r),n)}}})}N();function ed(t){t.registerCommand({name:"goal_stop",description:"Stop a goal task. Usage: /goal_stop <task-id-or-name>",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!z)return{text:Pe};let n=(e.args??"").trim();if(!n)return{text:"Usage: /goal_stop <task-id-or-name>"};let r=z.stopTask(n);return{text:Vr(r,n)}}})}N();var td="Usage: /goal_edit <task-id-or-name> <replacement-goal>";function nd(t){t.registerCommand({name:"goal_edit",description:"Edit a running goal task. Usage: /goal_edit <task-id-or-name> <replacement-goal>",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!z)return{text:Pe};let n=(e.args??"").trim();if(!n)return{text:td};let r=st(n),o=r?.value.trim(),i=r?.rest.trim();if(!o||!i)return{text:td};let s=z.editTask(o,i);return{text:Gr(s,o)}}})}import{execFile as Ff}from"child_process";import{createHash as yd}from"crypto";import{existsSync as Rn,mkdirSync as If,readFileSync as xf,renameSync as id,writeFileSync as Tf}from"fs";import{homedir as Cf}from"os";import{dirname as Mf,join as sd}from"path";var _f=new Set(["running","waiting_for_session","waiting_for_user","succeeded","failed","stopped"]);function $f(t){let e=t.OPENCLAW_HOME?.trim();return e||sd(Cf(),".openclaw")}function Ef(t){let e=t.OPENCLAW_CODE_AGENT_GOAL_TASKS_PATH?.trim();return e||sd($f(t),"code-agent-goal-tasks.json")}function ad(t){return t instanceof Error?t.message:String(t)}function ld(t){return!!t&&typeof t=="object"&&!Array.isArray(t)}var Df=100;function rd(t,e,n){let r=n==null?"":`-${n}`;return`${t}.invalid-${e}${r}.json`}function Of(t){if(!Rn(t))return;let e=Date.now(),n=rd(t,e);if(!Rn(n))return n;for(let r=1;r<=Df;r+=1){let o=rd(t,e,r);if(!Rn(o))return o}}function od(t,e){try{let n=Of(t);return n?(id(t,n),`${e}${n}`,!0):(Rn(t),!1)}catch(n){return`${ad(n)}`,!1}}function Wf(t){if(!ld(t))return;let e=t;if(!(typeof e.provider!="string"||typeof e.target!="string"))return{provider:e.provider,target:e.target,accountId:typeof e.accountId=="string"?e.accountId:void 0,threadId:typeof e.threadId=="string"?e.threadId:void 0,sessionKey:typeof e.sessionKey=="string"?e.sessionKey:void 0}}function Nf(t){if(!ld(t))return;let e=t;if(typeof e.id!="string"||typeof e.name!="string"||typeof e.goal!="string"||typeof e.workdir!="string"||typeof e.status!="string"||!_f.has(e.status))return;let n=e.status,r=n==="running"||n==="waiting_for_session"?"waiting_for_session":n;return{id:e.id,name:e.name,goal:e.goal,workdir:e.workdir,status:r,createdAt:typeof e.createdAt=="number"?e.createdAt:Date.now(),updatedAt:typeof e.updatedAt=="number"?e.updatedAt:Date.now(),iteration:typeof e.iteration=="number"?e.iteration:0,maxIterations:typeof e.maxIterations=="number"?e.maxIterations:8,sessionId:typeof e.sessionId=="string"?e.sessionId:void 0,sessionName:typeof e.sessionName=="string"?e.sessionName:void 0,harnessSessionId:typeof e.harnessSessionId=="string"?e.harnessSessionId:void 0,model:typeof e.model=="string"?e.model:void 0,reasoningEffort:typeof e.reasoningEffort=="string"?e.reasoningEffort:void 0,fastMode:e.fastMode===!0?!0:void 0,systemPrompt:typeof e.systemPrompt=="string"?e.systemPrompt:void 0,allowedTools:Array.isArray(e.allowedTools)?e.allowedTools.filter(o=>typeof o=="string"):void 0,originChannel:typeof e.originChannel=="string"?e.originChannel:void 0,originThreadId:typeof e.originThreadId=="string"||typeof e.originThreadId=="number"?e.originThreadId:void 0,originAgentId:typeof e.originAgentId=="string"?e.originAgentId:void 0,originSessionKey:typeof e.originSessionKey=="string"?e.originSessionKey:void 0,route:Wf(e.route),harness:typeof e.harness=="string"?e.harness:void 0,permissionMode:typeof e.permissionMode=="string"?e.permissionMode:void 0,loopMode:e.loopMode==="ralph"?"ralph":"verifier",completionPromise:typeof e.completionPromise=="string"?e.completionPromise:void 0,verifierCommands:Array.isArray(e.verifierCommands)?e.verifierCommands.filter(o=>!!o&&typeof o=="object"&&typeof o.label=="string"&&typeof o.command=="string"):[],lastVerifierSummary:typeof e.lastVerifierSummary=="string"?e.lastVerifierSummary:void 0,lastVerifierFingerprint:typeof e.lastVerifierFingerprint=="string"?e.lastVerifierFingerprint:void 0,repeatedFailureCount:typeof e.repeatedFailureCount=="number"?e.repeatedFailureCount:0,waitingForUserReason:typeof e.waitingForUserReason=="string"?e.waitingForUserReason:void 0,failureReason:typeof e.failureReason=="string"?e.failureReason:void 0}}function Lf(t){if(!Array.isArray(t))return;let e=[];for(let n of t){let r=Nf(n);if(!r)return;e.push(r)}return e}var zr=class{path;tasks=new Map;constructor(e=process.env){this.path=Ef(e),this.load()}load(){try{if(!Rn(this.path))return;let e=xf(this.path,"utf8"),n=JSON.parse(e),r=Lf(n);if(!r){od(this.path,"invalid")&&this.save();return}this.tasks.clear();for(let o of r)this.tasks.set(o.id,o);this.save()}catch(e){if(e.code==="ENOENT")return;od(this.path,"corrupt or unreadable")&&this.save()}}save(){try{If(Mf(this.path),{recursive:!0});let e=`${this.path}.tmp`;Tf(e,JSON.stringify([...this.tasks.values()],null,2),"utf8"),id(e,this.path)}catch(e){`${this.path}${ad(e)}`}}upsert(e){this.tasks.set(e.id,e),this.save()}get(e){let n=this.tasks.get(e);return n||[...this.tasks.values()].find(r=>r.name===e)}list(){return[...this.tasks.values()].sort((e,n)=>n.createdAt-e.createdAt)}};be();var Bf=8,kd=600*1e3,qf=4e3,Ji=1200,Uf="DONE",Kf=["BASH_ENV","ENV"];function Vf(t){return t.toLowerCase().replace(/[^a-z0-9]+/g,"-").replace(/^-+|-+$/g,"").slice(0,48)||"goal-task"}function Lt(t,e){return t.length<=e?t:`${t.slice(0,e-3)}...`}function je(t,e=20){let n=t.split(/\r?\n/).map(r=>r.trimEnd()).filter(r=>r.trim().length>0);return n.length<=e?n.join(`
115
+ (Pre-existing changes on ${c} were auto-stashed and restored.)`),j=_e(j,b),S={content:[{type:"text",text:j}]}}else if(b.rebaseConflict)S={content:[{type:"text",text:_e(`⚠️ Rebase conflicts — manual resolution required:
116
+
117
+ ${b.error}`,b)}]};else if(b.conflictFiles&&b.conflictFiles.length>0){let k=["Resolve merge conflicts in the following files and commit the resolution:","",...b.conflictFiles.map(P=>`- ${P}`),"",`After resolving, commit with message: "Resolve merge conflicts from ${l}"`].join(`
118
+ `);try{let P=v.spawn({prompt:k,workdir:d,name:`${n.session}-conflict-resolver`,harness:le(),permissionMode:"bypassPermissions",multiTurn:!0,route:o?.route??i?.route,originChannel:o?.originChannel??i?.originChannel,originThreadId:o?.originThreadId??i?.originThreadId,originAgentId:o?.originAgentId??i?.originAgentId,originSessionKey:o?.originSessionKey??i?.originSessionKey});S={content:[{type:"text",text:_e(`⚠️ Merge conflicts in ${b.conflictFiles.length} file(s) — spawned conflict resolver session: ${P.name}`,b)}]}}catch(P){S={content:[{type:"text",text:_e(`❌ Merge conflicts detected, but failed to spawn resolver: ${P instanceof Error?P.message:String(P)}`,b)}]}}}else{let k=b.dirtyError?`❌ Merge blocked: ${b.error}`:`❌ Merge failed: ${b.error??"unknown error"}`;S={content:[{type:"text",text:_e(k,b)}]}}}),S}}}qr();ne();B();X();ke();wn();function mf(t){return!!t&&typeof t=="object"}function Wl(t){return{name:"agent_worktree_cleanup",description:"Manage worktree cleanup with lifecycle-aware safety rules. Use preview_safe to list what Clean all safe would remove, clean_safe to execute it, or preview_all to see both safe and retained sandboxes with kept reasons.",parameters:h.Object({workdir:h.Optional(h.String({description:"Restrict cleanup to sessions rooted in this repository"})),base_branch:h.Optional(h.String({description:"Override base branch for lifecycle resolution"})),mode:h.Optional(h.Union([h.Literal("preview_safe"),h.Literal("clean_safe"),h.Literal("preview_all")],{description:"Cleanup mode. preview_safe shows what Clean all safe would remove, clean_safe performs that cleanup, preview_all shows both safe and retained worktrees. Defaults to preview_safe when dry_run=true, otherwise clean_safe."})),skip_session_check:h.Optional(h.Boolean({description:"Deprecated. Safe cleanup never removes live sessions."})),force:h.Optional(h.Boolean({description:"Deprecated alias for skip_session_check."})),dry_run:h.Optional(h.Boolean({description:"Show what would be cleaned without deleting anything."})),session:h.Optional(h.String({description:"Session name or ID to clean or dismiss."})),dismiss_session:h.Optional(h.Boolean({description:"When true and session is provided, permanently dismiss the worktree."}))}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!mf(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { workdir?, base_branch?, mode?, dry_run?, session?, dismiss_session? }."}]};let r=n.session,o=n.mode??(n.dry_run===!0?"preview_safe":"clean_safe"),i=o!=="clean_safe",s=o==="preview_all"||o==="clean_safe";if(r&&n.dismiss_session===!0)return{content:[{type:"text",text:await v.dismissWorktree(r)}]};let a=$r(v);if(r&&(a=a.filter(g=>Er(g,r)),a.length===0)){let g=Ot(v,r);if(!g.persistedSession&&!g.activeSession)return{content:[{type:"text",text:`Error: Session "${r}" not found.`}]}}if(n.workdir&&(a=a.filter(g=>g.workdir===n.workdir)),a.length===0)return{content:[{type:"text",text:"No managed worktrees matched the requested scope."}]};let l=[],d=[],u=[],c=[];for(let g of a){let{persistedSession:m,activeSession:f,resolvedLifecycle:y}=_r(v,g,{baseBranch:n.base_branch});if(!y.cleanupSafe){if(s){let S=y.reasons.length>0?y.reasons.map(Dr).join(", "):at(y.derivedState);d.push(`${g.name} [kept: ${S}]`)}continue}if(l.push(`${g.name} (${at(y.derivedState)})`),!i)try{let S=g.workdir;if(!((m??f)&&de(m??f))&&g.worktreePath&&ce(S,g.worktreePath,{destructive:!1}),g.worktreeBranch&&ye(S,g.worktreeBranch),m){let I=y.derivedState==="merged"||y.derivedState==="released"?y.derivedState:y.lifecycle.state,b=new Date().toISOString(),A=I==="merged"?m.worktreeMergedAt:I==="dismissed"?m.worktreeDismissedAt:void 0;v.updatePersistedSession(g.id,{worktreePath:void 0,worktreeBranch:void 0,lifecycle:"terminal",worktreeState:"none",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeMerged:I==="merged"?!0:m.worktreeMerged,worktreeMergedAt:I==="merged"?m.worktreeMergedAt??b:m.worktreeMergedAt,worktreeLifecycle:{...m.worktreeLifecycle??y.lifecycle,state:I,updatedAt:b,resolvedAt:m.worktreeLifecycle?.resolvedAt??A??b,resolutionSource:m.worktreeLifecycle?.resolutionSource??"maintenance",baseBranch:n.base_branch??y.lifecycle.baseBranch??m.worktreeBaseBranch,targetRepo:m.worktreePrTargetRepo,pushRemote:m.worktreePushRemote,notes:y.reasons}})}u.push(`${g.name} (${at(y.derivedState)})`)}catch(S){c.push(`${g.name}: ${S instanceof Error?S.message:String(S)}`)}}let p=[o==="clean_safe"?"Clean all safe:":o==="preview_all"?"Worktree lifecycle review:":"Clean all safe preview:"];return p.push(` SAFE ${i?"NOW":"FOUND"} (${l.length}): ${l.join(", ")||"(none)"}`),s&&p.push(` KEPT (${d.length}): ${d.join(", ")||"(none)"}`),i||(p.push(` CLEANED (${u.length}): ${u.join(", ")||"(none)"}`),p.push(` FAILURES (${c.length}): ${c.join(", ")||"(none)"}`)),{content:[{type:"text",text:p.join(`
119
+ `)}]}}}}ne();B();wn();function ff(t){if(t==null)return!0;if(Array.isArray(t)||typeof t!="object")return!1;let e=t.session;return e===void 0||typeof e=="string"}function Nl(t){return{name:"agent_worktree_status",description:"Show lifecycle-first worktree status for coding agent sessions. Displays product-facing lifecycle state, released handling, cleanup safety, and retained reasons.",parameters:h.Object({session:h.Optional(h.String({description:"Session name or ID to show status for (optional, shows all if omitted)"}))}),async execute(e,n){if(!v)return{content:[{type:"text",text:"Error: SessionManager not initialized. The code-agent service must be running."}]};if(!ff(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { session? }."}]};let r=n&&typeof n=="object"?n.session:void 0,o=$r(v);if(r&&(o=o.filter(s=>Er(s,r)),o.length===0))return{content:[{type:"text",text:`Error: Session "${r}" not found or has no worktree.`}]};if(o.length===0)return{content:[{type:"text",text:"No sessions with worktrees found."}]};let i=[];for(let s of o){let{persistedSession:a,resolvedLifecycle:l}=_r(v,s),d=l.cleanupSafe?"safe now":l.preserve?"preserve":"blocked";i.push(`Session: ${s.name} [${s.id}]`),i.push(` Branch: ${s.worktreeBranch??"(unknown)"} → ${l.lifecycle.baseBranch??a?.worktreeBaseBranch??"main"}`),i.push(` Repo: ${s.workdir}`),i.push(` Lifecycle:${at(l.lifecycle.state)}`),l.derivedState!==l.lifecycle.state&&i.push(` Derived: ${at(l.derivedState)}`),i.push(` Cleanup: ${d}`),l.evidence.prUrl&&i.push(` PR: ${l.evidence.prUrl} (${l.evidence.prState??"unknown"})`),(l.evidence.branchAheadCount!=null||l.evidence.baseAheadCount!=null)&&i.push(` Ahead: ${l.evidence.branchAheadCount??0} ahead / ${l.evidence.baseAheadCount??0} behind`),i.push(` Reasons: ${l.reasons.length>0?l.reasons.map(Dr).join(", "):"none"}`),i.push("")}return{content:[{type:"text",text:i.join(`
120
+ `).trim()}]}}}}ne();B();se();Gn();import{existsSync as gf}from"fs";function hf(t=[]){return t.map((e,n)=>({label:`check-${n+1}`,command:e.trim()})).filter(e=>e.command.length>0)}function Kr(t,e){let n=t.goal.trim();if(!n)return{kind:"error",text:"Error: goal must not be empty."};let r=t.workdir||e.workspaceDir||D.defaultWorkdir||process.cwd();if(!gf(r))return{kind:"error",text:`Error: Working directory does not exist: ${r}`};let o=hf(t.verifierCommands),i=t.goalMode??(o.length>0?"verifier":"ralph");if(i==="verifier"&&o.length===0)return{kind:"error",text:"Error: verifier mode requires at least one non-empty verifier command."};let s=t.harness??le(),a=t.model??pt(s),l=Oe(s,a),d=En(s);if(!l&&(s!=="opencode"||d&&d.length>0))return{kind:"error",text:`Error: No default model configured for harness "${s}". Set plugins.entries["openclaw-code-agent"].config.harnesses.${s}.defaultModel or pass model explicitly.`};if(l&&!vt(s,l))return{kind:"error",text:`Error: Model "${a}" is not supported for harness "${s}". Use a bare Codex model id such as "gpt-5.5".`};if(l&&!Un(s,l,d))return{kind:"error",text:`Error: Model "${a}" is not allowed. Permitted models: ${d?.join(", ")}`};let u=Vn(s,l,d),c=e.sessionKey||void 0,p=Dn(e),g=Xt(e,p||Ze(r)),m=ft(e,g,c);return{kind:"resolved",goal:n,name:t.name,workdir:r,model:u,reasoningEffort:Ke(s),fastMode:mt(s),systemPrompt:t.systemPrompt,allowedTools:t.allowedTools,maxIterations:t.maxIterations,permissionMode:t.permissionMode??"bypassPermissions",harness:s,loopMode:i,completionPromise:t.completionPromise,originChannel:g,originThreadId:m?.threadId,originAgentId:e.agentId||void 0,originSessionKey:c,route:m,verifierCommands:o}}function Ur(t,e){return["Goal task launched.",` Name: ${t.name}`,` ID: ${t.id}`,` Dir: ${t.workdir}`,` Session: ${t.sessionName} [${t.sessionId}]`,` Harness: ${e.harness}`,` Model: ${e.model??"default"}`,...e.fastMode?[" Fast mode: enabled"]:[],` Loop mode: ${t.loopMode}`,` Max controller iterations: ${t.maxIterations}`,` Goal: "${e.goal.length>100?`${e.goal.slice(0,100)}...`:e.goal}"`,...t.loopMode==="ralph"?[` Completion promise: ${t.completionPromise}`]:[" Verifiers:",...e.verifierCommands.map(r=>` - ${r.command}`)],"","Controller iteration progress advances only when the goal controller starts another agent turn; internal agent review passes are reported in the completion summary.","","Use goal_status to follow progress or goal_stop to terminate the task."].join(`
121
+ `)}function yf(t){return!t||typeof t!="object"?!1:typeof t.goal=="string"}function Ll(t){return{name:"goal_launch",description:"Launch an explicit goal loop. Use this only when the user specifically asks for a goal task, Ralph-style autonomous loop, iterative loop, autonomous repair loop, or keep-going-until-checks-pass workflow. This is not the default session path.",parameters:h.Object({goal:h.String({description:"End goal for the autonomous task"}),verifier_commands:h.Optional(h.Array(h.String({description:"Shell command that must pass for the goal to be considered complete"}),{minItems:1,description:"Verifier commands run after each coding turn"})),name:h.Optional(h.String({description:"Short task name (kebab-case preferred)"})),workdir:h.Optional(h.String({description:"Working directory (defaults to cwd / configured workspace)"})),model:h.Optional(h.String({description:"Model name to use"})),system_prompt:h.Optional(h.String({description:"Additional system prompt"})),allowed_tools:h.Optional(h.Array(h.String(),{description:"Allowed tools for the underlying agent session"})),max_iterations:h.Optional(h.Number({description:"Maximum verifier-driven repair iterations",minimum:1})),goal_mode:h.Optional(h.Union([h.Literal("ralph"),h.Literal("verifier")],{description:"Loop strategy. 'ralph' repeats until a completion promise appears. 'verifier' repeats until verifier commands pass. Defaults to 'ralph' when no verifiers are provided, otherwise 'verifier'."})),completion_promise:h.Optional(h.String({description:"Exact completion promise for Ralph-mode loops. Defaults to 'DONE'."})),permission_mode:h.Optional(h.Union([h.Literal("default"),h.Literal("plan"),h.Literal("bypassPermissions")],{description:"Permission mode for the underlying agent session. Defaults to bypassPermissions for autonomous goal loops."})),harness:h.Optional(h.String({description:"Agent harness to use ('claude-code', 'codex', or experimental 'opencode')."}))}),async execute(e,n){if(!z)return{content:[{type:"text",text:"Error: GoalController not initialized. The code-agent service must be running."}]};if(!yf(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected at least { goal }."}]};let r=Kr({goal:n.goal,verifierCommands:n.verifier_commands,name:n.name,workdir:n.workdir,model:n.model,systemPrompt:n.system_prompt,allowedTools:n.allowed_tools,maxIterations:n.max_iterations,permissionMode:n.permission_mode,harness:n.harness,goalMode:n.goal_mode,completionPromise:n.completion_promise},t);if(r.kind!=="resolved")return{content:[{type:"text",text:r.text}]};try{let o=await z.launchTask({goal:r.goal,name:r.name,workdir:r.workdir,model:r.model,reasoningEffort:r.reasoningEffort,fastMode:r.fastMode,systemPrompt:r.systemPrompt,allowedTools:r.allowedTools,maxIterations:r.maxIterations,permissionMode:r.permissionMode,loopMode:r.loopMode,completionPromise:r.completionPromise,originChannel:r.originChannel,originThreadId:r.originThreadId,originAgentId:r.originAgentId,originSessionKey:r.originSessionKey,route:r.route,harness:r.harness,verifierCommands:r.verifierCommands});return{content:[{type:"text",text:Ur(o,r)}]}}catch(o){return{content:[{type:"text",text:`Error launching goal task: ${o instanceof Error?o.message:String(o)}`}]}}}}}ne();function ji(t,e){return t.split(`
122
+ `).map(n=>`${e}${n}`)}function Bl(t,e){return t.length<=e?t:`${t.slice(0,e-3).trimEnd()}...`}function kf(t,e=8,n=600){let r=t.map(i=>i.trimEnd()).filter(i=>i.trim().length>0);if(r.length===0)return;let o=r.slice(-e).join(`
123
+ `);return o.length<=n?o:`...${o.slice(-(n-3))}`}function Sf(t,e){let n=e?.trim(),r=(t??"").split(/\r?\n/).map(o=>o.trim().replace(/^[-*]\s+/,"")).filter(o=>o.length>0).filter(o=>!(n&&o===n)).filter(o=>!/^<promise>.*<\/promise>$/.test(o));return r.length===0?[]:r.slice(-3).map(o=>Bl(o,180))}function vf(t){let e=(t??"").split(/\r?\n/).map(n=>n.trim()).filter(n=>n.length>0);return e.length===0?[]:e.slice(0,2).map(n=>Bl(n,180))}function Vr(t){let e=[],n=vf(t.verifierSummary),r=Sf(t.output,t.completionPromise);if(n.length===0&&r.length===0)return;t.completionDetected===!0&&e.push("Completion was claimed, but the loop is continuing after verification.");for(let i of n)e.push(`Verifier: ${i}`);let o=Math.max(0,3-e.length);if(o>0)for(let i of r.slice(-o))e.push(`Agent: ${i}`);return["Iteration summary:",...e.map(i=>`- ${i}`)].join(`
124
+ `)}function Hi(t){if(t)return{phase:t.phase,awaitingInput:t.isAwaitingInput??!!t.pendingInputState,latestOutput:kf(t.getOutput(20))}}function zi(t,e,n){let r=t.loopMode??"verifier",o=[`${t.name} [${t.id}]`,` Status: ${t.status}`,...r==="ralph"?[" Loop mode: ralph",` Iteration: ${t.iteration}/${t.maxIterations}`]:[` Repair iteration: ${t.iteration}/${t.maxIterations}`],` Workdir: ${t.workdir}`];return r==="ralph"&&t.completionPromise&&o.push(` Completion promise: ${t.completionPromise}`),t.sessionId&&o.push(` Session: ${t.sessionName??"(unknown)"} [${t.sessionId}]`),e?.phase&&o.push(` Phase: ${e.phase}`),e?.awaitingInput!==void 0&&o.push(` Awaiting input: ${e.awaitingInput?"yes":"no"}`),n&&o.push(...ji(n," ")),t.lastVerifierSummary&&(o.push(" Last verifier:"),o.push(...ji(t.lastVerifierSummary," "))),e?.latestOutput&&(o.push(" Latest activity:"),o.push(...ji(e.latestOutput," "))),t.waitingForUserReason&&o.push(` Waiting on user: ${t.waitingForUserReason}`),t.failureReason&&o.push(` Failure: ${t.failureReason}`),o.join(`
125
+ `)}var we="Error: GoalController not initialized. The code-agent service must be running.";function Gr(t,e,n){let r=n?.trim();if(r){let i=t.getTask(r);if(!i)return`Error: Goal task "${r}" not found.`;let s=i.sessionId?e(i.sessionId):void 0;return zi(i,Hi(s))}let o=t.listTasks();return o.length===0?"No goal tasks found.":o.map(i=>{let s=i.sessionId?e(i.sessionId):void 0;return zi(i,Hi(s))}).join(`
126
+
127
+ `)}function jr(t,e){return t?t.action==="already_terminal"?`Task is already ${t.task.status}.`:`Task "${t.task.name}" (${t.task.id}) stopped.`:`Error: Goal task "${e}" not found.`}function Hr(t,e){switch(t.action){case"updated":return`Task "${t.task.name}" (${t.task.id}) goal updated.`;case"not_found":return`Error: Goal task "${e}" not found.`;case"invalid_goal":return"Error: replacement goal must not be empty.";case"not_editable":return t.task.status!=="waiting_for_user"?`Task is already ${t.task.status}.`:`Error: Goal task "${t.task.name}" is ${t.task.status} and cannot be edited.`}}B();function Fl(t){return{name:"goal_status",description:"Show status for explicit goal tasks managed by the goal controller. Use this to inspect one goal task or list all goal tasks.",parameters:h.Object({task:h.Optional(h.String({description:"Task name or ID. Omit to list all tasks."}))}),async execute(e,n){if(!z)return{content:[{type:"text",text:we}]};let r=n&&typeof n=="object"&&typeof n.task=="string"?n.task:void 0;return{content:[{type:"text",text:Gr(z,o=>v?.resolve(o),r)}]}}}}ne();B();function wf(t){return!!t&&typeof t=="object"&&typeof t.task=="string"}function ql(t){return{name:"goal_stop",description:"Stop an explicit goal task and kill its underlying agent session.",parameters:h.Object({task:h.String({description:"Goal task name or ID"})}),async execute(e,n){if(!z)return{content:[{type:"text",text:we}]};if(!wf(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { task }."}]};let r=z.stopTask(n.task);return{content:[{type:"text",text:jr(r,n.task)}]}}}}ne();B();function Pf(t){if(!t||typeof t!="object")return!1;let e=t;return typeof e.task=="string"&&typeof e.goal=="string"}function Kl(t){return{name:"goal_edit",description:"Edit the goal text for an active goal task without stopping or relaunching its session.",parameters:h.Object({task:h.String({description:"Goal task name or ID"}),goal:h.String({description:"Replacement goal text"})}),async execute(e,n){if(!z)return{content:[{type:"text",text:we}]};if(!Pf(n))return{content:[{type:"text",text:"Error: Invalid parameters. Expected { task, goal }."}]};let r=z.editTask(n.task,n.goal);return{content:[{type:"text",text:Hr(r,n.task)}]}}}}B();qr();import{createHash as bf}from"crypto";var ee="code-agent";var Rf=new Set(["1","true","yes","on"]);function Ji(){let t=process.env.OPENCLAW_CODE_AGENT_BUTTON_DIAGNOSTICS?.trim().toLowerCase();return!!(t&&Rf.has(t))}function Pe(t){if(!(typeof t!="string"||t.length===0))return bf("sha256").update(t).digest("hex").slice(0,12)}function Ul(t){return typeof t.callbackData=="string"?t.callbackData:typeof t.value=="string"?t.value:void 0}function J(t){let e=(t??[]).filter(r=>Array.isArray(r)&&r.length>0),n=e.flat();return{buttonRows:e.length||void 0,buttonCount:n.length||void 0,buttonLabels:n.length>0?n.map(r=>typeof r.label=="string"?r.label:void 0):void 0,callbackByteLengths:n.length>0?n.map(r=>{let o=Ul(r);return o?Buffer.byteLength(o,"utf8"):void 0}):void 0,callbackHashes:n.length>0?n.map(r=>Pe(Ul(r))):void 0,buttonStyles:n.length>0?n.map(r=>typeof r.style=="string"?r.style:void 0):void 0}}function He(t){return t&&typeof t=="object"&&!Array.isArray(t)?t:void 0}function Gl(t){let e=He(t),n=Array.isArray(e?.blocks)?e.blocks:void 0;if(n)return n.map(r=>He(r)?.type).filter(r=>typeof r=="string"&&r.length>0)}function jl(t){let e=He(t),n=Array.isArray(e?.blocks)?e.blocks:void 0;if(!n)return;let r=n.map(o=>{let i=He(o);return i?.type!=="buttons"||!Array.isArray(i.buttons)?[]:i.buttons}).filter(o=>o.length>0);return r.length>0?r:void 0}function Yi(t){let e=jl(t);return{presentationBlockTypes:Gl(t),...J(e)}}function Zi(t){let e=He(t),n=e?.interactive,r=He(e?.channelData),o=He(r?.telegram),i=Array.isArray(o?.buttons)?o.buttons:void 0;return{renderedPayloadKeys:e?Object.keys(e).sort():void 0,interactiveBlockTypes:Gl(n),...Vl("interactive",J(jl(n))),...Vl("telegramChannelData",J(i)),hasPresentation:!!e?.presentation,hasInteractive:!!n,hasTelegramChannelDataButtons:!!i?.some(s=>s.length>0)}}function Hl(t){let e=He(t);return e?{sendResultKeys:Object.keys(e).sort(),messageId:Qi(e.messageId),chatId:Qi(e.chatId),telegramThreadId:Qi(e.messageThreadId??e.threadId),channel:typeof e.channel=="string"?e.channel:void 0}:{sendResultType:typeof t}}function Qi(t){return typeof t=="string"||typeof t=="number"?t:void 0}function Vl(t,e){let n={};for(let[r,o]of Object.entries(e))o!==void 0&&(n[`${t}${r.charAt(0).toUpperCase()}${r.slice(1)}`]=o);return n}function L(t,e){if(!Ji())return;let n=Object.fromEntries(Object.entries(e).filter(([,r])=>r!==void 0));`${JSON.stringify({event:t,callbackNamespace:ee,...n})}`}var Xi=new Set,zl="⚠️ Could not submit that answer. The question prompt is still active; try again or reply with the answer.",An=new Map;async function Zl(t){try{await t}catch(e){let n=e instanceof Error?e.message:String(e);`${n}`}}async function Ql(t,e,n){if(!t)return n();for(;;){let o=An.get(t)?.operation;if(!o)break;await Zl(o)}let r=Promise.resolve().then(n);An.set(t,{operation:r,tokenId:e});try{return await r}finally{An.get(t)?.operation===r&&An.delete(t)}}function Af(t){let e=t.trim().replace(new RegExp(`^${ee}:`),"");return e||null}function If(t){return t.trim().startsWith(`${ee}:`)}async function zr(t,e=!1){if(t.channel==="telegram")try{return(await Z(t,{alreadyAcknowledged:e,forceTelegramMarkupEdit:!0})).textDelivered}catch(r){let o=r instanceof Error?r.message:String(r);return`${o}`,!1}let n=t.respond;if(typeof n.clearComponents=="function")try{return await n.clearComponents(),!1}catch(r){if(Nt(r))return!1;let o=r instanceof Error?r.message:String(r);`${o}`}if(typeof n.clearButtons=="function")try{await n.clearButtons()}catch(r){let o=r instanceof Error?r.message:String(r);`${o}`}else!e&&typeof n.acknowledge=="function"&&await n.acknowledge();return!1}async function Le(t,e=!1){await Z(t,{alreadyAcknowledged:e,forceTelegramMarkupEdit:t.channel==="telegram"})}function Jr(t){if(t&&typeof t=="object"&&"content"in t&&Array.isArray(t.content)){let e=t.content[0];return typeof e?.text=="string"?e.text:"(done)"}return"(done)"}function Jl(t){if(t&&typeof t=="object"&&"meta"in t){let e=t.meta;if(typeof e?.success=="boolean")return e.success}return ns(Jr(t))}function ns(t){return!/^\s*(?:Error\b:?|❌|⚠️)/.test(t)}function Yr(t){return t==="plan-approve"||t==="plan-request-changes"||t==="plan-reject"}function xf(t){if(Yr(t.kind))return`${t.sessionId}:v${t.planDecisionVersion??"unknown"}`}function Tf(t){return t?t.approvalState==="approved"||!t.pendingPlanApproval:!1}function Cf(...t){let e;for(let n of t)n!=null&&(e=e==null?n:Math.max(e,n));return e}function Mf(t){if(t.actionablePlanDecisionVersion!=null)return t.actionablePlanDecisionVersion;let e=Cf(t.approvalPromptRequiredVersion,t.approvalPromptVersion);return e??t.canonicalPlanPromptVersion??t.planDecisionVersion}function es(t,e){if(!Yr(t.kind))return;if(!e)return"This plan decision is stale because the session is no longer available.";let n=Mf(e);if(t.planDecisionVersion!=null&&n!=null&&t.planDecisionVersion!==n)return"This plan decision is stale because a newer plan review state already exists.";if(!e.pendingPlanApproval)return"This plan is no longer awaiting approval.";if(t.kind==="plan-approve"&&e.approvalState==="changes_requested"&&!e.pendingPlanApproval)return"Changes were already requested for this plan. Wait for the revised plan before approving.";if(t.kind==="plan-request-changes"&&e.approvalState==="changes_requested")return"Changes were already requested for this plan. Send your feedback to the agent instead."}function Xl(t,...e){return e.find(n=>typeof n=="string"&&t(n))}function Qr(...t){return Xl(e=>e.trim().length>0,...t)}function Yl(...t){return Xl(If,...t)}function _f(t){let e="callback"in t?Yl(t.callback?.data,t.callback?.callback_data,t.callback?.callbackData):void 0;if(e)return e;let n="interaction"in t?t.interaction:void 0,r=Yl(n?.data,n?.callback_data,n?.callbackData);if(r)return r;let o="callback"in t?Qr(t.callback?.payload):void 0;if(o)return o;let i=Qr(n?.payload);return i||(("callback"in t?Qr(t.callback?.data,t.callback?.callback_data,t.callback?.callbackData):void 0)??Qr(n?.data,n?.callback_data,n?.callbackData)??"")}function Nt(t){let e=t instanceof Error?t.message:String(t);return/message is not modified/i.test(e)}function $f(t){let e=t instanceof Error?t.message:String(t);return/empty message/i.test(e)}async function Z(t,e={}){let n=t.respond,{alreadyAcknowledged:r=!1,forceTelegramMarkupEdit:o=!1,text:i}=e;if(t.channel==="telegram"){if(typeof i=="string"&&typeof n.editMessage=="function")try{return await n.editMessage({text:i,buttons:[]}),typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!0}}catch(a){if(Nt(a))return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!0};let l=a instanceof Error?a.message:String(a);`${l}`}if(o&&typeof n.editButtons=="function")try{return await n.editButtons({buttons:[]}),typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}catch(a){if(Nt(a))return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1};let l=a instanceof Error?a.message:String(a);`${l}`}let s="callback"in t&&typeof t.callback?.messageText=="string"?t.callback.messageText:void 0;if(o&&typeof s=="string"&&typeof n.editMessage=="function")try{return await n.editMessage({text:s,buttons:[]}),typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}catch(a){if(Nt(a))return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1};let l=a instanceof Error?a.message:String(a);`${l}`}return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}if(typeof n.clearComponents=="function")try{return await n.clearComponents(typeof i=="string"?{text:i}:void 0),{textDelivered:typeof i=="string"}}catch(s){if(Nt(s))return{textDelivered:typeof i=="string"};if($f(s)){if(typeof i!="string"&&r)return{textDelivered:!1};if(typeof i!="string"&&typeof n.acknowledge=="function")return await n.acknowledge(),{textDelivered:!1};typeof i!="string"&&n.acknowledge}else{if(typeof i!="string")throw s;{let a=s instanceof Error?s.message:String(s);`${a}`}}}if(typeof i=="string"&&typeof n.editMessage=="function"){try{await n.editMessage({text:i})}catch(s){if(Nt(s))return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!0};let a=s instanceof Error?s.message:String(s);return`${a}`,typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!0}}return typeof n.clearButtons=="function"&&await n.clearButtons(),{textDelivered:!1}}async function Ef(t){let e=t.respond;if(typeof e.acknowledge!="function")return!1;try{return await e.acknowledge(),!0}catch(n){let r=n instanceof Error?n.message:String(n);return`${r}`,!1}}async function O(t,e){if(t.channel==="telegram"){await t.respond.reply({text:e});return}await t.respond.reply({text:e,ephemeral:!0})}var ts=["plan-approve","plan-request-changes","plan-reject"];function Df(t){switch(t){case"plan-approve":return"Approve";case"plan-request-changes":return"Revise";case"plan-reject":return"Reject";default:return"Continue"}}function Of(t){switch(t){case"plan-approve":return"primary";case"plan-reject":return"danger";default:return"secondary"}}function Wf(t,e){let n=t,o=(typeof n?.listActiveActionTokens=="function"?ts.flatMap(a=>n.listActiveActionTokens?.(a)??[]):[e]).filter(a=>Yr(a.kind)&&a.sessionId===e.sessionId&&(e.planDecisionVersion==null||a.planDecisionVersion==null||a.planDecisionVersion===e.planDecisionVersion)).sort((a,l)=>ts.indexOf(a.kind)-ts.indexOf(l.kind)),i=new Set,s=o.filter(a=>i.has(a.kind)?!1:(i.add(a.kind),!0)).map(a=>({label:typeof a.label=="string"&&a.label.trim()?a.label:Df(a.kind),callbackData:`${ee}:${a.id}`,style:Of(a.kind)}));return s.length>0?[s]:void 0}async function Nf(t,e,n,r){if(t.channel!=="telegram"){await O(t,e);return}let o=Wf(n,r);await t.respond.reply({text:o?`${e}
128
+
129
+ Approval is still pending. Try again below.`:e,...o?{buttons:o}:{}})}function ed(t="telegram",e={}){let n=e.makeAgentMergeTool??Wr,r=e.makeAgentPrTool??Rn;return L("callback_handler_registered",{channel:t,namespace:ee}),{channel:t,namespace:ee,handler:async o=>{let i=await Ef(o);if(!o.auth.isAuthorizedSender)return await O(o,"⛔ Unauthorized."),{handled:!0};let s=_f(o),a=Af(s);if(L("callback_received",{channel:o.channel,namespace:ee,payloadByteLength:Buffer.byteLength(s,"utf8"),tokenHash:Pe(a),isAuthorizedSender:o.auth.isAuthorizedSender}),!a)return await O(o,"⚠️ Unrecognized callback payload."),{handled:!0};if(!v)return await O(o,"⚠️ Code agent service not running."),{handled:!0};let l=v.getActionToken(a);if(L("callback_token_lookup_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),tokenFound:!!l,actionKind:l?.kind,sessionId:l?.sessionId,planDecisionVersion:l?.planDecisionVersion}),!l)return await Z(o,{alreadyAcknowledged:i}),o.channel!=="telegram"&&await O(o,"⚠️ This action is stale or has already been used."),{handled:!0};if(l.kind==="question-answer"&&l.consumedAt!=null)return await Z(o,{alreadyAcknowledged:i}),await O(o,"⚠️ That question button is no longer active. Use the latest question prompt."),{handled:!0};let d=l.sessionId,u=v.resolve?.(d)??v.getPersistedSession?.(d),c=u?.name??d,p=es(l,u);if(L("callback_plan_validation_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),actionKind:l.kind,sessionId:d,sessionName:c,planDecisionVersion:l.planDecisionVersion,valid:!p}),p)return Yr(l.kind)?await Le(o,i):await Z(o,{alreadyAcknowledged:i}),await O(o,`⚠️ ${p}`),{handled:!0};if(l.kind==="question-answer"){if(l.optionIndex==null)return await Z(o,{alreadyAcknowledged:i}),await O(o,"⚠️ Invalid question-answer action."),{handled:!0};if(Xi.has(a))return await O(o,"⚠️ That answer is already being submitted. If the question remains active, try again."),{handled:!0};Xi.add(a);let f=!1;try{f=await v.resolvePendingInputOption(d,l.optionIndex,{requestId:l.pendingInputRequestId,questionId:l.pendingInputQuestionId})}catch(S){let R=S instanceof Error?S.message:String(S);return`${R}`,await O(o,zl),{handled:!0}}finally{Xi.delete(a)}if(!f)return await O(o,zl),{handled:!0};let y=v.consumeActionToken(a);return L("callback_token_consume_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),consumed:!!y,actionKind:y?.kind,sessionId:y?.sessionId,planDecisionVersion:y?.planDecisionVersion}),y?(await Z(o,{alreadyAcknowledged:i}),await O(o,"✅ Answer submitted."),{handled:!0}):(await Z(o,{alreadyAcknowledged:i}),await O(o,"✅ Answer submitted."),{handled:!0})}let g=xf(l);if(g)for(;;){let f=An.get(g);if(!f)break;if(f.tokenId===a)return await Le(o,i),await O(o,"⚠️ This plan decision is already being processed."),{handled:!0};await Zl(f.operation);let y=v.getActionToken(a);if(!y)return await Le(o,i),o.channel!=="telegram"&&await O(o,"⚠️ This action is stale or has already been used."),{handled:!0};if(d=y.sessionId,u=v.resolve?.(d)??v.getPersistedSession?.(d),c=u?.name??d,p=es(y,u),L("callback_plan_validation_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),actionKind:y.kind,sessionId:d,sessionName:c,planDecisionVersion:y.planDecisionVersion,valid:!p,afterPlanDecisionLock:!0}),p)return await Le(o,i),await O(o,`⚠️ ${p}`),{handled:!0};l=y}if(l.kind==="plan-approve"){let f=l,y=!1,S=async(b=!1)=>{y||!b&&o.channel!=="telegram"||(await Le(o,i),y=!0)},R=await Ql(g,a,async()=>(await S(),ve(v,{session:f.sessionId,message:"Approved. Go ahead.",approve:!0,userInitiated:!0})));if(R.isError){let b=v.resolve?.(f.sessionId)??v.getPersistedSession?.(f.sessionId),A=Tf(b);if(A){let k=v.consumeActionToken(a);L("callback_token_consume_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),consumed:!!k,actionKind:k?.kind,sessionId:k?.sessionId??f.sessionId,planDecisionVersion:k?.planDecisionVersion,approvalAppliedAfterError:!0}),await S(!0)}return A?await O(o,`⚠️ ${R.text}`):await Nf(o,`⚠️ ${R.text}`,v,f),{handled:!0}}let I=v.consumeActionToken(a);return L("callback_token_consume_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),consumed:!!I,actionKind:I?.kind,sessionId:I?.sessionId??f.sessionId,planDecisionVersion:I?.planDecisionVersion}),I?(await S(!0),{handled:!0}):(await S(!0),o.channel!=="telegram"&&await O(o,"⚠️ This action is stale or has already been used."),{handled:!0})}if(l.kind==="plan-reject"||l.kind==="plan-request-changes")return await Ql(g,a,async()=>{let f=v.getActionToken(a);if(!f)return await Le(o,i),o.channel!=="telegram"&&await O(o,"⚠️ This action is stale or has already been used."),{handled:!0};d=f.sessionId,u=v.resolve?.(d)??v.getPersistedSession?.(d),c=u?.name??d;let y=es(f,u);if(L("callback_plan_validation_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),actionKind:f.kind,sessionId:d,sessionName:c,planDecisionVersion:f.planDecisionVersion,valid:!y,afterPlanDecisionLock:!0}),y)return await Le(o,i),await O(o,`⚠️ ${y}`),{handled:!0};let S=v.consumeActionToken(a);if(L("callback_token_consume_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),consumed:!!S,actionKind:S?.kind,sessionId:S?.sessionId,planDecisionVersion:S?.planDecisionVersion}),!S)return await Le(o,i),o.channel!=="telegram"&&await O(o,"⚠️ This action is stale or has already been used."),{handled:!0};if(await Le(o,i),S.kind==="plan-reject"){let R=$i(v,d);await O(o,`❌ ${R.text}`)}else{let R=Ei(v,d);await O(o,`✏️ ${R.text}`)}return{handled:!0}});let m=v.consumeActionToken(a);if(L("callback_token_consume_completed",{channel:o.channel,namespace:ee,tokenHash:Pe(a),consumed:!!m,actionKind:m?.kind,sessionId:m?.sessionId,planDecisionVersion:m?.planDecisionVersion}),!m)return await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:l.kind==="plan-offer-start"||l.kind==="plan-offer-dismiss"}),o.channel!=="telegram"&&await O(o,"⚠️ This action is stale or has already been used."),{handled:!0};switch(m.kind){case"worktree-merge":{let f=await n().execute("callback",{session:d}),y=Jr(f);if(Jl(f)){await zr(o,i);break}await O(o,y);break}case"worktree-decide-later":{let f=v.snoozeWorktreeDecision(d,{notifyUser:!1});if(ns(f)){let S=`⏭️ Snoozed 24h for [${c}]`;await zr(o,i),await O(o,S)}else await O(o,f);break}case"worktree-dismiss":{let f=await v.dismissWorktree(d),y=ns(f);y&&await zr(o,i),await O(o,y?"✅ Discarded":f);break}case"worktree-create-pr":case"worktree-update-pr":{let f=await r().execute("callback",{session:d}),y=Jr(f);if(Jl(f)){await zr(o,i);break}await O(o,y);break}case"worktree-view-pr":{await Z(o,{alreadyAcknowledged:i});let f=v.getPersistedSession?.(d),y=l.targetUrl??f?.worktreePrUrl;await O(o,y?`PR: ${y}`:"⚠️ PR URL is no longer available.");break}case"plan-offer-start":{if(!m.launchPrompt||!m.launchWorkdir){await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,"⚠️ This action is missing the plan launch context.");break}let f;try{f=v.launchPlanOffer({route:m.route,prompt:m.launchPrompt,workdir:m.launchWorkdir,name:m.launchName,worktreeStrategy:m.launchWorktreeStrategy})}catch(y){let S=y instanceof Error?y.message:String(y);await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,`⚠️ Failed to start planning session: ${S}`);break}await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,`▶️ Planning session started: ${f.name} [${f.id}]`);break}case"plan-offer-dismiss":{await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,"✅ Dismissed.");break}case"repo-policy-set":{if(!m.repoPolicy||!m.repoPolicyWorkdir){await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,"⚠️ This action is missing the repo policy context.");break}if(!m.launchPrompt||!m.launchWorkdir){await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,"⚠️ This action is missing the launch context.");break}if(typeof v.resolveRepoPolicy=="function"){let S=v.resolveRepoPolicy(m.repoPolicyWorkdir);if(S.identity){let R=Et(m.repoPolicy,S.prAvailable);if(R){await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,`⚠️ ${R}`);break}}}let f=v.setRepoPolicy(m.repoPolicyWorkdir,m.repoPolicy);if(!f){await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,`⚠️ Could not resolve a git repository for ${m.repoPolicyWorkdir}.`);break}v.clearRepoPolicyChoiceTokens(m.sessionId);let y;try{y=v.launchAfterRepoPolicyChoice({route:m.route,prompt:m.launchPrompt,workdir:m.launchWorkdir,name:m.launchName,model:m.launchModel,reasoningEffort:m.launchReasoningEffort,fastMode:m.launchFastMode,systemPrompt:m.launchSystemPrompt,allowedTools:m.launchAllowedTools,resumeSessionId:m.launchResumeSessionId,resumeWorktreeFrom:m.launchResumeWorktreeFrom,sessionIdOverride:m.launchSessionIdOverride,clearedPersistedCodexResume:m.launchClearedPersistedCodexResume,forkSession:m.launchForkSession,forceNewSession:m.launchForceNewSession,permissionMode:m.launchPermissionMode,planApproval:m.launchPlanApproval,harness:m.launchHarness,worktreeStrategy:m.launchWorktreeStrategy,worktreeBaseBranch:m.launchWorktreeBaseBranch,worktreePrTargetRepo:m.launchWorktreePrTargetRepo,originAgentId:m.launchOriginAgentId}).text}catch(S){let R=S instanceof Error?S.message:String(S);await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,`⚠️ Repo policy saved, but launch failed: ${R}`);break}await Z(o,{alreadyAcknowledged:i,forceTelegramMarkupEdit:!0}),await O(o,[`✅ Repo policy saved: ${bl(f.policy).title}.`,"",y].join(`
130
+ `));break}case"session-restart":case"session-resume":{await Z(o,{alreadyAcknowledged:i});let f=await ve(v,{session:d,message:"Continue where you left off.",userInitiated:!0});await O(o,f.isError?`⚠️ ${f.text}`:`▶️ ${f.text}`);break}case"view-output":{await Z(o,{alreadyAcknowledged:i});let f=await Ir().execute("callback",{session:d,lines:50});await O(o,Jr(f));break}default:{await Z(o,{alreadyAcknowledged:i}),await O(o,"⚠️ Unknown callback action.");break}}return{handled:!0}}}}B();se();function Lt(t){return td(t).map(e=>e.value)}function td(t){return Array.from(t.matchAll(/"[^"]*"|'[^']*'|\S+/g),e=>{let n=e[0],r=e.index??0;return{value:Lf(n),raw:n,start:r,end:r+n.length}})}function lt(t){let[e]=td(t);if(e)return{value:e.value,rest:t.slice(e.end).trimStart()}}function Lf(t){return t.length>1&&(t.startsWith('"')&&t.endsWith('"')||t.startsWith("'")&&t.endsWith("'"))?t.slice(1,-1):t}function Bf(t){return t instanceof Error?t.message:String(t)}function Ff(t){let e=Lt(t),n,r=e;return e[0]==="--name"&&e[1]&&(n=e[1],r=e.slice(2)),{name:n,prompt:r.join(" ").trim()}}function nd(t){t.registerCommand({name:"agent",description:"Launch a coding agent session. Usage: /agent [--name <name>] <prompt>",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!v)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=(e.args??"").trim();if(!n)return{text:"Usage: /agent [--name <name>] <prompt>"};let{name:r,prompt:o}=Ff(n);if(!o)return{text:"Usage: /agent [--name <name>] <prompt>"};try{let i=Xn({prompt:o,name:r},e,v);if(i.kind!=="resolved")return{text:i.text};let s=v.spawn({prompt:o,name:r,workdir:i.workdir,model:i.resolvedModel,reasoningEffort:i.reasoningEffort,fastMode:i.fastMode,codexApprovalPolicy:i.harness==="codex"?"never":void 0,originChannel:i.originChannel,originThreadId:i.originThreadId,originAgentId:e.agentId||void 0,originSessionKey:i.originSessionKey,route:i.route,harness:i.harness,permissionMode:i.permissionMode,planApproval:i.planApproval,taskLifecycle:or(e)});return{text:v.formatLaunchResult({prompt:o,workdir:i.workdir,harness:i.harness,permissionMode:i.permissionMode??D.permissionMode,planApproval:i.planApproval},s)}}catch(i){let s=Bf(i),a=s.includes("Max sessions")?"":`
131
+
132
+ Use /agent_sessions to see active sessions.`;return{text:`Error launching session: ${s}${a}`}}}})}B();function rd(t){t.registerCommand({name:"agent_sessions",description:"List coding agent sessions. Usage: /agent_sessions [--full]",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!v)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=(e.args??"").split(/\s+/).includes("--full");return{text:Rr(v,"all",void 0,{full:n})}}})}B();function od(t){t.registerCommand({name:"agent_kill",description:"Kill a coding agent session by name or ID",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!v)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=e.args?.trim();return n?{text:Ar(v,n,"killed")}:{text:"Usage: /agent_kill <name-or-id>"}}})}B();function id(t){t.registerCommand({name:"agent_respond",description:"Send a follow-up message to a running coding agent session. Usage: /agent_respond <id-or-name> <message>",acceptsArgs:!0,requireAuth:!0,handler:async e=>{if(!v)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=(e.args??"").trim();if(!n)return{text:`Usage: /agent_respond <id-or-name> <message>
133
+ /agent_respond --interrupt <id-or-name> <message>`};let r=!1,o=n,i=lt(o);i?.value==="--interrupt"&&(r=!0,o=i.rest);let s=lt(o);if(!s)return{text:"Error: Missing message. Usage: /agent_respond <id-or-name> <message>"};let a=s.value,l=s.rest;return l.trim()?{text:(await ve(v,{session:a,message:l,interrupt:r,userInitiated:!0})).text}:{text:"Error: Empty message. Usage: /agent_respond <id-or-name> <message>"}}})}B();function sd(t){t.registerCommand({name:"agent_stats",description:"Show OpenClaw Code Agent usage metrics",acceptsArgs:!1,requireAuth:!0,handler:()=>{if(!v)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let e=v.getMetrics(),n=v.list("running").length;return{text:tr(e,n)}}})}B();function qf(t){return t==="pr-required"||t==="pr-allowed"||t==="never-pr"||t==="manual"}function ad(t){t.registerCommand({name:"agent_policy",description:"Inspect or set the current repo integration policy. Usage: /agent_policy [pr-required|pr-allowed|never-pr|manual|reset|list|cleanup]",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!v)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let r=lt((e.args??"").trim())?.value;if(r==="list"){let a=v.listRepoPolicies();return{text:a.length===0?"No stored repo policies.":a.map(l=>`${l.policy} | ${l.provider} | ${l.repoRoot}`).join(`
134
+ `)}}if(r==="cleanup"){let a=v.cleanupRepoPolicies();return{text:a.length===0?"No stale repo policies found.":[`Removed ${a.length} stale repo ${a.length===1?"policy":"policies"}.`,...a.map(l=>`${l.policy} | ${l.provider} | ${l.repoRoot}`)].join(`
135
+ `)}}let o=e.workspaceDir;if(!o)return{text:"Error: workspaceDir is required."};if(r==="reset")return{text:v.resetRepoPolicy(o)?`Repo policy reset for ${o}.`:`No stored repo policy found for ${o}.`};if(r&&qf(r)){if(typeof v.resolveRepoPolicy=="function"){let d=v.resolveRepoPolicy(o);if(d.identity){let u=Et(r,d.prAvailable);if(u)return{text:`Error: ${u}`}}}let a=v.setRepoPolicy(o,r);if(!a)return{text:`Error: ${o} is not a git repository.`};let l=`Repo policy set to ${a.policy} for ${a.repoRoot}.`;try{if(typeof v.continueLaunchAfterManualRepoPolicy!="function")return{text:l};let d=v.continueLaunchAfterManualRepoPolicy(a.repoRoot,r);if(d.kind==="launched")return{text:[l,"",d.text].join(`
136
+ `)};if(d.kind==="ambiguous")return{text:[l,"",`Repo policy saved, but ${d.count} pending launches match this policy. Run the intended launch again to avoid starting the wrong session.`].join(`
137
+ `)}}catch(d){let u=d instanceof Error?d.message:String(d);return{text:[l,"",`Repo policy saved, but the deferred launch failed: ${u}`,"The pending launch context was kept so you can retry the same /agent_policy command or run the intended launch again."].join(`
138
+ `)}}return{text:l}}let i=v.resolveRepoPolicy(o);if(!i.identity)return{text:`No git repository found for ${o}.`};let s=hn(i.prAvailable).map(a=>a.policy).join(", ");return{text:[`Repo policy: ${i.policy??"unknown"}`,`Repo: ${i.identity.repoRoot}`,`Provider: ${i.provider}${i.prAvailable?"":" (PR automation unavailable)"}`,...i.identity.remoteUrl?[`Remote: ${i.identity.remoteUrl}`]:[],"",`Set with /agent_policy ${s}.`].join(`
139
+ `)}}})}B();var Kf=50;function ld(t){t.registerCommand({name:"agent_output",description:"Show recent output from a coding agent session. Usage: /agent_output <id-or-name> [--full] [--lines N]",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!v)return{text:"Error: SessionManager not initialized. The code-agent service must be running."};let n=(e.args??"").trim();if(!n)return{text:"Usage: /agent_output <id-or-name> [--full] [--lines N]"};let r=Lt(n),o="",i=!1,s=Kf;for(let l=0;l<r.length;l++)if(r[l]==="--full")i=!0;else if(r[l]==="--lines"&&l+1<r.length){let d=parseInt(r[l+1],10);!isNaN(d)&&d>0&&(s=d),l++}else o||(o=r[l]);return o?{text:br(v,o,{full:i,lines:s})}:{text:"Usage: /agent_output <id-or-name> [--full] [--lines N]"}}})}B();var dd="Usage: /goal [--name <name>] [--workdir <dir>] [--model <model>] [--harness <name>] [--mode <ralph|verifier>] [--completion-promise <text>] [--max-iterations N] [--verify <cmd> ...] <goal>";function ud(t){t.registerCommand({name:"goal",description:"Launch an explicit goal task (Ralph-style completion loop or verifier-driven loop)",acceptsArgs:!0,requireAuth:!0,handler:async e=>{if(!z)return{text:"Error: GoalController not initialized. The code-agent service must be running."};let n=(e.args??"").trim();if(!n)return{text:dd};let r=Lt(n),o,i,s,a,l="bypassPermissions",d,u,c,p=[],g=[];for(let y=0;y<r.length;y++){let S=r[y];if(S==="--name"&&y+1<r.length)o=r[++y];else if(S==="--workdir"&&y+1<r.length)i=r[++y];else if(S==="--model"&&y+1<r.length)s=r[++y];else if(S==="--max-iterations"&&y+1<r.length){let R=parseInt(r[++y],10);!Number.isNaN(R)&&R>0&&(a=R)}else if(S==="--permission-mode"&&y+1<r.length){let R=r[++y];if(R==="default"||R==="plan"||R==="bypassPermissions")l=R;else return{text:`Error: Invalid permission mode "${R}".`}}else if(S==="--harness"&&y+1<r.length)d=r[++y];else if(S==="--mode"&&y+1<r.length){let R=r[++y];if(R==="ralph"||R==="verifier")u=R;else return{text:`Error: Invalid goal mode "${R}". Use ralph or verifier.`}}else if(S==="--completion-promise"&&y+1<r.length)c=r[++y];else if(S==="--verify"&&y+1<r.length){let R=r[++y].trim();if(!R)return{text:"Error: --verify commands must not be empty."};p.push(R)}else g.push(S)}let m=g.join(" ").trim();if(!m)return{text:dd};let f=Kr({goal:m,verifierCommands:p,name:o,workdir:i,model:s,maxIterations:a,permissionMode:l,harness:d,goalMode:u,completionPromise:c},e);if(f.kind!=="resolved")return{text:f.text};try{let y=await z.launchTask({goal:f.goal,name:f.name,workdir:f.workdir,model:f.model,reasoningEffort:f.reasoningEffort,fastMode:f.fastMode,maxIterations:f.maxIterations,permissionMode:f.permissionMode,harness:f.harness,loopMode:f.loopMode,completionPromise:f.completionPromise,originChannel:f.originChannel,originThreadId:f.originThreadId,originAgentId:f.originAgentId,originSessionKey:f.originSessionKey,route:f.route,verifierCommands:f.verifierCommands});return{text:Ur(y,f)}}catch(y){return{text:`Error launching goal task: ${y instanceof Error?y.message:String(y)}`}}}})}B();function cd(t){t.registerCommand({name:"goal_status",description:"Show one goal task or list all explicit goal tasks. Usage: /goal_status [<task-id-or-name>]",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!z)return{text:we};let n=(e.args??"").trim();return{text:Gr(z,r=>v?.resolve(r),n)}}})}B();function pd(t){t.registerCommand({name:"goal_stop",description:"Stop a goal task. Usage: /goal_stop <task-id-or-name>",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!z)return{text:we};let n=(e.args??"").trim();if(!n)return{text:"Usage: /goal_stop <task-id-or-name>"};let r=z.stopTask(n);return{text:jr(r,n)}}})}B();var md="Usage: /goal_edit <task-id-or-name> <replacement-goal>";function fd(t){t.registerCommand({name:"goal_edit",description:"Edit a running goal task. Usage: /goal_edit <task-id-or-name> <replacement-goal>",acceptsArgs:!0,requireAuth:!0,handler:e=>{if(!z)return{text:we};let n=(e.args??"").trim();if(!n)return{text:md};let r=lt(n),o=r?.value.trim(),i=r?.rest.trim();if(!o||!i)return{text:md};let s=z.editTask(o,i);return{text:Hr(s,o)}}})}import{execFile as ng}from"child_process";import{createHash as Cd}from"crypto";import{existsSync as In,mkdirSync as Uf,readFileSync as Vf,renameSync as yd,writeFileSync as Gf}from"fs";import{homedir as jf}from"os";import{dirname as Hf,join as kd}from"path";var zf=new Set(["running","waiting_for_session","waiting_for_user","succeeded","failed","stopped"]);function Qf(t){let e=t.OPENCLAW_HOME?.trim();return e||kd(jf(),".openclaw")}function Jf(t){let e=t.OPENCLAW_CODE_AGENT_GOAL_TASKS_PATH?.trim();return e||kd(Qf(t),"code-agent-goal-tasks.json")}function Sd(t){return t instanceof Error?t.message:String(t)}function vd(t){return!!t&&typeof t=="object"&&!Array.isArray(t)}var Yf=100;function gd(t,e,n){let r=n==null?"":`-${n}`;return`${t}.invalid-${e}${r}.json`}function Zf(t){if(!In(t))return;let e=Date.now(),n=gd(t,e);if(!In(n))return n;for(let r=1;r<=Yf;r+=1){let o=gd(t,e,r);if(!In(o))return o}}function hd(t,e){try{let n=Zf(t);return n?(yd(t,n),`${e}${n}`,!0):(In(t),!1)}catch(n){return`${Sd(n)}`,!1}}function Xf(t){if(!vd(t))return;let e=t;if(!(typeof e.provider!="string"||typeof e.target!="string"))return{provider:e.provider,target:e.target,accountId:typeof e.accountId=="string"?e.accountId:void 0,threadId:typeof e.threadId=="string"?e.threadId:void 0,sessionKey:typeof e.sessionKey=="string"?e.sessionKey:void 0}}function eg(t){if(!vd(t))return;let e=t;if(typeof e.id!="string"||typeof e.name!="string"||typeof e.goal!="string"||typeof e.workdir!="string"||typeof e.status!="string"||!zf.has(e.status))return;let n=e.status,r=n==="running"||n==="waiting_for_session"?"waiting_for_session":n;return{id:e.id,name:e.name,goal:e.goal,workdir:e.workdir,status:r,createdAt:typeof e.createdAt=="number"?e.createdAt:Date.now(),updatedAt:typeof e.updatedAt=="number"?e.updatedAt:Date.now(),iteration:typeof e.iteration=="number"?e.iteration:0,maxIterations:typeof e.maxIterations=="number"?e.maxIterations:8,sessionId:typeof e.sessionId=="string"?e.sessionId:void 0,sessionName:typeof e.sessionName=="string"?e.sessionName:void 0,harnessSessionId:typeof e.harnessSessionId=="string"?e.harnessSessionId:void 0,model:typeof e.model=="string"?e.model:void 0,reasoningEffort:typeof e.reasoningEffort=="string"?e.reasoningEffort:void 0,fastMode:e.fastMode===!0?!0:void 0,systemPrompt:typeof e.systemPrompt=="string"?e.systemPrompt:void 0,allowedTools:Array.isArray(e.allowedTools)?e.allowedTools.filter(o=>typeof o=="string"):void 0,originChannel:typeof e.originChannel=="string"?e.originChannel:void 0,originThreadId:typeof e.originThreadId=="string"||typeof e.originThreadId=="number"?e.originThreadId:void 0,originAgentId:typeof e.originAgentId=="string"?e.originAgentId:void 0,originSessionKey:typeof e.originSessionKey=="string"?e.originSessionKey:void 0,route:Xf(e.route),harness:typeof e.harness=="string"?e.harness:void 0,permissionMode:typeof e.permissionMode=="string"?e.permissionMode:void 0,loopMode:e.loopMode==="ralph"?"ralph":"verifier",completionPromise:typeof e.completionPromise=="string"?e.completionPromise:void 0,verifierCommands:Array.isArray(e.verifierCommands)?e.verifierCommands.filter(o=>!!o&&typeof o=="object"&&typeof o.label=="string"&&typeof o.command=="string"):[],lastVerifierSummary:typeof e.lastVerifierSummary=="string"?e.lastVerifierSummary:void 0,lastVerifierFingerprint:typeof e.lastVerifierFingerprint=="string"?e.lastVerifierFingerprint:void 0,repeatedFailureCount:typeof e.repeatedFailureCount=="number"?e.repeatedFailureCount:0,waitingForUserReason:typeof e.waitingForUserReason=="string"?e.waitingForUserReason:void 0,failureReason:typeof e.failureReason=="string"?e.failureReason:void 0}}function tg(t){if(!Array.isArray(t))return;let e=[];for(let n of t){let r=eg(n);if(!r)return;e.push(r)}return e}var Zr=class{path;tasks=new Map;constructor(e=process.env){this.path=Jf(e),this.load()}load(){try{if(!In(this.path))return;let e=Vf(this.path,"utf8"),n=JSON.parse(e),r=tg(n);if(!r){hd(this.path,"invalid")&&this.save();return}this.tasks.clear();for(let o of r)this.tasks.set(o.id,o);this.save()}catch(e){if(e.code==="ENOENT")return;hd(this.path,"corrupt or unreadable")&&this.save()}}save(){try{Uf(Hf(this.path),{recursive:!0});let e=`${this.path}.tmp`;Gf(e,JSON.stringify([...this.tasks.values()],null,2),"utf8"),yd(e,this.path)}catch(e){`${this.path}${Sd(e)}`}}upsert(e){this.tasks.set(e.id,e),this.save()}get(e){let n=this.tasks.get(e);return n||[...this.tasks.values()].find(r=>r.name===e)}list(){return[...this.tasks.values()].sort((e,n)=>n.createdAt-e.createdAt)}};Re();var rg=8,Md=600*1e3,og=4e3,rs=1200,ig="DONE",sg=["BASH_ENV","ENV"];function ag(t){return t.toLowerCase().replace(/[^a-z0-9]+/g,"-").replace(/^-+|-+$/g,"").slice(0,48)||"goal-task"}function Bt(t,e){return t.length<=e?t:`${t.slice(0,e-3)}...`}function ze(t,e=20){let n=t.split(/\r?\n/).map(r=>r.trimEnd()).filter(r=>r.trim().length>0);return n.length<=e?n.join(`
138
140
  `):n.slice(-e).join(`
139
- `)}function Gf(t){let e=(t??"").split(/\r?\n/).map(n=>n.trim()).filter(n=>n.length>0).filter(n=>!/^Iteration summary:$/i.test(n)).map(n=>n.replace(/^[-*]\s+/,""));return e.length>0?e.join(`
140
- `):void 0}function dd(t){return t.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")}function ud(t){let e=t?.trim();return e&&e.length>0?e:Uf}function jf(t){return t.route??zt(t.originChannel,t.originThreadId,t.originSessionKey)}function Yi(t){return t.map((e,n)=>({label:e.label.trim()||`check-${n+1}`,command:e.command.trim(),timeoutMs:e.timeoutMs??kd})).filter(e=>e.command.length>0)}function Hf(t){return t.loopMode==="verifier"}function zf(t){return Yi(t.verifierCommands).length>0}function cd(t){return Hf(t)&&!zf(t)}function Qr(){return"Verifier-mode goal tasks require at least one verifier command."}function pd(t){let e=t.steps.filter(n=>!n.ok).map(n=>`${n.label}:${n.exitCode}:${je(n.output,12)}`).join(`
141
- `);return yd("sha1").update(e).digest("hex")}function Qf(t){return yd("sha1").update(je(t,24)).digest("hex")}function md(t){let e=t.toLowerCase().replace(/\s+/g," ").trim();if(!e)return;if(/\b(can i|may i|should i|do you want me to|would you like me to)\b/.test(e)&&/\b(read|write|edit|modify|change|inspect|search|run|execute|install|delete|move|rename|open)\b/.test(e))return"Yes, proceed.";if(/\b(should i continue|shall i continue|want me to continue|should i proceed|shall i proceed|can i proceed|go ahead)\b/.test(e))return"Yes, continue."}function Jf(t){if(t.loopMode==="ralph")return["You are working inside a Ralph Wiggum-style autonomous loop.","","Goal:",t.goal,"","Loop rules:","- Keep making concrete progress toward the goal in this repository.","- An external controller will continue looping until you emit the completion promise or the iteration budget is exhausted.",`- When the goal is truly complete, output this exact marker on its own line: <promise>${t.completionPromise}</promise>`,"- Do not output that completion marker early, approximately, or with altered spelling.","- If you are not done yet, do not emit the completion marker.","- Do not ask to stop or wait for confirmation unless blocked by a real product, architecture, credential, or approval decision.","- Re-run useful local checks before ending each turn.",t.verifierCommands.length>0?"- External verifier commands will also be run after you claim completion.":"- There may not be external verifiers, so your completion promise is the success gate."].join(`
141
+ `)}function lg(t){let e=(t??"").split(/\r?\n/).map(n=>n.trim()).filter(n=>n.length>0).filter(n=>!/^Iteration summary:$/i.test(n)).map(n=>n.replace(/^[-*]\s+/,""));return e.length>0?e.join(`
142
+ `):void 0}function wd(t){return t.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")}function Pd(t){let e=t?.trim();return e&&e.length>0?e:ig}function dg(t){return t.route??Qt(t.originChannel,t.originThreadId,t.originSessionKey)}function os(t){return t.map((e,n)=>({label:e.label.trim()||`check-${n+1}`,command:e.command.trim(),timeoutMs:e.timeoutMs??Md})).filter(e=>e.command.length>0)}function ug(t){return t.loopMode==="verifier"}function cg(t){return os(t.verifierCommands).length>0}function bd(t){return ug(t)&&!cg(t)}function Xr(){return"Verifier-mode goal tasks require at least one verifier command."}function Rd(t){let e=t.steps.filter(n=>!n.ok).map(n=>`${n.label}:${n.exitCode}:${ze(n.output,12)}`).join(`
143
+ `);return Cd("sha1").update(e).digest("hex")}function pg(t){return Cd("sha1").update(ze(t,24)).digest("hex")}function Ad(t){let e=t.toLowerCase().replace(/\s+/g," ").trim();if(!e)return;if(/\b(can i|may i|should i|do you want me to|would you like me to)\b/.test(e)&&/\b(read|write|edit|modify|change|inspect|search|run|execute|install|delete|move|rename|open)\b/.test(e))return"Yes, proceed.";if(/\b(should i continue|shall i continue|want me to continue|should i proceed|shall i proceed|can i proceed|go ahead)\b/.test(e))return"Yes, continue."}function mg(t){if(t.loopMode==="ralph")return["You are working inside a Ralph Wiggum-style autonomous loop.","","Goal:",t.goal,"","Loop rules:","- Keep making concrete progress toward the goal in this repository.","- An external controller will continue looping until you emit the completion promise or the iteration budget is exhausted.",`- When the goal is truly complete, output this exact marker on its own line: <promise>${t.completionPromise}</promise>`,"- Do not output that completion marker early, approximately, or with altered spelling.","- If you are not done yet, do not emit the completion marker.","- Do not ask to stop or wait for confirmation unless blocked by a real product, architecture, credential, or approval decision.","- Re-run useful local checks before ending each turn.",t.verifierCommands.length>0?"- External verifier commands will also be run after you claim completion.":"- There may not be external verifiers, so your completion promise is the success gate."].join(`
142
144
  `);let e=t.verifierCommands.map(n=>`- ${n.label}: ${n.command}`).join(`
143
145
  `);return["You are working on an autonomous goal-driven task.","","Goal:",t.goal,"","Working rules:","- Make concrete progress toward the goal in this repository.","- An external controller will run these verifier commands after your turn:",e,"- If any verifier fails, you will receive the exact failures and must continue fixing the remaining gaps.","- Do not stop early just because you think the task is probably done.","- Do not ask for confirmation unless you are blocked by a real product, architecture, or credential decision.","- Before ending a turn, run any local checks you think are useful."].join(`
144
- `)}function fd(t){return t.loopMode==="ralph"?["The OpenClaw gateway restarted while this Ralph-style goal task was running.","Resume from the prior session context and continue immediately.","","Goal:",t.goal,"","Instructions:","- Continue from the current repo state and prior session context without restarting from scratch.",`- Only emit <promise>${t.completionPromise}</promise> when the goal is actually complete.`,"- The external controller will keep looping until that marker appears or the iteration budget is exhausted.","- Do not ask for confirmation just because the gateway restarted."].join(`
146
+ `)}function Id(t){return t.loopMode==="ralph"?["The OpenClaw gateway restarted while this Ralph-style goal task was running.","Resume from the prior session context and continue immediately.","","Goal:",t.goal,"","Instructions:","- Continue from the current repo state and prior session context without restarting from scratch.",`- Only emit <promise>${t.completionPromise}</promise> when the goal is actually complete.`,"- The external controller will keep looping until that marker appears or the iteration budget is exhausted.","- Do not ask for confirmation just because the gateway restarted."].join(`
145
147
  `):["The OpenClaw gateway restarted while this autonomous goal task was running.","Resume from the prior session context and continue toward the same goal immediately.","","Goal:",t.goal,"","Instructions:","- Re-orient yourself from the existing repo state and prior session context.","- Continue the task without restarting from scratch unless the prior approach is clearly invalid.","- The external controller will continue running verifier commands after your turns.","- Do not ask for confirmation just because the gateway restarted."].join(`
146
- `)}function Yf(t,e){let n=e.steps.filter(o=>!o.ok).map(o=>[`- ${o.label} failed (exit ${o.exitCode})`,je(o.output,18)].join(`
148
+ `)}function fg(t,e){let n=e.steps.filter(o=>!o.ok).map(o=>[`- ${o.label} failed (exit ${o.exitCode})`,ze(o.output,18)].join(`
147
149
  `)).join(`
148
150
 
149
151
  `);return["The external verifier did not pass.",t.repeatedFailureCount>=2?"The same verifier fingerprint has repeated. Use a different debugging strategy than your previous attempt.":"Fix only the remaining issues from the verifier output below.","","Goal:",t.goal,"","Verifier failures:",n,"","Instructions:","- Continue from the current code state and prior session context.","- Make the minimum necessary changes to satisfy the remaining verifier failures.","- Re-run relevant checks yourself before ending the turn.","- Do not ask for confirmation unless you are truly blocked on a human decision."].join(`
150
- `)}function Zf(t,e){let n=je(e,18)||"(no meaningful output)",r=t.repeatedFailureCount>=2?"The loop has repeated without converging. Use a different strategy than the previous attempt.":"Continue from the current repo state and prior session context.";return["Continue the same Ralph-style goal task.","","Goal:",t.goal,"","Status:",`- The last turn ended without the completion promise <promise>${t.completionPromise}</promise>.`,`- Current iteration: ${t.iteration}/${t.maxIterations}.`,`- ${r}`,"","Latest output / blockers:",n,"","Instructions:","- Keep working until the goal is actually complete.",`- Only emit <promise>${t.completionPromise}</promise> when all requested work is done.`,"- If you are not done, do not emit the completion promise.",t.verifierCommands.length>0?"- If you believe you are done, make sure the expected verifiers are likely to pass before emitting the completion promise.":"- There may not be external verifiers, so your completion promise is the success signal."].join(`
151
- `)}function Xf(t,e){let n=e.steps.filter(r=>!r.ok).map(r=>[`- ${r.label} failed (exit ${r.exitCode})`,je(r.output,18)].join(`
152
+ `)}function gg(t,e){let n=ze(e,18)||"(no meaningful output)",r=t.repeatedFailureCount>=2?"The loop has repeated without converging. Use a different strategy than the previous attempt.":"Continue from the current repo state and prior session context.";return["Continue the same Ralph-style goal task.","","Goal:",t.goal,"","Status:",`- The last turn ended without the completion promise <promise>${t.completionPromise}</promise>.`,`- Current iteration: ${t.iteration}/${t.maxIterations}.`,`- ${r}`,"","Latest output / blockers:",n,"","Instructions:","- Keep working until the goal is actually complete.",`- Only emit <promise>${t.completionPromise}</promise> when all requested work is done.`,"- If you are not done, do not emit the completion promise.",t.verifierCommands.length>0?"- If you believe you are done, make sure the expected verifiers are likely to pass before emitting the completion promise.":"- There may not be external verifiers, so your completion promise is the success signal."].join(`
153
+ `)}function hg(t,e){let n=e.steps.filter(r=>!r.ok).map(r=>[`- ${r.label} failed (exit ${r.exitCode})`,ze(r.output,18)].join(`
152
154
  `)).join(`
153
155
 
154
156
  `);return["You emitted the completion promise, but the external verifiers did not pass.","","Goal:",t.goal,"","Verifier failures:",n,"","Instructions:","- Continue from the current repo state and fix only the remaining gaps.",`- Do not emit <promise>${t.completionPromise}</promise> again until the goal is fully complete and the failing checks are addressed.`,"- Re-run relevant checks yourself before ending the turn."].join(`
155
- `)}function eg(t,e){let n=e.trim();if(!n)return!1;let r=new RegExp(`(^|\\n)\\s*${dd(n)}\\s*(\\n|$)`,"i"),o=new RegExp(`<promise>\\s*${dd(n)}\\s*<\\/promise>`,"i");return r.test(t)||o.test(t)}function gd(t){return t.steps.map(e=>`${e.ok?"PASS":"FAIL"} ${e.label} (exit ${e.exitCode}, ${Math.round(e.durationMs)}ms)`).join(`
156
- `)}function at(t){return t instanceof Error?t.message:String(t)}function hd(t){return t==="succeeded"||t==="failed"||t==="stopped"}function tg(t){return Lt(t.error?.trim()||"Underlying session failed.",Ji)}function ng(t=process.env){let e={...t};for(let n of Kf)delete e[n];return e}function rg(t,e){return new Promise(n=>{let r=Date.now();Ff("bash",["-lc",e.command],{cwd:t,timeout:e.timeoutMs??kd,maxBuffer:1024*1024,env:ng()},(o,i,s)=>{let l=Date.now()-r,a=typeof o?.code=="number"?o.code:o?1:0,d=`${i??""}${s?`
157
- ${s}`:""}`.trim();n({label:e.label,command:e.command,ok:!o,exitCode:a,durationMs:l,output:Lt(d||"(no output)",qf)})})})}var Jr=class{store;sessionManager;restorePromise=null;inFlight=new Set;observerDisposers=new Map;scheduledEvaluations=new Map;dirtyEvaluations=new Set;dirtyEvaluationSessionIds=new Map;started=!1;constructor(e){this.sessionManager=e,this.store=new zr}start(){this.started||(this.started=!0,!this.restorePromise&&(this.restorePromise=this.restoreRecoverableTasks().catch(e=>{`${at(e)}`}).finally(()=>{this.restorePromise=null})))}stop(){this.started=!1,this.clearScheduledEvaluations(),this.detachSessionObservers(),this.captureRecoverableTasks(),this.store.save()}listTasks(){return this.store.list()}getTask(e){return this.store.get(e)}async launchTask(e){let n=e.loopMode??"verifier",r=Yi(e.verifierCommands);if(n==="verifier"&&r.length===0)throw new Error(Qr());let i={id:rr(8),name:Vf(e.name??e.goal),goal:e.goal.trim(),workdir:e.workdir,status:"waiting_for_session",createdAt:Date.now(),updatedAt:Date.now(),iteration:0,maxIterations:e.maxIterations??Bf,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,systemPrompt:e.systemPrompt,allowedTools:e.allowedTools,originChannel:e.originChannel,originThreadId:e.originThreadId,originAgentId:e.originAgentId,originSessionKey:e.originSessionKey,route:e.route,harness:e.harness,permissionMode:e.permissionMode??"bypassPermissions",loopMode:n,completionPromise:ud(e.completionPromise),verifierCommands:r,repeatedFailureCount:0},s=await this.spawnTaskSession(i,Jf(i));return this.attachSessionObservers(i,s),i.sessionId=s.id,i.sessionName=s.name,i.harnessSessionId=s.harnessSessionId,i.status="running",i.updatedAt=Date.now(),this.store.upsert(i),this.scheduleTaskEvaluation(i.id,"launch",s.id),this.notify(i,`🎯 [${i.name}] Goal task started
157
+ `)}function yg(t,e){let n=e.trim();if(!n)return!1;let r=new RegExp(`(^|\\n)\\s*${wd(n)}\\s*(\\n|$)`,"i"),o=new RegExp(`<promise>\\s*${wd(n)}\\s*<\\/promise>`,"i");return r.test(t)||o.test(t)}function xd(t){return t.steps.map(e=>`${e.ok?"PASS":"FAIL"} ${e.label} (exit ${e.exitCode}, ${Math.round(e.durationMs)}ms)`).join(`
158
+ `)}function dt(t){return t instanceof Error?t.message:String(t)}function Td(t){return t==="succeeded"||t==="failed"||t==="stopped"}function kg(t){return Bt(t.error?.trim()||"Underlying session failed.",rs)}function Sg(t=process.env){let e={...t};for(let n of sg)delete e[n];return e}function vg(t,e){return new Promise(n=>{let r=Date.now();ng("bash",["-lc",e.command],{cwd:t,timeout:e.timeoutMs??Md,maxBuffer:1024*1024,env:Sg()},(o,i,s)=>{let a=Date.now()-r,l=typeof o?.code=="number"?o.code:o?1:0,d=`${i??""}${s?`
159
+ ${s}`:""}`.trim();n({label:e.label,command:e.command,ok:!o,exitCode:l,durationMs:a,output:Bt(d||"(no output)",og)})})})}var eo=class{store;sessionManager;restorePromise=null;inFlight=new Set;observerDisposers=new Map;scheduledEvaluations=new Map;dirtyEvaluations=new Set;dirtyEvaluationSessionIds=new Map;started=!1;constructor(e){this.sessionManager=e,this.store=new Zr}start(){this.started||(this.started=!0,!this.restorePromise&&(this.restorePromise=this.restoreRecoverableTasks().catch(e=>{`${dt(e)}`}).finally(()=>{this.restorePromise=null})))}stop(){this.started=!1,this.clearScheduledEvaluations(),this.detachSessionObservers(),this.captureRecoverableTasks(),this.store.save()}listTasks(){return this.store.list()}getTask(e){return this.store.get(e)}async launchTask(e){let n=e.loopMode??"verifier",r=os(e.verifierCommands);if(n==="verifier"&&r.length===0)throw new Error(Xr());let i={id:ir(8),name:ag(e.name??e.goal),goal:e.goal.trim(),workdir:e.workdir,status:"waiting_for_session",createdAt:Date.now(),updatedAt:Date.now(),iteration:0,maxIterations:e.maxIterations??rg,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,systemPrompt:e.systemPrompt,allowedTools:e.allowedTools,originChannel:e.originChannel,originThreadId:e.originThreadId,originAgentId:e.originAgentId,originSessionKey:e.originSessionKey,route:e.route,harness:e.harness,permissionMode:e.permissionMode??"bypassPermissions",loopMode:n,completionPromise:Pd(e.completionPromise),verifierCommands:r,repeatedFailureCount:0},s=await this.spawnTaskSession(i,mg(i));return this.attachSessionObservers(i,s),i.sessionId=s.id,i.sessionName=s.name,i.harnessSessionId=s.harnessSessionId,i.status="running",i.updatedAt=Date.now(),this.store.upsert(i),this.scheduleTaskEvaluation(i.id,"launch",s.id),this.notify(i,`🎯 [${i.name}] Goal task started
158
160
 
159
161
  Goal:
160
- ${Lt(i.goal,500)}`,"goal-task-started"),i}stopTask(e){let n=this.store.get(e);if(n)return hd(n.status)?{task:n,action:"already_terminal"}:(n.sessionId&&this.sessionManager.kill(n.sessionId,"user"),this.markTaskStopped(n,"Stopped by user."),{task:n,action:"stopped"})}editTask(e,n){let r=n.trim();if(!r)return{action:"invalid_goal"};let o=this.store.get(e);if(!o)return{action:"not_found"};if(hd(o.status)||o.status==="waiting_for_user")return{action:"not_editable",task:o};let i=o.goal;return o.goal=r,o.updatedAt=Date.now(),this.store.upsert(o),this.notify(o,`✏️ [${o.name}] Goal task edited
162
+ ${Bt(i.goal,500)}`,"goal-task-started"),i}stopTask(e){let n=this.store.get(e);if(n)return Td(n.status)?{task:n,action:"already_terminal"}:(n.sessionId&&this.sessionManager.kill(n.sessionId,"user"),this.markTaskStopped(n,"Stopped by user."),{task:n,action:"stopped"})}editTask(e,n){let r=n.trim();if(!r)return{action:"invalid_goal"};let o=this.store.get(e);if(!o)return{action:"not_found"};if(Td(o.status)||o.status==="waiting_for_user")return{action:"not_editable",task:o};let i=o.goal;return o.goal=r,o.updatedAt=Date.now(),this.store.upsert(o),this.notify(o,`✏️ [${o.name}] Goal task edited
161
163
 
162
164
  Goal:
163
- ${Lt(o.goal,500)}`,"goal-task-edited"),{action:"updated",task:o,previousGoal:i}}async spawnTaskSession(e,n){return this.spawnManagedTaskSession(e,n)}async spawnManagedTaskSession(e,n,r){let o=r?this.sessionManager.resolveHarnessSessionId(r)??r:void 0,i=r?this.sessionManager.resolve(r):void 0,s=o?this.sessionManager.getPersistedSession(o)??this.sessionManager.getPersistedSession(r??o):void 0,{resumeSessionId:l}=mt({requestedResumeSessionId:o,activeSession:i?{harnessSessionId:i.harnessSessionId}:void 0,persistedSession:s?{harness:s.harness,backendRef:s.backendRef}:void 0}),a={prompt:n,name:e.name,workdir:e.workdir,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,systemPrompt:e.systemPrompt,allowedTools:e.allowedTools,originChannel:e.originChannel,originThreadId:e.originThreadId,originAgentId:e.originAgentId,originSessionKey:e.originSessionKey,route:jf(e),permissionMode:e.permissionMode,multiTurn:!0,goalTaskId:e.id,harness:e.harness,resumeSessionId:l,resumeWorktreeFrom:o,worktreeStrategy:"off"};return this.sessionManager.spawnAndAwaitRunning(a,{notifyLaunch:!1})}async resumeTaskSession(e,n,r){if(!r.harnessSessionId){let i=await this.spawnTaskSession(e,["The previous session ended without a resumable harness session id.","Continue working on the same goal.","",n].join(`
164
- `));return this.attachSessionObservers(e,i),i}let o=await this.spawnManagedTaskSession(e,n,r.harnessSessionId);return this.attachSessionObservers(e,o),o}resolveResumeSessionId(e){if(e.harnessSessionId)return e.harnessSessionId;if(e.sessionId){let r=this.sessionManager.resolveHarnessSessionId(e.sessionId);if(r)return r}let n=this.sessionManager.resolveHarnessSessionId(e.name);if(n)return n}captureRecoverableTasks(){for(let e of this.store.list()){if(e.status!=="running"&&e.status!=="waiting_for_session")continue;let n=e.sessionId?this.sessionManager.resolve(e.sessionId):void 0;n&&(e.sessionId=n.id,e.sessionName=n.name,e.harnessSessionId=n.harnessSessionId??e.harnessSessionId,e.route=n.route??e.route,e.updatedAt=Date.now(),e.status="waiting_for_session",this.store.upsert(e))}}async restoreRecoverableTasks(){for(let e of this.store.list()){if(!this.started)break;if(e.status==="waiting_for_user"){this.markTaskFailed(e,"Goal task was waiting for user input and cannot continue autonomously");continue}if(e.status!=="waiting_for_session"&&e.status!=="running")continue;if(cd(e)){this.markTaskFailed(e,Qr());continue}if(e.sessionId){let r=this.sessionManager.resolve(e.sessionId);if(r&&(r.status==="starting"||r.status==="running"))continue}let n=this.resolveResumeSessionId(e);if(!n){this.markTaskFailed(e,"Goal task could not be resumed after gateway restart because no resumable session id was available.");continue}try{let r=await this.spawnManagedTaskSession(e,fd(e),n);if(!this.started){e.sessionId=r.id,e.sessionName=r.name,e.harnessSessionId=r.harnessSessionId??n,e.route=r.route??e.route,e.status="waiting_for_session",e.updatedAt=Date.now(),this.store.upsert(e),this.sessionManager.kill(r.id,"shutdown");break}this.attachSessionObservers(e,r),e.sessionId=r.id,e.sessionName=r.name,e.harnessSessionId=r.harnessSessionId??n,e.route=r.route??e.route,e.status="running",e.updatedAt=Date.now(),this.store.upsert(e),this.notifyIterationStatus(e,`🔄 [${e.name}] Goal task resumed after gateway restart`,r),this.scheduleTaskEvaluation(e.id,"restore",r.id)}catch(r){this.markTaskFailed(e,`Failed to resume the goal task after gateway restart: ${at(r)}`)}}}async runVerifiers(e){let n=Yi(e.verifierCommands);if(n.length===0){let s={status:"fail",steps:[{label:"verifier-config",command:"(none configured)",ok:!1,exitCode:1,durationMs:0,output:Qr()}],summary:"",fingerprint:""};return s.fingerprint=pd(s),s.summary=gd(s),s}let r=[];for(let s of n)r.push(await rg(e.workdir,s));let i={status:r.every(s=>s.ok)?"pass":"fail",steps:r,summary:"",fingerprint:""};return i.fingerprint=pd(i),i.summary=gd(i),i}notify(e,n,r){this.sessionManager.emitGoalTaskUpdate(e,n,r)}notifyIterationStatus(e,n,r,o){let i=e.loopMode==="ralph"?"iteration":"repair iteration",s=/\b(?:repair\s+)?iteration\s+\d+\/\d+\b/i.test(n)?n:`${n} ${i} ${e.iteration}/${e.maxIterations}`,l=Gf(o),a=l?`${s}
165
+ ${Bt(o.goal,500)}`,"goal-task-edited"),{action:"updated",task:o,previousGoal:i}}async spawnTaskSession(e,n){return this.spawnManagedTaskSession(e,n)}async spawnManagedTaskSession(e,n,r){let o=r?this.sessionManager.resolveHarnessSessionId(r)??r:void 0,i=r?this.sessionManager.resolve(r):void 0,s=o?this.sessionManager.getPersistedSession(o)??this.sessionManager.getPersistedSession(r??o):void 0,{resumeSessionId:a}=gt({requestedResumeSessionId:o,activeSession:i?{harnessSessionId:i.harnessSessionId}:void 0,persistedSession:s?{harness:s.harness,backendRef:s.backendRef}:void 0}),l={prompt:n,name:e.name,workdir:e.workdir,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,systemPrompt:e.systemPrompt,allowedTools:e.allowedTools,originChannel:e.originChannel,originThreadId:e.originThreadId,originAgentId:e.originAgentId,originSessionKey:e.originSessionKey,route:dg(e),permissionMode:e.permissionMode,multiTurn:!0,goalTaskId:e.id,harness:e.harness,resumeSessionId:a,resumeWorktreeFrom:o,worktreeStrategy:"off"};return this.sessionManager.spawnAndAwaitRunning(l,{notifyLaunch:!1})}async resumeTaskSession(e,n,r){if(!r.harnessSessionId){let i=await this.spawnTaskSession(e,["The previous session ended without a resumable harness session id.","Continue working on the same goal.","",n].join(`
166
+ `));return this.attachSessionObservers(e,i),i}let o=await this.spawnManagedTaskSession(e,n,r.harnessSessionId);return this.attachSessionObservers(e,o),o}resolveResumeSessionId(e){if(e.harnessSessionId)return e.harnessSessionId;if(e.sessionId){let r=this.sessionManager.resolveHarnessSessionId(e.sessionId);if(r)return r}let n=this.sessionManager.resolveHarnessSessionId(e.name);if(n)return n}captureRecoverableTasks(){for(let e of this.store.list()){if(e.status!=="running"&&e.status!=="waiting_for_session")continue;let n=e.sessionId?this.sessionManager.resolve(e.sessionId):void 0;n&&(e.sessionId=n.id,e.sessionName=n.name,e.harnessSessionId=n.harnessSessionId??e.harnessSessionId,e.route=n.route??e.route,e.updatedAt=Date.now(),e.status="waiting_for_session",this.store.upsert(e))}}async restoreRecoverableTasks(){for(let e of this.store.list()){if(!this.started)break;if(e.status==="waiting_for_user"){this.markTaskFailed(e,"Goal task was waiting for user input and cannot continue autonomously");continue}if(e.status!=="waiting_for_session"&&e.status!=="running")continue;if(bd(e)){this.markTaskFailed(e,Xr());continue}if(e.sessionId){let r=this.sessionManager.resolve(e.sessionId);if(r&&(r.status==="starting"||r.status==="running"))continue}let n=this.resolveResumeSessionId(e);if(!n){this.markTaskFailed(e,"Goal task could not be resumed after gateway restart because no resumable session id was available.");continue}try{let r=await this.spawnManagedTaskSession(e,Id(e),n);if(!this.started){e.sessionId=r.id,e.sessionName=r.name,e.harnessSessionId=r.harnessSessionId??n,e.route=r.route??e.route,e.status="waiting_for_session",e.updatedAt=Date.now(),this.store.upsert(e),this.sessionManager.kill(r.id,"shutdown");break}this.attachSessionObservers(e,r),e.sessionId=r.id,e.sessionName=r.name,e.harnessSessionId=r.harnessSessionId??n,e.route=r.route??e.route,e.status="running",e.updatedAt=Date.now(),this.store.upsert(e),this.notifyIterationStatus(e,`🔄 [${e.name}] Goal task resumed after gateway restart`,r),this.scheduleTaskEvaluation(e.id,"restore",r.id)}catch(r){this.markTaskFailed(e,`Failed to resume the goal task after gateway restart: ${dt(r)}`)}}}async runVerifiers(e){let n=os(e.verifierCommands);if(n.length===0){let s={status:"fail",steps:[{label:"verifier-config",command:"(none configured)",ok:!1,exitCode:1,durationMs:0,output:Xr()}],summary:"",fingerprint:""};return s.fingerprint=Rd(s),s.summary=xd(s),s}let r=[];for(let s of n)r.push(await vg(e.workdir,s));let i={status:r.every(s=>s.ok)?"pass":"fail",steps:r,summary:"",fingerprint:""};return i.fingerprint=Rd(i),i.summary=xd(i),i}notify(e,n,r){this.sessionManager.emitGoalTaskUpdate(e,n,r)}notifyIterationStatus(e,n,r,o){let i=e.loopMode==="ralph"?"iteration":"repair iteration",s=/\b(?:repair\s+)?iteration\s+\d+\/\d+\b/i.test(n)?n:`${n} ${i} ${e.iteration}/${e.maxIterations}`,a=lg(o),l=a?`${s}
165
167
 
166
- ${l}`:s;this.notify(e,a,"goal-task-progress")}setTaskRunningWithSession(e,n){e.sessionId=n.id,e.sessionName=n.name,e.harnessSessionId=n.harnessSessionId,e.route=n.route??e.route,e.status="running",e.waitingForUserReason=void 0,e.updatedAt=Date.now(),this.store.upsert(e)}attachSessionObservers(e,n){if(this.observerDisposers.has(n.id))return;let r=(i,s)=>{(s==="completed"||s==="failed"||s==="killed")&&(this.removeSessionObserver(n.id),this.scheduleTaskEvaluation(e.id,`status:${s}`,n.id))},o=()=>{let i=this.store.get(e.id);i&&(i.sessionId=n.id,i.sessionName=n.name,i.harnessSessionId=n.harnessSessionId,i.route=n.route??i.route,i.updatedAt=Date.now(),i.status==="waiting_for_session"&&(i.status="running"),this.store.upsert(i),this.notifyIterationStatus(i,`🔄 [${i.name}] Coding turn complete`,n),this.scheduleTaskEvaluation(e.id,"turnEnd",n.id))};n.on("statusChange",r),n.on("turnEnd",o),this.observerDisposers.set(n.id,()=>{n.off?.("statusChange",r),n.off?.("turnEnd",o),n.removeListener?.("statusChange",r),n.removeListener?.("turnEnd",o)})}scheduleTaskEvaluation(e,n,r){if(!this.started)return;let o=this.scheduledEvaluations.get(e);if(o){!o.sessionId&&r&&(o.sessionId=r);return}let i={timer:setTimeout(()=>{this.scheduledEvaluations.delete(e),this.evaluateTask(e,n,i.sessionId).catch(s=>{`${n}${at(s)}`})},0),sessionId:r};i.timer.unref?.(),this.scheduledEvaluations.set(e,i)}clearScheduledEvaluations(){for(let e of this.scheduledEvaluations.values())clearTimeout(e.timer);this.scheduledEvaluations.clear(),this.dirtyEvaluations.clear(),this.dirtyEvaluationSessionIds.clear()}detachSessionObservers(){for(let e of[...this.observerDisposers.keys()])this.removeSessionObserver(e)}removeSessionObserver(e){let n=this.observerDisposers.get(e);n&&(this.observerDisposers.delete(e),n())}markTaskFailed(e,n){e.status="failed",e.failureReason=Lt(n,Ji),e.updatedAt=Date.now(),this.store.upsert(e),this.notify(e,`❌ [${e.name}] Goal task failed
168
+ ${a}`:s;this.notify(e,l,"goal-task-progress")}setTaskRunningWithSession(e,n){e.sessionId=n.id,e.sessionName=n.name,e.harnessSessionId=n.harnessSessionId,e.route=n.route??e.route,e.status="running",e.waitingForUserReason=void 0,e.updatedAt=Date.now(),this.store.upsert(e)}attachSessionObservers(e,n){if(this.observerDisposers.has(n.id))return;let r=(i,s)=>{(s==="completed"||s==="failed"||s==="killed")&&(this.removeSessionObserver(n.id),this.scheduleTaskEvaluation(e.id,`status:${s}`,n.id))},o=()=>{let i=this.store.get(e.id);i&&(i.sessionId=n.id,i.sessionName=n.name,i.harnessSessionId=n.harnessSessionId,i.route=n.route??i.route,i.updatedAt=Date.now(),i.status==="waiting_for_session"&&(i.status="running"),this.store.upsert(i),this.notifyIterationStatus(i,`🔄 [${i.name}] Coding turn complete`,n),this.scheduleTaskEvaluation(e.id,"turnEnd",n.id))};n.on("statusChange",r),n.on("turnEnd",o),this.observerDisposers.set(n.id,()=>{n.off?.("statusChange",r),n.off?.("turnEnd",o),n.removeListener?.("statusChange",r),n.removeListener?.("turnEnd",o)})}scheduleTaskEvaluation(e,n,r){if(!this.started)return;let o=this.scheduledEvaluations.get(e);if(o){!o.sessionId&&r&&(o.sessionId=r);return}let i={timer:setTimeout(()=>{this.scheduledEvaluations.delete(e),this.evaluateTask(e,n,i.sessionId).catch(s=>{`${n}${dt(s)}`})},0),sessionId:r};i.timer.unref?.(),this.scheduledEvaluations.set(e,i)}clearScheduledEvaluations(){for(let e of this.scheduledEvaluations.values())clearTimeout(e.timer);this.scheduledEvaluations.clear(),this.dirtyEvaluations.clear(),this.dirtyEvaluationSessionIds.clear()}detachSessionObservers(){for(let e of[...this.observerDisposers.keys()])this.removeSessionObserver(e)}removeSessionObserver(e){let n=this.observerDisposers.get(e);n&&(this.observerDisposers.delete(e),n())}markTaskFailed(e,n){e.status="failed",e.failureReason=Bt(n,rs),e.updatedAt=Date.now(),this.store.upsert(e),this.notify(e,`❌ [${e.name}] Goal task failed
167
169
 
168
170
  ${e.failureReason}`,"goal-task-failed")}markTaskFailedWaitingForUser(e,n){this.markTaskFailed(e,`Goal task was waiting for user input and cannot continue autonomously: ${n}`)}markTaskSucceeded(e,n){e.status="succeeded",e.lastVerifierSummary=n,e.updatedAt=Date.now(),this.store.upsert(e),this.notify(e,`✅ [${e.name}] Goal task succeeded
169
171
 
170
- ${n}`,"goal-task-succeeded")}markTaskStopped(e,n){e.status="stopped",e.failureReason=Lt(n,Ji),e.updatedAt=Date.now(),this.store.upsert(e),this.notify(e,`⛔ [${e.name}] Goal task stopped
172
+ ${n}`,"goal-task-succeeded")}markTaskStopped(e,n){e.status="stopped",e.failureReason=Bt(n,rs),e.updatedAt=Date.now(),this.store.upsert(e),this.notify(e,`⛔ [${e.name}] Goal task stopped
171
173
 
172
174
  ${e.failureReason}`,"goal-task-stopped")}async handleRunningSession(e,n){if(n.pendingPlanApproval){let s=await ve(this.sessionManager,{session:n.id,message:"Approved. Implement the plan.",approve:!0,userInitiated:!1});s.isError&&this.markTaskFailed(e,s.text);return}if(!n.pendingInputState){this.setTaskRunningWithSession(e,n);return}let r=n.getOutput(30).join(`
173
- `),o=md(r);if(!o){this.markTaskFailedWaitingForUser(e,je(r,24)||"The session is waiting for user input.");return}let i=await ve(this.sessionManager,{session:n.id,message:o,userInitiated:!1});if(i.isError||i.text.includes("Auto-respond limit reached")){this.markTaskFailedWaitingForUser(e,i.text);return}e.status="running",e.waitingForUserReason=void 0,e.updatedAt=Date.now(),this.store.upsert(e)}async resumeAfterIdleTimeout(e,n,r){try{let o=await this.resumeTaskSession(e,r,n);this.setTaskRunningWithSession(e,o),this.notifyIterationStatus(e,`🔄 [${e.name}] Goal task resumed after idle timeout`,o),this.scheduleTaskEvaluation(e.id,"idle-timeout-resume",o.id)}catch(o){this.markTaskFailed(e,`Failed to resume the goal task after idle timeout: ${at(o)}`)}}async handleTerminalSession(e,n){if(n.status==="failed"){this.markTaskFailed(e,tg(n));return}if(n.status==="killed"&&n.killReason==="user"){this.markTaskStopped(e,"Stopped by user.");return}if(n.status==="killed"&&n.killReason==="idle-timeout"){let s=n.getOutput(60).join(`
174
- `);if(n.pendingPlanApproval){let l=await ve(this.sessionManager,{session:n.id,message:"Approved. Implement the plan.",approve:!0,userInitiated:!1});if(l.isError){this.markTaskFailed(e,l.text);return}let a=this.sessionManager.resolve(n.id);if(!a){this.markTaskFailed(e,"Failed to resolve the resumed goal task session after idle timeout plan approval.");return}this.attachSessionObservers(e,a),this.setTaskRunningWithSession(e,a),this.notifyIterationStatus(e,`🔄 [${e.name}] Goal task resumed after idle timeout`,a),this.scheduleTaskEvaluation(e.id,"idle-timeout-plan-resume",a.id);return}if(n.pendingInputState){let l=md(s);if(!l){this.markTaskFailed(e,`Goal task was waiting for user input and cannot continue autonomously: ${je(s,24)||"The goal task hit idle timeout while waiting for user input."}`);return}await this.resumeAfterIdleTimeout(e,n,["The previous session hit idle timeout while waiting for a response.",`Use this response and continue the goal: ${l}`].join(`
175
-
176
- `));return}await this.resumeAfterIdleTimeout(e,n,fd(e));return}if(n.status==="killed"&&n.killReason!=="done"){this.markTaskFailed(e,`Underlying session was killed (${n.killReason}).`);return}if(e.loopMode==="ralph"){let s=n.getOutput(200).join(`
177
- `),l=ud(e.completionPromise);if(eg(s,l)){if(e.verifierCommands.length===0){this.markTaskSucceeded(e,`Completion promise "${l}" detected in agent output.`);return}let m=await this.runVerifiers(e);if(e.lastVerifierSummary=m.summary,e.updatedAt=Date.now(),m.status==="pass"){this.markTaskSucceeded(e,[`Completion promise "${l}" detected.`,m.summary].join(`
178
- `));return}if(e.lastVerifierFingerprint===m.fingerprint?e.repeatedFailureCount+=1:e.repeatedFailureCount=1,e.lastVerifierFingerprint=m.fingerprint,e.iteration+1>=e.maxIterations){this.markTaskFailed(e,[`Goal task emitted completion promise but verifiers still failed before hitting the iteration budget (${e.maxIterations}).`,m.summary].join(`
179
- `));return}e.iteration+=1;let p=Xf(e,m),f=Ur({output:s,verifierSummary:m.summary,completionPromise:l,completionDetected:!0});try{let h=await this.resumeTaskSession(e,p,n);this.setTaskRunningWithSession(e,h),this.notifyIterationStatus(e,`🔁 [${e.name}] Completion claimed but verifiers still failed`,void 0,f),this.scheduleTaskEvaluation(e.id,"ralph-verifier-resume",h.id)}catch(h){this.markTaskFailed(e,`Failed to resume the Ralph goal task after verifier failure: ${at(h)}`)}return}let d=Qf(s);if(e.lastVerifierFingerprint===d?e.repeatedFailureCount+=1:e.repeatedFailureCount=1,e.lastVerifierFingerprint=d,e.iteration+1>=e.maxIterations){this.markTaskFailed(e,[`Completion promise "${l}" was not emitted before hitting the iteration budget (${e.maxIterations}).`,"Latest output:",je(s,20)||"(no output)"].join(`
180
- `));return}e.iteration+=1;let u=Zf(e,s),c=Ur({output:s,completionPromise:l,completionDetected:!1});try{let m=await this.resumeTaskSession(e,u,n);this.setTaskRunningWithSession(e,m),this.notifyIterationStatus(e,`🔁 [${e.name}] Continued`,void 0,c),this.scheduleTaskEvaluation(e.id,"ralph-continue",m.id)}catch(m){this.markTaskFailed(e,`Failed to continue the Ralph goal task: ${at(m)}`)}return}let r=await this.runVerifiers(e);if(e.lastVerifierSummary=r.summary,e.updatedAt=Date.now(),r.status==="pass"){this.markTaskSucceeded(e,r.summary);return}if(e.lastVerifierFingerprint===r.fingerprint?e.repeatedFailureCount+=1:e.repeatedFailureCount=1,e.lastVerifierFingerprint=r.fingerprint,e.iteration+1>=e.maxIterations){this.markTaskFailed(e,[`Verifier did not pass before hitting the iteration budget (${e.maxIterations}).`,r.summary].join(`
181
- `));return}e.iteration+=1;let o=Yf(e,r),i=Ur({verifierSummary:r.summary});try{let s=await this.resumeTaskSession(e,o,n);this.setTaskRunningWithSession(e,s),this.notifyIterationStatus(e,`🔁 [${e.name}] Repair iteration started after verifier failure`,void 0,i),this.scheduleTaskEvaluation(e.id,"repair-resume",s.id)}catch(s){this.markTaskFailed(e,`Failed to resume the goal task: ${at(s)}`)}}async evaluateTask(e,n,r){this.restorePromise&&await this.restorePromise;let o=this.store.get(e);o&&await this.reconcileTask(o,n,r)}async reconcileTask(e,n="manual",r){if(!(e.status==="succeeded"||e.status==="failed"||e.status==="stopped")){if(this.inFlight.has(e.id)){this.dirtyEvaluations.add(e.id),!this.dirtyEvaluationSessionIds.get(e.id)&&r?this.dirtyEvaluationSessionIds.set(e.id,r):this.dirtyEvaluationSessionIds.has(e.id)||this.dirtyEvaluationSessionIds.set(e.id,r);return}this.inFlight.add(e.id);try{if(r&&e.sessionId&&e.sessionId!==r){let i=this.sessionManager.resolve(r);if(i&&(i.status==="completed"||i.status==="failed"||i.status==="killed"))return}let o=r?this.sessionManager.resolve(r)??(e.sessionId?this.sessionManager.resolve(e.sessionId):void 0):e.sessionId?this.sessionManager.resolve(e.sessionId):void 0;if(e.status==="waiting_for_user"){this.markTaskFailed(e,"Goal task was waiting for user input and cannot continue autonomously");return}if(cd(e)){this.markTaskFailed(e,Qr());return}if(!o){this.markTaskFailed(e,"Underlying session could not be found.");return}if(e.sessionName=o.name,e.harnessSessionId=o.harnessSessionId,e.route=o.route??e.route,e.updatedAt=Date.now(),this.store.upsert(e),o.status==="starting"||o.status==="running"){await this.handleRunningSession(e,o);return}await this.handleTerminalSession(e,o)}finally{if(this.inFlight.delete(e.id),this.dirtyEvaluations.has(e.id)){this.dirtyEvaluations.delete(e.id);let o=this.dirtyEvaluationSessionIds.get(e.id);this.dirtyEvaluationSessionIds.delete(e.id),this.scheduleTaskEvaluation(e.id,`${n}:dirty`,o)}}}}};import{createHash as wu}from"crypto";ie();import{existsSync as og,realpathSync as ig}from"fs";import{resolve as sg}from"path";function Sd(t){if(!t)return;let e=sg(t);try{if(og(e))return ig.native(e)}catch{}return e}function Yr(t,e){return!t||!e?!1:Sd(t)===Sd(e)}Z();ie();import{existsSync as ag}from"fs";Z();ye();function vd(t){return t instanceof Error?t.message:String(t)}function lg(t){let e=t.worktreeStrategy??D.defaultWorktreeStrategy;return!!e&&e!=="off"&&mi(on({harnessName:t.harness??ae(),backendRef:t.backendRef}))}function dg(t,e,n,r){let o=["","You are working in a git worktree.",`Worktree path: ${n}`,`Branch: ${r}`,"",`IMPORTANT: ALL file edits must be made within this worktree at ${n}.`,`Do NOT edit files directly in ${e} (the original workspace).`,`If your task references files by absolute path under ${e}, rewrite those`,"paths relative to your current working directory. For example:",` "${e}/src/file.py" → use relative path "src/file.py"`,"","Before finishing, run `git status --short` in this worktree.","If you made actual task changes, commit all of them to this branch before finishing.","Use `git add` and `git commit`. If no repository changes are needed, leave the worktree clean before finishing.","Do NOT run `git checkout`, `git switch`, or `git reset --hard` as these will detach or corrupt the worktree HEAD.","","When making changes, please note:","- Do NOT commit planning documents, investigation notes, or analysis artifacts to this branch","- Only commit actual code, configuration, tests, and documentation changes that were explicitly requested as part of the task"].join(`
182
- `);return(t??"")+o}function ug(t,e){let n=t.resumeWorktreeFrom??t.resumeSessionId;if(!n)return{};let r=e(n);if(!r)return{};let o=!!r.harness||!!r.backendRef,i=(()=>{if(r.workdir&&r.workdir!==r.worktreePath)return r.workdir;if(r.worktreePath){let l=pr(r.worktreePath);return r.workdir&&l&&Yr(r.workdir,l)?r.workdir:l??r.workdir}return r.workdir})();if(t.worktreeStrategy||(r.worktreeLifecycle?.state==="pr_open"||r.worktreePrUrl?t.worktreeStrategy="auto-pr":r.worktreeStrategy&&(t.worktreeStrategy=r.worktreeStrategy)),!t.planApproval&&r.planApproval&&(t.planApproval=r.planApproval),!r.worktreePath){let l=o&&Qn(on({persistedHarness:r.harness,backendRef:r.backendRef}));return{originalWorkdir:i,canCreateManagedWorktreeForResumeWithoutPersistedPath:l}}if(!r.worktreeBranch)throw new Error(`Cannot resume session "${n}": persisted worktree metadata is missing worktreeBranch.`);let s=Qn(on({persistedHarness:r.harness,backendRef:r.backendRef}))&&!!r.backendRef?.worktreePath;if(ag(r.worktreePath))return`${r.worktreePath}`,{actualWorkdir:r.worktreePath,originalWorkdir:i??r.worktreePath,worktreePath:r.worktreePath,worktreeBranchName:r.worktreeBranch};if(!i)return`${r.worktreePath}`,{clearedResumeSessionId:!!t.resumeSessionId,clearedResumeWorktreeFrom:!!t.resumeWorktreeFrom};if(s)return`${r.worktreePath}`,{actualWorkdir:i,originalWorkdir:i,worktreeBranchName:r.worktreeBranch,clearedResumeWorktreeFrom:!!t.resumeWorktreeFrom,restoredMissingNativeBackendWorktree:!0};try{fr(i);let l=vi(i,r.worktreeBranch.replace(/^agent\//,""),{allowExistingBranch:!0});return`${r.worktreeBranch}${l}`,{actualWorkdir:l,originalWorkdir:i,worktreePath:l,worktreeBranchName:r.worktreeBranch}}catch(l){return`${vd(l)}`,{actualWorkdir:i,originalWorkdir:i,clearedResumeSessionId:!!t.resumeSessionId,clearedResumeWorktreeFrom:!!t.resumeWorktreeFrom,failedResumeWorktreeRestore:!0}}}function Pd(t,e,n){let{actualWorkdir:r,originalWorkdir:o,worktreePath:i,worktreeBranchName:s,clearedResumeSessionId:l,clearedResumeWorktreeFrom:a,restoredMissingNativeBackendWorktree:d,canCreateManagedWorktreeForResumeWithoutPersistedPath:u,failedResumeWorktreeRestore:c}=ug(t,n);l&&(t.resumeSessionId=void 0),a&&(t.resumeWorktreeFrom=void 0),r??=t.workdir,o??=t.workdir;let m=!!(t.resumeSessionId??t.resumeWorktreeFrom),p=t.worktreeStrategy??D.defaultWorktreeStrategy;p&&(t.worktreeStrategy=p);let f=lg(t),k=(!m||!!u)&&!d&&!i&&p&&p!=="off"&&!f;if(c&&p&&p!=="off")throw new Error(`Cannot launch session "${e}": worktree strategy "${p}" was requested, but no isolated worktree was prepared. Launch with worktree_strategy "off" only when running in the base checkout is intentional.`);if(f&&!ki(o))throw new Error(`Cannot launch session "${e}": worktree strategy "${p}" requires a git worktree, but "${o}" is not a git repository.`);if(k&&ki(o)){if(!Na(o))throw new Error(`Cannot launch session "${e}": insufficient space for worktree creation.`);try{if(i=vi(o,e),r=i,s=At(i),!s)throw new Error(`created worktree at ${i} but failed to resolve branch name`);`${i}`}catch(v){throw new Error(`Cannot launch session "${e}": worktree creation failed: ${vd(v)}`)}}else if(k)throw new Error(`Cannot launch session "${e}": worktree strategy "${p}" requires a git worktree, but "${o}" is not a git repository.`);if(m&&i&&(r=i),p&&p!=="off"&&!i)throw new Error(`Cannot launch session "${e}": worktree strategy "${p}" was requested, but no isolated worktree was prepared. Launch with worktree_strategy "off" only when running in the base checkout is intentional.`);return{actualWorkdir:r,originalWorkdir:o,effectiveSystemPrompt:i&&s?dg(t.systemPrompt,o,i,s):t.systemPrompt,worktreePath:i,worktreeBranchName:s,clearedResumeSessionId:l,clearedResumeWorktreeFrom:a,restoredMissingNativeBackendWorktree:d,failedResumeWorktreeRestore:c}}var Zr=class{constructor(e){this.getPersistedSession=e}getPersistedSession;prepareSpawn(e,n){return Pd(e,n,this.getPersistedSession)}hydrateSpawnedSession(e,n,r){r.worktreeStrategy&&r.worktreeStrategy!=="off"&&(e.originalWorkdir=n.originalWorkdir),n.worktreePath&&(e.worktreePath=n.worktreePath,e.worktreeBranch=n.worktreeBranchName,e.worktreeState="provisioned"),r.worktreePrTargetRepo&&(e.worktreePrTargetRepo=r.worktreePrTargetRepo)}};Z();var Xr=class{constructor(e){this.deps=e}deps;applySessionPatch(e,n){let r=this.normalizeCompletionWakePatch(n),o=this.deps.store.getPersistedSession(e);o&&(Object.assign(o,r),this.deps.store.assertPersistedEntry(o));let i=this.findActiveSessionForRef(e,o);return i&&this.applyPatchToActiveSession(i,r),!o&&!i?!1:(o&&this.deps.store.saveIndex(),!0)}normalizeCompletionWakePatch(e){return"completionWakeSucceededAt"in e&&e.completionWakeSucceededAt||"completionWakeSkippedAt"in e&&e.completionWakeSkippedAt?{...e,completionWakeSummaryRequired:void 0}:e}matchesExistingSession(e,n){if(!n)return!1;let r=$(e),o=$(n);return!!(n.sessionId&&e.id===n.sessionId||o&&o===r||n?.harnessSessionId&&e.harnessSessionId===n.harnessSessionId||n?.name&&e.name===n.name)}findActiveSessionForRef(e,n){let r=this.deps.resolveSession(e);if(r)return r;for(let o of this.deps.sessions.values())if(U(o)===e||$(o)===e||o.harnessSessionId===e||this.matchesExistingSession(o,n))return o}applyPatchToActiveSession(e,n){this.applyControlStatePatch(e,n),this.applySessionMetadataPatch(e,n),this.applyWorktreeMetadataPatch(e,n)}applyControlStatePatch(e,n){let r={};if(this.copyControlPatchField(r,n,"lifecycle"),this.copyControlPatchField(r,n,"approvalState"),this.copyControlPatchField(r,n,"approvalExecutionState"),this.copyControlPatchField(r,n,"worktreeState"),this.copyControlPatchField(r,n,"runtimeState"),this.copyControlPatchField(r,n,"deliveryState"),this.copyControlPatchField(r,n,"requestedPermissionMode"),this.copyControlPatchField(r,n,"currentPermissionMode"),this.copyControlPatchField(r,n,"pendingPlanApproval"),this.copyControlPatchField(r,n,"planApprovalContext"),this.copyControlPatchField(r,n,"planDecisionVersion"),this.copyControlPatchField(r,n,"actionablePlanDecisionVersion"),this.copyControlPatchField(r,n,"canonicalPlanPromptVersion"),this.copyControlPatchField(r,n,"approvalPromptRequiredVersion"),this.copyControlPatchField(r,n,"approvalPromptVersion"),this.copyControlPatchField(r,n,"approvalPromptStatus"),this.copyControlPatchField(r,n,"approvalPromptTransport"),this.copyControlPatchField(r,n,"approvalPromptMessageKind"),this.copyControlPatchField(r,n,"approvalPromptLastAttemptAt"),this.copyControlPatchField(r,n,"approvalPromptDeliveredAt"),this.copyControlPatchField(r,n,"approvalPromptFailedAt"),this.copyControlPatchField(r,n,"planModeApproved"),this.copyControlPatchField(r,n,"pendingWorktreeDecisionSince"),typeof e.applyControlPatch=="function"){e.applyControlPatch(r);return}this.assignIfPresent(e,"lifecycle",n,"lifecycle"),this.assignIfPresent(e,"approvalState",n,"approvalState"),this.assignIfPresent(e,"approvalExecutionState",n,"approvalExecutionState"),this.assignIfPresent(e,"worktreeState",n,"worktreeState"),this.assignIfPresent(e,"runtimeState",n,"runtimeState"),this.assignIfPresent(e,"deliveryState",n,"deliveryState"),this.assignIfPresent(e,"requestedPermissionMode",n,"requestedPermissionMode"),this.assignIfPresent(e,"currentPermissionMode",n,"currentPermissionMode"),this.assignIfPresent(e,"pendingPlanApproval",n,"pendingPlanApproval"),this.assignIfPresent(e,"planApprovalContext",n,"planApprovalContext"),this.assignIfPresent(e,"planDecisionVersion",n,"planDecisionVersion"),this.assignIfPresent(e,"actionablePlanDecisionVersion",n,"actionablePlanDecisionVersion"),this.assignIfPresent(e,"canonicalPlanPromptVersion",n,"canonicalPlanPromptVersion"),this.assignIfPresent(e,"approvalPromptRequiredVersion",n,"approvalPromptRequiredVersion"),this.assignIfPresent(e,"approvalPromptVersion",n,"approvalPromptVersion"),this.assignIfPresent(e,"approvalPromptStatus",n,"approvalPromptStatus"),this.assignIfPresent(e,"approvalPromptTransport",n,"approvalPromptTransport"),this.assignIfPresent(e,"approvalPromptMessageKind",n,"approvalPromptMessageKind"),this.assignIfPresent(e,"approvalPromptLastAttemptAt",n,"approvalPromptLastAttemptAt"),this.assignIfPresent(e,"approvalPromptDeliveredAt",n,"approvalPromptDeliveredAt"),this.assignIfPresent(e,"approvalPromptFailedAt",n,"approvalPromptFailedAt"),this.setControlFieldIfPresent(e,"planModeApproved",n)}applySessionMetadataPatch(e,n){this.assignIfDefined(e,"approvalRationale",n.approvalRationale)}applyWorktreeMetadataPatch(e,n){this.assignIfDefined(e,"worktreePath",n.worktreePath),this.assignIfDefined(e,"worktreeBranch",n.worktreeBranch),this.assignIfDefined(e,"worktreePrUrl",n.worktreePrUrl),this.assignIfDefined(e,"worktreePrNumber",n.worktreePrNumber),this.assignIfDefined(e,"worktreeMerged",n.worktreeMerged),this.assignIfDefined(e,"worktreeMergedAt",n.worktreeMergedAt),this.assignIfDefined(e,"worktreeDisposition",n.worktreeDisposition),this.assignIfDefined(e,"worktreePrTargetRepo",n.worktreePrTargetRepo),this.assignIfDefined(e,"worktreePushRemote",n.worktreePushRemote),this.assignIfDefined(e,"worktreeLifecycle",n.worktreeLifecycle),"autoMergeParentSessionId"in n&&(e.autoMergeParentSessionId=n.autoMergeParentSessionId),"autoMergeConflictResolutionAttemptCount"in n&&(e.autoMergeConflictResolutionAttemptCount=n.autoMergeConflictResolutionAttemptCount),"autoMergeResolverSessionId"in n&&(e.autoMergeResolverSessionId=n.autoMergeResolverSessionId)}assignIfDefined(e,n,r){r!==void 0&&(e[n]=r)}assignIfPresent(e,n,r,o){Object.hasOwn(r,o)&&(e[n]=r[o])}copyControlPatchField(e,n,r){Object.hasOwn(n,r)&&(e[r]=n[r])}setControlFieldIfPresent(e,n,r){Object.hasOwn(r,n)&&e.setControlField?.(n,r[n])}};Z();var cg=new Set(["starting","running"]),eo=class{constructor(e,n){this.sessions=e;this.store=n}sessions;store;resolveActive(e){let n=this.sessions.get(e);return n||(this.findPreferredMatch(e,r=>r.name===e)??this.findPreferredMatch(e,r=>$(r)===e)??this.findPreferredMatch(e,r=>r.harnessSessionId===e))}getPersistedSession(e){return this.store.getPersistedSession(e)}resolveBackendConversationId(e){let n=this.resolveActive(e);return this.store.resolveBackendConversationId(e,n?$(n)??n.harnessSessionId:void 0)}findPreferredMatch(e,n){let r,o;for(let i of this.sessions.values())n(i,e)&&((!o||i.startedAt>o.startedAt)&&(o=i),cg.has(i.status)&&(!r||i.startedAt>r.startedAt)&&(r=i));return r??o}};Z();Z();ye();import{existsSync as pg}from"fs";var wd=new Set(["merged","released","pr_open","dismissed","cleanup_failed"]),to=class{constructor(e){this.deps=e}deps;async plan(e){let n=U(e)??e.harnessSessionId;if(this.deps.isAlreadyMerged(n))return`${e.name}`,{kind:"skip",result:{notificationSent:!0,worktreeRemoved:!1}};let r=wd.has(e.worktreeState)?e.worktreeState:e.worktreeLifecycle?.state&&wd.has(e.worktreeLifecycle.state)?e.worktreeLifecycle.state:void 0;if(r&&!(r==="pr_open"&&e.worktreeStrategy==="auto-pr"))return`${e.name}${e.worktreeLifecycle?.state??e.worktreeState}`,{kind:"skip",result:{notificationSent:!0,worktreeRemoved:!1}};if(e.status!=="completed")return{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}};if(!this.deps.shouldRunWorktreeStrategy(e))return`${e.name}${e.phase}`,{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}};let o=e.worktreeStrategy;if(!o||o==="off"||o==="manual")return{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}};let i=e.worktreePath,s=this.deps.resolveWorktreeRepoDir(e.originalWorkdir,i),l=e.worktreeBranch;if(!s)return{kind:"notify",label:"worktree-missing-repo-dir",message:`⚠️ [${e.name}] Cannot determine the original repo for worktree ${i}. Manual inspection is required.`};if(!l)return{kind:"notify",label:"worktree-no-branch-name",message:`⚠️ [${e.name}] Cannot determine branch name for worktree ${i}. The worktree may have been removed or is in detached HEAD state. Manual cleanup may be needed.`};let a=le(e);if(a&&!pg(i))return{kind:"no-change",repoDir:s,worktreePath:i,nativeBackendWorktree:a};let d=e.worktreeBaseBranch??Ce(s),u=this.deps.getWorktreeCompletionState(s,i,l,d);if(u==="no-change")return{kind:"no-change",repoDir:s,worktreePath:i,nativeBackendWorktree:a};if(u==="merged")return{kind:"merged",repoDir:s,worktreePath:i,branchName:l,nativeBackendWorktree:a};if(u==="released")return{kind:"released",repoDir:s,worktreePath:i,branchName:l,nativeBackendWorktree:a,reasons:["merge_noop_content_already_on_base"]};if(u==="base-advanced")return{kind:"notify",label:"worktree-no-commits-ahead",message:`⚠️ [${e.name}] Auto-merge: branch '${l}' has no commits ahead of '${d}', but '${d}' has new commits — commits likely landed outside the worktree branch. Verify that commits were not made directly to '${d}' instead of the worktree branch. Worktree: ${i}`};if(u==="dirty-uncommitted")return{kind:"dirty-uncommitted",worktreePath:i,branchName:l,baseBranch:d};let c=Oe(s,l,d);if(!c)return`${l}`,{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}};let m=e.repoIntegrationPolicy?void 0:this.deps.resolveRepoPolicy?.(s),p=Sl({requestedStrategy:o,policy:e.repoIntegrationPolicy??m?.policy,prAvailable:e.repoIntegrationPolicy?this.deps.isPrAvailable(s):m?.prAvailable??this.deps.isPrAvailable(s)});return p.strategy?{kind:"decision",strategy:p.strategy,policyReason:p.reason,policyBlocked:p.blocked,allowedActions:p.allowedActions,repoDir:s,worktreePath:i,branchName:l,baseBranch:d,diffSummary:c,sessionRef:n??void 0}:{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}}}};kn();function mg(t){if(t.requestedPermissionMode==="plan"){if(t.approvalExecutionState==="approved_then_implemented"){if(t.planApproval==="ask"&&t.approvalPromptStatus==="delivered"&&t.approvalPromptMessageKind==="canonical_buttons"&&t.approvalPromptDeliveredAt)return"Approval interpretation: canonical Approve/Revise/Reject buttons were delivered, and implementation after approval was expected.";if(t.approvalState==="approved")return"Approval interpretation: explicit plan approval was recorded before implementation, so leaving plan-only mode was expected."}if(t.approvalExecutionState==="implemented_without_required_approval")return"Approval interpretation: implementation left plan-only mode without a recorded approval."}}function fg(){return/https?:\/\/github\.com\/[^\s)]+\/[^\s)]+\/pull\/(\d+)(?=[\s).,;:]|$)/gi}function gg(){return/https?:\/\/\S+/gi}function no(t){let e=mg(t);return[`Requested permission mode: ${t.requestedPermissionMode??"unknown"}`,`Effective permission mode: ${t.currentPermissionMode??"unknown"}`,`Deterministic approval/execution state: ${t.approvalExecutionState??"unknown"}`,...e?[e]:[]]}function Zi(t){switch(t){case"user":return"Stopped by user";case"shutdown":return"Stopped by shutdown";case"startup-timeout":return"Stopped by startup timeout";case"unknown":case void 0:return"Stopped unexpectedly";default:return"Stopped"}}function hg(){return{requiresShortFactualSummary:!0,owner:"agent",appliesToOrdinaryTerminalCompletions:!0}}function yg(){return{requiresShortFactualSummary:!0,owner:"agent",appliesToWorktreeTerminalOutcomes:!0}}function kg(){return{requiresShortFactualSummary:!0,owner:"agent",appliesToGoalTaskCompletions:!0}}function Xi(t){let{sessionId:e,canonicalStatusDetail:n,canonicalStatusDelivered:r=!0,hasOriginRouteBlock:o=!1}=t,i=o?["7. Before sending that follow-up, honor the Session origin route block above. If originRoute differs from the current chat, do NOT use a plain final assistant reply; use a routed send path that preserves provider/target/threadId."]:[],s=o?8:7,l=o?9:8;return["[ACTION REQUIRED] Follow your autonomy rules for session completion:",`1. Use agent_output(session='${e}', full=true) to read the full result.`,"2. If this is part of a multi-phase pipeline, launch the next phase NOW — do not wait for user input.",`3. ${n??(r?"The plugin already sent the canonical completion status to the user.":"The plugin did not confirm delivery of the canonical completion status to the user.")}`,"4. Treat the completed session output as source material, not visible delivery. A meaningful final summary inside agent_output is not enough to skip, because the user may only have seen the plugin's terse status line.","5. If the visible result is only the plugin's terse status line, use the full output to send the user one short factual completion summary for this completed session. Do this even when agent_output already contains a good final summary.","6. This requirement applies to ordinary terminal/manual completions too, not just delegated worktree decisions.",...i,`${s}. That follow-up belongs to you alone; keep it brief, concrete, and grounded in reliable result data. Send at most one orchestrator-owned human summary for this terminal/worktree outcome.`,...r?[`${l}. Do NOT repeat the plugin's status line, and do NOT rely on the plugin to summarize the completed work for you.`]:[`${l}. Because canonical status delivery was not confirmed, account for that gap yourself when you follow up; do NOT assume the plugin already reached the user.`],`${l+1}. Send a normal concise final response after any routed follow-up is visibly sent. Do not use marker text, do not answer NO_REPLY, and do not ask the user whether they want the summary.`]}function Sg(t){let{contract:e,canonicalStatusDelivered:n}=t;return["Completion diagnostics:",`- Canonical completion status delivered to user: ${n?"yes":"no"}`,`- Plugin requested short factual follow-up summary: ${e.requiresShortFactualSummary?"yes":"no"}`,`- Contract applies to ordinary terminal/manual completions: ${e.appliesToOrdinaryTerminalCompletions?"yes":"no"}`]}function es(t){let{session:e,originThreadLine:n,preview:r}=t,o=!!n.trim(),i=`$${(e.costUsd??0).toFixed(2)}`,s=Re(e.duration),l=hg(),a=d=>["Coding agent session completed.",`Name: ${e.name} | ID: ${e.id}`,`Status: ${e.status}`,...o?[n]:[],...no(e),"","Output preview:",r,"",...Sg({contract:l,canonicalStatusDelivered:d}),"",...Xi({sessionId:e.id,canonicalStatusDelivered:d,hasOriginRouteBlock:o})].join(`
183
- `);return{userMessage:`✅ [${e.name}] Completed | ${i} | ${s}${Zn({harness:e.harnessName,model:e.model})}`,wakeMessageOnNotifySuccess:a(!0),wakeMessageOnNotifyFailed:a(!1),followupContract:l}}function Ft(t){let e=yg(),n=!!t.originThreadLine.trim(),r=(t.detailLines??[]).map(i=>bd(i).trim()).filter(i=>i.length>0),o=bd(t.outcomeLine);return["Worktree follow-through outcome recorded.",`Name: ${t.sessionName??"unknown"} | ID: ${t.sessionId}`,...n?[t.originThreadLine]:[],"","Canonical outcome status:",o,...r.length>0?["","Outcome details:",...r.map(i=>`- ${i}`)]:[],"","Completion diagnostics:",`- Canonical worktree status delivered to user: ${t.canonicalStatusDelivered?"yes":"no"}`,`- Plugin requested short factual follow-up summary: ${e.requiresShortFactualSummary?"yes":"no"}`,`- Contract applies to worktree terminal outcomes: ${e.appliesToWorktreeTerminalOutcomes?"yes":"no"}`,"","[ACTION REQUIRED] Follow your autonomy rules for worktree follow-through:",`1. Use agent_output(session='${t.sessionId}', full=true) to read the full result if output is available.`,"2. Treat the completed session output as source material, not visible delivery. A meaningful final summary inside agent_output is not enough to skip, because the user may only have seen the plugin's terse status line.","3. Use the full output plus the canonical outcome facts above to send the user one short factual outcome summary. Do this even when agent_output already contains a good final summary.","4. If full output is unavailable or not meaningful, say only what is proven by the merge/PR facts above; do not invent task details.","5. Mention blockers such as push failure when present; do not describe a local-only merge as pushed.","6. Do not include raw PR URLs in the follow-up summary. The plugin already posted the PR link in the canonical status; refer to PRs by number, repo, and branch instead.",...n?["7. Before sending that follow-up, honor the Session origin route block above. If originRoute differs from the current chat, do NOT use a plain final assistant reply; use a routed send path that preserves provider/target/threadId."]:[],`${n?8:7}. Do NOT repeat only the plugin status line; keep the follow-up brief, concrete, and non-duplicative. Send at most one human-visible summary for this terminal/worktree outcome, counting summaries already sent by the foreground assistant turn or routed message tools.`,`${n?9:8}. Send a normal concise final response after any routed follow-up is visibly sent. Do not use marker text, do not answer NO_REPLY, and do not ask the user whether they want the summary.`].join(`
184
- `)}function ts(t){let e=kg(),n=!!t.originThreadLine.trim();return["Goal task succeeded.",`Task: ${t.taskName}`,`Name: ${t.sessionName??t.taskName} | ID: ${t.sessionId}`,...n?[t.originThreadLine]:[],"","Canonical goal status:",t.summary,"","Completion diagnostics:",`- Canonical goal success status delivered to user: ${t.canonicalStatusDelivered?"yes":"no"}`,`- Plugin requested short factual follow-up summary: ${e.requiresShortFactualSummary?"yes":"no"}`,`- Contract applies to goal task completions: ${e.appliesToGoalTaskCompletions?"yes":"no"}`,"","[ACTION REQUIRED] Follow your autonomy rules for goal task completion:",`1. Use agent_output(session='${t.sessionId}', full=true) to read the full result if output is available.`,"2. Treat the completed session output as source material, not visible delivery. A meaningful final summary inside agent_output is not enough to skip, because the user may only have seen the plugin's terse goal status line.","3. Send the user one short factual completion summary grounded in the full output plus the canonical goal status above. Do this even when agent_output already contains a good final summary.","4. If full output is unavailable or not meaningful, say only what is proven by the goal status above; do not invent task details.",...n?["5. Before sending that follow-up, honor the Session origin route block above. If originRoute differs from the current chat, do NOT use a plain final assistant reply; use a routed send path that preserves provider/target/threadId."]:[],`${n?6:5}. Do NOT repeat only the plugin status line; keep the follow-up brief, concrete, and non-duplicative. Send at most one human-visible summary for this goal success outcome, counting summaries already sent by the foreground assistant turn or routed message tools.`,`${n?7:6}. Send a normal concise final response after any routed follow-up is visibly sent. Do not use marker text, do not answer NO_REPLY, and do not ask the user whether they want the summary.`].join(`
185
- `)}function bd(t){return t.replace(fg(),"PR #$1").replace(gg(),"[link omitted]")}function ns(t){let{session:e,originThreadLine:n,errorSummary:r,preview:o,worktreeAutoCleaned:i,failedButtons:s}=t,l=o.trim()?["","Output preview:",o]:[],a=i?["","Note: Worktree and branch were auto-removed (zero cost, startup failure)."]:[],d=`$${(e.costUsd??0).toFixed(2)}`,u=Re(e.duration);return{userMessage:[`❌ [${e.name}] Failed | ${d} | ${u}${Zn({harness:e.harnessName,model:e.model})}`,` ⚠️ ${r}`].join(`
186
- `),wakeMessage:["Coding agent session failed.",`Name: ${e.name} | ID: ${e.id}`,`Status: ${e.status}`,n,...no(e),...e.harnessSessionId?[`Backend conversation ID: ${e.harnessSessionId}`]:[],"","Failure summary:",r,...l,...a,"","[ACTION REQUIRED] Follow your autonomy rules for session failure:",`1. Use agent_output(session='${e.id}', full=true) to inspect the full failure context.`,`2. Continue the same session with agent_respond(session='${e.id}', message='<next instruction>').`,` If you intentionally want to fork or switch harnesses, launch a new session with agent_launch(resume_session_id='${e.id}', fork_session=true, ...)`," If the failure is a launch/config issue, relaunch fresh with agent_launch(prompt=...).","3. Notify the user with the failure cause and the next action you are taking."].join(`
187
- `),buttons:s}}function rs(t){let{session:e,originThreadLine:n,preview:r}=t,o=`$${(e.costUsd??0).toFixed(2)}`;return{userMessage:`⏸️ [${e.name}] Turn completed | ${o}${Zn({harness:e.harnessName,model:e.model})}`,wakeMessage:["Coding agent session turn ended.",`Name: ${e.name}`,`ID: ${e.id}`,`Status: ${e.status}`,`Lifecycle: ${e.lifecycle}`,"","Last output (~20 lines):",r,...n?["",n]:[]].join(`
188
- `)}}function os(t){let{sessionName:e,sessionId:n,branchName:r,baseBranch:o,promptSnippet:i,commitLines:s,moreNote:l,originThreadLine:a,diffSummary:d,allowedActions:u,policyReason:c}=t,m=!!a?.trim();return[`[DELEGATED WORKTREE DECISION] Session "${e}" completed with changes.`,"",`Session ID: ${n}`,`Branch: ${r} → ${o}`,`Commits: ${d.commits} | Files: ${d.filesChanged} | +${d.insertions} / -${d.deletions}`,...m?[a]:[],"",...s,...l?[l]:[],"","Original task prompt (first 500 chars):",i,"",...c?[`Policy constraint: ${c}`,""]:[],"You own the next step for this worktree.",...u?.merge===!1?["- Do not call agent_merge(); repo policy does not allow direct merge for this session."]:[`- Merge immediately with agent_merge(session="${e}", base_branch="${o}") if the changes are clearly in-scope and low-risk.`],...u?.pr===!1?["- Do not call agent_pr(); PR creation is unavailable or forbidden by repo policy."]:[`- If a PR is safer or human choice is needed, call agent_request_worktree_decision(session="${e}", summary="...") so the user gets the canonical Merge/Open PR/Later/Discard buttons.`],`- If scope or risk is unclear, call agent_request_worktree_decision(session="${e}", summary="...") with a concise risk summary instead of sending a plain-text-only question.`,"- Never call agent_pr() autonomously in delegate mode.","- After deciding, notify the user briefly with what you did and why.",...m?["- Send any human follow-up to the Session origin route above; if it differs from the current chat, do not use a plain final assistant reply."]:[]].join(`
189
- `)}function is(t,e){return[`[DELEGATED WORKTREE DECISION REMINDER] Session "${t.name}" still has an unresolved worktree decision.`,"",`Session ID: ${t.sessionId??t.harnessSessionId}`,`Branch: ${t.worktreeBranch??"unknown"}`,`Pending: ${e}h`,"","Resolve it now:",`- agent_merge(session="${t.name}") if the diff is clearly safe and in scope`,"- If a PR is safer, ask the user before agent_pr()","- If scope or risk is unclear, ask the user for guidance","- Never call agent_pr() autonomously in delegate mode"].join(`
190
- `)}function ss(t){let{sessionName:e,sessionId:n,cleanupSummary:r,preview:o,originThreadLine:i,requestedPermissionMode:s,currentPermissionMode:l,approvalExecutionState:a,approvalState:d,planApproval:u,approvalPromptStatus:c,approvalPromptMessageKind:m,approvalPromptDeliveredAt:p}=t,f=o.trim()?["","Output preview:",o]:[],h=!!i?.trim();return["Coding agent session completed with no repository changes.",`Name: ${e} | ID: ${n}`,`Worktree outcome: ${r}`,...h?[i]:[],...no({requestedPermissionMode:s,currentPermissionMode:l,approvalExecutionState:a,approvalState:d,planApproval:u,approvalPromptStatus:c,approvalPromptMessageKind:m,approvalPromptDeliveredAt:p}),...f,"",...Xi({sessionId:n,canonicalStatusDetail:"The plugin already sent the canonical completion status to the user, including that no repo changes were kept.",hasOriginRouteBlock:h})].join(`
191
- `)}var Id=3200,as=3e3,vg=2400,Pg=120,wg=5,bg=280,Rd=1400,Ad="- Additional plan details omitted for brevity.";function xd(t){return t.replace(/^#{1,6}\s+/,"").replace(/^[-*+]\s+/,"").replace(/^\d+[.)]\s+/,"").replace(/^`([^`]+)`$/,"$1").trim()}function Rg(t){return t.split(`
192
- `).map(e=>e.trim()).filter(Boolean).map(xd).map(e=>se(e,220)).filter(e=>e.length>0).filter(e=>!/^(plan|proposed plan|implementation plan|review summary|full plan)[:]?$/i.test(e)).filter(e=>!/^(should|can|could|would|will)\b.*\?$/i.test(e)).filter(e=>!/^(thinking|checking|considering|analyzing)\b/i.test(e))}function Ag(t){return t.split(`
193
- `).map(e=>e.trim()).filter(Boolean).map(xd).filter(e=>e.length>0).filter(e=>!/^(plan|proposed plan|implementation plan|review summary|summary|why this was escalated|full plan)[:]?$/i.test(e)).filter(e=>!/^(should|can|could|would|will)\b.*\?$/i.test(e)).filter(e=>!/^(thinking|checking|considering|analyzing)\b/i.test(e))}function ls(t){let e=Rg(t);return e.length===0?`Review summary:
175
+ `),o=Ad(r);if(!o){this.markTaskFailedWaitingForUser(e,ze(r,24)||"The session is waiting for user input.");return}let i=await ve(this.sessionManager,{session:n.id,message:o,userInitiated:!1});if(i.isError||i.text.includes("Auto-respond limit reached")){this.markTaskFailedWaitingForUser(e,i.text);return}e.status="running",e.waitingForUserReason=void 0,e.updatedAt=Date.now(),this.store.upsert(e)}async resumeAfterIdleTimeout(e,n,r){try{let o=await this.resumeTaskSession(e,r,n);this.setTaskRunningWithSession(e,o),this.notifyIterationStatus(e,`🔄 [${e.name}] Goal task resumed after idle timeout`,o),this.scheduleTaskEvaluation(e.id,"idle-timeout-resume",o.id)}catch(o){this.markTaskFailed(e,`Failed to resume the goal task after idle timeout: ${dt(o)}`)}}async handleTerminalSession(e,n){if(n.status==="failed"){this.markTaskFailed(e,kg(n));return}if(n.status==="killed"&&n.killReason==="user"){this.markTaskStopped(e,"Stopped by user.");return}if(n.status==="killed"&&n.killReason==="idle-timeout"){let s=n.getOutput(60).join(`
176
+ `);if(n.pendingPlanApproval){let a=await ve(this.sessionManager,{session:n.id,message:"Approved. Implement the plan.",approve:!0,userInitiated:!1});if(a.isError){this.markTaskFailed(e,a.text);return}let l=this.sessionManager.resolve(n.id);if(!l){this.markTaskFailed(e,"Failed to resolve the resumed goal task session after idle timeout plan approval.");return}this.attachSessionObservers(e,l),this.setTaskRunningWithSession(e,l),this.notifyIterationStatus(e,`🔄 [${e.name}] Goal task resumed after idle timeout`,l),this.scheduleTaskEvaluation(e.id,"idle-timeout-plan-resume",l.id);return}if(n.pendingInputState){let a=Ad(s);if(!a){this.markTaskFailed(e,`Goal task was waiting for user input and cannot continue autonomously: ${ze(s,24)||"The goal task hit idle timeout while waiting for user input."}`);return}await this.resumeAfterIdleTimeout(e,n,["The previous session hit idle timeout while waiting for a response.",`Use this response and continue the goal: ${a}`].join(`
177
+
178
+ `));return}await this.resumeAfterIdleTimeout(e,n,Id(e));return}if(n.status==="killed"&&n.killReason!=="done"){this.markTaskFailed(e,`Underlying session was killed (${n.killReason}).`);return}if(e.loopMode==="ralph"){let s=n.getOutput(200).join(`
179
+ `),a=Pd(e.completionPromise);if(yg(s,a)){if(e.verifierCommands.length===0){this.markTaskSucceeded(e,`Completion promise "${a}" detected in agent output.`);return}let p=await this.runVerifiers(e);if(e.lastVerifierSummary=p.summary,e.updatedAt=Date.now(),p.status==="pass"){this.markTaskSucceeded(e,[`Completion promise "${a}" detected.`,p.summary].join(`
180
+ `));return}if(e.lastVerifierFingerprint===p.fingerprint?e.repeatedFailureCount+=1:e.repeatedFailureCount=1,e.lastVerifierFingerprint=p.fingerprint,e.iteration+1>=e.maxIterations){this.markTaskFailed(e,[`Goal task emitted completion promise but verifiers still failed before hitting the iteration budget (${e.maxIterations}).`,p.summary].join(`
181
+ `));return}e.iteration+=1;let g=hg(e,p),m=Vr({output:s,verifierSummary:p.summary,completionPromise:a,completionDetected:!0});try{let f=await this.resumeTaskSession(e,g,n);this.setTaskRunningWithSession(e,f),this.notifyIterationStatus(e,`🔁 [${e.name}] Completion claimed but verifiers still failed`,void 0,m),this.scheduleTaskEvaluation(e.id,"ralph-verifier-resume",f.id)}catch(f){this.markTaskFailed(e,`Failed to resume the Ralph goal task after verifier failure: ${dt(f)}`)}return}let d=pg(s);if(e.lastVerifierFingerprint===d?e.repeatedFailureCount+=1:e.repeatedFailureCount=1,e.lastVerifierFingerprint=d,e.iteration+1>=e.maxIterations){this.markTaskFailed(e,[`Completion promise "${a}" was not emitted before hitting the iteration budget (${e.maxIterations}).`,"Latest output:",ze(s,20)||"(no output)"].join(`
182
+ `));return}e.iteration+=1;let u=gg(e,s),c=Vr({output:s,completionPromise:a,completionDetected:!1});try{let p=await this.resumeTaskSession(e,u,n);this.setTaskRunningWithSession(e,p),this.notifyIterationStatus(e,`🔁 [${e.name}] Continued`,void 0,c),this.scheduleTaskEvaluation(e.id,"ralph-continue",p.id)}catch(p){this.markTaskFailed(e,`Failed to continue the Ralph goal task: ${dt(p)}`)}return}let r=await this.runVerifiers(e);if(e.lastVerifierSummary=r.summary,e.updatedAt=Date.now(),r.status==="pass"){this.markTaskSucceeded(e,r.summary);return}if(e.lastVerifierFingerprint===r.fingerprint?e.repeatedFailureCount+=1:e.repeatedFailureCount=1,e.lastVerifierFingerprint=r.fingerprint,e.iteration+1>=e.maxIterations){this.markTaskFailed(e,[`Verifier did not pass before hitting the iteration budget (${e.maxIterations}).`,r.summary].join(`
183
+ `));return}e.iteration+=1;let o=fg(e,r),i=Vr({verifierSummary:r.summary});try{let s=await this.resumeTaskSession(e,o,n);this.setTaskRunningWithSession(e,s),this.notifyIterationStatus(e,`🔁 [${e.name}] Repair iteration started after verifier failure`,void 0,i),this.scheduleTaskEvaluation(e.id,"repair-resume",s.id)}catch(s){this.markTaskFailed(e,`Failed to resume the goal task: ${dt(s)}`)}}async evaluateTask(e,n,r){this.restorePromise&&await this.restorePromise;let o=this.store.get(e);o&&await this.reconcileTask(o,n,r)}async reconcileTask(e,n="manual",r){if(!(e.status==="succeeded"||e.status==="failed"||e.status==="stopped")){if(this.inFlight.has(e.id)){this.dirtyEvaluations.add(e.id),!this.dirtyEvaluationSessionIds.get(e.id)&&r?this.dirtyEvaluationSessionIds.set(e.id,r):this.dirtyEvaluationSessionIds.has(e.id)||this.dirtyEvaluationSessionIds.set(e.id,r);return}this.inFlight.add(e.id);try{if(r&&e.sessionId&&e.sessionId!==r){let i=this.sessionManager.resolve(r);if(i&&(i.status==="completed"||i.status==="failed"||i.status==="killed"))return}let o=r?this.sessionManager.resolve(r)??(e.sessionId?this.sessionManager.resolve(e.sessionId):void 0):e.sessionId?this.sessionManager.resolve(e.sessionId):void 0;if(e.status==="waiting_for_user"){this.markTaskFailed(e,"Goal task was waiting for user input and cannot continue autonomously");return}if(bd(e)){this.markTaskFailed(e,Xr());return}if(!o){this.markTaskFailed(e,"Underlying session could not be found.");return}if(e.sessionName=o.name,e.harnessSessionId=o.harnessSessionId,e.route=o.route??e.route,e.updatedAt=Date.now(),this.store.upsert(e),o.status==="starting"||o.status==="running"){await this.handleRunningSession(e,o);return}await this.handleTerminalSession(e,o)}finally{if(this.inFlight.delete(e.id),this.dirtyEvaluations.has(e.id)){this.dirtyEvaluations.delete(e.id);let o=this.dirtyEvaluationSessionIds.get(e.id);this.dirtyEvaluationSessionIds.delete(e.id),this.scheduleTaskEvaluation(e.id,`${n}:dirty`,o)}}}}};import{createHash as Du}from"crypto";se();import{existsSync as wg,realpathSync as Pg}from"fs";import{resolve as bg}from"path";function _d(t){if(!t)return;let e=bg(t);try{if(wg(e))return Pg.native(e)}catch{}return e}function to(t,e){return!t||!e?!1:_d(t)===_d(e)}X();se();import{existsSync as Rg}from"fs";X();ke();function $d(t){return t instanceof Error?t.message:String(t)}function Ag(t){let e=t.worktreeStrategy??D.defaultWorktreeStrategy;return!!e&&e!=="off"&&yi(sn({harnessName:t.harness??le(),backendRef:t.backendRef}))}function Ig(t,e,n,r){let o=["","You are working in a git worktree.",`Worktree path: ${n}`,`Branch: ${r}`,"",`IMPORTANT: ALL file edits must be made within this worktree at ${n}.`,`Do NOT edit files directly in ${e} (the original workspace).`,`If your task references files by absolute path under ${e}, rewrite those`,"paths relative to your current working directory. For example:",` "${e}/src/file.py" → use relative path "src/file.py"`,"","Before finishing, run `git status --short` in this worktree.","If you made actual task changes, commit all of them to this branch before finishing.","Use `git add` and `git commit`. If no repository changes are needed, leave the worktree clean before finishing.","Do NOT run `git checkout`, `git switch`, or `git reset --hard` as these will detach or corrupt the worktree HEAD.","","When making changes, please note:","- Do NOT commit planning documents, investigation notes, or analysis artifacts to this branch","- Only commit actual code, configuration, tests, and documentation changes that were explicitly requested as part of the task"].join(`
184
+ `);return(t??"")+o}function xg(t,e){let n=t.resumeWorktreeFrom??t.resumeSessionId;if(!n)return{};let r=e(n);if(!r)return{};let o=!!r.harness||!!r.backendRef,i=(()=>{if(r.workdir&&r.workdir!==r.worktreePath)return r.workdir;if(r.worktreePath){let a=fr(r.worktreePath);return r.workdir&&a&&to(r.workdir,a)?r.workdir:a??r.workdir}return r.workdir})();if(t.worktreeStrategy||(r.worktreeLifecycle?.state==="pr_open"||r.worktreePrUrl?t.worktreeStrategy="auto-pr":r.worktreeStrategy&&(t.worktreeStrategy=r.worktreeStrategy)),!t.planApproval&&r.planApproval&&(t.planApproval=r.planApproval),!r.worktreePath){let a=o&&Yn(sn({persistedHarness:r.harness,backendRef:r.backendRef}));return{originalWorkdir:i,canCreateManagedWorktreeForResumeWithoutPersistedPath:a}}if(!r.worktreeBranch)throw new Error(`Cannot resume session "${n}": persisted worktree metadata is missing worktreeBranch.`);let s=Yn(sn({persistedHarness:r.harness,backendRef:r.backendRef}))&&!!r.backendRef?.worktreePath;if(Rg(r.worktreePath))return`${r.worktreePath}`,{actualWorkdir:r.worktreePath,originalWorkdir:i??r.worktreePath,worktreePath:r.worktreePath,worktreeBranchName:r.worktreeBranch};if(!i)return`${r.worktreePath}`,{clearedResumeSessionId:!!t.resumeSessionId,clearedResumeWorktreeFrom:!!t.resumeWorktreeFrom};if(s)return`${r.worktreePath}`,{actualWorkdir:i,originalWorkdir:i,worktreeBranchName:r.worktreeBranch,clearedResumeWorktreeFrom:!!t.resumeWorktreeFrom,restoredMissingNativeBackendWorktree:!0};try{hr(i);let a=Ri(i,r.worktreeBranch.replace(/^agent\//,""),{allowExistingBranch:!0});return`${r.worktreeBranch}${a}`,{actualWorkdir:a,originalWorkdir:i,worktreePath:a,worktreeBranchName:r.worktreeBranch}}catch(a){return`${$d(a)}`,{actualWorkdir:i,originalWorkdir:i,clearedResumeSessionId:!!t.resumeSessionId,clearedResumeWorktreeFrom:!!t.resumeWorktreeFrom,failedResumeWorktreeRestore:!0}}}function Ed(t,e,n){let{actualWorkdir:r,originalWorkdir:o,worktreePath:i,worktreeBranchName:s,clearedResumeSessionId:a,clearedResumeWorktreeFrom:l,restoredMissingNativeBackendWorktree:d,canCreateManagedWorktreeForResumeWithoutPersistedPath:u,failedResumeWorktreeRestore:c}=xg(t,n);a&&(t.resumeSessionId=void 0),l&&(t.resumeWorktreeFrom=void 0),r??=t.workdir,o??=t.workdir;let p=!!(t.resumeSessionId??t.resumeWorktreeFrom),g=t.worktreeStrategy??D.defaultWorktreeStrategy;g&&(t.worktreeStrategy=g);let m=Ag(t),y=(!p||!!u)&&!d&&!i&&g&&g!=="off"&&!m;if(c&&g&&g!=="off")throw new Error(`Cannot launch session "${e}": worktree strategy "${g}" was requested, but no isolated worktree was prepared. Launch with worktree_strategy "off" only when running in the base checkout is intentional.`);if(m&&!Pi(o))throw new Error(`Cannot launch session "${e}": worktree strategy "${g}" requires a git worktree, but "${o}" is not a git repository.`);if(y&&Pi(o)){if(!Va(o))throw new Error(`Cannot launch session "${e}": insufficient space for worktree creation.`);try{if(i=Ri(o,e),r=i,s=xt(i),!s)throw new Error(`created worktree at ${i} but failed to resolve branch name`);`${i}`}catch(S){throw new Error(`Cannot launch session "${e}": worktree creation failed: ${$d(S)}`)}}else if(y)throw new Error(`Cannot launch session "${e}": worktree strategy "${g}" requires a git worktree, but "${o}" is not a git repository.`);if(p&&i&&(r=i),g&&g!=="off"&&!i)throw new Error(`Cannot launch session "${e}": worktree strategy "${g}" was requested, but no isolated worktree was prepared. Launch with worktree_strategy "off" only when running in the base checkout is intentional.`);return{actualWorkdir:r,originalWorkdir:o,effectiveSystemPrompt:i&&s?Ig(t.systemPrompt,o,i,s):t.systemPrompt,worktreePath:i,worktreeBranchName:s,clearedResumeSessionId:a,clearedResumeWorktreeFrom:l,restoredMissingNativeBackendWorktree:d,failedResumeWorktreeRestore:c}}var no=class{constructor(e){this.getPersistedSession=e}getPersistedSession;prepareSpawn(e,n){return Ed(e,n,this.getPersistedSession)}hydrateSpawnedSession(e,n,r){r.worktreeStrategy&&r.worktreeStrategy!=="off"&&(e.originalWorkdir=n.originalWorkdir),n.worktreePath&&(e.worktreePath=n.worktreePath,e.worktreeBranch=n.worktreeBranchName,e.worktreeState="provisioned"),r.worktreePrTargetRepo&&(e.worktreePrTargetRepo=r.worktreePrTargetRepo)}};X();var ro=class{constructor(e){this.deps=e}deps;applySessionPatch(e,n){let r=this.normalizeCompletionWakePatch(n),o=this.deps.store.getPersistedSession(e);o&&(Object.assign(o,r),this.deps.store.assertPersistedEntry(o));let i=this.findActiveSessionForRef(e,o);return i&&this.applyPatchToActiveSession(i,r),!o&&!i?!1:(o&&this.deps.store.saveIndex(),!0)}normalizeCompletionWakePatch(e){return"completionWakeSucceededAt"in e&&e.completionWakeSucceededAt||"completionWakeSkippedAt"in e&&e.completionWakeSkippedAt?{...e,completionWakeSummaryRequired:void 0}:e}matchesExistingSession(e,n){if(!n)return!1;let r=$(e),o=$(n);return!!(n.sessionId&&e.id===n.sessionId||o&&o===r||n?.harnessSessionId&&e.harnessSessionId===n.harnessSessionId||n?.name&&e.name===n.name)}findActiveSessionForRef(e,n){let r=this.deps.resolveSession(e);if(r)return r;for(let o of this.deps.sessions.values())if(U(o)===e||$(o)===e||o.harnessSessionId===e||this.matchesExistingSession(o,n))return o}applyPatchToActiveSession(e,n){this.applyControlStatePatch(e,n),this.applySessionMetadataPatch(e,n),this.applyWorktreeMetadataPatch(e,n)}applyControlStatePatch(e,n){let r={};if(this.copyControlPatchField(r,n,"lifecycle"),this.copyControlPatchField(r,n,"approvalState"),this.copyControlPatchField(r,n,"approvalExecutionState"),this.copyControlPatchField(r,n,"worktreeState"),this.copyControlPatchField(r,n,"runtimeState"),this.copyControlPatchField(r,n,"deliveryState"),this.copyControlPatchField(r,n,"requestedPermissionMode"),this.copyControlPatchField(r,n,"currentPermissionMode"),this.copyControlPatchField(r,n,"pendingPlanApproval"),this.copyControlPatchField(r,n,"planApprovalContext"),this.copyControlPatchField(r,n,"planDecisionVersion"),this.copyControlPatchField(r,n,"actionablePlanDecisionVersion"),this.copyControlPatchField(r,n,"canonicalPlanPromptVersion"),this.copyControlPatchField(r,n,"approvalPromptRequiredVersion"),this.copyControlPatchField(r,n,"approvalPromptVersion"),this.copyControlPatchField(r,n,"approvalPromptStatus"),this.copyControlPatchField(r,n,"approvalPromptTransport"),this.copyControlPatchField(r,n,"approvalPromptMessageKind"),this.copyControlPatchField(r,n,"approvalPromptLastAttemptAt"),this.copyControlPatchField(r,n,"approvalPromptDeliveredAt"),this.copyControlPatchField(r,n,"approvalPromptFailedAt"),this.copyControlPatchField(r,n,"planModeApproved"),this.copyControlPatchField(r,n,"pendingWorktreeDecisionSince"),typeof e.applyControlPatch=="function"){e.applyControlPatch(r);return}this.assignIfPresent(e,"lifecycle",n,"lifecycle"),this.assignIfPresent(e,"approvalState",n,"approvalState"),this.assignIfPresent(e,"approvalExecutionState",n,"approvalExecutionState"),this.assignIfPresent(e,"worktreeState",n,"worktreeState"),this.assignIfPresent(e,"runtimeState",n,"runtimeState"),this.assignIfPresent(e,"deliveryState",n,"deliveryState"),this.assignIfPresent(e,"requestedPermissionMode",n,"requestedPermissionMode"),this.assignIfPresent(e,"currentPermissionMode",n,"currentPermissionMode"),this.assignIfPresent(e,"pendingPlanApproval",n,"pendingPlanApproval"),this.assignIfPresent(e,"planApprovalContext",n,"planApprovalContext"),this.assignIfPresent(e,"planDecisionVersion",n,"planDecisionVersion"),this.assignIfPresent(e,"actionablePlanDecisionVersion",n,"actionablePlanDecisionVersion"),this.assignIfPresent(e,"canonicalPlanPromptVersion",n,"canonicalPlanPromptVersion"),this.assignIfPresent(e,"approvalPromptRequiredVersion",n,"approvalPromptRequiredVersion"),this.assignIfPresent(e,"approvalPromptVersion",n,"approvalPromptVersion"),this.assignIfPresent(e,"approvalPromptStatus",n,"approvalPromptStatus"),this.assignIfPresent(e,"approvalPromptTransport",n,"approvalPromptTransport"),this.assignIfPresent(e,"approvalPromptMessageKind",n,"approvalPromptMessageKind"),this.assignIfPresent(e,"approvalPromptLastAttemptAt",n,"approvalPromptLastAttemptAt"),this.assignIfPresent(e,"approvalPromptDeliveredAt",n,"approvalPromptDeliveredAt"),this.assignIfPresent(e,"approvalPromptFailedAt",n,"approvalPromptFailedAt"),this.setControlFieldIfPresent(e,"planModeApproved",n)}applySessionMetadataPatch(e,n){this.assignIfDefined(e,"approvalRationale",n.approvalRationale)}applyWorktreeMetadataPatch(e,n){this.assignIfDefined(e,"worktreePath",n.worktreePath),this.assignIfDefined(e,"worktreeBranch",n.worktreeBranch),this.assignIfDefined(e,"worktreePrUrl",n.worktreePrUrl),this.assignIfDefined(e,"worktreePrNumber",n.worktreePrNumber),this.assignIfDefined(e,"worktreeMerged",n.worktreeMerged),this.assignIfDefined(e,"worktreeMergedAt",n.worktreeMergedAt),this.assignIfDefined(e,"worktreeDisposition",n.worktreeDisposition),this.assignIfDefined(e,"worktreePrTargetRepo",n.worktreePrTargetRepo),this.assignIfDefined(e,"worktreePushRemote",n.worktreePushRemote),this.assignIfDefined(e,"worktreeLifecycle",n.worktreeLifecycle),"autoMergeParentSessionId"in n&&(e.autoMergeParentSessionId=n.autoMergeParentSessionId),"autoMergeConflictResolutionAttemptCount"in n&&(e.autoMergeConflictResolutionAttemptCount=n.autoMergeConflictResolutionAttemptCount),"autoMergeResolverSessionId"in n&&(e.autoMergeResolverSessionId=n.autoMergeResolverSessionId)}assignIfDefined(e,n,r){r!==void 0&&(e[n]=r)}assignIfPresent(e,n,r,o){Object.hasOwn(r,o)&&(e[n]=r[o])}copyControlPatchField(e,n,r){Object.hasOwn(n,r)&&(e[r]=n[r])}setControlFieldIfPresent(e,n,r){Object.hasOwn(r,n)&&e.setControlField?.(n,r[n])}};X();var Tg=new Set(["starting","running"]),oo=class{constructor(e,n){this.sessions=e;this.store=n}sessions;store;resolveActive(e){let n=this.sessions.get(e);return n||(this.findPreferredMatch(e,r=>r.name===e)??this.findPreferredMatch(e,r=>$(r)===e)??this.findPreferredMatch(e,r=>r.harnessSessionId===e))}getPersistedSession(e){return this.store.getPersistedSession(e)}resolveBackendConversationId(e){let n=this.resolveActive(e);return this.store.resolveBackendConversationId(e,n?$(n)??n.harnessSessionId:void 0)}findPreferredMatch(e,n){let r,o;for(let i of this.sessions.values())n(i,e)&&((!o||i.startedAt>o.startedAt)&&(o=i),Tg.has(i.status)&&(!r||i.startedAt>r.startedAt)&&(r=i));return r??o}};X();X();ke();import{existsSync as Cg}from"fs";var Dd=new Set(["merged","released","pr_open","dismissed","cleanup_failed"]),io=class{constructor(e){this.deps=e}deps;async plan(e){let n=U(e)??e.harnessSessionId;if(this.deps.isAlreadyMerged(n))return`${e.name}`,{kind:"skip",result:{notificationSent:!0,worktreeRemoved:!1}};let r=Dd.has(e.worktreeState)?e.worktreeState:e.worktreeLifecycle?.state&&Dd.has(e.worktreeLifecycle.state)?e.worktreeLifecycle.state:void 0;if(r&&!(r==="pr_open"&&e.worktreeStrategy==="auto-pr"))return`${e.name}${e.worktreeLifecycle?.state??e.worktreeState}`,{kind:"skip",result:{notificationSent:!0,worktreeRemoved:!1}};if(e.status!=="completed")return{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}};if(!this.deps.shouldRunWorktreeStrategy(e))return`${e.name}${e.phase}`,{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}};let o=e.worktreeStrategy;if(!o||o==="off"||o==="manual")return{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}};let i=e.worktreePath,s=this.deps.resolveWorktreeRepoDir(e.originalWorkdir,i),a=e.worktreeBranch;if(!s)return{kind:"notify",label:"worktree-missing-repo-dir",message:`⚠️ [${e.name}] Cannot determine the original repo for worktree ${i}. Manual inspection is required.`};if(!a)return{kind:"notify",label:"worktree-no-branch-name",message:`⚠️ [${e.name}] Cannot determine branch name for worktree ${i}. The worktree may have been removed or is in detached HEAD state. Manual cleanup may be needed.`};let l=de(e);if(l&&!Cg(i))return{kind:"no-change",repoDir:s,worktreePath:i,nativeBackendWorktree:l};let d=e.worktreeBaseBranch??Me(s),u=this.deps.getWorktreeCompletionState(s,i,a,d);if(u==="no-change")return{kind:"no-change",repoDir:s,worktreePath:i,nativeBackendWorktree:l};if(u==="merged")return{kind:"merged",repoDir:s,worktreePath:i,branchName:a,nativeBackendWorktree:l};if(u==="released")return{kind:"released",repoDir:s,worktreePath:i,branchName:a,nativeBackendWorktree:l,reasons:["merge_noop_content_already_on_base"]};if(u==="base-advanced")return{kind:"notify",label:"worktree-no-commits-ahead",message:`⚠️ [${e.name}] Auto-merge: branch '${a}' has no commits ahead of '${d}', but '${d}' has new commits — commits likely landed outside the worktree branch. Verify that commits were not made directly to '${d}' instead of the worktree branch. Worktree: ${i}`};if(u==="dirty-uncommitted")return{kind:"dirty-uncommitted",worktreePath:i,branchName:a,baseBranch:d};let c=We(s,a,d);if(!c)return`${a}`,{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}};let p=e.repoIntegrationPolicy?void 0:this.deps.resolveRepoPolicy?.(s),g=Il({requestedStrategy:o,policy:e.repoIntegrationPolicy??p?.policy,prAvailable:e.repoIntegrationPolicy?this.deps.isPrAvailable(s):p?.prAvailable??this.deps.isPrAvailable(s)});return g.strategy?{kind:"decision",strategy:g.strategy,policyReason:g.reason,policyBlocked:g.blocked,allowedActions:g.allowedActions,repoDir:s,worktreePath:i,branchName:a,baseBranch:d,diffSummary:c,sessionRef:n??void 0}:{kind:"skip",result:{notificationSent:!1,worktreeRemoved:!1}}}};Sn();function Mg(t){if(t.requestedPermissionMode==="plan"){if(t.approvalExecutionState==="approved_then_implemented"){if(t.planApproval==="ask"&&t.approvalPromptStatus==="delivered"&&t.approvalPromptMessageKind==="canonical_buttons"&&t.approvalPromptDeliveredAt)return"Approval interpretation: canonical Approve/Revise/Reject buttons were delivered, and implementation after approval was expected.";if(t.approvalState==="approved")return"Approval interpretation: explicit plan approval was recorded before implementation, so leaving plan-only mode was expected."}if(t.approvalExecutionState==="implemented_without_required_approval")return"Approval interpretation: implementation left plan-only mode without a recorded approval."}}function _g(){return/https?:\/\/github\.com\/[^\s)]+\/[^\s)]+\/pull\/(\d+)(?=[\s).,;:]|$)/gi}function $g(){return/https?:\/\/\S+/gi}function so(t){let e=Mg(t);return[`Requested permission mode: ${t.requestedPermissionMode??"unknown"}`,`Effective permission mode: ${t.currentPermissionMode??"unknown"}`,`Deterministic approval/execution state: ${t.approvalExecutionState??"unknown"}`,...e?[e]:[]]}function is(t){switch(t){case"user":return"Stopped by user";case"shutdown":return"Stopped by shutdown";case"startup-timeout":return"Stopped by startup timeout";case"unknown":case void 0:return"Stopped unexpectedly";default:return"Stopped"}}function Eg(){return{requiresShortFactualSummary:!0,owner:"agent",appliesToOrdinaryTerminalCompletions:!0}}function Dg(){return{requiresShortFactualSummary:!0,owner:"agent",appliesToWorktreeTerminalOutcomes:!0}}function Og(){return{requiresShortFactualSummary:!0,owner:"agent",appliesToGoalTaskCompletions:!0}}function ss(t){let{sessionId:e,canonicalStatusDetail:n,canonicalStatusDelivered:r=!0,hasOriginRouteBlock:o=!1}=t,i=o?["7. Before sending that follow-up, honor the Session origin route block above. If originRoute differs from the current chat, do NOT use a plain final assistant reply; use a routed send path that preserves provider/target/threadId."]:[],s=o?8:7,a=o?9:8;return["[ACTION REQUIRED] Follow your autonomy rules for session completion:",`1. Use agent_output(session='${e}', full=true) to read the full result.`,"2. If this is part of a multi-phase pipeline, launch the next phase NOW — do not wait for user input.",`3. ${n??(r?"The plugin already sent the canonical completion status to the user.":"The plugin did not confirm delivery of the canonical completion status to the user.")}`,"4. Treat the completed session output as source material, not visible delivery. A meaningful final summary inside agent_output is not enough to skip, because the user may only have seen the plugin's terse status line.","5. If the visible result is only the plugin's terse status line, use the full output to send the user one short factual completion summary for this completed session. Do this even when agent_output already contains a good final summary.","6. This requirement applies to ordinary terminal/manual completions too, not just delegated worktree decisions.",...i,`${s}. That follow-up belongs to you alone; keep it brief, concrete, and grounded in reliable result data. Send at most one orchestrator-owned human summary for this terminal/worktree outcome.`,...r?[`${a}. Do NOT repeat the plugin's status line, and do NOT rely on the plugin to summarize the completed work for you.`]:[`${a}. Because canonical status delivery was not confirmed, account for that gap yourself when you follow up; do NOT assume the plugin already reached the user.`],`${a+1}. Send a normal concise final response after any routed follow-up is visibly sent. Do not use marker text, do not answer NO_REPLY, and do not ask the user whether they want the summary.`]}function Wg(t){let{contract:e,canonicalStatusDelivered:n}=t;return["Completion diagnostics:",`- Canonical completion status delivered to user: ${n?"yes":"no"}`,`- Plugin requested short factual follow-up summary: ${e.requiresShortFactualSummary?"yes":"no"}`,`- Contract applies to ordinary terminal/manual completions: ${e.appliesToOrdinaryTerminalCompletions?"yes":"no"}`]}function as(t){let{session:e,originThreadLine:n,preview:r}=t,o=!!n.trim(),i=`$${(e.costUsd??0).toFixed(2)}`,s=Ae(e.duration),a=Eg(),l=d=>["Coding agent session completed.",`Name: ${e.name} | ID: ${e.id}`,`Status: ${e.status}`,...o?[n]:[],...so(e),"","Output preview:",r,"",...Wg({contract:a,canonicalStatusDelivered:d}),"",...ss({sessionId:e.id,canonicalStatusDelivered:d,hasOriginRouteBlock:o})].join(`
185
+ `);return{userMessage:`✅ [${e.name}] Completed | ${i} | ${s}${er({harness:e.harnessName,model:e.model})}`,wakeMessageOnNotifySuccess:l(!0),wakeMessageOnNotifyFailed:l(!1),followupContract:a}}function Ft(t){let e=Dg(),n=!!t.originThreadLine.trim(),r=(t.detailLines??[]).map(i=>Od(i).trim()).filter(i=>i.length>0),o=Od(t.outcomeLine);return["Worktree follow-through outcome recorded.",`Name: ${t.sessionName??"unknown"} | ID: ${t.sessionId}`,...n?[t.originThreadLine]:[],"","Canonical outcome status:",o,...r.length>0?["","Outcome details:",...r.map(i=>`- ${i}`)]:[],"","Completion diagnostics:",`- Canonical worktree status delivered to user: ${t.canonicalStatusDelivered?"yes":"no"}`,`- Plugin requested short factual follow-up summary: ${e.requiresShortFactualSummary?"yes":"no"}`,`- Contract applies to worktree terminal outcomes: ${e.appliesToWorktreeTerminalOutcomes?"yes":"no"}`,"","[ACTION REQUIRED] Follow your autonomy rules for worktree follow-through:",`1. Use agent_output(session='${t.sessionId}', full=true) to read the full result if output is available.`,"2. Treat the completed session output as source material, not visible delivery. A meaningful final summary inside agent_output is not enough to skip, because the user may only have seen the plugin's terse status line.","3. Use the full output plus the canonical outcome facts above to send the user one short factual outcome summary. Do this even when agent_output already contains a good final summary.","4. If full output is unavailable or not meaningful, say only what is proven by the merge/PR facts above; do not invent task details.","5. Mention blockers such as push failure when present; do not describe a local-only merge as pushed.","6. Do not include raw PR URLs in the follow-up summary. The plugin already posted the PR link in the canonical status; refer to PRs by number, repo, and branch instead.",...n?["7. Before sending that follow-up, honor the Session origin route block above. If originRoute differs from the current chat, do NOT use a plain final assistant reply; use a routed send path that preserves provider/target/threadId."]:[],`${n?8:7}. Do NOT repeat only the plugin status line; keep the follow-up brief, concrete, and non-duplicative. Send at most one human-visible summary for this terminal/worktree outcome, counting summaries already sent by the foreground assistant turn or routed message tools.`,`${n?9:8}. Send a normal concise final response after any routed follow-up is visibly sent. Do not use marker text, do not answer NO_REPLY, and do not ask the user whether they want the summary.`].join(`
186
+ `)}function ls(t){let e=Og(),n=!!t.originThreadLine.trim();return["Goal task succeeded.",`Task: ${t.taskName}`,`Name: ${t.sessionName??t.taskName} | ID: ${t.sessionId}`,...n?[t.originThreadLine]:[],"","Canonical goal status:",t.summary,"","Completion diagnostics:",`- Canonical goal success status delivered to user: ${t.canonicalStatusDelivered?"yes":"no"}`,`- Plugin requested short factual follow-up summary: ${e.requiresShortFactualSummary?"yes":"no"}`,`- Contract applies to goal task completions: ${e.appliesToGoalTaskCompletions?"yes":"no"}`,"","[ACTION REQUIRED] Follow your autonomy rules for goal task completion:",`1. Use agent_output(session='${t.sessionId}', full=true) to read the full result if output is available.`,"2. Treat the completed session output as source material, not visible delivery. A meaningful final summary inside agent_output is not enough to skip, because the user may only have seen the plugin's terse goal status line.","3. Send the user one short factual completion summary grounded in the full output plus the canonical goal status above. Do this even when agent_output already contains a good final summary.","4. If full output is unavailable or not meaningful, say only what is proven by the goal status above; do not invent task details.",...n?["5. Before sending that follow-up, honor the Session origin route block above. If originRoute differs from the current chat, do NOT use a plain final assistant reply; use a routed send path that preserves provider/target/threadId."]:[],`${n?6:5}. Do NOT repeat only the plugin status line; keep the follow-up brief, concrete, and non-duplicative. Send at most one human-visible summary for this goal success outcome, counting summaries already sent by the foreground assistant turn or routed message tools.`,`${n?7:6}. Send a normal concise final response after any routed follow-up is visibly sent. Do not use marker text, do not answer NO_REPLY, and do not ask the user whether they want the summary.`].join(`
187
+ `)}function Od(t){return t.replace(_g(),"PR #$1").replace($g(),"[link omitted]")}function ds(t){let{session:e,originThreadLine:n,errorSummary:r,preview:o,worktreeAutoCleaned:i,failedButtons:s}=t,a=o.trim()?["","Output preview:",o]:[],l=i?["","Note: Worktree and branch were auto-removed (zero cost, startup failure)."]:[],d=`$${(e.costUsd??0).toFixed(2)}`,u=Ae(e.duration);return{userMessage:[`❌ [${e.name}] Failed | ${d} | ${u}${er({harness:e.harnessName,model:e.model})}`,` ⚠️ ${r}`].join(`
188
+ `),wakeMessage:["Coding agent session failed.",`Name: ${e.name} | ID: ${e.id}`,`Status: ${e.status}`,n,...so(e),...e.harnessSessionId?[`Backend conversation ID: ${e.harnessSessionId}`]:[],"","Failure summary:",r,...a,...l,"","[ACTION REQUIRED] Follow your autonomy rules for session failure:",`1. Use agent_output(session='${e.id}', full=true) to inspect the full failure context.`,`2. Continue the same session with agent_respond(session='${e.id}', message='<next instruction>').`,` If you intentionally want to fork or switch harnesses, launch a new session with agent_launch(resume_session_id='${e.id}', fork_session=true, ...)`," If the failure is a launch/config issue, relaunch fresh with agent_launch(prompt=...).","3. Notify the user with the failure cause and the next action you are taking."].join(`
189
+ `),buttons:s}}function us(t){let{session:e,originThreadLine:n,preview:r}=t,o=`$${(e.costUsd??0).toFixed(2)}`;return{userMessage:`⏸️ [${e.name}] Turn completed | ${o}${er({harness:e.harnessName,model:e.model})}`,wakeMessage:["Coding agent session turn ended.",`Name: ${e.name}`,`ID: ${e.id}`,`Status: ${e.status}`,`Lifecycle: ${e.lifecycle}`,"","Last output (~20 lines):",r,...n?["",n]:[]].join(`
190
+ `)}}function cs(t){let{sessionName:e,sessionId:n,branchName:r,baseBranch:o,promptSnippet:i,commitLines:s,moreNote:a,originThreadLine:l,diffSummary:d,allowedActions:u,policyReason:c}=t,p=!!l?.trim();return[`[DELEGATED WORKTREE DECISION] Session "${e}" completed with changes.`,"",`Session ID: ${n}`,`Branch: ${r} → ${o}`,`Commits: ${d.commits} | Files: ${d.filesChanged} | +${d.insertions} / -${d.deletions}`,...p?[l]:[],"",...s,...a?[a]:[],"","Original task prompt (first 500 chars):",i,"",...c?[`Policy constraint: ${c}`,""]:[],"You own the next step for this worktree.",...u?.merge===!1?["- Do not call agent_merge(); repo policy does not allow direct merge for this session."]:[`- Merge immediately with agent_merge(session="${e}", base_branch="${o}") if the changes are clearly in-scope and low-risk.`],...u?.pr===!1?["- Do not call agent_pr(); PR creation is unavailable or forbidden by repo policy."]:[`- If a PR is safer or human choice is needed, call agent_request_worktree_decision(session="${e}", summary="...") so the user gets the canonical Merge/Open PR/Later/Discard buttons.`],`- If scope or risk is unclear, call agent_request_worktree_decision(session="${e}", summary="...") with a concise risk summary instead of sending a plain-text-only question.`,"- Never call agent_pr() autonomously in delegate mode.","- After deciding, notify the user briefly with what you did and why.",...p?["- Send any human follow-up to the Session origin route above; if it differs from the current chat, do not use a plain final assistant reply."]:[]].join(`
191
+ `)}function ps(t,e){return[`[DELEGATED WORKTREE DECISION REMINDER] Session "${t.name}" still has an unresolved worktree decision.`,"",`Session ID: ${t.sessionId??t.harnessSessionId}`,`Branch: ${t.worktreeBranch??"unknown"}`,`Pending: ${e}h`,"","Resolve it now:",`- agent_merge(session="${t.name}") if the diff is clearly safe and in scope`,"- If a PR is safer, ask the user before agent_pr()","- If scope or risk is unclear, ask the user for guidance","- Never call agent_pr() autonomously in delegate mode"].join(`
192
+ `)}function ms(t){let{sessionName:e,sessionId:n,cleanupSummary:r,preview:o,originThreadLine:i,requestedPermissionMode:s,currentPermissionMode:a,approvalExecutionState:l,approvalState:d,planApproval:u,approvalPromptStatus:c,approvalPromptMessageKind:p,approvalPromptDeliveredAt:g}=t,m=o.trim()?["","Output preview:",o]:[],f=!!i?.trim();return["Coding agent session completed with no repository changes.",`Name: ${e} | ID: ${n}`,`Worktree outcome: ${r}`,...f?[i]:[],...so({requestedPermissionMode:s,currentPermissionMode:a,approvalExecutionState:l,approvalState:d,planApproval:u,approvalPromptStatus:c,approvalPromptMessageKind:p,approvalPromptDeliveredAt:g}),...m,"",...ss({sessionId:n,canonicalStatusDetail:"The plugin already sent the canonical completion status to the user, including that no repo changes were kept.",hasOriginRouteBlock:f})].join(`
193
+ `)}var Ld=3200,fs=3e3,Ng=2400,Lg=120,Bg=5,Fg=280,Wd=1400,Nd="- Additional plan details omitted for brevity.";function Bd(t){return t.replace(/^#{1,6}\s+/,"").replace(/^[-*+]\s+/,"").replace(/^\d+[.)]\s+/,"").replace(/^`([^`]+)`$/,"$1").trim()}function qg(t){return t.split(`
194
+ `).map(e=>e.trim()).filter(Boolean).map(Bd).map(e=>ae(e,220)).filter(e=>e.length>0).filter(e=>!/^(plan|proposed plan|implementation plan|review summary|full plan)[:]?$/i.test(e)).filter(e=>!/^(should|can|could|would|will)\b.*\?$/i.test(e)).filter(e=>!/^(thinking|checking|considering|analyzing)\b/i.test(e))}function Kg(t){return t.split(`
195
+ `).map(e=>e.trim()).filter(Boolean).map(Bd).filter(e=>e.length>0).filter(e=>!/^(plan|proposed plan|implementation plan|review summary|summary|why this was escalated|full plan)[:]?$/i.test(e)).filter(e=>!/^(should|can|could|would|will)\b.*\?$/i.test(e)).filter(e=>!/^(thinking|checking|considering|analyzing)\b/i.test(e))}function gs(t){let e=qg(t);return e.length===0?`Review summary:
194
196
  - Plan details are available in the full session output.`:["Review summary:",...e.slice(0,6).map(n=>`- ${n}`)].join(`
195
- `)}function Ig(t){let e=[],n=!1;for(let o of t){let i=o.replace(/\s+/g," ").trim();if(!i)continue;let s=se(i,bg);s.length<i.length&&(n=!0);let l=`- ${s}`;if(e.length>=wg||[...e,l].join(`
196
- `).length>Rd){n=!0;break}e.push(l)}if(e.length===0)return["- Plan details are available in the full session output."];if(!n)return e;let r=[...e];for(;r.length>0&&[...r,Ad].join(`
197
- `).length>Rd;)r.pop();return[...r,Ad]}function ds(t){return Ig(Ag(t)).join(`
198
- `)}function xg(t,e){let n=[],r=t.trim();for(;r.length>e;){let o=r.lastIndexOf(" ",e);o<Math.floor(e*.6)&&(o=e),n.push(r.slice(0,o).trimEnd()),r=r.slice(o).trimStart()}return r.length>0&&n.push(r),n}function Tg(t,e){let n=t.split(`
199
- `),r=[],o="",i=()=>{o.trim().length>0&&(r.push(o.trimEnd()),o="")};for(let s of n){if(s.length>e){i();for(let a of xg(s,e))r.push(a);continue}let l=o.length>0?`${o}
200
- ${s}`:s;if(l.length>e){i(),o=s;continue}o=l}return i(),r}function Td(t){return se(t.trim(),Pg)}function Cd(t,e){return e?t?`
197
+ `)}function Ug(t){let e=[],n=!1;for(let o of t){let i=o.replace(/\s+/g," ").trim();if(!i)continue;let s=ae(i,Fg);s.length<i.length&&(n=!0);let a=`- ${s}`;if(e.length>=Bg||[...e,a].join(`
198
+ `).length>Wd){n=!0;break}e.push(a)}if(e.length===0)return["- Plan details are available in the full session output."];if(!n)return e;let r=[...e];for(;r.length>0&&[...r,Nd].join(`
199
+ `).length>Wd;)r.pop();return[...r,Nd]}function hs(t){return Ug(Kg(t)).join(`
200
+ `)}function Vg(t,e){let n=[],r=t.trim();for(;r.length>e;){let o=r.lastIndexOf(" ",e);o<Math.floor(e*.6)&&(o=e),n.push(r.slice(0,o).trimEnd()),r=r.slice(o).trimStart()}return r.length>0&&n.push(r),n}function Gg(t,e){let n=t.split(`
201
+ `),r=[],o="",i=()=>{o.trim().length>0&&(r.push(o.trimEnd()),o="")};for(let s of n){if(s.length>e){i();for(let l of Vg(s,e))r.push(l);continue}let a=o.length>0?`${o}
202
+ ${s}`:s;if(a.length>e){i(),o=s;continue}o=a}return i(),r}function Fd(t){return ae(t.trim(),Lg)}function qd(t,e){return e?t?`
201
203
 
202
204
  Choose Approve, Revise, or Reject below.`:`
203
205
 
204
206
  Approval is still pending for this plan version.`:`
205
207
 
206
- Continued in next message.`}function Cg(t){let{sessionName:e,actionableVersion:n,fullPlanText:r,hasButtons:o}=t,i=`📋 [${e}] Plan v${n??"?"} ready for approval:`,s=`
208
+ Continued in next message.`}function jg(t){let{sessionName:e,actionableVersion:n,fullPlanText:r,hasButtons:o}=t,i=`📋 [${e}] Plan v${n??"?"} ready for approval:`,s=`
207
209
 
208
210
  Full plan (truncated):
209
- `,l=Cd(o,!0),a=Math.max(0,as-i.length-s.length-l.length);return`${i}${s}${se(r,a)}${l}`}function Mg(t){let{sessionName:e,actionableVersion:n,fullPlanText:r,hasButtons:o}=t,i=Td(e),s=vg;for(;s>0;){let l=Tg(r,s),a=l.map((c,m)=>{let p=l.length,f=[`📋 [${i}] Plan v${n??"?"} ready for approval (${m+1}/${p}):`,"",m===0?"Full plan:":""].filter(Boolean).join(`
210
- `),h=Cd(o,m===p-1);return`${f}
211
- ${c}${h}`}),d=a.reduce((c,m)=>Math.max(c,m.length),0);if(d<=as)return a;let u=d-as;s-=Math.max(u,50)}return[Cg({sessionName:i,actionableVersion:n,fullPlanText:r,hasButtons:o})]}function us(t){let{preview:e,artifact:n}=t,r=n?.markdown?.trim();return r&&r.length<=Id?`Full plan:
212
- ${r}`:ls(r||e)}function Md(t){let{sessionName:e,actionableVersion:n,preview:r,artifact:o,hasButtons:i}=t,s=o?.markdown?.trim(),l=Td(e);if(s){let d=`📋 [${l}] Plan v${n??"?"} ready for approval:
211
+ `,a=qd(o,!0),l=Math.max(0,fs-i.length-s.length-a.length);return`${i}${s}${ae(r,l)}${a}`}function Hg(t){let{sessionName:e,actionableVersion:n,fullPlanText:r,hasButtons:o}=t,i=Fd(e),s=Ng;for(;s>0;){let a=Gg(r,s),l=a.map((c,p)=>{let g=a.length,m=[`📋 [${i}] Plan v${n??"?"} ready for approval (${p+1}/${g}):`,"",p===0?"Full plan:":""].filter(Boolean).join(`
212
+ `),f=qd(o,p===g-1);return`${m}
213
+ ${c}${f}`}),d=l.reduce((c,p)=>Math.max(c,p.length),0);if(d<=fs)return l;let u=d-fs;s-=Math.max(u,50)}return[jg({sessionName:i,actionableVersion:n,fullPlanText:r,hasButtons:o})]}function ys(t){let{preview:e,artifact:n}=t,r=n?.markdown?.trim();return r&&r.length<=Ld?`Full plan:
214
+ ${r}`:gs(r||e)}function Kd(t){let{sessionName:e,actionableVersion:n,preview:r,artifact:o,hasButtons:i}=t,s=o?.markdown?.trim(),a=Fd(e);if(s){let d=`📋 [${a}] Plan v${n??"?"} ready for approval:
213
215
 
214
216
  Full plan:
215
217
  ${s}
216
218
 
217
- ${i?"Choose Approve, Revise, or Reject below.":"Approval is still pending for this plan version."}`;return d.length<=Id?{displayMode:"single-full-plan",userMessages:[d],reviewSummary:`Full plan:
218
- ${s}`}:{displayMode:"chunked-full-plan",userMessages:Mg({sessionName:e,actionableVersion:n,fullPlanText:s,hasButtons:i}),reviewSummary:ls(s)}}let a=ls(r);return{displayMode:"summary",userMessages:[`📋 [${l}] Plan v${n??"?"} ready for approval:
219
+ ${i?"Choose Approve, Revise, or Reject below.":"Approval is still pending for this plan version."}`;return d.length<=Ld?{displayMode:"single-full-plan",userMessages:[d],reviewSummary:`Full plan:
220
+ ${s}`}:{displayMode:"chunked-full-plan",userMessages:Hg({sessionName:e,actionableVersion:n,fullPlanText:s,hasButtons:i}),reviewSummary:gs(s)}}let l=gs(r);return{displayMode:"summary",userMessages:[`📋 [${a}] Plan v${n??"?"} ready for approval:
219
221
 
220
- ${a}
222
+ ${l}
221
223
 
222
- ${i?"Choose Approve, Revise, or Reject below.":"Approval is still pending for this plan version."}`],reviewSummary:a}}function _d(t){let e=t?.trim();return e||void 0}function _g(t){let e=_d(t.questionText)??"The session is waiting for your reply.",n=_d(t.contextSummary);return n?[`❓ [${t.sessionName}] Question waiting for reply:`,"",e,"",`Why: ${n}`].join(`
224
+ ${i?"Choose Approve, Revise, or Reject below.":"Approval is still pending for this plan version."}`],reviewSummary:l}}function Ud(t){let e=t?.trim();return e||void 0}function zg(t){let e=Ud(t.questionText)??"The session is waiting for your reply.",n=Ud(t.contextSummary);return n?[`❓ [${t.sessionName}] Question waiting for reply:`,"",e,"",`Why: ${n}`].join(`
223
225
  `):`❓ [${t.sessionName}] Question waiting for reply:
224
226
 
225
- ${e}`}function $g(t,e){return e!=null&&t.approvalPromptRequiredVersion===e&&(t.approvalPromptStatus==="delivered"||t.approvalPromptStatus==="fallback_delivered")}function An(t){let{session:e,summary:n}=t,r=e.actionablePlanDecisionVersion??e.planDecisionVersion;return[`📋 [${e.name}] Plan v${r??"?"} needs your decision.`,"","Interactive Approve / Revise / Reject buttons could not be delivered, so reply here instead:",'- Reply "approve" to approve and start implementation','- Reply "reject" to reject and stop the session',"- Any other reply will be sent back as revision feedback","","Why this was escalated:","",n].join(`
226
- `)}function cs(t){let{session:e,preview:n,questionText:r,questionContextSummary:o,planArtifact:i,originThreadLine:s,planApprovalMode:l,planApprovalButtons:a,questionButtons:d}=t,u=e.pendingPlanApproval,c=e.actionablePlanDecisionVersion??e.planDecisionVersion,m=$g(e,c),p=l??"delegate",f=u&&p==="ask"&&!m?Md({sessionName:e.name,actionableVersion:c,preview:n,artifact:i,hasButtons:!!a}):void 0,h=u?f?.reviewSummary??us({preview:n,artifact:i}):void 0,k=u?f&&f.userMessages.length===1?f.userMessages[0]:void 0:_g({sessionName:e.name,questionText:r??n,contextSummary:o,hasButtons:!!d}),v=u&&f&&f.userMessages.length>1?f.userMessages.map((x,b,A)=>({text:x,buttons:b===A.length-1?a:void 0})):void 0;if(u){let x=p,b="Permission mode: plan → will switch to bypassPermissions on approval";return x==="delegate"?{label:"plan-approval",userMessage:k,userMessages:v,planReviewSummary:h,wakeMessage:["[DELEGATED PLAN APPROVAL] Coding agent session has finished its plan and is requesting approval to implement.",`Name: ${e.name} | ID: ${e.id} | Plan v${c??"?"}`,s,b,"","⚠️ YOU MUST COMPLETE THESE STEPS IN ORDER. Do NOT skip any step.","","━━━ STEP 1 (MANDATORY): Read the full plan ━━━",`Call agent_output(session='${e.id}', full=true) to read the FULL plan output.`,"The preview below is truncated — you MUST read the full output before making any decision.","","Preview (truncated):",n,"","━━━ STEP 2 (MANDATORY): Review privately ━━━","You are the delegated decision-maker. Review the plan yourself before involving the user.","If you approve directly, you own the user-facing explanation of what was approved and why.","Keep it short and user-facing: one sentence is usually enough.","","━━━ STEP 3 (ONLY AFTER steps 1 and 2): Decide ━━━","Choose ONE:","","APPROVE the plan directly if ALL of the following are true:","- You have read the FULL plan (not just the preview)","- The plan scope matches the original task request","- The changes are low-risk (no destructive operations, no credential handling, no production deployments)","- The plan is clear and well-scoped (no ambiguous requirements or open design questions)","- No architectural decisions that the user should weigh in on","- The working directory and codebase are correct","","ESCALATE to the user and WAIT if ANY of the following are true:","- The plan involves destructive operations (deleting files, dropping tables, force-pushing)","- The plan involves credentials, secrets, or production environments","- The plan requires architectural decisions not covered by the original task","- The scope has expanded beyond the original request","- The requirements are ambiguous or the plan makes assumptions the user should confirm","- You are unsure — when in doubt, always escalate","",`If approving: call agent_respond(session='${e.id}', message='Approved. Go ahead.', approve=true, approval_rationale='<brief reason>').`,"That rationale should say why approval was safe: for example scope match, low risk, or no meaningful ambiguity.","After approving directly, send the user a short plain-text follow-up explaining what was approved and why.","The plugin's thumbs-up line is only the minimal approval acknowledgment, not the explanation.",`If escalating: call agent_request_plan_approval(session='${e.id}', summary='...') exactly once so the plugin posts the single canonical Approve / Revise / Reject prompt.`,"That summary must concisely explain why this was escalated, plus changed files/components, risk level and why, scope match/expansion, and any concerns or assumptions.","After the canonical prompt exists, WAIT for the user's button click or explicit response and do NOT send a second plain-text recap.",`To request changes without user escalation: call agent_respond(session='${e.id}', message='<your feedback>') and do NOT set approve=true. The agent will revise the plan.`].join(`
227
- `)}:x==="ask"?{label:"plan-approval",userMessage:k,userMessages:v,planReviewSummary:h,wakeMessage:["[USER APPROVAL REQUESTED] Coding agent session has finished its plan. The user has been notified via Telegram and must approve directly.",`Name: ${e.name} | ID: ${e.id} | Plan v${c??"?"}`,s,b,"","DO NOT approve this plan yourself. Wait for the user's explicit approval or rejection.","Once the user responds, forward their decision:",` To approve: agent_respond(session='${e.id}', message='Approved. Go ahead.', approve=true)`,` To request changes: agent_respond(session='${e.id}', message='<user feedback>')`,"","Preview (truncated):",n].join(`
228
- `),buttons:v?void 0:a}:{label:"plan-approval",userMessage:k,planReviewSummary:h,wakeMessage:["[AUTO-APPROVE] Session has a plan ready. Approve it now:",`agent_respond(session='${e.id}', message='Approved. Go ahead.', approve=true)`].join(`
229
- `)}}let I=e.multiTurn?"Multi-turn session":"Session";return{label:"waiting",userMessage:k,wakeMessage:[`[SYSTEM INSTRUCTION: Follow your auto-respond rules strictly. If this is a permission request or "should I continue?" → auto-respond. For ALL other questions → forward the agent's EXACT question to the user. Do NOT add your own analysis, commentary, or interpretation. Do NOT "nudge" or "poke" the session.]`,"",`${I} is waiting for a genuine user reply.`,`Name: ${e.name} | ID: ${e.id}`,s,"","Last output:",n,"",`Use agent_respond(session='${e.id}', message='...') to send a reply, or agent_output(session='${e.id}', full: true) to see full context before deciding.`].join(`
230
- `),buttons:d}}var ro=3,ps=180,Eg=4e3,$d=32;function Ed(){let t=bt(),e=qg(t);if(e)return{async generateWorktreeDecisionSummary(n){if(typeof e.generateWorktreeDecisionSummary=="function")return await e.generateWorktreeDecisionSummary(n);if(typeof e.summarizeWorktreeDecision=="function")return await e.summarizeWorktreeDecision(n);let r=Ug(n);if(typeof e.generateObject=="function")return await e.generateObject({task:"openclaw-code-agent.worktree-decision-summary",prompt:r,input:n});if(typeof e.generateText=="function")return await e.generateText({task:"openclaw-code-agent.worktree-decision-summary",prompt:r});if(typeof e.complete=="function")return await e.complete({prompt:r})}}}function Dg(t,e){let n=Kg(e);if(n.length>0)return n;let r=Og(t);if(r.length>0)return r;let o=[],i=t.changedFiles.slice(0,3).map(l=>`\`${l}\``);if(i.length>0){let l=t.changedFiles.length-i.length;o.push(l>0?`Touches ${i.join(", ")} and ${l} more file${l===1?"":"s"}`:`Touches ${i.join(", ")}`)}let s=[...new Set(t.commitMessages.map(l=>l.message.trim()).filter(Boolean))].slice(0,2);return s.length>0&&o.push(`Recent work: ${s.join("; ")}`),o}function Og(t){let e=new Set,n=t.commitMessages.length===1?t.changedFiles:[];return t.commitMessages.map(r=>Wg(r.message,n)).filter(r=>!!r).filter(r=>{let o=r.toLowerCase();return e.has(o)?!1:(e.add(o),!0)}).slice(0,ro)}function Wg(t,e){let n=Ng(t);if(!n)return;let r=e.length===1?` in \`${e[0]}\``:e.length>1&&e.length<=3?` across ${e.map(o=>`\`${o}\``).join(", ")}`:"";return ms(`${n}${r}.`,ps)}function Ng(t){let e=oo(io(t)).replace(/^(?:feat|fix|docs|style|refactor|perf|test|tests|build|ci|chore|revert)(?:\([^)]+\))?!?:\s*/i,"").replace(/\.$/,"").trim();if(!e||fs(e))return;let n=e.match(/^([a-z]+)\b(.*)$/i);if(!n)return e;let r=n[1].toLowerCase(),o=n[2]??"",s=new Map([["add","Adds"],["address","Addresses"],["block","Blocks"],["change","Changes"],["clarify","Clarifies"],["clean","Cleans"],["cover","Covers"],["create","Creates"],["deduplicate","Deduplicates"],["delete","Deletes"],["disable","Disables"],["document","Documents"],["enable","Enables"],["extract","Extracts"],["fix","Fixes"],["guard","Guards"],["harden","Hardens"],["implement","Implements"],["improve","Improves"],["init","Initializes"],["initialize","Initializes"],["migrate","Migrates"],["move","Moves"],["normalize","Normalizes"],["preserve","Preserves"],["prevent","Prevents"],["refactor","Refactors"],["remove","Removes"],["rename","Renames"],["restore","Restores"],["simplify","Simplifies"],["tighten","Tightens"],["update","Updates"],["use","Uses"],["wire","Wires"],["wrap","Wraps"]]).get(r);return s?`${s}${o}`:`${r[0].toUpperCase()}${r.slice(1)}${o}`}async function Dd(t){let e=Lg(t),n=Dg(t.diffSummary??{changedFiles:e.changedFiles,commitMessages:e.commitSubjects.map(r=>({message:r}))},t.outputPreview);if(!t.provider)return{source:"fallback",lines:n,evidence:e,error:"LLM summary provider unavailable."};try{let r=await t.provider.generateWorktreeDecisionSummary(e),o=Fg(r);return o.length>0?{source:"llm",lines:o,evidence:e}:{source:"fallback",lines:n,evidence:e,error:"LLM-generated worktree summary failed schema validation."}}catch(r){let o=r instanceof Error?r.message:String(r);return`${o}`,{source:"fallback",lines:n,evidence:e,error:"LLM summary provider failed."}}}function Lg(t){let e=t.diffSummary;return{sessionName:t.sessionName,objective:jg(t.prompt),stats:e?{commits:e.commits,filesChanged:e.filesChanged,insertions:e.insertions,deletions:e.deletions}:void 0,changedFiles:e?.changedFiles??[],commitSubjects:e?.commitMessages.map(n=>oo(n.message)).filter(Boolean).slice(0,8)??[],outputPreview:ms(io(t.outputPreview??""),Eg)}}function Fg(t){let e=Bg(t),n=Array.isArray(e)?e:e&&typeof e=="object"&&Array.isArray(e.summary)?e.summary:void 0;if(!n||n.length===0||n.length>ro)return[];let r=n.map(o=>typeof o=="string"?oo(o):"").filter(Boolean);return r.length!==n.length?[]:r.some(o=>o.length>ps)?[]:r.some(fs)?[]:r}function Bg(t){if(typeof t!="string")return t;let e=t.trim();if(e)try{return JSON.parse(e)}catch{return{summary:e.split(`
231
- `).map(n=>n.replace(/^[-*•]\s+/,"").trim()).filter(Boolean).slice(0,ro)}}}function qg(t){return[t?.worktreeDecisionSummary,t?.llm,t?.ai,t?.model,t?.models].find(n=>!!(n&&typeof n=="object"&&(typeof n.generateWorktreeDecisionSummary=="function"||typeof n.summarizeWorktreeDecision=="function"||typeof n.generateObject=="function"||typeof n.generateText=="function"||typeof n.complete=="function")))}function Ug(t){return["Summarize the completed OpenClaw Code Agent work for a worktree decision notification.",'Return only JSON with shape {"summary":["..."]}.',"Write 1-3 concise, user-facing bullets that help a human choose Merge, Open PR, Later, or Discard.","Do not mention that you are summarizing. Do not invent changes not supported by the evidence.","","Evidence:",JSON.stringify(t,null,2)].join(`
232
- `)}function Kg(t){let e=new Set;return io(t??"").replace(/\r\n/g,`
227
+ ${e}`}function Qg(t,e){return e!=null&&t.approvalPromptRequiredVersion===e&&(t.approvalPromptStatus==="delivered"||t.approvalPromptStatus==="fallback_delivered")}function xn(t){let{session:e,summary:n}=t,r=e.actionablePlanDecisionVersion??e.planDecisionVersion;return[`📋 [${e.name}] Plan v${r??"?"} needs your decision.`,"","Interactive Approve / Revise / Reject buttons could not be delivered, so reply here instead:",'- Reply "approve" to approve and start implementation','- Reply "reject" to reject and stop the session',"- Any other reply will be sent back as revision feedback","","Why this was escalated:","",n].join(`
228
+ `)}function ks(t){let{session:e,preview:n,questionText:r,questionContextSummary:o,planArtifact:i,originThreadLine:s,planApprovalMode:a,planApprovalButtons:l,questionButtons:d}=t,u=e.pendingPlanApproval,c=e.actionablePlanDecisionVersion??e.planDecisionVersion,p=Qg(e,c),g=a??"delegate",m=u&&g==="ask"&&!p?Kd({sessionName:e.name,actionableVersion:c,preview:n,artifact:i,hasButtons:!!l}):void 0,f=u?m?.reviewSummary??ys({preview:n,artifact:i}):void 0,y=u?m&&m.userMessages.length===1?m.userMessages[0]:void 0:zg({sessionName:e.name,questionText:r??n,contextSummary:o,hasButtons:!!d}),S=u&&m&&m.userMessages.length>1?m.userMessages.map((I,b,A)=>({text:I,buttons:b===A.length-1?l:void 0})):void 0;if(u){let I=g,b="Permission mode: plan → will switch to bypassPermissions on approval";return I==="delegate"?{label:"plan-approval",userMessage:y,userMessages:S,planReviewSummary:f,wakeMessage:["[DELEGATED PLAN APPROVAL] Coding agent session has finished its plan and is requesting approval to implement.",`Name: ${e.name} | ID: ${e.id} | Plan v${c??"?"}`,s,b,"","⚠️ YOU MUST COMPLETE THESE STEPS IN ORDER. Do NOT skip any step.","","━━━ STEP 1 (MANDATORY): Read the full plan ━━━",`Call agent_output(session='${e.id}', full=true) to read the FULL plan output.`,"The preview below is truncated — you MUST read the full output before making any decision.","","Preview (truncated):",n,"","━━━ STEP 2 (MANDATORY): Review privately ━━━","You are the delegated decision-maker. Review the plan yourself before involving the user.","If you approve directly, you own the user-facing explanation of what was approved and why.","Keep it short and user-facing: one sentence is usually enough.","","━━━ STEP 3 (ONLY AFTER steps 1 and 2): Decide ━━━","Choose ONE:","","APPROVE the plan directly if ALL of the following are true:","- You have read the FULL plan (not just the preview)","- The plan scope matches the original task request","- The changes are low-risk (no destructive operations, no credential handling, no production deployments)","- The plan is clear and well-scoped (no ambiguous requirements or open design questions)","- No architectural decisions that the user should weigh in on","- The working directory and codebase are correct","","ESCALATE to the user and WAIT if ANY of the following are true:","- The plan involves destructive operations (deleting files, dropping tables, force-pushing)","- The plan involves credentials, secrets, or production environments","- The plan requires architectural decisions not covered by the original task","- The scope has expanded beyond the original request","- The requirements are ambiguous or the plan makes assumptions the user should confirm","- You are unsure — when in doubt, always escalate","",`If approving: call agent_respond(session='${e.id}', message='Approved. Go ahead.', approve=true, approval_rationale='<brief reason>').`,"That rationale should say why approval was safe: for example scope match, low risk, or no meaningful ambiguity.","After approving directly, send the user a short plain-text follow-up explaining what was approved and why.","The plugin's thumbs-up line is only the minimal approval acknowledgment, not the explanation.",`If escalating: call agent_request_plan_approval(session='${e.id}', summary='...') exactly once so the plugin posts the single canonical Approve / Revise / Reject prompt.`,"That summary must concisely explain why this was escalated, plus changed files/components, risk level and why, scope match/expansion, and any concerns or assumptions.","After the canonical prompt exists, WAIT for the user's button click or explicit response and do NOT send a second plain-text recap.",`To request changes without user escalation: call agent_respond(session='${e.id}', message='<your feedback>') and do NOT set approve=true. The agent will revise the plan.`].join(`
229
+ `)}:I==="ask"?{label:"plan-approval",userMessage:y,userMessages:S,planReviewSummary:f,wakeMessage:["[USER APPROVAL REQUESTED] Coding agent session has finished its plan. The user has been notified via Telegram and must approve directly.",`Name: ${e.name} | ID: ${e.id} | Plan v${c??"?"}`,s,b,"","DO NOT approve this plan yourself. Wait for the user's explicit approval or rejection.","Once the user responds, forward their decision:",` To approve: agent_respond(session='${e.id}', message='Approved. Go ahead.', approve=true)`,` To request changes: agent_respond(session='${e.id}', message='<user feedback>')`,"","Preview (truncated):",n].join(`
230
+ `),buttons:S?void 0:l}:{label:"plan-approval",userMessage:y,planReviewSummary:f,wakeMessage:["[AUTO-APPROVE] Session has a plan ready. Approve it now:",`agent_respond(session='${e.id}', message='Approved. Go ahead.', approve=true)`].join(`
231
+ `)}}let R=e.multiTurn?"Multi-turn session":"Session";return{label:"waiting",userMessage:y,wakeMessage:[`[SYSTEM INSTRUCTION: Follow your auto-respond rules strictly. If this is a permission request or "should I continue?" → auto-respond. For ALL other questions → forward the agent's EXACT question to the user. Do NOT add your own analysis, commentary, or interpretation. Do NOT "nudge" or "poke" the session.]`,"",`${R} is waiting for a genuine user reply.`,`Name: ${e.name} | ID: ${e.id}`,s,"","Last output:",n,"",`Use agent_respond(session='${e.id}', message='...') to send a reply, or agent_output(session='${e.id}', full: true) to see full context before deciding.`].join(`
232
+ `),buttons:d}}var ao=3,Ss=180,Jg=4e3,Vd=32;function Gd(){let t=At(),e=oh(t);if(e)return{async generateWorktreeDecisionSummary(n){if(typeof e.generateWorktreeDecisionSummary=="function")return await e.generateWorktreeDecisionSummary(n);if(typeof e.summarizeWorktreeDecision=="function")return await e.summarizeWorktreeDecision(n);let r=ih(n);if(typeof e.generateObject=="function")return await e.generateObject({task:"openclaw-code-agent.worktree-decision-summary",prompt:r,input:n});if(typeof e.generateText=="function")return await e.generateText({task:"openclaw-code-agent.worktree-decision-summary",prompt:r});if(typeof e.complete=="function")return await e.complete({prompt:r})}}}function Yg(t,e){let n=sh(e);if(n.length>0)return n;let r=Zg(t);if(r.length>0)return r;let o=[],i=t.changedFiles.slice(0,3).map(a=>`\`${a}\``);if(i.length>0){let a=t.changedFiles.length-i.length;o.push(a>0?`Touches ${i.join(", ")} and ${a} more file${a===1?"":"s"}`:`Touches ${i.join(", ")}`)}let s=[...new Set(t.commitMessages.map(a=>a.message.trim()).filter(Boolean))].slice(0,2);return s.length>0&&o.push(`Recent work: ${s.join("; ")}`),o}function Zg(t){let e=new Set,n=t.commitMessages.length===1?t.changedFiles:[];return t.commitMessages.map(r=>Xg(r.message,n)).filter(r=>!!r).filter(r=>{let o=r.toLowerCase();return e.has(o)?!1:(e.add(o),!0)}).slice(0,ao)}function Xg(t,e){let n=eh(t);if(!n)return;let r=e.length===1?` in \`${e[0]}\``:e.length>1&&e.length<=3?` across ${e.map(o=>`\`${o}\``).join(", ")}`:"";return vs(`${n}${r}.`,Ss)}function eh(t){let e=lo(uo(t)).replace(/^(?:feat|fix|docs|style|refactor|perf|test|tests|build|ci|chore|revert)(?:\([^)]+\))?!?:\s*/i,"").replace(/\.$/,"").trim();if(!e||ws(e))return;let n=e.match(/^([a-z]+)\b(.*)$/i);if(!n)return e;let r=n[1].toLowerCase(),o=n[2]??"",s=new Map([["add","Adds"],["address","Addresses"],["block","Blocks"],["change","Changes"],["clarify","Clarifies"],["clean","Cleans"],["cover","Covers"],["create","Creates"],["deduplicate","Deduplicates"],["delete","Deletes"],["disable","Disables"],["document","Documents"],["enable","Enables"],["extract","Extracts"],["fix","Fixes"],["guard","Guards"],["harden","Hardens"],["implement","Implements"],["improve","Improves"],["init","Initializes"],["initialize","Initializes"],["migrate","Migrates"],["move","Moves"],["normalize","Normalizes"],["preserve","Preserves"],["prevent","Prevents"],["refactor","Refactors"],["remove","Removes"],["rename","Renames"],["restore","Restores"],["simplify","Simplifies"],["tighten","Tightens"],["update","Updates"],["use","Uses"],["wire","Wires"],["wrap","Wraps"]]).get(r);return s?`${s}${o}`:`${r[0].toUpperCase()}${r.slice(1)}${o}`}async function jd(t){let e=th(t),n=Yg(t.diffSummary??{changedFiles:e.changedFiles,commitMessages:e.commitSubjects.map(r=>({message:r}))},t.outputPreview);if(!t.provider)return{source:"fallback",lines:n,evidence:e,error:"LLM summary provider unavailable."};try{let r=await t.provider.generateWorktreeDecisionSummary(e),o=nh(r);return o.length>0?{source:"llm",lines:o,evidence:e}:{source:"fallback",lines:n,evidence:e,error:"LLM-generated worktree summary failed schema validation."}}catch(r){let o=r instanceof Error?r.message:String(r);return`${o}`,{source:"fallback",lines:n,evidence:e,error:"LLM summary provider failed."}}}function th(t){let e=t.diffSummary;return{sessionName:t.sessionName,objective:dh(t.prompt),stats:e?{commits:e.commits,filesChanged:e.filesChanged,insertions:e.insertions,deletions:e.deletions}:void 0,changedFiles:e?.changedFiles??[],commitSubjects:e?.commitMessages.map(n=>lo(n.message)).filter(Boolean).slice(0,8)??[],outputPreview:vs(uo(t.outputPreview??""),Jg)}}function nh(t){let e=rh(t),n=Array.isArray(e)?e:e&&typeof e=="object"&&Array.isArray(e.summary)?e.summary:void 0;if(!n||n.length===0||n.length>ao)return[];let r=n.map(o=>typeof o=="string"?lo(o):"").filter(Boolean);return r.length!==n.length?[]:r.some(o=>o.length>Ss)?[]:r.some(ws)?[]:r}function rh(t){if(typeof t!="string")return t;let e=t.trim();if(e)try{return JSON.parse(e)}catch{return{summary:e.split(`
233
+ `).map(n=>n.replace(/^[-*•]\s+/,"").trim()).filter(Boolean).slice(0,ao)}}}function oh(t){return[t?.worktreeDecisionSummary,t?.llm,t?.ai,t?.model,t?.models].find(n=>!!(n&&typeof n=="object"&&(typeof n.generateWorktreeDecisionSummary=="function"||typeof n.summarizeWorktreeDecision=="function"||typeof n.generateObject=="function"||typeof n.generateText=="function"||typeof n.complete=="function")))}function ih(t){return["Summarize the completed OpenClaw Code Agent work for a worktree decision notification.",'Return only JSON with shape {"summary":["..."]}.',"Write 1-3 concise, user-facing bullets that help a human choose Merge, Open PR, Later, or Discard.","Do not mention that you are summarizing. Do not invent changes not supported by the evidence.","","Evidence:",JSON.stringify(t,null,2)].join(`
234
+ `)}function sh(t){let e=new Set;return uo(t??"").replace(/\r\n/g,`
233
235
  `).split(`
234
- `).map(r=>oo(r)).map(r=>Vg(r)).filter(Gg).filter(r=>{let o=r.toLowerCase();return e.has(o)?!1:(e.add(o),!0)}).slice(0,ro)}function Vg(t){return t.replace(/^(?:summary|done|completed|changes|validation|verified)\s*:\s*/i,"").trim()}function Gg(t){return t.length<12||t.length>ps||fs(t)||/^(```|>|command\b|exit code\b|\$|[a-z0-9_-]+@[a-z0-9_-]+:)/i.test(t)||/^(?:running|ran|pnpm|npm|node|git|tsc|vitest|jest)\b/i.test(t)||/^(?:pass|fail|ok|error)\b[:\s]/i.test(t)||/^(?:changed files?|files changed|recent commits?|commits?)\b/i.test(t)?!1:/^(?:implemented|updated|added|fixed|changed|removed|verified|covered|refactored|improved|created|documented|hardened|restored|simplified|renamed|moved|wired|handled|blocked|reduced|deduplicated|normalized|addressed|prevented)\b/i.test(t)||/\b(?:so that|coverage|validation|regression|cleanup|summary|notification|callback|button|merge|worktree|policy)\b/i.test(t)&&/\b(?:preserv(?:e|es|ed|ing)|clear(?:s|ed|ing)?|reuse(?:s|d|ing)?|cover(?:s|ed|ing)?|pass(?:es|ed|ing)?|fail(?:s|ed|ing)?|complete(?:s|d)?|fall(?:s|ing)? back)\b/i.test(t)}function jg(t){let e=t?.replace(/\r\n/g,`
236
+ `).map(r=>lo(r)).map(r=>ah(r)).filter(lh).filter(r=>{let o=r.toLowerCase();return e.has(o)?!1:(e.add(o),!0)}).slice(0,ao)}function ah(t){return t.replace(/^(?:summary|done|completed|changes|validation|verified)\s*:\s*/i,"").trim()}function lh(t){return t.length<12||t.length>Ss||ws(t)||/^(```|>|command\b|exit code\b|\$|[a-z0-9_-]+@[a-z0-9_-]+:)/i.test(t)||/^(?:running|ran|pnpm|npm|node|git|tsc|vitest|jest)\b/i.test(t)||/^(?:pass|fail|ok|error)\b[:\s]/i.test(t)||/^(?:changed files?|files changed|recent commits?|commits?)\b/i.test(t)?!1:/^(?:implemented|updated|added|fixed|changed|removed|verified|covered|refactored|improved|created|documented|hardened|restored|simplified|renamed|moved|wired|handled|blocked|reduced|deduplicated|normalized|addressed|prevented)\b/i.test(t)||/\b(?:so that|coverage|validation|regression|cleanup|summary|notification|callback|button|merge|worktree|policy)\b/i.test(t)&&/\b(?:preserv(?:e|es|ed|ing)|clear(?:s|ed|ing)?|reuse(?:s|d|ing)?|cover(?:s|ed|ing)?|pass(?:es|ed|ing)?|fail(?:s|ed|ing)?|complete(?:s|d)?|fall(?:s|ing)? back)\b/i.test(t)}function dh(t){let e=t?.replace(/\r\n/g,`
235
237
  `).split(`
236
- `).map(o=>o.trim()).filter(Boolean).join(" ");if(!e)return;let n=e.match(/^[^.!?]+[.!?]/)?.[0]??e,r=io(n).replace(/\s+/g," ").trim();return r?ms(r,180):void 0}function oo(t){return t.replace(/^[-*•]\s+/,"").replace(/\s+/g," ").trim()}function ms(t,e){return t.length<=e?t:`${t.slice(0,Math.max(0,e-3)).trimEnd()}...`}function io(t){return t.replace(/\b[A-Za-z0-9_-]*(?:api[_-]?key|token|secret|password|passwd|pwd|credential|credentials|authorization|auth)[A-Za-z0-9_-]*\b\s*[:=]\s*["']?[^"'\s,;)]+/gi,"[redacted credential]").replace(/\b(?:ghp|gho|ghu|ghs|ghr)_[A-Za-z0-9_]{16,}\b/g,"[redacted token]").replace(/\bgithub_pat_[A-Za-z0-9_]{20,}\b/g,"[redacted token]").replace(/\bsk-[A-Za-z0-9_-]{20,}\b/g,"[redacted token]").replace(/\bhttps?:\/\/\S+/gi,"[redacted link]").replace(new RegExp(`\\b[A-Za-z0-9_-]{${$d},}\\b`,"g"),"[redacted token]")}function fs(t){return/\b[A-Za-z0-9_-]*(?:api[_-]?key|token|secret|password|passwd|pwd|credential|credentials|authorization|auth)[A-Za-z0-9_-]*\b\s*[:=]\s*["']?[^"'\s,;)]+/i.test(t)||/\b(?:ghp|gho|ghu|ghs|ghr)_[A-Za-z0-9_]{16,}\b/.test(t)||/\bgithub_pat_[A-Za-z0-9_]{20,}\b/.test(t)||/\bsk-[A-Za-z0-9_-]{20,}\b/.test(t)||/\bhttps?:\/\/\S+/i.test(t)||new RegExp(`\\b[A-Za-z0-9_-]{${$d},}\\b`).test(t)}ye();var so=class{constructor(e){this.deps=e;this.actions=new to({shouldRunWorktreeStrategy:e.shouldRunWorktreeStrategy,isAlreadyMerged:e.isAlreadyMerged,resolveWorktreeRepoDir:e.resolveWorktreeRepoDir,getWorktreeCompletionState:e.getWorktreeCompletionState,isPrAvailable:e.isPrAvailable??(()=>!0),resolveRepoPolicy:e.resolveRepoPolicy})}deps;actions;buildConflictResolverPrompt(e){return["Resolve the git rebase conflict for the auto-merge worktree and finish the rebase cleanly.","",`Original session: ${e.session.name} [${e.session.id}]`,`Repository root: ${e.repoDir}`,`Conflicted worktree: ${e.worktreePath}`,`Branch: ${e.branchName}`,`Base branch: ${e.baseBranch}`,"","Requirements:","- Work only inside the conflicted worktree.","- Inspect the current rebase state and resolve only the necessary conflict hunks.","- Make only minimal follow-up edits needed to keep the rebased branch correct.","- Continue the rebase until it completes successfully.","- Run relevant local verification before you finish.","- Do not broaden scope or start unrelated refactors.",`- Stop only when the branch is cleanly rebased onto ${e.baseBranch}.`,e.mergeError?"":void 0,e.mergeError?"Rebase failure details:":void 0,e.mergeError].filter(n=>typeof n=="string").join(`
238
+ `).map(o=>o.trim()).filter(Boolean).join(" ");if(!e)return;let n=e.match(/^[^.!?]+[.!?]/)?.[0]??e,r=uo(n).replace(/\s+/g," ").trim();return r?vs(r,180):void 0}function lo(t){return t.replace(/^[-*•]\s+/,"").replace(/\s+/g," ").trim()}function vs(t,e){return t.length<=e?t:`${t.slice(0,Math.max(0,e-3)).trimEnd()}...`}function uo(t){return t.replace(/\b[A-Za-z0-9_-]*(?:api[_-]?key|token|secret|password|passwd|pwd|credential|credentials|authorization|auth)[A-Za-z0-9_-]*\b\s*[:=]\s*["']?[^"'\s,;)]+/gi,"[redacted credential]").replace(/\b(?:ghp|gho|ghu|ghs|ghr)_[A-Za-z0-9_]{16,}\b/g,"[redacted token]").replace(/\bgithub_pat_[A-Za-z0-9_]{20,}\b/g,"[redacted token]").replace(/\bsk-[A-Za-z0-9_-]{20,}\b/g,"[redacted token]").replace(/\bhttps?:\/\/\S+/gi,"[redacted link]").replace(new RegExp(`\\b[A-Za-z0-9_-]{${Vd},}\\b`,"g"),"[redacted token]")}function ws(t){return/\b[A-Za-z0-9_-]*(?:api[_-]?key|token|secret|password|passwd|pwd|credential|credentials|authorization|auth)[A-Za-z0-9_-]*\b\s*[:=]\s*["']?[^"'\s,;)]+/i.test(t)||/\b(?:ghp|gho|ghu|ghs|ghr)_[A-Za-z0-9_]{16,}\b/.test(t)||/\bgithub_pat_[A-Za-z0-9_]{20,}\b/.test(t)||/\bsk-[A-Za-z0-9_-]{20,}\b/.test(t)||/\bhttps?:\/\/\S+/i.test(t)||new RegExp(`\\b[A-Za-z0-9_-]{${Vd},}\\b`).test(t)}ke();var co=class{constructor(e){this.deps=e;this.actions=new io({shouldRunWorktreeStrategy:e.shouldRunWorktreeStrategy,isAlreadyMerged:e.isAlreadyMerged,resolveWorktreeRepoDir:e.resolveWorktreeRepoDir,getWorktreeCompletionState:e.getWorktreeCompletionState,isPrAvailable:e.isPrAvailable??(()=>!0),resolveRepoPolicy:e.resolveRepoPolicy})}deps;actions;buildConflictResolverPrompt(e){return["Resolve the git rebase conflict for the auto-merge worktree and finish the rebase cleanly.","",`Original session: ${e.session.name} [${e.session.id}]`,`Repository root: ${e.repoDir}`,`Conflicted worktree: ${e.worktreePath}`,`Branch: ${e.branchName}`,`Base branch: ${e.baseBranch}`,"","Requirements:","- Work only inside the conflicted worktree.","- Inspect the current rebase state and resolve only the necessary conflict hunks.","- Make only minimal follow-up edits needed to keep the rebased branch correct.","- Continue the rebase until it completes successfully.","- Run relevant local verification before you finish.","- Do not broaden scope or start unrelated refactors.",`- Stop only when the branch is cleanly rebased onto ${e.baseBranch}.`,e.mergeError?"":void 0,e.mergeError?"Rebase failure details:":void 0,e.mergeError].filter(n=>typeof n=="string").join(`
237
239
  `)}notifyAutoMergeConflictEscalation(e,n,r,o,i=[]){this.deps.dispatchSessionNotification(e,{label:"worktree-merge-conflict-escalated",idempotencyKey:`worktree-merge-conflict-escalated:${e.id}:${n}`,userMessage:[`⚠️ [${e.name}] Auto-merge could not finish after one conflict-resolution attempt.`,`Branch \`${n}\` was preserved for manual follow-up.`,"",r,...i.map(s=>`⚠️ ${s}`)].join(`
238
- `),buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,o,{},[[this.deps.makeOpenPrButton(e.id)]])})}updatePersistedSessionFor(e,n){for(let r of pe(e))this.deps.updatePersistedSession(r,n)}markPendingDecision(e,n={}){this.updatePersistedSessionFor(e,Tr(e,n))}markAutoMergeConflictResolving(e,n,r){this.updatePersistedSessionFor(e,Pl(e,n,r,{notes:[`resolver_session:${n}`]}))}markMerged(e){this.updatePersistedSessionFor(e,$t(e,{clearResolverSessionId:!0}))}markReleased(e,n=[]){let r=new Date().toISOString();this.updatePersistedSessionFor(e,{lifecycle:"terminal",worktreeState:"released",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeLifecycle:{state:"released",updatedAt:r,resolvedAt:r,resolutionSource:"lifecycle_resolver",baseBranch:e.worktreeBaseBranch,targetRepo:e.worktreePrTargetRepo,pushRemote:e.worktreePushRemote,notes:n}})}async handleWorktreeStrategy(e){let n=await this.actions.plan(e);if(n.kind==="skip")return n.result;if(n.kind==="notify")return this.deps.dispatchSessionNotification(e,{label:n.label,idempotencyKey:["worktree-action",e.id,n.label,e.completedAt??"unknown",e.worktreeBranch??"unknown",e.worktreePath??"unknown"].join(":"),userMessage:n.message}),{notificationSent:!0,worktreeRemoved:!1};if(n.kind==="dirty-uncommitted")return this.handleDirtyUncommittedCompletion(e,n.worktreePath,n.branchName,n.baseBranch);if(n.kind==="no-change")return this.handleNoChange(e,n.repoDir,n.worktreePath,n.nativeBackendWorktree);if(n.kind==="merged"){let r=n.nativeBackendWorktree?!0:ue(n.repoDir,n.worktreePath);return he(n.repoDir,n.branchName),this.markMerged(e),{notificationSent:!1,worktreeRemoved:r}}if(n.kind==="released"){let r=n.nativeBackendWorktree?!0:ue(n.repoDir,n.worktreePath);return he(n.repoDir,n.branchName),this.markReleased(e,n.reasons),{notificationSent:!1,worktreeRemoved:r}}return n.policyBlocked?(this.markPendingDecision(e,{notes:n.policyReason?[n.policyReason]:void 0}),this.deps.dispatchSessionNotification(e,{label:"worktree-policy-blocked",idempotencyKey:`worktree-policy-blocked:${e.id}:${n.branchName}:${n.baseBranch}`,userMessage:`⚠️ [${e.name}] ${n.policyReason??"Repo policy blocked automatic follow-through."}`,buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,n.allowedActions,{allowDelegate:!0})}),{notificationSent:!0,worktreeRemoved:!1}):n.strategy==="ask"?await this.handleAskStrategy(e,n.branchName,n.baseBranch,n.diffSummary,n.allowedActions,n.policyReason):n.strategy==="delegate"?this.handleDelegateStrategy(e,n.branchName,n.baseBranch,n.diffSummary,n.allowedActions,n.policyReason):n.strategy==="auto-merge"?(await this.handleAutoMergeStrategy(e,n.repoDir,n.worktreePath,n.branchName,n.baseBranch,n.diffSummary,n.sessionRef,n.allowedActions),{notificationSent:!0,worktreeRemoved:!1}):n.strategy==="auto-pr"?this.handleAutoPrStrategy(e,n.repoDir,n.worktreePath,n.branchName,n.baseBranch,n.allowedActions):{notificationSent:!1,worktreeRemoved:!1}}async handleNoChange(e,n,r,o=le(e)){let i=o?!0:ue(n,r);return i?(e.worktreePath=void 0,this.updatePersistedSessionFor(e,{worktreePath:void 0,worktreeDisposition:"no-change-cleaned",worktreeState:"none",worktreeLifecycle:{state:"no_change",updatedAt:new Date().toISOString(),resolvedAt:new Date().toISOString(),resolutionSource:"strategy_no_change",baseBranch:e.worktreeBaseBranch,targetRepo:e.worktreePrTargetRepo,pushRemote:e.worktreePushRemote}}),this.deps.dispatchSessionNotification(e,this.deps.worktreeMessages.buildNoChangeNotification({session:e,nativeBackendWorktree:o,cleanupSucceeded:!0,worktreePath:r,preview:this.deps.getOutputPreview(e),originThreadLine:this.deps.originThreadLine(e)}))):this.deps.dispatchSessionNotification(e,this.deps.worktreeMessages.buildNoChangeNotification({session:e,nativeBackendWorktree:o,cleanupSucceeded:!1,worktreePath:r,preview:this.deps.getOutputPreview(e),originThreadLine:this.deps.originThreadLine(e)})),{notificationSent:!0,worktreeRemoved:i}}async handleAskStrategy(e,n,r,o,i,s){let l=await Dd({sessionName:e.name,prompt:e.prompt,diffSummary:o,outputPreview:this.deps.getOutputPreview(e,4e3),provider:this.deps.worktreeSummaryProvider});return this.deps.dispatchSessionNotification(e,this.deps.worktreeMessages.buildAskNotification({session:e,branchName:n,baseBranch:r,diffSummary:o,summaryLines:l.lines,policyReason:s,buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,i)})),this.markPendingDecision(e),{notificationSent:!0,worktreeRemoved:!1}}handleDelegateStrategy(e,n,r,o,i,s){return this.deps.dispatchSessionNotification(e,this.deps.worktreeMessages.buildDelegateNotification({session:e,branchName:n,baseBranch:r,diffSummary:o,policyReason:s,allowedActions:i,originThreadLine:this.deps.originThreadLine(e)})),this.markPendingDecision(e),{notificationSent:!0,worktreeRemoved:!1}}getPolicyAwareWorktreeDecisionButtons(e,n,r={},o){if(this.deps.getPolicyAwareWorktreeDecisionButtons)return this.deps.getPolicyAwareWorktreeDecisionButtons(e,r,n);if(o&&n.pr)return o;if(!(o&&!n.pr&&!n.merge))return this.deps.getWorktreeDecisionButtons(e)}handleDirtyUncommittedCompletion(e,n,r,o){this.markPendingDecision(e,{notes:["dirty_uncommitted_completion"]});let i=tt(n),s=i.slice(0,20).map(a=>`- ${a}`),l=i.length>20?[`- ...and ${i.length-20} more`]:[];return this.deps.dispatchSessionNotification(e,{label:"worktree-dirty-uncommitted",idempotencyKey:`worktree-dirty-uncommitted:${e.id}:${r}:${o}`,userMessage:[`⚠️ [${e.name}] Session completed with uncommitted worktree changes.`,"",`Branch \`${r}\` has no commits ahead of \`${o}\`, so merge/PR follow-through is blocked until the worktree is fixed.`,`Worktree: ${n}`,"",...s.length>0?["Dirty entries:",...s,...l,""]:[],"Resume the session or inspect the worktree, then commit real task changes or clean temporary files. Discard only if these local changes should be permanently removed."].join(`
239
- `)}),{notificationSent:!0,worktreeRemoved:!1}}handleAutoMergeSuccess(e,n,r,o,i,s){he(n,r),this.markMerged(e);let l=rt({kind:"merge",branch:r,base:o,filesChanged:i.filesChanged,insertions:i.insertions,deletions:i.deletions}),a=l;s.stashPopConflict?a+=`
240
- ⚠️ Pre-merge stash pop conflicted — run \`git stash show ${s.stashRef??"stash@{0}"}\` in ${n} to review stashed changes.`:s.stashed&&(a+=`
241
- (Pre-existing changes on ${o} were auto-stashed and restored.)`),a=Me(a,s);let d=Ct(s),u=[s.fastForward?"Merge type: fast-forward.":"Merge type: merge commit.",`Auto-merge landed ${r} into ${o}.`,"Local worktree branch cleanup was requested.",...s.stashPopConflict?[`Pre-merge stash pop conflicted; run git stash show ${s.stashRef??"stash@{0}"} in ${n} to review stashed changes.`]:[],...!s.stashPopConflict&&s.stashed?[`Pre-existing changes on ${o} were auto-stashed and restored.`]:[],...d];this.deps.dispatchSessionNotification(e,{label:"worktree-merge-success",idempotencyKey:`worktree-merge-success:${e.id}:${r}:${o}`,userMessage:a,notifyUser:"always",completionSummary:{required:!0,producer:"worktree",outcomeKey:`terminal:${e.id}`},completionWakeSummaryRequired:!0,completionWakeOutcomeKey:`terminal:${e.id}`,deferConditionalWakeUntilNextTick:!0,wakeMessageOnNotifySuccess:Ft({sessionId:e.id,sessionName:e.name,outcomeLine:l,originThreadLine:this.deps.originThreadLine(e),detailLines:u,canonicalStatusDelivered:!0}),wakeMessageOnNotifyFailed:Ft({sessionId:e.id,sessionName:e.name,outcomeLine:l,originThreadLine:this.deps.originThreadLine(e),detailLines:u,canonicalStatusDelivered:!1})})}async handleInitialAutoMergeConflict(e,n,r,o,i,s,l,a){let d=a?Ct(a):[],u=e.autoMergeConflictResolutionAttemptCount??0;if(u>=1){this.markPendingDecision(e,{notes:["auto_merge_conflict_retry_exhausted"],clearResolverSessionId:!0}),this.notifyAutoMergeConflictEscalation(e,o,s.pr?`The rebased branch still conflicts with \`${i}\`. Open a PR or resolve manually in ${r}.`:`The rebased branch still conflicts with \`${i}\`. Resolve manually in ${r}.`,s,d);return}let c=this.buildConflictResolverPrompt({session:e,repoDir:n,worktreePath:r,branchName:o,baseBranch:i,mergeError:l});try{let m=await this.deps.spawnConflictResolver({session:e,repoDir:n,worktreePath:r,branchName:o,baseBranch:i,prompt:c});this.markAutoMergeConflictResolving(e,m.id,u+1),this.deps.dispatchSessionNotification(e,{label:"worktree-merge-conflict-resolving",idempotencyKey:`worktree-merge-conflict-resolving:${e.id}:${o}:${m.id}`,userMessage:[`⚠️ [${e.name}] Auto-merge hit a rebase conflict. Started resolver session ${m.name} and will retry automatically if it succeeds.`,...d.map(p=>`⚠️ ${p}`)].join(`
242
- `)})}catch(m){this.markPendingDecision(e,{notes:["auto_merge_conflict_resolver_spawn_failed"]}),this.deps.dispatchSessionNotification(e,{label:"worktree-merge-conflict-spawn-failed",idempotencyKey:`worktree-merge-conflict-spawn-failed:${e.id}:${o}`,userMessage:[`❌ [${e.name}] Auto-merge hit a rebase conflict and failed to start the resolver: ${m instanceof Error?m.message:String(m)}`,...d.map(p=>`⚠️ ${p}`)].join(`
240
+ `),buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,o,{},[[this.deps.makeOpenPrButton(e.id)]])})}updatePersistedSessionFor(e,n){for(let r of me(e))this.deps.updatePersistedSession(r,n)}markPendingDecision(e,n={}){this.updatePersistedSessionFor(e,Mr(e,n))}markAutoMergeConflictResolving(e,n,r){this.updatePersistedSessionFor(e,Tl(e,n,r,{notes:[`resolver_session:${n}`]}))}markMerged(e){this.updatePersistedSessionFor(e,Dt(e,{clearResolverSessionId:!0}))}markReleased(e,n=[]){let r=new Date().toISOString();this.updatePersistedSessionFor(e,{lifecycle:"terminal",worktreeState:"released",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeLifecycle:{state:"released",updatedAt:r,resolvedAt:r,resolutionSource:"lifecycle_resolver",baseBranch:e.worktreeBaseBranch,targetRepo:e.worktreePrTargetRepo,pushRemote:e.worktreePushRemote,notes:n}})}async handleWorktreeStrategy(e){let n=await this.actions.plan(e);if(n.kind==="skip")return n.result;if(n.kind==="notify")return this.deps.dispatchSessionNotification(e,{label:n.label,idempotencyKey:["worktree-action",e.id,n.label,e.completedAt??"unknown",e.worktreeBranch??"unknown",e.worktreePath??"unknown"].join(":"),userMessage:n.message}),{notificationSent:!0,worktreeRemoved:!1};if(n.kind==="dirty-uncommitted")return this.handleDirtyUncommittedCompletion(e,n.worktreePath,n.branchName,n.baseBranch);if(n.kind==="no-change")return this.handleNoChange(e,n.repoDir,n.worktreePath,n.nativeBackendWorktree);if(n.kind==="merged"){let r=n.nativeBackendWorktree?!0:ce(n.repoDir,n.worktreePath);return ye(n.repoDir,n.branchName),this.markMerged(e),{notificationSent:!1,worktreeRemoved:r}}if(n.kind==="released"){let r=n.nativeBackendWorktree?!0:ce(n.repoDir,n.worktreePath);return ye(n.repoDir,n.branchName),this.markReleased(e,n.reasons),{notificationSent:!1,worktreeRemoved:r}}return n.policyBlocked?(this.markPendingDecision(e,{notes:n.policyReason?[n.policyReason]:void 0}),this.deps.dispatchSessionNotification(e,{label:"worktree-policy-blocked",idempotencyKey:`worktree-policy-blocked:${e.id}:${n.branchName}:${n.baseBranch}`,userMessage:`⚠️ [${e.name}] ${n.policyReason??"Repo policy blocked automatic follow-through."}`,buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,n.allowedActions,{allowDelegate:!0})}),{notificationSent:!0,worktreeRemoved:!1}):n.strategy==="ask"?await this.handleAskStrategy(e,n.branchName,n.baseBranch,n.diffSummary,n.allowedActions,n.policyReason):n.strategy==="delegate"?this.handleDelegateStrategy(e,n.branchName,n.baseBranch,n.diffSummary,n.allowedActions,n.policyReason):n.strategy==="auto-merge"?(await this.handleAutoMergeStrategy(e,n.repoDir,n.worktreePath,n.branchName,n.baseBranch,n.diffSummary,n.sessionRef,n.allowedActions),{notificationSent:!0,worktreeRemoved:!1}):n.strategy==="auto-pr"?this.handleAutoPrStrategy(e,n.repoDir,n.worktreePath,n.branchName,n.baseBranch,n.allowedActions):{notificationSent:!1,worktreeRemoved:!1}}async handleNoChange(e,n,r,o=de(e)){let i=o?!0:ce(n,r);return i?(e.worktreePath=void 0,this.updatePersistedSessionFor(e,{worktreePath:void 0,worktreeDisposition:"no-change-cleaned",worktreeState:"none",worktreeLifecycle:{state:"no_change",updatedAt:new Date().toISOString(),resolvedAt:new Date().toISOString(),resolutionSource:"strategy_no_change",baseBranch:e.worktreeBaseBranch,targetRepo:e.worktreePrTargetRepo,pushRemote:e.worktreePushRemote}}),this.deps.dispatchSessionNotification(e,this.deps.worktreeMessages.buildNoChangeNotification({session:e,nativeBackendWorktree:o,cleanupSucceeded:!0,worktreePath:r,preview:this.deps.getOutputPreview(e),originThreadLine:this.deps.originThreadLine(e)}))):this.deps.dispatchSessionNotification(e,this.deps.worktreeMessages.buildNoChangeNotification({session:e,nativeBackendWorktree:o,cleanupSucceeded:!1,worktreePath:r,preview:this.deps.getOutputPreview(e),originThreadLine:this.deps.originThreadLine(e)})),{notificationSent:!0,worktreeRemoved:i}}async handleAskStrategy(e,n,r,o,i,s){let a=await jd({sessionName:e.name,prompt:e.prompt,diffSummary:o,outputPreview:this.deps.getOutputPreview(e,4e3),provider:this.deps.worktreeSummaryProvider});return this.deps.dispatchSessionNotification(e,this.deps.worktreeMessages.buildAskNotification({session:e,branchName:n,baseBranch:r,diffSummary:o,summaryLines:a.lines,policyReason:s,buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,i)})),this.markPendingDecision(e),{notificationSent:!0,worktreeRemoved:!1}}handleDelegateStrategy(e,n,r,o,i,s){return this.deps.dispatchSessionNotification(e,this.deps.worktreeMessages.buildDelegateNotification({session:e,branchName:n,baseBranch:r,diffSummary:o,policyReason:s,allowedActions:i,originThreadLine:this.deps.originThreadLine(e)})),this.markPendingDecision(e),{notificationSent:!0,worktreeRemoved:!1}}getPolicyAwareWorktreeDecisionButtons(e,n,r={},o){if(this.deps.getPolicyAwareWorktreeDecisionButtons)return this.deps.getPolicyAwareWorktreeDecisionButtons(e,r,n);if(o&&n.pr)return o;if(!(o&&!n.pr&&!n.merge))return this.deps.getWorktreeDecisionButtons(e)}handleDirtyUncommittedCompletion(e,n,r,o){this.markPendingDecision(e,{notes:["dirty_uncommitted_completion"]});let i=rt(n),s=i.slice(0,20).map(l=>`- ${l}`),a=i.length>20?[`- ...and ${i.length-20} more`]:[];return this.deps.dispatchSessionNotification(e,{label:"worktree-dirty-uncommitted",idempotencyKey:`worktree-dirty-uncommitted:${e.id}:${r}:${o}`,userMessage:[`⚠️ [${e.name}] Session completed with uncommitted worktree changes.`,"",`Branch \`${r}\` has no commits ahead of \`${o}\`, so merge/PR follow-through is blocked until the worktree is fixed.`,`Worktree: ${n}`,"",...s.length>0?["Dirty entries:",...s,...a,""]:[],"Resume the session or inspect the worktree, then commit real task changes or clean temporary files. Discard only if these local changes should be permanently removed."].join(`
241
+ `)}),{notificationSent:!0,worktreeRemoved:!1}}handleAutoMergeSuccess(e,n,r,o,i,s){ye(n,r),this.markMerged(e);let a=it({kind:"merge",branch:r,base:o,filesChanged:i.filesChanged,insertions:i.insertions,deletions:i.deletions}),l=a;s.stashPopConflict?l+=`
242
+ ⚠️ Pre-merge stash pop conflicted — run \`git stash show ${s.stashRef??"stash@{0}"}\` in ${n} to review stashed changes.`:s.stashed&&(l+=`
243
+ (Pre-existing changes on ${o} were auto-stashed and restored.)`),l=_e(l,s);let d=_t(s),u=[s.fastForward?"Merge type: fast-forward.":"Merge type: merge commit.",`Auto-merge landed ${r} into ${o}.`,"Local worktree branch cleanup was requested.",...s.stashPopConflict?[`Pre-merge stash pop conflicted; run git stash show ${s.stashRef??"stash@{0}"} in ${n} to review stashed changes.`]:[],...!s.stashPopConflict&&s.stashed?[`Pre-existing changes on ${o} were auto-stashed and restored.`]:[],...d];this.deps.dispatchSessionNotification(e,{label:"worktree-merge-success",idempotencyKey:`worktree-merge-success:${e.id}:${r}:${o}`,userMessage:l,notifyUser:"always",completionSummary:{required:!0,producer:"worktree",outcomeKey:`terminal:${e.id}`},completionWakeSummaryRequired:!0,completionWakeOutcomeKey:`terminal:${e.id}`,deferConditionalWakeUntilNextTick:!0,wakeMessageOnNotifySuccess:Ft({sessionId:e.id,sessionName:e.name,outcomeLine:a,originThreadLine:this.deps.originThreadLine(e),detailLines:u,canonicalStatusDelivered:!0}),wakeMessageOnNotifyFailed:Ft({sessionId:e.id,sessionName:e.name,outcomeLine:a,originThreadLine:this.deps.originThreadLine(e),detailLines:u,canonicalStatusDelivered:!1})})}async handleInitialAutoMergeConflict(e,n,r,o,i,s,a,l){let d=l?_t(l):[],u=e.autoMergeConflictResolutionAttemptCount??0;if(u>=1){this.markPendingDecision(e,{notes:["auto_merge_conflict_retry_exhausted"],clearResolverSessionId:!0}),this.notifyAutoMergeConflictEscalation(e,o,s.pr?`The rebased branch still conflicts with \`${i}\`. Open a PR or resolve manually in ${r}.`:`The rebased branch still conflicts with \`${i}\`. Resolve manually in ${r}.`,s,d);return}let c=this.buildConflictResolverPrompt({session:e,repoDir:n,worktreePath:r,branchName:o,baseBranch:i,mergeError:a});try{let p=await this.deps.spawnConflictResolver({session:e,repoDir:n,worktreePath:r,branchName:o,baseBranch:i,prompt:c});this.markAutoMergeConflictResolving(e,p.id,u+1),this.deps.dispatchSessionNotification(e,{label:"worktree-merge-conflict-resolving",idempotencyKey:`worktree-merge-conflict-resolving:${e.id}:${o}:${p.id}`,userMessage:[`⚠️ [${e.name}] Auto-merge hit a rebase conflict. Started resolver session ${p.name} and will retry automatically if it succeeds.`,...d.map(g=>`⚠️ ${g}`)].join(`
244
+ `)})}catch(p){this.markPendingDecision(e,{notes:["auto_merge_conflict_resolver_spawn_failed"]}),this.deps.dispatchSessionNotification(e,{label:"worktree-merge-conflict-spawn-failed",idempotencyKey:`worktree-merge-conflict-spawn-failed:${e.id}:${o}`,userMessage:[`❌ [${e.name}] Auto-merge hit a rebase conflict and failed to start the resolver: ${p instanceof Error?p.message:String(p)}`,...d.map(g=>`⚠️ ${g}`)].join(`
243
245
  `),buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,s,{},[[this.deps.makeOpenPrButton(e.id)]])})}}handleAutoMergeRetryFailure(e,n,r,o,i){this.markPendingDecision(e,{notes:["auto_merge_conflict_retry_failed"],clearResolverSessionId:!0}),this.deps.dispatchSessionNotification(e,{label:"worktree-merge-error",idempotencyKey:`worktree-merge-error:${e.id}:${n}`,userMessage:[o,"","Auto-merge retry did not complete after conflict resolution.",`Branch \`${n}\` was preserved for manual follow-up in ${r}.`].join(`
244
- `),buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,i,{},[[this.deps.makeOpenPrButton(e.id)]])})}async handleAutoMergeStrategy(e,n,r,o,i,s,l=U(e)??e.harnessSessionId,a={merge:!0,pr:!0}){this.deps.isAlreadyMerged(l)||e.autoMergeResolverSessionId||await this.deps.enqueueMerge(n,async()=>{if(this.deps.isAlreadyMerged(l))return;let d=this.deps.mergeBranch(n,o,i,"merge",r);if(d.success){this.handleAutoMergeSuccess(e,n,o,i,s,d);return}if(d.rebaseConflict){await this.handleInitialAutoMergeConflict(e,n,r,o,i,a,d.error,d);return}let u=Me(d.dirtyError?`❌ [${e.name}] Merge blocked: ${d.error}`:`❌ [${e.name}] Merge failed: ${d.error??"unknown error"}`,d);if(e.worktreeState==="merge_conflict_resolving"||e.worktreeLifecycle?.state==="merge_conflict_resolving"){this.handleAutoMergeRetryFailure(e,o,r,u,a);return}this.deps.dispatchSessionNotification(e,{label:"worktree-merge-error",idempotencyKey:`worktree-merge-error:${e.id}:${o}`,userMessage:u})},()=>{this.deps.dispatchSessionNotification(e,{label:"worktree-merge-queued",idempotencyKey:`worktree-merge-queued:${e.id}:${o}`,userMessage:`🕐 [${e.name}] Merge queued — another merge for this repo is in progress. Will notify when complete.`})})}async handleAutoPrStrategy(e,n,r,o,i,s={merge:!0,pr:!0}){if(this.updatePersistedSessionFor(e,{lifecycle:"terminal",worktreeState:"pr_in_progress"}),!(await this.deps.runAutoPr(e,i)).success){let a=At(n);if(!!(a&&a!==o&&It(n,o,a)&&tt(r).length===0)){let u=le(e)?!0:ue(n,r);return u&&(e.worktreePath=void 0,this.updatePersistedSessionFor(e,{worktreePath:void 0})),he(n,o),this.markReleased(e,[`released_by_branch:${a}`]),{notificationSent:!1,worktreeRemoved:u}}this.markPendingDecision(e),this.deps.dispatchSessionNotification(e,{label:"worktree-auto-pr-failed",idempotencyKey:`worktree-auto-pr-failed:${e.id}:${i}`,userMessage:`⚠️ [${e.name}] Auto-PR did not complete. The worktree is preserved for an explicit merge or PR decision.`,buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,s)})}return{notificationSent:!0,worktreeRemoved:!1}}};import{existsSync as Th,statSync as Ch,writeFileSync as Mh}from"fs";be();import{randomUUID as Hg}from"crypto";function zg(t){return t==="plan-approve"||t==="plan-request-changes"||t==="plan-reject"}var ao=class{constructor(e,n){this.onChange=e;this.retentionMs=n}onChange;retentionMs;tokens=new Map;afterChange;replaceAll(e){this.tokens.clear();for(let n of e)this.tokens.set(n.id,n)}clear(){this.tokens.clear(),this.notifyChanged()}listForPersistence(){return[...this.tokens.values()]}createActionToken(e,n,r={}){let o={id:Hg(),sessionId:e,kind:n,createdAt:Date.now(),...r};return this.tokens.set(o.id,o),this.notifyChanged(),o}getActionToken(e){let n=this.tokens.get(e);if(n){if(n.expiresAt!=null&&n.expiresAt<=Date.now()){this.tokens.delete(e),this.notifyChanged();return}return n}}listActiveActionTokens(e){let n=[];for(let r of[...this.tokens.keys()]){let o=this.getActionToken(r);!o||o.consumedAt!=null||e&&o.kind!==e||n.push(o)}return n}consumeActionToken(e){let n=this.getActionToken(e);if(!(!n||n.consumedAt!=null))return n.consumedAt=Date.now(),this.notifyChanged(),n}deleteActionTokensForSession(e){let n=!1;for(let[r,o]of this.tokens)o.sessionId===e&&(this.tokens.delete(r),n=!0);n&&this.notifyChanged()}deleteActionTokensForSessionByKind(e,n){let r=!1;for(let[o,i]of this.tokens)i.sessionId===e&&i.kind===n&&(this.tokens.delete(o),r=!0);r&&this.notifyChanged()}deletePlanDecisionTokensForSession(e,n){let r=!1;for(let[o,i]of this.tokens)i.sessionId!==e||!zg(i.kind)||n!=null&&i.planDecisionVersion===n||(this.tokens.delete(o),r=!0);r&&this.notifyChanged()}purgeExpiredActionTokens(e=Date.now()){let n=!1;for(let[r,o]of this.tokens){let i=o.expiresAt!=null&&o.expiresAt<=e,s=o.consumedAt!=null&&e-o.consumedAt>=this.retentionMs;(i||s)&&(this.tokens.delete(r),n=!0)}return n&&this.notifyChanged(),n}nextExpiryAt(){let e;for(let n of this.tokens.values()){let r=[n.expiresAt,n.consumedAt!=null?n.consumedAt+this.retentionMs:void 0].filter(o=>o!=null&&Number.isFinite(o));for(let o of r)(e==null||o<e)&&(e=o)}return e}setAfterChangeListener(e){this.afterChange=e}notifyChanged(){this.onChange(),this.afterChange?.()}};Z();Z();var lo=class{constructor(e){this.indexes=e}indexes;hasRecordedSession(e){return this.indexes.idIndex.has(e)}getLatestPersistedByName(e){let n,r=Number.NEGATIVE_INFINITY,o=Number.NEGATIVE_INFINITY,i=Number.NEGATIVE_INFINITY,s=0;for(let l of this.indexes.persisted.values()){if(l.name!==e){s++;continue}let a=l.createdAt??Number.NEGATIVE_INFINITY,d=l.completedAt??Number.NEGATIVE_INFINITY;(a>r||a===r&&d>o||a===r&&d===o&&s>i)&&(n=l,r=a,o=d,i=s),s++}return n}resolveBackendConversationId(e,n){if(n)return n;let r=this.indexes.idIndex.get(e);if(r){let s=this.indexes.persisted.get(r);return(s?$(s):void 0)??r}let o=this.getLatestPersistedByName(e);if(o)return $(o)??o.harnessSessionId;let i=this.indexes.backendIdIndex.get(e);if(i){let s=this.indexes.persisted.get(i);return(s?$(s):void 0)??i}if(this.indexes.persisted.has(e)){let s=this.indexes.persisted.get(e);return s?$(s)??e:e}if(/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(e))return e}resolveHarnessSessionId(e,n){return this.resolveBackendConversationId(e,n)}getPersistedSession(e){let n=this.indexes.idIndex.get(e);if(n)return this.indexes.persisted.get(n);let r=this.getLatestPersistedByName(e);if(r)return r;let o=this.indexes.backendIdIndex.get(e);return o?this.indexes.persisted.get(o):this.indexes.persisted.get(e)}listPersistedSessions(){return[...this.indexes.persisted.values()].sort((e,n)=>(n.completedAt??0)-(e.completedAt??0))}};import{existsSync as Vd,mkdirSync as vh,readFileSync as Ph,readdirSync as wh,renameSync as Gd,statSync as jd,unlinkSync as Hd,writeFileSync as zd}from"fs";import{tmpdir as bh}from"os";import{dirname as Rh,join as Qd}from"path";import{homedir as Qg}from"node:os";import{join as Jg}from"node:path";function Od(t){let e=t.OPENCLAW_HOME?.trim();if(e)return e;let n=t.HOME?.trim()||Qg();return Jg(n,".openclaw")}be();var uo=7,Yg=new Set(["running","completed","failed","killed"]);function He(t){return!!t&&typeof t=="object"}function Bt(t,e=""){return typeof t=="string"&&t.trim().length>0?t:e}function P(t){return typeof t=="string"&&t.trim().length>0?t:void 0}function me(t){return typeof t=="number"&&Number.isFinite(t)?t:void 0}function Wd(t){return typeof t=="string"&&ml.has(t)?t:void 0}function gs(t){return t==="default"||t==="plan"||t==="bypassPermissions"?t:void 0}function Zg(t){return t==="never"||t==="on-request"?"never":void 0}function Nd(t){return t==="approve"||t==="ask"||t==="delegate"?t:void 0}function Xg(t){if(t==="plan-mode"||t==="codex-first-turn-plan"||t==="soft-plan")return"plan-mode"}function Ld(t){return typeof t=="string"&&Ir.has(t)?t:void 0}function hs(t){return typeof t=="string"&&pl.has(t)?t:void 0}function Fd(t){return t==="github"||t==="unsupported"?t:void 0}function eh(t){return t==="stored"||t==="seeded"||t==="unknown"?t:void 0}function th(t){return t==="user"||t==="idle-timeout"||t==="startup-timeout"||t==="shutdown"||t==="done"||t==="unknown"?t:void 0}function nh(t){return t==="starting"||t==="active"||t==="awaiting_plan_decision"||t==="awaiting_user_input"||t==="awaiting_worktree_decision"||t==="suspended"||t==="terminal"?t:void 0}function rh(t){return t==="not_required"||t==="pending"||t==="approved"||t==="changes_requested"||t==="rejected"?t:void 0}function oh(t){return t==="none"||t==="provisioned"||t==="pending_decision"||t==="merge_conflict_resolving"||t==="merge_in_progress"||t==="pr_in_progress"||t==="merged"||t==="released"||t==="pr_open"||t==="dismissed"||t==="cleanup_failed"?t:void 0}function ih(t){return t==="none"||t==="provisioned"||t==="pending_decision"||t==="merge_conflict_resolving"||t==="pr_open"||t==="merged"||t==="released"||t==="dismissed"||t==="no_change"||t==="cleanup_failed"?t:void 0}function sh(t){return t==="live"||t==="stopped"?t:void 0}function ah(t){return t==="not_sent"||t==="sending"||t==="delivered"||t==="fallback_delivered"||t==="failed"?t:void 0}function lh(t){return t==="direct-telegram"?"direct-message":t==="none"||t==="direct-message"||t==="wake-only"?t:void 0}function dh(t){return t==="none"||t==="canonical_buttons"||t==="explicit_fallback_text"?t:void 0}function uh(t){return t==="idle"||t==="notifying"||t==="wake_pending"||t==="failed"?t:void 0}function ch(t){return t==="in_flight"||t==="delivered"?t:void 0}function ph(t){if(!Array.isArray(t))return;let e=t.map(n=>{if(!He(n))return;let r=P(n.key),o=ch(n.status),i=P(n.recordedAt);if(!(!r||!o||!i||!Number.isFinite(Date.parse(i))))return{key:r,status:o,recordedAt:i,label:P(n.label)}}).filter(n=>!!n);return e.length>0?e.slice(-64):void 0}function mh(t){if(!Array.isArray(t))return;let e=t.map(n=>{if(!He(n))return;let r=P(n.key),o=P(n.recordedAt);if(!(!r||!o||!Number.isFinite(Date.parse(o))))return{key:r,recordedAt:o,label:P(n.label),skipReason:P(n.skipReason)}}).filter(n=>!!n);return e.length>0?e.slice(-1024):void 0}function fh(t){return t==="awaiting_plan_output"||t==="awaiting_approval"||t==="approved_then_implemented"||t==="implemented_without_required_approval"||t==="not_plan_gated"?t:void 0}function gh(t){return t==="plan-approve"||t==="plan-request-changes"||t==="plan-reject"||t==="plan-offer-start"||t==="plan-offer-dismiss"||t==="repo-policy-set"||t==="worktree-merge"||t==="worktree-create-pr"||t==="worktree-update-pr"||t==="worktree-view-pr"||t==="worktree-decide-later"||t==="worktree-dismiss"||t==="session-resume"||t==="session-restart"||t==="view-output"||t==="question-answer"?t:void 0}function Bd(t){if(!He(t))return;let e=P(t.provider),n=P(t.accountId),r=P(t.target),o=P(t.threadId),i=P(t.sessionKey);if(!(!e||!r))return{provider:e,accountId:n,target:r,threadId:o,sessionKey:i}}function hh(t,e,n){if(He(t)){let r=P(t.kind),o=P(t.conversationId);if(o&&(r==="claude-code"||r==="codex-app-server"||r==="opencode-server"))return{kind:r,conversationId:o,runId:P(t.runId),worktreeId:P(t.worktreeId),worktreePath:P(t.worktreePath)}}if(e==="claude-code")return{kind:"claude-code",conversationId:n}}function yh(t){if(!He(t))return;let e=ih(t.state),n=P(t.updatedAt);if(!e||!n)return;let r=P(t.resolutionSource);return{state:e,updatedAt:n,resolvedAt:P(t.resolvedAt),resolutionSource:r==="agent_merge"||r==="agent_pr"||r==="strategy_no_change"||r==="lifecycle_resolver"||r==="dismiss"||r==="maintenance"?r:void 0,baseBranch:P(t.baseBranch),targetRepo:P(t.targetRepo),pushRemote:P(t.pushRemote),notes:Array.isArray(t.notes)?t.notes.filter(o=>typeof o=="string"&&o.length>0):void 0}}function kh(t){let e=new Date(0).toISOString(),n=P(t.worktreeMergedAt)??P(t.worktreeDismissedAt)??P(t.pendingWorktreeDecisionSince)??e;if(t.worktreeMerged===!0||t.worktreeDisposition==="merged")return{state:"merged",updatedAt:n,resolvedAt:P(t.worktreeMergedAt)??n,resolutionSource:"agent_merge",baseBranch:P(t.worktreeBaseBranch),targetRepo:P(t.worktreePrTargetRepo),pushRemote:P(t.worktreePushRemote)};if(t.worktreeDisposition==="dismissed")return{state:"dismissed",updatedAt:n,resolvedAt:P(t.worktreeDismissedAt)??n,resolutionSource:"dismiss",baseBranch:P(t.worktreeBaseBranch),targetRepo:P(t.worktreePrTargetRepo),pushRemote:P(t.worktreePushRemote)};if(t.worktreeDisposition==="no-change-cleaned")return{state:"no_change",updatedAt:n,resolvedAt:n,resolutionSource:"strategy_no_change",baseBranch:P(t.worktreeBaseBranch),targetRepo:P(t.worktreePrTargetRepo),pushRemote:P(t.worktreePushRemote)};if(t.worktreeDisposition==="pr-opened"||t.worktreeState==="pr_open")return{state:"pr_open",updatedAt:n,baseBranch:P(t.worktreeBaseBranch),targetRepo:P(t.worktreePrTargetRepo),pushRemote:P(t.worktreePushRemote)};if(t.pendingWorktreeDecisionSince||t.worktreeState==="pending_decision")return{state:"pending_decision",updatedAt:n,baseBranch:P(t.worktreeBaseBranch),targetRepo:P(t.worktreePrTargetRepo),pushRemote:P(t.worktreePushRemote)};if(t.worktreeState==="merge_conflict_resolving")return{state:"merge_conflict_resolving",updatedAt:n,baseBranch:P(t.worktreeBaseBranch),targetRepo:P(t.worktreePrTargetRepo),pushRemote:P(t.worktreePushRemote)};if(P(t.worktreePath)||P(t.worktreeBranch))return{state:"provisioned",updatedAt:n,baseBranch:P(t.worktreeBaseBranch),targetRepo:P(t.worktreePrTargetRepo),pushRemote:P(t.worktreePushRemote)}}function Sh(t){if(typeof t=="string"&&Yg.has(t))return t==="running"?"killed":t}function qd(t){if(!He(t))return;let e=Bt(t.harnessSessionId);if(!e)return;let n=Sh(t.status);if(!n)return;let r=t.status==="running",o=P(t.worktreePath),i=P(t.worktreeBranch),s=P(t.originChannel),l=typeof t.originThreadId=="string"||typeof t.originThreadId=="number"?t.originThreadId:void 0,a=P(t.originSessionKey),d=Bd(t.route);if(!d)return;let u=Qe({route:d,originChannel:s,originThreadId:l,originSessionKey:a});if(!u||o&&!i)return;let c=P(t.harness),m=hh(t.backendRef,c,e),p=yh(t.worktreeLifecycle)??kh(t),f=P(t.completionWakeSucceededAt),h=P(t.completionWakeSkippedAt),k=t.completionWakeSummaryRequired===!0&&!h?!0:void 0;return{sessionId:P(t.sessionId),harnessSessionId:e,backendRef:m,name:Bt(t.name,e),prompt:Bt(t.prompt),workdir:Bt(t.workdir,"(unknown)"),model:P(t.model),reasoningEffort:Wd(t.reasoningEffort),fastMode:t.fastMode===!0?!0:void 0,createdAt:me(t.createdAt),completedAt:me(t.completedAt),status:n,lifecycle:r?"suspended":nh(t.lifecycle),approvalState:rh(t.approvalState),worktreeState:oh(t.worktreeState),runtimeState:r?"stopped":sh(t.runtimeState),deliveryState:uh(t.deliveryState),notificationDedupe:ph(t.notificationDedupe),completionSummaryDedupe:mh(t.completionSummaryDedupe),completionWakeIssuedAt:P(t.completionWakeIssuedAt),completionWakeSucceededAt:f,completionWakeFailedAt:P(t.completionWakeFailedAt),completionWakeSkippedAt:h,completionWakeSkipReason:P(t.completionWakeSkipReason),completionWakeSummaryRequired:k,killReason:th(t.killReason),costUsd:typeof t.costUsd=="number"&&Number.isFinite(t.costUsd)?t.costUsd:0,originAgentId:P(t.originAgentId),originChannel:s,originThreadId:l,originSessionKey:a,route:u,outputPath:P(t.outputPath),harness:c,goalTaskId:P(t.goalTaskId),requestedPermissionMode:gs(t.requestedPermissionMode),currentPermissionMode:gs(t.currentPermissionMode),approvalExecutionState:fh(t.approvalExecutionState),approvalRationale:P(t.approvalRationale),planModeApproved:t.planModeApproved===!0,pendingPlanApproval:t.pendingPlanApproval===!0,planApprovalContext:Xg(t.planApprovalContext),planDecisionVersion:me(t.planDecisionVersion),actionablePlanDecisionVersion:me(t.actionablePlanDecisionVersion),canonicalPlanPromptVersion:me(t.canonicalPlanPromptVersion),approvalPromptRequiredVersion:me(t.approvalPromptRequiredVersion),approvalPromptVersion:me(t.approvalPromptVersion),approvalPromptStatus:ah(t.approvalPromptStatus),approvalPromptTransport:lh(t.approvalPromptTransport),approvalPromptMessageKind:dh(t.approvalPromptMessageKind),approvalPromptLastAttemptAt:P(t.approvalPromptLastAttemptAt),approvalPromptDeliveredAt:P(t.approvalPromptDeliveredAt),approvalPromptFailedAt:P(t.approvalPromptFailedAt),planApproval:Nd(t.planApproval),codexApprovalPolicy:Zg(t.codexApprovalPolicy),worktreePath:o,worktreeBranch:i,worktreeStrategy:Ld(t.worktreeStrategy),repoIntegrationPolicy:hs(t.repoIntegrationPolicy),repoIntegrationPolicySource:eh(t.repoIntegrationPolicySource),repoProvider:Fd(t.repoProvider),worktreeMerged:typeof t.worktreeMerged=="boolean"?t.worktreeMerged:void 0,worktreeMergedAt:P(t.worktreeMergedAt),worktreePrUrl:P(t.worktreePrUrl),worktreePrNumber:me(t.worktreePrNumber),pendingWorktreeDecisionSince:P(t.pendingWorktreeDecisionSince),lastWorktreeReminderAt:P(t.lastWorktreeReminderAt),worktreeBaseBranch:P(t.worktreeBaseBranch),worktreePrTargetRepo:P(t.worktreePrTargetRepo),autoMergeParentSessionId:P(t.autoMergeParentSessionId),autoMergeConflictResolutionAttemptCount:me(t.autoMergeConflictResolutionAttemptCount),autoMergeResolverSessionId:P(t.autoMergeResolverSessionId),worktreePushRemote:P(t.worktreePushRemote),worktreeDecisionSnoozedUntil:P(t.worktreeDecisionSnoozedUntil),worktreeDisposition:t.worktreeDisposition==="active"||t.worktreeDisposition==="pr-opened"||t.worktreeDisposition==="merged"||t.worktreeDisposition==="dismissed"||t.worktreeDisposition==="no-change-cleaned"?t.worktreeDisposition:void 0,worktreeDismissedAt:P(t.worktreeDismissedAt),worktreeLifecycle:p,resumable:r?!0:t.resumable===!0}}function Ud(t){if(!He(t))return;let e=P(t.key),n=P(t.repoRoot),r=hs(t.policy),o=Fd(t.provider)??"unsupported",i=P(t.createdAt),s=P(t.updatedAt),l=t.source==="seeded"?"seeded":"stored";if(!(!e||!n||!r||!i||!s)&&!(!Number.isFinite(Date.parse(i))||!Number.isFinite(Date.parse(s))))return{key:e,policy:r,repoRoot:n,remoteUrl:P(t.remoteUrl),provider:o,createdAt:i,updatedAt:s,source:l}}function Kd(t){if(!He(t))return;let e=gh(t.kind),n=Bt(t.id),r=Bt(t.sessionId),o=me(t.createdAt);if(!(!n||!r||!e||o==null))return{id:n,sessionId:r,kind:e,createdAt:o,planDecisionVersion:me(t.planDecisionVersion),expiresAt:me(t.expiresAt),consumedAt:me(t.consumedAt),optionIndex:me(t.optionIndex),pendingInputRequestId:P(t.pendingInputRequestId),pendingInputQuestionId:P(t.pendingInputQuestionId),label:P(t.label),targetUrl:P(t.targetUrl),route:Bd(t.route),launchName:P(t.launchName),launchPrompt:P(t.launchPrompt),launchWorkdir:P(t.launchWorkdir),launchModel:P(t.launchModel),launchReasoningEffort:Wd(t.launchReasoningEffort),launchFastMode:t.launchFastMode===!0?!0:void 0,launchSystemPrompt:P(t.launchSystemPrompt),launchAllowedTools:Array.isArray(t.launchAllowedTools)?t.launchAllowedTools.filter(i=>typeof i=="string"):void 0,launchResumeSessionId:P(t.launchResumeSessionId),launchResumeWorktreeFrom:P(t.launchResumeWorktreeFrom),launchSessionIdOverride:P(t.launchSessionIdOverride),launchClearedPersistedCodexResume:t.launchClearedPersistedCodexResume===!0?!0:void 0,launchForkSession:typeof t.launchForkSession=="boolean"?t.launchForkSession:void 0,launchForceNewSession:typeof t.launchForceNewSession=="boolean"?t.launchForceNewSession:void 0,launchPermissionMode:gs(t.launchPermissionMode),launchPlanApproval:Nd(t.launchPlanApproval),launchHarness:P(t.launchHarness),launchWorktreeStrategy:Ld(t.launchWorktreeStrategy),launchWorktreeBaseBranch:P(t.launchWorktreeBaseBranch),launchWorktreePrTargetRepo:P(t.launchWorktreePrTargetRepo),launchOriginAgentId:P(t.launchOriginAgentId),repoPolicy:hs(t.repoPolicy),repoPolicyWorkdir:P(t.repoPolicyWorkdir)}}function co(t){if(!t.backendRef?.kind||!t.backendRef.conversationId)throw new Error(`Persisted session ${t.harnessSessionId} is missing required backend ref metadata.`);if(!t.route?.provider||!t.route.target)throw new Error(`Persisted session ${t.harnessSessionId} is missing required route metadata.`);if(t.worktreePath&&!t.worktreeBranch)throw new Error(`Persisted session ${t.harnessSessionId} is missing required worktreeBranch metadata.`)}function ys(t){return!!t&&typeof t=="object"}function ks(t){return t instanceof Error?t.message:String(t)}function Jd(t,e,n=Date.now()){let r=`${t}.${e}-${n}`;for(let o=0;o<100;o+=1){let i=o===0?"":`-${o}`,s=`${r}${i}.json`;if(!Vd(s))return s}}function Ss(){let t=bh();return wh(t).filter(e=>e.startsWith("openclaw-agent-")&&e.endsWith(".txt")).map(e=>Qd(t,e))}function Yd(t){let e=t.OPENCLAW_CODE_AGENT_SESSIONS_PATH?.trim();return e||Qd(Od(t),"code-agent-sessions.json")}function Zd(t,e,n,r=[]){try{vh(Rh(t),{recursive:!0});let o=t+".tmp";zd(o,JSON.stringify({schemaVersion:uo,sessions:e,actionTokens:n,repoPolicies:r},null,2),"utf-8"),Gd(o,t)}catch(o){`${ks(o)}`}}function Ah(t,e){try{if(!Vd(t))return!1;let n=Jd(t,"legacy");return n?(Gd(t,n),`${e}${n}`,!0):!1}catch(n){return`${ks(n)}`,!1}}var Ih={archiveLegacySessionIndex:Ah};function xh(t,e){try{if(e.length===0)return;let n=Jd(t,"codex-sdk-legacy");if(!n)return;zd(n,JSON.stringify(e,null,2),"utf-8"),`${e.length}${n}`}catch(n){`${ks(n)}`}}function Xd(t,e,n=[]){try{let r=new Set(n);for(let o of Ss())if(!r.has(o))try{let i=jd(o).mtimeMs;t-i>e&&Hd(o)}catch{}}catch{}}function eu(t,e,n=[]){try{let r=new Set(n),o;for(let i of Ss())if(!r.has(i))try{let s=jd(i).mtimeMs+e;if(s<=t)return t;o=o==null?s:Math.min(o,s)}catch{}return o}catch{return}}function tu(t){try{let e=new Set(t);for(let n of Ss())if(!e.has(n))try{Hd(n)}catch{}}catch{}}function nu(t){let{indexPath:e,clearAll:n,indexPersistedEntry:r,setActionToken:o,setRepoPolicy:i,purgeExpiredActionTokens:s,saveIndex:l}=t,a=d=>Ih.archiveLegacySessionIndex(e,d)?(n(),!0):!1;try{let d=Ph(e,"utf-8"),u=JSON.parse(d);if(Array.isArray(u)){if(!a("legacy array store"))return;l();return}if(!ys(u)||u.schemaVersion!==uo&&u.schemaVersion!==6&&u.schemaVersion!==4){if(!a(`schema mismatch (expected v${uo})`))return;l();return}let c=(b,A)=>{if(!Object.prototype.hasOwnProperty.call(u,b))return[];let y=u[b];if(Array.isArray(y))return y;a(A)&&l()},m=c("sessions","invalid sessions collection");if(m===void 0)return;let p=[],f=[];for(let b of m){if(ys(b)&&b.harness==="codex"){let y=ys(b.backendRef)?b.backendRef:void 0;if((typeof y?.kind=="string"?y.kind:void 0)!=="codex-app-server"){p.push(b);continue}}let A=qd(b);if(!A){if(!a("invalid v4 session entry"))return;l();return}f.push(A)}p.length>0&&xh(e,p);let h=c("actionTokens","invalid action token collection");if(h===void 0)return;let k=[];for(let b of h){let A=Kd(b);if(!A){if(!a("invalid v4 action token"))return;l();return}k.push(A)}let v=c("repoPolicies","invalid repo policy collection");if(v===void 0)return;let I=[],x=!1;for(let b of v){let A=Ud(b);if(!A){x=!0;continue}I.push(A)}for(let b of f)r(b);for(let b of k)o(b);for(let b of I)i(b);p.length>0&&l(),x&&l(),s()}catch(d){if(d.code==="ENOENT"||!a("corrupt or unreadable"))return;l()}}var _h=new Set(["completed","failed","killed"]),vs=1440*60*1e3;function $h(t){return t instanceof Error?t.message:String(t)}var Eh={statSync:Ch};function Dh(t){try{return Eh.statSync(t).isDirectory()}catch(e){let n=e.code;return n!=="ENOENT"&&n!=="ENOTDIR"}}var po=class{persisted=new Map;repoPolicies=new Map;idIndex=new Map;nameIndex=new Map;backendIdIndex=new Map;actionTokens;actionTokenStore;indexPath;queries;constructor(e={}){let n=e.env??process.env;this.indexPath=e.indexPath??Yd(n),this.actionTokenStore=new ao(()=>this.saveIndex(),vs),this.actionTokens=this.actionTokenStore.tokens,this.queries=new lo({persisted:this.persisted,idIndex:this.idIndex,nameIndex:this.nameIndex,backendIdIndex:this.backendIdIndex}),n.OPENCLAW_DEBUG_SESSION_STORE==="1"&&`${this.indexPath}`,this.loadIndex()}loadIndex(){nu({indexPath:this.indexPath,clearAll:()=>{this.persisted.clear(),this.repoPolicies.clear(),this.idIndex.clear(),this.nameIndex.clear(),this.backendIdIndex.clear(),this.actionTokenStore.clear()},indexPersistedEntry:e=>this.indexPersistedEntry(e),setActionToken:e=>{this.actionTokens.set(e.id,e)},setRepoPolicy:e=>{this.repoPolicies.set(e.key,e)},purgeExpiredActionTokens:()=>this.actionTokenStore.purgeExpiredActionTokens(),saveIndex:()=>this.saveIndex()})}saveIndex(){Zd(this.indexPath,[...this.persisted.values()],this.actionTokenStore.listForPersistence(),[...this.repoPolicies.values()])}assertPersistedEntry(e){co(e)}getEntryStorageKey(e){return e.harnessSessionId}buildPersistedBackendRef(e){let n=pi(e),r=n==="codex"?"codex-app-server":n==="opencode"?"opencode-server":"claude-code";return e.backendRef??{kind:e.backendKind??r,conversationId:e.harnessSessionId}}getSessionApprovalSnapshot(e){if(typeof e.approvalSnapshot=="function")return e.approvalSnapshot();let n=typeof e.controlStateSnapshot=="function"?e.controlStateSnapshot():{planModeApproved:!1};return{requestedPermissionMode:e.requestedPermissionMode,currentPermissionMode:e.currentPermissionMode,approvalExecutionState:e.approvalExecutionState,approvalRationale:e.approvalRationale,planModeApproved:n.planModeApproved,pendingPlanApproval:e.pendingPlanApproval,planApprovalContext:e.planApprovalContext,planDecisionVersion:e.planDecisionVersion,actionablePlanDecisionVersion:e.actionablePlanDecisionVersion,canonicalPlanPromptVersion:e.canonicalPlanPromptVersion,approvalPromptRequiredVersion:e.approvalPromptRequiredVersion,approvalPromptVersion:e.approvalPromptVersion,approvalPromptStatus:e.approvalPromptStatus,approvalPromptTransport:e.approvalPromptTransport,approvalPromptMessageKind:e.approvalPromptMessageKind,approvalPromptLastAttemptAt:e.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:e.approvalPromptDeliveredAt,approvalPromptFailedAt:e.approvalPromptFailedAt,planApproval:e.planApproval,codexApprovalPolicy:e.codexApprovalPolicy}}getSessionRoutingSnapshot(e){return typeof e.routingSnapshot=="function"?e.routingSnapshot():{route:e.route,originAgentId:e.originAgentId,originChannel:e.originChannel,originThreadId:e.originThreadId,originSessionKey:e.originSessionKey}}getSessionWorktreeSnapshot(e){return typeof e.worktreeSnapshot=="function"?e.worktreeSnapshot():{worktreePath:e.worktreePath,worktreeBranch:e.worktreeBranch,worktreeStrategy:e.worktreeStrategy,repoIntegrationPolicy:e.repoIntegrationPolicy,repoIntegrationPolicySource:e.repoIntegrationPolicySource,repoProvider:e.repoProvider,worktreeBaseBranch:e.worktreeBaseBranch,worktreePrTargetRepo:e.worktreePrTargetRepo,autoMergeParentSessionId:e.autoMergeParentSessionId,autoMergeConflictResolutionAttemptCount:e.autoMergeConflictResolutionAttemptCount,autoMergeResolverSessionId:e.autoMergeResolverSessionId,worktreeLifecycle:e.worktreeLifecycle}}indexPersistedEntry(e){let n=this.getEntryStorageKey(e);this.persisted.set(n,e),e.sessionId&&this.idIndex.set(e.sessionId,n),e.name&&this.nameIndex.set(e.name,n);let r=$(e);r&&this.backendIdIndex.set(r,n)}removePersistedIndexes(e){let n=this.getEntryStorageKey(e);this.persisted.delete(n);for(let[r,o]of this.idIndex)o===n&&this.idIndex.delete(r);for(let[r,o]of this.nameIndex)o===n&&this.nameIndex.delete(r);for(let[r,o]of this.backendIdIndex)o===n&&this.backendIdIndex.delete(r)}markRunning(e){if(!e.harnessSessionId)return;let n=this.getSessionApprovalSnapshot(e),r=this.getSessionRoutingSnapshot(e),o=this.getSessionWorktreeSnapshot(e),i=Qe({route:r.route,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey});if(!i)return;let s={sessionId:e.id,harnessSessionId:e.harnessSessionId,backendRef:this.buildPersistedBackendRef(e),name:e.name,prompt:e.prompt,workdir:e.originalWorkdir??e.workdir,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,createdAt:e.startedAt,status:"running",lifecycle:e.lifecycle,approvalState:e.approvalState,worktreeState:e.worktreeState,runtimeState:e.runtimeState,deliveryState:e.deliveryState,notificationDedupe:this.getExistingNotificationDedupe(e),costUsd:0,originAgentId:r.originAgentId,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey,route:i,outputPath:et(e.id),harness:e.harnessName,requestedPermissionMode:n.requestedPermissionMode,currentPermissionMode:n.currentPermissionMode,approvalExecutionState:n.approvalExecutionState,approvalRationale:n.approvalRationale,planModeApproved:n.planModeApproved,pendingPlanApproval:n.pendingPlanApproval,planApprovalContext:n.planApprovalContext,planDecisionVersion:n.planDecisionVersion,actionablePlanDecisionVersion:n.actionablePlanDecisionVersion,canonicalPlanPromptVersion:n.canonicalPlanPromptVersion,approvalPromptRequiredVersion:n.approvalPromptRequiredVersion,approvalPromptVersion:n.approvalPromptVersion,approvalPromptStatus:n.approvalPromptStatus,approvalPromptTransport:n.approvalPromptTransport,approvalPromptMessageKind:n.approvalPromptMessageKind,approvalPromptLastAttemptAt:n.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:n.approvalPromptDeliveredAt,approvalPromptFailedAt:n.approvalPromptFailedAt,planApproval:n.planApproval,codexApprovalPolicy:n.codexApprovalPolicy,worktreePath:o.worktreePath,worktreeBranch:o.worktreeBranch,worktreeStrategy:o.worktreeStrategy,repoIntegrationPolicy:o.repoIntegrationPolicy,repoIntegrationPolicySource:o.repoIntegrationPolicySource,repoProvider:o.repoProvider,worktreeBaseBranch:o.worktreeBaseBranch,worktreePrTargetRepo:o.worktreePrTargetRepo,autoMergeParentSessionId:o.autoMergeParentSessionId,autoMergeConflictResolutionAttemptCount:o.autoMergeConflictResolutionAttemptCount,autoMergeResolverSessionId:o.autoMergeResolverSessionId,worktreeLifecycle:o.worktreeLifecycle,resumable:e.isExplicitlyResumable};co(s),this.indexPersistedEntry(s),this.saveIndex()}hasRecordedSession(e){return this.queries.hasRecordedSession(e)}persistTerminal(e){if(!e.harnessSessionId)return;let n=this.getSessionApprovalSnapshot(e),r=this.getSessionRoutingSnapshot(e),o=this.getSessionWorktreeSnapshot(e),i=Qe({route:r.route,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey});if(!i)return;let s;try{let a=et(e.id);if(Th(a))s=a;else{let d=e.getOutput().join(`
245
- `);d.length>0&&(Mh(a,d,"utf-8"),s=a)}}catch(a){`${e.id}${$h(a)}`}let l={sessionId:e.id,harnessSessionId:e.harnessSessionId,backendRef:this.buildPersistedBackendRef(e),name:e.name,prompt:e.prompt,workdir:e.originalWorkdir??e.workdir,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,createdAt:e.startedAt,completedAt:e.completedAt,status:e.status,lifecycle:e.lifecycle,approvalState:e.approvalState,worktreeState:e.worktreeState,runtimeState:e.runtimeState,deliveryState:e.deliveryState,notificationDedupe:this.getExistingNotificationDedupe(e),killReason:e.killReason,costUsd:e.costUsd,originAgentId:r.originAgentId,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey,route:i,outputPath:s,harness:e.harnessName,goalTaskId:e.goalTaskId,requestedPermissionMode:n.requestedPermissionMode,currentPermissionMode:n.currentPermissionMode,approvalExecutionState:n.approvalExecutionState,approvalRationale:n.approvalRationale,planModeApproved:n.planModeApproved,pendingPlanApproval:n.pendingPlanApproval,planApprovalContext:n.planApprovalContext,planDecisionVersion:n.planDecisionVersion,actionablePlanDecisionVersion:n.actionablePlanDecisionVersion,canonicalPlanPromptVersion:n.canonicalPlanPromptVersion,approvalPromptRequiredVersion:n.approvalPromptRequiredVersion,approvalPromptVersion:n.approvalPromptVersion,approvalPromptStatus:n.approvalPromptStatus,approvalPromptTransport:n.approvalPromptTransport,approvalPromptMessageKind:n.approvalPromptMessageKind,approvalPromptLastAttemptAt:n.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:n.approvalPromptDeliveredAt,approvalPromptFailedAt:n.approvalPromptFailedAt,planApproval:n.planApproval,codexApprovalPolicy:n.codexApprovalPolicy,worktreePath:o.worktreePath,worktreeBranch:o.worktreeBranch,worktreeStrategy:o.worktreeStrategy,worktreeBaseBranch:o.worktreeBaseBranch,worktreePrTargetRepo:o.worktreePrTargetRepo,autoMergeParentSessionId:o.autoMergeParentSessionId,autoMergeConflictResolutionAttemptCount:o.autoMergeConflictResolutionAttemptCount,autoMergeResolverSessionId:o.autoMergeResolverSessionId,worktreeLifecycle:o.worktreeLifecycle,resumable:e.isExplicitlyResumable};co(l),this.indexPersistedEntry(l),this.saveIndex()}getExistingNotificationDedupe(e){return this.getPersistedSession(e.id)?.notificationDedupe??(e.harnessSessionId?this.getPersistedSession(e.harnessSessionId)?.notificationDedupe:void 0)??($(e)?this.getPersistedSession($(e))?.notificationDedupe:void 0)}getLatestPersistedByName(e){return this.queries.getLatestPersistedByName(e)}resolveBackendConversationId(e,n){return this.queries.resolveBackendConversationId(e,n)}resolveHarnessSessionId(e,n){return this.queries.resolveHarnessSessionId(e,n)}getPersistedSession(e){return this.queries.getPersistedSession(e)}listPersistedSessions(){return this.queries.listPersistedSessions()}getRepoPolicy(e){return this.repoPolicies.get(e)}listRepoPolicies(){return[...this.repoPolicies.values()].sort((e,n)=>e.repoRoot.localeCompare(n.repoRoot)||e.key.localeCompare(n.key))}setRepoPolicy(e){let n=this.repoPolicies.get(e.key),r={...e,createdAt:n?.createdAt??e.createdAt,updatedAt:new Date().toISOString(),source:"stored"};return this.repoPolicies.set(r.key,r),this.saveIndex(),r}updateRepoPolicy(e,n){let r=this.repoPolicies.get(e);if(r)return this.setRepoPolicy({...r,policy:n})}resetRepoPolicy(e){let n=this.repoPolicies.delete(e);return n&&this.saveIndex(),n}removeRepoPolicies(e){let n=[];for(let r of e){let o=this.repoPolicies.get(r);o&&(this.repoPolicies.delete(r),n.push(o))}return n.length>0&&this.saveIndex(),n.sort((r,o)=>r.repoRoot.localeCompare(o.repoRoot)||r.key.localeCompare(o.key))}cleanupRepoPolicies(){let e=[];for(let[n,r]of this.repoPolicies)Dh(r.repoRoot)||(this.repoPolicies.delete(n),e.push(r));return e.length>0&&this.saveIndex(),e.sort((n,r)=>n.repoRoot.localeCompare(r.repoRoot)||n.key.localeCompare(r.key))}cleanupTmpOutputFiles(e){this.actionTokenStore.purgeExpiredActionTokens(e),Xd(e,vs,this.getReferencedOutputPaths())}getNextTmpOutputCleanupAt(e){return eu(e,vs,this.getReferencedOutputPaths())}evictOldestPersisted(e){let n=this.listPersistedSessions();if(n.length<=e)return[];let r=n.slice(e);for(let o of r)this.removePersistedIndexes(o);return this.saveIndex(),r}shouldGcActiveSession(e,n,r){return!e.completedAt||!_h.has(e.status)?!1:n-e.completedAt>r}getActionToken(e){return this.actionTokenStore.getActionToken(e)}consumeActionToken(e){return this.actionTokenStore.consumeActionToken(e)}deleteActionTokensForSession(e){this.actionTokenStore.deleteActionTokensForSession(e)}purgeExpiredActionTokens(e=Date.now()){return this.actionTokenStore.purgeExpiredActionTokens(e)}getNextActionTokenExpiry(){return this.actionTokenStore.nextExpiryAt()}onActionTokensChanged(e){this.actionTokenStore.setAfterChangeListener(e)}hasOutputPathReference(e){for(let n of this.persisted.values())if(n.outputPath===e)return!0;return!1}getReferencedOutputPaths(){return[...new Set([...this.persisted.values()].map(e=>e.outputPath).filter(e=>typeof e=="string"&&e.length>0))]}cleanupOrphanOutputFiles(){tu(this.getReferencedOutputPaths())}};var Oh=new Set(["completed","failed","killed"]),mo=class{metrics={totalCostUsd:0,costPerDay:new Map,sessionsByStatus:{completed:0,failed:0,killed:0},totalLaunched:0,totalDurationMs:0,sessionsWithDuration:0,mostExpensive:null};incrementLaunched(){this.metrics.totalLaunched++}recordSession(e){let n=e.costUsd??0,r=e.status;this.metrics.totalCostUsd+=n;let o=new Date(e.completedAt??e.startedAt).toISOString().slice(0,10);if(this.metrics.costPerDay.set(o,(this.metrics.costPerDay.get(o)??0)+n),Oh.has(r)&&this.metrics.sessionsByStatus[r]++,e.completedAt){let i=e.completedAt-e.startedAt;this.metrics.totalDurationMs+=i,this.metrics.sessionsWithDuration++}(!this.metrics.mostExpensive||n>this.metrics.mostExpensive.costUsd)&&(this.metrics.mostExpensive={id:e.id,name:e.name,costUsd:n,prompt:se(e.prompt,80)})}getMetrics(){return{totalCostUsd:this.metrics.totalCostUsd,costPerDay:new Map(this.metrics.costPerDay),sessionsByStatus:{...this.metrics.sessionsByStatus},totalLaunched:this.metrics.totalLaunched,totalDurationMs:this.metrics.totalDurationMs,sessionsWithDuration:this.metrics.sessionsWithDuration,mostExpensive:this.metrics.mostExpensive?{...this.metrics.mostExpensive}:null}}};import*as iu from"child_process";var ru=5e3,su=64,Wh={primary:"primary",success:"success",positive:"success",danger:"danger",destructive:"danger",negative:"danger"},Nh={execFile:iu.execFile},ze=class extends Error{constructor(e){super(e),this.name="MissingRuntimeDirectNotificationCapabilityError"}},go=class{constructor(e=Nh.execFile){this.execFile=e}execFile;async send(e,n,r){L("direct_send_started",{...we(e),messageTextLength:n.length,...J(r)});try{await this.sendViaRuntime(e,n,r),L("direct_send_succeeded",{...we(e),deliveryPath:"runtime",...J(r)});return}catch(o){if(!(o instanceof ze))throw L("direct_send_failed",{...we(e),deliveryPath:"runtime",...J(r),error:Ps(o)}),o;L("direct_send_runtime_capability_missing",{...we(e),deliveryPath:"runtime",...J(r),reason:o.message}),await this.sendViaBoundedCliFallback(e,n,r,o.message),L("direct_send_succeeded",{...we(e),deliveryPath:"cli-fallback",...J(r)})}}async sendViaRuntime(e,n,r){let o=bt(),i=Ra(),s=o?.channel?.outbound?.loadAdapter;if(!o)throw new ze("OpenClaw plugin runtime is unavailable for direct notification delivery");if(i==null)throw new ze("OpenClaw runtime config snapshot is unavailable for direct notification delivery");if(!o.channel)throw new ze(`OpenClaw plugin runtime channel surface is unavailable for direct notification delivery (runtimeVersion=${ws(o)})`);if(!o.channel.outbound)throw new ze(`OpenClaw plugin runtime channel outbound surface is unavailable for direct notification delivery (runtimeVersion=${ws(o)})`);if(!s)throw new ze(`OpenClaw plugin runtime channel outbound loadAdapter is unavailable for direct notification delivery (runtimeVersion=${ws(o)})`);let l=await s(e.channel);if(!l)throw new Error(`OpenClaw outbound adapter for channel "${e.channel}" is unavailable`);let a=yo(r);if(L("runtime_adapter_loaded",{...we(e),adapterHasRenderPresentation:typeof l.renderPresentation=="function",adapterHasSendPayload:typeof l.sendPayload=="function",adapterHasSendText:typeof l.sendText=="function",...J(r),...a?Hi(a):{}}),a){await this.sendPresentation(l,i,e,n,a);return}if(!l.sendText)throw new Error(`OpenClaw outbound adapter for channel "${e.channel}" cannot send text`);await l.sendText({cfg:i,to:e.target,text:n,accountId:e.accountId,threadId:e.threadId})}async sendPresentation(e,n,r,o,i){let s=Fh(i),l={text:o,presentation:i,interactive:s};L("presentation_render_started",{...we(r),messageTextLength:o.length,adapterHasRenderPresentation:typeof e.renderPresentation=="function",adapterHasSendPayload:typeof e.sendPayload=="function",...Hi(i)});let a={cfg:n,to:r.target,text:o,payload:l,accountId:r.accountId,threadId:r.threadId},d=e.renderPresentation?await e.renderPresentation({payload:l,presentation:i,ctx:a}):l,u=qh(d,s,r.channel);if(L("presentation_render_completed",{...we(r),adapterHasRenderPresentation:typeof e.renderPresentation=="function",adapterHasSendPayload:typeof e.sendPayload=="function",...zi(u)}),!u||typeof u!="object"||!e.sendPayload)throw new Error(`OpenClaw outbound adapter for channel "${r.channel}" cannot preserve interactive presentation`);let c=await e.sendPayload({...a,payload:u});L("presentation_send_payload_completed",{...we(r),...zi(u),...Bl(c)})}sendViaBoundedCliFallback(e,n,r,o){return new Promise((i,s)=>{let l=Lh(e,n,r);L("direct_send_cli_fallback_started",{...we(e),deliveryPath:"cli-fallback",reason:o,messageTextLength:n.length,...J(r)}),this.execFile("openclaw",l,{timeout:ru,killSignal:"SIGKILL"},(a,d,u)=>{if(!a){L("direct_send_cli_fallback_completed",{...we(e),deliveryPath:"cli-fallback",...J(r)}),i();return}let c=u?.trim()?` | stderr: ${u.trim()}`:"";L("direct_send_cli_fallback_failed",{...we(e),deliveryPath:"cli-fallback",...J(r),error:Ps(a),stderrLength:u?.length}),s(new Error(`${o}; bounded openclaw message send fallback failed within ${ru}ms timeout: ${Ps(a)}${c}`))})})}};function we(t){return{channel:t.channel,target:t.target,accountId:t.accountId,threadId:t.threadId,sessionKey:t.sessionKey}}function Lh(t,e,n){let r=yo(n),o=["message","send","--channel",t.channel,"--target",t.target,"--message",e];return t.accountId&&o.push("--account",t.accountId),t.threadId&&o.push("--thread-id",t.threadId),r&&o.push("--presentation",JSON.stringify(r)),o}function Ps(t){return t instanceof Error?t.message:String(t)}function ws(t){if(!t||typeof t!="object")return"unknown";let e=t.version;return typeof e=="string"&&e.trim()?e:"unknown"}function yo(t){let e=(t??[]).filter(n=>Array.isArray(n)&&n.length>0).map(n=>({type:"buttons",buttons:n.map(r=>({label:r.label,value:Hh(r.callbackData),...r.style?{style:r.style}:{}}))}));return e.length>0?{blocks:e}:void 0}function Fh(t){let e=t.blocks.filter(n=>n.type==="buttons"&&n.buttons.length>0).map(n=>({type:"buttons",buttons:n.buttons.map(r=>({label:r.label,value:r.value,...r.style?{style:r.style}:{}}))}));return e.length>0?{blocks:e}:void 0}function Bh(t){if(!t||typeof t!="object"||Array.isArray(t))return!1;let e=t.interactive;if(!e||typeof e!="object"||Array.isArray(e))return!1;let n=e.blocks;return Array.isArray(n)&&n.some(r=>{if(!r||typeof r!="object"||Array.isArray(r))return!1;let o=r;return o.type==="buttons"&&Array.isArray(o.buttons)&&o.buttons.length>0})}function qh(t,e,n){if(!e)return t;let r=Bh(t)?t:Uh(t,e);return n!=="telegram"?r:Kh(r,e)}function Uh(t,e){return!t||typeof t!="object"||Array.isArray(t)?t:{...t,interactive:e}}function Kh(t,e){if(!t||typeof t!="object"||Array.isArray(t))return t;let n=t,r=qt(n.channelData),o=qt(r?.telegram),i=Gh(o?.buttons);if(i)return{...n,channelData:{...r??{},telegram:{...o??{},buttons:i}}};let s=Vh(e);return s?{...n,channelData:{...r??{},telegram:{...o??{},buttons:s}}}:t}function Vh(t){let e=t.blocks.filter(n=>n.type==="buttons"&&n.buttons.length>0).map(n=>n.buttons.filter(r=>typeof r.value=="string"&&r.value.trim().length>0&&Buffer.byteLength(r.value,"utf8")<=su).map(r=>({text:r.label,callback_data:r.value,...au(r.style)}))).filter(n=>n.length>0);return e.length>0?e:void 0}function Gh(t){if(!Array.isArray(t))return;let e=t.map(n=>Array.isArray(n)?n.map(r=>{if(!r||typeof r!="object"||Array.isArray(r))return;let{style:o,...i}=r;if(!(typeof i.text!="string"||i.text.trim().length===0)&&!(i.callback_data!==void 0&&(typeof i.callback_data!="string"||i.callback_data.trim().length===0||Buffer.byteLength(i.callback_data,"utf8")>su))&&jh(i))return{...i,...au(o)}}).filter(r=>!!r):[]).filter(n=>n.length>0);return e.length>0?e:void 0}function jh(t){return ho(t.callback_data)||ho(t.url)||fo(t.web_app)||fo(t.webApp)||fo(t.login_url)||fo(t.loginUrl)||typeof t.switch_inline_query=="string"||typeof t.switch_inline_query_current_chat=="string"||qt(t.switch_inline_query_chosen_chat)!==void 0||qt(t.callback_game)!==void 0||t.pay===!0||ou(t.copy_text)||ou(t.copyText)}function ho(t){return typeof t=="string"&&t.trim().length>0}function fo(t){let e=qt(t);return ho(e?.url)}function ou(t){let e=qt(t);return ho(e?.text)}function au(t){if(typeof t!="string")return{};let e=t.trim().toLowerCase(),n=Wh[e];return n?{style:n}:{}}function qt(t){return t&&typeof t=="object"&&!Array.isArray(t)?t:void 0}function Hh(t){return t.startsWith(`${ke}:`)?t:`${ke}:${t}`}import*as lu from"child_process";var Ut=class{tails=new Map;enqueue(e,n,r){let o=this.tails.get(e);o!==void 0&&r?.();let s=(o?.catch(()=>{})??Promise.resolve()).then(()=>n()),l=s.catch(()=>{});return this.tails.set(e,l),l.finally(()=>{this.tails.get(e)===l&&this.tails.delete(e)}),s}clear(){this.tails.clear()}};var bs=3e4,zh=2e3,Qh=2e4,fe=4;function In(t){return t instanceof Error?t.message:String(t)}function Jh(){return new Error(`Dispatch timed out after ${bs}ms`)}function Yh(t){if(!(t instanceof Error))return!1;let e=t;return e.killed===!0&&e.signal==="SIGKILL"}var Zh={execFile:lu.execFile},ko=class{pendingRetryTimers=new Map;orderedDispatches=new Ut;disposed=!1;clearPendingRetries(){for(let e of this.pendingRetryTimers.values())for(let n of e)clearTimeout(n.timer),n.onCleared?.();this.pendingRetryTimers.clear()}clearRetryTimersForSession(e){let n=this.pendingRetryTimers.get(e);if(n){for(let r of n)clearTimeout(r.timer),r.onCleared?.();this.pendingRetryTimers.delete(e)}}dispose(){this.disposed=!0,this.clearPendingRetries(),this.orderedDispatches.clear()}execute(e,n,r=1){if(!this.disposed){if(r===1&&n.orderingKey){this.enqueueOrderedDispatch(n.orderingKey,o=>this.executeNow(e,n,o,r));return}this.executeNow(e,n,void 0,r)}}executePromise(e,n,r=1){if(!this.disposed){if(r===1&&n.orderingKey){this.enqueueOrderedDispatch(n.orderingKey,o=>this.executePromiseNow(e,n,o,r));return}this.executePromiseNow(e,n,void 0,r)}}executeNow(e,n,r,o=1){if(this.disposed||n.shouldContinue?.()===!1){r?.();return}let i=Date.now();o===1&&n.onStarted?.(),this.log("info","dispatch_started",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe}),Zh.execFile("openclaw",e,{timeout:bs,killSignal:"SIGKILL"},(s,l,a)=>{if(this.disposed){r?.();return}let d=Date.now()-i;if(!s){let f=n.successValidator?.(l??"");if(f?.outcome==="failure"){this.log("error","dispatch_success_validation_failed",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:d,error:f.reason,terminal:!0}),n.onFinalFailure?.(),r?.();return}if(f?.outcome==="skipped"){this.log("info","dispatch_skipped",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:d,reason:f.reason}),n.shouldContinue?.()!==!1&&n.onSkipped?.(f.reason),r?.();return}this.log("info","dispatch_succeeded",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:d}),n.shouldContinue?.()!==!1&&n.onSuccess?.(),r?.();return}let u=a?.trim()?` | stderr: ${a.trim()}`:"";if(n.shouldContinue?.()===!1){r?.();return}if(n.target==="message.send"&&Yh(s)){this.log("error","dispatch_failed",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:d,error:`${In(s)}${u}`,terminal:!0,ambiguousResult:!0}),n.onAmbiguousResult?.(),r?.();return}if(o>=fe||n.terminalOnFailure===!0){this.log("error","dispatch_failed",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:d,error:`${In(s)}${u}`,terminal:!0}),n.onFinalFailure?.(),r?.();return}let m=this.retryDelayMs(o);this.log("error","dispatch_retry_scheduled",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:d,retryDelayMs:m,error:`${In(s)}${u}`});let p={timer:setTimeout(()=>{let f=this.pendingRetryTimers.get(n.sessionId);if(f&&(f.delete(p),f.size===0&&this.pendingRetryTimers.delete(n.sessionId)),n.shouldContinue?.()===!1){r?.();return}this.executeNow(e,n,r,o+1)},m),onCleared:r};p.timer.unref?.(),this.pendingRetryTimers.has(n.sessionId)||this.pendingRetryTimers.set(n.sessionId,new Set),this.pendingRetryTimers.get(n.sessionId).add(p)})}executePromiseNow(e,n,r,o=1){if(this.disposed||n.shouldContinue?.()===!1){r?.();return}let i=Date.now();o===1&&n.onStarted?.(),this.log("info","dispatch_started",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe}),this.executePromiseWithTimeout(e).then(()=>{if(this.disposed){r?.();return}let s=Date.now()-i;this.log("info","dispatch_succeeded",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:s}),n.shouldContinue?.()!==!1&&n.onSuccess?.(),r?.()}).catch(s=>{if(this.disposed){r?.();return}let l=Date.now()-i;if(n.shouldContinue?.()===!1){r?.();return}if(o>=fe||n.terminalOnFailure===!0){this.log("error","dispatch_failed",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:l,error:In(s),terminal:!0,...n.terminalOnFailure===!0&&o<fe?{terminalReason:"non_retryable"}:{}}),n.onFinalFailure?.(),r?.();return}let a=this.retryDelayMs(o);this.log("error","dispatch_retry_scheduled",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:fe,elapsedMs:l,retryDelayMs:a,error:In(s)});let d={timer:setTimeout(()=>{let u=this.pendingRetryTimers.get(n.sessionId);if(u&&(u.delete(d),u.size===0&&this.pendingRetryTimers.delete(n.sessionId)),n.shouldContinue?.()===!1){r?.();return}this.executePromiseNow(e,n,r,o+1)},a),onCleared:r};d.timer.unref?.(),this.pendingRetryTimers.has(n.sessionId)||this.pendingRetryTimers.set(n.sessionId,new Set),this.pendingRetryTimers.get(n.sessionId).add(d)})}executePromiseWithTimeout(e){return new Promise((n,r)=>{let o=!1,i=setTimeout(()=>{o||(o=!0,r(Jh()))},bs);i.unref?.(),Promise.resolve().then(e).then(()=>{o||(o=!0,clearTimeout(i),n())}).catch(s=>{o||(o=!0,clearTimeout(i),r(s))})})}retryDelayMs(e){let n=Math.max(0,e-1),r=zh*2**n;return Math.min(r,Qh)}enqueueOrderedDispatch(e,n){this.orderedDispatches.enqueue(e,async()=>{this.disposed||await new Promise(r=>{let o=!1;n(()=>{o||(o=!0,r())})})})}log(e,n,r){let o=`[WakeDispatcher] ${JSON.stringify({event:n,...r})}`;if(e==="error"){console.error(o);return}}};be();var So=class{resolve(e){let n=_e(e);if(!(!n?.provider||!n.target))return{channel:n.provider,target:n.target,accountId:n.accountId,threadId:n.threadId,sessionKey:n.sessionKey}}summary(e){if(!e)return"system";let n=e.accountId?`|${e.accountId}`:"",r=e.threadId?`#${e.threadId}`:"";return`${e.channel}${n}|${e.target}${r}`}};import{randomUUID as Xh}from"crypto";var vo=class{constructor(e={}){}buildChatSendArgs(e,n,r,o=Xh()){return["gateway","call","chat.send","--expect-final","--timeout","30000","--params",JSON.stringify({sessionKey:e,message:n,deliver:r,idempotencyKey:o})]}buildDirectNotificationArgs(e,n,r){let o=yo(r),i=["message","send","--channel",e.channel,"--target",e.target,"--message",n];return e.accountId&&i.push("--account",e.accountId),e.threadId&&i.push("--thread-id",e.threadId),o&&i.push("--presentation",JSON.stringify(o)),i}buildSystemEventArgs(e){return["system","event","--text",e,"--mode","now"]}};function ey(t){let e=ty(t).trim();return e?/^NO_REPLY$/i.test(e)?{outcome:"failure",reason:"completion follow-up wake ended with NO_REPLY"}:{outcome:"success"}:{outcome:"failure",reason:"completion follow-up wake produced no final response"}}function ty(t){let e=t.trim();if(!e)return"";try{return Rs(JSON.parse(e)).trim()}catch{return e}}function Rs(t){if(typeof t=="string")return t;if(Array.isArray(t))return t.map(r=>Rs(r)).filter(Boolean).join(`
246
- `);if(!t||typeof t!="object")return"";let e=t,n=["final","finalResponse","final_response","assistantFinal","assistant_final","response","text","content"];for(let r of n){let o=e[r];if(typeof o=="string"&&o.trim())return o}for(let r of["result","message","data"]){let o=Rs(e[r]);if(o.trim())return o}return""}var Po=class{routes=new So;transport;directNotifications;executor=new ko;constructor(e={}){this.transport=e.transport??new vo(e.transportOptions),this.directNotifications=e.directNotifications===void 0?new go:e.directNotifications}clearPendingRetries(){this.executor.clearPendingRetries()}clearRetryTimersForSession(e){this.executor.clearRetryTimersForSession(e)}dispose(){this.executor.dispose()}buildDispatchContext(e){let n=e.buttons??[],r=n.flat();return{transportRoute:e.routeSummary,transportChannel:e.route?.channel??"system",transportTarget:e.route?.target??"system",transportAccountId:e.route?.accountId,transportThreadId:e.route?.threadId,transportSessionKey:e.route?.sessionKey,messageTextLength:e.text.length,buttonsPresent:r.length>0,buttonRows:n.length||void 0,buttonCount:r.length||void 0,buttonLabels:r.length>0?r.map(o=>o.label):void 0,maxCallbackDataLength:r.length>0?Math.max(...r.map(o=>o.callbackData.length)):void 0}}sendWake(e,n,r,o,i,s,l,a,d,u){let c=this.routes.resolve(e),m=l;if(m?.()===!1)return;let p=c?.sessionKey?.trim();if(!p){this.executor.execute(this.transport.buildSystemEventArgs(n),{label:`${r}-system`,sessionId:e.id,target:"system.event",phase:o,routeSummary:"system",messageKind:"wake",dispatchContext:this.buildDispatchContext({routeSummary:"system",text:n}),onSuccess:s,onSkipped:d,onFinalFailure:i,successValidator:a,shouldContinue:m});return}this.executor.execute(this.transport.buildChatSendArgs(p,n,!0,u),{label:r,sessionId:e.id,target:"chat.send",phase:o,routeSummary:`session:${p}`,messageKind:"wake",dispatchContext:this.buildDispatchContext({routeSummary:`session:${p}`,route:c,text:n}),onSuccess:s,onSkipped:d,successValidator:a,shouldContinue:m,onFinalFailure:()=>{m?.()!==!1&&this.executor.execute(this.transport.buildSystemEventArgs(n),{label:`${r}-fallback`,sessionId:e.id,target:"system.event",phase:o,routeSummary:"system",messageKind:"wake",dispatchContext:this.buildDispatchContext({routeSummary:"system",text:n}),onSuccess:s,onSkipped:d,onFinalFailure:i,successValidator:a,shouldContinue:m})}})}sendUserNotification(e,n,r,o,i,s,l=!1,a){if(a?.()===!1)return;let d=!!o?.some(f=>Array.isArray(f)&&f.length>0),u=this.routes.resolve(e);L("wake_notify_selected",{sessionId:e.id,sessionName:e.name,label:r,messageTextLength:n.length,requireDirectDelivery:l,hasDirectNotificationTransport:!!this.directNotifications,routeSummary:u?this.routes.summary(u):"system",channel:u?.channel,target:u?.target,accountId:u?.accountId,threadId:u?.threadId,sessionKey:u?.sessionKey,...J(o)});let c=u?`notify:${u.channel}|${u.accountId??""}|${u.target}|${u.threadId??""}`:`notify:system:${e.id}`;if(!u){if(L("wake_notify_no_direct_route",{sessionId:e.id,sessionName:e.name,label:r,requireDirectDelivery:l,hasInteractiveButtons:d,...J(o)}),l){`${r}${e.id}`,i?.();return}if(d){`${r}${e.id}`,i?.();return}this.executor.execute(this.transport.buildSystemEventArgs(n),{label:`${r}-notify-system`,sessionId:e.id,target:"system.event",phase:"notify",routeSummary:"system",messageKind:"notify",dispatchContext:this.buildDispatchContext({routeSummary:"system",text:n,buttons:o}),orderingKey:c,onSuccess:s,onFinalFailure:i,shouldContinue:a});return}let m=()=>{if(L("wake_notify_direct_failed",{sessionId:e.id,sessionName:e.name,label:r,requireDirectDelivery:l,hasInteractiveButtons:d,channel:u.channel,target:u.target,accountId:u.accountId,threadId:u.threadId,sessionKey:u.sessionKey,...J(o)}),l){`${r}${e.id}`,i?.();return}if(d){`${r}${e.id}`,i?.();return}this.executor.execute(this.transport.buildSystemEventArgs(n),{label:`${r}-notify-fallback`,sessionId:e.id,target:"system.event",phase:"notify",routeSummary:"system",messageKind:"notify",dispatchContext:this.buildDispatchContext({routeSummary:"system",text:n}),orderingKey:c,onSuccess:s,onFinalFailure:i,shouldContinue:a})},p={label:`${r}-notify`,sessionId:e.id,target:"message.send",phase:"notify",routeSummary:this.routes.summary(u),messageKind:"notify",dispatchContext:this.buildDispatchContext({routeSummary:this.routes.summary(u),route:u,text:n,buttons:o}),orderingKey:c,onSuccess:s,onAmbiguousResult:m,onFinalFailure:m,terminalOnFailure:this.directNotifications?!0:void 0,shouldContinue:a};if(this.directNotifications){L("wake_notify_dispatching_direct_runtime",{sessionId:e.id,sessionName:e.name,label:r,channel:u.channel,target:u.target,accountId:u.accountId,threadId:u.threadId,sessionKey:u.sessionKey,...J(o)}),this.executor.executePromise(()=>this.directNotifications.send(u,n,o),p);return}L("wake_notify_dispatching_cli_message_send",{sessionId:e.id,sessionName:e.name,label:r,channel:u.channel,target:u.target,accountId:u.accountId,threadId:u.threadId,sessionKey:u.sessionKey,...J(o)}),this.executor.execute(this.transport.buildDirectNotificationArgs(u,n,o),p)}sendUserNotificationSequence(e,n,r,o,i,s=!1,l){let a=n.map(u=>({text:u.text.trim(),buttons:u.buttons})).filter(u=>u.text.length>0);if(a.length===0){o?.();return}L("wake_notify_sequence_started",{sessionId:e.id,sessionName:e.name,label:r,chunkCount:a.length,buttonChunkIndexes:a.map((u,c)=>u.buttons?.some(m=>Array.isArray(m)&&m.length>0)?c+1:void 0).filter(u=>typeof u=="number"),requireDirectDelivery:s});let d=u=>{if(l?.()===!1)return;let c=a[u];if(!c){L("wake_notify_sequence_succeeded",{sessionId:e.id,sessionName:e.name,label:r,chunkCount:a.length}),i?.();return}let m=u===0?o:i;L("wake_notify_sequence_chunk_selected",{sessionId:e.id,sessionName:e.name,label:r,chunkIndex:u+1,chunkCount:a.length,messageTextLength:c.text.length,failureHandler:u===0?"all-failed":"sequence-success",...J(c.buttons)}),this.sendUserNotification(e,c.text,`${r}-part-${u+1}`,c.buttons,m,()=>d(u+1),s,l)};d(0)}dispatchSessionNotification(e,n){let r=n.hooks,o=n.wakeMessageOnNotifySuccess!=null||n.wakeMessageOnNotifyFailed!=null,i=n.notifyUser??(n.wakeMessage?"on-wake-fallback":"always"),s=(n.userMessages?.length?n.userMessages:n.userMessage?.trim()?[{text:n.userMessage.trim(),buttons:n.buttons}]:[]).map(u=>({text:u.text.trim(),buttons:u.buttons})).filter(u=>u.text.length>0),l=n.wakeMessage?.trim(),a=n.shouldDispatch,d=n.completionWakeSummaryRequired===!0?ey:void 0;if(o){let u=n.wakeMessageOnNotifySuccess?.trim(),c=n.wakeMessageOnNotifyFailed?.trim(),m=k=>{k&&a?.()!==!1&&(r?.onWakeStarted?.(),this.sendWake(e,k,`${n.label}-wake`,"wake",r?.onWakeFailed,r?.onWakeSucceeded,a,d,r?.onWakeSkipped,n.idempotencyKey))},p=k=>{if(k){if(n.deferConditionalWakeUntilNextTick===!0||n.deferConditionalWakeMs!==void 0){let v=Math.max(0,Math.floor(n.deferConditionalWakeMs??0));setTimeout(()=>m(k),v).unref?.();return}m(k)}},f=()=>{a?.()!==!1&&(r?.onNotifySucceeded?.(),u&&p(u))},h=c?()=>{a?.()!==!1&&(r?.onNotifyFailed?.(),n.onUserNotifyFailed?.(),p(c))}:()=>{a?.()!==!1&&(r?.onNotifyFailed?.(),n.onUserNotifyFailed?.())};if(s.length>0){if(a?.()===!1)return;r?.onNotifyStarted?.(),this.sendUserNotificationSequence(e,s,n.label,h,f,n.requireDirectUserNotification===!0,a)}else h();return}if(i==="always"&&s.length>0){if(a?.()===!1)return;r?.onNotifyStarted?.(),this.sendUserNotificationSequence(e,s,n.label,()=>{a?.()!==!1&&(r?.onNotifyFailed?.(),n.onUserNotifyFailed?.())},()=>{a?.()!==!1&&r?.onNotifySucceeded?.()},n.requireDirectUserNotification===!0,a)}if(l&&a?.()!==!1){if(r?.onWakeStarted?.(),i==="on-wake-fallback"&&s.length>0&&!this.routes.resolve(e)?.sessionKey){if(a?.()===!1)return;r?.onNotifyStarted?.(),this.sendUserNotificationSequence(e,s,n.label,()=>{a?.()!==!1&&(r?.onNotifyFailed?.(),n.onUserNotifyFailed?.())},()=>{a?.()!==!1&&r?.onNotifySucceeded?.()},!1,a)}this.sendWake(e,l,`${n.label}-wake`,"wake",r?.onWakeFailed,r?.onWakeSucceeded,a,d,r?.onWakeSkipped,n.idempotencyKey)}}};var du=36,uu=2,cu="...";function ny(t){let e=Array.from(t);return e.length<=du?t:`${e.slice(0,du-cu.length).join("")}${cu}`}var wo=class{constructor(e,n){this.actionTokens=e;this.isGitHubCliAvailable=n}actionTokens;isGitHubCliAvailable;createActionToken(e,n,r={}){return this.actionTokens.createActionToken(e,n,{expiresAt:Date.now()+10080*60*1e3,...r})}consumeActionToken(e){return this.actionTokens.consumeActionToken(e)}getActionToken(e){return this.actionTokens.getActionToken(e)}listActiveActionTokens(e){return this.actionTokens.listActiveActionTokens(e)}clearRepoPolicyChoiceTokens(e){this.actionTokens.deleteActionTokensForSessionByKind(e,"repo-policy-set")}clearPlanDecisionTokens(e,n){this.actionTokens.deletePlanDecisionTokensForSession(e,n)}makeActionButton(e,n,r,o={}){let i=this.createActionToken(e,n,{label:r,...o});return{label:r,callbackData:i.id,style:this.resolveButtonStyle(n)}}resolveButtonStyle(e){switch(e){case"plan-approve":case"worktree-create-pr":case"worktree-update-pr":case"plan-offer-start":case"repo-policy-set":return"primary";case"worktree-merge":case"session-resume":case"session-restart":return"success";case"plan-reject":case"worktree-dismiss":return"danger";default:return"secondary"}}getWorktreeDecisionButtons(e,n,r={merge:!0,pr:!0}){if(!n)return[];let o=[],i=[];if(r.merge&&i.push(this.makeActionButton(e,"worktree-merge","Merge")),r.pr&&this.isGitHubCliAvailable())n.worktreePrUrl?(i.push(this.makeActionButton(e,"worktree-view-pr","View PR",{targetUrl:n.worktreePrUrl})),i.length>0&&o.push(i),o.push([this.makeActionButton(e,"worktree-update-pr","Sync PR"),this.makeActionButton(e,"worktree-decide-later","Later")])):(i.push(this.makeActionButton(e,"worktree-create-pr","Open PR")),i.length>0&&o.push(i),o.push([this.makeActionButton(e,"worktree-decide-later","Later"),this.makeActionButton(e,"worktree-dismiss","Discard")]));else return o.push([...i,this.makeActionButton(e,"worktree-decide-later","Later")]),o.push([this.makeActionButton(e,"worktree-dismiss","Discard")]),o;return n.worktreePrUrl&&o.push([this.makeActionButton(e,"worktree-dismiss","Discard")]),o}getPlanApprovalButtons(e,n){let r=n?.actionablePlanDecisionVersion??n?.planDecisionVersion;this.clearPlanDecisionTokens(e,r);let o=[[this.makeActionButton(e,"plan-approve","Approve",{planDecisionVersion:r}),this.makeActionButton(e,"plan-request-changes","Revise",{planDecisionVersion:r}),this.makeActionButton(e,"plan-reject","Reject",{planDecisionVersion:r})]];return L("plan_approval_buttons_created",{sessionId:e,planDecisionVersion:r,...J(o)}),o}getResumeButtons(e,n){let r=[];return n.isExplicitlyResumable&&r.push(this.makeActionButton(e,"session-resume","Resume")),r.push(this.makeActionButton(e,"view-output","View output")),[r]}getQuestionButtons(e,n,r={}){if(n.length===0)return;let o=n.map((s,l)=>{let a=this.createActionToken(e,"question-answer",{label:s.label,optionIndex:l,pendingInputRequestId:r.requestId,pendingInputQuestionId:r.questionId});return{label:ny(s.label),callbackData:a.id,style:this.resolveButtonStyle("question-answer")}}),i=[];for(let s=0;s<o.length;s+=uu)i.push(o.slice(s,s+uu));return i}getPlanOfferButtons(e){let{offerId:n,route:r,planName:o,planPrompt:i,planWorkdir:s,planWorktreeStrategy:l}=e,a=[[this.makeActionButton(n,"plan-offer-start","Start Plan",{route:r,launchName:o,launchPrompt:i,launchWorkdir:s,launchWorktreeStrategy:l}),this.makeActionButton(n,"plan-offer-dismiss","Dismiss",{route:r})]];return L("plan_offer_buttons_created",{offerId:n,planName:o,channel:r.provider,target:r.target,accountId:r.accountId,threadId:r.threadId,sessionKey:r.sessionKey,planPromptLength:i.length,planWorkdirLength:s.length,planWorktreeStrategy:l,...J(a)}),a}getRepoPolicyChoiceButtons(e){let n=gn(e.prAvailable??!0),r=Array.from({length:Math.ceil(n.length/2)},(o,i)=>n.slice(i*2,i*2+2)).map(o=>o.map(i=>this.makeActionButton(e.choiceId,"repo-policy-set",i.label,{route:e.route,repoPolicy:i.policy,repoPolicyWorkdir:e.repoRoot,launchName:e.launchName,launchPrompt:e.launchPrompt,launchWorkdir:e.launchWorkdir,launchModel:e.launchModel,launchReasoningEffort:e.launchReasoningEffort,launchFastMode:e.launchFastMode,launchSystemPrompt:e.launchSystemPrompt,launchAllowedTools:e.launchAllowedTools,launchResumeSessionId:e.launchResumeSessionId,launchResumeWorktreeFrom:e.launchResumeWorktreeFrom,launchSessionIdOverride:e.launchSessionIdOverride,launchClearedPersistedCodexResume:e.launchClearedPersistedCodexResume,launchForkSession:e.launchForkSession,launchForceNewSession:e.launchForceNewSession,launchPermissionMode:e.launchPermissionMode,launchPlanApproval:e.launchPlanApproval,launchHarness:e.launchHarness,launchWorktreeStrategy:e.launchWorktreeStrategy,launchWorktreeBaseBranch:e.launchWorktreeBaseBranch,launchWorktreePrTargetRepo:e.launchWorktreePrTargetRepo,launchOriginAgentId:e.launchOriginAgentId})));return L("repo_policy_choice_buttons_created",{choiceId:e.choiceId,repoRoot:e.repoRoot,channel:e.route.provider,target:e.route.target,accountId:e.route.accountId,threadId:e.route.threadId,sessionKey:e.route.sessionKey,labels:n.map(o=>o.label),...J(r)}),r}};Z();be();import{createHash as sy}from"crypto";var ry="duplicate notification already delivered or in flight",bo=class{maxRecords;inFlightTtlMs;now;inFlight=new Set;delivered=new Set;constructor(e={}){this.maxRecords=Math.max(1,Math.floor(e.maxRecords??64)),this.inFlightTtlMs=Math.max(1,Math.floor(e.inFlightTtlMs??6e5)),this.now=e.now??(()=>new Date)}claim(e,n,r){if(!e)return{allowed:!0};let o=this.now(),i=this.prune(n??[],o),s=i.find(l=>l.key===e);return this.delivered.has(e)||this.inFlight.has(e)||s?.status==="delivered"||s?.status==="in_flight"&&this.isFreshInFlight(s,o)?{allowed:!1,records:i,reason:ry}:(this.inFlight.add(e),this.delivered.delete(e),{allowed:!0,records:this.upsert(i,{key:e,status:"in_flight",recordedAt:o.toISOString(),label:r})})}deliveredRecords(e,n,r){if(!e)return;let o=this.now();return this.inFlight.delete(e),this.delivered.add(e),this.upsert(this.prune(n??[],o),{key:e,status:"delivered",recordedAt:o.toISOString(),label:r})}releasedRecords(e,n){if(!e)return;let r=this.now();return this.inFlight.delete(e),this.prune(n??[],r).filter(o=>!(o.key===e&&o.status==="in_flight"))}prune(e,n){let r=e.filter(o=>o.status==="delivered"?!0:this.isFreshInFlight(o,n));return r.slice(Math.max(0,r.length-this.maxRecords))}isFreshInFlight(e,n){let r=Date.parse(e.recordedAt);return Number.isFinite(r)?n.getTime()-r<this.inFlightTtlMs:!1}upsert(e,n){let o=[...e.filter(i=>i.key!==n.key),n];return o.slice(Math.max(0,o.length-this.maxRecords))}};be();Z();be();import{createHash as oy}from"crypto";var iy=1024,xn="duplicate completion follow-up wake already handled",Ro="prior human-visible summary already delivered",Ao=class{inFlight=new Set;completed=new Map;claimKeysByPrimary=new Map;maxCompletedKeys;constructor(e={}){this.maxCompletedKeys=Math.max(1,Math.floor(e.maxCompletedKeys??iy))}decide(e,n,r){if(n?.required!==!0)return{required:!1,allowed:!1,explicit:!1};let o=this.buildKeySet(e,n);if(!o)return{required:!0,allowed:!0,explicit:!1};let i=this.normalizeRecords(r),s=new Map(i.map(u=>[u.key,u])),l=o.decisionKeys.find(u=>this.inFlight.has(u)||this.completed.has(u)||s.has(u)),a=l?this.completed.get(l):void 0,d=l?s.get(l):void 0;return l?{required:!0,allowed:!1,explicit:o.explicit,dedupeKey:o.primary,skipReason:a?.skipReason??d?.skipReason??xn}:(this.registerClaim(o.primary,o.claimKeys),{required:!0,allowed:!0,key:o.primary,explicit:o.explicit})}recordVisibleDelivery(e,n,r,o){if(n.required!==!0)return{required:!1,allowed:!1,explicit:!1};let i=this.buildKeySet(e,n);if(!i)return{required:!0,allowed:!0,explicit:!1};let s=this.normalizeRecords(r),l=new Map(s.map(m=>[m.key,m])),a=i.decisionKeys.find(m=>this.completed.has(m)||l.has(m)),d=a?this.completed.get(a):void 0,u=a?l.get(a):void 0;if(d||u)return{required:!0,allowed:!1,explicit:i.explicit,dedupeKey:i.primary,skipReason:d?.skipReason??u?.skipReason};this.finishKeys(i.primary,i.claimKeys,!0,Ro);let c=this.deliveredRecords(i.claimKeys,s,o,Ro);return{required:!0,allowed:!0,key:i.primary,explicit:i.explicit,records:c}}finish(e,n,r=xn){if(!e)return;let o=this.claimKeysByPrimary.get(e)??[e];this.finishKeys(e,o,n,r)}completionRecordsAfterDelivery(e,n,r,o=xn){if(!e)return;let i=this.claimKeysByPrimary.get(e)??[e];return this.deliveredRecords(i,n,r,o)}registerClaim(e,n){for(let r of n)this.inFlight.add(r);for(this.claimKeysByPrimary.delete(e),this.claimKeysByPrimary.set(e,n);this.claimKeysByPrimary.size>this.maxCompletedKeys;){let r=this.claimKeysByPrimary.keys().next().value;if(r===void 0)break;let o=this.claimKeysByPrimary.get(r)??[r];for(let i of o)this.inFlight.delete(i);this.claimKeysByPrimary.delete(r)}}finishKeys(e,n,r,o=xn){for(let i of n)this.inFlight.delete(i);if(this.claimKeysByPrimary.delete(e),!!r){for(let i of n)this.completed.get(i)?.skipReason===Ro&&o!==Ro||(this.completed.delete(i),this.completed.set(i,{skipReason:o}));for(;this.completed.size>this.maxCompletedKeys;){let i=this.completed.keys().next().value;if(i===void 0)break;this.completed.delete(i)}}}buildKeySet(e,n){let r=this.getDeliveryRef(e);if(!r)return;let o=this.normalizeOutcomeKey(e,n.outcomeKey?.trim());if(o){let l=`${this.buildVisibleScope(r,e)}:outcome:${this.digest(o)}`,a=this.isGoalLike(e,n,o),d=this.buildSessionAliasKeys(r,e,"visible-summary"),u=this.buildSessionAliasKeys(r,e,"goal-summary"),c=this.isTerminalLike(n,o);return{primary:l,explicit:!0,claimKeys:[l,...d,...a?u:[]],decisionKeys:[l,...a||c?d:[],...u]}}let i=n.fallbackFingerprint?.trim();if(!i)return;let s=`${r}:${n.producer}:${this.digest(i)}`;return{primary:s,explicit:!1,claimKeys:[s],decisionKeys:[s]}}isGoalLike(e,n,r){return!!e.goalTaskId?.trim()||n.producer==="goal"||/^goal:/i.test(r)}isTerminalLike(e,n){return e.producer==="terminal"||/^terminal:/i.test(n)}normalizeOutcomeKey(e,n){let r=e.goalTaskId?.trim();if(r)return`goal:${r}`;let o=this.normalizeWorktreePrOutcomeKey(n);return o||n}normalizeWorktreePrOutcomeKey(e){if(!e)return;let n=e.split(":");if(n[0]!=="worktree-pr"||n.length<5)return;let r=n[1]?.trim().toLowerCase();if(!r||!/^(?:draft-)?(?:opened|updated)$/.test(r))return;let o=n[2]?.trim()||"default-repo",i=n[3]?.trim();if(!i)return;let s=this.normalizePrIdentity(i),l=n[4]?.trim();if(!(!s||!l))return["worktree-pr",o.toLowerCase(),s,l].join(":")}normalizePrIdentity(e){let n=e.match(/#?(\d+)$/);if(n?.[1])return`#${n[1]}`;let r=e.match(/\/pull\/(\d+)(?:\b|\/|$)/);if(r?.[1])return`#${r[1]}`;let o=e.trim();return o||void 0}buildVisibleScope(e,n){let r=_e(n);return r?`route:${this.digest(JSON.stringify({provider:r.provider,accountId:r.accountId,target:r.target,threadId:r.threadId}))}`:e}buildSessionAliasKeys(e,n,r){let o=this.buildVisibleScope(e,n),i=["id"in n?n.id:void 0,"sessionId"in n?n.sessionId:void 0,n.name,$(n),n.harnessSessionId,e].map(s=>s?.trim()).filter(s=>!!s);return[...new Set(i)].map(s=>`${o}:session:${this.digest(s)}:${r}`)}getDeliveryRef(e){return U(e)??$(e)??""}digest(e){return oy("sha256").update(e).digest("hex").slice(0,16)}normalizeRecords(e){return e?.length?e.filter(n=>n.key.trim()&&Number.isFinite(Date.parse(n.recordedAt))).slice(-this.maxCompletedKeys):[]}deliveredRecords(e,n,r,o=xn){let i=new Date().toISOString(),a=[...this.normalizeRecords(n).filter(d=>!e.includes(d.key)),...e.map(d=>({key:d,recordedAt:i,label:r,skipReason:o}))];return a.slice(Math.max(0,a.length-this.maxCompletedKeys))}};var ay=2e3,ly=new Set(["1","true","yes","on"]);function dy(){let t=process.env.OPENCLAW_CODE_AGENT_NOTIFICATION_DIAGNOSTICS?.trim().toLowerCase();return!!(t&&ly.has(t))||ji()}function uy(t){dy()&&process.stderr.write(`[SessionNotification] ${JSON.stringify(t)}
247
- `)}var Io=class{constructor(e,n,r={}){this.wakeDispatcher=e;this.applyPersistedPatch=n;this.completionSummaries=new Ao({maxCompletedKeys:r.maxCompletedCompletionWakeKeys}),this.notificationDedupe=new bo({maxRecords:r.maxNotificationDedupeRecords}),this.getPersistedSession=r.getPersistedSession}wakeDispatcher;applyPersistedPatch;completionSummaries;notificationDedupe;getPersistedSession;dispatch(e,n){let r=this.getDeliveryRef(e),o=this.getPersistedSession?.(r),i=this.buildNotificationDedupeKey(e,n),s=this.notificationDedupe.claim(i,o?.notificationDedupe,n.label);if(s.records&&this.applyNotificationDedupePatch(r,s.records),!s.allowed){this.logNotificationDecision({session:e,request:n,deliveryRef:r,dedupeKey:i,decision:"skip",reason:s.reason??"duplicate notification skipped",deliveryPath:"notify"}),n.hooks?.onDuplicateSkipped?.(s.reason??"duplicate notification skipped");return}let l=this.buildCompletionSummaryFact(n),a=n.completionSummaryOwner==="foreground"&&l?.required===!0,d=a?this.completionSummaries.recordVisibleDelivery(e,l,o?.completionSummaryDedupe,n.label):this.completionSummaries.decide(e,l,o?.completionSummaryDedupe);d.records&&this.applyCompletionSummaryDedupePatch(r,d.records);let u=a?this.withoutCompletionWake(n):n;if(d.required&&!d.allowed)if(this.logNotificationDecision({session:e,request:n,deliveryRef:r,dedupeKey:d.dedupeKey??d.key,outcomeKey:l?.outcomeKey,decision:a?"skip":d.explicit?"send_without_followup":"skip",reason:d.skipReason??"completion follow-up wake suppressed",deliveryPath:a?"foreground-summary":"wake",followupKind:l?.producer}),n.hooks?.onWakeSkipped?.(d.skipReason??"completion follow-up wake suppressed"),a){this.releaseNotificationDedupe(r,i);return}else if(d.explicit)u=this.withoutCompletionWake(n);else{this.releaseNotificationDedupe(r,i);return}l?.required===!0&&this.logNotificationDecision({session:e,request:u,deliveryRef:r,dedupeKey:d.dedupeKey??d.key,outcomeKey:l.outcomeKey,decision:a?"record_visible":u.completionWakeSummaryRequired===!0?"send_with_followup":"send_without_followup",reason:a?"foreground summary owns completion follow-up":void 0,deliveryPath:a?"foreground-summary":"wake",followupKind:l.producer});let c=this.buildCompletionWakePatch(u),m=!!(u.wakeMessage?.trim()||u.wakeMessageOnNotifySuccess?.trim()),p=!!(u.wakeMessage?.trim()||u.wakeMessageOnNotifyFailed?.trim()),f=!1,h=!1,k=()=>{h||(h=!0,f||(this.releaseNotificationDedupe(r,i),f=!0),this.completionSummaries.finish(d.key,!1))},v=u.shouldDispatch?()=>{let x=u.shouldDispatch?.()!==!1;return x||k(),x}:void 0,I={onNotifyStarted:()=>{this.applyDeliveryState(r,"notifying"),u.hooks?.onNotifyStarted?.()},onNotifySucceeded:()=>{f=!0,this.markNotificationDedupeDelivered(r,i,u.label),this.applyNotifyDeliveryState(r,m?"wake_pending":"idle",m?c:void 0),m||this.completionSummaries.finish(d.key,!1),u.hooks?.onNotifySucceeded?.()},onNotifyFailed:()=>{this.applyNotifyDeliveryState(r,p?"wake_pending":"failed",p?c:void 0),p||(this.completionSummaries.finish(d.key,!1),this.releaseNotificationDedupe(r,i),f=!0),u.hooks?.onNotifyFailed?.()},onWakeStarted:()=>{this.applyPersistedPatchWithCompletionWake(r,"wake_pending",c,{completionWakeIssuedAt:new Date().toISOString(),completionWakeSucceededAt:void 0,completionWakeFailedAt:void 0,completionWakeSkippedAt:void 0,completionWakeSkipReason:void 0}),u.hooks?.onWakeStarted?.()},onWakeSucceeded:()=>{f=!0,this.markNotificationDedupeDelivered(r,i,u.label),this.markCompletionSummaryDelivered(r,d.key,u.label),this.applyPersistedPatchWithCompletionWake(r,"idle",this.buildCompletionWakeSucceededPatch(c),{completionWakeSucceededAt:new Date().toISOString(),completionWakeFailedAt:void 0,completionWakeSkippedAt:void 0,completionWakeSkipReason:void 0}),this.completionSummaries.finish(d.key,!0),u.hooks?.onWakeSucceeded?.()},onWakeSkipped:x=>{if(h){u.hooks?.onWakeSkipped?.(x);return}f=!0,this.markNotificationDedupeDelivered(r,i,u.label),this.markCompletionSummaryDelivered(r,d.key,u.label,x),this.applyPersistedPatchWithCompletionWake(r,"idle",this.buildCompletionWakeSucceededPatch(c),{completionWakeSucceededAt:void 0,completionWakeFailedAt:void 0,completionWakeSkippedAt:new Date().toISOString(),completionWakeSkipReason:x}),this.completionSummaries.finish(d.key,!0),u.hooks?.onWakeSkipped?.(x)},onWakeFailed:()=>{this.applyPersistedPatchWithCompletionWake(r,"failed",c,{completionWakeFailedAt:new Date().toISOString()}),this.completionSummaries.finish(d.key,!1),this.releaseNotificationDedupe(r,i),f=!0,u.hooks?.onWakeFailed?.()}};this.wakeDispatcher.dispatchSessionNotification(e,{...u,idempotencyKey:i??u.idempotencyKey,shouldDispatch:v,hooks:I})}notifyWorktreeOutcome(e,n,r={}){let o=this.getDeliveryRef(e),i=d=>Ft({sessionId:o,sessionName:e.name,outcomeLine:n,originThreadLine:Qt(e),detailLines:r.detailLines,canonicalStatusDelivered:d}),s=r.summaryWakeRequired??!0,l={required:s,producer:"worktree-pr",outcomeKey:r.completionWakeOutcomeKey??`terminal:${o}`},a=r.completionSummaryOwner!=="foreground";if(s&&!a){let d=this.getDeliveryRef(e),u=this.completionSummaries.recordVisibleDelivery(e,l,d?this.getPersistedSession?.(d)?.completionSummaryDedupe:void 0,"worktree-outcome");u.records&&this.applyCompletionSummaryDedupePatch(d,u.records)}this.dispatch(e,{label:"worktree-outcome",userMessage:n,notifyUser:"always",requireDirectUserNotification:!0,completionSummary:{...l,required:s&&a},completionWakeSummaryRequired:s&&a,completionWakeOutcomeKey:r.completionWakeOutcomeKey??`terminal:${o}`,idempotencyKey:`worktree-outcome:${r.completionWakeOutcomeKey??n}`,deferConditionalWakeUntilNextTick:!0,deferConditionalWakeMs:ay,wakeMessageOnNotifySuccess:s&&a?i(!0):void 0,wakeMessageOnNotifyFailed:s&&a?i(!1):void 0})}dispose(){this.wakeDispatcher.dispose()}getDeliveryRef(e){return U(e)??$(e)??""}applyDeliveryState(e,n){!e||!n||this.applyPersistedPatch(e,{deliveryState:n})}applyNotifyDeliveryState(e,n,r){!e||!n||this.applyPersistedPatch(e,r?{deliveryState:n,...r}:{deliveryState:n})}applyPersistedPatchWithCompletionWake(e,n,r,o){!e||!n||this.applyPersistedPatch(e,r?{deliveryState:n,...r,...o}:{deliveryState:n})}buildCompletionWakePatch(e){if(e.completionWakeSummaryRequired===!0)return{completionWakeSummaryRequired:!0}}buildCompletionWakeSucceededPatch(e){if(e)return{completionWakeSummaryRequired:void 0}}withoutCompletionWake(e){return{...e,completionSummary:e.completionSummary?{...e.completionSummary,required:!1}:void 0,wakeMessage:void 0,wakeMessageOnNotifySuccess:void 0,wakeMessageOnNotifyFailed:void 0,completionWakeSummaryRequired:!1}}buildCompletionSummaryFact(e){if(e.completionSummary)return e.completionSummary;if(e.completionWakeSummaryRequired!==!0)return;let n=[e.wakeMessage,e.wakeMessageOnNotifySuccess,e.wakeMessageOnNotifyFailed].map(r=>r?.trim()).filter(r=>!!r);return{required:!0,producer:"legacy",outcomeKey:e.completionWakeOutcomeKey,fallbackFingerprint:n.length>0?`${e.label}
246
+ `),buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,i,{},[[this.deps.makeOpenPrButton(e.id)]])})}async handleAutoMergeStrategy(e,n,r,o,i,s,a=U(e)??e.harnessSessionId,l={merge:!0,pr:!0}){this.deps.isAlreadyMerged(a)||e.autoMergeResolverSessionId||await this.deps.enqueueMerge(n,async()=>{if(this.deps.isAlreadyMerged(a))return;let d=this.deps.mergeBranch(n,o,i,"merge",r);if(d.success){this.handleAutoMergeSuccess(e,n,o,i,s,d);return}if(d.rebaseConflict){await this.handleInitialAutoMergeConflict(e,n,r,o,i,l,d.error,d);return}let u=_e(d.dirtyError?`❌ [${e.name}] Merge blocked: ${d.error}`:`❌ [${e.name}] Merge failed: ${d.error??"unknown error"}`,d);if(e.worktreeState==="merge_conflict_resolving"||e.worktreeLifecycle?.state==="merge_conflict_resolving"){this.handleAutoMergeRetryFailure(e,o,r,u,l);return}this.deps.dispatchSessionNotification(e,{label:"worktree-merge-error",idempotencyKey:`worktree-merge-error:${e.id}:${o}`,userMessage:u})},()=>{this.deps.dispatchSessionNotification(e,{label:"worktree-merge-queued",idempotencyKey:`worktree-merge-queued:${e.id}:${o}`,userMessage:`🕐 [${e.name}] Merge queued — another merge for this repo is in progress. Will notify when complete.`})})}async handleAutoPrStrategy(e,n,r,o,i,s={merge:!0,pr:!0}){if(this.updatePersistedSessionFor(e,{lifecycle:"terminal",worktreeState:"pr_in_progress"}),!(await this.deps.runAutoPr(e,i)).success){let l=xt(n);if(!!(l&&l!==o&&Tt(n,o,l)&&rt(r).length===0)){let u=de(e)?!0:ce(n,r);return u&&(e.worktreePath=void 0,this.updatePersistedSessionFor(e,{worktreePath:void 0})),ye(n,o),this.markReleased(e,[`released_by_branch:${l}`]),{notificationSent:!1,worktreeRemoved:u}}this.markPendingDecision(e),this.deps.dispatchSessionNotification(e,{label:"worktree-auto-pr-failed",idempotencyKey:`worktree-auto-pr-failed:${e.id}:${i}`,userMessage:`⚠️ [${e.name}] Auto-PR did not complete. The worktree is preserved for an explicit merge or PR decision.`,buttons:this.getPolicyAwareWorktreeDecisionButtons(e.id,s)})}return{notificationSent:!0,worktreeRemoved:!1}}};import{existsSync as Gh,statSync as jh,writeFileSync as Hh}from"fs";Re();import{randomUUID as uh}from"crypto";function ch(t){return t==="plan-approve"||t==="plan-request-changes"||t==="plan-reject"}var po=class{constructor(e,n){this.onChange=e;this.retentionMs=n}onChange;retentionMs;tokens=new Map;afterChange;replaceAll(e){this.tokens.clear();for(let n of e)this.tokens.set(n.id,n)}clear(){this.tokens.clear(),this.notifyChanged()}listForPersistence(){return[...this.tokens.values()]}createActionToken(e,n,r={}){let o={id:uh(),sessionId:e,kind:n,createdAt:Date.now(),...r};return this.tokens.set(o.id,o),this.notifyChanged(),o}getActionToken(e){let n=this.tokens.get(e);if(n){if(n.expiresAt!=null&&n.expiresAt<=Date.now()){this.tokens.delete(e),this.notifyChanged();return}return n}}listActiveActionTokens(e){let n=[];for(let r of[...this.tokens.keys()]){let o=this.getActionToken(r);!o||o.consumedAt!=null||e&&o.kind!==e||n.push(o)}return n}consumeActionToken(e){let n=this.getActionToken(e);if(!(!n||n.consumedAt!=null))return n.consumedAt=Date.now(),this.notifyChanged(),n}deleteActionTokensForSession(e){let n=!1;for(let[r,o]of this.tokens)o.sessionId===e&&(this.tokens.delete(r),n=!0);n&&this.notifyChanged()}deleteActionTokensForSessionByKind(e,n){let r=!1;for(let[o,i]of this.tokens)i.sessionId===e&&i.kind===n&&(this.tokens.delete(o),r=!0);r&&this.notifyChanged()}deletePlanDecisionTokensForSession(e,n){let r=!1;for(let[o,i]of this.tokens)i.sessionId!==e||!ch(i.kind)||n!=null&&i.planDecisionVersion===n||(this.tokens.delete(o),r=!0);r&&this.notifyChanged()}purgeExpiredActionTokens(e=Date.now()){let n=!1;for(let[r,o]of this.tokens){let i=o.expiresAt!=null&&o.expiresAt<=e,s=o.consumedAt!=null&&e-o.consumedAt>=this.retentionMs;(i||s)&&(this.tokens.delete(r),n=!0)}return n&&this.notifyChanged(),n}nextExpiryAt(){let e;for(let n of this.tokens.values()){let r=[n.expiresAt,n.consumedAt!=null?n.consumedAt+this.retentionMs:void 0].filter(o=>o!=null&&Number.isFinite(o));for(let o of r)(e==null||o<e)&&(e=o)}return e}setAfterChangeListener(e){this.afterChange=e}notifyChanged(){this.onChange(),this.afterChange?.()}};X();X();var mo=class{constructor(e){this.indexes=e}indexes;hasRecordedSession(e){return this.indexes.idIndex.has(e)}getLatestPersistedByName(e){let n,r=Number.NEGATIVE_INFINITY,o=Number.NEGATIVE_INFINITY,i=Number.NEGATIVE_INFINITY,s=0;for(let a of this.indexes.persisted.values()){if(a.name!==e){s++;continue}let l=a.createdAt??Number.NEGATIVE_INFINITY,d=a.completedAt??Number.NEGATIVE_INFINITY;(l>r||l===r&&d>o||l===r&&d===o&&s>i)&&(n=a,r=l,o=d,i=s),s++}return n}resolveBackendConversationId(e,n){if(n)return n;let r=this.indexes.idIndex.get(e);if(r){let s=this.indexes.persisted.get(r);return(s?$(s):void 0)??r}let o=this.getLatestPersistedByName(e);if(o)return $(o)??o.harnessSessionId;let i=this.indexes.backendIdIndex.get(e);if(i){let s=this.indexes.persisted.get(i);return(s?$(s):void 0)??i}if(this.indexes.persisted.has(e)){let s=this.indexes.persisted.get(e);return s?$(s)??e:e}if(/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(e))return e}resolveHarnessSessionId(e,n){return this.resolveBackendConversationId(e,n)}getPersistedSession(e){let n=this.indexes.idIndex.get(e);if(n)return this.indexes.persisted.get(n);let r=this.getLatestPersistedByName(e);if(r)return r;let o=this.indexes.backendIdIndex.get(e);return o?this.indexes.persisted.get(o):this.indexes.persisted.get(e)}listPersistedSessions(){return[...this.indexes.persisted.values()].sort((e,n)=>(n.completedAt??0)-(e.completedAt??0))}};import{existsSync as nu,mkdirSync as Nh,readFileSync as Lh,readdirSync as Bh,renameSync as ru,statSync as ou,unlinkSync as iu,writeFileSync as su}from"fs";import{tmpdir as Fh}from"os";import{dirname as qh,join as au}from"path";import{homedir as ph}from"node:os";import{join as mh}from"node:path";function Hd(t){let e=t.OPENCLAW_HOME?.trim();if(e)return e;let n=t.HOME?.trim()||ph();return mh(n,".openclaw")}Re();var fo=7,fh=new Set(["running","completed","failed","killed"]);function Qe(t){return!!t&&typeof t=="object"}function qt(t,e=""){return typeof t=="string"&&t.trim().length>0?t:e}function w(t){return typeof t=="string"&&t.trim().length>0?t:void 0}function fe(t){return typeof t=="number"&&Number.isFinite(t)?t:void 0}function zd(t){return typeof t=="string"&&vl.has(t)?t:void 0}function Ps(t){return t==="default"||t==="plan"||t==="bypassPermissions"?t:void 0}function gh(t){return t==="never"||t==="on-request"?"never":void 0}function Qd(t){return t==="approve"||t==="ask"||t==="delegate"?t:void 0}function hh(t){if(t==="plan-mode"||t==="codex-first-turn-plan"||t==="soft-plan")return"plan-mode"}function Jd(t){return typeof t=="string"&&Tr.has(t)?t:void 0}function bs(t){return typeof t=="string"&&Sl.has(t)?t:void 0}function Yd(t){return t==="github"||t==="unsupported"?t:void 0}function yh(t){return t==="stored"||t==="seeded"||t==="unknown"?t:void 0}function kh(t){return t==="user"||t==="idle-timeout"||t==="startup-timeout"||t==="shutdown"||t==="done"||t==="unknown"?t:void 0}function Sh(t){return t==="starting"||t==="active"||t==="awaiting_plan_decision"||t==="awaiting_user_input"||t==="awaiting_worktree_decision"||t==="suspended"||t==="terminal"?t:void 0}function vh(t){return t==="not_required"||t==="pending"||t==="approved"||t==="changes_requested"||t==="rejected"?t:void 0}function wh(t){return t==="none"||t==="provisioned"||t==="pending_decision"||t==="merge_conflict_resolving"||t==="merge_in_progress"||t==="pr_in_progress"||t==="merged"||t==="released"||t==="pr_open"||t==="dismissed"||t==="cleanup_failed"?t:void 0}function Ph(t){return t==="none"||t==="provisioned"||t==="pending_decision"||t==="merge_conflict_resolving"||t==="pr_open"||t==="merged"||t==="released"||t==="dismissed"||t==="no_change"||t==="cleanup_failed"?t:void 0}function bh(t){return t==="live"||t==="stopped"?t:void 0}function Rh(t){return t==="not_sent"||t==="sending"||t==="delivered"||t==="fallback_delivered"||t==="failed"?t:void 0}function Ah(t){return t==="direct-telegram"?"direct-message":t==="none"||t==="direct-message"||t==="wake-only"?t:void 0}function Ih(t){return t==="none"||t==="canonical_buttons"||t==="explicit_fallback_text"?t:void 0}function xh(t){return t==="idle"||t==="notifying"||t==="wake_pending"||t==="failed"?t:void 0}function Th(t){return t==="in_flight"||t==="delivered"?t:void 0}function Ch(t){if(!Array.isArray(t))return;let e=t.map(n=>{if(!Qe(n))return;let r=w(n.key),o=Th(n.status),i=w(n.recordedAt);if(!(!r||!o||!i||!Number.isFinite(Date.parse(i))))return{key:r,status:o,recordedAt:i,label:w(n.label)}}).filter(n=>!!n);return e.length>0?e.slice(-64):void 0}function Mh(t){if(!Array.isArray(t))return;let e=t.map(n=>{if(!Qe(n))return;let r=w(n.key),o=w(n.recordedAt);if(!r||!o||!Number.isFinite(Date.parse(o)))return;let i=Array.isArray(n.linkedKeys)?[...new Set(n.linkedKeys.map(w).filter(s=>!!(s&&s!==r)))]:void 0;return{key:r,linkedKeys:i&&i.length>0?i:void 0,recordedAt:o,label:w(n.label),skipReason:w(n.skipReason)}}).filter(n=>!!n);return e.length>0?e.slice(-1024):void 0}function _h(t){return t==="awaiting_plan_output"||t==="awaiting_approval"||t==="approved_then_implemented"||t==="implemented_without_required_approval"||t==="not_plan_gated"?t:void 0}function $h(t){return t==="plan-approve"||t==="plan-request-changes"||t==="plan-reject"||t==="plan-offer-start"||t==="plan-offer-dismiss"||t==="repo-policy-set"||t==="worktree-merge"||t==="worktree-create-pr"||t==="worktree-update-pr"||t==="worktree-view-pr"||t==="worktree-decide-later"||t==="worktree-dismiss"||t==="session-resume"||t==="session-restart"||t==="view-output"||t==="question-answer"?t:void 0}function Zd(t){if(!Qe(t))return;let e=w(t.provider),n=w(t.accountId),r=w(t.target),o=w(t.threadId),i=w(t.sessionKey);if(!(!e||!r))return{provider:e,accountId:n,target:r,threadId:o,sessionKey:i}}function Eh(t,e,n){if(Qe(t)){let r=w(t.kind),o=w(t.conversationId);if(o&&(r==="claude-code"||r==="codex-app-server"||r==="opencode-server"))return{kind:r,conversationId:o,runId:w(t.runId),worktreeId:w(t.worktreeId),worktreePath:w(t.worktreePath)}}if(e==="claude-code")return{kind:"claude-code",conversationId:n}}function Dh(t){if(!Qe(t))return;let e=Ph(t.state),n=w(t.updatedAt);if(!e||!n)return;let r=w(t.resolutionSource);return{state:e,updatedAt:n,resolvedAt:w(t.resolvedAt),resolutionSource:r==="agent_merge"||r==="agent_pr"||r==="strategy_no_change"||r==="lifecycle_resolver"||r==="dismiss"||r==="maintenance"?r:void 0,baseBranch:w(t.baseBranch),targetRepo:w(t.targetRepo),pushRemote:w(t.pushRemote),notes:Array.isArray(t.notes)?t.notes.filter(o=>typeof o=="string"&&o.length>0):void 0}}function Oh(t){let e=new Date(0).toISOString(),n=w(t.worktreeMergedAt)??w(t.worktreeDismissedAt)??w(t.pendingWorktreeDecisionSince)??e;if(t.worktreeMerged===!0||t.worktreeDisposition==="merged")return{state:"merged",updatedAt:n,resolvedAt:w(t.worktreeMergedAt)??n,resolutionSource:"agent_merge",baseBranch:w(t.worktreeBaseBranch),targetRepo:w(t.worktreePrTargetRepo),pushRemote:w(t.worktreePushRemote)};if(t.worktreeDisposition==="dismissed")return{state:"dismissed",updatedAt:n,resolvedAt:w(t.worktreeDismissedAt)??n,resolutionSource:"dismiss",baseBranch:w(t.worktreeBaseBranch),targetRepo:w(t.worktreePrTargetRepo),pushRemote:w(t.worktreePushRemote)};if(t.worktreeDisposition==="no-change-cleaned")return{state:"no_change",updatedAt:n,resolvedAt:n,resolutionSource:"strategy_no_change",baseBranch:w(t.worktreeBaseBranch),targetRepo:w(t.worktreePrTargetRepo),pushRemote:w(t.worktreePushRemote)};if(t.worktreeDisposition==="pr-opened"||t.worktreeState==="pr_open")return{state:"pr_open",updatedAt:n,baseBranch:w(t.worktreeBaseBranch),targetRepo:w(t.worktreePrTargetRepo),pushRemote:w(t.worktreePushRemote)};if(t.pendingWorktreeDecisionSince||t.worktreeState==="pending_decision")return{state:"pending_decision",updatedAt:n,baseBranch:w(t.worktreeBaseBranch),targetRepo:w(t.worktreePrTargetRepo),pushRemote:w(t.worktreePushRemote)};if(t.worktreeState==="merge_conflict_resolving")return{state:"merge_conflict_resolving",updatedAt:n,baseBranch:w(t.worktreeBaseBranch),targetRepo:w(t.worktreePrTargetRepo),pushRemote:w(t.worktreePushRemote)};if(w(t.worktreePath)||w(t.worktreeBranch))return{state:"provisioned",updatedAt:n,baseBranch:w(t.worktreeBaseBranch),targetRepo:w(t.worktreePrTargetRepo),pushRemote:w(t.worktreePushRemote)}}function Wh(t){if(typeof t=="string"&&fh.has(t))return t==="running"?"killed":t}function Xd(t){if(!Qe(t))return;let e=qt(t.harnessSessionId);if(!e)return;let n=Wh(t.status);if(!n)return;let r=t.status==="running",o=w(t.worktreePath),i=w(t.worktreeBranch),s=w(t.originChannel),a=typeof t.originThreadId=="string"||typeof t.originThreadId=="number"?t.originThreadId:void 0,l=w(t.originSessionKey),d=Zd(t.route);if(!d)return;let u=Ye({route:d,originChannel:s,originThreadId:a,originSessionKey:l});if(!u||o&&!i)return;let c=w(t.harness),p=Eh(t.backendRef,c,e),g=Dh(t.worktreeLifecycle)??Oh(t),m=w(t.completionWakeSucceededAt),f=w(t.completionWakeSkippedAt),y=t.completionWakeSummaryRequired===!0&&!f?!0:void 0;return{sessionId:w(t.sessionId),harnessSessionId:e,backendRef:p,name:qt(t.name,e),prompt:qt(t.prompt),workdir:qt(t.workdir,"(unknown)"),model:w(t.model),reasoningEffort:zd(t.reasoningEffort),fastMode:t.fastMode===!0?!0:void 0,createdAt:fe(t.createdAt),completedAt:fe(t.completedAt),status:n,lifecycle:r?"suspended":Sh(t.lifecycle),approvalState:vh(t.approvalState),worktreeState:wh(t.worktreeState),runtimeState:r?"stopped":bh(t.runtimeState),deliveryState:xh(t.deliveryState),notificationDedupe:Ch(t.notificationDedupe),completionSummaryDedupe:Mh(t.completionSummaryDedupe),completionWakeIssuedAt:w(t.completionWakeIssuedAt),completionWakeSucceededAt:m,completionWakeFailedAt:w(t.completionWakeFailedAt),completionWakeSkippedAt:f,completionWakeSkipReason:w(t.completionWakeSkipReason),completionWakeSummaryRequired:y,killReason:kh(t.killReason),costUsd:typeof t.costUsd=="number"&&Number.isFinite(t.costUsd)?t.costUsd:0,originAgentId:w(t.originAgentId),originChannel:s,originThreadId:a,originSessionKey:l,route:u,outputPath:w(t.outputPath),harness:c,goalTaskId:w(t.goalTaskId),requestedPermissionMode:Ps(t.requestedPermissionMode),currentPermissionMode:Ps(t.currentPermissionMode),approvalExecutionState:_h(t.approvalExecutionState),approvalRationale:w(t.approvalRationale),planModeApproved:t.planModeApproved===!0,pendingPlanApproval:t.pendingPlanApproval===!0,planApprovalContext:hh(t.planApprovalContext),planDecisionVersion:fe(t.planDecisionVersion),actionablePlanDecisionVersion:fe(t.actionablePlanDecisionVersion),canonicalPlanPromptVersion:fe(t.canonicalPlanPromptVersion),approvalPromptRequiredVersion:fe(t.approvalPromptRequiredVersion),approvalPromptVersion:fe(t.approvalPromptVersion),approvalPromptStatus:Rh(t.approvalPromptStatus),approvalPromptTransport:Ah(t.approvalPromptTransport),approvalPromptMessageKind:Ih(t.approvalPromptMessageKind),approvalPromptLastAttemptAt:w(t.approvalPromptLastAttemptAt),approvalPromptDeliveredAt:w(t.approvalPromptDeliveredAt),approvalPromptFailedAt:w(t.approvalPromptFailedAt),planApproval:Qd(t.planApproval),codexApprovalPolicy:gh(t.codexApprovalPolicy),worktreePath:o,worktreeBranch:i,worktreeStrategy:Jd(t.worktreeStrategy),repoIntegrationPolicy:bs(t.repoIntegrationPolicy),repoIntegrationPolicySource:yh(t.repoIntegrationPolicySource),repoProvider:Yd(t.repoProvider),worktreeMerged:typeof t.worktreeMerged=="boolean"?t.worktreeMerged:void 0,worktreeMergedAt:w(t.worktreeMergedAt),worktreePrUrl:w(t.worktreePrUrl),worktreePrNumber:fe(t.worktreePrNumber),pendingWorktreeDecisionSince:w(t.pendingWorktreeDecisionSince),lastWorktreeReminderAt:w(t.lastWorktreeReminderAt),worktreeBaseBranch:w(t.worktreeBaseBranch),worktreePrTargetRepo:w(t.worktreePrTargetRepo),autoMergeParentSessionId:w(t.autoMergeParentSessionId),autoMergeConflictResolutionAttemptCount:fe(t.autoMergeConflictResolutionAttemptCount),autoMergeResolverSessionId:w(t.autoMergeResolverSessionId),worktreePushRemote:w(t.worktreePushRemote),worktreeDecisionSnoozedUntil:w(t.worktreeDecisionSnoozedUntil),worktreeDisposition:t.worktreeDisposition==="active"||t.worktreeDisposition==="pr-opened"||t.worktreeDisposition==="merged"||t.worktreeDisposition==="dismissed"||t.worktreeDisposition==="no-change-cleaned"?t.worktreeDisposition:void 0,worktreeDismissedAt:w(t.worktreeDismissedAt),worktreeLifecycle:g,resumable:r?!0:t.resumable===!0}}function eu(t){if(!Qe(t))return;let e=w(t.key),n=w(t.repoRoot),r=bs(t.policy),o=Yd(t.provider)??"unsupported",i=w(t.createdAt),s=w(t.updatedAt),a=t.source==="seeded"?"seeded":"stored";if(!(!e||!n||!r||!i||!s)&&!(!Number.isFinite(Date.parse(i))||!Number.isFinite(Date.parse(s))))return{key:e,policy:r,repoRoot:n,remoteUrl:w(t.remoteUrl),provider:o,createdAt:i,updatedAt:s,source:a}}function tu(t){if(!Qe(t))return;let e=$h(t.kind),n=qt(t.id),r=qt(t.sessionId),o=fe(t.createdAt);if(!(!n||!r||!e||o==null))return{id:n,sessionId:r,kind:e,createdAt:o,planDecisionVersion:fe(t.planDecisionVersion),expiresAt:fe(t.expiresAt),consumedAt:fe(t.consumedAt),optionIndex:fe(t.optionIndex),pendingInputRequestId:w(t.pendingInputRequestId),pendingInputQuestionId:w(t.pendingInputQuestionId),label:w(t.label),targetUrl:w(t.targetUrl),route:Zd(t.route),launchName:w(t.launchName),launchPrompt:w(t.launchPrompt),launchWorkdir:w(t.launchWorkdir),launchModel:w(t.launchModel),launchReasoningEffort:zd(t.launchReasoningEffort),launchFastMode:t.launchFastMode===!0?!0:void 0,launchSystemPrompt:w(t.launchSystemPrompt),launchAllowedTools:Array.isArray(t.launchAllowedTools)?t.launchAllowedTools.filter(i=>typeof i=="string"):void 0,launchResumeSessionId:w(t.launchResumeSessionId),launchResumeWorktreeFrom:w(t.launchResumeWorktreeFrom),launchSessionIdOverride:w(t.launchSessionIdOverride),launchClearedPersistedCodexResume:t.launchClearedPersistedCodexResume===!0?!0:void 0,launchForkSession:typeof t.launchForkSession=="boolean"?t.launchForkSession:void 0,launchForceNewSession:typeof t.launchForceNewSession=="boolean"?t.launchForceNewSession:void 0,launchPermissionMode:Ps(t.launchPermissionMode),launchPlanApproval:Qd(t.launchPlanApproval),launchHarness:w(t.launchHarness),launchWorktreeStrategy:Jd(t.launchWorktreeStrategy),launchWorktreeBaseBranch:w(t.launchWorktreeBaseBranch),launchWorktreePrTargetRepo:w(t.launchWorktreePrTargetRepo),launchOriginAgentId:w(t.launchOriginAgentId),repoPolicy:bs(t.repoPolicy),repoPolicyWorkdir:w(t.repoPolicyWorkdir)}}function go(t){if(!t.backendRef?.kind||!t.backendRef.conversationId)throw new Error(`Persisted session ${t.harnessSessionId} is missing required backend ref metadata.`);if(!t.route?.provider||!t.route.target)throw new Error(`Persisted session ${t.harnessSessionId} is missing required route metadata.`);if(t.worktreePath&&!t.worktreeBranch)throw new Error(`Persisted session ${t.harnessSessionId} is missing required worktreeBranch metadata.`)}function Rs(t){return!!t&&typeof t=="object"}function As(t){return t instanceof Error?t.message:String(t)}function lu(t,e,n=Date.now()){let r=`${t}.${e}-${n}`;for(let o=0;o<100;o+=1){let i=o===0?"":`-${o}`,s=`${r}${i}.json`;if(!nu(s))return s}}function Is(){let t=Fh();return Bh(t).filter(e=>e.startsWith("openclaw-agent-")&&e.endsWith(".txt")).map(e=>au(t,e))}function du(t){let e=t.OPENCLAW_CODE_AGENT_SESSIONS_PATH?.trim();return e||au(Hd(t),"code-agent-sessions.json")}function uu(t,e,n,r=[]){try{Nh(qh(t),{recursive:!0});let o=t+".tmp";su(o,JSON.stringify({schemaVersion:fo,sessions:e,actionTokens:n,repoPolicies:r},null,2),"utf-8"),ru(o,t)}catch(o){`${As(o)}`}}function Kh(t,e){try{if(!nu(t))return!1;let n=lu(t,"legacy");return n?(ru(t,n),`${e}${n}`,!0):!1}catch(n){return`${As(n)}`,!1}}var Uh={archiveLegacySessionIndex:Kh};function Vh(t,e){try{if(e.length===0)return;let n=lu(t,"codex-sdk-legacy");if(!n)return;su(n,JSON.stringify(e,null,2),"utf-8"),`${e.length}${n}`}catch(n){`${As(n)}`}}function cu(t,e,n=[]){try{let r=new Set(n);for(let o of Is())if(!r.has(o))try{let i=ou(o).mtimeMs;t-i>e&&iu(o)}catch{}}catch{}}function pu(t,e,n=[]){try{let r=new Set(n),o;for(let i of Is())if(!r.has(i))try{let s=ou(i).mtimeMs+e;if(s<=t)return t;o=o==null?s:Math.min(o,s)}catch{}return o}catch{return}}function mu(t){try{let e=new Set(t);for(let n of Is())if(!e.has(n))try{iu(n)}catch{}}catch{}}function fu(t){let{indexPath:e,clearAll:n,indexPersistedEntry:r,setActionToken:o,setRepoPolicy:i,purgeExpiredActionTokens:s,saveIndex:a}=t,l=d=>Uh.archiveLegacySessionIndex(e,d)?(n(),!0):!1;try{let d=Lh(e,"utf-8"),u=JSON.parse(d);if(Array.isArray(u)){if(!l("legacy array store"))return;a();return}if(!Rs(u)||u.schemaVersion!==fo&&u.schemaVersion!==6&&u.schemaVersion!==4){if(!l(`schema mismatch (expected v${fo})`))return;a();return}let c=(b,A)=>{if(!Object.prototype.hasOwnProperty.call(u,b))return[];let k=u[b];if(Array.isArray(k))return k;l(A)&&a()},p=c("sessions","invalid sessions collection");if(p===void 0)return;let g=[],m=[];for(let b of p){if(Rs(b)&&b.harness==="codex"){let k=Rs(b.backendRef)?b.backendRef:void 0;if((typeof k?.kind=="string"?k.kind:void 0)!=="codex-app-server"){g.push(b);continue}}let A=Xd(b);if(!A){if(!l("invalid v4 session entry"))return;a();return}m.push(A)}g.length>0&&Vh(e,g);let f=c("actionTokens","invalid action token collection");if(f===void 0)return;let y=[];for(let b of f){let A=tu(b);if(!A){if(!l("invalid v4 action token"))return;a();return}y.push(A)}let S=c("repoPolicies","invalid repo policy collection");if(S===void 0)return;let R=[],I=!1;for(let b of S){let A=eu(b);if(!A){I=!0;continue}R.push(A)}for(let b of m)r(b);for(let b of y)o(b);for(let b of R)i(b);g.length>0&&a(),I&&a(),s()}catch(d){if(d.code==="ENOENT"||!l("corrupt or unreadable"))return;a()}}var zh=new Set(["completed","failed","killed"]),xs=1440*60*1e3;function Qh(t){return t instanceof Error?t.message:String(t)}var Jh={statSync:jh};function Yh(t){try{return Jh.statSync(t).isDirectory()}catch(e){let n=e.code;return n!=="ENOENT"&&n!=="ENOTDIR"}}var ho=class{persisted=new Map;repoPolicies=new Map;idIndex=new Map;nameIndex=new Map;backendIdIndex=new Map;actionTokens;actionTokenStore;indexPath;queries;constructor(e={}){let n=e.env??process.env;this.indexPath=e.indexPath??du(n),this.actionTokenStore=new po(()=>this.saveIndex(),xs),this.actionTokens=this.actionTokenStore.tokens,this.queries=new mo({persisted:this.persisted,idIndex:this.idIndex,nameIndex:this.nameIndex,backendIdIndex:this.backendIdIndex}),n.OPENCLAW_DEBUG_SESSION_STORE==="1"&&`${this.indexPath}`,this.loadIndex()}loadIndex(){fu({indexPath:this.indexPath,clearAll:()=>{this.persisted.clear(),this.repoPolicies.clear(),this.idIndex.clear(),this.nameIndex.clear(),this.backendIdIndex.clear(),this.actionTokenStore.clear()},indexPersistedEntry:e=>this.indexPersistedEntry(e),setActionToken:e=>{this.actionTokens.set(e.id,e)},setRepoPolicy:e=>{this.repoPolicies.set(e.key,e)},purgeExpiredActionTokens:()=>this.actionTokenStore.purgeExpiredActionTokens(),saveIndex:()=>this.saveIndex()})}saveIndex(){uu(this.indexPath,[...this.persisted.values()],this.actionTokenStore.listForPersistence(),[...this.repoPolicies.values()])}assertPersistedEntry(e){go(e)}getEntryStorageKey(e){return e.harnessSessionId}buildPersistedBackendRef(e){let n=hi(e),r=n==="codex"?"codex-app-server":n==="opencode"?"opencode-server":"claude-code";return e.backendRef??{kind:e.backendKind??r,conversationId:e.harnessSessionId}}getSessionApprovalSnapshot(e){if(typeof e.approvalSnapshot=="function")return e.approvalSnapshot();let n=typeof e.controlStateSnapshot=="function"?e.controlStateSnapshot():{planModeApproved:!1};return{requestedPermissionMode:e.requestedPermissionMode,currentPermissionMode:e.currentPermissionMode,approvalExecutionState:e.approvalExecutionState,approvalRationale:e.approvalRationale,planModeApproved:n.planModeApproved,pendingPlanApproval:e.pendingPlanApproval,planApprovalContext:e.planApprovalContext,planDecisionVersion:e.planDecisionVersion,actionablePlanDecisionVersion:e.actionablePlanDecisionVersion,canonicalPlanPromptVersion:e.canonicalPlanPromptVersion,approvalPromptRequiredVersion:e.approvalPromptRequiredVersion,approvalPromptVersion:e.approvalPromptVersion,approvalPromptStatus:e.approvalPromptStatus,approvalPromptTransport:e.approvalPromptTransport,approvalPromptMessageKind:e.approvalPromptMessageKind,approvalPromptLastAttemptAt:e.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:e.approvalPromptDeliveredAt,approvalPromptFailedAt:e.approvalPromptFailedAt,planApproval:e.planApproval,codexApprovalPolicy:e.codexApprovalPolicy}}getSessionRoutingSnapshot(e){return typeof e.routingSnapshot=="function"?e.routingSnapshot():{route:e.route,originAgentId:e.originAgentId,originChannel:e.originChannel,originThreadId:e.originThreadId,originSessionKey:e.originSessionKey}}getSessionWorktreeSnapshot(e){return typeof e.worktreeSnapshot=="function"?e.worktreeSnapshot():{worktreePath:e.worktreePath,worktreeBranch:e.worktreeBranch,worktreeStrategy:e.worktreeStrategy,repoIntegrationPolicy:e.repoIntegrationPolicy,repoIntegrationPolicySource:e.repoIntegrationPolicySource,repoProvider:e.repoProvider,worktreeBaseBranch:e.worktreeBaseBranch,worktreePrTargetRepo:e.worktreePrTargetRepo,autoMergeParentSessionId:e.autoMergeParentSessionId,autoMergeConflictResolutionAttemptCount:e.autoMergeConflictResolutionAttemptCount,autoMergeResolverSessionId:e.autoMergeResolverSessionId,worktreeLifecycle:e.worktreeLifecycle}}indexPersistedEntry(e){let n=this.getEntryStorageKey(e);this.persisted.set(n,e),e.sessionId&&this.idIndex.set(e.sessionId,n),e.name&&this.nameIndex.set(e.name,n);let r=$(e);r&&this.backendIdIndex.set(r,n)}removePersistedIndexes(e){let n=this.getEntryStorageKey(e);this.persisted.delete(n);for(let[r,o]of this.idIndex)o===n&&this.idIndex.delete(r);for(let[r,o]of this.nameIndex)o===n&&this.nameIndex.delete(r);for(let[r,o]of this.backendIdIndex)o===n&&this.backendIdIndex.delete(r)}markRunning(e){if(!e.harnessSessionId)return;let n=this.getSessionApprovalSnapshot(e),r=this.getSessionRoutingSnapshot(e),o=this.getSessionWorktreeSnapshot(e),i=Ye({route:r.route,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey});if(!i)return;let s={sessionId:e.id,harnessSessionId:e.harnessSessionId,backendRef:this.buildPersistedBackendRef(e),name:e.name,prompt:e.prompt,workdir:e.originalWorkdir??e.workdir,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,createdAt:e.startedAt,status:"running",lifecycle:e.lifecycle,approvalState:e.approvalState,worktreeState:e.worktreeState,runtimeState:e.runtimeState,deliveryState:e.deliveryState,notificationDedupe:this.getExistingNotificationDedupe(e),costUsd:0,originAgentId:r.originAgentId,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey,route:i,outputPath:nt(e.id),harness:e.harnessName,requestedPermissionMode:n.requestedPermissionMode,currentPermissionMode:n.currentPermissionMode,approvalExecutionState:n.approvalExecutionState,approvalRationale:n.approvalRationale,planModeApproved:n.planModeApproved,pendingPlanApproval:n.pendingPlanApproval,planApprovalContext:n.planApprovalContext,planDecisionVersion:n.planDecisionVersion,actionablePlanDecisionVersion:n.actionablePlanDecisionVersion,canonicalPlanPromptVersion:n.canonicalPlanPromptVersion,approvalPromptRequiredVersion:n.approvalPromptRequiredVersion,approvalPromptVersion:n.approvalPromptVersion,approvalPromptStatus:n.approvalPromptStatus,approvalPromptTransport:n.approvalPromptTransport,approvalPromptMessageKind:n.approvalPromptMessageKind,approvalPromptLastAttemptAt:n.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:n.approvalPromptDeliveredAt,approvalPromptFailedAt:n.approvalPromptFailedAt,planApproval:n.planApproval,codexApprovalPolicy:n.codexApprovalPolicy,worktreePath:o.worktreePath,worktreeBranch:o.worktreeBranch,worktreeStrategy:o.worktreeStrategy,repoIntegrationPolicy:o.repoIntegrationPolicy,repoIntegrationPolicySource:o.repoIntegrationPolicySource,repoProvider:o.repoProvider,worktreeBaseBranch:o.worktreeBaseBranch,worktreePrTargetRepo:o.worktreePrTargetRepo,autoMergeParentSessionId:o.autoMergeParentSessionId,autoMergeConflictResolutionAttemptCount:o.autoMergeConflictResolutionAttemptCount,autoMergeResolverSessionId:o.autoMergeResolverSessionId,worktreeLifecycle:o.worktreeLifecycle,resumable:e.isExplicitlyResumable};go(s),this.indexPersistedEntry(s),this.saveIndex()}hasRecordedSession(e){return this.queries.hasRecordedSession(e)}persistTerminal(e){if(!e.harnessSessionId)return;let n=this.getSessionApprovalSnapshot(e),r=this.getSessionRoutingSnapshot(e),o=this.getSessionWorktreeSnapshot(e),i=Ye({route:r.route,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey});if(!i)return;let s;try{let l=nt(e.id);if(Gh(l))s=l;else{let d=e.getOutput().join(`
247
+ `);d.length>0&&(Hh(l,d,"utf-8"),s=l)}}catch(l){`${e.id}${Qh(l)}`}let a={sessionId:e.id,harnessSessionId:e.harnessSessionId,backendRef:this.buildPersistedBackendRef(e),name:e.name,prompt:e.prompt,workdir:e.originalWorkdir??e.workdir,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,createdAt:e.startedAt,completedAt:e.completedAt,status:e.status,lifecycle:e.lifecycle,approvalState:e.approvalState,worktreeState:e.worktreeState,runtimeState:e.runtimeState,deliveryState:e.deliveryState,notificationDedupe:this.getExistingNotificationDedupe(e),killReason:e.killReason,costUsd:e.costUsd,originAgentId:r.originAgentId,originChannel:r.originChannel,originThreadId:r.originThreadId,originSessionKey:r.originSessionKey,route:i,outputPath:s,harness:e.harnessName,goalTaskId:e.goalTaskId,requestedPermissionMode:n.requestedPermissionMode,currentPermissionMode:n.currentPermissionMode,approvalExecutionState:n.approvalExecutionState,approvalRationale:n.approvalRationale,planModeApproved:n.planModeApproved,pendingPlanApproval:n.pendingPlanApproval,planApprovalContext:n.planApprovalContext,planDecisionVersion:n.planDecisionVersion,actionablePlanDecisionVersion:n.actionablePlanDecisionVersion,canonicalPlanPromptVersion:n.canonicalPlanPromptVersion,approvalPromptRequiredVersion:n.approvalPromptRequiredVersion,approvalPromptVersion:n.approvalPromptVersion,approvalPromptStatus:n.approvalPromptStatus,approvalPromptTransport:n.approvalPromptTransport,approvalPromptMessageKind:n.approvalPromptMessageKind,approvalPromptLastAttemptAt:n.approvalPromptLastAttemptAt,approvalPromptDeliveredAt:n.approvalPromptDeliveredAt,approvalPromptFailedAt:n.approvalPromptFailedAt,planApproval:n.planApproval,codexApprovalPolicy:n.codexApprovalPolicy,worktreePath:o.worktreePath,worktreeBranch:o.worktreeBranch,worktreeStrategy:o.worktreeStrategy,worktreeBaseBranch:o.worktreeBaseBranch,worktreePrTargetRepo:o.worktreePrTargetRepo,autoMergeParentSessionId:o.autoMergeParentSessionId,autoMergeConflictResolutionAttemptCount:o.autoMergeConflictResolutionAttemptCount,autoMergeResolverSessionId:o.autoMergeResolverSessionId,worktreeLifecycle:o.worktreeLifecycle,resumable:e.isExplicitlyResumable};go(a),this.indexPersistedEntry(a),this.saveIndex()}getExistingNotificationDedupe(e){return this.getPersistedSession(e.id)?.notificationDedupe??(e.harnessSessionId?this.getPersistedSession(e.harnessSessionId)?.notificationDedupe:void 0)??($(e)?this.getPersistedSession($(e))?.notificationDedupe:void 0)}getLatestPersistedByName(e){return this.queries.getLatestPersistedByName(e)}resolveBackendConversationId(e,n){return this.queries.resolveBackendConversationId(e,n)}resolveHarnessSessionId(e,n){return this.queries.resolveHarnessSessionId(e,n)}getPersistedSession(e){return this.queries.getPersistedSession(e)}listPersistedSessions(){return this.queries.listPersistedSessions()}getRepoPolicy(e){return this.repoPolicies.get(e)}listRepoPolicies(){return[...this.repoPolicies.values()].sort((e,n)=>e.repoRoot.localeCompare(n.repoRoot)||e.key.localeCompare(n.key))}setRepoPolicy(e){let n=this.repoPolicies.get(e.key),r={...e,createdAt:n?.createdAt??e.createdAt,updatedAt:new Date().toISOString(),source:"stored"};return this.repoPolicies.set(r.key,r),this.saveIndex(),r}updateRepoPolicy(e,n){let r=this.repoPolicies.get(e);if(r)return this.setRepoPolicy({...r,policy:n})}resetRepoPolicy(e){let n=this.repoPolicies.delete(e);return n&&this.saveIndex(),n}removeRepoPolicies(e){let n=[];for(let r of e){let o=this.repoPolicies.get(r);o&&(this.repoPolicies.delete(r),n.push(o))}return n.length>0&&this.saveIndex(),n.sort((r,o)=>r.repoRoot.localeCompare(o.repoRoot)||r.key.localeCompare(o.key))}cleanupRepoPolicies(){let e=[];for(let[n,r]of this.repoPolicies)Yh(r.repoRoot)||(this.repoPolicies.delete(n),e.push(r));return e.length>0&&this.saveIndex(),e.sort((n,r)=>n.repoRoot.localeCompare(r.repoRoot)||n.key.localeCompare(r.key))}cleanupTmpOutputFiles(e){this.actionTokenStore.purgeExpiredActionTokens(e),cu(e,xs,this.getReferencedOutputPaths())}getNextTmpOutputCleanupAt(e){return pu(e,xs,this.getReferencedOutputPaths())}evictOldestPersisted(e){let n=this.listPersistedSessions();if(n.length<=e)return[];let r=n.slice(e);for(let o of r)this.removePersistedIndexes(o);return this.saveIndex(),r}shouldGcActiveSession(e,n,r){return!e.completedAt||!zh.has(e.status)?!1:n-e.completedAt>r}getActionToken(e){return this.actionTokenStore.getActionToken(e)}consumeActionToken(e){return this.actionTokenStore.consumeActionToken(e)}deleteActionTokensForSession(e){this.actionTokenStore.deleteActionTokensForSession(e)}purgeExpiredActionTokens(e=Date.now()){return this.actionTokenStore.purgeExpiredActionTokens(e)}getNextActionTokenExpiry(){return this.actionTokenStore.nextExpiryAt()}onActionTokensChanged(e){this.actionTokenStore.setAfterChangeListener(e)}hasOutputPathReference(e){for(let n of this.persisted.values())if(n.outputPath===e)return!0;return!1}getReferencedOutputPaths(){return[...new Set([...this.persisted.values()].map(e=>e.outputPath).filter(e=>typeof e=="string"&&e.length>0))]}cleanupOrphanOutputFiles(){mu(this.getReferencedOutputPaths())}};var Zh=new Set(["completed","failed","killed"]),yo=class{metrics={totalCostUsd:0,costPerDay:new Map,sessionsByStatus:{completed:0,failed:0,killed:0},totalLaunched:0,totalDurationMs:0,sessionsWithDuration:0,mostExpensive:null};incrementLaunched(){this.metrics.totalLaunched++}recordSession(e){let n=e.costUsd??0,r=e.status;this.metrics.totalCostUsd+=n;let o=new Date(e.completedAt??e.startedAt).toISOString().slice(0,10);if(this.metrics.costPerDay.set(o,(this.metrics.costPerDay.get(o)??0)+n),Zh.has(r)&&this.metrics.sessionsByStatus[r]++,e.completedAt){let i=e.completedAt-e.startedAt;this.metrics.totalDurationMs+=i,this.metrics.sessionsWithDuration++}(!this.metrics.mostExpensive||n>this.metrics.mostExpensive.costUsd)&&(this.metrics.mostExpensive={id:e.id,name:e.name,costUsd:n,prompt:ae(e.prompt,80)})}getMetrics(){return{totalCostUsd:this.metrics.totalCostUsd,costPerDay:new Map(this.metrics.costPerDay),sessionsByStatus:{...this.metrics.sessionsByStatus},totalLaunched:this.metrics.totalLaunched,totalDurationMs:this.metrics.totalDurationMs,sessionsWithDuration:this.metrics.sessionsWithDuration,mostExpensive:this.metrics.mostExpensive?{...this.metrics.mostExpensive}:null}}};import*as yu from"child_process";var gu=5e3,ku=64,Xh={primary:"primary",success:"success",positive:"success",danger:"danger",destructive:"danger",negative:"danger"},ey={execFile:yu.execFile},Je=class extends Error{constructor(e){super(e),this.name="MissingRuntimeDirectNotificationCapabilityError"}},So=class{constructor(e=ey.execFile){this.execFile=e}execFile;async send(e,n,r){L("direct_send_started",{...be(e),messageTextLength:n.length,...J(r)});try{await this.sendViaRuntime(e,n,r),L("direct_send_succeeded",{...be(e),deliveryPath:"runtime",...J(r)});return}catch(o){if(!(o instanceof Je))throw L("direct_send_failed",{...be(e),deliveryPath:"runtime",...J(r),error:Ts(o)}),o;L("direct_send_runtime_capability_missing",{...be(e),deliveryPath:"runtime",...J(r),reason:o.message}),await this.sendViaBoundedCliFallback(e,n,r,o.message),L("direct_send_succeeded",{...be(e),deliveryPath:"cli-fallback",...J(r)})}}async sendViaRuntime(e,n,r){let o=At(),i=_a(),s=o?.channel?.outbound?.loadAdapter;if(!o)throw new Je("OpenClaw plugin runtime is unavailable for direct notification delivery");if(i==null)throw new Je("OpenClaw runtime config snapshot is unavailable for direct notification delivery");if(!o.channel)throw new Je(`OpenClaw plugin runtime channel surface is unavailable for direct notification delivery (runtimeVersion=${Cs(o)})`);if(!o.channel.outbound)throw new Je(`OpenClaw plugin runtime channel outbound surface is unavailable for direct notification delivery (runtimeVersion=${Cs(o)})`);if(!s)throw new Je(`OpenClaw plugin runtime channel outbound loadAdapter is unavailable for direct notification delivery (runtimeVersion=${Cs(o)})`);let a=await s(e.channel);if(!a)throw new Error(`OpenClaw outbound adapter for channel "${e.channel}" is unavailable`);let l=wo(r);if(L("runtime_adapter_loaded",{...be(e),adapterHasRenderPresentation:typeof a.renderPresentation=="function",adapterHasSendPayload:typeof a.sendPayload=="function",adapterHasSendText:typeof a.sendText=="function",...J(r),...l?Yi(l):{}}),l){await this.sendPresentation(a,i,e,n,l);return}if(!a.sendText)throw new Error(`OpenClaw outbound adapter for channel "${e.channel}" cannot send text`);await a.sendText({cfg:i,to:e.target,text:n,accountId:e.accountId,threadId:e.threadId})}async sendPresentation(e,n,r,o,i){let s=ny(i),a={text:o,presentation:i,interactive:s};L("presentation_render_started",{...be(r),messageTextLength:o.length,adapterHasRenderPresentation:typeof e.renderPresentation=="function",adapterHasSendPayload:typeof e.sendPayload=="function",...Yi(i)});let l={cfg:n,to:r.target,text:o,payload:a,accountId:r.accountId,threadId:r.threadId},d=e.renderPresentation?await e.renderPresentation({payload:a,presentation:i,ctx:l}):a,u=oy(d,s,r.channel);if(L("presentation_render_completed",{...be(r),adapterHasRenderPresentation:typeof e.renderPresentation=="function",adapterHasSendPayload:typeof e.sendPayload=="function",...Zi(u)}),!u||typeof u!="object"||!e.sendPayload)throw new Error(`OpenClaw outbound adapter for channel "${r.channel}" cannot preserve interactive presentation`);let c=await e.sendPayload({...l,payload:u});L("presentation_send_payload_completed",{...be(r),...Zi(u),...Hl(c)})}sendViaBoundedCliFallback(e,n,r,o){return new Promise((i,s)=>{let a=ty(e,n,r);L("direct_send_cli_fallback_started",{...be(e),deliveryPath:"cli-fallback",reason:o,messageTextLength:n.length,...J(r)}),this.execFile("openclaw",a,{timeout:gu,killSignal:"SIGKILL"},(l,d,u)=>{if(!l){L("direct_send_cli_fallback_completed",{...be(e),deliveryPath:"cli-fallback",...J(r)}),i();return}let c=u?.trim()?` | stderr: ${u.trim()}`:"";L("direct_send_cli_fallback_failed",{...be(e),deliveryPath:"cli-fallback",...J(r),error:Ts(l),stderrLength:u?.length}),s(new Error(`${o}; bounded openclaw message send fallback failed within ${gu}ms timeout: ${Ts(l)}${c}`))})})}};function be(t){return{channel:t.channel,target:t.target,accountId:t.accountId,threadId:t.threadId,sessionKey:t.sessionKey}}function ty(t,e,n){let r=wo(n),o=["message","send","--channel",t.channel,"--target",t.target,"--message",e];return t.accountId&&o.push("--account",t.accountId),t.threadId&&o.push("--thread-id",t.threadId),r&&o.push("--presentation",JSON.stringify(r)),o}function Ts(t){return t instanceof Error?t.message:String(t)}function Cs(t){if(!t||typeof t!="object")return"unknown";let e=t.version;return typeof e=="string"&&e.trim()?e:"unknown"}function wo(t){let e=(t??[]).filter(n=>Array.isArray(n)&&n.length>0).map(n=>({type:"buttons",buttons:n.map(r=>({label:r.label,value:uy(r.callbackData),...r.style?{style:r.style}:{}}))}));return e.length>0?{blocks:e}:void 0}function ny(t){let e=t.blocks.filter(n=>n.type==="buttons"&&n.buttons.length>0).map(n=>({type:"buttons",buttons:n.buttons.map(r=>({label:r.label,value:r.value,...r.style?{style:r.style}:{}}))}));return e.length>0?{blocks:e}:void 0}function ry(t){if(!t||typeof t!="object"||Array.isArray(t))return!1;let e=t.interactive;if(!e||typeof e!="object"||Array.isArray(e))return!1;let n=e.blocks;return Array.isArray(n)&&n.some(r=>{if(!r||typeof r!="object"||Array.isArray(r))return!1;let o=r;return o.type==="buttons"&&Array.isArray(o.buttons)&&o.buttons.length>0})}function oy(t,e,n){if(!e)return t;let r=ry(t)?t:iy(t,e);return n!=="telegram"?r:sy(r,e)}function iy(t,e){return!t||typeof t!="object"||Array.isArray(t)?t:{...t,interactive:e}}function sy(t,e){if(!t||typeof t!="object"||Array.isArray(t))return t;let n=t,r=Kt(n.channelData),o=Kt(r?.telegram),i=ly(o?.buttons);if(i)return{...n,channelData:{...r??{},telegram:{...o??{},buttons:i}}};let s=ay(e);return s?{...n,channelData:{...r??{},telegram:{...o??{},buttons:s}}}:t}function ay(t){let e=t.blocks.filter(n=>n.type==="buttons"&&n.buttons.length>0).map(n=>n.buttons.filter(r=>typeof r.value=="string"&&r.value.trim().length>0&&Buffer.byteLength(r.value,"utf8")<=ku).map(r=>({text:r.label,callback_data:r.value,...Su(r.style)}))).filter(n=>n.length>0);return e.length>0?e:void 0}function ly(t){if(!Array.isArray(t))return;let e=t.map(n=>Array.isArray(n)?n.map(r=>{if(!r||typeof r!="object"||Array.isArray(r))return;let{style:o,...i}=r;if(!(typeof i.text!="string"||i.text.trim().length===0)&&!(i.callback_data!==void 0&&(typeof i.callback_data!="string"||i.callback_data.trim().length===0||Buffer.byteLength(i.callback_data,"utf8")>ku))&&dy(i))return{...i,...Su(o)}}).filter(r=>!!r):[]).filter(n=>n.length>0);return e.length>0?e:void 0}function dy(t){return vo(t.callback_data)||vo(t.url)||ko(t.web_app)||ko(t.webApp)||ko(t.login_url)||ko(t.loginUrl)||typeof t.switch_inline_query=="string"||typeof t.switch_inline_query_current_chat=="string"||Kt(t.switch_inline_query_chosen_chat)!==void 0||Kt(t.callback_game)!==void 0||t.pay===!0||hu(t.copy_text)||hu(t.copyText)}function vo(t){return typeof t=="string"&&t.trim().length>0}function ko(t){let e=Kt(t);return vo(e?.url)}function hu(t){let e=Kt(t);return vo(e?.text)}function Su(t){if(typeof t!="string")return{};let e=t.trim().toLowerCase(),n=Xh[e];return n?{style:n}:{}}function Kt(t){return t&&typeof t=="object"&&!Array.isArray(t)?t:void 0}function uy(t){return t.startsWith(`${ee}:`)?t:`${ee}:${t}`}import*as vu from"child_process";var Ut=class{tails=new Map;enqueue(e,n,r){let o=this.tails.get(e);o!==void 0&&r?.();let s=(o?.catch(()=>{})??Promise.resolve()).then(()=>n()),a=s.catch(()=>{});return this.tails.set(e,a),a.finally(()=>{this.tails.get(e)===a&&this.tails.delete(e)}),s}clear(){this.tails.clear()}};var Ms=3e4,cy=2e3,py=2e4,ge=4;function Tn(t){return t instanceof Error?t.message:String(t)}function my(){return new Error(`Dispatch timed out after ${Ms}ms`)}function fy(t){if(!(t instanceof Error))return!1;let e=t;return e.killed===!0&&e.signal==="SIGKILL"}var gy={execFile:vu.execFile},Po=class{pendingRetryTimers=new Map;orderedDispatches=new Ut;disposed=!1;clearPendingRetries(){for(let e of this.pendingRetryTimers.values())for(let n of e)clearTimeout(n.timer),n.onCleared?.();this.pendingRetryTimers.clear()}clearRetryTimersForSession(e){let n=this.pendingRetryTimers.get(e);if(n){for(let r of n)clearTimeout(r.timer),r.onCleared?.();this.pendingRetryTimers.delete(e)}}dispose(){this.disposed=!0,this.clearPendingRetries(),this.orderedDispatches.clear()}execute(e,n,r=1){if(!this.disposed){if(r===1&&n.orderingKey){this.enqueueOrderedDispatch(n.orderingKey,o=>this.executeNow(e,n,o,r));return}this.executeNow(e,n,void 0,r)}}executePromise(e,n,r=1){if(!this.disposed){if(r===1&&n.orderingKey){this.enqueueOrderedDispatch(n.orderingKey,o=>this.executePromiseNow(e,n,o,r));return}this.executePromiseNow(e,n,void 0,r)}}executeNow(e,n,r,o=1){if(this.disposed||n.shouldContinue?.()===!1){r?.();return}let i=Date.now();o===1&&n.onStarted?.(),this.log("info","dispatch_started",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge}),gy.execFile("openclaw",e,{timeout:Ms,killSignal:"SIGKILL"},(s,a,l)=>{if(this.disposed){r?.();return}let d=Date.now()-i;if(!s){let m=n.successValidator?.(a??"");if(m?.outcome==="failure"){this.log("error","dispatch_success_validation_failed",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:d,error:m.reason,terminal:!0}),n.onFinalFailure?.(),r?.();return}if(m?.outcome==="skipped"){this.log("info","dispatch_skipped",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:d,reason:m.reason}),n.shouldContinue?.()!==!1&&n.onSkipped?.(m.reason),r?.();return}this.log("info","dispatch_succeeded",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:d}),n.shouldContinue?.()!==!1&&n.onSuccess?.(),r?.();return}let u=l?.trim()?` | stderr: ${l.trim()}`:"";if(n.shouldContinue?.()===!1){r?.();return}if(n.target==="message.send"&&fy(s)){this.log("error","dispatch_failed",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:d,error:`${Tn(s)}${u}`,terminal:!0,ambiguousResult:!0}),n.onAmbiguousResult?.(),r?.();return}if(o>=ge||n.terminalOnFailure===!0){this.log("error","dispatch_failed",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:d,error:`${Tn(s)}${u}`,terminal:!0}),n.onFinalFailure?.(),r?.();return}let p=this.retryDelayMs(o);this.log("error","dispatch_retry_scheduled",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:d,retryDelayMs:p,error:`${Tn(s)}${u}`});let g={timer:setTimeout(()=>{let m=this.pendingRetryTimers.get(n.sessionId);if(m&&(m.delete(g),m.size===0&&this.pendingRetryTimers.delete(n.sessionId)),n.shouldContinue?.()===!1){r?.();return}this.executeNow(e,n,r,o+1)},p),onCleared:r};g.timer.unref?.(),this.pendingRetryTimers.has(n.sessionId)||this.pendingRetryTimers.set(n.sessionId,new Set),this.pendingRetryTimers.get(n.sessionId).add(g)})}executePromiseNow(e,n,r,o=1){if(this.disposed||n.shouldContinue?.()===!1){r?.();return}let i=Date.now();o===1&&n.onStarted?.(),this.log("info","dispatch_started",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge}),this.executePromiseWithTimeout(e).then(()=>{if(this.disposed){r?.();return}let s=Date.now()-i;this.log("info","dispatch_succeeded",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:s}),n.shouldContinue?.()!==!1&&n.onSuccess?.(),r?.()}).catch(s=>{if(this.disposed){r?.();return}let a=Date.now()-i;if(n.shouldContinue?.()===!1){r?.();return}if(o>=ge||n.terminalOnFailure===!0){this.log("error","dispatch_failed",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:a,error:Tn(s),terminal:!0,...n.terminalOnFailure===!0&&o<ge?{terminalReason:"non_retryable"}:{}}),n.onFinalFailure?.(),r?.();return}let l=this.retryDelayMs(o);this.log("error","dispatch_retry_scheduled",{label:n.label,sessionId:n.sessionId,target:n.target,phase:n.phase,messageKind:n.messageKind,route:n.routeSummary,...n.dispatchContext,attempt:o,maxAttempts:ge,elapsedMs:a,retryDelayMs:l,error:Tn(s)});let d={timer:setTimeout(()=>{let u=this.pendingRetryTimers.get(n.sessionId);if(u&&(u.delete(d),u.size===0&&this.pendingRetryTimers.delete(n.sessionId)),n.shouldContinue?.()===!1){r?.();return}this.executePromiseNow(e,n,r,o+1)},l),onCleared:r};d.timer.unref?.(),this.pendingRetryTimers.has(n.sessionId)||this.pendingRetryTimers.set(n.sessionId,new Set),this.pendingRetryTimers.get(n.sessionId).add(d)})}executePromiseWithTimeout(e){return new Promise((n,r)=>{let o=!1,i=setTimeout(()=>{o||(o=!0,r(my()))},Ms);i.unref?.(),Promise.resolve().then(e).then(()=>{o||(o=!0,clearTimeout(i),n())}).catch(s=>{o||(o=!0,clearTimeout(i),r(s))})})}retryDelayMs(e){let n=Math.max(0,e-1),r=cy*2**n;return Math.min(r,py)}enqueueOrderedDispatch(e,n){this.orderedDispatches.enqueue(e,async()=>{this.disposed||await new Promise(r=>{let o=!1;n(()=>{o||(o=!0,r())})})})}log(e,n,r){let o=`[WakeDispatcher] ${JSON.stringify({event:n,...r})}`;if(e==="error"){console.error(o);return}}};Re();var bo=class{resolve(e){let n=$e(e);if(!(!n?.provider||!n.target))return{channel:n.provider,target:n.target,accountId:n.accountId,threadId:n.threadId,sessionKey:n.sessionKey}}summary(e){if(!e)return"system";let n=e.accountId?`|${e.accountId}`:"",r=e.threadId?`#${e.threadId}`:"";return`${e.channel}${n}|${e.target}${r}`}};import{randomUUID as hy}from"crypto";var Ro=class{constructor(e={}){}buildChatSendArgs(e,n,r,o=hy()){return["gateway","call","chat.send","--expect-final","--timeout","30000","--params",JSON.stringify({sessionKey:e,message:n,deliver:r,idempotencyKey:o})]}buildDirectNotificationArgs(e,n,r){let o=wo(r),i=["message","send","--channel",e.channel,"--target",e.target,"--message",n];return e.accountId&&i.push("--account",e.accountId),e.threadId&&i.push("--thread-id",e.threadId),o&&i.push("--presentation",JSON.stringify(o)),i}buildSystemEventArgs(e){return["system","event","--text",e,"--mode","now"]}};function yy(t){let e=ky(t).trim();return e?/^NO_REPLY$/i.test(e)?{outcome:"failure",reason:"completion follow-up wake ended with NO_REPLY"}:{outcome:"success"}:{outcome:"failure",reason:"completion follow-up wake produced no final response"}}function ky(t){let e=t.trim();if(!e)return"";try{return _s(JSON.parse(e)).trim()}catch{return e}}function _s(t){if(typeof t=="string")return t;if(Array.isArray(t))return t.map(r=>_s(r)).filter(Boolean).join(`
248
+ `);if(!t||typeof t!="object")return"";let e=t,n=["final","finalResponse","final_response","assistantFinal","assistant_final","response","text","content"];for(let r of n){let o=e[r];if(typeof o=="string"&&o.trim())return o}for(let r of["result","message","data"]){let o=_s(e[r]);if(o.trim())return o}return""}var Ao=class{routes=new bo;transport;directNotifications;executor=new Po;constructor(e={}){this.transport=e.transport??new Ro(e.transportOptions),this.directNotifications=e.directNotifications===void 0?new So:e.directNotifications}clearPendingRetries(){this.executor.clearPendingRetries()}clearRetryTimersForSession(e){this.executor.clearRetryTimersForSession(e)}dispose(){this.executor.dispose()}buildDispatchContext(e){let n=e.buttons??[],r=n.flat();return{transportRoute:e.routeSummary,transportChannel:e.route?.channel??"system",transportTarget:e.route?.target??"system",transportAccountId:e.route?.accountId,transportThreadId:e.route?.threadId,transportSessionKey:e.route?.sessionKey,messageTextLength:e.text.length,buttonsPresent:r.length>0,buttonRows:n.length||void 0,buttonCount:r.length||void 0,buttonLabels:r.length>0?r.map(o=>o.label):void 0,maxCallbackDataLength:r.length>0?Math.max(...r.map(o=>o.callbackData.length)):void 0}}sendWake(e,n,r,o,i,s,a,l,d,u){let c=this.routes.resolve(e),p=a;if(p?.()===!1)return;let g=c?.sessionKey?.trim();if(!g){this.executor.execute(this.transport.buildSystemEventArgs(n),{label:`${r}-system`,sessionId:e.id,target:"system.event",phase:o,routeSummary:"system",messageKind:"wake",dispatchContext:this.buildDispatchContext({routeSummary:"system",text:n}),onSuccess:s,onSkipped:d,onFinalFailure:i,successValidator:l,shouldContinue:p});return}this.executor.execute(this.transport.buildChatSendArgs(g,n,!0,u),{label:r,sessionId:e.id,target:"chat.send",phase:o,routeSummary:`session:${g}`,messageKind:"wake",dispatchContext:this.buildDispatchContext({routeSummary:`session:${g}`,route:c,text:n}),onSuccess:s,onSkipped:d,successValidator:l,shouldContinue:p,onFinalFailure:()=>{p?.()!==!1&&this.executor.execute(this.transport.buildSystemEventArgs(n),{label:`${r}-fallback`,sessionId:e.id,target:"system.event",phase:o,routeSummary:"system",messageKind:"wake",dispatchContext:this.buildDispatchContext({routeSummary:"system",text:n}),onSuccess:s,onSkipped:d,onFinalFailure:i,successValidator:l,shouldContinue:p})}})}sendUserNotification(e,n,r,o,i,s,a=!1,l){if(l?.()===!1)return;let d=!!o?.some(m=>Array.isArray(m)&&m.length>0),u=this.routes.resolve(e);L("wake_notify_selected",{sessionId:e.id,sessionName:e.name,label:r,messageTextLength:n.length,requireDirectDelivery:a,hasDirectNotificationTransport:!!this.directNotifications,routeSummary:u?this.routes.summary(u):"system",channel:u?.channel,target:u?.target,accountId:u?.accountId,threadId:u?.threadId,sessionKey:u?.sessionKey,...J(o)});let c=u?`notify:${u.channel}|${u.accountId??""}|${u.target}|${u.threadId??""}`:`notify:system:${e.id}`;if(!u){if(L("wake_notify_no_direct_route",{sessionId:e.id,sessionName:e.name,label:r,requireDirectDelivery:a,hasInteractiveButtons:d,...J(o)}),a){`${r}${e.id}`,i?.();return}if(d){`${r}${e.id}`,i?.();return}this.executor.execute(this.transport.buildSystemEventArgs(n),{label:`${r}-notify-system`,sessionId:e.id,target:"system.event",phase:"notify",routeSummary:"system",messageKind:"notify",dispatchContext:this.buildDispatchContext({routeSummary:"system",text:n,buttons:o}),orderingKey:c,onSuccess:s,onFinalFailure:i,shouldContinue:l});return}let p=()=>{if(L("wake_notify_direct_failed",{sessionId:e.id,sessionName:e.name,label:r,requireDirectDelivery:a,hasInteractiveButtons:d,channel:u.channel,target:u.target,accountId:u.accountId,threadId:u.threadId,sessionKey:u.sessionKey,...J(o)}),a){`${r}${e.id}`,i?.();return}if(d){`${r}${e.id}`,i?.();return}this.executor.execute(this.transport.buildSystemEventArgs(n),{label:`${r}-notify-fallback`,sessionId:e.id,target:"system.event",phase:"notify",routeSummary:"system",messageKind:"notify",dispatchContext:this.buildDispatchContext({routeSummary:"system",text:n}),orderingKey:c,onSuccess:s,onFinalFailure:i,shouldContinue:l})},g={label:`${r}-notify`,sessionId:e.id,target:"message.send",phase:"notify",routeSummary:this.routes.summary(u),messageKind:"notify",dispatchContext:this.buildDispatchContext({routeSummary:this.routes.summary(u),route:u,text:n,buttons:o}),orderingKey:c,onSuccess:s,onAmbiguousResult:p,onFinalFailure:p,terminalOnFailure:this.directNotifications?!0:void 0,shouldContinue:l};if(this.directNotifications){L("wake_notify_dispatching_direct_runtime",{sessionId:e.id,sessionName:e.name,label:r,channel:u.channel,target:u.target,accountId:u.accountId,threadId:u.threadId,sessionKey:u.sessionKey,...J(o)}),this.executor.executePromise(()=>this.directNotifications.send(u,n,o),g);return}L("wake_notify_dispatching_cli_message_send",{sessionId:e.id,sessionName:e.name,label:r,channel:u.channel,target:u.target,accountId:u.accountId,threadId:u.threadId,sessionKey:u.sessionKey,...J(o)}),this.executor.execute(this.transport.buildDirectNotificationArgs(u,n,o),g)}sendUserNotificationSequence(e,n,r,o,i,s=!1,a){let l=n.map(u=>({text:u.text.trim(),buttons:u.buttons})).filter(u=>u.text.length>0);if(l.length===0){o?.();return}L("wake_notify_sequence_started",{sessionId:e.id,sessionName:e.name,label:r,chunkCount:l.length,buttonChunkIndexes:l.map((u,c)=>u.buttons?.some(p=>Array.isArray(p)&&p.length>0)?c+1:void 0).filter(u=>typeof u=="number"),requireDirectDelivery:s});let d=u=>{if(a?.()===!1)return;let c=l[u];if(!c){L("wake_notify_sequence_succeeded",{sessionId:e.id,sessionName:e.name,label:r,chunkCount:l.length}),i?.();return}let p=u===0?o:i;L("wake_notify_sequence_chunk_selected",{sessionId:e.id,sessionName:e.name,label:r,chunkIndex:u+1,chunkCount:l.length,messageTextLength:c.text.length,failureHandler:u===0?"all-failed":"sequence-success",...J(c.buttons)}),this.sendUserNotification(e,c.text,`${r}-part-${u+1}`,c.buttons,p,()=>d(u+1),s,a)};d(0)}dispatchSessionNotification(e,n){let r=n.hooks,o=n.wakeMessageOnNotifySuccess!=null||n.wakeMessageOnNotifyFailed!=null,i=n.notifyUser??(n.wakeMessage?"on-wake-fallback":"always"),s=(n.userMessages?.length?n.userMessages:n.userMessage?.trim()?[{text:n.userMessage.trim(),buttons:n.buttons}]:[]).map(u=>({text:u.text.trim(),buttons:u.buttons})).filter(u=>u.text.length>0),a=n.wakeMessage?.trim(),l=n.shouldDispatch,d=n.completionWakeSummaryRequired===!0?yy:void 0;if(o){let u=n.wakeMessageOnNotifySuccess?.trim(),c=n.wakeMessageOnNotifyFailed?.trim(),p=y=>{y&&l?.()!==!1&&(r?.onWakeStarted?.(),this.sendWake(e,y,`${n.label}-wake`,"wake",r?.onWakeFailed,r?.onWakeSucceeded,l,d,r?.onWakeSkipped,n.idempotencyKey))},g=y=>{if(y){if(n.deferConditionalWakeUntilNextTick===!0||n.deferConditionalWakeMs!==void 0){let S=Math.max(0,Math.floor(n.deferConditionalWakeMs??0));setTimeout(()=>p(y),S).unref?.();return}p(y)}},m=()=>{l?.()!==!1&&(r?.onNotifySucceeded?.(),u&&g(u))},f=c?()=>{l?.()!==!1&&(r?.onNotifyFailed?.(),n.onUserNotifyFailed?.(),g(c))}:()=>{l?.()!==!1&&(r?.onNotifyFailed?.(),n.onUserNotifyFailed?.())};if(s.length>0){if(l?.()===!1)return;r?.onNotifyStarted?.(),this.sendUserNotificationSequence(e,s,n.label,f,m,n.requireDirectUserNotification===!0,l)}else f();return}if(i==="always"&&s.length>0){if(l?.()===!1)return;r?.onNotifyStarted?.(),this.sendUserNotificationSequence(e,s,n.label,()=>{l?.()!==!1&&(r?.onNotifyFailed?.(),n.onUserNotifyFailed?.())},()=>{l?.()!==!1&&r?.onNotifySucceeded?.()},n.requireDirectUserNotification===!0,l)}if(a&&l?.()!==!1){if(r?.onWakeStarted?.(),i==="on-wake-fallback"&&s.length>0&&!this.routes.resolve(e)?.sessionKey){if(l?.()===!1)return;r?.onNotifyStarted?.(),this.sendUserNotificationSequence(e,s,n.label,()=>{l?.()!==!1&&(r?.onNotifyFailed?.(),n.onUserNotifyFailed?.())},()=>{l?.()!==!1&&r?.onNotifySucceeded?.()},!1,l)}this.sendWake(e,a,`${n.label}-wake`,"wake",r?.onWakeFailed,r?.onWakeSucceeded,l,d,r?.onWakeSkipped,n.idempotencyKey)}}};var wu=36,Pu=2,bu="...";function Sy(t){let e=Array.from(t);return e.length<=wu?t:`${e.slice(0,wu-bu.length).join("")}${bu}`}var Io=class{constructor(e,n){this.actionTokens=e;this.isGitHubCliAvailable=n}actionTokens;isGitHubCliAvailable;createActionToken(e,n,r={}){return this.actionTokens.createActionToken(e,n,{expiresAt:Date.now()+10080*60*1e3,...r})}consumeActionToken(e){return this.actionTokens.consumeActionToken(e)}getActionToken(e){return this.actionTokens.getActionToken(e)}listActiveActionTokens(e){return this.actionTokens.listActiveActionTokens(e)}clearRepoPolicyChoiceTokens(e){this.actionTokens.deleteActionTokensForSessionByKind(e,"repo-policy-set")}clearPlanDecisionTokens(e,n){this.actionTokens.deletePlanDecisionTokensForSession(e,n)}makeActionButton(e,n,r,o={}){let i=this.createActionToken(e,n,{label:r,...o});return{label:r,callbackData:i.id,style:this.resolveButtonStyle(n)}}resolveButtonStyle(e){switch(e){case"plan-approve":case"worktree-create-pr":case"worktree-update-pr":case"plan-offer-start":case"repo-policy-set":return"primary";case"worktree-merge":case"session-resume":case"session-restart":return"success";case"plan-reject":case"worktree-dismiss":return"danger";default:return"secondary"}}getWorktreeDecisionButtons(e,n,r={merge:!0,pr:!0}){if(!n)return[];let o=[],i=[];if(r.merge&&i.push(this.makeActionButton(e,"worktree-merge","Merge")),r.pr&&this.isGitHubCliAvailable())n.worktreePrUrl?(i.push(this.makeActionButton(e,"worktree-view-pr","View PR",{targetUrl:n.worktreePrUrl})),i.length>0&&o.push(i),o.push([this.makeActionButton(e,"worktree-update-pr","Sync PR"),this.makeActionButton(e,"worktree-decide-later","Later")])):(i.push(this.makeActionButton(e,"worktree-create-pr","Open PR")),i.length>0&&o.push(i),o.push([this.makeActionButton(e,"worktree-decide-later","Later"),this.makeActionButton(e,"worktree-dismiss","Discard")]));else return o.push([...i,this.makeActionButton(e,"worktree-decide-later","Later")]),o.push([this.makeActionButton(e,"worktree-dismiss","Discard")]),o;return n.worktreePrUrl&&o.push([this.makeActionButton(e,"worktree-dismiss","Discard")]),o}getPlanApprovalButtons(e,n){let r=n?.actionablePlanDecisionVersion??n?.planDecisionVersion;this.clearPlanDecisionTokens(e,r);let o=[[this.makeActionButton(e,"plan-approve","Approve",{planDecisionVersion:r}),this.makeActionButton(e,"plan-request-changes","Revise",{planDecisionVersion:r}),this.makeActionButton(e,"plan-reject","Reject",{planDecisionVersion:r})]];return L("plan_approval_buttons_created",{sessionId:e,planDecisionVersion:r,...J(o)}),o}getResumeButtons(e,n){let r=[];return n.isExplicitlyResumable&&r.push(this.makeActionButton(e,"session-resume","Resume")),r.push(this.makeActionButton(e,"view-output","View output")),[r]}getQuestionButtons(e,n,r={}){if(n.length===0)return;let o=n.map((s,a)=>{let l=this.createActionToken(e,"question-answer",{label:s.label,optionIndex:a,pendingInputRequestId:r.requestId,pendingInputQuestionId:r.questionId});return{label:Sy(s.label),callbackData:l.id,style:this.resolveButtonStyle("question-answer")}}),i=[];for(let s=0;s<o.length;s+=Pu)i.push(o.slice(s,s+Pu));return i}getPlanOfferButtons(e){let{offerId:n,route:r,planName:o,planPrompt:i,planWorkdir:s,planWorktreeStrategy:a}=e,l=[[this.makeActionButton(n,"plan-offer-start","Start Plan",{route:r,launchName:o,launchPrompt:i,launchWorkdir:s,launchWorktreeStrategy:a}),this.makeActionButton(n,"plan-offer-dismiss","Dismiss",{route:r})]];return L("plan_offer_buttons_created",{offerId:n,planName:o,channel:r.provider,target:r.target,accountId:r.accountId,threadId:r.threadId,sessionKey:r.sessionKey,planPromptLength:i.length,planWorkdirLength:s.length,planWorktreeStrategy:a,...J(l)}),l}getRepoPolicyChoiceButtons(e){let n=hn(e.prAvailable??!0),r=Array.from({length:Math.ceil(n.length/2)},(o,i)=>n.slice(i*2,i*2+2)).map(o=>o.map(i=>this.makeActionButton(e.choiceId,"repo-policy-set",i.label,{route:e.route,repoPolicy:i.policy,repoPolicyWorkdir:e.repoRoot,launchName:e.launchName,launchPrompt:e.launchPrompt,launchWorkdir:e.launchWorkdir,launchModel:e.launchModel,launchReasoningEffort:e.launchReasoningEffort,launchFastMode:e.launchFastMode,launchSystemPrompt:e.launchSystemPrompt,launchAllowedTools:e.launchAllowedTools,launchResumeSessionId:e.launchResumeSessionId,launchResumeWorktreeFrom:e.launchResumeWorktreeFrom,launchSessionIdOverride:e.launchSessionIdOverride,launchClearedPersistedCodexResume:e.launchClearedPersistedCodexResume,launchForkSession:e.launchForkSession,launchForceNewSession:e.launchForceNewSession,launchPermissionMode:e.launchPermissionMode,launchPlanApproval:e.launchPlanApproval,launchHarness:e.launchHarness,launchWorktreeStrategy:e.launchWorktreeStrategy,launchWorktreeBaseBranch:e.launchWorktreeBaseBranch,launchWorktreePrTargetRepo:e.launchWorktreePrTargetRepo,launchOriginAgentId:e.launchOriginAgentId})));return L("repo_policy_choice_buttons_created",{choiceId:e.choiceId,repoRoot:e.repoRoot,channel:e.route.provider,target:e.route.target,accountId:e.route.accountId,threadId:e.route.threadId,sessionKey:e.route.sessionKey,labels:n.map(o=>o.label),...J(r)}),r}};X();Re();import{createHash as by}from"crypto";var vy="duplicate notification already delivered or in flight",xo=class{maxRecords;inFlightTtlMs;now;inFlight=new Set;delivered=new Set;constructor(e={}){this.maxRecords=Math.max(1,Math.floor(e.maxRecords??64)),this.inFlightTtlMs=Math.max(1,Math.floor(e.inFlightTtlMs??6e5)),this.now=e.now??(()=>new Date)}claim(e,n,r){if(!e)return{allowed:!0};let o=this.now(),i=this.prune(n??[],o),s=i.find(a=>a.key===e);return this.delivered.has(e)||this.inFlight.has(e)||s?.status==="delivered"||s?.status==="in_flight"&&this.isFreshInFlight(s,o)?{allowed:!1,records:i,reason:vy}:(this.inFlight.add(e),this.delivered.delete(e),{allowed:!0,records:this.upsert(i,{key:e,status:"in_flight",recordedAt:o.toISOString(),label:r})})}deliveredRecords(e,n,r){if(!e)return;let o=this.now();return this.inFlight.delete(e),this.delivered.add(e),this.upsert(this.prune(n??[],o),{key:e,status:"delivered",recordedAt:o.toISOString(),label:r})}releasedRecords(e,n){if(!e)return;let r=this.now();return this.inFlight.delete(e),this.prune(n??[],r).filter(o=>!(o.key===e&&o.status==="in_flight"))}prune(e,n){let r=e.filter(o=>o.status==="delivered"?!0:this.isFreshInFlight(o,n));return r.slice(Math.max(0,r.length-this.maxRecords))}isFreshInFlight(e,n){let r=Date.parse(e.recordedAt);return Number.isFinite(r)?n.getTime()-r<this.inFlightTtlMs:!1}upsert(e,n){let o=[...e.filter(i=>i.key!==n.key),n];return o.slice(Math.max(0,o.length-this.maxRecords))}};Re();X();Re();import{createHash as wy}from"crypto";var Py=1024,Cn="duplicate completion follow-up wake already handled",To="prior human-visible summary already delivered",Co=class{inFlight=new Set;completed=new Map;claimKeysByPrimary=new Map;maxCompletedKeys;constructor(e={}){this.maxCompletedKeys=Math.max(1,Math.floor(e.maxCompletedKeys??Py))}decide(e,n,r){if(n?.required!==!0)return{required:!1,allowed:!1,explicit:!1};let o=this.buildKeySet(e,n);if(!o)return{required:!0,allowed:!0,explicit:!1};let i=this.normalizeRecords(r),s=this.buildPersistedKeyMap(i),a=o.decisionKeys.find(u=>this.inFlight.has(u)||!!this.getCompletedRecord(u)||s.has(u)),l=a?this.getCompletedRecord(a):void 0,d=a?s.get(a):void 0;return a?{required:!0,allowed:!1,explicit:o.explicit,dedupeKey:o.primary,skipReason:l?.skipReason??d?.skipReason??Cn}:(this.registerClaim(o.primary,o.claimKeys),{required:!0,allowed:!0,key:o.primary,explicit:o.explicit})}recordVisibleDelivery(e,n,r,o){if(n.required!==!0)return{required:!1,allowed:!1,explicit:!1};let i=this.buildKeySet(e,n);if(!i)return{required:!0,allowed:!0,explicit:!1};let s=this.normalizeRecords(r),a=this.buildPersistedKeyMap(s),l=i.decisionKeys.find(p=>!!this.getCompletedRecord(p)||a.has(p)),d=l?this.getCompletedRecord(l):void 0,u=l?a.get(l):void 0;if(d||u)return{required:!0,allowed:!1,explicit:i.explicit,dedupeKey:i.primary,skipReason:d?.skipReason??u?.skipReason};this.finishKeys(i.primary,i.claimKeys,!0,To);let c=this.deliveredRecords(i.claimKeys,s,o,To);return{required:!0,allowed:!0,key:i.primary,explicit:i.explicit,records:c}}finish(e,n,r=Cn){if(!e)return;let o=this.claimKeysByPrimary.get(e)??[e];this.finishKeys(e,o,n,r)}completionRecordsAfterDelivery(e,n,r,o=Cn){if(!e)return;let i=this.claimKeysByPrimary.get(e)??[e];return this.deliveredRecords(i,n,r,o)}registerClaim(e,n){for(let r of n)this.inFlight.add(r);for(this.claimKeysByPrimary.delete(e),this.claimKeysByPrimary.set(e,n);this.claimKeysByPrimary.size>this.maxCompletedKeys;){let r=this.claimKeysByPrimary.keys().next().value;if(r===void 0)break;let o=this.claimKeysByPrimary.get(r)??[r];for(let i of o)this.inFlight.delete(i);this.claimKeysByPrimary.delete(r)}}finishKeys(e,n,r,o=Cn){for(let i of n)this.inFlight.delete(i);if(this.claimKeysByPrimary.delete(e),!!r){for(let i of n)this.completed.get(i)?.skipReason===To&&o!==To||(this.completed.delete(i),this.completed.set(i,{skipReason:o,linkedKeys:n.filter(a=>a!==i)}));for(;this.completed.size>this.maxCompletedKeys;){let i=this.completed.keys().next().value;if(i===void 0)break;this.completed.delete(i)}}}buildKeySet(e,n){let r=this.getDeliveryRef(e);if(!r)return;let o=this.normalizeOutcomeKey(e,n.outcomeKey?.trim());if(o){let a=`${this.buildVisibleScope(r,e)}:outcome:${this.digest(o)}`,l=this.isGoalLike(e,n,o),d=this.buildSessionAliasKeys(r,e,"visible-summary"),u=this.buildSessionAliasKeys(r,e,"goal-summary"),c=this.isTerminalLike(n,o),p=o.startsWith("worktree-pr:")?this.normalizeWorktreePrOutcome(n.outcomeKey?.trim()):void 0,g=p?.aliases.map(m=>`${this.buildVisibleScope(r,e)}:outcome:${this.digest(m)}`)??[];return{primary:a,explicit:!0,claimKeys:[...d,...l?u:[],...g,a],decisionKeys:[a,...p?.blocksAliases?g:[],...l||c?d:[],...u]}}let i=n.fallbackFingerprint?.trim();if(!i)return;let s=`${r}:${n.producer}:${this.digest(i)}`;return{primary:s,explicit:!1,claimKeys:[s],decisionKeys:[s]}}isGoalLike(e,n,r){return!!e.goalTaskId?.trim()||n.producer==="goal"||/^goal:/i.test(r)}isTerminalLike(e,n){return e.producer==="terminal"||/^terminal:/i.test(n)}normalizeOutcomeKey(e,n){let r=e.goalTaskId?.trim();if(r)return`goal:${r}`;let o=this.normalizeWorktreePrOutcome(n);return o?o.primary:n}normalizeWorktreePrOutcome(e){if(!e)return;let n=e.split(":");if(n[0]!=="worktree-pr"||n.length<5)return;let r=n[1]?.trim().toLowerCase();if(!r||!/^(?:draft-)?(?:opened|updated)$/.test(r))return;let o=n[2]?.trim()||"default-repo",i=n[3]?.trim();if(!i)return;let s=this.normalizePrIdentity(i),a=n[4]?.trim();if(!s||!a)return;let l=["worktree-pr",o.toLowerCase(),s,a].join(":"),d=`${l}:created`;if(r.endsWith("updated")){let u=n.slice(5).join(":").trim();return{primary:u?`${l}:updated:${u}`:`${l}:updated`,aliases:[d,l],blocksAliases:!1}}return{primary:d,aliases:[l],blocksAliases:!0}}normalizePrIdentity(e){let n=e.match(/#?(\d+)$/);if(n?.[1])return`#${n[1]}`;let r=e.match(/\/pull\/(\d+)(?:\b|\/|$)/);if(r?.[1])return`#${r[1]}`;let o=e.trim();return o||void 0}buildVisibleScope(e,n){let r=$e(n);return r?`route:${this.digest(JSON.stringify({provider:r.provider,accountId:r.accountId,target:r.target,threadId:r.threadId}))}`:e}buildSessionAliasKeys(e,n,r){let o=this.buildVisibleScope(e,n),i=["id"in n?n.id:void 0,"sessionId"in n?n.sessionId:void 0,n.name,$(n),n.harnessSessionId,e].map(s=>s?.trim()).filter(s=>!!s);return[...new Set(i)].map(s=>`${o}:session:${this.digest(s)}:${r}`)}getDeliveryRef(e){return U(e)??$(e)??""}digest(e){return wy("sha256").update(e).digest("hex").slice(0,16)}normalizeRecords(e){return e?.length?e.filter(n=>n.key.trim()&&Number.isFinite(Date.parse(n.recordedAt))).slice(-this.maxCompletedKeys):[]}buildPersistedKeyMap(e){let n=new Map;for(let r of e){n.set(r.key,r);for(let o of r.linkedKeys??[])o.trim()&&n.set(o,r)}return n}getCompletedRecord(e){let n=this.completed.get(e);if(n)return n;for(let r of this.completed.values())if(r.linkedKeys?.includes(e))return r}deliveredRecords(e,n,r,o=Cn){let i=new Date().toISOString(),s=this.normalizeRecords(n),a=new Set(e),d=[...s.filter(u=>!a.has(u.key)&&!(u.linkedKeys??[]).some(c=>a.has(c))),...e.map(u=>{let c=e.filter(p=>p!==u);return{key:u,linkedKeys:c.length>0?c:void 0,recordedAt:i,label:r,skipReason:o}})];return d.slice(Math.max(0,d.length-this.maxCompletedKeys))}};var Ry=2e3,Ay=new Set(["1","true","yes","on"]);function Iy(){let t=process.env.OPENCLAW_CODE_AGENT_NOTIFICATION_DIAGNOSTICS?.trim().toLowerCase();return!!(t&&Ay.has(t))||Ji()}function xy(t){Iy()&&process.stderr.write(`[SessionNotification] ${JSON.stringify(t)}
249
+ `)}var Mo=class{constructor(e,n,r={}){this.wakeDispatcher=e;this.applyPersistedPatch=n;this.completionSummaries=new Co({maxCompletedKeys:r.maxCompletedCompletionWakeKeys}),this.notificationDedupe=new xo({maxRecords:r.maxNotificationDedupeRecords}),this.getPersistedSession=r.getPersistedSession}wakeDispatcher;applyPersistedPatch;completionSummaries;notificationDedupe;getPersistedSession;dispatch(e,n){let r=this.getDeliveryRef(e),o=this.getPersistedSession?.(r),i=this.buildNotificationDedupeKey(e,n),s=this.notificationDedupe.claim(i,o?.notificationDedupe,n.label);if(s.records&&this.applyNotificationDedupePatch(r,s.records),!s.allowed){this.logNotificationDecision({session:e,request:n,deliveryRef:r,dedupeKey:i,decision:"skip",reason:s.reason??"duplicate notification skipped",deliveryPath:"notify"}),n.hooks?.onDuplicateSkipped?.(s.reason??"duplicate notification skipped");return}let a=this.buildCompletionSummaryFact(n),l=n.completionSummaryOwner==="foreground"&&a?.required===!0,d=l?this.completionSummaries.recordVisibleDelivery(e,a,o?.completionSummaryDedupe,n.label):this.completionSummaries.decide(e,a,o?.completionSummaryDedupe);d.records&&this.applyCompletionSummaryDedupePatch(r,d.records);let u=l?this.withoutCompletionWake(n):n;if(d.required&&!d.allowed)if(this.logNotificationDecision({session:e,request:n,deliveryRef:r,dedupeKey:d.dedupeKey??d.key,outcomeKey:a?.outcomeKey,decision:l?"skip":d.explicit?"send_without_followup":"skip",reason:d.skipReason??"completion follow-up wake suppressed",deliveryPath:l?"foreground-summary":"wake",followupKind:a?.producer}),n.hooks?.onWakeSkipped?.(d.skipReason??"completion follow-up wake suppressed"),l){this.releaseNotificationDedupe(r,i);return}else if(d.explicit)u=this.withoutCompletionWake(n);else{this.releaseNotificationDedupe(r,i);return}a?.required===!0&&this.logNotificationDecision({session:e,request:u,deliveryRef:r,dedupeKey:d.dedupeKey??d.key,outcomeKey:a.outcomeKey,decision:l?"record_visible":u.completionWakeSummaryRequired===!0?"send_with_followup":"send_without_followup",reason:l?"foreground summary owns completion follow-up":void 0,deliveryPath:l?"foreground-summary":"wake",followupKind:a.producer});let c=this.buildCompletionWakePatch(u),p=!!(u.wakeMessage?.trim()||u.wakeMessageOnNotifySuccess?.trim()),g=!!(u.wakeMessage?.trim()||u.wakeMessageOnNotifyFailed?.trim()),m=!1,f=!1,y=()=>{f||(f=!0,m||(this.releaseNotificationDedupe(r,i),m=!0),this.completionSummaries.finish(d.key,!1))},S=u.shouldDispatch?()=>{let I=u.shouldDispatch?.()!==!1;return I||y(),I}:void 0,R={onNotifyStarted:()=>{this.applyDeliveryState(r,"notifying"),u.hooks?.onNotifyStarted?.()},onNotifySucceeded:()=>{m=!0,this.markNotificationDedupeDelivered(r,i,u.label),this.applyNotifyDeliveryState(r,p?"wake_pending":"idle",p?c:void 0),p||this.completionSummaries.finish(d.key,!1),u.hooks?.onNotifySucceeded?.()},onNotifyFailed:()=>{this.applyNotifyDeliveryState(r,g?"wake_pending":"failed",g?c:void 0),g||(this.completionSummaries.finish(d.key,!1),this.releaseNotificationDedupe(r,i),m=!0),u.hooks?.onNotifyFailed?.()},onWakeStarted:()=>{this.applyPersistedPatchWithCompletionWake(r,"wake_pending",c,{completionWakeIssuedAt:new Date().toISOString(),completionWakeSucceededAt:void 0,completionWakeFailedAt:void 0,completionWakeSkippedAt:void 0,completionWakeSkipReason:void 0}),u.hooks?.onWakeStarted?.()},onWakeSucceeded:()=>{m=!0,this.markNotificationDedupeDelivered(r,i,u.label),this.markCompletionSummaryDelivered(r,d.key,u.label),this.applyPersistedPatchWithCompletionWake(r,"idle",this.buildCompletionWakeSucceededPatch(c),{completionWakeSucceededAt:new Date().toISOString(),completionWakeFailedAt:void 0,completionWakeSkippedAt:void 0,completionWakeSkipReason:void 0}),this.completionSummaries.finish(d.key,!0),u.hooks?.onWakeSucceeded?.()},onWakeSkipped:I=>{if(f){u.hooks?.onWakeSkipped?.(I);return}m=!0,this.markNotificationDedupeDelivered(r,i,u.label),this.markCompletionSummaryDelivered(r,d.key,u.label,I),this.applyPersistedPatchWithCompletionWake(r,"idle",this.buildCompletionWakeSucceededPatch(c),{completionWakeSucceededAt:void 0,completionWakeFailedAt:void 0,completionWakeSkippedAt:new Date().toISOString(),completionWakeSkipReason:I}),this.completionSummaries.finish(d.key,!0),u.hooks?.onWakeSkipped?.(I)},onWakeFailed:()=>{this.applyPersistedPatchWithCompletionWake(r,"failed",c,{completionWakeFailedAt:new Date().toISOString()}),this.completionSummaries.finish(d.key,!1),this.releaseNotificationDedupe(r,i),m=!0,u.hooks?.onWakeFailed?.()}};this.wakeDispatcher.dispatchSessionNotification(e,{...u,idempotencyKey:i??u.idempotencyKey,shouldDispatch:S,hooks:R})}notifyWorktreeOutcome(e,n,r={}){let o=this.getDeliveryRef(e),i=d=>Ft({sessionId:o,sessionName:e.name,outcomeLine:n,originThreadLine:Jt(e),detailLines:r.detailLines,canonicalStatusDelivered:d}),s=r.summaryWakeRequired??!0,a={required:s,producer:"worktree-pr",outcomeKey:r.completionWakeOutcomeKey??`terminal:${o}`},l=r.completionSummaryOwner!=="foreground";if(s&&!l){let d=this.getDeliveryRef(e),u=this.completionSummaries.recordVisibleDelivery(e,a,d?this.getPersistedSession?.(d)?.completionSummaryDedupe:void 0,"worktree-outcome");u.records&&this.applyCompletionSummaryDedupePatch(d,u.records)}this.dispatch(e,{label:"worktree-outcome",userMessage:n,notifyUser:"always",requireDirectUserNotification:!0,completionSummary:{...a,required:s&&l},completionWakeSummaryRequired:s&&l,completionWakeOutcomeKey:r.completionWakeOutcomeKey??`terminal:${o}`,idempotencyKey:`worktree-outcome:${r.completionWakeOutcomeKey??n}`,deferConditionalWakeUntilNextTick:!0,deferConditionalWakeMs:Ry,wakeMessageOnNotifySuccess:s&&l?i(!0):void 0,wakeMessageOnNotifyFailed:s&&l?i(!1):void 0})}dispose(){this.wakeDispatcher.dispose()}getDeliveryRef(e){return U(e)??$(e)??""}applyDeliveryState(e,n){!e||!n||this.applyPersistedPatch(e,{deliveryState:n})}applyNotifyDeliveryState(e,n,r){!e||!n||this.applyPersistedPatch(e,r?{deliveryState:n,...r}:{deliveryState:n})}applyPersistedPatchWithCompletionWake(e,n,r,o){!e||!n||this.applyPersistedPatch(e,r?{deliveryState:n,...r,...o}:{deliveryState:n})}buildCompletionWakePatch(e){if(e.completionWakeSummaryRequired===!0)return{completionWakeSummaryRequired:!0}}buildCompletionWakeSucceededPatch(e){if(e)return{completionWakeSummaryRequired:void 0}}withoutCompletionWake(e){return{...e,completionSummary:e.completionSummary?{...e.completionSummary,required:!1}:void 0,wakeMessage:void 0,wakeMessageOnNotifySuccess:void 0,wakeMessageOnNotifyFailed:void 0,completionWakeSummaryRequired:!1}}buildCompletionSummaryFact(e){if(e.completionSummary)return e.completionSummary;if(e.completionWakeSummaryRequired!==!0)return;let n=[e.wakeMessage,e.wakeMessageOnNotifySuccess,e.wakeMessageOnNotifyFailed].map(r=>r?.trim()).filter(r=>!!r);return{required:!0,producer:"legacy",outcomeKey:e.completionWakeOutcomeKey,fallbackFingerprint:n.length>0?`${e.label}
248
250
  ${n.join(`
249
251
  ---completion-wake---
250
- `)}`:void 0}}buildNotificationDedupeKey(e,n){let r=n.idempotencyKey?.trim();if(!r)return;let o=this.getDeliveryRef(e);if(!o)return;let i=_e(e),s=i?{provider:i.provider,accountId:i.accountId,target:i.target,threadId:i.threadId}:{deliveryRef:o};return`notification:${this.digest(JSON.stringify({scope:s,semanticKey:r}))}`}markNotificationDedupeDelivered(e,n,r){let o=this.notificationDedupe.deliveredRecords(n,e?this.getPersistedSession?.(e)?.notificationDedupe:void 0,r);o&&this.applyNotificationDedupePatch(e,o)}releaseNotificationDedupe(e,n){let r=this.notificationDedupe.releasedRecords(n,e?this.getPersistedSession?.(e)?.notificationDedupe:void 0);r&&this.applyNotificationDedupePatch(e,r)}applyNotificationDedupePatch(e,n){this.getPersistedSession&&e&&this.applyPersistedPatch(e,{notificationDedupe:n})}markCompletionSummaryDelivered(e,n,r,o){let i=this.completionSummaries.completionRecordsAfterDelivery(n,e?this.getPersistedSession?.(e)?.completionSummaryDedupe:void 0,r,o);i&&this.applyCompletionSummaryDedupePatch(e,i)}applyCompletionSummaryDedupePatch(e,n){this.getPersistedSession&&e&&this.applyPersistedPatch(e,{completionSummaryDedupe:n})}logNotificationDecision(e){let n=_e(e.session);uy({event:"oca_notification_decision",sessionId:"id"in e.session?e.session.id:e.session.sessionId,sessionName:e.session.name,harnessSessionId:e.session.harnessSessionId,originRoute:n?{provider:n.provider,accountId:n.accountId,target:n.target,threadId:n.threadId,sessionKey:n.sessionKey}:void 0,outcomeType:e.outcomeKey?.split(":").slice(0,2).join(":")??e.request.label,notificationKind:e.request.label,followupKind:e.followupKind,dedupeKey:e.dedupeKey,deliveryPath:e.deliveryPath,decision:e.decision,reason:e.reason,completionWakeSummaryRequired:e.request.completionWakeSummaryRequired,deliveryRef:e.deliveryRef})}digest(e){return sy("sha256").update(e).digest("hex").slice(0,16)}};ye();import{existsSync as cy}from"fs";var xo=class{getCompletionState(e,n,r,o){let i=cn(e,r,o);if(i===void 0)return"has-commits";if(i===0){let s=cn(e,o,r);return s===void 0?"has-commits":s>0?It(e,r,o)?"merged":"base-advanced":nt(n)?"dirty-uncommitted":"no-change"}return nt(n)?"dirty-uncommitted":mr(e,r,o)?"released":"has-commits"}isResolvedWorktreeEligibleForCleanup(e,n,r){if(!e.worktreePath||!e.workdir||!cy(e.worktreePath)||e.pendingWorktreeDecisionSince||e.worktreeState==="pending_decision")return!1;let o=e.worktreeMergedAt??e.worktreeDismissedAt??e.completedAt??e.createdAt,i=typeof o=="string"?new Date(o).getTime():Number(o??0);return!!i&&n-i>=r}};import{randomUUID as py}from"node:crypto";function my(t){let e=t.pendingInputState,n=e?.activeQuestionIndex??0;return e?.questions?.[n]?.id??(e?.activeQuestionIndex!=null?`q${e.activeQuestionIndex}`:void 0)}var To=class{constructor(e,n,r,o){this.pendingQuestions=e;this.dispatchSessionNotification=n;this.clearWaitingTimestamp=r;this.getQuestionButtons=o}pendingQuestions;dispatchSessionNotification;clearWaitingTimestamp;getQuestionButtons;async handleAskUserQuestion(e,n){let i=n?.questions??[];if(i.length===0)throw new Error("AskUserQuestion: no questions in input");let s=i[0],l=s.options??[],a=`❓ [${e.name}] ${s.question}`,d=my(e),u=e.pendingInputState?.requestId??`legacy:${py()}`,c=this.getQuestionButtons(e.id,l,{requestId:u,questionId:d}),m=[`[ASK USER QUESTION] Session "${e.name}" has a question requiring user input.`,"",`Question: ${s.question}`,...l.length>0?["Options:",...l.map((p,f)=>` ${f+1}. ${p.label}`)]:[],"",`Send the question to the user and call agent_respond(session="${e.id}", message="<answer>") with their answer.`].join(`
251
- `);return new Promise((p,f)=>{let h=this.pendingQuestions.get(e.id);h&&(clearTimeout(h.timeoutHandle),h.reject(new Error(`AskUserQuestion superseded by a newer question for session "${e.name}".`)));let k=setTimeout(()=>{this.pendingQuestions.delete(e.id),f(new Error(`AskUserQuestion timed out after ${6e5/1e3}s for session "${e.name}"`))},6e5);k.unref?.(),this.pendingQuestions.set(e.id,{resolve:p,reject:f,questions:i,timeoutHandle:k,requestId:u,questionId:d}),this.dispatchSessionNotification(e,{label:"ask-user-question",idempotencyKey:`ask-user-question:${e.id}:${u}`,userMessage:a,notifyUser:"always",buttons:c,wakeMessageOnNotifySuccess:["AskUserQuestion delivered to the user.",`Session: ${e.name} | ID: ${e.id}`,`Question: ${s.question}`,"Await their selection — do NOT answer this question yourself."].join(`
252
- `),wakeMessageOnNotifyFailed:m})})}resolveAskUserQuestion(e,n,r={}){let o=this.pendingQuestions.get(e);if(!o)return`${e}`,!1;if(r.requestId&&r.requestId!==o.requestId)return`${e}${o.requestId}${r.requestId}`,!1;if(r.questionId&&r.questionId!==o.questionId)return`${e}${o.questionId??""}${r.questionId}`,!1;let i=o.questions[0],s=i.options??[],l=s[n];return l?(clearTimeout(o.timeoutHandle),this.pendingQuestions.delete(e),this.clearWaitingTimestamp(e),o.resolve({behavior:"allow",updatedInput:{questions:o.questions,answers:{[i.question]:l.label}}}),!0):(`${n}${e}${s.length}`,!1)}dispose(){for(let e of this.pendingQuestions.values())clearTimeout(e.timeoutHandle),e.reject(new Error("SessionManager disposed before AskUserQuestion resolved."));this.pendingQuestions.clear()}};Z();mn();var fy=new Set(["merged","released","dismissed","none","cleanup_failed"]),gy=new Set(["merged","released","dismissed","no_change","none","cleanup_failed"]),Co=class t{constructor(e,n,r,o){this.buildRoutingProxy=e;this.dispatchNotification=n;this.updatePersistedSession=r;this.getWorktreeDecisionButtons=o}buildRoutingProxy;dispatchNotification;updatePersistedSession;getWorktreeDecisionButtons;static REMINDER_THRESHOLD_MS=10800*1e3;static REMINDER_INTERVAL_MS=10800*1e3;getNextReminderAt(e){let n=new Date(e.pendingWorktreeDecisionSince).getTime();if(this.getWorktreeDecisionReminderStatus(e,n)!=="pending")return;let r=[n+t.REMINDER_THRESHOLD_MS];if(e.worktreeDecisionSnoozedUntil){let o=new Date(e.worktreeDecisionSnoozedUntil).getTime();Number.isFinite(o)&&r.push(o)}if(e.lastWorktreeReminderAt){let o=new Date(e.lastWorktreeReminderAt).getTime();Number.isFinite(o)&&r.push(o+t.REMINDER_INTERVAL_MS)}return Math.max(...r)}sendReminderIfDue(e,n=Date.now()){this.clearResolvedReminderState(e);let r=this.getNextReminderAt(e);if(r==null||r>n)return!1;let o=n-new Date(e.pendingWorktreeDecisionSince).getTime(),i=Math.floor(Math.max(0,o)/(3600*1e3));try{this.sendReminderNotification(e,i)}catch(s){return`${e.name}${s instanceof Error?s.message:String(s)}`,!1}for(let s of pe(e))this.updatePersistedSession(s,{lastWorktreeReminderAt:new Date(n).toISOString()});return!0}sendReminderNotification(e,n){let r=this.buildRoutingProxy({id:e.sessionId??e.name??$(e)??e.harnessSessionId,sessionId:e.sessionId,harnessSessionId:e.harnessSessionId,backendRef:e.backendRef,route:e.route});if(e.worktreeStrategy==="delegate"){this.dispatchNotification(r,{label:`worktree-stale-reminder-${e.name}`,wakeMessage:is(e,n),notifyUser:"never"});return}let o=[`⏰ Reminder: branch \`${e.worktreeBranch??"unknown"}\` is still waiting for a merge decision.`,`Session: ${e.name} | Pending: ${n}h`,"",`agent_merge(session="${e.name}") or agent_pr(session="${e.name}") or agent_worktree_cleanup() to resolve.`].join(`
253
- `);this.dispatchNotification(r,{label:`worktree-stale-reminder-${e.name}`,userMessage:o,notifyUser:"always",buttons:this.getWorktreeDecisionButtons(U(e)??e.harnessSessionId,e)})}clearResolvedReminderState(e){if(!e.pendingWorktreeDecisionSince&&!e.lastWorktreeReminderAt&&!e.worktreeDecisionSnoozedUntil||!this.isResolvedWorktreeDecision(e))return!1;let n=!1;for(let r of pe(e))n=this.updatePersistedSession(r,{pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0})||n;return n}getWorktreeDecisionReminderStatus(e,n){if(this.hasResolvedWorktreeDecisionMarker(e))return"resolved";if(!e.pendingWorktreeDecisionSince)return"inactive";let r=n??new Date(e.pendingWorktreeDecisionSince).getTime();if(!Number.isFinite(r))return"inactive";let o=e.worktreeState==="pending_decision"||e.lifecycle==="awaiting_worktree_decision"||e.worktreeLifecycle?.state==="pending_decision",i=e.worktreeState==null&&e.lifecycle==null&&e.worktreeLifecycle?.state==null&&!e.worktreeMerged&&!e.worktreePrUrl;if(!o&&!i)return"inactive";let s=Ve(e,{activeSession:!1,includePrSync:!1});return this.isResolvedDerivedWorktreeState(s.derivedState)?"resolved":"pending"}isResolvedWorktreeDecision(e){if(this.hasResolvedWorktreeDecisionMarker(e))return!0;let n=Ve(e,{activeSession:!1,includePrSync:!1});return this.isResolvedDerivedWorktreeState(n.derivedState)}hasResolvedWorktreeDecisionMarker(e){return!!(e.worktreeMerged||e.worktreePrUrl||e.lifecycle==="terminal"||e.worktreeState&&fy.has(e.worktreeState)||e.worktreeLifecycle?.state&&gy.has(e.worktreeLifecycle.state))}isResolvedDerivedWorktreeState(e){return e==="merged"||e==="released"||e==="no_change"||e==="cleanup_failed"}};ye();Z();be();function Tn(t,e){return e!=null&&t.approvalPromptRequiredVersion===e&&hy(t.approvalPromptStatus)}function hy(t){return t==="delivered"||t==="fallback_delivered"}function Cn(t,e){return!t||e==null?!1:!!(t.pendingPlanApproval&&t.approvalState==="pending"&&t.lifecycle==="awaiting_plan_decision"&&(t.actionablePlanDecisionVersion??t.planDecisionVersion)===e)}function Kt(t,e,n=!1){let r="id"in t?t.id:t.sessionId??"unknown-session";return[n?"Plan review fallback text delivered to the user because interactive buttons could not be delivered.":"Plan approval buttons delivered to the user.",`Session: ${t.name??"unknown"} | ID: ${r} | Plan v${e??"?"}`,`Wait for their ${n?"explicit reply":"button callback"} — do NOT approve or reject this plan yourself.`].join(`
254
- `)}function Mo(t){let e="id"in t.session?t.session.id:t.session.sessionId??"unknown-session",n=t.originThreadLine??(t.session.originThreadId!=null?`Origin thread: ${t.session.originThreadId}`:"");return["[PLAN APPROVAL DELIVERY FAILED] The plugin could not deliver the canonical plan review buttons or the explicit fallback text to the user.",`Name: ${t.session.name??"unknown"} | ID: ${e} | Plan v${t.planDecisionVersion??"?"}`,n,"","No user-visible actionable review prompt is confirmed for this plan version.","Intervene manually before assuming the user saw the plan review request."].filter(Boolean).join(`
255
- `)}import{existsSync as Iy,readFileSync as xy}from"fs";var yy=4e3,pu=180,ky=300;function mu(){let t=bt(),e=Py(t);if(e)return{async generateQuestionContextSummary(n){if(typeof e.generateQuestionContextSummary=="function")return await e.generateQuestionContextSummary(n);if(typeof e.summarizeQuestionContext=="function")return await e.summarizeQuestionContext(n);let r=wy(n);if(typeof e.generateObject=="function")return await e.generateObject({task:"openclaw-code-agent.question-context-summary",prompt:r,input:n});if(typeof e.generateText=="function")return await e.generateText({task:"openclaw-code-agent.question-context-summary",prompt:r});if(typeof e.complete=="function")return await e.complete({prompt:r})}}}async function fu(t){let e=_o(t.question??""),n=_o(by(e,t.context??""));if(!t.provider||!e||!n)return;let r={sessionName:t.sessionName,question:e,context:Ry(n,yy)};try{let o=await Ay(t.provider.generateQuestionContextSummary(r),t.timeoutMs??ky);return Sy(o)}catch(o){let i=o instanceof Error?o.message:String(o);i!=="question-context-summary timed out"&&`${i}`;return}}function Sy(t){let e=vy(t),n=typeof e=="string"?e:e&&typeof e=="object"&&typeof e.summary=="string"?e.summary:void 0,r=_o(n??"").replace(/^[-*•]\s+/,"").trim();if(!(!r||r.length>pu)&&!(r.split(/[.!?]+/).filter(o=>o.trim()).length>1))return r}function vy(t){if(typeof t!="string")return t;let e=t.trim();if(e)try{return JSON.parse(e)}catch{return e}}function Py(t){return[t?.questionContextSummary,t?.llm,t?.ai,t?.model,t?.models].find(n=>!!(n&&typeof n=="object"&&(typeof n.generateQuestionContextSummary=="function"||typeof n.summarizeQuestionContext=="function"||typeof n.generateObject=="function"||typeof n.generateText=="function"||typeof n.complete=="function")))}function wy(t){return["Summarize why an OpenClaw Code Agent question is being asked.",'Return only JSON with shape {"summary":"..."}.',`Write one concise user-facing sentence under ${pu} characters.`,"Do not answer the question. Do not invent choices. Do not alter option labels or semantics.","","Evidence:",JSON.stringify(t,null,2)].join(`
256
- `)}function by(t,e){return t?e.split(/\r?\n/).filter(n=>_o(n)!==t).join(`
257
- `):e}function _o(t){return t.replace(/\s+/g," ").trim()}function Ry(t,e){return t.length<=e?t:`${t.slice(0,Math.max(0,e-3)).trimEnd()}...`}function Ay(t,e){return new Promise((n,r)=>{let o=setTimeout(()=>r(new Error("question-context-summary timed out")),e);o.unref?.(),t.then(i=>{clearTimeout(o),n(i)},i=>{clearTimeout(o),r(i)})})}var Ty=280;function Cy(t,e){if(t.latestPlanArtifactVersion===e&&t.latestPlanArtifact)return t.latestPlanArtifact;let n=t.planFilePath?.trim();if(!(!n||!Iy(n)))try{let r=xy(n,"utf-8").trim();return r?{markdown:r,steps:[]}:void 0}catch{return}}function My(t){let e=[t.total>1?`Question ${t.index+1}`:void 0,t.question.header].filter(Boolean).join(" - "),n=[...e?[e]:[],t.question.question];return t.optionDescriptions.length>0&&n.push("","Options:",...t.optionDescriptions.map(r=>`${r.label} - ${r.description}`)),n.join(`
258
- `)}function _y(t){return t.options.map(e=>({label:e.label,description:e.description?.trim()??""})).filter(e=>e.description&&e.description.length<=Ty)}function gu(t){let e=t?.activeQuestionIndex??0;return t?.questions?.[e]?.id??(t?.activeQuestionIndex!=null?`q${t.activeQuestionIndex}`:void 0)}function $y(t,e,n){let r=t.pendingInputState;return!!(r&&r.requestId===e&&gu(r)===n)}var $o=class{constructor(e){this.deps=e}deps;dispatchPlanApprovalFallback(e,n,r){let o=new Date().toISOString();this.deps.dispatchSessionNotification(e,{label:"plan-approval-fallback",idempotencyKey:`plan-approval:${e.id}:v${n??"unknown"}:fallback`,userMessage:An({session:e,summary:r}),notifyUser:"always",shouldDispatch:()=>Cn(e,n),hooks:{onNotifyStarted:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"sending",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o})},onNotifySucceeded:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"fallback_delivered",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o,approvalPromptDeliveredAt:new Date().toISOString(),approvalPromptFailedAt:void 0})},onNotifyFailed:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"failed",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o,approvalPromptFailedAt:new Date().toISOString()})}},wakeMessageOnNotifySuccess:Kt(e,n,!0),wakeMessageOnNotifyFailed:Mo({session:e,planDecisionVersion:n,originThreadLine:this.deps.originThreadLine(e)})})}logCompletionWakeDiagnostic(e){JSON.stringify({event:e.event,sessionId:e.session.id,sessionName:e.session.name,canonicalStatusDelivered:e.canonicalStatusDelivered,requestedShortFactualSummary:e.followupSummaryRequired,completionKind:"terminal"})}shouldRequestCompletionFollowup(e){return e.originSessionKey?.trim()?.startsWith("agent:main:cron:")?!1:!!_e(e)}async handleTurnEnd(e,n){if(e.status!=="running"){`${e.id}${e.status}`;return}if(!e.goalTaskId){if(n||e.pendingPlanApproval){await this.emitWaitingForInput(e);return}if(e.worktreeStrategy==="ask"||e.worktreeStrategy==="delegate"){`${e.id}${e.worktreeStrategy}`;return}this.deps.shouldEmitTurnCompleteWake(e)&&this.emitTurnComplete(e)}}async handleSessionTerminal(e){if(this.deps.persistSession(e),this.deps.clearWaitingTimestamp(e.id),e.goalTaskId){this.deps.clearRetryTimersForSession(e.id);return}let n={notificationSent:!1,worktreeRemoved:!1};e.worktreePath&&e.originalWorkdir&&(n=await this.deps.handleWorktreeStrategy(e));let r=!1;if(e.worktreePath&&e.originalWorkdir&&e.status==="failed"&&e.costUsd===0&&e.duration<3e4){let l=this.deps.resolveWorktreeRepoDir(e.originalWorkdir,e.worktreePath),a=e.worktreeBranch,d=le(e);`${e.name}${e.costUsd.toFixed(2)}${e.duration}`;let u=!1;if(l&&!d&&(u=ue(l,e.worktreePath)),l&&a&&!d&&u&&he(l,a),u){for(let c of pe(e))this.deps.updatePersistedSession(c,{worktreePath:void 0,worktreeBranch:void 0});r=!0}}let o=e.worktreeStrategy&&e.worktreeStrategy!=="off"&&e.worktreeStrategy!=="manual";if(!r&&e.worktreePath&&e.originalWorkdir){let l=this.deps.resolveWorktreeRepoDir(e.originalWorkdir,e.worktreePath),a=le(e);n.worktreeRemoved?`${e.name}`:o?`${e.name}${e.worktreeStrategy}`:l&&!a&&ue(l,e.worktreePath)}if(n.notificationSent){`${e.id}`;return}if(e.killReason==="done"){if(this.deps.hasTurnCompleteWakeMarker(e.id)||!this.deps.shouldEmitTerminalWake(e))return;this.emitCompleted(e);return}if(e.status==="completed"){if(!this.deps.shouldEmitTerminalWake(e))return;this.emitCompleted(e);return}if(e.status==="failed"){if(!this.deps.shouldEmitTerminalWake(e))return;let l=e.error||e.result?.is_error&&e.result.result||e.result?.result||this.deps.extractLastOutputLine(e)||`Session failed with no error details (session=${e.id}, subtype=${e.result?.subtype??"none"}, turns=${e.result?.num_turns??0})`;this.emitFailed(e,se(l,200),r);return}let i=`$${(e.costUsd??0).toFixed(2)}`,s=e.duration;if(e.killReason==="idle-timeout"){let l=e.pendingPlanApproval?this.deps.resolvePlanApprovalMode(e):void 0;if(e.pendingPlanApproval){let a=e.actionablePlanDecisionVersion??e.planDecisionVersion,d=Tn(e,a);if(l==="delegate"){this.deps.dispatchSessionNotification(e,{label:"plan-approval-timeout",idempotencyKey:`plan-approval-timeout:${e.id}:v${a??"unknown"}:delegate`,wakeMessage:["[DELEGATED PLAN APPROVAL REMINDER] Plan review is still pending after the session hit idle timeout.",`Name: ${e.name} | ID: ${e.id}`,this.deps.originThreadLine(e),"The agent already produced a plan and is waiting for a delegated decision.","Review privately first. Approve directly with agent_respond(..., approve=true, approval_rationale='...') if the plan is clearly within scope and low risk.","Escalate only if needed via agent_request_plan_approval(summary='...').","If you approve directly, follow up with a short user-facing explanation; the plugin's thumbs-up line is only the minimal approval acknowledgment.","If a canonical approval prompt was already posted for this plan version, do not restate it in plain text."].join(`
259
- `),notifyUser:"never"}),this.deps.clearRetryTimersForSession(e.id);return}if(l==="ask"&&d){this.deps.dispatchSessionNotification(e,{label:"plan-approval-timeout",idempotencyKey:`plan-approval-timeout:${e.id}:v${a??"unknown"}:already-delivered`,notifyUser:"never",wakeMessage:["[PLAN APPROVAL REMINDER] The user already has an actionable plan review prompt for this plan version.",`Name: ${e.name} | ID: ${e.id} | Plan v${a??"?"}`,this.deps.originThreadLine(e),"Do NOT post another approval summary unless canonical delivery is known to be missing."].join(`
260
- `)}),this.deps.clearRetryTimersForSession(e.id);return}this.deps.dispatchSessionNotification(e,{label:"plan-approval-timeout",idempotencyKey:`plan-approval-timeout:${e.id}:v${a??"unknown"}:user-prompt`,userMessage:[`📋 [${e.name}] Plan v${a??"?"} still awaiting approval after idle timeout | ${i} | ${Re(s)}`,"","The agent already produced a plan and is waiting for your decision.","Approve resumes the session and starts implementation.","Revise resumes it in plan mode so it can update the plan first.","Reject keeps the session stopped."].join(`
261
- `),notifyUser:"always",buttons:l==="ask"&&!d?this.deps.getPlanApprovalButtons(e.id,{...e,planDecisionVersion:a}):void 0}),this.deps.clearRetryTimersForSession(e.id);return}this.deps.dispatchSessionNotification(e,{label:"suspended",idempotencyKey:`suspended:${e.id}:${e.killReason??"idle-timeout"}:${e.completedAt??"unknown"}`,userMessage:`💤 [${e.name}] Suspended after idle timeout | ${i} | ${Re(s)}`,notifyUser:"always",buttons:this.deps.getResumeButtons(e.id,e)}),this.deps.clearRetryTimersForSession(e.id);return}this.deps.notifySession(e,`⛔ [${e.name}] ${Zi(e.killReason)} | ${i} | ${Re(s)}`),this.deps.clearRetryTimersForSession(e.id)}async emitWaitingForInput(e){let n=e.pendingInputState?.questions,r=n?.[e.pendingInputState?.activeQuestionIndex??0],o=e.pendingInputState?.requestId,i=gu(e.pendingInputState),s=o?[o,i].filter(Boolean).join(":"):void 0,l=s?`pending-input:${s}`:void 0;if(!this.deps.debounceWaitingEvent(e.id,l))return;let a=e.pendingPlanApproval?this.deps.resolvePlanApprovalMode(e):void 0,d=e.actionablePlanDecisionVersion??e.planDecisionVersion,u=e.pendingPlanApproval&&a==="ask"&&Tn(e,d),c=e.pendingInputState?.promptText?.trim()||void 0,m=e.pendingPlanApproval?void 0:this.deps.getOutputPreview(e),p=!e.pendingPlanApproval&&c?c:!e.pendingPlanApproval&&m!==void 0?m:this.deps.getOutputPreview(e,e.pendingPlanApproval&&a!=="delegate"?Number.POSITIVE_INFINITY:void 0),f=e.pendingInputState?.options.map(w=>({label:w}))??[],h=!n||n.length===0?f:r&&r.options.length>0&&r.options.length<=6&&!r.options.some(w=>w.isOther)&&!r.multiSelect?r.options:n.length===1&&r&&r.options.length===0?f:[],k=e.pendingPlanApproval&&a==="ask"&&!u?this.deps.getPlanApprovalButtons(e.id,{...e,planDecisionVersion:d}):!e.pendingPlanApproval&&h.length?this.deps.getQuestionButtons(e.id,h,{requestId:e.pendingInputState?.requestId,questionId:r?.id}):void 0,v=Cy(e,d),I=r?_y(r):[],x=r?My({question:r,index:e.pendingInputState?.activeQuestionIndex??0,total:n?.length??1,optionDescriptions:I}):c,b=!e.pendingPlanApproval&&this.deps.questionContextSummaryProvider?await fu({sessionName:e.name,question:x??p,context:m,provider:this.deps.questionContextSummaryProvider}):void 0,A=cs({session:e,preview:p,questionText:e.pendingPlanApproval?void 0:x,questionContextPreview:m,questionContextSummary:b,planArtifact:v,originThreadLine:this.deps.originThreadLine(e),planApprovalMode:a,planApprovalButtons:k,questionButtons:e.pendingPlanApproval?void 0:k}),y=A.planReviewSummary??p;if(A.label==="plan-approval"&&a==="ask"&&u){this.deps.dispatchSessionNotification(e,{label:A.label,idempotencyKey:`plan-approval:${e.id}:v${d??"unknown"}:canonical`,userMessage:A.userMessage,userMessages:A.userMessages,notifyUser:"never",buttons:A.buttons,wakeMessage:A.wakeMessage});return}if(A.label==="plan-approval"&&a==="ask"){this.deps.dispatchSessionNotification(e,{label:A.label,idempotencyKey:`plan-approval:${e.id}:v${d??"unknown"}:canonical`,userMessage:A.userMessage,userMessages:A.userMessages,notifyUser:"always",buttons:A.buttons,hooks:{onNotifyStarted:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"sending",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptLastAttemptAt:new Date().toISOString()})},onNotifySucceeded:()=>{this.deps.updatePersistedSession(e.id,{canonicalPlanPromptVersion:d,approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"delivered",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptDeliveredAt:new Date().toISOString(),approvalPromptFailedAt:void 0})},onNotifyFailed:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"failed",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptFailedAt:new Date().toISOString()})}},shouldDispatch:()=>Cn(e,d),onUserNotifyFailed:()=>this.dispatchPlanApprovalFallback(e,d,y),wakeMessageOnNotifySuccess:Kt(e,d)});return}if(A.label==="plan-approval"){this.deps.dispatchSessionNotification(e,{label:A.label,idempotencyKey:`plan-approval:${e.id}:v${d??"unknown"}:wake-only`,userMessage:A.userMessage,wakeMessage:A.wakeMessage,notifyUser:"never",buttons:A.buttons});return}this.deps.dispatchSessionNotification(e,{label:A.label,idempotencyKey:`waiting:${e.id}:${s??`${A.label}:${A.userMessage}`}`,userMessage:A.userMessage,notifyUser:"always",buttons:A.buttons,shouldDispatch:o?()=>$y(e,o,i):void 0,wakeMessageOnNotifyFailed:A.wakeMessage})}emitTurnComplete(e){`${e.id}${e.result?.num_turns??0}${e.worktreeStrategy??"none"}`;let n=rs({session:e,originThreadLine:this.deps.originThreadLine(e),preview:this.deps.getOutputPreview(e)});this.deps.dispatchSessionNotification(e,{label:"turn-complete",idempotencyKey:`turn-complete:${e.id}:${e.result?.num_turns??0}`,userMessage:n.userMessage,wakeMessage:n.wakeMessage,notifyUser:"always",onUserNotifyFailed:()=>{`${e.id}`,this.deps.shouldEmitTerminalWake(e)&&this.emitCompleted(e)}})}emitCompleted(e){let n=this.deps.getOutputPreview(e),r=this.shouldRequestCompletionFollowup(e),o=es({session:e,originThreadLine:this.deps.originThreadLine(e),preview:n}),i;this.deps.dispatchSessionNotification(e,{label:"completed",idempotencyKey:`terminal-completed:${e.id}`,userMessage:o.userMessage,notifyUser:"always",completionSummary:{required:r,producer:"terminal",outcomeKey:`terminal:${e.id}`},completionWakeSummaryRequired:r,completionWakeOutcomeKey:`terminal:${e.id}`,requireDirectUserNotification:!0,wakeMessageOnNotifySuccess:r?o.wakeMessageOnNotifySuccess:void 0,wakeMessageOnNotifyFailed:r?o.wakeMessageOnNotifyFailed:void 0,hooks:{onNotifySucceeded:()=>{i=!0,this.logCompletionWakeDiagnostic({session:e,event:"completion_notify_succeeded",canonicalStatusDelivered:i,followupSummaryRequired:r})},onNotifyFailed:()=>{i=!1,this.logCompletionWakeDiagnostic({session:e,event:"completion_notify_failed",canonicalStatusDelivered:i,followupSummaryRequired:r})},onWakeSucceeded:()=>{this.logCompletionWakeDiagnostic({session:e,event:"completion_wake_succeeded",canonicalStatusDelivered:i,followupSummaryRequired:r})}}})}emitFailed(e,n,r){let o=ns({session:e,originThreadLine:this.deps.originThreadLine(e),errorSummary:n,preview:this.deps.getOutputPreview(e),worktreeAutoCleaned:r,failedButtons:this.deps.getResumeButtons(e.id,e)});this.deps.dispatchSessionNotification(e,{label:"failed",idempotencyKey:`terminal-failed:${e.id}:${n}`,userMessage:o.userMessage,wakeMessage:o.wakeMessage,notifyUser:"always",buttons:o.buttons})}};Z();ye();import{existsSync as Ey}from"fs";var Eo=class{constructor(e){this.deps=e}deps;async dismissWorktree(e){let n=this.deps.getPersistedSession(e),r=this.deps.resolveActiveSession(e),o=r??n;if(!o)return`Error: Session "${e}" not found.`;let i=r?.worktreePath??n?.worktreePath,s=this.deps.resolveWorktreeRepoDir(r?.originalWorkdir??n?.workdir,i),l=r?.worktreeBranch??n?.worktreeBranch,a=r?.name??n?.name??e;if(!s)return`Error: No workdir found for session "${e}".`;let d=le(o);!d&&i&&Ey(i)&&ue(s,i,{destructive:!0}),l&&he(s,l);for(let c of pe(r??n))this.deps.updatePersistedSession(c,{worktreeDisposition:"dismissed",worktreeDismissedAt:new Date().toISOString(),pendingWorktreeDecisionSince:void 0,worktreeState:"dismissed",lifecycle:"terminal",worktreePath:void 0,worktreeBranch:void 0,worktreeLifecycle:{state:"dismissed",updatedAt:new Date().toISOString(),resolvedAt:new Date().toISOString(),resolutionSource:"dismiss",baseBranch:n?.worktreeLifecycle?.baseBranch,targetRepo:n?.worktreePrTargetRepo,pushRemote:n?.worktreePushRemote}});let u=d?`🗑️ [${a}] Branch \`${l??"unknown"}\` dismissed. Native backend worktree released for backend cleanup.`:`🗑️ [${a}] Branch \`${l??"unknown"}\` dismissed and permanently deleted.`;return this.deps.dispatchNotification(this.deps.buildRoutingProxy({id:U(r??n??{id:e})??e,sessionId:n?.sessionId,harnessSessionId:r?.harnessSessionId??n?.harnessSessionId,backendRef:r?.backendRef??n?.backendRef,route:r?.route??n?.route}),{label:"worktree-dismissed",idempotencyKey:`worktree-dismissed:${U(r??n??{id:e})??e}:${l??"unknown"}`,userMessage:u,notifyUser:"always"}),u}snoozeWorktreeDecision(e,n={}){let r=this.deps.getPersistedSession(e);if(!r)return`Error: Session "${e}" not found.`;let o=Date.now(),i=new Date(o+1440*60*1e3).toISOString();for(let a of pe(r))this.deps.updatePersistedSession(a,{worktreeDecisionSnoozedUntil:i,lastWorktreeReminderAt:new Date(o).toISOString()});let l=`⏭️ Reminder snoozed 24h for \`${r.worktreeBranch??"unknown"}\` (session: ${r.name})`;return n.notifyUser!==!1&&this.deps.dispatchNotification(this.deps.buildRoutingProxy({id:U(r)??$(r)??r.harnessSessionId,sessionId:r.sessionId,harnessSessionId:r.harnessSessionId,backendRef:r.backendRef,route:r.route}),{label:"worktree-snoozed",idempotencyKey:`worktree-snoozed:${U(r)??$(r)??r.harnessSessionId}:${i}`,userMessage:l,notifyUser:"always"}),l}};var hu=new Set(["starting","running"]),Do=class{sessions=new Map;activeSessionCount(){return[...this.sessions.values()].filter(e=>hu.has(e.status)).length}uniqueName(e){let n=new Set([...this.sessions.values()].filter(o=>hu.has(o.status)).map(o=>o.name));if(!n.has(e))return e;let r=2;for(;n.has(`${e}-${r}`);)r+=1;return`${e}-${r}`}add(e){this.sessions.set(e.id,e)}remove(e){this.sessions.delete(e)}get(e){return this.sessions.get(e)}list(){return[...this.sessions.values()]}};var Oo=class{constructor(e){this.deps=e}deps;initializeSession(e,n,r,o={}){if(this.deps.hydrateSpawnedSession(e,n,r),r.taskLifecycle?.create(e),e.on("statusChange",(i,s)=>{s==="running"?(e.harnessSessionId&&this.deps.markRunning(e),r.taskLifecycle?.progress(e)):(s==="completed"||s==="failed"||s==="killed")&&(r.taskLifecycle?.finalize(e),this.deps.handleTerminal(e).catch(l=>{console.error(`[SessionRuntimeBootstrap] handleTerminal threw for session ${e.id}:`,l)}))}),e.on("lifecycleChange",(i,s)=>{r.taskLifecycle?.progress(e)}),e.on("turnEnd",(i,s)=>{this.deps.handleTurnEnd(e,s).catch(l=>{console.error(`[SessionRuntimeBootstrap] handleTurnEnd threw for session ${e.id}:`,l)})}),e.start(),o.notifyLaunch!==!1){let i=this.deps.formatLaunchWorkdirLabel(e),s=`🚀 [${e.name}] Launched | ${i} | ${ln({harness:e.harnessName,model:e.model})??"default"}`;this.deps.notifySession(e,s,"launch")}return e}};var Wo=class{buildNoChangeNotification(e){let{session:n,nativeBackendWorktree:r,cleanupSucceeded:o,worktreePath:i,preview:s,originThreadLine:l}=e,a=o?r?"native backend worktree released for backend cleanup":"worktree cleaned up":`cleanup failed; worktree still exists at ${i}`;return{label:o?"worktree-no-changes":"worktree-no-changes-cleanup-failed",idempotencyKey:`worktree-no-change:${n.id}:${o?"cleaned":"cleanup-failed"}`,userMessage:o?r?`ℹ️ [${n.name}] Session completed with no changes — native backend worktree released for backend cleanup`:`ℹ️ [${n.name}] Session completed with no changes — worktree cleaned up`:`⚠️ [${n.name}] Session completed with no changes, but worktree cleanup failed. Worktree still exists at ${i}`,wakeMessage:ss({sessionName:n.name,sessionId:n.id,cleanupSummary:a,preview:s,originThreadLine:l,requestedPermissionMode:n.requestedPermissionMode,currentPermissionMode:n.currentPermissionMode,approvalExecutionState:n.approvalExecutionState,approvalState:n.approvalState,planApproval:n.planApproval,approvalPromptStatus:n.approvalPromptStatus,approvalPromptMessageKind:n.approvalPromptMessageKind,approvalPromptDeliveredAt:n.approvalPromptDeliveredAt}),notifyUser:"always"}}buildAskNotification(e){let{session:n,branchName:r,baseBranch:o,diffSummary:i,buttons:s,summaryLines:l=[],policyReason:a}=e,d=i.commitMessages.slice(0,5).map(m=>`• ${m.hash} ${m.message} (${m.author})`),u=i.commits>5?`...and ${i.commits-5} more`:"",c=n.worktreePrTargetRepo?`Branch: \`${r}\` → \`${o}\` | PR target: ${n.worktreePrTargetRepo}`:`Branch: \`${r}\` → \`${o}\``;return{label:"worktree-merge-ask",idempotencyKey:["worktree-decision",n.id,r,o,i.commits,i.commitMessages.map(m=>m.hash).join(",")].join(":"),userMessage:[`🔀 Worktree decision required for session \`${n.name}\``,"",c,`Commits: ${i.commits} | Files: ${i.filesChanged} | +${i.insertions} / -${i.deletions}`,"",...l.length>0?["Summary:",...l.map(m=>`- ${m}`),""]:[],...a?[`Policy: ${a}`,""]:[],"Recent commits:",...d,...u?[u]:[],"",`⚠️ Discard will permanently delete branch \`${r}\` and all local changes. This cannot be undone.`].join(`
252
+ `)}`:void 0}}buildNotificationDedupeKey(e,n){let r=n.idempotencyKey?.trim();if(!r)return;let o=this.getDeliveryRef(e);if(!o)return;let i=$e(e),s=i?{provider:i.provider,accountId:i.accountId,target:i.target,threadId:i.threadId}:{deliveryRef:o};return`notification:${this.digest(JSON.stringify({scope:s,semanticKey:r}))}`}markNotificationDedupeDelivered(e,n,r){let o=this.notificationDedupe.deliveredRecords(n,e?this.getPersistedSession?.(e)?.notificationDedupe:void 0,r);o&&this.applyNotificationDedupePatch(e,o)}releaseNotificationDedupe(e,n){let r=this.notificationDedupe.releasedRecords(n,e?this.getPersistedSession?.(e)?.notificationDedupe:void 0);r&&this.applyNotificationDedupePatch(e,r)}applyNotificationDedupePatch(e,n){this.getPersistedSession&&e&&this.applyPersistedPatch(e,{notificationDedupe:n})}markCompletionSummaryDelivered(e,n,r,o){let i=this.completionSummaries.completionRecordsAfterDelivery(n,e?this.getPersistedSession?.(e)?.completionSummaryDedupe:void 0,r,o);i&&this.applyCompletionSummaryDedupePatch(e,i)}applyCompletionSummaryDedupePatch(e,n){this.getPersistedSession&&e&&this.applyPersistedPatch(e,{completionSummaryDedupe:n})}logNotificationDecision(e){let n=$e(e.session);xy({event:"oca_notification_decision",sessionId:"id"in e.session?e.session.id:e.session.sessionId,sessionName:e.session.name,harnessSessionId:e.session.harnessSessionId,originRoute:n?{provider:n.provider,accountId:n.accountId,target:n.target,threadId:n.threadId,sessionKey:n.sessionKey}:void 0,outcomeType:e.outcomeKey?.split(":").slice(0,2).join(":")??e.request.label,notificationKind:e.request.label,followupKind:e.followupKind,dedupeKey:e.dedupeKey,deliveryPath:e.deliveryPath,decision:e.decision,reason:e.reason,completionWakeSummaryRequired:e.request.completionWakeSummaryRequired,deliveryRef:e.deliveryRef})}digest(e){return by("sha256").update(e).digest("hex").slice(0,16)}};ke();import{existsSync as Ty}from"fs";var _o=class{getCompletionState(e,n,r,o){let i=pn(e,r,o);if(i===void 0)return"has-commits";if(i===0){let s=pn(e,o,r);return s===void 0?"has-commits":s>0?Tt(e,r,o)?"merged":"base-advanced":ot(n)?"dirty-uncommitted":"no-change"}return ot(n)?"dirty-uncommitted":gr(e,r,o)?"released":"has-commits"}isResolvedWorktreeEligibleForCleanup(e,n,r){if(!e.worktreePath||!e.workdir||!Ty(e.worktreePath)||e.pendingWorktreeDecisionSince||e.worktreeState==="pending_decision")return!1;let o=e.worktreeMergedAt??e.worktreeDismissedAt??e.completedAt??e.createdAt,i=typeof o=="string"?new Date(o).getTime():Number(o??0);return!!i&&n-i>=r}};import{randomUUID as Cy}from"node:crypto";function My(t){let e=t.pendingInputState,n=e?.activeQuestionIndex??0;return e?.questions?.[n]?.id??(e?.activeQuestionIndex!=null?`q${e.activeQuestionIndex}`:void 0)}var $o=class{constructor(e,n,r,o){this.pendingQuestions=e;this.dispatchSessionNotification=n;this.clearWaitingTimestamp=r;this.getQuestionButtons=o}pendingQuestions;dispatchSessionNotification;clearWaitingTimestamp;getQuestionButtons;async handleAskUserQuestion(e,n){let i=n?.questions??[];if(i.length===0)throw new Error("AskUserQuestion: no questions in input");let s=i[0],a=s.options??[],l=`❓ [${e.name}] ${s.question}`,d=My(e),u=e.pendingInputState?.requestId??`legacy:${Cy()}`,c=this.getQuestionButtons(e.id,a,{requestId:u,questionId:d}),p=[`[ASK USER QUESTION] Session "${e.name}" has a question requiring user input.`,"",`Question: ${s.question}`,...a.length>0?["Options:",...a.map((g,m)=>` ${m+1}. ${g.label}`)]:[],"",`Send the question to the user and call agent_respond(session="${e.id}", message="<answer>") with their answer.`].join(`
253
+ `);return new Promise((g,m)=>{let f=this.pendingQuestions.get(e.id);f&&(clearTimeout(f.timeoutHandle),f.reject(new Error(`AskUserQuestion superseded by a newer question for session "${e.name}".`)));let y=setTimeout(()=>{this.pendingQuestions.delete(e.id),m(new Error(`AskUserQuestion timed out after ${6e5/1e3}s for session "${e.name}"`))},6e5);y.unref?.(),this.pendingQuestions.set(e.id,{resolve:g,reject:m,questions:i,timeoutHandle:y,requestId:u,questionId:d}),this.dispatchSessionNotification(e,{label:"ask-user-question",idempotencyKey:`ask-user-question:${e.id}:${u}`,userMessage:l,notifyUser:"always",buttons:c,wakeMessageOnNotifySuccess:["AskUserQuestion delivered to the user.",`Session: ${e.name} | ID: ${e.id}`,`Question: ${s.question}`,"Await their selection — do NOT answer this question yourself."].join(`
254
+ `),wakeMessageOnNotifyFailed:p})})}resolveAskUserQuestion(e,n,r={}){let o=this.pendingQuestions.get(e);if(!o)return`${e}`,!1;if(r.requestId&&r.requestId!==o.requestId)return`${e}${o.requestId}${r.requestId}`,!1;if(r.questionId&&r.questionId!==o.questionId)return`${e}${o.questionId??""}${r.questionId}`,!1;let i=o.questions[0],s=i.options??[],a=s[n];return a?(clearTimeout(o.timeoutHandle),this.pendingQuestions.delete(e),this.clearWaitingTimestamp(e),o.resolve({behavior:"allow",updatedInput:{questions:o.questions,answers:{[i.question]:a.label}}}),!0):(`${n}${e}${s.length}`,!1)}dispose(){for(let e of this.pendingQuestions.values())clearTimeout(e.timeoutHandle),e.reject(new Error("SessionManager disposed before AskUserQuestion resolved."));this.pendingQuestions.clear()}};X();fn();var _y=new Set(["merged","released","dismissed","none","cleanup_failed"]),$y=new Set(["merged","released","dismissed","no_change","none","cleanup_failed"]),Eo=class t{constructor(e,n,r,o){this.buildRoutingProxy=e;this.dispatchNotification=n;this.updatePersistedSession=r;this.getWorktreeDecisionButtons=o}buildRoutingProxy;dispatchNotification;updatePersistedSession;getWorktreeDecisionButtons;static REMINDER_THRESHOLD_MS=10800*1e3;static REMINDER_INTERVAL_MS=10800*1e3;getNextReminderAt(e){let n=new Date(e.pendingWorktreeDecisionSince).getTime();if(this.getWorktreeDecisionReminderStatus(e,n)!=="pending")return;let r=[n+t.REMINDER_THRESHOLD_MS];if(e.worktreeDecisionSnoozedUntil){let o=new Date(e.worktreeDecisionSnoozedUntil).getTime();Number.isFinite(o)&&r.push(o)}if(e.lastWorktreeReminderAt){let o=new Date(e.lastWorktreeReminderAt).getTime();Number.isFinite(o)&&r.push(o+t.REMINDER_INTERVAL_MS)}return Math.max(...r)}sendReminderIfDue(e,n=Date.now()){this.clearResolvedReminderState(e);let r=this.getNextReminderAt(e);if(r==null||r>n)return!1;let o=n-new Date(e.pendingWorktreeDecisionSince).getTime(),i=Math.floor(Math.max(0,o)/(3600*1e3));try{this.sendReminderNotification(e,i)}catch(s){return`${e.name}${s instanceof Error?s.message:String(s)}`,!1}for(let s of me(e))this.updatePersistedSession(s,{lastWorktreeReminderAt:new Date(n).toISOString()});return!0}sendReminderNotification(e,n){let r=this.buildRoutingProxy({id:e.sessionId??e.name??$(e)??e.harnessSessionId,sessionId:e.sessionId,harnessSessionId:e.harnessSessionId,backendRef:e.backendRef,route:e.route});if(e.worktreeStrategy==="delegate"){this.dispatchNotification(r,{label:`worktree-stale-reminder-${e.name}`,wakeMessage:ps(e,n),notifyUser:"never"});return}let o=[`⏰ Reminder: branch \`${e.worktreeBranch??"unknown"}\` is still waiting for a merge decision.`,`Session: ${e.name} | Pending: ${n}h`,"",`agent_merge(session="${e.name}") or agent_pr(session="${e.name}") or agent_worktree_cleanup() to resolve.`].join(`
255
+ `);this.dispatchNotification(r,{label:`worktree-stale-reminder-${e.name}`,userMessage:o,notifyUser:"always",buttons:this.getWorktreeDecisionButtons(U(e)??e.harnessSessionId,e)})}clearResolvedReminderState(e){if(!e.pendingWorktreeDecisionSince&&!e.lastWorktreeReminderAt&&!e.worktreeDecisionSnoozedUntil||!this.isResolvedWorktreeDecision(e))return!1;let n=!1;for(let r of me(e))n=this.updatePersistedSession(r,{pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0})||n;return n}getWorktreeDecisionReminderStatus(e,n){if(this.hasResolvedWorktreeDecisionMarker(e))return"resolved";if(!e.pendingWorktreeDecisionSince)return"inactive";let r=n??new Date(e.pendingWorktreeDecisionSince).getTime();if(!Number.isFinite(r))return"inactive";let o=e.worktreeState==="pending_decision"||e.lifecycle==="awaiting_worktree_decision"||e.worktreeLifecycle?.state==="pending_decision",i=e.worktreeState==null&&e.lifecycle==null&&e.worktreeLifecycle?.state==null&&!e.worktreeMerged&&!e.worktreePrUrl;if(!o&&!i)return"inactive";let s=je(e,{activeSession:!1,includePrSync:!1});return this.isResolvedDerivedWorktreeState(s.derivedState)?"resolved":"pending"}isResolvedWorktreeDecision(e){if(this.hasResolvedWorktreeDecisionMarker(e))return!0;let n=je(e,{activeSession:!1,includePrSync:!1});return this.isResolvedDerivedWorktreeState(n.derivedState)}hasResolvedWorktreeDecisionMarker(e){return!!(e.worktreeMerged||e.worktreePrUrl||e.lifecycle==="terminal"||e.worktreeState&&_y.has(e.worktreeState)||e.worktreeLifecycle?.state&&$y.has(e.worktreeLifecycle.state))}isResolvedDerivedWorktreeState(e){return e==="merged"||e==="released"||e==="no_change"||e==="cleanup_failed"}};ke();X();Re();function Mn(t,e){return e!=null&&t.approvalPromptRequiredVersion===e&&Ey(t.approvalPromptStatus)}function Ey(t){return t==="delivered"||t==="fallback_delivered"}function _n(t,e){return!t||e==null?!1:!!(t.pendingPlanApproval&&t.approvalState==="pending"&&t.lifecycle==="awaiting_plan_decision"&&(t.actionablePlanDecisionVersion??t.planDecisionVersion)===e)}function Vt(t,e,n=!1){let r="id"in t?t.id:t.sessionId??"unknown-session";return[n?"Plan review fallback text delivered to the user because interactive buttons could not be delivered.":"Plan approval buttons delivered to the user.",`Session: ${t.name??"unknown"} | ID: ${r} | Plan v${e??"?"}`,`Wait for their ${n?"explicit reply":"button callback"} — do NOT approve or reject this plan yourself.`].join(`
256
+ `)}function Do(t){let e="id"in t.session?t.session.id:t.session.sessionId??"unknown-session",n=t.originThreadLine??(t.session.originThreadId!=null?`Origin thread: ${t.session.originThreadId}`:"");return["[PLAN APPROVAL DELIVERY FAILED] The plugin could not deliver the canonical plan review buttons or the explicit fallback text to the user.",`Name: ${t.session.name??"unknown"} | ID: ${e} | Plan v${t.planDecisionVersion??"?"}`,n,"","No user-visible actionable review prompt is confirmed for this plan version.","Intervene manually before assuming the user saw the plan review request."].filter(Boolean).join(`
257
+ `)}import{existsSync as Uy,readFileSync as Vy}from"fs";var Dy=4e3,Ru=180,Oy=300;function Au(){let t=At(),e=Ly(t);if(e)return{async generateQuestionContextSummary(n){if(typeof e.generateQuestionContextSummary=="function")return await e.generateQuestionContextSummary(n);if(typeof e.summarizeQuestionContext=="function")return await e.summarizeQuestionContext(n);let r=By(n);if(typeof e.generateObject=="function")return await e.generateObject({task:"openclaw-code-agent.question-context-summary",prompt:r,input:n});if(typeof e.generateText=="function")return await e.generateText({task:"openclaw-code-agent.question-context-summary",prompt:r});if(typeof e.complete=="function")return await e.complete({prompt:r})}}}async function Iu(t){let e=Oo(t.question??""),n=Oo(Fy(e,t.context??""));if(!t.provider||!e||!n)return;let r={sessionName:t.sessionName,question:e,context:qy(n,Dy)};try{let o=await Ky(t.provider.generateQuestionContextSummary(r),t.timeoutMs??Oy);return Wy(o)}catch(o){let i=o instanceof Error?o.message:String(o);i!=="question-context-summary timed out"&&`${i}`;return}}function Wy(t){let e=Ny(t),n=typeof e=="string"?e:e&&typeof e=="object"&&typeof e.summary=="string"?e.summary:void 0,r=Oo(n??"").replace(/^[-*•]\s+/,"").trim();if(!(!r||r.length>Ru)&&!(r.split(/[.!?]+/).filter(o=>o.trim()).length>1))return r}function Ny(t){if(typeof t!="string")return t;let e=t.trim();if(e)try{return JSON.parse(e)}catch{return e}}function Ly(t){return[t?.questionContextSummary,t?.llm,t?.ai,t?.model,t?.models].find(n=>!!(n&&typeof n=="object"&&(typeof n.generateQuestionContextSummary=="function"||typeof n.summarizeQuestionContext=="function"||typeof n.generateObject=="function"||typeof n.generateText=="function"||typeof n.complete=="function")))}function By(t){return["Summarize why an OpenClaw Code Agent question is being asked.",'Return only JSON with shape {"summary":"..."}.',`Write one concise user-facing sentence under ${Ru} characters.`,"Do not answer the question. Do not invent choices. Do not alter option labels or semantics.","","Evidence:",JSON.stringify(t,null,2)].join(`
258
+ `)}function Fy(t,e){return t?e.split(/\r?\n/).filter(n=>Oo(n)!==t).join(`
259
+ `):e}function Oo(t){return t.replace(/\s+/g," ").trim()}function qy(t,e){return t.length<=e?t:`${t.slice(0,Math.max(0,e-3)).trimEnd()}...`}function Ky(t,e){return new Promise((n,r)=>{let o=setTimeout(()=>r(new Error("question-context-summary timed out")),e);o.unref?.(),t.then(i=>{clearTimeout(o),n(i)},i=>{clearTimeout(o),r(i)})})}var Gy=280;function jy(t,e){if(t.latestPlanArtifactVersion===e&&t.latestPlanArtifact)return t.latestPlanArtifact;let n=t.planFilePath?.trim();if(!(!n||!Uy(n)))try{let r=Vy(n,"utf-8").trim();return r?{markdown:r,steps:[]}:void 0}catch{return}}function Hy(t){let e=[t.total>1?`Question ${t.index+1}`:void 0,t.question.header].filter(Boolean).join(" - "),n=[...e?[e]:[],t.question.question];return t.optionDescriptions.length>0&&n.push("","Options:",...t.optionDescriptions.map(r=>`${r.label} - ${r.description}`)),n.join(`
260
+ `)}function zy(t){return t.options.map(e=>({label:e.label,description:e.description?.trim()??""})).filter(e=>e.description&&e.description.length<=Gy)}function xu(t){let e=t?.activeQuestionIndex??0;return t?.questions?.[e]?.id??(t?.activeQuestionIndex!=null?`q${t.activeQuestionIndex}`:void 0)}function Qy(t,e,n){let r=t.pendingInputState;return!!(r&&r.requestId===e&&xu(r)===n)}var Wo=class{constructor(e){this.deps=e}deps;dispatchPlanApprovalFallback(e,n,r){let o=new Date().toISOString();this.deps.dispatchSessionNotification(e,{label:"plan-approval-fallback",idempotencyKey:`plan-approval:${e.id}:v${n??"unknown"}:fallback`,userMessage:xn({session:e,summary:r}),notifyUser:"always",shouldDispatch:()=>_n(e,n),hooks:{onNotifyStarted:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"sending",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o})},onNotifySucceeded:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"fallback_delivered",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o,approvalPromptDeliveredAt:new Date().toISOString(),approvalPromptFailedAt:void 0})},onNotifyFailed:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"failed",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o,approvalPromptFailedAt:new Date().toISOString()})}},wakeMessageOnNotifySuccess:Vt(e,n,!0),wakeMessageOnNotifyFailed:Do({session:e,planDecisionVersion:n,originThreadLine:this.deps.originThreadLine(e)})})}logCompletionWakeDiagnostic(e){JSON.stringify({event:e.event,sessionId:e.session.id,sessionName:e.session.name,canonicalStatusDelivered:e.canonicalStatusDelivered,requestedShortFactualSummary:e.followupSummaryRequired,completionKind:"terminal"})}shouldRequestCompletionFollowup(e){return e.originSessionKey?.trim()?.startsWith("agent:main:cron:")?!1:!!$e(e)}async handleTurnEnd(e,n){if(e.status!=="running"){`${e.id}${e.status}`;return}if(!e.goalTaskId){if(n||e.pendingPlanApproval){await this.emitWaitingForInput(e);return}if(e.worktreeStrategy==="ask"||e.worktreeStrategy==="delegate"){`${e.id}${e.worktreeStrategy}`;return}this.deps.shouldEmitTurnCompleteWake(e)&&this.emitTurnComplete(e)}}async handleSessionTerminal(e){if(this.deps.persistSession(e),this.deps.clearWaitingTimestamp(e.id),e.goalTaskId){this.deps.clearRetryTimersForSession(e.id);return}let n={notificationSent:!1,worktreeRemoved:!1};e.worktreePath&&e.originalWorkdir&&(n=await this.deps.handleWorktreeStrategy(e));let r=!1;if(e.worktreePath&&e.originalWorkdir&&e.status==="failed"&&e.costUsd===0&&e.duration<3e4){let a=this.deps.resolveWorktreeRepoDir(e.originalWorkdir,e.worktreePath),l=e.worktreeBranch,d=de(e);`${e.name}${e.costUsd.toFixed(2)}${e.duration}`;let u=!1;if(a&&!d&&(u=ce(a,e.worktreePath)),a&&l&&!d&&u&&ye(a,l),u){for(let c of me(e))this.deps.updatePersistedSession(c,{worktreePath:void 0,worktreeBranch:void 0});r=!0}}let o=e.worktreeStrategy&&e.worktreeStrategy!=="off"&&e.worktreeStrategy!=="manual";if(!r&&e.worktreePath&&e.originalWorkdir){let a=this.deps.resolveWorktreeRepoDir(e.originalWorkdir,e.worktreePath),l=de(e);n.worktreeRemoved?`${e.name}`:o?`${e.name}${e.worktreeStrategy}`:a&&!l&&ce(a,e.worktreePath)}if(n.notificationSent){`${e.id}`;return}if(e.killReason==="done"){if(this.deps.hasTurnCompleteWakeMarker(e.id)||!this.deps.shouldEmitTerminalWake(e))return;this.emitCompleted(e);return}if(e.status==="completed"){if(!this.deps.shouldEmitTerminalWake(e))return;this.emitCompleted(e);return}if(e.status==="failed"){if(!this.deps.shouldEmitTerminalWake(e))return;let a=e.error||e.result?.is_error&&e.result.result||e.result?.result||this.deps.extractLastOutputLine(e)||`Session failed with no error details (session=${e.id}, subtype=${e.result?.subtype??"none"}, turns=${e.result?.num_turns??0})`;this.emitFailed(e,ae(a,200),r);return}let i=`$${(e.costUsd??0).toFixed(2)}`,s=e.duration;if(e.killReason==="idle-timeout"){let a=e.pendingPlanApproval?this.deps.resolvePlanApprovalMode(e):void 0;if(e.pendingPlanApproval){let l=e.actionablePlanDecisionVersion??e.planDecisionVersion,d=Mn(e,l);if(a==="delegate"){this.deps.dispatchSessionNotification(e,{label:"plan-approval-timeout",idempotencyKey:`plan-approval-timeout:${e.id}:v${l??"unknown"}:delegate`,wakeMessage:["[DELEGATED PLAN APPROVAL REMINDER] Plan review is still pending after the session hit idle timeout.",`Name: ${e.name} | ID: ${e.id}`,this.deps.originThreadLine(e),"The agent already produced a plan and is waiting for a delegated decision.","Review privately first. Approve directly with agent_respond(..., approve=true, approval_rationale='...') if the plan is clearly within scope and low risk.","Escalate only if needed via agent_request_plan_approval(summary='...').","If you approve directly, follow up with a short user-facing explanation; the plugin's thumbs-up line is only the minimal approval acknowledgment.","If a canonical approval prompt was already posted for this plan version, do not restate it in plain text."].join(`
261
+ `),notifyUser:"never"}),this.deps.clearRetryTimersForSession(e.id);return}if(a==="ask"&&d){this.deps.dispatchSessionNotification(e,{label:"plan-approval-timeout",idempotencyKey:`plan-approval-timeout:${e.id}:v${l??"unknown"}:already-delivered`,notifyUser:"never",wakeMessage:["[PLAN APPROVAL REMINDER] The user already has an actionable plan review prompt for this plan version.",`Name: ${e.name} | ID: ${e.id} | Plan v${l??"?"}`,this.deps.originThreadLine(e),"Do NOT post another approval summary unless canonical delivery is known to be missing."].join(`
262
+ `)}),this.deps.clearRetryTimersForSession(e.id);return}this.deps.dispatchSessionNotification(e,{label:"plan-approval-timeout",idempotencyKey:`plan-approval-timeout:${e.id}:v${l??"unknown"}:user-prompt`,userMessage:[`📋 [${e.name}] Plan v${l??"?"} still awaiting approval after idle timeout | ${i} | ${Ae(s)}`,"","The agent already produced a plan and is waiting for your decision.","Approve resumes the session and starts implementation.","Revise resumes it in plan mode so it can update the plan first.","Reject keeps the session stopped."].join(`
263
+ `),notifyUser:"always",buttons:a==="ask"&&!d?this.deps.getPlanApprovalButtons(e.id,{...e,planDecisionVersion:l}):void 0}),this.deps.clearRetryTimersForSession(e.id);return}this.deps.dispatchSessionNotification(e,{label:"suspended",idempotencyKey:`suspended:${e.id}:${e.killReason??"idle-timeout"}:${e.completedAt??"unknown"}`,userMessage:`💤 [${e.name}] Suspended after idle timeout | ${i} | ${Ae(s)}`,notifyUser:"always",buttons:this.deps.getResumeButtons(e.id,e)}),this.deps.clearRetryTimersForSession(e.id);return}this.deps.notifySession(e,`⛔ [${e.name}] ${is(e.killReason)} | ${i} | ${Ae(s)}`),this.deps.clearRetryTimersForSession(e.id)}async emitWaitingForInput(e){let n=e.pendingInputState?.questions,r=n?.[e.pendingInputState?.activeQuestionIndex??0],o=e.pendingInputState?.requestId,i=xu(e.pendingInputState),s=o?[o,i].filter(Boolean).join(":"):void 0,a=s?`pending-input:${s}`:void 0;if(!this.deps.debounceWaitingEvent(e.id,a))return;let l=e.pendingPlanApproval?this.deps.resolvePlanApprovalMode(e):void 0,d=e.actionablePlanDecisionVersion??e.planDecisionVersion,u=e.pendingPlanApproval&&l==="ask"&&Mn(e,d),c=e.pendingInputState?.promptText?.trim()||void 0,p=e.pendingPlanApproval?void 0:this.deps.getOutputPreview(e),g=!e.pendingPlanApproval&&c?c:!e.pendingPlanApproval&&p!==void 0?p:this.deps.getOutputPreview(e,e.pendingPlanApproval&&l!=="delegate"?Number.POSITIVE_INFINITY:void 0),m=e.pendingInputState?.options.map(P=>({label:P}))??[],f=!n||n.length===0?m:r&&r.options.length>0&&r.options.length<=6&&!r.options.some(P=>P.isOther)&&!r.multiSelect?r.options:n.length===1&&r&&r.options.length===0?m:[],y=e.pendingPlanApproval&&l==="ask"&&!u?this.deps.getPlanApprovalButtons(e.id,{...e,planDecisionVersion:d}):!e.pendingPlanApproval&&f.length?this.deps.getQuestionButtons(e.id,f,{requestId:e.pendingInputState?.requestId,questionId:r?.id}):void 0,S=jy(e,d),R=r?zy(r):[],I=r?Hy({question:r,index:e.pendingInputState?.activeQuestionIndex??0,total:n?.length??1,optionDescriptions:R}):c,b=!e.pendingPlanApproval&&this.deps.questionContextSummaryProvider?await Iu({sessionName:e.name,question:I??g,context:p,provider:this.deps.questionContextSummaryProvider}):void 0,A=ks({session:e,preview:g,questionText:e.pendingPlanApproval?void 0:I,questionContextPreview:p,questionContextSummary:b,planArtifact:S,originThreadLine:this.deps.originThreadLine(e),planApprovalMode:l,planApprovalButtons:y,questionButtons:e.pendingPlanApproval?void 0:y}),k=A.planReviewSummary??g;if(A.label==="plan-approval"&&l==="ask"&&u){this.deps.dispatchSessionNotification(e,{label:A.label,idempotencyKey:`plan-approval:${e.id}:v${d??"unknown"}:canonical`,userMessage:A.userMessage,userMessages:A.userMessages,notifyUser:"never",buttons:A.buttons,wakeMessage:A.wakeMessage});return}if(A.label==="plan-approval"&&l==="ask"){this.deps.dispatchSessionNotification(e,{label:A.label,idempotencyKey:`plan-approval:${e.id}:v${d??"unknown"}:canonical`,userMessage:A.userMessage,userMessages:A.userMessages,notifyUser:"always",buttons:A.buttons,hooks:{onNotifyStarted:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"sending",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptLastAttemptAt:new Date().toISOString()})},onNotifySucceeded:()=>{this.deps.updatePersistedSession(e.id,{canonicalPlanPromptVersion:d,approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"delivered",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptDeliveredAt:new Date().toISOString(),approvalPromptFailedAt:void 0})},onNotifyFailed:()=>{this.deps.updatePersistedSession(e.id,{approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"failed",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptFailedAt:new Date().toISOString()})}},shouldDispatch:()=>_n(e,d),onUserNotifyFailed:()=>this.dispatchPlanApprovalFallback(e,d,k),wakeMessageOnNotifySuccess:Vt(e,d)});return}if(A.label==="plan-approval"){this.deps.dispatchSessionNotification(e,{label:A.label,idempotencyKey:`plan-approval:${e.id}:v${d??"unknown"}:wake-only`,userMessage:A.userMessage,wakeMessage:A.wakeMessage,notifyUser:"never",buttons:A.buttons});return}this.deps.dispatchSessionNotification(e,{label:A.label,idempotencyKey:`waiting:${e.id}:${s??`${A.label}:${A.userMessage}`}`,userMessage:A.userMessage,notifyUser:"always",buttons:A.buttons,shouldDispatch:o?()=>Qy(e,o,i):void 0,wakeMessageOnNotifyFailed:A.wakeMessage})}emitTurnComplete(e){`${e.id}${e.result?.num_turns??0}${e.worktreeStrategy??"none"}`;let n=us({session:e,originThreadLine:this.deps.originThreadLine(e),preview:this.deps.getOutputPreview(e)});this.deps.dispatchSessionNotification(e,{label:"turn-complete",idempotencyKey:`turn-complete:${e.id}:${e.result?.num_turns??0}`,userMessage:n.userMessage,wakeMessage:n.wakeMessage,notifyUser:"always",onUserNotifyFailed:()=>{`${e.id}`,this.deps.shouldEmitTerminalWake(e)&&this.emitCompleted(e)}})}emitCompleted(e){let n=this.deps.getOutputPreview(e),r=this.shouldRequestCompletionFollowup(e),o=as({session:e,originThreadLine:this.deps.originThreadLine(e),preview:n}),i;this.deps.dispatchSessionNotification(e,{label:"completed",idempotencyKey:`terminal-completed:${e.id}`,userMessage:o.userMessage,notifyUser:"always",completionSummary:{required:r,producer:"terminal",outcomeKey:`terminal:${e.id}`},completionWakeSummaryRequired:r,completionWakeOutcomeKey:`terminal:${e.id}`,requireDirectUserNotification:!0,wakeMessageOnNotifySuccess:r?o.wakeMessageOnNotifySuccess:void 0,wakeMessageOnNotifyFailed:r?o.wakeMessageOnNotifyFailed:void 0,hooks:{onNotifySucceeded:()=>{i=!0,this.logCompletionWakeDiagnostic({session:e,event:"completion_notify_succeeded",canonicalStatusDelivered:i,followupSummaryRequired:r})},onNotifyFailed:()=>{i=!1,this.logCompletionWakeDiagnostic({session:e,event:"completion_notify_failed",canonicalStatusDelivered:i,followupSummaryRequired:r})},onWakeSucceeded:()=>{this.logCompletionWakeDiagnostic({session:e,event:"completion_wake_succeeded",canonicalStatusDelivered:i,followupSummaryRequired:r})}}})}emitFailed(e,n,r){let o=ds({session:e,originThreadLine:this.deps.originThreadLine(e),errorSummary:n,preview:this.deps.getOutputPreview(e),worktreeAutoCleaned:r,failedButtons:this.deps.getResumeButtons(e.id,e)});this.deps.dispatchSessionNotification(e,{label:"failed",idempotencyKey:`terminal-failed:${e.id}:${n}`,userMessage:o.userMessage,wakeMessage:o.wakeMessage,notifyUser:"always",buttons:o.buttons})}};X();ke();import{existsSync as Jy}from"fs";var No=class{constructor(e){this.deps=e}deps;async dismissWorktree(e){let n=this.deps.getPersistedSession(e),r=this.deps.resolveActiveSession(e),o=r??n;if(!o)return`Error: Session "${e}" not found.`;let i=r?.worktreePath??n?.worktreePath,s=this.deps.resolveWorktreeRepoDir(r?.originalWorkdir??n?.workdir,i),a=r?.worktreeBranch??n?.worktreeBranch,l=r?.name??n?.name??e;if(!s)return`Error: No workdir found for session "${e}".`;let d=de(o);!d&&i&&Jy(i)&&ce(s,i,{destructive:!0}),a&&ye(s,a);for(let c of me(r??n))this.deps.updatePersistedSession(c,{worktreeDisposition:"dismissed",worktreeDismissedAt:new Date().toISOString(),pendingWorktreeDecisionSince:void 0,worktreeState:"dismissed",lifecycle:"terminal",worktreePath:void 0,worktreeBranch:void 0,worktreeLifecycle:{state:"dismissed",updatedAt:new Date().toISOString(),resolvedAt:new Date().toISOString(),resolutionSource:"dismiss",baseBranch:n?.worktreeLifecycle?.baseBranch,targetRepo:n?.worktreePrTargetRepo,pushRemote:n?.worktreePushRemote}});let u=d?`🗑️ [${l}] Branch \`${a??"unknown"}\` dismissed. Native backend worktree released for backend cleanup.`:`🗑️ [${l}] Branch \`${a??"unknown"}\` dismissed and permanently deleted.`;return this.deps.dispatchNotification(this.deps.buildRoutingProxy({id:U(r??n??{id:e})??e,sessionId:n?.sessionId,harnessSessionId:r?.harnessSessionId??n?.harnessSessionId,backendRef:r?.backendRef??n?.backendRef,route:r?.route??n?.route}),{label:"worktree-dismissed",idempotencyKey:`worktree-dismissed:${U(r??n??{id:e})??e}:${a??"unknown"}`,userMessage:u,notifyUser:"always"}),u}snoozeWorktreeDecision(e,n={}){let r=this.deps.getPersistedSession(e);if(!r)return`Error: Session "${e}" not found.`;let o=Date.now(),i=new Date(o+1440*60*1e3).toISOString();for(let l of me(r))this.deps.updatePersistedSession(l,{worktreeDecisionSnoozedUntil:i,lastWorktreeReminderAt:new Date(o).toISOString()});let a=`⏭️ Reminder snoozed 24h for \`${r.worktreeBranch??"unknown"}\` (session: ${r.name})`;return n.notifyUser!==!1&&this.deps.dispatchNotification(this.deps.buildRoutingProxy({id:U(r)??$(r)??r.harnessSessionId,sessionId:r.sessionId,harnessSessionId:r.harnessSessionId,backendRef:r.backendRef,route:r.route}),{label:"worktree-snoozed",idempotencyKey:`worktree-snoozed:${U(r)??$(r)??r.harnessSessionId}:${i}`,userMessage:a,notifyUser:"always"}),a}};var Tu=new Set(["starting","running"]),Lo=class{sessions=new Map;activeSessionCount(){return[...this.sessions.values()].filter(e=>Tu.has(e.status)).length}uniqueName(e){let n=new Set([...this.sessions.values()].filter(o=>Tu.has(o.status)).map(o=>o.name));if(!n.has(e))return e;let r=2;for(;n.has(`${e}-${r}`);)r+=1;return`${e}-${r}`}add(e){this.sessions.set(e.id,e)}remove(e){this.sessions.delete(e)}get(e){return this.sessions.get(e)}list(){return[...this.sessions.values()]}};var Bo=class{constructor(e){this.deps=e}deps;initializeSession(e,n,r,o={}){if(this.deps.hydrateSpawnedSession(e,n,r),r.taskLifecycle?.create(e),e.on("statusChange",(i,s)=>{s==="running"?(e.harnessSessionId&&this.deps.markRunning(e),r.taskLifecycle?.progress(e)):(s==="completed"||s==="failed"||s==="killed")&&(r.taskLifecycle?.finalize(e),this.deps.handleTerminal(e).catch(a=>{console.error(`[SessionRuntimeBootstrap] handleTerminal threw for session ${e.id}:`,a)}))}),e.on("lifecycleChange",(i,s)=>{r.taskLifecycle?.progress(e)}),e.on("turnEnd",(i,s)=>{this.deps.handleTurnEnd(e,s).catch(a=>{console.error(`[SessionRuntimeBootstrap] handleTurnEnd threw for session ${e.id}:`,a)})}),e.start(),o.notifyLaunch!==!1){let i=this.deps.formatLaunchWorkdirLabel(e),s=`🚀 [${e.name}] Launched | ${i} | ${dn({harness:e.harnessName,model:e.model})??"default"}`;this.deps.notifySession(e,s,"launch")}return e}};var Fo=class{buildNoChangeNotification(e){let{session:n,nativeBackendWorktree:r,cleanupSucceeded:o,worktreePath:i,preview:s,originThreadLine:a}=e,l=o?r?"native backend worktree released for backend cleanup":"worktree cleaned up":`cleanup failed; worktree still exists at ${i}`;return{label:o?"worktree-no-changes":"worktree-no-changes-cleanup-failed",idempotencyKey:`worktree-no-change:${n.id}:${o?"cleaned":"cleanup-failed"}`,userMessage:o?r?`ℹ️ [${n.name}] Session completed with no changes — native backend worktree released for backend cleanup`:`ℹ️ [${n.name}] Session completed with no changes — worktree cleaned up`:`⚠️ [${n.name}] Session completed with no changes, but worktree cleanup failed. Worktree still exists at ${i}`,wakeMessage:ms({sessionName:n.name,sessionId:n.id,cleanupSummary:l,preview:s,originThreadLine:a,requestedPermissionMode:n.requestedPermissionMode,currentPermissionMode:n.currentPermissionMode,approvalExecutionState:n.approvalExecutionState,approvalState:n.approvalState,planApproval:n.planApproval,approvalPromptStatus:n.approvalPromptStatus,approvalPromptMessageKind:n.approvalPromptMessageKind,approvalPromptDeliveredAt:n.approvalPromptDeliveredAt}),notifyUser:"always"}}buildAskNotification(e){let{session:n,branchName:r,baseBranch:o,diffSummary:i,buttons:s,summaryLines:a=[],policyReason:l}=e,d=i.commitMessages.slice(0,5).map(p=>`• ${p.hash} ${p.message} (${p.author})`),u=i.commits>5?`...and ${i.commits-5} more`:"",c=n.worktreePrTargetRepo?`Branch: \`${r}\` → \`${o}\` | PR target: ${n.worktreePrTargetRepo}`:`Branch: \`${r}\` → \`${o}\``;return{label:"worktree-merge-ask",idempotencyKey:["worktree-decision",n.id,r,o,i.commits,i.commitMessages.map(p=>p.hash).join(",")].join(":"),userMessage:[`🔀 Worktree decision required for session \`${n.name}\``,"",c,`Commits: ${i.commits} | Files: ${i.filesChanged} | +${i.insertions} / -${i.deletions}`,"",...a.length>0?["Summary:",...a.map(p=>`- ${p}`),""]:[],...l?[`Policy: ${l}`,""]:[],"Recent commits:",...d,...u?[u]:[],"",`⚠️ Discard will permanently delete branch \`${r}\` and all local changes. This cannot be undone.`].join(`
262
264
  `),notifyUser:"always",buttons:s,wakeMessageOnNotifySuccess:["Worktree decision buttons delivered to the user.",`Session: ${n.name} | ID: ${n.id}`,c,"Wait for their button callback — do NOT act on this worktree yourself."].join(`
263
265
  `),wakeMessageOnNotifyFailed:[`🔀 Worktree decision required for session \`${n.name}\``,"",c,`Commits: ${i.commits} | Files: ${i.filesChanged} | +${i.insertions} / -${i.deletions}`].join(`
264
- `)}}buildDelegateNotification(e){let{session:n,branchName:r,baseBranch:o,diffSummary:i,policyReason:s,allowedActions:l,originThreadLine:a}=e,d=i.commitMessages.slice(0,5).map(m=>`• ${m.hash} ${m.message} (${m.author})`),u=i.commits>5?`...and ${i.commits-5} more`:void 0,c=n.prompt?n.prompt.slice(0,500):"(no prompt)";return{label:"worktree-delegate",idempotencyKey:["worktree-delegate",n.id,r,o,i.commits,i.commitMessages.map(m=>m.hash).join(",")].join(":"),wakeMessage:os({sessionName:n.name,sessionId:n.id,branchName:r,baseBranch:o,promptSnippet:c,commitLines:d,moreNote:u,originThreadLine:a,diffSummary:i,allowedActions:l,policyReason:s}),notifyUser:"never"}}};function yu(t,e=1e3){let n=!Number.isFinite(e),r=typeof t.getOutput=="function"?t.getOutput():[],o=n?r.join(`
265
- `):Dy(t);return n?o:o.length>e?ku(t)?va(o,e):Pa(o,e):o}function Dy(t){let e=typeof t.getOutput=="function"?t.getOutput():[],n=e.join(`
266
- `).trim();return n?ku(t)?Oy(n)??n:e.slice(-20).join(`
267
- `):""}function ku(t){if(t.status==="completed"||t.killReason==="done")return!0;let e=t;return e.approvalState==="approved"||e.planModeApproved===!0||(e.planDecisionVersion??0)>0}function Oy(t){let n=t.split(/\n\s*\n+/).map(r=>r.trim()).filter(r=>/[A-Za-z0-9]/.test(r)).at(-1);if(n)return n.length>=120||n.includes(`
268
- `)?n:void 0}be();ye();ie();import{unlinkSync as Wy}from"fs";var No=class t{timers=new Map;disposed=!1;static MAX_DELAY_MS=2147483647;schedule(e,n,r){if(this.disposed||(this.cancel(e),!Number.isFinite(n)))return;let o=Math.max(0,n-Date.now()),i=setTimeout(()=>{if(this.timers.delete(e),!this.disposed){if(n-Date.now()>0){this.schedule(e,n,r);return}r()}},Math.min(o,t.MAX_DELAY_MS));i.unref?.(),this.timers.set(e,i)}cancel(e){let n=this.timers.get(e);n&&(clearTimeout(n),this.timers.delete(e))}cancelPrefix(e){for(let n of this.timers.keys())n.startsWith(e)&&this.cancel(n)}dispose(){this.disposed=!0;for(let e of this.timers.values())clearTimeout(e);this.timers.clear()}};Z();mn();ye();var Su=10080*60*1e3,Ny=300*1e3,vu="tmp-output:cleanup",Ly=60*1e3;function Fy(t){return t instanceof Error?t.message:String(t)}var Lo=class{constructor(e){this.deps=e}deps;scheduler=new No;lastTmpOutputCleanupAttemptAt;schedule(e,n,r){this.scheduler.schedule(e,n,r)}cancel(e){this.scheduler.cancel(e)}cancelPrefix(e){this.scheduler.cancelPrefix(e)}bootstrapMaintenanceSchedules(){let e=Date.now();this.runTmpOutputCleanup(e);for(let n of this.deps.store.listPersistedSessions())this.syncPersistedSessionMaintenance(n);this.syncActionTokenExpiryDeadline(),this.deps.store.cleanupOrphanOutputFiles(),this.syncTmpOutputCleanupDeadline(e)}syncRuntimeGcDeadline(e){if(!e.completedAt)return;let n=this.runtimeGcKey(e.id);this.schedule(n,e.completedAt+this.runtimeGcMaxAgeMs(),()=>{let r=this.deps.sessions.get(e.id);if(!r||!r.completedAt)return;let o=this.runtimeGcMaxAgeMs();if(!this.deps.store.shouldGcActiveSession(r,Date.now(),o)){this.syncRuntimeGcDeadline(r);return}this.deps.removeRuntimeSession(e.id),this.deps.persistSession(r,{scheduleRuntimeGc:!1}),this.deps.clearRuntimeSessionState(e.id)})}cancelRuntimeGc(e){this.cancel(this.runtimeGcKey(e))}cancelPersistedMaintenance(e){let n=this.persistedMaintenanceRef(e);n&&this.cancelPrefix(`persisted:${n}:`)}syncPersistedSessionMaintenance(e){let n=this.persistedMaintenanceRef(e);if(!n)return;this.cancel(this.persistedMaintenanceKey(n,"worktree-reminder"));let r=this.deps.reminders.getNextReminderAt(e);r!=null?this.schedulePersistedWorktreeReminder(n,r):this.deps.reminders.clearResolvedReminderState(e),this.cancel(this.persistedMaintenanceKey(n,"worktree-retention"));let o=Ve(e,{activeSession:!1,includePrSync:e.worktreeLifecycle?.state==="pr_open"||!!e.worktreePrUrl}),i=this.resolvedAtIso(e),s=this.isLegacyResolvedWorktree(e);if((o.cleanupSafe||s)&&typeof i=="string"){let l=new Date(i).getTime();Number.isFinite(l)&&this.schedule(this.persistedMaintenanceKey(n,"worktree-retention"),l+Su,()=>{let a=this.deps.store.getPersistedSession(n);a&&this.reconcileResolvedWorktreeRetention(a,Date.now())})}}reconcileResolvedWorktreeRetention(e,n){let r=Ve(e,{activeSession:!1,includePrSync:e.worktreeLifecycle?.state==="pr_open"||!!e.worktreePrUrl}),o=this.resolvedAtIso(e),i=o?new Date(o).getTime():0,s=this.legacyResolvedWorktreeState(e);if(!(!r.cleanupSafe&&!s||!o||!Number.isFinite(i)||n-i<Su))try{if(!e.worktreePath&&!le(e))return;let l=this.deps.resolveWorktreeRepoDir(e.workdir,e.worktreePath);if(!l)return;let a=le(e)?!1:ue(l,e.worktreePath);if(!le(e)&&!a)return;for(let d of pe(e))this.deps.updatePersistedSession(d,{worktreePath:void 0,worktreeBranch:void 0,worktreeState:"none",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeLifecycle:{...e.worktreeLifecycle??r.lifecycle,state:r.cleanupSafe?r.derivedState:s??r.derivedState,updatedAt:new Date(n).toISOString(),resolvedAt:e.worktreeLifecycle?.resolvedAt??o,resolutionSource:e.worktreeLifecycle?.resolutionSource??"maintenance",notes:r.reasons}})}catch(l){`${e.worktreePath}${Fy(l)}`}}syncActionTokenExpiryDeadline(){let e="tokens:expiry";this.cancel(e);let n=this.deps.store.getNextActionTokenExpiry();n!=null&&this.schedule(e,n,()=>{this.deps.store.purgeExpiredActionTokens(Date.now())||this.syncActionTokenExpiryDeadline()})}syncTmpOutputCleanupDeadline(e=Date.now()){this.cancel(vu);let n=this.deps.store.getNextTmpOutputCleanupAt(e);if(n==null){this.lastTmpOutputCleanupAttemptAt=void 0;return}n>e&&(this.lastTmpOutputCleanupAttemptAt=void 0),this.schedule(vu,this.getTmpOutputCleanupScheduleAt(n,e),()=>{let r=Date.now();this.runTmpOutputCleanup(r),this.syncTmpOutputCleanupDeadline(r)})}enforcePersistedRetention(){let e=this.deps.store.evictOldestPersisted(this.deps.getMaxPersistedSessions());for(let n of e)this.cancelPersistedMaintenance(n),n.sessionId&&this.cancelRuntimeGc(n.sessionId),this.cleanupOutputPathIfUnreferenced(n.outputPath)}dispose(){this.scheduler.dispose()}persistedMaintenanceRef(e){return e.sessionId??$(e)??e.harnessSessionId}runtimeGcKey(e){return`runtime-gc:${e}`}persistedMaintenanceKey(e,n){return`persisted:${e}:${n}`}runtimeGcMaxAgeMs(){return(D.sessionGcAgeMinutes??1440)*6e4}runTmpOutputCleanup(e){this.lastTmpOutputCleanupAttemptAt=e,this.deps.store.cleanupTmpOutputFiles(e)}getTmpOutputCleanupScheduleAt(e,n){if(e>n||this.lastTmpOutputCleanupAttemptAt==null)return e;let r=this.lastTmpOutputCleanupAttemptAt+Ly;return r>n?r:e}schedulePersistedWorktreeReminder(e,n){let r=this.persistedMaintenanceKey(e,"worktree-reminder");this.schedule(r,n,()=>{let o=this.deps.store.getPersistedSession(e);if(!o||this.deps.reminders.sendReminderIfDue(o,Date.now()))return;let s=this.deps.reminders.getNextReminderAt(o);s!=null&&this.schedulePersistedWorktreeReminder(e,Math.max(s,Date.now()+Ny))})}cleanupOutputPathIfUnreferenced(e){if(!(!e||this.deps.store.hasOutputPathReference(e)))try{Wy(e)}catch{}}resolvedAtIso(e){return e.worktreeLifecycle?.resolvedAt??e.worktreeMergedAt??e.worktreeDismissedAt??(e.completedAt?new Date(e.completedAt).toISOString():void 0)}isLegacyResolvedWorktree(e){return this.legacyResolvedWorktreeState(e)!=null}legacyResolvedWorktreeState(e){if(e.worktreeMerged===!0||e.worktreeDisposition==="merged"||e.worktreeState==="merged")return"merged";if(e.worktreeDisposition==="dismissed"||e.worktreeState==="dismissed")return"dismissed";if(e.worktreeDisposition==="no-change-cleaned")return"no_change"}};kn();var Pu=new Set(["completed","failed","killed"]),By=new Set(["starting","running"]),qy=5e3;function Uy(t,e){return wu("sha256").update(JSON.stringify({route:t.route?{provider:t.route.provider,target:t.route.target,accountId:t.route.accountId,threadId:t.route.threadId,sessionKey:t.route.sessionKey}:void 0,prompt:t.prompt,workdir:t.workdir,name:t.name,model:t.model,reasoningEffort:t.reasoningEffort,fastMode:t.fastMode,systemPrompt:t.systemPrompt,allowedTools:t.allowedTools?[...t.allowedTools].sort():t.allowedTools,resumeSessionId:t.resumeSessionId,resumeWorktreeFrom:t.resumeWorktreeFrom,sessionIdOverride:t.sessionIdOverride,clearedPersistedCodexResume:t.clearedPersistedCodexResume,forkSession:t.forkSession,forceNewSession:t.forceNewSession,permissionMode:t.permissionMode,planApproval:t.planApproval,harness:t.harness,worktreeStrategy:t.worktreeStrategy,effectiveWorktreeStrategy:e,worktreeBaseBranch:t.worktreeBaseBranch,worktreePrTargetRepo:t.worktreePrTargetRepo,originAgentId:t.originAgentId})).digest("hex").slice(0,16)}function Ky(t){return wu("sha256").update(JSON.stringify({route:t.route?{provider:t.route.provider,target:t.route.target,accountId:t.route.accountId,threadId:t.route.threadId,sessionKey:t.route.sessionKey}:void 0,prompt:t.launchPrompt,workdir:t.launchWorkdir,name:t.launchName,model:t.launchModel,reasoningEffort:t.launchReasoningEffort,fastMode:t.launchFastMode,systemPrompt:t.launchSystemPrompt,allowedTools:t.launchAllowedTools?[...t.launchAllowedTools].sort():t.launchAllowedTools,resumeSessionId:t.launchResumeSessionId,resumeWorktreeFrom:t.launchResumeWorktreeFrom,sessionIdOverride:t.launchSessionIdOverride,clearedPersistedCodexResume:t.launchClearedPersistedCodexResume,forkSession:t.launchForkSession,forceNewSession:t.launchForceNewSession,permissionMode:t.launchPermissionMode,planApproval:t.launchPlanApproval,harness:t.launchHarness,worktreeStrategy:t.launchWorktreeStrategy,worktreeBaseBranch:t.launchWorktreeBaseBranch,worktreePrTargetRepo:t.launchWorktreePrTargetRepo,originAgentId:t.launchOriginAgentId})).digest("hex").slice(0,16)}var Fo=class t{registry;sessions;maxSessions;maxPersistedSessions;lastWaitingEventTimestamps=new Map;lastTurnCompleteMarkers=new Map;lastTerminalWakeMarkers=new Map;mergeQueue=new Ut;pendingAskUserQuestions=new Map;store;metrics;wakeDispatcher;interactions;notifications;worktrees;questions;lifecycle;restore;stateSync;references;worktreeStrategy;worktreeDecisions;runtimeBootstrap;worktreeMessages;maintenance;constructor(e=20,n=50,r={}){this.maxSessions=e,this.maxPersistedSessions=n;let o=t.createServiceBundle(this,r);this.registry=o.registry,this.sessions=o.sessions,this.store=o.store,this.metrics=o.metrics,this.wakeDispatcher=o.wakeDispatcher,this.interactions=o.interactions,this.notifications=o.notifications,this.worktrees=o.worktrees,this.questions=o.questions,this.lifecycle=o.lifecycle,this.restore=o.restore,this.stateSync=o.stateSync,this.references=o.references,this.worktreeStrategy=o.worktreeStrategy,this.worktreeDecisions=o.worktreeDecisions,this.runtimeBootstrap=o.runtimeBootstrap,this.worktreeMessages=o.worktreeMessages,this.maintenance=o.maintenance}static createServiceBundle(e,n){let r=new Do,o=r.sessions,i=new po(n.store),s=new mo,l=new Po,a=new wo(i.actionTokenStore,Ae),d=new eo(o,i),u=new Xr({store:i,sessions:o,resolveSession:y=>d.resolveActive(y)}),c=new Io(l,(y,w)=>u.applySessionPatch(y,w),{getPersistedSession:y=>i.getPersistedSession(y)}),m=new xo,p=new Zr(y=>i.getPersistedSession(y)),f=new Wo,h=new so({shouldRunWorktreeStrategy:y=>e.shouldRunWorktreeStrategy(y),isAlreadyMerged:y=>e.isAlreadyMerged(y),resolveWorktreeRepoDir:(y,w)=>e.resolveWorktreeRepoDir(y,w),getWorktreeCompletionState:(y,w,F,ce)=>e.getWorktreeCompletionState(y,w,F,ce),updatePersistedSession:(y,w)=>e.updatePersistedSession(y,w),dispatchSessionNotification:(y,w)=>e.dispatchSessionNotification(y,w),getOutputPreview:(y,w)=>e.getOutputPreview(y,w),originThreadLine:y=>e.originThreadLine(y),getWorktreeDecisionButtons:y=>e.getWorktreeDecisionButtons(y),getPolicyAwareWorktreeDecisionButtons:(y,w,F)=>e.getWorktreeDecisionButtons(y,w,F),makeOpenPrButton:y=>e.makeActionButton(y,"worktree-create-pr","Open PR"),isPrAvailable:y=>e.resolveRepoPolicy(y).prAvailable,resolveRepoPolicy:y=>e.resolveRepoPolicy(y),worktreeSummaryProvider:n.worktreeSummaryProvider,worktreeMessages:f,enqueueMerge:(y,w,F)=>e.enqueueMerge(y,w,F),mergeBranch:yr,spawnConflictResolver:async({session:y,worktreePath:w,prompt:F})=>e.spawn({prompt:F,workdir:w,name:`${y.name}-conflict-resolver`,harness:y.harnessName||ae(),model:y.model,reasoningEffort:y.reasoningEffort,fastMode:y.fastMode,permissionMode:"bypassPermissions",multiTurn:!0,worktreeStrategy:"off",autoMergeParentSessionId:y.id,route:y.route,originChannel:y.originChannel,originThreadId:y.originThreadId,originAgentId:y.originAgentId,originSessionKey:y.originSessionKey},{notifyLaunch:!1}),runAutoPr:async(y,w)=>{let{makeAgentPrTool:F}=await Promise.resolve().then(()=>(Fr(),Tl));return{success:(await F().execute("auto-pr",{session:y.id,base_branch:w}))?.meta?.success===!0}}}),k=new To(e.pendingAskUserQuestions,(y,w)=>e.dispatchSessionNotification(y,w),y=>{e.clearWaitingTimestampsForSession(y)},(y,w,F)=>a.getQuestionButtons(y,w,F)),v=new Co(y=>e.buildRoutingProxy(y),(y,w)=>c.dispatch(y,w),(y,w)=>e.updatePersistedSession(y,w),(y,w)=>e.getPolicyAwareWorktreeDecisionButtons(y,{},void 0,w)),I=new Lo({store:i,sessions:o,reminders:v,removeRuntimeSession:y=>r.remove(y),persistSession:(y,w)=>e.persistSession(y,w),clearRuntimeSessionState:y=>{e.clearWaitingTimestampsForSession(y),e.lastTurnCompleteMarkers.delete(y),e.lastTerminalWakeMarkers.delete(y)},resolveWorktreeRepoDir:(y,w)=>e.resolveWorktreeRepoDir(y,w),updatePersistedSession:(y,w)=>e.updatePersistedSession(y,w),getMaxPersistedSessions:()=>e.maxPersistedSessions});i.onActionTokensChanged(()=>e.syncActionTokenExpiryDeadline());let x=new $o({persistSession:y=>e.persistSession(y),clearWaitingTimestamp:y=>{e.clearWaitingTimestampsForSession(y)},handleWorktreeStrategy:y=>e.handleWorktreeStrategy(y),resolveWorktreeRepoDir:(y,w)=>e.resolveWorktreeRepoDir(y,w),updatePersistedSession:(y,w)=>e.updatePersistedSession(y,w),dispatchSessionNotification:(y,w)=>e.dispatchSessionNotification(y,w),notifySession:(y,w,F)=>e.notifySession(y,w,F),clearRetryTimersForSession:y=>l.clearRetryTimersForSession(y),hasTurnCompleteWakeMarker:y=>e.lastTurnCompleteMarkers.has(y),shouldEmitTurnCompleteWake:y=>e.shouldEmitTurnCompleteWake(y),shouldEmitTerminalWake:y=>e.shouldEmitTerminalWake(y),resolvePlanApprovalMode:y=>e.resolvePlanApprovalMode(y),getPlanApprovalButtons:(y,w)=>a.getPlanApprovalButtons(y,w),getResumeButtons:(y,w)=>a.getResumeButtons(y,w),getQuestionButtons:(y,w,F)=>a.getQuestionButtons(y,w,F),extractLastOutputLine:y=>e.extractLastOutputLine(y),getOutputPreview:(y,w)=>e.getOutputPreview(y,w),originThreadLine:y=>e.originThreadLine(y),debounceWaitingEvent:(y,w)=>e.debounceWaitingEvent(y,w),isAlreadyMerged:y=>e.isAlreadyMerged(y),questionContextSummaryProvider:n.questionContextSummaryProvider??mu()}),b=new Eo({getPersistedSession:y=>i.getPersistedSession(y),resolveActiveSession:y=>d.resolveActive(y),resolveWorktreeRepoDir:(y,w)=>e.resolveWorktreeRepoDir(y,w),updatePersistedSession:(y,w)=>e.updatePersistedSession(y,w),dispatchNotification:(y,w)=>c.dispatch(y,w),buildRoutingProxy:y=>e.buildRoutingProxy(y)}),A=new Oo({hydrateSpawnedSession:(y,w,F)=>{p.hydrateSpawnedSession(y,w,F)},markRunning:y=>{i.markRunning(y),e.onPersistedSessionChanged(i.getPersistedSession(y.id))},handleTerminal:async y=>e.onSessionTerminal(y),handleTurnEnd:(y,w)=>x.handleTurnEnd(y,w),formatLaunchWorkdirLabel:y=>e.formatLaunchWorkdirLabel(y),notifySession:(y,w,F)=>e.notifySession(y,w,F)});return{registry:r,sessions:o,store:i,metrics:s,wakeDispatcher:l,interactions:a,notifications:c,worktrees:m,questions:k,lifecycle:x,restore:p,stateSync:u,references:d,worktreeStrategy:h,worktreeDecisions:b,runtimeBootstrap:A,worktreeMessages:f,maintenance:I}}get persisted(){return this.store.persisted}get idIndex(){return this.store.idIndex}get nameIndex(){return this.store.nameIndex}uniqueName(e){return this.registry.uniqueName(e)}syncRuntimeGcDeadline(e){this.maintenance.syncRuntimeGcDeadline(e)}onPersistedSessionChanged(e){e&&(this.syncPersistedSessionMaintenance(e),this.enforcePersistedRetention())}syncPersistedSessionMaintenance(e){this.maintenance.syncPersistedSessionMaintenance(e)}syncActionTokenExpiryDeadline(){this.maintenance.syncActionTokenExpiryDeadline()}syncTmpOutputCleanupDeadline(e=Date.now()){this.maintenance.syncTmpOutputCleanupDeadline(e)}enforcePersistedRetention(){this.maintenance.enforcePersistedRetention()}bootstrapMaintenanceSchedules(){this.maintenance.bootstrapMaintenanceSchedules()}disposeMaintenance(){this.maintenance.dispose()}spawn(e,n={}){if(this.registry.activeSessionCount()>=this.maxSessions)throw new Error(`Max sessions reached (${this.maxSessions}). Use agent_sessions to list active sessions and agent_kill to end one.`);if(e.sessionIdOverride){let p=this.registry.get(e.sessionIdOverride);if(p?.status==="starting"||p?.status==="running")throw new Error(`Cannot reuse session ID ${e.sessionIdOverride}: that session is still ${p.status}.`);p&&this.registry.remove(p.id),this.clearWaitingTimestampsForSession(e.sessionIdOverride),this.lastTurnCompleteMarkers.delete(e.sessionIdOverride),this.lastTerminalWakeMarkers.delete(e.sessionIdOverride),this.maintenance.cancelRuntimeGc(e.sessionIdOverride)}let o=e.name||ka(e.prompt),i=this.uniqueName(o);if(i!==o&&`${o}${i}`,!e.route?.provider||!e.route.target)throw new Error(`Cannot launch session "${i}": missing explicit route metadata.`);let s=this.checkRepoPolicyForLaunch(e.workdir,e.worktreeStrategy);if(!s.ok){let p=s;throw new Error(p.text)}e.repoIntegrationPolicy=s.resolution.policy,e.repoIntegrationPolicySource=s.resolution.source==="none"?void 0:s.resolution.source,e.repoProvider=s.resolution.provider;let l=this.restore.prepareSpawn(e,i),a=e.harness??"claude-code",d=this,u,c=a==="claude-code"&&!e.canUseTool?async(p,f)=>{if(!u)throw new Error("canUseTool called before session ID was set");return d.handleAskUserQuestion(u,f)}:e.canUseTool,m=new Sr({...e,workdir:l.actualWorkdir,systemPrompt:l.effectiveSystemPrompt,canUseTool:c},i);return u=m.id,this.registry.add(m),this.metrics.incrementLaunched(),this.runtimeBootstrap.initializeSession(m,l,e,n)}async spawnAndAwaitRunning(e,n={}){let r=this.spawn(e,n);return await this.waitForRunningSession(r),r}async waitForRunningSession(e){if(e.status==="running")return;if(Pu.has(e.status))throw new Error(this.describeLaunchFailure(e));let n=e.on?.bind(e),r=e.off?.bind(e)??e.removeListener?.bind(e);if(!n||!r)throw new Error(`Session ${e.name} [${e.id}] did not expose lifecycle events during startup.`);await new Promise((o,i)=>{let s=(a,d)=>{if(d==="running"){l(),o();return}Pu.has(d)&&(l(),i(new Error(this.describeLaunchFailure(e))))},l=()=>{r("statusChange",s)};n("statusChange",s)})}describeLaunchFailure(e){let n=e.killReason?` (reason: ${e.killReason})`:"",r=e.error||e.result?.result||`status=${e.status}${n}`;return`Session ${e.name} [${e.id}] failed to start: ${r}`}formatLaunchResult(e,n){return Mn({prompt:e.prompt,workdir:e.workdir,harness:e.harness,permissionMode:e.permissionMode??D.permissionMode,planApproval:e.planApproval,resumeSessionId:e.resumeSessionId,forkSession:e.forkSession,forceNewSession:e.forceNewSession,clearedPersistedCodexResume:e.clearedPersistedCodexResume},n)}shouldRunWorktreeStrategy(e){let n=e.lifecycle;return!(n==="starting"||n==="awaiting_plan_decision"||n==="awaiting_user_input"||e.pendingPlanApproval)}resolveRepoPolicy(e){let n=hn(e);if(!n)return{source:"none",provider:"unsupported",prAvailable:!1};let r=this.store.getRepoPolicy(n.key);if(r)return{identity:n,policy:r.policy,source:"stored",provider:n.provider,prAvailable:n.provider==="github"&&Ae(),record:r};let o=kl(n);if(o){let i=Di(n,o,"seeded");return{identity:n,policy:o,source:"seeded",provider:n.provider,prAvailable:Oi({provider:n.provider}),record:i}}return{identity:n,source:"unknown",provider:n.provider,prAvailable:Oi({provider:n.provider})}}checkRepoPolicyForLaunch(e,n){let r=n??D.defaultWorktreeStrategy??"off",o=this.resolveRepoPolicy(e);return r==="off"?{ok:!0,resolution:o}:o.source==="none"?{ok:!0,resolution:o}:o.source==="unknown"&&o.identity?{ok:!1,text:Wi(o.identity,r,o.prAvailable)}:{ok:!0,resolution:o}}getRepoPolicyRecordForWorkdir(e){return this.resolveRepoPolicy(e).record}listRepoPolicies(){return this.store.listRepoPolicies()}cleanupRepoPolicies(){let e=[...this.store.cleanupRepoPolicies()],n=[];for(let r of this.store.listRepoPolicies()){let o=hn(r.repoRoot);!o||o.key===r.key||n.push(r.key)}return e.push(...this.store.removeRepoPolicies(n)),e.sort((r,o)=>r.repoRoot.localeCompare(o.repoRoot)||r.key.localeCompare(o.key))}setRepoPolicy(e,n){let r=hn(e);if(r)return this.store.setRepoPolicy(Di(r,n,"stored"))}resetRepoPolicy(e){let n=hn(e);return n?this.store.resetRepoPolicy(n.key):!1}requestRepoPolicyForLaunch(e){let n=e.worktreeStrategy??D.defaultWorktreeStrategy??"off",r=this.resolveRepoPolicy(e.workdir);if(!r.identity)return`Error: ${e.workdir} is not a git repository.`;let o=Wi(r.identity,n,r.prAvailable);if(!e.route?.provider||!e.route.target)return o;let i=`repo-policy:${r.identity.key}`,s=this.interactions.getRepoPolicyChoiceButtons({choiceId:i,route:e.route,repoRoot:r.identity.repoRoot,launchPrompt:e.prompt,launchWorkdir:e.workdir,launchName:e.name,launchModel:e.model,launchReasoningEffort:e.reasoningEffort,launchFastMode:e.fastMode,launchSystemPrompt:e.systemPrompt,launchAllowedTools:e.allowedTools,launchResumeSessionId:e.resumeSessionId,launchResumeWorktreeFrom:e.resumeWorktreeFrom,launchSessionIdOverride:e.sessionIdOverride,launchClearedPersistedCodexResume:e.clearedPersistedCodexResume,launchForkSession:e.forkSession,launchForceNewSession:e.forceNewSession,launchPermissionMode:e.permissionMode,launchPlanApproval:e.planApproval,launchHarness:e.harness,launchWorktreeStrategy:n,launchWorktreeBaseBranch:e.worktreeBaseBranch,launchWorktreePrTargetRepo:e.worktreePrTargetRepo,launchOriginAgentId:e.originAgentId,prAvailable:r.prAvailable}),l=Uy(e,n);return this.notifications.dispatch(this.buildRoutingProxy({id:i,name:"repo-policy",route:e.route}),{label:"repo-policy-choice",idempotencyKey:`repo-policy-choice:${r.identity.key}:${n}:${l}`,userMessage:[o,"","After you choose a policy, OCA will continue this launch automatically."].join(`
266
+ `)}}buildDelegateNotification(e){let{session:n,branchName:r,baseBranch:o,diffSummary:i,policyReason:s,allowedActions:a,originThreadLine:l}=e,d=i.commitMessages.slice(0,5).map(p=>`• ${p.hash} ${p.message} (${p.author})`),u=i.commits>5?`...and ${i.commits-5} more`:void 0,c=n.prompt?n.prompt.slice(0,500):"(no prompt)";return{label:"worktree-delegate",idempotencyKey:["worktree-delegate",n.id,r,o,i.commits,i.commitMessages.map(p=>p.hash).join(",")].join(":"),wakeMessage:cs({sessionName:n.name,sessionId:n.id,branchName:r,baseBranch:o,promptSnippet:c,commitLines:d,moreNote:u,originThreadLine:l,diffSummary:i,allowedActions:a,policyReason:s}),notifyUser:"never"}}};function Cu(t,e=1e3){let n=!Number.isFinite(e),r=typeof t.getOutput=="function"?t.getOutput():[],o=n?r.join(`
267
+ `):Yy(t);return n?o:o.length>e?Mu(t)?xa(o,e):Ta(o,e):o}function Yy(t){let e=typeof t.getOutput=="function"?t.getOutput():[],n=e.join(`
268
+ `).trim();return n?Mu(t)?Zy(n)??n:e.slice(-20).join(`
269
+ `):""}function Mu(t){if(t.status==="completed"||t.killReason==="done")return!0;let e=t;return e.approvalState==="approved"||e.planModeApproved===!0||(e.planDecisionVersion??0)>0}function Zy(t){let n=t.split(/\n\s*\n+/).map(r=>r.trim()).filter(r=>/[A-Za-z0-9]/.test(r)).at(-1);if(n)return n.length>=120||n.includes(`
270
+ `)?n:void 0}Re();ke();se();import{unlinkSync as Xy}from"fs";var qo=class t{timers=new Map;disposed=!1;static MAX_DELAY_MS=2147483647;schedule(e,n,r){if(this.disposed||(this.cancel(e),!Number.isFinite(n)))return;let o=Math.max(0,n-Date.now()),i=setTimeout(()=>{if(this.timers.delete(e),!this.disposed){if(n-Date.now()>0){this.schedule(e,n,r);return}r()}},Math.min(o,t.MAX_DELAY_MS));i.unref?.(),this.timers.set(e,i)}cancel(e){let n=this.timers.get(e);n&&(clearTimeout(n),this.timers.delete(e))}cancelPrefix(e){for(let n of this.timers.keys())n.startsWith(e)&&this.cancel(n)}dispose(){this.disposed=!0;for(let e of this.timers.values())clearTimeout(e);this.timers.clear()}};X();fn();ke();var _u=10080*60*1e3,ek=300*1e3,$u="tmp-output:cleanup",tk=60*1e3;function nk(t){return t instanceof Error?t.message:String(t)}var Ko=class{constructor(e){this.deps=e}deps;scheduler=new qo;lastTmpOutputCleanupAttemptAt;schedule(e,n,r){this.scheduler.schedule(e,n,r)}cancel(e){this.scheduler.cancel(e)}cancelPrefix(e){this.scheduler.cancelPrefix(e)}bootstrapMaintenanceSchedules(){let e=Date.now();this.runTmpOutputCleanup(e);for(let n of this.deps.store.listPersistedSessions())this.syncPersistedSessionMaintenance(n);this.syncActionTokenExpiryDeadline(),this.deps.store.cleanupOrphanOutputFiles(),this.syncTmpOutputCleanupDeadline(e)}syncRuntimeGcDeadline(e){if(!e.completedAt)return;let n=this.runtimeGcKey(e.id);this.schedule(n,e.completedAt+this.runtimeGcMaxAgeMs(),()=>{let r=this.deps.sessions.get(e.id);if(!r||!r.completedAt)return;let o=this.runtimeGcMaxAgeMs();if(!this.deps.store.shouldGcActiveSession(r,Date.now(),o)){this.syncRuntimeGcDeadline(r);return}this.deps.removeRuntimeSession(e.id),this.deps.persistSession(r,{scheduleRuntimeGc:!1}),this.deps.clearRuntimeSessionState(e.id)})}cancelRuntimeGc(e){this.cancel(this.runtimeGcKey(e))}cancelPersistedMaintenance(e){let n=this.persistedMaintenanceRef(e);n&&this.cancelPrefix(`persisted:${n}:`)}syncPersistedSessionMaintenance(e){let n=this.persistedMaintenanceRef(e);if(!n)return;this.cancel(this.persistedMaintenanceKey(n,"worktree-reminder"));let r=this.deps.reminders.getNextReminderAt(e);r!=null?this.schedulePersistedWorktreeReminder(n,r):this.deps.reminders.clearResolvedReminderState(e),this.cancel(this.persistedMaintenanceKey(n,"worktree-retention"));let o=je(e,{activeSession:!1,includePrSync:e.worktreeLifecycle?.state==="pr_open"||!!e.worktreePrUrl}),i=this.resolvedAtIso(e),s=this.isLegacyResolvedWorktree(e);if((o.cleanupSafe||s)&&typeof i=="string"){let a=new Date(i).getTime();Number.isFinite(a)&&this.schedule(this.persistedMaintenanceKey(n,"worktree-retention"),a+_u,()=>{let l=this.deps.store.getPersistedSession(n);l&&this.reconcileResolvedWorktreeRetention(l,Date.now())})}}reconcileResolvedWorktreeRetention(e,n){let r=je(e,{activeSession:!1,includePrSync:e.worktreeLifecycle?.state==="pr_open"||!!e.worktreePrUrl}),o=this.resolvedAtIso(e),i=o?new Date(o).getTime():0,s=this.legacyResolvedWorktreeState(e);if(!(!r.cleanupSafe&&!s||!o||!Number.isFinite(i)||n-i<_u))try{if(!e.worktreePath&&!de(e))return;let a=this.deps.resolveWorktreeRepoDir(e.workdir,e.worktreePath);if(!a)return;let l=de(e)?!1:ce(a,e.worktreePath);if(!de(e)&&!l)return;for(let d of me(e))this.deps.updatePersistedSession(d,{worktreePath:void 0,worktreeBranch:void 0,worktreeState:"none",pendingWorktreeDecisionSince:void 0,lastWorktreeReminderAt:void 0,worktreeDecisionSnoozedUntil:void 0,worktreeLifecycle:{...e.worktreeLifecycle??r.lifecycle,state:r.cleanupSafe?r.derivedState:s??r.derivedState,updatedAt:new Date(n).toISOString(),resolvedAt:e.worktreeLifecycle?.resolvedAt??o,resolutionSource:e.worktreeLifecycle?.resolutionSource??"maintenance",notes:r.reasons}})}catch(a){`${e.worktreePath}${nk(a)}`}}syncActionTokenExpiryDeadline(){let e="tokens:expiry";this.cancel(e);let n=this.deps.store.getNextActionTokenExpiry();n!=null&&this.schedule(e,n,()=>{this.deps.store.purgeExpiredActionTokens(Date.now())||this.syncActionTokenExpiryDeadline()})}syncTmpOutputCleanupDeadline(e=Date.now()){this.cancel($u);let n=this.deps.store.getNextTmpOutputCleanupAt(e);if(n==null){this.lastTmpOutputCleanupAttemptAt=void 0;return}n>e&&(this.lastTmpOutputCleanupAttemptAt=void 0),this.schedule($u,this.getTmpOutputCleanupScheduleAt(n,e),()=>{let r=Date.now();this.runTmpOutputCleanup(r),this.syncTmpOutputCleanupDeadline(r)})}enforcePersistedRetention(){let e=this.deps.store.evictOldestPersisted(this.deps.getMaxPersistedSessions());for(let n of e)this.cancelPersistedMaintenance(n),n.sessionId&&this.cancelRuntimeGc(n.sessionId),this.cleanupOutputPathIfUnreferenced(n.outputPath)}dispose(){this.scheduler.dispose()}persistedMaintenanceRef(e){return e.sessionId??$(e)??e.harnessSessionId}runtimeGcKey(e){return`runtime-gc:${e}`}persistedMaintenanceKey(e,n){return`persisted:${e}:${n}`}runtimeGcMaxAgeMs(){return(D.sessionGcAgeMinutes??1440)*6e4}runTmpOutputCleanup(e){this.lastTmpOutputCleanupAttemptAt=e,this.deps.store.cleanupTmpOutputFiles(e)}getTmpOutputCleanupScheduleAt(e,n){if(e>n||this.lastTmpOutputCleanupAttemptAt==null)return e;let r=this.lastTmpOutputCleanupAttemptAt+tk;return r>n?r:e}schedulePersistedWorktreeReminder(e,n){let r=this.persistedMaintenanceKey(e,"worktree-reminder");this.schedule(r,n,()=>{let o=this.deps.store.getPersistedSession(e);if(!o||this.deps.reminders.sendReminderIfDue(o,Date.now()))return;let s=this.deps.reminders.getNextReminderAt(o);s!=null&&this.schedulePersistedWorktreeReminder(e,Math.max(s,Date.now()+ek))})}cleanupOutputPathIfUnreferenced(e){if(!(!e||this.deps.store.hasOutputPathReference(e)))try{Xy(e)}catch{}}resolvedAtIso(e){return e.worktreeLifecycle?.resolvedAt??e.worktreeMergedAt??e.worktreeDismissedAt??(e.completedAt?new Date(e.completedAt).toISOString():void 0)}isLegacyResolvedWorktree(e){return this.legacyResolvedWorktreeState(e)!=null}legacyResolvedWorktreeState(e){if(e.worktreeMerged===!0||e.worktreeDisposition==="merged"||e.worktreeState==="merged")return"merged";if(e.worktreeDisposition==="dismissed"||e.worktreeState==="dismissed")return"dismissed";if(e.worktreeDisposition==="no-change-cleaned")return"no_change"}};Sn();var Eu=new Set(["completed","failed","killed"]),rk=new Set(["starting","running"]),ok=5e3;function ik(t,e){return Du("sha256").update(JSON.stringify({route:t.route?{provider:t.route.provider,target:t.route.target,accountId:t.route.accountId,threadId:t.route.threadId,sessionKey:t.route.sessionKey}:void 0,prompt:t.prompt,workdir:t.workdir,name:t.name,model:t.model,reasoningEffort:t.reasoningEffort,fastMode:t.fastMode,systemPrompt:t.systemPrompt,allowedTools:t.allowedTools?[...t.allowedTools].sort():t.allowedTools,resumeSessionId:t.resumeSessionId,resumeWorktreeFrom:t.resumeWorktreeFrom,sessionIdOverride:t.sessionIdOverride,clearedPersistedCodexResume:t.clearedPersistedCodexResume,forkSession:t.forkSession,forceNewSession:t.forceNewSession,permissionMode:t.permissionMode,planApproval:t.planApproval,harness:t.harness,worktreeStrategy:t.worktreeStrategy,effectiveWorktreeStrategy:e,worktreeBaseBranch:t.worktreeBaseBranch,worktreePrTargetRepo:t.worktreePrTargetRepo,originAgentId:t.originAgentId})).digest("hex").slice(0,16)}function sk(t){return Du("sha256").update(JSON.stringify({route:t.route?{provider:t.route.provider,target:t.route.target,accountId:t.route.accountId,threadId:t.route.threadId,sessionKey:t.route.sessionKey}:void 0,prompt:t.launchPrompt,workdir:t.launchWorkdir,name:t.launchName,model:t.launchModel,reasoningEffort:t.launchReasoningEffort,fastMode:t.launchFastMode,systemPrompt:t.launchSystemPrompt,allowedTools:t.launchAllowedTools?[...t.launchAllowedTools].sort():t.launchAllowedTools,resumeSessionId:t.launchResumeSessionId,resumeWorktreeFrom:t.launchResumeWorktreeFrom,sessionIdOverride:t.launchSessionIdOverride,clearedPersistedCodexResume:t.launchClearedPersistedCodexResume,forkSession:t.launchForkSession,forceNewSession:t.launchForceNewSession,permissionMode:t.launchPermissionMode,planApproval:t.launchPlanApproval,harness:t.launchHarness,worktreeStrategy:t.launchWorktreeStrategy,worktreeBaseBranch:t.launchWorktreeBaseBranch,worktreePrTargetRepo:t.launchWorktreePrTargetRepo,originAgentId:t.launchOriginAgentId})).digest("hex").slice(0,16)}var Uo=class t{registry;sessions;maxSessions;maxPersistedSessions;lastWaitingEventTimestamps=new Map;lastTurnCompleteMarkers=new Map;lastTerminalWakeMarkers=new Map;mergeQueue=new Ut;pendingAskUserQuestions=new Map;store;metrics;wakeDispatcher;interactions;notifications;worktrees;questions;lifecycle;restore;stateSync;references;worktreeStrategy;worktreeDecisions;runtimeBootstrap;worktreeMessages;maintenance;constructor(e=20,n=50,r={}){this.maxSessions=e,this.maxPersistedSessions=n;let o=t.createServiceBundle(this,r);this.registry=o.registry,this.sessions=o.sessions,this.store=o.store,this.metrics=o.metrics,this.wakeDispatcher=o.wakeDispatcher,this.interactions=o.interactions,this.notifications=o.notifications,this.worktrees=o.worktrees,this.questions=o.questions,this.lifecycle=o.lifecycle,this.restore=o.restore,this.stateSync=o.stateSync,this.references=o.references,this.worktreeStrategy=o.worktreeStrategy,this.worktreeDecisions=o.worktreeDecisions,this.runtimeBootstrap=o.runtimeBootstrap,this.worktreeMessages=o.worktreeMessages,this.maintenance=o.maintenance}static createServiceBundle(e,n){let r=new Lo,o=r.sessions,i=new ho(n.store),s=new yo,a=new Ao,l=new Io(i.actionTokenStore,Ie),d=new oo(o,i),u=new ro({store:i,sessions:o,resolveSession:k=>d.resolveActive(k)}),c=new Mo(a,(k,P)=>u.applySessionPatch(k,P),{getPersistedSession:k=>i.getPersistedSession(k)}),p=new _o,g=new no(k=>i.getPersistedSession(k)),m=new Fo,f=new co({shouldRunWorktreeStrategy:k=>e.shouldRunWorktreeStrategy(k),isAlreadyMerged:k=>e.isAlreadyMerged(k),resolveWorktreeRepoDir:(k,P)=>e.resolveWorktreeRepoDir(k,P),getWorktreeCompletionState:(k,P,F,pe)=>e.getWorktreeCompletionState(k,P,F,pe),updatePersistedSession:(k,P)=>e.updatePersistedSession(k,P),dispatchSessionNotification:(k,P)=>e.dispatchSessionNotification(k,P),getOutputPreview:(k,P)=>e.getOutputPreview(k,P),originThreadLine:k=>e.originThreadLine(k),getWorktreeDecisionButtons:k=>e.getWorktreeDecisionButtons(k),getPolicyAwareWorktreeDecisionButtons:(k,P,F)=>e.getWorktreeDecisionButtons(k,P,F),makeOpenPrButton:k=>e.makeActionButton(k,"worktree-create-pr","Open PR"),isPrAvailable:k=>e.resolveRepoPolicy(k).prAvailable,resolveRepoPolicy:k=>e.resolveRepoPolicy(k),worktreeSummaryProvider:n.worktreeSummaryProvider,worktreeMessages:m,enqueueMerge:(k,P,F)=>e.enqueueMerge(k,P,F),mergeBranch:Sr,spawnConflictResolver:async({session:k,worktreePath:P,prompt:F})=>e.spawn({prompt:F,workdir:P,name:`${k.name}-conflict-resolver`,harness:k.harnessName||le(),model:k.model,reasoningEffort:k.reasoningEffort,fastMode:k.fastMode,permissionMode:"bypassPermissions",multiTurn:!0,worktreeStrategy:"off",autoMergeParentSessionId:k.id,route:k.route,originChannel:k.originChannel,originThreadId:k.originThreadId,originAgentId:k.originAgentId,originSessionKey:k.originSessionKey},{notifyLaunch:!1}),runAutoPr:async(k,P)=>{let{makeAgentPrTool:F}=await Promise.resolve().then(()=>(qr(),Ol));return{success:(await F().execute("auto-pr",{session:k.id,base_branch:P}))?.meta?.success===!0}}}),y=new $o(e.pendingAskUserQuestions,(k,P)=>e.dispatchSessionNotification(k,P),k=>{e.clearWaitingTimestampsForSession(k)},(k,P,F)=>l.getQuestionButtons(k,P,F)),S=new Eo(k=>e.buildRoutingProxy(k),(k,P)=>c.dispatch(k,P),(k,P)=>e.updatePersistedSession(k,P),(k,P)=>e.getPolicyAwareWorktreeDecisionButtons(k,{},void 0,P)),R=new Ko({store:i,sessions:o,reminders:S,removeRuntimeSession:k=>r.remove(k),persistSession:(k,P)=>e.persistSession(k,P),clearRuntimeSessionState:k=>{e.clearWaitingTimestampsForSession(k),e.lastTurnCompleteMarkers.delete(k),e.lastTerminalWakeMarkers.delete(k)},resolveWorktreeRepoDir:(k,P)=>e.resolveWorktreeRepoDir(k,P),updatePersistedSession:(k,P)=>e.updatePersistedSession(k,P),getMaxPersistedSessions:()=>e.maxPersistedSessions});i.onActionTokensChanged(()=>e.syncActionTokenExpiryDeadline());let I=new Wo({persistSession:k=>e.persistSession(k),clearWaitingTimestamp:k=>{e.clearWaitingTimestampsForSession(k)},handleWorktreeStrategy:k=>e.handleWorktreeStrategy(k),resolveWorktreeRepoDir:(k,P)=>e.resolveWorktreeRepoDir(k,P),updatePersistedSession:(k,P)=>e.updatePersistedSession(k,P),dispatchSessionNotification:(k,P)=>e.dispatchSessionNotification(k,P),notifySession:(k,P,F)=>e.notifySession(k,P,F),clearRetryTimersForSession:k=>a.clearRetryTimersForSession(k),hasTurnCompleteWakeMarker:k=>e.lastTurnCompleteMarkers.has(k),shouldEmitTurnCompleteWake:k=>e.shouldEmitTurnCompleteWake(k),shouldEmitTerminalWake:k=>e.shouldEmitTerminalWake(k),resolvePlanApprovalMode:k=>e.resolvePlanApprovalMode(k),getPlanApprovalButtons:(k,P)=>l.getPlanApprovalButtons(k,P),getResumeButtons:(k,P)=>l.getResumeButtons(k,P),getQuestionButtons:(k,P,F)=>l.getQuestionButtons(k,P,F),extractLastOutputLine:k=>e.extractLastOutputLine(k),getOutputPreview:(k,P)=>e.getOutputPreview(k,P),originThreadLine:k=>e.originThreadLine(k),debounceWaitingEvent:(k,P)=>e.debounceWaitingEvent(k,P),isAlreadyMerged:k=>e.isAlreadyMerged(k),questionContextSummaryProvider:n.questionContextSummaryProvider??Au()}),b=new No({getPersistedSession:k=>i.getPersistedSession(k),resolveActiveSession:k=>d.resolveActive(k),resolveWorktreeRepoDir:(k,P)=>e.resolveWorktreeRepoDir(k,P),updatePersistedSession:(k,P)=>e.updatePersistedSession(k,P),dispatchNotification:(k,P)=>c.dispatch(k,P),buildRoutingProxy:k=>e.buildRoutingProxy(k)}),A=new Bo({hydrateSpawnedSession:(k,P,F)=>{g.hydrateSpawnedSession(k,P,F)},markRunning:k=>{i.markRunning(k),e.onPersistedSessionChanged(i.getPersistedSession(k.id))},handleTerminal:async k=>e.onSessionTerminal(k),handleTurnEnd:(k,P)=>I.handleTurnEnd(k,P),formatLaunchWorkdirLabel:k=>e.formatLaunchWorkdirLabel(k),notifySession:(k,P,F)=>e.notifySession(k,P,F)});return{registry:r,sessions:o,store:i,metrics:s,wakeDispatcher:a,interactions:l,notifications:c,worktrees:p,questions:y,lifecycle:I,restore:g,stateSync:u,references:d,worktreeStrategy:f,worktreeDecisions:b,runtimeBootstrap:A,worktreeMessages:m,maintenance:R}}get persisted(){return this.store.persisted}get idIndex(){return this.store.idIndex}get nameIndex(){return this.store.nameIndex}uniqueName(e){return this.registry.uniqueName(e)}syncRuntimeGcDeadline(e){this.maintenance.syncRuntimeGcDeadline(e)}onPersistedSessionChanged(e){e&&(this.syncPersistedSessionMaintenance(e),this.enforcePersistedRetention())}syncPersistedSessionMaintenance(e){this.maintenance.syncPersistedSessionMaintenance(e)}syncActionTokenExpiryDeadline(){this.maintenance.syncActionTokenExpiryDeadline()}syncTmpOutputCleanupDeadline(e=Date.now()){this.maintenance.syncTmpOutputCleanupDeadline(e)}enforcePersistedRetention(){this.maintenance.enforcePersistedRetention()}bootstrapMaintenanceSchedules(){this.maintenance.bootstrapMaintenanceSchedules()}disposeMaintenance(){this.maintenance.dispose()}spawn(e,n={}){if(this.registry.activeSessionCount()>=this.maxSessions)throw new Error(`Max sessions reached (${this.maxSessions}). Use agent_sessions to list active sessions and agent_kill to end one.`);if(e.sessionIdOverride){let g=this.registry.get(e.sessionIdOverride);if(g?.status==="starting"||g?.status==="running")throw new Error(`Cannot reuse session ID ${e.sessionIdOverride}: that session is still ${g.status}.`);g&&this.registry.remove(g.id),this.clearWaitingTimestampsForSession(e.sessionIdOverride),this.lastTurnCompleteMarkers.delete(e.sessionIdOverride),this.lastTerminalWakeMarkers.delete(e.sessionIdOverride),this.maintenance.cancelRuntimeGc(e.sessionIdOverride)}let o=e.name||Aa(e.prompt),i=this.uniqueName(o);if(i!==o&&`${o}${i}`,!e.route?.provider||!e.route.target)throw new Error(`Cannot launch session "${i}": missing explicit route metadata.`);let s=this.checkRepoPolicyForLaunch(e.workdir,e.worktreeStrategy);if(!s.ok){let g=s;throw new Error(g.text)}e.repoIntegrationPolicy=s.resolution.policy,e.repoIntegrationPolicySource=s.resolution.source==="none"?void 0:s.resolution.source,e.repoProvider=s.resolution.provider;let a=this.restore.prepareSpawn(e,i),l=e.harness??"claude-code",d=this,u,c=l==="claude-code"&&!e.canUseTool?async(g,m)=>{if(!u)throw new Error("canUseTool called before session ID was set");return d.handleAskUserQuestion(u,m)}:e.canUseTool,p=new wr({...e,workdir:a.actualWorkdir,systemPrompt:a.effectiveSystemPrompt,canUseTool:c},i);return u=p.id,this.registry.add(p),this.metrics.incrementLaunched(),this.runtimeBootstrap.initializeSession(p,a,e,n)}async spawnAndAwaitRunning(e,n={}){let r=this.spawn(e,n);return await this.waitForRunningSession(r),r}async waitForRunningSession(e){if(e.status==="running")return;if(Eu.has(e.status))throw new Error(this.describeLaunchFailure(e));let n=e.on?.bind(e),r=e.off?.bind(e)??e.removeListener?.bind(e);if(!n||!r)throw new Error(`Session ${e.name} [${e.id}] did not expose lifecycle events during startup.`);await new Promise((o,i)=>{let s=(l,d)=>{if(d==="running"){a(),o();return}Eu.has(d)&&(a(),i(new Error(this.describeLaunchFailure(e))))},a=()=>{r("statusChange",s)};n("statusChange",s)})}describeLaunchFailure(e){let n=e.killReason?` (reason: ${e.killReason})`:"",r=e.error||e.result?.result||`status=${e.status}${n}`;return`Session ${e.name} [${e.id}] failed to start: ${r}`}formatLaunchResult(e,n){return $n({prompt:e.prompt,workdir:e.workdir,harness:e.harness,permissionMode:e.permissionMode??D.permissionMode,planApproval:e.planApproval,resumeSessionId:e.resumeSessionId,forkSession:e.forkSession,forceNewSession:e.forceNewSession,clearedPersistedCodexResume:e.clearedPersistedCodexResume},n)}shouldRunWorktreeStrategy(e){let n=e.lifecycle;return!(n==="starting"||n==="awaiting_plan_decision"||n==="awaiting_user_input"||e.pendingPlanApproval)}resolveRepoPolicy(e){let n=yn(e);if(!n)return{source:"none",provider:"unsupported",prAvailable:!1};let r=this.store.getRepoPolicy(n.key);if(r)return{identity:n,policy:r.policy,source:"stored",provider:n.provider,prAvailable:n.provider==="github"&&Ie(),record:r};let o=Al(n);if(o){let i=Li(n,o,"seeded");return{identity:n,policy:o,source:"seeded",provider:n.provider,prAvailable:Bi({provider:n.provider}),record:i}}return{identity:n,source:"unknown",provider:n.provider,prAvailable:Bi({provider:n.provider})}}checkRepoPolicyForLaunch(e,n){let r=n??D.defaultWorktreeStrategy??"off",o=this.resolveRepoPolicy(e);return r==="off"?{ok:!0,resolution:o}:o.source==="none"?{ok:!0,resolution:o}:o.source==="unknown"&&o.identity?{ok:!1,text:Fi(o.identity,r,o.prAvailable)}:{ok:!0,resolution:o}}getRepoPolicyRecordForWorkdir(e){return this.resolveRepoPolicy(e).record}listRepoPolicies(){return this.store.listRepoPolicies()}cleanupRepoPolicies(){let e=[...this.store.cleanupRepoPolicies()],n=[];for(let r of this.store.listRepoPolicies()){let o=yn(r.repoRoot);!o||o.key===r.key||n.push(r.key)}return e.push(...this.store.removeRepoPolicies(n)),e.sort((r,o)=>r.repoRoot.localeCompare(o.repoRoot)||r.key.localeCompare(o.key))}setRepoPolicy(e,n){let r=yn(e);if(r)return this.store.setRepoPolicy(Li(r,n,"stored"))}resetRepoPolicy(e){let n=yn(e);return n?this.store.resetRepoPolicy(n.key):!1}requestRepoPolicyForLaunch(e){let n=e.worktreeStrategy??D.defaultWorktreeStrategy??"off",r=this.resolveRepoPolicy(e.workdir);if(!r.identity)return`Error: ${e.workdir} is not a git repository.`;let o=Fi(r.identity,n,r.prAvailable);if(!e.route?.provider||!e.route.target)return o;let i=`repo-policy:${r.identity.key}`,s=this.interactions.getRepoPolicyChoiceButtons({choiceId:i,route:e.route,repoRoot:r.identity.repoRoot,launchPrompt:e.prompt,launchWorkdir:e.workdir,launchName:e.name,launchModel:e.model,launchReasoningEffort:e.reasoningEffort,launchFastMode:e.fastMode,launchSystemPrompt:e.systemPrompt,launchAllowedTools:e.allowedTools,launchResumeSessionId:e.resumeSessionId,launchResumeWorktreeFrom:e.resumeWorktreeFrom,launchSessionIdOverride:e.sessionIdOverride,launchClearedPersistedCodexResume:e.clearedPersistedCodexResume,launchForkSession:e.forkSession,launchForceNewSession:e.forceNewSession,launchPermissionMode:e.permissionMode,launchPlanApproval:e.planApproval,launchHarness:e.harness,launchWorktreeStrategy:n,launchWorktreeBaseBranch:e.worktreeBaseBranch,launchWorktreePrTargetRepo:e.worktreePrTargetRepo,launchOriginAgentId:e.originAgentId,prAvailable:r.prAvailable}),a=ik(e,n);return this.notifications.dispatch(this.buildRoutingProxy({id:i,name:"repo-policy",route:e.route}),{label:"repo-policy-choice",idempotencyKey:`repo-policy-choice:${r.identity.key}:${n}:${a}`,userMessage:[o,"","After you choose a policy, OCA will continue this launch automatically."].join(`
269
271
  `),notifyUser:"always",requireDirectUserNotification:!0,buttons:s,wakeMessageOnNotifySuccess:["Repo policy choice buttons delivered to the user.",`Repo: ${r.identity.repoRoot}`,"Wait for their policy choice; do not set the policy or relaunch separately."].join(`
270
- `),wakeMessageOnNotifyFailed:o}),[`Repo policy choice prompt sent for ${r.identity.repoRoot}.`,r.prAvailable?"Wait for the user's Require PR, Merge or PR, No PR, or Manual response.":"Wait for the user's No PR or Manual response.","Do not send a separate plain-text policy question."].join(" ")}launchAfterRepoPolicyChoice(e){let n=e.route;if(!n?.provider||!n.target)throw new Error("missing route metadata for stored launch");let r=e.harness??ae(),o=e.permissionMode??D.permissionMode,i=e.planApproval??D.planApproval,s=this.spawn({prompt:e.prompt,workdir:e.workdir,sessionIdOverride:e.sessionIdOverride,name:e.name,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,systemPrompt:e.systemPrompt,allowedTools:e.allowedTools,resumeSessionId:e.resumeSessionId,resumeWorktreeFrom:e.resumeWorktreeFrom,forkSession:e.resumeSessionId?e.forkSession:!1,multiTurn:!0,permissionMode:o,planApproval:i,codexApprovalPolicy:r==="codex"?"never":void 0,originChannel:this.originChannelFromRoute(n),originThreadId:n.threadId,originAgentId:e.originAgentId,originSessionKey:n.sessionKey,route:n,harness:r,worktreeStrategy:e.worktreeStrategy,worktreeBaseBranch:e.worktreeBaseBranch,worktreePrTargetRepo:e.worktreePrTargetRepo});return{session:s,text:this.formatLaunchResult({prompt:e.prompt,workdir:e.workdir,harness:r,permissionMode:o,planApproval:i,forceNewSession:e.forceNewSession,resumeSessionId:e.resumeSessionId,forkSession:e.forkSession,clearedPersistedCodexResume:e.clearedPersistedCodexResume},s)}}continueLaunchAfterManualRepoPolicy(e,n){let r=this.resolveRepoPolicy(e);if(!r.identity)return{kind:"none"};let o=this.interactions.listActiveActionTokens("repo-policy-set").filter(u=>u.repoPolicyWorkdir===r.identity?.repoRoot),i=()=>{for(let u of new Set(o.map(c=>c.sessionId)))this.clearRepoPolicyChoiceTokens(u)},s=o.filter(u=>u.repoPolicy===n&&!!u.launchPrompt&&!!u.launchWorkdir&&!!u.route?.provider&&!!u.route?.target);if(s.length===0)return i(),{kind:"none"};let l=new Map;for(let u of s){let c=Ky(u);l.has(c)||l.set(c,u)}if(l.size>1)return i(),{kind:"ambiguous",count:l.size};let a=[...l.values()][0];if(!a.launchPrompt||!a.launchWorkdir)return{kind:"none"};let d=this.launchAfterRepoPolicyChoice({route:a.route,prompt:a.launchPrompt,workdir:a.launchWorkdir,name:a.launchName,model:a.launchModel,reasoningEffort:a.launchReasoningEffort,fastMode:a.launchFastMode,systemPrompt:a.launchSystemPrompt,allowedTools:a.launchAllowedTools,resumeSessionId:a.launchResumeSessionId,resumeWorktreeFrom:a.launchResumeWorktreeFrom,sessionIdOverride:a.launchSessionIdOverride,clearedPersistedCodexResume:a.launchClearedPersistedCodexResume,forkSession:a.launchForkSession,forceNewSession:a.launchForceNewSession,permissionMode:a.launchPermissionMode,planApproval:a.launchPlanApproval,harness:a.launchHarness,worktreeStrategy:a.launchWorktreeStrategy,worktreeBaseBranch:a.launchWorktreeBaseBranch,worktreePrTargetRepo:a.launchWorktreePrTargetRepo,originAgentId:a.launchOriginAgentId});return this.consumeActionToken(a.id),this.clearRepoPolicyChoiceTokens(a.sessionId),{kind:"launched",...d}}makeActionButton(e,n,r,o={}){return this.interactions.makeActionButton(e,n,r,o)}consumeActionToken(e){return this.interactions.consumeActionToken(e)}getActionToken(e){return this.interactions.getActionToken(e)}clearRepoPolicyChoiceTokens(e){this.interactions.clearRepoPolicyChoiceTokens(e)}clearPlanDecisionTokens(e,n){this.interactions.clearPlanDecisionTokens(e,n)}isCurrentPendingPlanDecision(e,n){let r=this.resolve(e)??this.getPersistedSession(e);return Cn(r,n)}dispatchPlanApprovalFallback(e,n,r){let o=new Date().toISOString();this.notifications.dispatch(e,{label:"plan-approval-fallback",idempotencyKey:`plan-approval:${e.id}:v${n??"unknown"}:fallback`,userMessage:An({session:e,summary:r}),notifyUser:"always",shouldDispatch:()=>this.isCurrentPendingPlanDecision(e.id,n),hooks:{onNotifyStarted:()=>{this.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"sending",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o})},onNotifySucceeded:()=>{this.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"fallback_delivered",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o,approvalPromptDeliveredAt:new Date().toISOString(),approvalPromptFailedAt:void 0})},onNotifyFailed:()=>{this.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"failed",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o,approvalPromptFailedAt:new Date().toISOString()})}},wakeMessageOnNotifySuccess:Kt(e,n,!0),wakeMessageOnNotifyFailed:Mo({session:e,planDecisionVersion:n})})}getWorktreeDecisionButtons(e,n={},r={merge:!0,pr:!0}){let o=this.resolve(e)??this.getPersistedSession(e);if(!(!o||o.worktreeStrategy==="delegate"&&n.allowDelegate!==!0))return this.interactions.getWorktreeDecisionButtons(e,o,r)}getPolicyAwareWorktreeDecisionButtons(e,n={},r,o){let i=r??this.resolve(e),s=o??this.getPersistedSession(e),l=this.resolveWorktreeRepoDir(i?.originalWorkdir??s?.workdir,i?.worktreePath??s?.worktreePath),a=l?this.resolveRepoPolicy(l):void 0,d=i?.repoIntegrationPolicy??s?.repoIntegrationPolicy,u=d??a?.policy,c=a?.prAvailable??!!(d&&d!=="never-pr"&&d!=="manual"),m=u?Ei({policy:u,prAvailable:c}):{merge:!0,pr:!0};return this.getWorktreeDecisionButtons(e,n,m)}getWorktreeCompletionState(e,n,r,o){return this.worktrees.getCompletionState(e,n,r,o)}notifyWorktreeOutcome(e,n,r){this.notifications.notifyWorktreeOutcome(e,n,r)}requestPlanApprovalFromUser(e,n){let r=n.trim();if(!r)return"Error: summary must not be empty.";let o=ds(r),i=this.resolve(e),s=i?void 0:this.getPersistedSession(e),l=i??s;if(!l)return`Error: Session "${e}" not found.`;if(!l.pendingPlanApproval)return`Error: Session "${e}" is not awaiting plan approval.`;let a=U(i??s??{id:e})??e;if(this.resolvePlanApprovalMode(l)!=="delegate")return`Error: Session "${e}" already uses direct user plan approval. Do not send a duplicate approval prompt.`;let d=l.actionablePlanDecisionVersion??l.planDecisionVersion;if(Tn(l,d))return[`An actionable plan review prompt already exists for session ${l.name} [${a}].`,"Wait for the user's Approve, Revise, or Reject response.","Do not send a separate plain-text approval message."].join(" ");if(l.deliveryState==="notifying")return[`A plan approval prompt is already being delivered for session ${l.name} [${a}].`,"Wait for delivery to finish before retrying."].join(" ");let u=this.interactions.getPlanApprovalButtons(a,{...l,planDecisionVersion:d}),c=[`📋 [${l.name}] Plan v${d??"?"} needs your decision:`,"","Why this was escalated:","",o,"","Choose Approve, Revise, or Reject below."].join(`
271
- `);return this.notifications.dispatch(this.buildRoutingProxy({id:a,name:l.name,sessionId:s?.sessionId,harnessSessionId:i?.harnessSessionId??s?.harnessSessionId,backendRef:i?.backendRef??s?.backendRef,route:i?.route??s?.route}),{label:"plan-approval",idempotencyKey:`plan-approval:${a}:v${d??"unknown"}:canonical`,userMessage:c,notifyUser:"always",buttons:u,hooks:{onNotifyStarted:()=>{this.updatePersistedSession(a,{approvalPromptRequiredVersion:d,approvalPromptStatus:"sending",approvalPromptVersion:d,approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptLastAttemptAt:new Date().toISOString()})},onNotifySucceeded:()=>{this.updatePersistedSession(a,{canonicalPlanPromptVersion:d,approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"delivered",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptDeliveredAt:new Date().toISOString(),approvalPromptFailedAt:void 0})},onNotifyFailed:()=>{this.updatePersistedSession(a,{approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"failed",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptFailedAt:new Date().toISOString()})}},shouldDispatch:()=>this.isCurrentPendingPlanDecision(a,d),onUserNotifyFailed:()=>this.dispatchPlanApprovalFallback(this.buildRoutingProxy({id:a,name:l.name,sessionId:s?.sessionId,harnessSessionId:i?.harnessSessionId??s?.harnessSessionId,backendRef:i?.backendRef??s?.backendRef,route:i?.route??s?.route}),d,o),wakeMessageOnNotifySuccess:Kt({id:a,name:l.name},d)}),[`Canonical plan approval prompt sent for session ${l.name} [${a}].`,"Wait for the user's Approve, Revise, or Reject response.","Do not send a separate plain-text approval message."].join(" ")}requestWorktreeDecisionFromUser(e,n){let r=n.trim();if(!r)return"Error: summary must not be empty.";let o=this.resolve(e),i=this.getPersistedSession(e),s=o??i;if(!s)return`Error: Session "${e}" not found.`;if(s.worktreeStrategy!=="delegate")return`Error: Session "${e}" already uses direct user worktree decisions. Do not send a duplicate decision prompt.`;if(!(!!("pendingWorktreeDecisionSince"in s?s.pendingWorktreeDecisionSince:void 0)||s.worktreeState==="pending_decision"||s.worktreeLifecycle?.state==="pending_decision"))return`Error: Session "${e}" is not awaiting a delegated worktree decision.`;let d=U(o??i??{id:e})??e,u=o?.worktreePath??i?.worktreePath,c=o?.worktreeBranch??i?.worktreeBranch,m=this.resolveWorktreeRepoDir(o?.originalWorkdir??i?.workdir,u);if(!u)return`Error: Session "${e}" has no managed worktree path.`;if(!c)return`Error: Session "${e}" has no managed worktree branch.`;if(!m)return`Error: Session "${e}" has no resolvable repository root for worktree ${u}.`;let p=o?.worktreeBaseBranch??i?.worktreeBaseBranch??Ce(m),f=Oe(m,c,p);if(!f)return`Error: Could not compute worktree diff summary for session "${e}".`;let h=this.getPolicyAwareWorktreeDecisionButtons(d,{allowDelegate:!0},o,i);if(!h||h.length===0)return`Error: Could not create worktree decision buttons for session "${e}".`;let k=r.split(/\r?\n/).map(v=>v.replace(/^[-*]\s+/,"").trim()).filter(v=>v.length>0);return this.notifications.dispatch(this.buildRoutingProxy({id:d,name:s.name,sessionId:i?.sessionId,harnessSessionId:o?.harnessSessionId??i?.harnessSessionId,backendRef:o?.backendRef??i?.backendRef,route:o?.route??i?.route}),this.worktreeMessages.buildAskNotification({session:{id:d,name:s.name,worktreePrTargetRepo:o?.worktreePrTargetRepo??i?.worktreePrTargetRepo},branchName:c,baseBranch:p,diffSummary:f,summaryLines:k,buttons:h})),[`Canonical worktree decision prompt sent for session ${s.name} [${d}].`,"Wait for the user's Merge, Open PR, Later, or Discard response.","Do not send a separate plain-text worktree decision message."].join(" ")}buildRoutingProxy(e){return{id:U(e)??$(e)??e.harnessSessionId??"unknown-session",name:e.name,harnessSessionId:e.harnessSessionId,backendRef:e.backendRef?{...e.backendRef}:void 0,route:e.route}}resolveWorktreeRepoDir(e,n){return e&&(!n||!Yr(e,n))||!n?e:pr(n)??e}formatLaunchWorkdirLabel(e){if(!e.worktreePath)return e.workdir;let n=this.resolveWorktreeRepoDir(e.originalWorkdir,e.worktreePath);return!n||n===e.worktreePath?e.worktreePath:`${e.worktreePath} (worktree of ${n})`}async dismissWorktree(e){return this.worktreeDecisions.dismissWorktree(e)}snoozeWorktreeDecision(e,n){return this.worktreeDecisions.snoozeWorktreeDecision(e,n)}async handleWorktreeStrategy(e){return this.worktreeStrategy.handleWorktreeStrategy(e)}async onSessionTerminal(e){if(e.autoMergeParentSessionId){await this.handleAutoMergeResolverTerminal(e);return}return this.lifecycle.handleSessionTerminal(e)}async handleAutoMergeResolverTerminal(e){this.persistSession(e),this.clearWaitingTimestampsForSession(e.id),this.wakeDispatcher.clearRetryTimersForSession(e.id);let n=e.autoMergeParentSessionId;if(!n)return;let r=this.resolve(n),o=this.getPersistedSession(n),i=r??(o?this.buildRoutingProxy({id:o.sessionId,name:o.name,sessionId:o.sessionId,harnessSessionId:o.harnessSessionId,backendRef:o.backendRef,route:o.route}):void 0);if(!i){`${e.id}${n}`;return}if(e.status==="completed"&&r){this.updatePersistedSession(n,{autoMergeResolverSessionId:void 0}),await this.handleWorktreeStrategy(r);return}let s=r?.worktreeBranch??o?.worktreeBranch??"unknown",l=r?.worktreePath??o?.worktreePath??"(unknown worktree)",a=r?.worktreeBaseBranch??o?.worktreeBaseBranch,d=r?.worktreePrTargetRepo??o?.worktreePrTargetRepo,u=r?.worktreePushRemote??o?.worktreePushRemote;this.updatePersistedSession(n,Tr({worktreeBaseBranch:a,worktreePrTargetRepo:d,worktreePushRemote:u},{clearResolverSessionId:!0,notes:[e.status==="completed"?"auto_merge_conflict_resolver_completed_without_retry_target":"auto_merge_conflict_resolver_failed"]})),this.dispatchSessionNotification(i,{label:"worktree-merge-conflict-resolver-failed",idempotencyKey:`worktree-merge-conflict-resolver-failed:${n}:${e.id}`,userMessage:[`⚠️ [${i.name}] Auto-merge conflict resolution did not complete successfully.`,`Branch \`${s}\` was preserved for manual follow-up in ${l}.`,e.status==="completed"?"The resolver finished, but the original session could not be resumed for the merge retry.":`Resolver session ${e.name} ended with status=${e.status}.`].join(`
272
- `),buttons:this.getPolicyAwareWorktreeDecisionButtons(n,{allowDelegate:!0},r,o)})}persistSession(e,n={}){let r=n.scheduleRuntimeGc??!0;this.store.hasRecordedSession(e.id)||this.metrics.recordSession(e),this.store.persistTerminal(e),r&&this.syncRuntimeGcDeadline(e),this.onPersistedSessionChanged(this.store.getPersistedSession(e.id)),this.syncTmpOutputCleanupDeadline()}getMetrics(){return this.metrics.getMetrics()}notifySession(e,n,r="notification"){this.dispatchSessionNotification(e,{label:r,idempotencyKey:r==="agent-respond"?void 0:`notify:${e.id}:${r}:${n}`,userMessage:n,notifyUser:"always"})}sendPlanOffer(e){let n=this.interactions.getPlanOfferButtons({offerId:e.offerId,route:e.route,planName:e.planName,planPrompt:e.planPrompt,planWorkdir:e.planWorkdir,planWorktreeStrategy:e.planWorktreeStrategy});this.dispatchSessionNotification(this.buildRoutingProxy({id:e.offerId,route:e.route}),{label:"plan-offer",idempotencyKey:`plan-offer:${e.offerId}`,userMessage:e.text,notifyUser:"always",buttons:n})}emitGoalTaskUpdate(e,n,r="goal-task"){let o=e.sessionId??e.id,i=this.buildRoutingProxy({id:o,name:e.sessionName??e.name,route:e.route});i.originChannel=e.originChannel,i.originThreadId=e.originThreadId,i.originSessionKey=e.originSessionKey;let s=r==="goal-task-succeeded",l=[`✅ [${e.name}] Goal task succeeded`,e.sessionId?`Session: ${e.sessionName??e.name} [${e.sessionId}]`:void 0].filter(d=>!!d).join(`
273
- `),a=d=>ts({sessionId:o,sessionName:e.sessionName,taskName:e.name,summary:n,originThreadLine:Qt(i),canonicalStatusDelivered:d});this.dispatchSessionNotification(i,{label:r,idempotencyKey:`goal:${e.id}:${r}:${s?"success":n}`,userMessage:s?l:n,notifyUser:"always",completionSummary:s?{required:!0,producer:"goal",outcomeKey:`goal:${e.id}`}:void 0,completionWakeSummaryRequired:s,completionWakeOutcomeKey:s?`goal:${e.id}`:void 0,wakeMessageOnNotifySuccess:s?a(!0):void 0,wakeMessageOnNotifyFailed:s?a(!1):void 0})}launchPlanOffer(e){let n=e.route??{provider:"system",target:"system"};return this.spawn({prompt:e.prompt,workdir:e.workdir,name:e.name,harness:ae(),permissionMode:"plan",planApproval:"ask",worktreeStrategy:e.worktreeStrategy??"off",multiTurn:!0,route:n,originChannel:this.originChannelFromRoute(n),originThreadId:n.threadId,originSessionKey:n.sessionKey})}dispatchSessionNotification(e,n){this.notifications.dispatch(e,n)}originChannelFromRoute(e){return e.accountId?`${e.provider}|${e.accountId}|${e.target}`:`${e.provider}|${e.target}`}debounceWaitingEvent(e,n){let r=Date.now(),o=n?`${e}:${n}`:e,i=this.lastWaitingEventTimestamps.get(o);return i&&r-i<qy?!1:(this.lastWaitingEventTimestamps.set(o,r),!0)}clearWaitingTimestampsForSession(e){this.lastWaitingEventTimestamps.delete(e);let n=`${e}:`;for(let r of this.lastWaitingEventTimestamps.keys())r.startsWith(n)&&this.lastWaitingEventTimestamps.delete(r)}originThreadLine(e){return Qt(e)}extractLastOutputLine(e){return e.getOutput(3).filter(o=>o.trim()).pop()?.trim()||void 0}getOutputPreview(e,n=1e3){return yu(e,n)}resolvePlanApprovalMode(e){return e.planApproval??D.planApproval??"delegate"}shouldEmitTurnCompleteWake(e){let n=`${e.result?.session_id??""}|${e.result?.num_turns??0}|${e.result?.duration_ms??0}`;return this.lastTurnCompleteMarkers.get(e.id)===n?(`${e.id}${n}`,!1):(this.lastTurnCompleteMarkers.set(e.id,n),!0)}shouldEmitTerminalWake(e){let n=`${e.status}|${e.completedAt??0}|${e.result?.session_id??""}|${e.result?.num_turns??0}|${e.killReason}`;return this.lastTerminalWakeMarkers.get(e.id)===n?!1:(this.lastTerminalWakeMarkers.set(e.id,n),!0)}resolve(e){return this.references.resolveActive(e)}get(e){return this.registry.get(e)}list(e){let n=this.registry.list();return e&&e!=="all"&&(n=n.filter(r=>r.status===e)),n.sort((r,o)=>o.startedAt-r.startedAt)}kill(e,n){let r=this.registry.get(e);if(!r)return!1;if(r.pendingPlanApproval){this.clearPlanDecisionTokens(r.id);let o={lifecycle:"terminal",runtimeState:"stopped",pendingPlanApproval:!1,planApprovalContext:void 0,approvalState:r.approvalState==="pending"?"rejected":r.approvalState,planDecisionVersion:(r.planDecisionVersion??0)+1,actionablePlanDecisionVersion:void 0,canonicalPlanPromptVersion:void 0,approvalPromptRequiredVersion:void 0,approvalPromptVersion:void 0,approvalPromptStatus:"not_sent",approvalPromptTransport:"none",approvalPromptMessageKind:"none",approvalPromptLastAttemptAt:void 0,approvalPromptDeliveredAt:void 0,approvalPromptFailedAt:void 0};r.applyControlPatch(o),Object.assign(r,o),this.updatePersistedSession(r.id,o)}return r.kill(n??"user"),!0}killAll(e="user"){for(let n of this.sessions.values())By.has(n.status)&&this.kill(n.id,e)}resolveBackendConversationId(e){return this.references.resolveBackendConversationId(e)}resolveHarnessSessionId(e){return this.resolveBackendConversationId(e)}getPersistedSession(e){return this.references.getPersistedSession(e)}isAlreadyMerged(e){if(!e)return!1;let n=this.store.getPersistedSession(e);return n?.worktreeMerged===!0||n?.worktreeLifecycle?.state==="merged"||n?.worktreeLifecycle?.state==="released"}async enqueueMerge(e,n,r){return this.mergeQueue.enqueue(e,n,r)}updatePersistedSession(e,n){let r=this.stateSync.applySessionPatch(e,n);return r&&this.onPersistedSessionChanged(this.store.getPersistedSession(e)),r}listPersistedSessions(){return this.store.listPersistedSessions()}async handleAskUserQuestion(e,n){let r=this.sessions.get(e);if(!r)throw new Error(`Session "${e}" not found for AskUserQuestion intercept`);return this.questions.handleAskUserQuestion(r,n)}resolveAskUserQuestion(e,n,r={}){return this.questions.resolveAskUserQuestion(e,n,r)}async resolvePendingInputOption(e,n,r={}){let o=this.sessions.get(e);return o?.canSubmitPendingInputOption?.()?await o.submitPendingInputOption(n,r)?(this.clearWaitingTimestampsForSession(e),!0):!1:this.questions.resolveAskUserQuestion(e,n,r)}dispose(){this.disposeMaintenance(),this.questions.dispose(),this.notifications.dispose()}};N();ie();import{definePluginEntry as bu}from"openclaw/plugin-sdk/plugin-entry";function zy(t){let e=parseInt(process.env.OPENCLAW_WORKTREE_CLEANUP_AGE_HOURS??"168",10)||168,n=e*60*60*1e3,r=Date.now()-n,o=new Set(t.listPersistedSessions().map(a=>a.worktreePath).filter(a=>typeof a=="string"&&a.length>0)),i=new Set,s=process.env.OPENCLAW_WORKTREE_DIR??D.worktreeDir;if(s)i.add(s);else for(let a of t.listPersistedSessions())if(a.workdir)try{let d=Hy("git",["rev-parse","--show-toplevel"],{cwd:a.workdir,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();d&&i.add(Ru(d,".worktrees"))}catch{}if(i.size===0)return;let l=0;for(let a of i)try{let d=Vy(a);for(let u of d){if(!u.startsWith("openclaw-worktree-"))continue;let c=Ru(a,u);try{let m=Gy(c);if(!m.isDirectory()||m.mtimeMs>r||o.has(c))continue;jy(c,{recursive:!0,force:!0}),l++}catch(m){`${c}${m instanceof Error?m.message:String(m)}`}}}catch{}l>0&&`${l}${e}`}function Qy(t){let e=null,n=null,r=!1,o=!1,i=t.registerTool;wt(t.runtime);let s=c=>{if(r){c&&!o&&(wt(t.runtime,c.config),o=!0);return}let m=t.pluginConfig??{};_s(m),c?(wt(t.runtime,c.config),o=!0):(wt(t.runtime),o=!1),e=new Fo(D.maxSessions,D.maxPersistedSessions,{worktreeSummaryProvider:Ed()}),n=new Jr(e),Ko(e),Vo(n),n.start(),zy(e),e.bootstrapMaintenanceSchedules(),r=!0},l=()=>{n&&n.stop(),e&&e.killAll("shutdown"),e&&e.dispose(),n=null,e=null,r=!1,o=!1,wt(void 0),Vo(null),Ko(null)},a=(c,m)=>{i(p=>(s(),c(p)),m)},d={...t,registerCommand(c){t.registerCommand({...c,handler:m=>(s(),c.handler(m))})}},u=c=>{let m=Ul(c);t.registerInteractiveHandler({...m,handler:async p=>(s(),m.handler(p))})};a(c=>xa(c),{optional:!1,name:"agent_launch"}),a(c=>nl(c),{optional:!1,name:"agent_sessions"}),a(c=>rl(c),{optional:!1,name:"agent_kill"}),a(c=>Rr(c),{optional:!1,name:"agent_output"}),a(c=>dl(c),{optional:!1,name:"agent_respond"}),a(c=>ul(c),{optional:!1,name:"agent_request_plan_approval"}),a(c=>cl(c),{optional:!1,name:"agent_request_worktree_decision"}),a(c=>fl(c),{optional:!1,name:"agent_send_plan_offer"}),a(c=>gl(c),{optional:!1,name:"agent_stats"}),a(c=>vl(c),{optional:!1,name:"agent_repo_policy"}),a(c=>Dr(c),{optional:!1,name:"agent_merge"}),a(c=>bn(c),{optional:!1,name:"agent_pr"}),a(c=>Cl(c),{optional:!1,name:"agent_worktree_cleanup"}),a(c=>Ml(c),{optional:!1,name:"agent_worktree_status"}),a(c=>_l(c),{optional:!1,name:"goal_launch"}),a(c=>El(c),{optional:!1,name:"goal_status"}),a(c=>Dl(c),{optional:!1,name:"goal_stop"}),a(c=>Ol(c),{optional:!1,name:"goal_edit"}),u("telegram"),u("discord"),Vl(d),Gl(d),jl(d),Hl(d),zl(d),Ql(d),Jl(d),Zl(d),Xl(d),ed(d),nd(d),t.registerService({id:"openclaw-code-agent",start:s,stop:l})}var Lx=bu({id:"openclaw-code-agent",name:"OpenClaw Code Agent",description:"Multi-session coding-agent orchestration from OpenClaw chat",register:Qy});export{Lx as default,Qy as register};
272
+ `),wakeMessageOnNotifyFailed:o}),[`Repo policy choice prompt sent for ${r.identity.repoRoot}.`,r.prAvailable?"Wait for the user's Require PR, Merge or PR, No PR, or Manual response.":"Wait for the user's No PR or Manual response.","Do not send a separate plain-text policy question."].join(" ")}launchAfterRepoPolicyChoice(e){let n=e.route;if(!n?.provider||!n.target)throw new Error("missing route metadata for stored launch");let r=e.harness??le(),o=e.permissionMode??D.permissionMode,i=e.planApproval??D.planApproval,s=this.spawn({prompt:e.prompt,workdir:e.workdir,sessionIdOverride:e.sessionIdOverride,name:e.name,model:e.model,reasoningEffort:e.reasoningEffort,fastMode:e.fastMode,systemPrompt:e.systemPrompt,allowedTools:e.allowedTools,resumeSessionId:e.resumeSessionId,resumeWorktreeFrom:e.resumeWorktreeFrom,forkSession:e.resumeSessionId?e.forkSession:!1,multiTurn:!0,permissionMode:o,planApproval:i,codexApprovalPolicy:r==="codex"?"never":void 0,originChannel:this.originChannelFromRoute(n),originThreadId:n.threadId,originAgentId:e.originAgentId,originSessionKey:n.sessionKey,route:n,harness:r,worktreeStrategy:e.worktreeStrategy,worktreeBaseBranch:e.worktreeBaseBranch,worktreePrTargetRepo:e.worktreePrTargetRepo});return{session:s,text:this.formatLaunchResult({prompt:e.prompt,workdir:e.workdir,harness:r,permissionMode:o,planApproval:i,forceNewSession:e.forceNewSession,resumeSessionId:e.resumeSessionId,forkSession:e.forkSession,clearedPersistedCodexResume:e.clearedPersistedCodexResume},s)}}continueLaunchAfterManualRepoPolicy(e,n){let r=this.resolveRepoPolicy(e);if(!r.identity)return{kind:"none"};let o=this.interactions.listActiveActionTokens("repo-policy-set").filter(u=>u.repoPolicyWorkdir===r.identity?.repoRoot),i=()=>{for(let u of new Set(o.map(c=>c.sessionId)))this.clearRepoPolicyChoiceTokens(u)},s=o.filter(u=>u.repoPolicy===n&&!!u.launchPrompt&&!!u.launchWorkdir&&!!u.route?.provider&&!!u.route?.target);if(s.length===0)return i(),{kind:"none"};let a=new Map;for(let u of s){let c=sk(u);a.has(c)||a.set(c,u)}if(a.size>1)return i(),{kind:"ambiguous",count:a.size};let l=[...a.values()][0];if(!l.launchPrompt||!l.launchWorkdir)return{kind:"none"};let d=this.launchAfterRepoPolicyChoice({route:l.route,prompt:l.launchPrompt,workdir:l.launchWorkdir,name:l.launchName,model:l.launchModel,reasoningEffort:l.launchReasoningEffort,fastMode:l.launchFastMode,systemPrompt:l.launchSystemPrompt,allowedTools:l.launchAllowedTools,resumeSessionId:l.launchResumeSessionId,resumeWorktreeFrom:l.launchResumeWorktreeFrom,sessionIdOverride:l.launchSessionIdOverride,clearedPersistedCodexResume:l.launchClearedPersistedCodexResume,forkSession:l.launchForkSession,forceNewSession:l.launchForceNewSession,permissionMode:l.launchPermissionMode,planApproval:l.launchPlanApproval,harness:l.launchHarness,worktreeStrategy:l.launchWorktreeStrategy,worktreeBaseBranch:l.launchWorktreeBaseBranch,worktreePrTargetRepo:l.launchWorktreePrTargetRepo,originAgentId:l.launchOriginAgentId});return this.consumeActionToken(l.id),this.clearRepoPolicyChoiceTokens(l.sessionId),{kind:"launched",...d}}makeActionButton(e,n,r,o={}){return this.interactions.makeActionButton(e,n,r,o)}consumeActionToken(e){return this.interactions.consumeActionToken(e)}getActionToken(e){return this.interactions.getActionToken(e)}clearRepoPolicyChoiceTokens(e){this.interactions.clearRepoPolicyChoiceTokens(e)}clearPlanDecisionTokens(e,n){this.interactions.clearPlanDecisionTokens(e,n)}isCurrentPendingPlanDecision(e,n){let r=this.resolve(e)??this.getPersistedSession(e);return _n(r,n)}dispatchPlanApprovalFallback(e,n,r){let o=new Date().toISOString();this.notifications.dispatch(e,{label:"plan-approval-fallback",idempotencyKey:`plan-approval:${e.id}:v${n??"unknown"}:fallback`,userMessage:xn({session:e,summary:r}),notifyUser:"always",shouldDispatch:()=>this.isCurrentPendingPlanDecision(e.id,n),hooks:{onNotifyStarted:()=>{this.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"sending",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o})},onNotifySucceeded:()=>{this.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"fallback_delivered",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o,approvalPromptDeliveredAt:new Date().toISOString(),approvalPromptFailedAt:void 0})},onNotifyFailed:()=>{this.updatePersistedSession(e.id,{approvalPromptRequiredVersion:n,approvalPromptVersion:n,approvalPromptStatus:"failed",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"explicit_fallback_text",approvalPromptLastAttemptAt:o,approvalPromptFailedAt:new Date().toISOString()})}},wakeMessageOnNotifySuccess:Vt(e,n,!0),wakeMessageOnNotifyFailed:Do({session:e,planDecisionVersion:n})})}getWorktreeDecisionButtons(e,n={},r={merge:!0,pr:!0}){let o=this.resolve(e)??this.getPersistedSession(e);if(!(!o||o.worktreeStrategy==="delegate"&&n.allowDelegate!==!0))return this.interactions.getWorktreeDecisionButtons(e,o,r)}getPolicyAwareWorktreeDecisionButtons(e,n={},r,o){let i=r??this.resolve(e),s=o??this.getPersistedSession(e),a=this.resolveWorktreeRepoDir(i?.originalWorkdir??s?.workdir,i?.worktreePath??s?.worktreePath),l=a?this.resolveRepoPolicy(a):void 0,d=i?.repoIntegrationPolicy??s?.repoIntegrationPolicy,u=d??l?.policy,c=l?.prAvailable??!!(d&&d!=="never-pr"&&d!=="manual"),p=u?Ni({policy:u,prAvailable:c}):{merge:!0,pr:!0};return this.getWorktreeDecisionButtons(e,n,p)}getWorktreeCompletionState(e,n,r,o){return this.worktrees.getCompletionState(e,n,r,o)}notifyWorktreeOutcome(e,n,r){this.notifications.notifyWorktreeOutcome(e,n,r)}requestPlanApprovalFromUser(e,n){let r=n.trim();if(!r)return"Error: summary must not be empty.";let o=hs(r),i=this.resolve(e),s=i?void 0:this.getPersistedSession(e),a=i??s;if(!a)return`Error: Session "${e}" not found.`;if(!a.pendingPlanApproval)return`Error: Session "${e}" is not awaiting plan approval.`;let l=U(i??s??{id:e})??e;if(this.resolvePlanApprovalMode(a)!=="delegate")return`Error: Session "${e}" already uses direct user plan approval. Do not send a duplicate approval prompt.`;let d=a.actionablePlanDecisionVersion??a.planDecisionVersion;if(Mn(a,d))return[`An actionable plan review prompt already exists for session ${a.name} [${l}].`,"Wait for the user's Approve, Revise, or Reject response.","Do not send a separate plain-text approval message."].join(" ");if(a.deliveryState==="notifying")return[`A plan approval prompt is already being delivered for session ${a.name} [${l}].`,"Wait for delivery to finish before retrying."].join(" ");let u=this.interactions.getPlanApprovalButtons(l,{...a,planDecisionVersion:d}),c=[`📋 [${a.name}] Plan v${d??"?"} needs your decision:`,"","Why this was escalated:","",o,"","Choose Approve, Revise, or Reject below."].join(`
273
+ `);return this.notifications.dispatch(this.buildRoutingProxy({id:l,name:a.name,sessionId:s?.sessionId,harnessSessionId:i?.harnessSessionId??s?.harnessSessionId,backendRef:i?.backendRef??s?.backendRef,route:i?.route??s?.route}),{label:"plan-approval",idempotencyKey:`plan-approval:${l}:v${d??"unknown"}:canonical`,userMessage:c,notifyUser:"always",buttons:u,hooks:{onNotifyStarted:()=>{this.updatePersistedSession(l,{approvalPromptRequiredVersion:d,approvalPromptStatus:"sending",approvalPromptVersion:d,approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptLastAttemptAt:new Date().toISOString()})},onNotifySucceeded:()=>{this.updatePersistedSession(l,{canonicalPlanPromptVersion:d,approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"delivered",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptDeliveredAt:new Date().toISOString(),approvalPromptFailedAt:void 0})},onNotifyFailed:()=>{this.updatePersistedSession(l,{approvalPromptRequiredVersion:d,approvalPromptVersion:d,approvalPromptStatus:"failed",approvalPromptTransport:"direct-message",approvalPromptMessageKind:"canonical_buttons",approvalPromptFailedAt:new Date().toISOString()})}},shouldDispatch:()=>this.isCurrentPendingPlanDecision(l,d),onUserNotifyFailed:()=>this.dispatchPlanApprovalFallback(this.buildRoutingProxy({id:l,name:a.name,sessionId:s?.sessionId,harnessSessionId:i?.harnessSessionId??s?.harnessSessionId,backendRef:i?.backendRef??s?.backendRef,route:i?.route??s?.route}),d,o),wakeMessageOnNotifySuccess:Vt({id:l,name:a.name},d)}),[`Canonical plan approval prompt sent for session ${a.name} [${l}].`,"Wait for the user's Approve, Revise, or Reject response.","Do not send a separate plain-text approval message."].join(" ")}requestWorktreeDecisionFromUser(e,n){let r=n.trim();if(!r)return"Error: summary must not be empty.";let o=this.resolve(e),i=this.getPersistedSession(e),s=o??i;if(!s)return`Error: Session "${e}" not found.`;if(s.worktreeStrategy!=="delegate")return`Error: Session "${e}" already uses direct user worktree decisions. Do not send a duplicate decision prompt.`;if(!(!!("pendingWorktreeDecisionSince"in s?s.pendingWorktreeDecisionSince:void 0)||s.worktreeState==="pending_decision"||s.worktreeLifecycle?.state==="pending_decision"))return`Error: Session "${e}" is not awaiting a delegated worktree decision.`;let d=U(o??i??{id:e})??e,u=o?.worktreePath??i?.worktreePath,c=o?.worktreeBranch??i?.worktreeBranch,p=this.resolveWorktreeRepoDir(o?.originalWorkdir??i?.workdir,u);if(!u)return`Error: Session "${e}" has no managed worktree path.`;if(!c)return`Error: Session "${e}" has no managed worktree branch.`;if(!p)return`Error: Session "${e}" has no resolvable repository root for worktree ${u}.`;let g=o?.worktreeBaseBranch??i?.worktreeBaseBranch??Me(p),m=We(p,c,g);if(!m)return`Error: Could not compute worktree diff summary for session "${e}".`;let f=this.getPolicyAwareWorktreeDecisionButtons(d,{allowDelegate:!0},o,i);if(!f||f.length===0)return`Error: Could not create worktree decision buttons for session "${e}".`;let y=r.split(/\r?\n/).map(S=>S.replace(/^[-*]\s+/,"").trim()).filter(S=>S.length>0);return this.notifications.dispatch(this.buildRoutingProxy({id:d,name:s.name,sessionId:i?.sessionId,harnessSessionId:o?.harnessSessionId??i?.harnessSessionId,backendRef:o?.backendRef??i?.backendRef,route:o?.route??i?.route}),this.worktreeMessages.buildAskNotification({session:{id:d,name:s.name,worktreePrTargetRepo:o?.worktreePrTargetRepo??i?.worktreePrTargetRepo},branchName:c,baseBranch:g,diffSummary:m,summaryLines:y,buttons:f})),[`Canonical worktree decision prompt sent for session ${s.name} [${d}].`,"Wait for the user's Merge, Open PR, Later, or Discard response.","Do not send a separate plain-text worktree decision message."].join(" ")}buildRoutingProxy(e){return{id:U(e)??$(e)??e.harnessSessionId??"unknown-session",name:e.name,harnessSessionId:e.harnessSessionId,backendRef:e.backendRef?{...e.backendRef}:void 0,route:e.route}}resolveWorktreeRepoDir(e,n){return e&&(!n||!to(e,n))||!n?e:fr(n)??e}formatLaunchWorkdirLabel(e){if(!e.worktreePath)return e.workdir;let n=this.resolveWorktreeRepoDir(e.originalWorkdir,e.worktreePath);return!n||n===e.worktreePath?e.worktreePath:`${e.worktreePath} (worktree of ${n})`}async dismissWorktree(e){return this.worktreeDecisions.dismissWorktree(e)}snoozeWorktreeDecision(e,n){return this.worktreeDecisions.snoozeWorktreeDecision(e,n)}async handleWorktreeStrategy(e){return this.worktreeStrategy.handleWorktreeStrategy(e)}async onSessionTerminal(e){if(e.autoMergeParentSessionId){await this.handleAutoMergeResolverTerminal(e);return}return this.lifecycle.handleSessionTerminal(e)}async handleAutoMergeResolverTerminal(e){this.persistSession(e),this.clearWaitingTimestampsForSession(e.id),this.wakeDispatcher.clearRetryTimersForSession(e.id);let n=e.autoMergeParentSessionId;if(!n)return;let r=this.resolve(n),o=this.getPersistedSession(n),i=r??(o?this.buildRoutingProxy({id:o.sessionId,name:o.name,sessionId:o.sessionId,harnessSessionId:o.harnessSessionId,backendRef:o.backendRef,route:o.route}):void 0);if(!i){`${e.id}${n}`;return}if(e.status==="completed"&&r){this.updatePersistedSession(n,{autoMergeResolverSessionId:void 0}),await this.handleWorktreeStrategy(r);return}let s=r?.worktreeBranch??o?.worktreeBranch??"unknown",a=r?.worktreePath??o?.worktreePath??"(unknown worktree)",l=r?.worktreeBaseBranch??o?.worktreeBaseBranch,d=r?.worktreePrTargetRepo??o?.worktreePrTargetRepo,u=r?.worktreePushRemote??o?.worktreePushRemote;this.updatePersistedSession(n,Mr({worktreeBaseBranch:l,worktreePrTargetRepo:d,worktreePushRemote:u},{clearResolverSessionId:!0,notes:[e.status==="completed"?"auto_merge_conflict_resolver_completed_without_retry_target":"auto_merge_conflict_resolver_failed"]})),this.dispatchSessionNotification(i,{label:"worktree-merge-conflict-resolver-failed",idempotencyKey:`worktree-merge-conflict-resolver-failed:${n}:${e.id}`,userMessage:[`⚠️ [${i.name}] Auto-merge conflict resolution did not complete successfully.`,`Branch \`${s}\` was preserved for manual follow-up in ${a}.`,e.status==="completed"?"The resolver finished, but the original session could not be resumed for the merge retry.":`Resolver session ${e.name} ended with status=${e.status}.`].join(`
274
+ `),buttons:this.getPolicyAwareWorktreeDecisionButtons(n,{allowDelegate:!0},r,o)})}persistSession(e,n={}){let r=n.scheduleRuntimeGc??!0;this.store.hasRecordedSession(e.id)||this.metrics.recordSession(e),this.store.persistTerminal(e),r&&this.syncRuntimeGcDeadline(e),this.onPersistedSessionChanged(this.store.getPersistedSession(e.id)),this.syncTmpOutputCleanupDeadline()}getMetrics(){return this.metrics.getMetrics()}notifySession(e,n,r="notification"){this.dispatchSessionNotification(e,{label:r,idempotencyKey:r==="agent-respond"?void 0:`notify:${e.id}:${r}:${n}`,userMessage:n,notifyUser:"always"})}sendPlanOffer(e){let n=this.interactions.getPlanOfferButtons({offerId:e.offerId,route:e.route,planName:e.planName,planPrompt:e.planPrompt,planWorkdir:e.planWorkdir,planWorktreeStrategy:e.planWorktreeStrategy});this.dispatchSessionNotification(this.buildRoutingProxy({id:e.offerId,route:e.route}),{label:"plan-offer",idempotencyKey:`plan-offer:${e.offerId}`,userMessage:e.text,notifyUser:"always",buttons:n})}emitGoalTaskUpdate(e,n,r="goal-task"){let o=e.sessionId??e.id,i=this.buildRoutingProxy({id:o,name:e.sessionName??e.name,route:e.route});i.originChannel=e.originChannel,i.originThreadId=e.originThreadId,i.originSessionKey=e.originSessionKey;let s=r==="goal-task-succeeded",a=[`✅ [${e.name}] Goal task succeeded`,e.sessionId?`Session: ${e.sessionName??e.name} [${e.sessionId}]`:void 0].filter(d=>!!d).join(`
275
+ `),l=d=>ls({sessionId:o,sessionName:e.sessionName,taskName:e.name,summary:n,originThreadLine:Jt(i),canonicalStatusDelivered:d});this.dispatchSessionNotification(i,{label:r,idempotencyKey:`goal:${e.id}:${r}:${s?"success":n}`,userMessage:s?a:n,notifyUser:"always",completionSummary:s?{required:!0,producer:"goal",outcomeKey:`goal:${e.id}`}:void 0,completionWakeSummaryRequired:s,completionWakeOutcomeKey:s?`goal:${e.id}`:void 0,wakeMessageOnNotifySuccess:s?l(!0):void 0,wakeMessageOnNotifyFailed:s?l(!1):void 0})}launchPlanOffer(e){let n=e.route??{provider:"system",target:"system"};return this.spawn({prompt:e.prompt,workdir:e.workdir,name:e.name,harness:le(),permissionMode:"plan",planApproval:"ask",worktreeStrategy:e.worktreeStrategy??"off",multiTurn:!0,route:n,originChannel:this.originChannelFromRoute(n),originThreadId:n.threadId,originSessionKey:n.sessionKey})}dispatchSessionNotification(e,n){this.notifications.dispatch(e,n)}originChannelFromRoute(e){return e.accountId?`${e.provider}|${e.accountId}|${e.target}`:`${e.provider}|${e.target}`}debounceWaitingEvent(e,n){let r=Date.now(),o=n?`${e}:${n}`:e,i=this.lastWaitingEventTimestamps.get(o);return i&&r-i<ok?!1:(this.lastWaitingEventTimestamps.set(o,r),!0)}clearWaitingTimestampsForSession(e){this.lastWaitingEventTimestamps.delete(e);let n=`${e}:`;for(let r of this.lastWaitingEventTimestamps.keys())r.startsWith(n)&&this.lastWaitingEventTimestamps.delete(r)}originThreadLine(e){return Jt(e)}extractLastOutputLine(e){return e.getOutput(3).filter(o=>o.trim()).pop()?.trim()||void 0}getOutputPreview(e,n=1e3){return Cu(e,n)}resolvePlanApprovalMode(e){return e.planApproval??D.planApproval??"delegate"}shouldEmitTurnCompleteWake(e){let n=`${e.result?.session_id??""}|${e.result?.num_turns??0}|${e.result?.duration_ms??0}`;return this.lastTurnCompleteMarkers.get(e.id)===n?(`${e.id}${n}`,!1):(this.lastTurnCompleteMarkers.set(e.id,n),!0)}shouldEmitTerminalWake(e){let n=`${e.status}|${e.completedAt??0}|${e.result?.session_id??""}|${e.result?.num_turns??0}|${e.killReason}`;return this.lastTerminalWakeMarkers.get(e.id)===n?!1:(this.lastTerminalWakeMarkers.set(e.id,n),!0)}resolve(e){return this.references.resolveActive(e)}get(e){return this.registry.get(e)}list(e){let n=this.registry.list();return e&&e!=="all"&&(n=n.filter(r=>r.status===e)),n.sort((r,o)=>o.startedAt-r.startedAt)}kill(e,n){let r=this.registry.get(e);if(!r)return!1;if(r.pendingPlanApproval){this.clearPlanDecisionTokens(r.id);let o={lifecycle:"terminal",runtimeState:"stopped",pendingPlanApproval:!1,planApprovalContext:void 0,approvalState:r.approvalState==="pending"?"rejected":r.approvalState,planDecisionVersion:(r.planDecisionVersion??0)+1,actionablePlanDecisionVersion:void 0,canonicalPlanPromptVersion:void 0,approvalPromptRequiredVersion:void 0,approvalPromptVersion:void 0,approvalPromptStatus:"not_sent",approvalPromptTransport:"none",approvalPromptMessageKind:"none",approvalPromptLastAttemptAt:void 0,approvalPromptDeliveredAt:void 0,approvalPromptFailedAt:void 0};r.applyControlPatch(o),Object.assign(r,o),this.updatePersistedSession(r.id,o)}return r.kill(n??"user"),!0}killAll(e="user"){for(let n of this.sessions.values())rk.has(n.status)&&this.kill(n.id,e)}resolveBackendConversationId(e){return this.references.resolveBackendConversationId(e)}resolveHarnessSessionId(e){return this.resolveBackendConversationId(e)}getPersistedSession(e){return this.references.getPersistedSession(e)}isAlreadyMerged(e){if(!e)return!1;let n=this.store.getPersistedSession(e);return n?.worktreeMerged===!0||n?.worktreeLifecycle?.state==="merged"||n?.worktreeLifecycle?.state==="released"}async enqueueMerge(e,n,r){return this.mergeQueue.enqueue(e,n,r)}updatePersistedSession(e,n){let r=this.stateSync.applySessionPatch(e,n);return r&&this.onPersistedSessionChanged(this.store.getPersistedSession(e)),r}listPersistedSessions(){return this.store.listPersistedSessions()}async handleAskUserQuestion(e,n){let r=this.sessions.get(e);if(!r)throw new Error(`Session "${e}" not found for AskUserQuestion intercept`);return this.questions.handleAskUserQuestion(r,n)}resolveAskUserQuestion(e,n,r={}){return this.questions.resolveAskUserQuestion(e,n,r)}async resolvePendingInputOption(e,n,r={}){let o=this.sessions.get(e);return o?.canSubmitPendingInputOption?.()?await o.submitPendingInputOption(n,r)?(this.clearWaitingTimestampsForSession(e),!0):!1:this.questions.resolveAskUserQuestion(e,n,r)}dispose(){this.disposeMaintenance(),this.questions.dispose(),this.notifications.dispose()}};B();se();import{definePluginEntry as Ou}from"openclaw/plugin-sdk/plugin-entry";function ck(t){let e=parseInt(process.env.OPENCLAW_WORKTREE_CLEANUP_AGE_HOURS??"168",10)||168,n=e*60*60*1e3,r=Date.now()-n,o=new Set(t.listPersistedSessions().map(l=>l.worktreePath).filter(l=>typeof l=="string"&&l.length>0)),i=new Set,s=process.env.OPENCLAW_WORKTREE_DIR??D.worktreeDir;if(s)i.add(s);else for(let l of t.listPersistedSessions())if(l.workdir)try{let d=uk("git",["rev-parse","--show-toplevel"],{cwd:l.workdir,timeout:5e3,encoding:"utf-8",stdio:["pipe","pipe","pipe"]}).trim();d&&i.add(Wu(d,".worktrees"))}catch{}if(i.size===0)return;let a=0;for(let l of i)try{let d=ak(l);for(let u of d){if(!u.startsWith("openclaw-worktree-"))continue;let c=Wu(l,u);try{let p=lk(c);if(!p.isDirectory()||p.mtimeMs>r||o.has(c))continue;dk(c,{recursive:!0,force:!0}),a++}catch(p){`${c}${p instanceof Error?p.message:String(p)}`}}}catch{}a>0&&`${a}${e}`}function pk(t){let e=null,n=null,r=!1,o=!1,i=t.registerTool;Rt(t.runtime);let s=c=>{if(r){c&&!o&&(Rt(t.runtime,c.config),o=!0);return}let p=t.pluginConfig??{};Ls(p),c?(Rt(t.runtime,c.config),o=!0):(Rt(t.runtime),o=!1),e=new Uo(D.maxSessions,D.maxPersistedSessions,{worktreeSummaryProvider:Gd()}),n=new eo(e),Ho(e),zo(n),n.start(),ck(e),e.bootstrapMaintenanceSchedules(),r=!0},a=()=>{n&&n.stop(),e&&e.killAll("shutdown"),e&&e.dispose(),n=null,e=null,r=!1,o=!1,Rt(void 0),zo(null),Ho(null)},l=(c,p)=>{i(g=>(s(),c(g)),p)},d={...t,registerCommand(c){t.registerCommand({...c,handler:p=>(s(),c.handler(p))})}},u=c=>{let p=ed(c);t.registerInteractiveHandler({...p,handler:async g=>(s(),p.handler(g))})};l(c=>Da(c),{optional:!1,name:"agent_launch"}),l(c=>dl(c),{optional:!1,name:"agent_sessions"}),l(c=>ul(c),{optional:!1,name:"agent_kill"}),l(c=>Ir(c),{optional:!1,name:"agent_output"}),l(c=>hl(c),{optional:!1,name:"agent_respond"}),l(c=>yl(c),{optional:!1,name:"agent_request_plan_approval"}),l(c=>kl(c),{optional:!1,name:"agent_request_worktree_decision"}),l(c=>wl(c),{optional:!1,name:"agent_send_plan_offer"}),l(c=>Pl(c),{optional:!1,name:"agent_stats"}),l(c=>xl(c),{optional:!1,name:"agent_repo_policy"}),l(c=>Wr(c),{optional:!1,name:"agent_merge"}),l(c=>Rn(c),{optional:!1,name:"agent_pr"}),l(c=>Wl(c),{optional:!1,name:"agent_worktree_cleanup"}),l(c=>Nl(c),{optional:!1,name:"agent_worktree_status"}),l(c=>Ll(c),{optional:!1,name:"goal_launch"}),l(c=>Fl(c),{optional:!1,name:"goal_status"}),l(c=>ql(c),{optional:!1,name:"goal_stop"}),l(c=>Kl(c),{optional:!1,name:"goal_edit"}),u("telegram"),u("discord"),nd(d),rd(d),od(d),id(d),sd(d),ad(d),ld(d),ud(d),cd(d),pd(d),fd(d),t.registerService({id:"openclaw-code-agent",start:s,stop:a})}var tT=Ou({id:"openclaw-code-agent",name:"OpenClaw Code Agent",description:"Multi-session coding-agent orchestration from OpenClaw chat",register:pk});export{tT as default,pk as register};