@qiaolei81/copilot-session-viewer 0.3.8 → 0.3.9

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@qiaolei81/copilot-session-viewer",
3
- "version": "0.3.8",
3
+ "version": "0.3.9",
4
4
  "description": "Web UI for viewing GitHub Copilot CLI session logs",
5
5
  "author": "Lei Qiao <qiaolei81@gmail.com>",
6
6
  "license": "MIT",
@@ -1,17 +1,17 @@
1
- (()=>{var y=window.__PAGE_DATA||{},A=y.sessions||[],G=y.totalSessions||0,D=y.hasMore||!1,k=y.sourceHints||{},m=[...A],u={};u.copilot={offset:A.length,hasMore:D};var f=!1,S="sessionViewer.sourceFilter",$;try{$=localStorage.getItem(S)}catch{$=null}var i=$||"copilot";function g(){return u[i]||(u[i]={offset:0,hasMore:!0}),u[i]}async function B(){let e=g();if(f||!e.hasMore)return;f=!0;let t=document.getElementById("loading-indicator");t.style.display="block",window.trackClick("LoadMoreClicked",{currentPage:Math.floor(e.offset/20)+1,offset:e.offset,source:i});try{let s=await fetch(`/api/sessions/load-more?offset=${g().offset}&limit=20&source=${encodeURIComponent(i)}`);if(!s.ok)throw new Error("Failed to load more sessions");let o=await s.json(),n=new Set(m.map(r=>r.id)),a=[];for(let r of o.sessions)n.has(r.id)||(m.push(r),a.push(r));g().offset+=o.sessions.length,g().hasMore=o.hasMore,await C(a),E()}catch(s){console.error("Error loading more sessions:",s)}finally{f=!1,t.style.display="none"}}function F(){return m.filter(e=>e.source===i)}function E(){let e=document.getElementById("sessions-container");e.innerHTML="";let t=F();if(t.length===0){e.innerHTML='<div style="text-align: center; color: #6e7681; padding: 40px; font-size: 14px;">No sessions found for this filter.</div>';return}let s=O(t);Object.keys(s).sort((n,a)=>a.localeCompare(n)).forEach(n=>{let a=document.createElement("div");a.className="date-group-header",a.textContent=N(s[n][0].createdAt),e.appendChild(a);let r=document.createElement("div");r.className="recent-list",s[n].forEach(h=>{r.innerHTML+=R(h)}),e.appendChild(r)})}function z(){let e=window.pageYOffset||document.documentElement.scrollTop,t=window.innerHeight,s=document.documentElement.scrollHeight;e+t>=s-500&&g().hasMore&&!f&&B()}var w;function P(){w||(w=setTimeout(()=>{z(),w=null},100))}function Z(e){e.preventDefault();let t=document.getElementById("sessionInput").value.trim();t&&(window.location.href=`/session/${t}`)}document.getElementById("sessionForm").addEventListener("submit",Z);var M=document.getElementById("fileInput"),d=document.getElementById("importLink"),L=document.getElementById("importStatus");d.addEventListener("click",e=>{e.preventDefault(),M.click()});M.addEventListener("change",async e=>{let t=e.target.files[0];if(t){if(!t.name.endsWith(".zip")){p("error","\u274C Please select a .zip file");return}d.style.pointerEvents="none",d.style.opacity="0.5",d.textContent="Importing...",p("loading","Uploading and extracting session...");try{let s=new FormData;s.append("sessionZip",t);let o=await fetch("/session/import",{method:"POST",body:s}),n=await o.json();o.ok?(p("success",`\u2705 Session ${n.sessionId} imported successfully!`),setTimeout(()=>{window.location.reload()},1500)):(p("error",`\u274C Import failed: ${n.error}`),d.style.pointerEvents="auto",d.style.opacity="1",d.textContent="Import session from zip")}catch(s){p("error",`\u274C Import failed: ${s.message}`),d.style.pointerEvents="auto",d.style.opacity="1",d.textContent="Import session from zip"}finally{M.value=""}}});function p(e,t){L.className=`import-status ${e}`,L.textContent=t}function _(e){if(!e||e<0)return"\u2014";let t=Math.floor(e/1e3),s=Math.floor(t/60),o=Math.floor(s/60);if(o>0){let n=s%60;return`${o}h ${n}m`}else if(s>0){let n=t%60;return`${s}m ${n}s`}else return`${t}s`}function N(e){let t=new Date(e),s=t.getFullYear(),o=String(t.getMonth()+1).padStart(2,"0"),n=String(t.getDate()).padStart(2,"0");return`${s}/${o}/${n}`}function j(e){if(!e)return"Unknown";let t=new Date(e),s=t.getFullYear(),o=String(t.getMonth()+1).padStart(2,"0"),n=String(t.getDate()).padStart(2,"0");return`${s}-${o}-${n}`}function O(e){let t={};return e.forEach(s=>{let o=j(s.createdAt);t[o]||(t[o]=[]),t[o].push(s)}),t}function R(e){let t="",s=e.sourceBadgeClass||"source-copilot",o=e.sourceName||"Copilot";if(t+=`<span class="status-badge ${s}" title="${o}">${o}</span>`,e.sessionStatus==="wip"&&(t+='<span class="status-badge wip" title="Session in progress">\u{1F504} WIP</span>'),e.isImported&&(t+='<span class="status-badge imported" title="Imported session">\u{1F4E5}</span>'),e.hasInsight&&(t+='<span class="status-badge insight" title="Has Agent Review">\u{1F4A1}</span>'),e.selectedModel){let v=e.selectedModel.replace("claude-","").replace("gpt-","").replace("gemini-",""),l="model-other";e.selectedModel.includes("claude")?l="model-claude":e.selectedModel.includes("gpt")?l="model-gpt":e.selectedModel.includes("gemini")&&(l="model-gemini"),t+=`<span class="status-badge model ${l}" title="Model: ${c(e.selectedModel)}">${c(v)}</span>`}e.source==="modernize"&&e.modernizeVersion?t+=`<span class="status-badge version" title="Modernize version">${c(e.modernizeVersion)}</span>`:e.copilotVersion&&(t+=`<span class="status-badge version" title="CLI version">${c(e.copilotVersion)}</span>`);let n="";if(e.summary&&e.summary!=="No summary"&&e.summary!=="Legacy session"){let v=e.summary.replace(/"/g,"&quot;"),l=c(e.summary).replace(/\n+/g," ");n=`<div class="session-summary" title="${v}">${l}</div>`}else n='<div class="session-summary" style="color: #6e7681; font-style: italic;">No summary available</div>';let a="";e.workspace&&e.workspace.cwd&&(a=`
2
- <div class="session-info-item workspace" title="${c(e.workspace.cwd)}">
1
+ (()=>{var y=window.__PAGE_DATA||{},A=y.sessions||[],G=y.totalSessions||0,D=y.hasMore||!1,k=y.sourceHints||{},m=[...A],u={};u.copilot={offset:A.length,hasMore:D};var f=!1,S="sessionViewer.sourceFilter",$;try{$=localStorage.getItem(S)}catch{$=null}var i=$||"copilot";function g(){return u[i]||(u[i]={offset:0,hasMore:!0}),u[i]}async function F(){let e=g();if(f||!e.hasMore)return;f=!0;let t=document.getElementById("loading-indicator");t.style.display="block",window.trackClick("LoadMoreClicked",{currentPage:Math.floor(e.offset/20)+1,offset:e.offset,source:i});try{let s=await fetch(`/api/sessions/load-more?offset=${g().offset}&limit=20&source=${encodeURIComponent(i)}`);if(!s.ok)throw new Error("Failed to load more sessions");let o=await s.json(),n=new Set(m.map(r=>r.id)),a=[];for(let r of o.sessions)n.has(r.id)||(m.push(r),a.push(r));g().offset+=o.sessions.length,g().hasMore=o.hasMore,await C(a),E()}catch(s){console.error("Error loading more sessions:",s)}finally{f=!1,t.style.display="none"}}function B(){return m.filter(e=>e.source===i)}function E(){let e=document.getElementById("sessions-container");e.innerHTML="";let t=B();if(t.length===0){e.innerHTML='<div style="text-align: center; color: #6e7681; padding: 40px; font-size: 14px;">No sessions found for this filter.</div>';return}let s=O(t);Object.keys(s).sort((n,a)=>a.localeCompare(n)).forEach(n=>{let a=document.createElement("div");a.className="date-group-header",a.textContent=_(s[n][0].createdAt),e.appendChild(a);let r=document.createElement("div");r.className="recent-list",s[n].forEach(h=>{r.innerHTML+=R(h)}),e.appendChild(r)})}function z(){let e=window.pageYOffset||document.documentElement.scrollTop,t=window.innerHeight,s=document.documentElement.scrollHeight;e+t>=s-500&&g().hasMore&&!f&&F()}var w;function N(){w||(w=setTimeout(()=>{z(),w=null},100))}function P(e){e.preventDefault();let t=document.getElementById("sessionInput").value.trim();t&&(window.location.href=`/session/${t}`)}document.getElementById("sessionForm").addEventListener("submit",P);var M=document.getElementById("fileInput"),d=document.getElementById("importLink"),b=document.getElementById("importStatus");d.addEventListener("click",e=>{e.preventDefault(),M.click()});M.addEventListener("change",async e=>{let t=e.target.files[0];if(t){if(!t.name.endsWith(".zip")){p("error","\u274C Please select a .zip file");return}d.style.pointerEvents="none",d.style.opacity="0.5",d.textContent="Importing...",p("loading","Uploading and extracting session...");try{let s=new FormData;s.append("zipFile",t);let o=await fetch("/session/import",{method:"POST",body:s}),n=await o.json();o.ok?(p("success",`\u2705 Session ${n.sessionId} imported successfully!`),setTimeout(()=>{window.location.reload()},1500)):(p("error",`\u274C Import failed: ${n.error}`),d.style.pointerEvents="auto",d.style.opacity="1",d.textContent="Import session from zip")}catch(s){p("error",`\u274C Import failed: ${s.message}`),d.style.pointerEvents="auto",d.style.opacity="1",d.textContent="Import session from zip"}finally{M.value=""}}});function p(e,t){b.className=`import-status ${e}`,b.textContent=t}function Z(e){if(!e||e<0)return"\u2014";let t=Math.floor(e/1e3),s=Math.floor(t/60),o=Math.floor(s/60);if(o>0){let n=s%60;return`${o}h ${n}m`}else if(s>0){let n=t%60;return`${s}m ${n}s`}else return`${t}s`}function _(e){let t=new Date(e),s=t.getFullYear(),o=String(t.getMonth()+1).padStart(2,"0"),n=String(t.getDate()).padStart(2,"0");return`${s}/${o}/${n}`}function j(e){if(!e)return"Unknown";let t=new Date(e),s=t.getFullYear(),o=String(t.getMonth()+1).padStart(2,"0"),n=String(t.getDate()).padStart(2,"0");return`${s}-${o}-${n}`}function O(e){let t={};return e.forEach(s=>{let o=j(s.createdAt);t[o]||(t[o]=[]),t[o].push(s)}),t}function R(e){let t="",s=e.sourceBadgeClass||"source-copilot",o=e.sourceName||"Copilot";if(t+=`<span class="status-badge ${s}" title="${o}">${o}</span>`,e.sessionStatus==="wip"&&(t+='<span class="status-badge wip" title="Session in progress">\u{1F504} WIP</span>'),e.isImported&&(t+='<span class="status-badge imported" title="Imported session">\u{1F4E5}</span>'),e.hasInsight&&(t+='<span class="status-badge insight" title="Has Agent Review">\u{1F4A1}</span>'),e.selectedModel){let v=e.selectedModel.replace("claude-","").replace("gpt-","").replace("gemini-",""),c="model-other";e.selectedModel.includes("claude")?c="model-claude":e.selectedModel.includes("gpt")?c="model-gpt":e.selectedModel.includes("gemini")&&(c="model-gemini"),t+=`<span class="status-badge model ${c}" title="Model: ${l(e.selectedModel)}">${l(v)}</span>`}e.source==="modernize"&&e.modernizeVersion?t+=`<span class="status-badge version" title="Modernize version">${l(e.modernizeVersion)}</span>`:e.copilotVersion&&(t+=`<span class="status-badge version" title="CLI version">${l(e.copilotVersion)}</span>`),e.agentName&&(t+=`<span class="status-badge agent" title="Agent: ${l(e.agentName)}">\u{1F916} ${l(e.agentName)}</span>`);let n="";if(e.summary&&e.summary!=="No summary"&&e.summary!=="Legacy session"){let v=e.summary.replace(/"/g,"&quot;"),c=l(e.summary).replace(/\n+/g," ");n=`<div class="session-summary" title="${v}">${c}</div>`}else n='<div class="session-summary" style="color: #6e7681; font-style: italic;">No summary available</div>';let a="";e.workspace&&e.workspace.cwd&&(a=`
2
+ <div class="session-info-item workspace" title="${l(e.workspace.cwd)}">
3
3
  <svg viewBox="0 0 16 16" fill="currentColor"><path d="M1.75 1A1.75 1.75 0 000 2.75v10.5C0 14.216.784 15 1.75 15h12.5A1.75 1.75 0 0016 13.25v-8.5A1.75 1.75 0 0014.25 3H7.5a.25.25 0 01-.2-.1l-.9-1.2C6.07 1.26 5.55 1 5 1H1.75z"></path></svg>
4
- <span class="session-info-value">${c(e.workspace.cwd)}</span>
4
+ <span class="session-info-value">${l(e.workspace.cwd)}</span>
5
5
  </div>
6
6
  `);let r=e.createdAt?new Date(e.createdAt).toLocaleString("en-US",{month:"2-digit",day:"2-digit",hour:"2-digit",minute:"2-digit",hour12:!1}):"unknown",h="";e.duration&&(h=`
7
7
  <div class="session-info-item">
8
8
  <svg viewBox="0 0 16 16" fill="currentColor"><path d="M0 8a8 8 0 1 1 16 0A8 8 0 0 1 0 8Zm8-6.5a6.5 6.5 0 1 0 0 13 6.5 6.5 0 0 0 0-13ZM7.25 12.5v-5A.75.75 0 0 1 8 6.75h2.5a.75.75 0 0 1 0 1.5H8.75v4.25a.75.75 0 0 1-1.5 0Z"></path></svg>
9
- <span class="session-info-value">${_(e.duration)}</span>
9
+ <span class="session-info-value">${Z(e.duration)}</span>
10
10
  </div>
11
- `);let T=e.sessionStatus==="wip"?" recent-item-wip":"",I="";return e.tags&&e.tags.length>0&&(I=`<div class="session-tags">${e.tags.map(l=>`<span class="session-tag" style="background-color: ${V(l)}" title="${c(l)}">${c(l)}</span>`).join("")}</div>`),`
12
- <a href="/session/${e.id}" class="recent-item${T}" onclick="trackClick('SessionCardClicked', { sessionId: '${c(e.id)}', source: '${c(e.source||"unknown")}' })">
11
+ `);let T=e.sessionStatus==="wip"?" recent-item-wip":"",I="";return e.tags&&e.tags.length>0&&(I=`<div class="session-tags">${e.tags.map(c=>`<span class="session-tag" style="background-color: ${V(c)}" title="${l(c)}">${l(c)}</span>`).join("")}</div>`),`
12
+ <a href="/session/${e.id}" class="recent-item${T}" onclick="trackClick('SessionCardClicked', { sessionId: '${l(e.id)}', source: '${l(e.source||"unknown")}' })">
13
13
  <div class="session-id">
14
- <span class="session-id-text" title="${c(e.id)}">${c(e.id)}</span>
14
+ <span class="session-id-text" title="${l(e.id)}">${l(e.id)}</span>
15
15
  </div>
16
16
  <div class="session-badges-tags">
17
17
  <div class="session-badges">${t}</div>
@@ -32,4 +32,4 @@
32
32
  </div>
33
33
  </div>
34
34
  </a>
35
- `}function c(e){let t=document.createElement("div");return t.textContent=e,t.innerHTML}var b=["#3b82f6","#10b981","#f59e0b","#ef4444","#8b5cf6","#ec4899","#06b6d4","#f97316"];function V(e){let t=0;for(let s=0;s<e.length;s++)t=e.charCodeAt(s)+((t<<5)-t);return b[Math.abs(t)%b.length]}async function U(e){try{let t=e.map(n=>fetch(`/api/sessions/${n}/tags`).then(a=>a.ok?a.json():{tags:[]}).then(a=>({id:n,tags:a.tags||[]})).catch(()=>({id:n,tags:[]}))),s=await Promise.all(t),o={};return s.forEach(({id:n,tags:a})=>{o[n]=a}),o}catch(t){return console.error("Error loading session tags:",t),{}}}async function C(e){let t=e.map(o=>o.id),s=await U(t);e.forEach(o=>{o.tags=s[o.id]||[]})}function H(e){let t=document.getElementById("sourceHint");t&&k[e]?t.innerHTML='Sessions from <span class="hint-code">'+k[e]+"</span>":t&&(t.textContent="")}async function x(e){if(u[e]||(u[e]={offset:0,hasMore:!0}),u[e].offset===0&&!f){f=!0;let t=document.getElementById("sessions-container");t.innerHTML='<div style="text-align: center; color: #6e7681; padding: 40px; font-size: 14px;">\u23F3 Loading...</div>',document.getElementById("loading-indicator").style.display="none";try{let s=await fetch(`/api/sessions/load-more?offset=0&limit=20&source=${encodeURIComponent(e)}`);if(s.ok){let o=await s.json(),n=new Set(m.map(r=>r.id)),a=[];for(let r of o.sessions||[])n.has(r.id)||(m.push(r),a.push(r));u[e].offset=(o.sessions||[]).length,u[e].hasMore=o.hasMore,await C(a)}}catch(s){console.error("Failed to load sessions for source:",e,s)}finally{f=!1}}E()}function Y(){let e=document.querySelectorAll(".filter-pill");if(!new Set([...e].map(s=>s.getAttribute("data-source"))).has(i)){i="copilot";try{localStorage.setItem(S,i)}catch{}}e.forEach(s=>{s.classList.toggle("active",s.getAttribute("data-source")===i)}),H(i),e.forEach(s=>{s.addEventListener("click",async()=>{e.forEach(o=>o.classList.remove("active")),s.classList.add("active"),i=s.getAttribute("data-source");try{localStorage.setItem(S,i)}catch{}H(i),window.trackClick("FilterPillClicked",{pillName:s.textContent.trim(),dataSource:i}),await x(i)})})}document.addEventListener("DOMContentLoaded",async function(){await C(m),window.addEventListener("scroll",P),Y(),i==="copilot"?E():await x(i)});})();
35
+ `}function l(e){let t=document.createElement("div");return t.textContent=e,t.innerHTML}var L=["#3b82f6","#10b981","#f59e0b","#ef4444","#8b5cf6","#ec4899","#06b6d4","#f97316"];function V(e){let t=0;for(let s=0;s<e.length;s++)t=e.charCodeAt(s)+((t<<5)-t);return L[Math.abs(t)%L.length]}async function U(e){try{let t=e.map(n=>fetch(`/api/sessions/${n}/tags`).then(a=>a.ok?a.json():{tags:[]}).then(a=>({id:n,tags:a.tags||[]})).catch(()=>({id:n,tags:[]}))),s=await Promise.all(t),o={};return s.forEach(({id:n,tags:a})=>{o[n]=a}),o}catch(t){return console.error("Error loading session tags:",t),{}}}async function C(e){let t=e.map(o=>o.id),s=await U(t);e.forEach(o=>{o.tags=s[o.id]||[]})}function H(e){let t=document.getElementById("sourceHint");t&&k[e]?t.innerHTML='Sessions from <span class="hint-code">'+k[e]+"</span>":t&&(t.textContent="")}async function x(e){if(u[e]||(u[e]={offset:0,hasMore:!0}),u[e].offset===0&&!f){f=!0;let t=document.getElementById("sessions-container");t.innerHTML='<div style="text-align: center; color: #6e7681; padding: 40px; font-size: 14px;">\u23F3 Loading...</div>',document.getElementById("loading-indicator").style.display="none";try{let s=await fetch(`/api/sessions/load-more?offset=0&limit=20&source=${encodeURIComponent(e)}`);if(s.ok){let o=await s.json(),n=new Set(m.map(r=>r.id)),a=[];for(let r of o.sessions||[])n.has(r.id)||(m.push(r),a.push(r));u[e].offset=(o.sessions||[]).length,u[e].hasMore=o.hasMore,await C(a)}}catch(s){console.error("Failed to load sessions for source:",e,s)}finally{f=!1}}E()}function Y(){let e=document.querySelectorAll(".filter-pill");if(!new Set([...e].map(s=>s.getAttribute("data-source"))).has(i)){i="copilot";try{localStorage.setItem(S,i)}catch{}}e.forEach(s=>{s.classList.toggle("active",s.getAttribute("data-source")===i)}),H(i),e.forEach(s=>{s.addEventListener("click",async()=>{e.forEach(o=>o.classList.remove("active")),s.classList.add("active"),i=s.getAttribute("data-source");try{localStorage.setItem(S,i)}catch{}H(i),window.trackClick("FilterPillClicked",{pillName:s.textContent.trim(),dataSource:i}),await x(i)})})}document.addEventListener("DOMContentLoaded",async function(){await C(m),window.addEventListener("scroll",N),Y(),i==="copilot"?E():await x(i)});})();
@@ -1,13 +1,13 @@
1
- (()=>{var Ae=(d,g)=>()=>(g||d((g={exports:{}}).exports,g),g.exports);var Le=Ae((Bt,oe)=>{function qt(d){let g=new Map,f=new Map,y=0;for(let o of d)if(o.type==="subagent.started"){let u=o.data?.toolCallId;u&&f.set(u,{name:o.data?.agentDisplayName||o.data?.agentName||"SubAgent",colorIndex:y++})}for(let o of d)if(o.type==="assistant.message"&&o.data?.subAgentName&&o.data?.subAgentId){let u=o.data.subAgentId;f.has(u)||f.set(u,{name:o.data.subAgentName,colorIndex:y++}),g.set(o.stableId,u)}for(let o of d)if(o._subagent?.id){let u=o._subagent.id;f.has(u)||f.set(u,{name:o._subagent.name||"SubAgent",colorIndex:y++}),g.set(o.stableId,u)}if(f.size===0)return{ownerMap:g,subagentInfo:f};let B=new Map;for(let o of d)o.id&&B.set(o.id,o);for(let o of d)if(o.type==="assistant.message"){let u=o.data?.parentToolCallId;u&&f.has(u)&&g.set(o.stableId,u)}for(let o of d){if(o.type!=="reasoning")continue;let u=o.parentId,M=0;for(;u&&M<10;){let w=B.get(u);if(!w)break;if(w.type==="assistant.message"){let R=w.data?.parentToolCallId;R&&f.has(R)&&g.set(o.stableId,R);break}u=w.parentId,M++}}let m=new Map;for(let o of d){if(o.type!=="tool.execution_start")continue;let u=o.parentId,M=0;for(;u&&M<10;){let w=B.get(u);if(!w)break;if(w.type==="assistant.message"){let R=w.data?.parentToolCallId;if(R&&f.has(R)){g.set(o.stableId,R);let P=o.data?.toolCallId;P&&m.set(P,R)}break}u=w.parentId,M++}}for(let o of d){if(o.type!=="tool.execution_complete")continue;let u=o.data?.toolCallId;u&&m.has(u)&&g.set(o.stableId,m.get(u))}for(let o of d){if(o.type!=="tool.invocation")continue;let u=o.data?.parentToolCallId;u&&f.has(u)&&g.set(o.stableId,u)}let v=null;for(let o of d)o.type==="subagent.started"&&o.data?.toolCallId&&f.has(o.data.toolCallId)?v=o.data.toolCallId:(o.type==="subagent.completed"||o.type==="subagent.failed")&&o.data?.toolCallId===v?v=null:v&&!g.has(o.stableId)&&g.set(o.stableId,v);return{ownerMap:g,subagentInfo:f}}function Ft(d,g,f){return g?d.filter(y=>(y.type==="subagent.started"||y.type==="subagent.completed"||y.type==="subagent.failed")&&y.data?.toolCallId===g||f.get(y.stableId)===g||y._subagent?.id===g||y.data?.subAgentId===g):d}typeof oe<"u"&&oe.exports&&(oe.exports={computeSubagentOwnership:qt,filterBySubagent:Ft})});var Oe=Ae((Pt,ie)=>{function De(d){if(!d||typeof d!="object")return 0;let g=Number.isFinite(d.inputTokens)?d.inputTokens:0,f=Number.isFinite(d.cacheReadTokens)?d.cacheReadTokens:0,y=Number.isFinite(d.cacheWriteTokens)?d.cacheWriteTokens:0;return Math.max(g-f-y,0)}function Ut(d){if(!d||typeof d!="object")return null;let g=Number.isFinite(d.cacheReadTokens)?d.cacheReadTokens:0,f=De(d)+g;return g===0||f===0?null:Math.round(g/f*100)}typeof ie<"u"&&ie.exports&&(ie.exports={getDisplayInputTokens:De,getCacheHitRatio:Ut})});(function(){let{computeSubagentOwnership:d,filterBySubagent:g}=Le(),{getDisplayInputTokens:f,getCacheHitRatio:y}=Oe();if(typeof Vue>"u"){console.error("Vue is not loaded");return}if(typeof window.VueVirtualScroller>"u"){console.error("VueVirtualScroller is not loaded");return}console.log("Initializing Vue app...");let{createApp:B,ref:m,computed:v,onMounted:o,onBeforeUnmount:u,watch:M}=Vue,{DynamicScroller:w,DynamicScrollerItem:R}=window.VueVirtualScroller,P=B({components:{DynamicScroller:w,DynamicScrollerItem:R},setup(){let p=m(window.__PAGE_DATA.sessionId),x=m(window.__PAGE_DATA.metadata),re=m(!1),me=()=>window.innerWidth<=640,X=m(me()?!0:localStorage.getItem("sidebarCollapsed")==="true");M(X,t=>{me()||localStorage.setItem("sidebarCollapsed",t.toString())});let L=m({}),D=m({}),Y=50,ge=()=>{let t=Object.keys(L.value);t.length>Y&&t.slice(0,t.length-Y).forEach(s=>delete L.value[s]);let e=Object.keys(D.value);e.length>Y&&e.slice(0,e.length-Y).forEach(s=>delete D.value[s])},N=m("all"),H=m(""),F=m(""),pe=m(0),h=m(null),ve=m({start:0,end:0}),A=m(null),le=m(!1),_e=v(()=>{let t=0;return N.value!=="all"&&t++,A.value&&t++,H.value.trim()&&t++,t}),$e=()=>{N.value="all",A.value=null,H.value="",F.value="",le.value=!1},j=null,Z=null;M(H,t=>{clearTimeout(j),j=setTimeout(()=>{F.value=t,t.trim()&&window.trackClick&&window.trackClick("SearchUsed",{query:t.substring(0,50),resultCount:z.value.length,sessionId:p.value})},300)}),M(N,()=>{ge()}),M(F,()=>{ge()});let O=m([]),fe=m(!0),be=m(null),k=v(()=>O.value.filter(e=>e.type!=="assistant.turn_end"&&e.type!=="assistant.turn_complete").sort((e,a)=>{let s=e.timestamp?new Date(e.timestamp).getTime():0,n=a.timestamp?new Date(a.timestamp).getTime():0;return s!==n?s-n:(e._fileIndex??0)-(a._fileIndex??0)}).map((e,a)=>({...e,virtualIndex:a,stableId:e.id||`${e.timestamp}-${e.type}-${a}`}))),qe=t=>{if(!F.value.trim())return!0;let e=F.value.toLowerCase();return[t.data?.message,t.data?.text,t.data?.content,t.data?.reason,t.data?.reasoningText,t.data?.errorType,t.data?.previousModel,t.data?.newModel].filter(Boolean).join(" ").toLowerCase().includes(e)},z=v(()=>{let t=a=>{let s=a.type||"";return s!=="tool.execution_start"&&s!=="tool.execution_complete"},e=k.value.filter(t);return F.value.trim()&&(e=e.filter(qe)),e}),W=v(()=>{let t=z.value;if(A.value){let{ownerMap:s}=Q.value;t=g(t,A.value,s)}N.value!=="all"&&(t=t.filter(s=>s.type===N.value));let e=["assistant.turn_start","subagent.started","subagent.completed","subagent.failed"],a=t.length;return t.map((s,n)=>{let i=t[n+1],r=n===a-1,l=i&&e.includes(i.type);return{...s,filteredIndex:n,filteredTotal:a,isLastEvent:r||l}})}),Fe=v(()=>{let t={};return z.value.forEach(e=>{e.type&&(t[e.type]=(t[e.type]||0)+1)}),t}),Ue=v(()=>{if(!F.value.trim())return null;let t=z.value.length;return t>0?`${t} result${t!==1?"s":""}`:"No matches"}),ze=v(()=>{let t=Object.keys(L.value).filter(a=>L.value[a]).length,e=Object.keys(D.value).filter(a=>D.value[a]).length;return t+e}),Te=v(()=>{let t=z.value.length,e=[{type:"all",label:`All (${t})`,count:t}],a={};z.value.forEach(n=>{n.type&&(a[n.type]=(a[n.type]||0)+1)});let s=Object.entries(a).sort((n,i)=>i[1]-n[1]).map(([n,i])=>({type:n,label:`${n} (${i})`,count:i,disabled:!1}));return[...e,...s]}),G=v(()=>{let t=k.value.filter(a=>a.type==="assistant.turn_start"),e=k.value.filter(a=>a.type==="user.message");return t.map((a,s)=>{let n=s,i=new Date(a.timestamp).getTime(),r,l=t.indexOf(a)+1;l<t.length?r=new Date(t[l].timestamp).getTime():r=Date.now();let c=r-i,b=Math.floor(c/1e3),T=Math.floor(b/60),$=b%60,q=T>0?`${T}m ${$}s`:`${$}s`,V=k.value.slice(0,k.value.indexOf(a)).reverse().find(C=>C.type==="user.message"),te=V?e.indexOf(V)+1:0;return{id:n,index:a.virtualIndex,originalTurnId:a.data?.turnId,timestamp:a.timestamp,duration:q,message:V?.data?.content||V?.data?.transformedContent||"",userReqNumber:te}})}),Ve=v(()=>{let t=[],e=new Map;return G.value.forEach(a=>{let s=a.userReqNumber||0;if(!e.has(s)){let n={reqNumber:s,message:a.message,turns:[]};e.set(s,n),t.push(n)}e.get(s).turns.push(a)}),t}),Be=(t,e)=>t?t.length<=e?t:t.substring(0,e)+"\u2026":"",Q=v(()=>d(k.value)),Pe=v(()=>{let{subagentInfo:t}=Q.value;if(t.size===0)return[];let e=[];for(let[a,s]of t)e.push({toolCallId:a,name:s.name,colorIndex:s.colorIndex});return e}),He=v(()=>{if(!A.value)return null;let{ownerMap:t,subagentInfo:e}=Q.value,a=A.value;if(!e.has(a))return null;let s=0,n=null,i=null;for(let l of k.value){let c=(l.type==="subagent.started"||l.type==="subagent.completed"||l.type==="subagent.failed")&&l.data?.toolCallId===a,b=t.get(l.stableId)===a,T=l._subagent?.id===a,$=l.data?.subAgentId===a;if((c||b||T||$)&&(s++,l.timestamp!==null&&l.timestamp!==void 0)){let q=new Date(l.timestamp).getTime();(n===null||q<n)&&(n=q),(i===null||q>i)&&(i=q)}}let r=n===null||i===null?0:i-n;return{eventCount:s,durationMs:r}}),je=t=>{if(!t)return"";let e=new Date(t),a=String(e.getHours()).padStart(2,"0"),s=String(e.getMinutes()).padStart(2,"0"),n=String(e.getSeconds()).padStart(2,"0");return`${a}:${s}:${n}`},We=t=>{if(!t)return"";let e=new Date(t),a=String(e.getHours()).padStart(2,"0"),s=String(e.getMinutes()).padStart(2,"0"),n=String(e.getSeconds()).padStart(2,"0"),i=String(e.getMilliseconds()).padStart(3,"0");return`${a}:${s}:${n}.${i}`},S=new Map,he=200,Ge=t=>{if(!t)return"";if(S.has(t))return S.get(t);try{let e=t.replace(/\\r\\n/g,`
1
+ (()=>{var $e=(u,g)=>()=>(g||u((g={exports:{}}).exports,g),g.exports);var qe=$e((Gt,ie)=>{function Vt(u){let g=new Map,f=new Map,x=0;for(let n of u)if(n.type==="subagent.started"){let l=n.data?.toolCallId;l&&f.set(l,{name:n.data?.agentDisplayName||n.data?.agentName||"SubAgent",colorIndex:x++,meta:{agentName:n.data?.agentName||"",agentDisplayName:n.data?.agentDisplayName||"",agentDescription:n.data?.agentDescription||""}})}for(let n of u){if(n.type!=="tool.execution_start")continue;let l=n.data?.toolCallId;if(!l||!f.has(l))continue;let v=f.get(l),p=n.data?.arguments;if(typeof p=="string")try{p=JSON.parse(p)}catch{continue}!p||typeof p!="object"||(p.description&&(v.meta.taskDescription=p.description),p.name&&(v.meta.taskName=p.name),p.agent_type&&(v.meta.agentType=p.agent_type),p.mode&&(v.meta.taskMode=p.mode),p.description&&v.name===(v.meta.agentDisplayName||v.meta.agentName)&&(v.name=p.description))}for(let n of u)if(n.type==="assistant.message"&&n.data?.subAgentName&&n.data?.subAgentId){let l=n.data.subAgentId;f.has(l)||f.set(l,{name:n.data.subAgentName,colorIndex:x++,meta:{agentName:n.data.subAgentName}}),g.set(n.stableId,l)}for(let n of u)if(n._subagent?.id){let l=n._subagent.id;f.has(l)||f.set(l,{name:n._subagent.name||"SubAgent",colorIndex:x++,meta:{agentName:n._subagent.name||""}}),g.set(n.stableId,l)}if(f.size===0)return{ownerMap:g,subagentInfo:f};let V=new Map;for(let n of u)n.id&&V.set(n.id,n);for(let n of u)if(n.type==="assistant.message"){let l=n.data?.parentToolCallId;l&&f.has(l)&&g.set(n.stableId,l)}for(let n of u){if(n.type!=="reasoning")continue;let l=n.parentId,v=0;for(;l&&v<10;){let p=V.get(l);if(!p)break;if(p.type==="assistant.message"){let C=p.data?.parentToolCallId;C&&f.has(C)&&g.set(n.stableId,C);break}l=p.parentId,v++}}let m=new Map;for(let n of u){if(n.type!=="tool.execution_start")continue;let l=n.parentId,v=0;for(;l&&v<10;){let p=V.get(l);if(!p)break;if(p.type==="assistant.message"){let C=p.data?.parentToolCallId;if(C&&f.has(C)){g.set(n.stableId,C);let X=n.data?.toolCallId;X&&m.set(X,C)}break}l=p.parentId,v++}}for(let n of u){if(n.type!=="tool.execution_complete")continue;let l=n.data?.toolCallId;l&&m.has(l)&&g.set(n.stableId,m.get(l))}for(let n of u){if(n.type!=="tool.invocation")continue;let l=n.data?.parentToolCallId;l&&f.has(l)&&g.set(n.stableId,l)}let b=null;for(let n of u)n.type==="subagent.started"&&n.data?.toolCallId&&f.has(n.data.toolCallId)?b=n.data.toolCallId:(n.type==="subagent.completed"||n.type==="subagent.failed")&&n.data?.toolCallId===b?b=null:b&&!g.has(n.stableId)&&g.set(n.stableId,b);for(let[n,l]of f)for(let v of u){if(!(g.get(v.stableId)===n||v._subagent?.id===n||v.data?.subAgentId===n))continue;let C=v.model||v.data?.model;if(C){l.meta.model=C;break}}return{ownerMap:g,subagentInfo:f}}function Pt(u,g,f){return g?u.filter(x=>(x.type==="subagent.started"||x.type==="subagent.completed"||x.type==="subagent.failed")&&x.data?.toolCallId===g||f.get(x.stableId)===g||x._subagent?.id===g||x.data?.subAgentId===g):u}typeof ie<"u"&&ie.exports&&(ie.exports={computeSubagentOwnership:Vt,filterBySubagent:Pt})});var Fe=$e((Kt,re)=>{function Ue(u){if(!u||typeof u!="object")return 0;let g=Number.isFinite(u.inputTokens)?u.inputTokens:0,f=Number.isFinite(u.cacheReadTokens)?u.cacheReadTokens:0,x=Number.isFinite(u.cacheWriteTokens)?u.cacheWriteTokens:0;return Math.max(g-f-x,0)}function jt(u){if(!u||typeof u!="object")return null;let g=Number.isFinite(u.cacheReadTokens)?u.cacheReadTokens:0,f=Ue(u)+g;return g===0||f===0?null:Math.round(g/f*100)}typeof re<"u"&&re.exports&&(re.exports={getDisplayInputTokens:Ue,getCacheHitRatio:jt})});(function(){let{computeSubagentOwnership:u,filterBySubagent:g}=qe(),{getDisplayInputTokens:f,getCacheHitRatio:x}=Fe();if(typeof Vue>"u"){console.error("Vue is not loaded");return}if(typeof window.VueVirtualScroller>"u"){console.error("VueVirtualScroller is not loaded");return}console.log("Initializing Vue app...");let{createApp:V,ref:m,computed:b,onMounted:n,onBeforeUnmount:l,watch:v,nextTick:p}=Vue,{DynamicScroller:C,DynamicScrollerItem:X}=window.VueVirtualScroller,ve=V({components:{DynamicScroller:C,DynamicScrollerItem:X},setup(){let h=m(window.__PAGE_DATA.sessionId),w=m(window.__PAGE_DATA.metadata),le=m(!1),fe=()=>window.innerWidth<=640,Y=m(fe()?!0:localStorage.getItem("sidebarCollapsed")==="true");v(Y,e=>{fe()||localStorage.setItem("sidebarCollapsed",e.toString())});let D=m({}),L=m({}),Q=50,be=()=>{let e=Object.keys(D.value);e.length>Q&&e.slice(0,e.length-Q).forEach(s=>delete D.value[s]);let t=Object.keys(L.value);t.length>Q&&t.slice(0,t.length-Q).forEach(s=>delete L.value[s])},R=m("all"),P=m(""),U=m(""),he=m(0),k=m(null),Te=m({start:0,end:0}),A=m(null),Z=m(!1),de=m(""),ye=m(null),ce=m(!1),Be=b(()=>{let e=0;return R.value!=="all"&&e++,A.value&&e++,P.value.trim()&&e++,e}),ze=()=>{R.value="all",A.value=null,P.value="",U.value="",ce.value=!1},j=null,ee=null;v(P,e=>{clearTimeout(j),j=setTimeout(()=>{U.value=e,e.trim()&&window.trackClick&&window.trackClick("SearchUsed",{query:e.substring(0,50),resultCount:B.value.length,sessionId:h.value})},300)}),v(R,()=>{be()}),v(U,()=>{be()}),v(Z,e=>{e&&p(()=>{ye.value?.focus()})});let O=m([]),ke=m(!0),xe=m(null),S=b(()=>O.value.filter(t=>t.type!=="assistant.turn_end"&&t.type!=="assistant.turn_complete").sort((t,a)=>{let s=t.timestamp?new Date(t.timestamp).getTime():0,o=a.timestamp?new Date(a.timestamp).getTime():0;return s!==o?s-o:(t._fileIndex??0)-(a._fileIndex??0)}).map((t,a)=>({...t,virtualIndex:a,stableId:t.id||`${t.timestamp}-${t.type}-${a}`}))),Ve=e=>{if(!U.value.trim())return!0;let t=U.value.toLowerCase();return[e.data?.message,e.data?.text,e.data?.content,e.data?.reason,e.data?.reasoningText,e.data?.errorType,e.data?.previousModel,e.data?.newModel].filter(Boolean).join(" ").toLowerCase().includes(t)},B=b(()=>{let e=a=>{let s=a.type||"";return s!=="tool.execution_start"&&s!=="tool.execution_complete"},t=S.value.filter(e);return U.value.trim()&&(t=t.filter(Ve)),t}),H=b(()=>{let e=B.value;if(A.value){let{ownerMap:s}=G.value;e=g(e,A.value,s)}R.value!=="all"&&(e=e.filter(s=>s.type===R.value));let t=["assistant.turn_start","subagent.started","subagent.completed","subagent.failed"],a=e.length;return e.map((s,o)=>{let i=e[o+1],r=o===a-1,d=i&&t.includes(i.type);return{...s,filteredIndex:o,filteredTotal:a,isLastEvent:r||d}})}),Pe=b(()=>{let e={};return B.value.forEach(t=>{t.type&&(e[t.type]=(e[t.type]||0)+1)}),e}),je=b(()=>{if(!U.value.trim())return null;let e=B.value.length;return e>0?`${e} result${e!==1?"s":""}`:"No matches"}),He=b(()=>{let e=Object.keys(D.value).filter(a=>D.value[a]).length,t=Object.keys(L.value).filter(a=>L.value[a]).length;return e+t}),we=b(()=>{let e=B.value.length,t=[{type:"all",label:`All (${e})`,count:e}],a={};B.value.forEach(o=>{o.type&&(a[o.type]=(a[o.type]||0)+1)});let s=Object.entries(a).sort((o,i)=>i[1]-o[1]).map(([o,i])=>({type:o,label:`${o} (${i})`,count:i,disabled:!1}));return[...t,...s]}),W=b(()=>{let e=S.value.filter(a=>a.type==="assistant.turn_start"),t=S.value.filter(a=>a.type==="user.message");return e.map((a,s)=>{let o=s,i=new Date(a.timestamp).getTime(),r,d=e.indexOf(a)+1;d<e.length?r=new Date(e[d].timestamp).getTime():r=Date.now();let c=r-i,T=Math.floor(c/1e3),y=Math.floor(T/60),$=T%60,q=y>0?`${y}m ${$}s`:`${$}s`,z=S.value.slice(0,S.value.indexOf(a)).reverse().find(I=>I.type==="user.message"),ae=z?t.indexOf(z)+1:0;return{id:o,index:a.virtualIndex,originalTurnId:a.data?.turnId,timestamp:a.timestamp,duration:q,message:z?.data?.content||z?.data?.transformedContent||"",userReqNumber:ae}})}),We=b(()=>{let e=[],t=new Map;return W.value.forEach(a=>{let s=a.userReqNumber||0;if(!t.has(s)){let o={reqNumber:s,message:a.message,turns:[]};t.set(s,o),e.push(o)}t.get(s).turns.push(a)}),e}),Ge=(e,t)=>e?e.length<=t?e:e.substring(0,t)+"\u2026":"",G=b(()=>u(S.value)),ue=b(()=>{let{subagentInfo:e}=G.value;if(e.size===0)return[];let t=[];for(let[a,s]of e)t.push({toolCallId:a,name:s.name,colorIndex:s.colorIndex,meta:s.meta||{}});return t}),Ke=b(()=>{let e=de.value.toLowerCase().trim();return e?ue.value.filter(t=>{let a=t.meta||{};return[t.name,a.taskName,a.taskDescription,a.agentName,a.agentType,a.agentDescription,a.model].filter(Boolean).join(" ").toLowerCase().includes(e)}):ue.value}),Je=b(()=>{if(!A.value)return null;let{ownerMap:e,subagentInfo:t}=G.value,a=A.value;if(!t.has(a))return null;let s=0,o=null,i=null;for(let d of S.value){let c=(d.type==="subagent.started"||d.type==="subagent.completed"||d.type==="subagent.failed")&&d.data?.toolCallId===a,T=e.get(d.stableId)===a,y=d._subagent?.id===a,$=d.data?.subAgentId===a;if((c||T||y||$)&&(s++,d.timestamp!==null&&d.timestamp!==void 0)){let q=new Date(d.timestamp).getTime();(o===null||q<o)&&(o=q),(i===null||q>i)&&(i=q)}}let r=o===null||i===null?0:i-o;return{eventCount:s,durationMs:r}}),Xe=e=>{if(!e)return"";let t=new Date(e),a=String(t.getHours()).padStart(2,"0"),s=String(t.getMinutes()).padStart(2,"0"),o=String(t.getSeconds()).padStart(2,"0");return`${a}:${s}:${o}`},Ye=e=>{if(!e)return"";let t=new Date(e),a=String(t.getHours()).padStart(2,"0"),s=String(t.getMinutes()).padStart(2,"0"),o=String(t.getSeconds()).padStart(2,"0"),i=String(t.getMilliseconds()).padStart(3,"0");return`${a}:${s}:${o}.${i}`},E=new Map,Ce=200,Qe=e=>{if(!e)return"";if(E.has(e))return E.get(e);try{let t=e.replace(/\\r\\n/g,`
2
2
  `).replace(/\\n/g,`
3
- `).replace(/\\t/g," ").replace(/\\"/g,'"').replace(/\\\\/g,"\\"),a={ALLOWED_TAGS:["p","br","strong","em","code","pre","a","ul","ol","li","h1","h2","h3","h4","h5","h6","blockquote","table","thead","tbody","tr","th","td","hr","del","span","div","mark"],ALLOWED_ATTR:["href","style","class"],ALLOW_DATA_ATTR:!1,ALLOWED_URI_REGEXP:/^(?:(?:(?:f|ht)tps?|mailto|tel|callto|sms|cid|xmpp):|[^a-z]|[a-z+.-]+(?:[^a-z+.\-:]|$))/i},s=e.match(/^---\n([\s\S]*?)\n---\n([\s\S]*)$/);if(s){let r=s[1],l=s[2],c=r.split(`
4
- `),b=[],T=0;for(;T<c.length;){let C=c[T];if(!C.trim()||!C.includes(":")){T++;continue}let ae=C.indexOf(":"),se=C.substring(0,ae).trim(),ne=C.substring(ae+1).trim();if(ne==="|"||ne===">"){let Ne=[];for(T++;T<c.length&&(c[T].startsWith(" ")||c[T].startsWith(" ")||c[T].trim()==="");)Ne.push(c[T].trim()),T++;let _t=ne===">"?" ":`
5
- `;b.push({key:se,value:Ne.filter($t=>$t).join(_t)})}else b.push({key:se,value:ne}),T++}let $='<table style="margin-bottom: 16px; border-collapse: collapse; width: 100%;"><tbody>';b.forEach(C=>{let ae=DOMPurify.sanitize(C.key,{ALLOWED_TAGS:[]}),se=DOMPurify.sanitize(C.value,{ALLOWED_TAGS:[]});$+=`<tr><td style="padding: 4px 12px; border: 1px solid #30363d; font-weight: 600; color: #7d8590;">${ae}</td><td style="padding: 4px 12px; border: 1px solid #30363d;">${se}</td></tr>`}),$+="</tbody></table>";let q=marked.parse(l),V=DOMPurify.sanitize(q,a),te=$+V;if(S.size>=he){let C=S.keys().next().value;S.delete(C)}return S.set(t,te),te}let n=marked.parse(e),i=DOMPurify.sanitize(n,a);if(S.size>=he){let r=S.keys().next().value;S.delete(r)}return S.set(t,i),i}catch{return t}},Ke=t=>{let e={...L.value},a=!!e[t];e[t]?delete e[t]:e[t]=!0,L.value=e,window.trackClick&&window.trackClick("EventExpanded",{eventType:"tool",action:a?"collapse":"expand",sessionId:p.value})},Je=(t,e)=>{if(!e||!e.trim()||!t)return t;let a=e.trim(),s=Ce(a).replace(/[.*+?^${}()|[\]\\]/g,"\\$&"),n=document.createElement("div");n.innerHTML=t;let i=r=>{if(r.nodeType===Node.TEXT_NODE){let l=r.textContent,c=new RegExp(`(${s})`,"gi");if(c.test(l)){let b=l.replace(c,'<mark class="search-highlight">$1</mark>'),T=document.createElement("span");T.innerHTML=b,r.parentNode.replaceChild(T,r)}}else r.nodeType===Node.ELEMENT_NODE&&r.tagName!=="SCRIPT"&&r.tagName!=="STYLE"&&Array.from(r.childNodes).forEach(i)};return Array.from(n.childNodes).forEach(i),n.innerHTML},Xe=t=>{let e={...D.value},a=!!e[t];e[t]?delete e[t]:e[t]=!0,D.value=e,window.trackClick&&window.trackClick("EventExpanded",{eventType:"content",action:a?"collapse":"expand",sessionId:p.value})},Ye=t=>t?t.split(`
6
- `).length>20||t.length>2e3:!1,Ze=t=>{let e=t.split(`
7
- `);return e.length<=20?t:e.slice(0,20).join(`
3
+ `).replace(/\\t/g," ").replace(/\\"/g,'"').replace(/\\\\/g,"\\"),a={ALLOWED_TAGS:["p","br","strong","em","code","pre","a","ul","ol","li","h1","h2","h3","h4","h5","h6","blockquote","table","thead","tbody","tr","th","td","hr","del","span","div","mark"],ALLOWED_ATTR:["href","style","class"],ALLOW_DATA_ATTR:!1,ALLOWED_URI_REGEXP:/^(?:(?:(?:f|ht)tps?|mailto|tel|callto|sms|cid|xmpp):|[^a-z]|[a-z+.-]+(?:[^a-z+.\-:]|$))/i},s=t.match(/^---\n([\s\S]*?)\n---\n([\s\S]*)$/);if(s){let r=s[1],d=s[2],c=r.split(`
4
+ `),T=[],y=0;for(;y<c.length;){let I=c[y];if(!I.trim()||!I.includes(":")){y++;continue}let se=I.indexOf(":"),ne=I.substring(0,se).trim(),oe=I.substring(se+1).trim();if(oe==="|"||oe===">"){let _e=[];for(y++;y<c.length&&(c[y].startsWith(" ")||c[y].startsWith(" ")||c[y].trim()==="");)_e.push(c[y].trim()),y++;let Bt=oe===">"?" ":`
5
+ `;T.push({key:ne,value:_e.filter(zt=>zt).join(Bt)})}else T.push({key:ne,value:oe}),y++}let $='<table style="margin-bottom: 16px; border-collapse: collapse; width: 100%;"><tbody>';T.forEach(I=>{let se=DOMPurify.sanitize(I.key,{ALLOWED_TAGS:[]}),ne=DOMPurify.sanitize(I.value,{ALLOWED_TAGS:[]});$+=`<tr><td style="padding: 4px 12px; border: 1px solid #30363d; font-weight: 600; color: #7d8590;">${se}</td><td style="padding: 4px 12px; border: 1px solid #30363d;">${ne}</td></tr>`}),$+="</tbody></table>";let q=marked.parse(d),z=DOMPurify.sanitize(q,a),ae=$+z;if(E.size>=Ce){let I=E.keys().next().value;E.delete(I)}return E.set(e,ae),ae}let o=marked.parse(t),i=DOMPurify.sanitize(o,a);if(E.size>=Ce){let r=E.keys().next().value;E.delete(r)}return E.set(e,i),i}catch{return e}},Ze=e=>{let t={...D.value},a=!!t[e];t[e]?delete t[e]:t[e]=!0,D.value=t,window.trackClick&&window.trackClick("EventExpanded",{eventType:"tool",action:a?"collapse":"expand",sessionId:h.value})},et=(e,t)=>{if(!t||!t.trim()||!e)return e;let a=t.trim(),s=Me(a).replace(/[.*+?^${}()|[\]\\]/g,"\\$&"),o=document.createElement("div");o.innerHTML=e;let i=r=>{if(r.nodeType===Node.TEXT_NODE){let d=r.textContent,c=new RegExp(`(${s})`,"gi");if(c.test(d)){let T=d.replace(c,'<mark class="search-highlight">$1</mark>'),y=document.createElement("span");y.innerHTML=T,r.parentNode.replaceChild(y,r)}}else r.nodeType===Node.ELEMENT_NODE&&r.tagName!=="SCRIPT"&&r.tagName!=="STYLE"&&Array.from(r.childNodes).forEach(i)};return Array.from(o.childNodes).forEach(i),o.innerHTML},tt=e=>{let t={...L.value},a=!!t[e];t[e]?delete t[e]:t[e]=!0,L.value=t,window.trackClick&&window.trackClick("EventExpanded",{eventType:"content",action:a?"collapse":"expand",sessionId:h.value})},at=e=>e?e.split(`
6
+ `).length>20||e.length>2e3:!1,st=e=>{let t=e.split(`
7
+ `);return t.length<=20?e:t.slice(0,20).join(`
8
8
  `)+`
9
9
 
10
- ...`},Qe=(t,e)=>{if(e?.data?.badgeLabel&&e?.data?.badgeClass)return{label:e.data.badgeLabel,class:e.data.badgeClass};if(t==="message"&&e?.data?.role==="toolResult")return{label:"TOOL RESULT",class:"badge-tool"};if(t==="session.model_change")return{label:"MODEL CHANGE",class:"badge-session"};if(t==="session.truncation")return{label:"TRUNCATION",class:"badge-truncation"};if(t==="session.compaction_start"||t==="session.compaction_complete")return{label:"COMPACTION",class:"badge-compaction"};if(t==="system.notification")return{label:"SYSTEM",class:"badge-system"};let s=(t||"").split(".")[0]||"unknown";return{user:{label:"USER",class:"badge-user"},assistant:{label:"ASSISTANT",class:"badge-assistant"},reasoning:{label:"REASONING",class:"badge-reasoning"},turn:{label:"TURN",class:"badge-turn"},tool:{label:"TOOL",class:"badge-tool"},subagent:{label:"SUBAGENT",class:"badge-subagent"},skill:{label:"SKILL",class:"badge-skill"},session:{label:"SESSION",class:"badge-session"},error:{label:"ERROR",class:"badge-error"},abort:{label:"ABORT",class:"badge-error"}}[s]||{label:s.toUpperCase(),class:"badge-info"}},et=t=>{if(!t.complete)return{icon:"\u23F3",color:"tool-status-running",text:""};let e=t.complete.data||{};return e.error||e.isError?{icon:"\u274C",color:"tool-status-error",text:""}:{icon:"\u2713",color:"tool-status-success",text:""}},tt=t=>{if(!t.complete?.data?.error)return"";let e=t.complete.data.error;if(typeof e=="object"&&e.message)return e.message;if(typeof e=="string"){try{let a=JSON.parse(e);if(a.message)return a.message}catch{}return e}return String(e)},at=t=>{if(!t.complete)return"";let e=new Date(t.start.timestamp).getTime(),s=new Date(t.complete.timestamp).getTime()-e;return s>=100?`${parseFloat((s/1e3).toPrecision(3))}s`:""},zt=t=>{let e={};if(t.start?.timestamp&&(e.startTime=t.start.timestamp),t.complete?.timestamp&&(e.endTime=t.complete.timestamp),e.startTime&&e.endTime){let a=new Date(e.endTime).getTime()-new Date(e.startTime).getTime();a>=0&&(e.duration=`${parseFloat((a/1e3).toPrecision(3))}s (${a}ms)`)}return e},st=t=>{if(!t.start)return"";let e=t.start.data?.arguments||{},a=t.start.data?.toolName||t.tool||"",s="";if(a==="bash"||a==="exec")s=e.command||e.description||"";else if(a==="ask_user")s=e.question||e.message||"";else if(a==="read"||a==="write"||a==="edit")s=e.file_path||e.path||"";else if(a==="view")s=e.path||e.file||"";else if(a==="create")s=e.path||e.name||"";else if(a==="report_intent")s=e.intent||e.message||"";else if(a==="web_search")s=e.query||"";else if(a==="web_fetch")s=e.url||"";else if(a==="browser"){let n=e.action||"",i=e.targetUrl||e.url||"";s=i?`${n} ${i}`:n}else s=e.description||e.command||e.message||e.path||e.file_path||e.query||"";return s&&s.length>200&&(s=s.substring(0,200)+"..."),s},nt=t=>t.data?.tools&&t.data.tools.length>0,ot=t=>t.data?.tools&&Array.isArray(t.data.tools)?t.data.tools.filter(e=>e&&typeof e=="object"&&e.name).map(e=>{let a=e.result!==void 0||e.status==="completed"||e.status==="error",s={};if(e.startTime&&(s.startTime=e.startTime),e.endTime&&(s.endTime=e.endTime),s.startTime&&s.endTime){let n=new Date(s.endTime).getTime()-new Date(s.startTime).getTime();n>=0&&(s.duration=`${parseFloat((n/1e3).toPrecision(3))}s (${n}ms)`)}return{tool:e.name,timing:s,start:{timestamp:e.startTime,data:{toolName:e.name,arguments:e.input||e.arguments||{}}},complete:a?{timestamp:e.endTime,data:{result:e.result,error:e.status==="error"?e.error:null}}:null}}):[],ce=["#58a6ff","#f0883e","#a371f7","#3fb950","#f778ba","#79c0ff","#d29922","#56d4dd"],it=t=>{let e=0;for(let a=0;a<t.length;a++){let s=t.charCodeAt(a);e=(e<<5)-e+s,e=e&e}return e},ye=t=>{let{ownerMap:e,subagentInfo:a}=Q.value;if(t.type==="subagent.started"||t.type==="subagent.completed"||t.type==="subagent.failed"){let i=t.data?.toolCallId;if(i&&a.has(i)){let r=a.get(i);return{name:r.name,toolCallId:i,colorIndex:r.colorIndex}}return null}if(t._subagent){let i=t._subagent.id,r=t._subagent.name;if(a.has(i)){let l=a.get(i);return{name:l.name,toolCallId:i,colorIndex:l.colorIndex}}return{name:r,toolCallId:i,colorIndex:Math.abs(it(i))}}if(t.data?.subAgentId){let i=t.data.subAgentId,r=a.get(i);if(r)return{name:r.name,toolCallId:i,colorIndex:r.colorIndex}}let s=e.get(t.stableId);if(!s)return null;let n=a.get(s);return n?{name:n.name,toolCallId:s,colorIndex:n.colorIndex}:null},rt=t=>{let e=ye(t);return e?ce[e.colorIndex%ce.length]:null},lt=t=>{if(window.trackClick){let e=Te.value.find(a=>a.type===t);window.trackClick("EventFilterClicked",{filterType:t,filterLabel:e?e.label:t,sessionId:p.value})}N.value=t},ct=t=>{A.value=t,t&&(N.value="all"),window.trackClick&&window.trackClick("SubagentSelected",{subagent:t,sessionId:p.value})},xe=t=>{H.value="",N.value="all",A.value=null,pe.value=t.id,Vue.nextTick(()=>{if(h.value){let e=W.value.findIndex(a=>a.virtualIndex===t.index);if(e>=0){let a=s=>{s<=0||!h.value||(h.value.scrollToItem(e),setTimeout(()=>a(s-1),100))};setTimeout(()=>a(3),50)}}})},dt=()=>{if(!h.value)return;let t=e=>{e<=0||!h.value||(h.value.scrollToItem(0),setTimeout(()=>t(e-1),100))};t(3)},ut=()=>{if(!h.value)return;let t=W.value.length-1,e=a=>{a<=0||!h.value||(h.value.scrollToItem(t),setTimeout(()=>e(a-1),100))};e(5)},ke=t=>{window.trackClick&&window.trackClick("TurnClicked",{turnNumber:t,sessionId:p.value});let e=G.value.find(a=>a.id===t);if(e){let a=`UserReq${e.userReqNumber}_Turn${e.id}`,s=`${window.location.pathname}?eventType=assistant.turn_start&eventName=${a}`;window.history.pushState({},"",s),xe(e)}},mt=t=>{if(!t)return"";let e=t.replace(/\/$/,"").split("/");return e[e.length-1]||t},gt=t=>{let e=G.value.find(s=>s.index===t);if(!e)return"?";let a=e.originalTurnId??e.id;return e.userReqNumber>0?`${e.userReqNumber} - Turn ${a}`:`Turn ${a}`},pt=t=>G.value.find(a=>a.index===t)?.duration||null,Ce=t=>{let e=document.createElement("div");return e.textContent=t,e.innerHTML},vt=t=>t?new Date(t).toLocaleString():"N/A",ft=async()=>{console.log("[Export] exportSession called"),window.trackClick&&window.trackClick("ExportClicked",{sessionId:p.value}),re.value=!0;try{console.log("[Export] Fetching:",`/session/${p.value}/export`);let t=await fetch(`/session/${p.value}/export`);if(console.log("[Export] Response received:",t.status,t.ok),console.log("[Export] Response received:",t.status,t.ok),!t.ok)throw new Error("Share failed");console.log("[Export] Creating blob...");let e=await t.blob();console.log("[Export] Blob size:",e.size,"type:",e.type);let a=window.URL.createObjectURL(e);console.log("[Export] Creating download link...");let s=document.createElement("a");s.href=a,s.download=`session-${p.value}.zip`,document.body.appendChild(s),s.click(),console.log("[Export] Download triggered"),window.URL.revokeObjectURL(a),document.body.removeChild(s),console.log("[Export] Showing success feedback...");let n="\u{1F4E4} Share Session",i="\u2713 Downloaded!",r=document.querySelector(".export-btn");r&&(r.textContent=i,r.style.background="#238636",console.log("[Export] Button text updated to:",r.textContent),setTimeout(()=>{r.textContent=n,r.style.background="",console.log("[Export] Button text restored")},2e3))}catch(t){console.error("[Export] Share session error:",t),alert("Failed to share session: "+t.message)}finally{re.value=!1,console.log("[Export] Export complete")}},we=t=>{let e=document.querySelector(".filter-type-wrapper");e&&!e.contains(t.target)&&(le.value=!1)},Se=t=>{t.ctrlKey&&t.key==="b"&&(t.preventDefault(),X.value=!X.value)};u(()=>{document.removeEventListener("click",we),window.removeEventListener("keydown",Se),j&&(clearTimeout(j),j=null),Z&&(Z(),Z=null),L.value={},D.value={},S.clear()}),o(async()=>{document.addEventListener("click",we);try{console.log("[Navigation] Starting event loading...");let e=await fetch(`/api/sessions/${p.value}/events`);if(!e.ok)throw new Error(`Failed to load events: ${e.statusText}`);let a=await e.json();if(Array.isArray(a))O.value=a;else if(a.events&&Array.isArray(a.events))O.value=a.events,console.log("[Navigation] Pagination:",a.pagination);else throw new Error("Invalid response format");if(console.log("[Navigation] Events loaded:",O.value.length),O.value.length>0){let l=O.value[O.value.length-1],c=l.timestamp||l.time||l.data?.timestamp;c&&(x.value.updated=new Date(c))}let s=new URLSearchParams(window.location.search),n=s.get("eventType"),i=s.get("eventName"),r=s.get("eventTimestamp");console.log("[Navigation] URL params:",n,i,r),n&&i&&(console.log("[Navigation] Waiting for Vue to render..."),Vue.nextTick(()=>{console.log("[Navigation] nextTick - flatEvents count:",k.value?.length);let l=null;if(n==="assistant.turn_start"){let c=i.match(/UserReq(\d+)_Turn(\d+)/);if(c){let b=parseInt(c[2],10);if(!isNaN(b)){console.log("[Navigation] Jumping to turn:",b),ke(b);return}}}else n==="subagent.started"?(console.log("[Navigation] Searching for subagent:",i,"timestamp:",r),r&&(l=k.value.find(c=>c.type==="subagent.started"&&c.timestamp===r)),l||(l=k.value.find(c=>c.type==="subagent.started"&&(c.data?.agentDisplayName===i||c.data?.agentName===i||c.data?.label===i))),console.log("[Navigation] Target event found:",l?"YES":"NO","virtualIndex:",l?.virtualIndex)):l=k.value.find(c=>c.type===n);if(l){let c=W.value.findIndex(b=>b.virtualIndex===l.virtualIndex);if(console.log("[Navigation] Target in filteredEvents at index:",c),c>=0&&h.value){console.log("[Navigation] Scrolling to index:",c);let b=T=>{T<=0||!h.value||(h.value.scrollToItem(c),setTimeout(()=>b(T-1),100))};setTimeout(()=>b(3),50)}else console.log("[Navigation] Failed - targetIndex:",c,"scrollerRef:",!!h.value)}else console.log("[Navigation] Target event not found")}))}catch(e){console.error("Error loading events:",e),be.value=e.message}finally{fe.value=!1}window.addEventListener("keydown",Se),window.marked&&marked.setOptions({breaks:!0,gfm:!0});let t=()=>{if(!h.value)return;let e=null;if(h.value.$el&&typeof h.value.$el.querySelector=="function"?e=h.value.$el.querySelector(".vue-recycle-scroller"):h.value.querySelector&&typeof h.value.querySelector=="function"&&(e=h.value.querySelector(".vue-recycle-scroller")),e||(e=document.querySelector(".vue-recycle-scroller")),e){let a=e.scrollTop,s=e.clientHeight,n=80,i=Math.floor(a/n),r=Math.ceil(s/n),l=Math.min(i+r,W.value.length),c=Math.max(1,i+1),b=Math.max(1,l);ve.value={start:Math.min(c,b),end:b}}};setTimeout(()=>{t();let e=document.querySelector(".vue-recycle-scroller");e&&(e.addEventListener("scroll",t),Z=()=>{e.removeEventListener("scroll",t)})},500)});let K=m([]),de=m([]),J=m(!1),I=m([]),_=m(""),ue=m(null),E=m(""),U=m(!1),ee=m([]),Ie=m(0),bt=t=>!t||t===0?"0":t<1e3?t.toString():Math.floor(t/1e3)+"K",Tt=t=>{if(!t||t===0)return"0s";let e=Math.floor(t/1e3);if(e<60)return(t/1e3).toFixed(1)+"s";let a=Math.floor(e/60),s=e%60;return`${a}m ${s}s`},ht=v(()=>{if(!x.value.usage||!x.value.usage.modelMetrics)return 0;let t=0;for(let e in x.value.usage.modelMetrics){let a=x.value.usage.modelMetrics[e].usage;a&&(t+=(a.inputTokens||0)+(a.outputTokens||0))}return t}),yt=v(()=>{if(!x.value.usage||!x.value.usage.modelMetrics)return 0;let t=0;for(let e in x.value.usage.modelMetrics)t+=x.value.usage.modelMetrics[e].requests?.count||0;return t}),xt=v(()=>!x.value.usage||!x.value.usage.modelMetrics?0:Object.keys(x.value.usage.modelMetrics).length),kt=t=>{let e=x.value.usage?.modelMetrics[t];return!e||!e.usage?null:y(e.usage)},Ct=t=>{let e=x.value.usage?.modelMetrics[t];return!e||!e.usage?0:f(e.usage)},wt=v(()=>{let t=new Map;for(let e of k.value)if(e.data?.tools&&Array.isArray(e.data.tools))for(let a of e.data.tools)a&&a.name&&t.set(a.name,(t.get(a.name)||0)+1);return Array.from(t,([e,a])=>({name:e,count:a})).sort((e,a)=>a.count-e.count)}),St=t=>t==null?"":t+" premium",Ee=["#3b82f6","#10b981","#f59e0b","#ef4444","#8b5cf6","#ec4899","#06b6d4","#f97316"],It=t=>{let e=0;for(let a=0;a<t.length;a++)e=t.charCodeAt(a)+((e<<5)-e);return Ee[Math.abs(e)%Ee.length]},Et=async()=>{try{let t=await fetch(`/api/sessions/${p.value}/tags`);if(t.ok){let e=await t.json();K.value=e.tags||[]}}catch(t){console.error("Error loading tags:",t)}},Me=async()=>{try{let t=await fetch("/api/tags");if(t.ok){let e=await t.json();de.value=e.tags||[]}}catch(t){console.error("Error loading all tags:",t)}},Mt=async t=>{try{window.trackClick&&t.filter(s=>!K.value.includes(s)).forEach(s=>{window.trackClick("TagAdded",{sessionId:p.value,tag:s})});let e=await fetch(`/api/sessions/${p.value}/tags`,{method:"PUT",headers:{"Content-Type":"application/json"},body:JSON.stringify({tags:t})});if(e.ok){let a=await e.json();return K.value=a.tags||[],E.value="",!0}else{let a=await e.json();return E.value=a.error||"Failed to save tags",!1}}catch(e){return console.error("Error saving tags:",e),E.value="Network error",!1}},Rt=()=>{I.value=[...K.value],J.value=!0,E.value="",setTimeout(()=>{ue.value&&ue.value.focus()},10)},Nt=()=>{J.value=!1,I.value=[],_.value="",U.value=!1,E.value=""},Re=()=>{let t=_.value.trim().toLowerCase();if(t){if(t.length>30){E.value="Tag must be 30 characters or less";return}if(I.value.length>=10){E.value="Maximum 10 tags per session";return}if(I.value.includes(t)){E.value="Tag already added",_.value="";return}I.value.push(t),_.value="",U.value=!1,E.value=""}},At=t=>{I.value=I.value.filter(e=>e!==t),E.value=""},Lt=()=>{let t=_.value.trim().toLowerCase();if(!t){U.value=!1,ee.value=[];return}let e=de.value.filter(a=>a.toLowerCase().includes(t)&&!I.value.includes(a)).slice(0,5);e.length>0?(U.value=!0,ee.value=e,Ie.value=0):(U.value=!1,ee.value=[])},Dt=t=>{_.value=t,Re()},Ot=async()=>{setTimeout(async()=>{if(!J.value)return;await Mt(I.value)&&(J.value=!1,I.value=[],_.value="",U.value=!1,await Me())},200)};return o(async()=>{await Et(),await Me()}),{sessionId:p,metadata:x,exporting:re,sidebarCollapsed:X,expandedTools:L,expandedContent:D,expansionCount:ze,currentFilter:N,searchText:H,currentTurnIndex:pe,scrollerRef:h,visibleRange:ve,loadedEvents:O,eventsLoading:fe,eventsError:be,flatEvents:k,filteredEvents:W,eventCounts:Fe,filters:Te,turns:G,userReqs:Ve,truncateText:Be,formatTime:je,formatToolTime:We,formatDateTime:vt,renderMarkdown:Ge,highlightSearchText:Je,toggleTool:Ke,toggleContent:Xe,isContentTooLong:Ye,truncateContent:Ze,getBadgeInfo:Qe,getToolStatus:et,getToolErrorMessage:tt,getToolDuration:at,getToolCommand:st,hasTools:nt,getToolGroups:ot,getSubagentInfo:ye,getSubagentColor:rt,setFilter:lt,selectSubagent:ct,selectedSubagent:A,subagentList:Pe,subagentTokenUsage:He,SUBAGENT_COLORS:ce,typeFilterOpen:le,activeFilterCount:_e,clearAllFilters:$e,scrollToTurn:xe,scrollToTop:dt,scrollToBottom:ut,jumpToTurn:ke,getTurnNumber:gt,getTurnDuration:pt,repoBasename:mt,escapeHtml:Ce,exportSession:ft,searchResultCount:Ue,sessionTags:K,allTags:de,tagsEditing:J,editingTags:I,tagInputValue:_,tagInputRef:ue,tagsError:E,showAutocomplete:U,autocompleteOptions:ee,autocompleteSelectedIndex:Ie,getTagColor:It,startEditTags:Rt,cancelEditTags:Nt,addTag:Re,removeTagFromEdit:At,updateAutocomplete:Lt,selectAutocompleteOption:Dt,saveTagsOnBlur:Ot,formatTokens:bt,formatDuration:Tt,formatCost:St,totalTokens:ht,totalRequests:yt,totalModels:xt,getDisplayUsageInputTokens:Ct,getModelCacheHitRatio:kt,toolCallingSummary:wt}},template:`
10
+ ...`},nt=(e,t)=>{if(t?.data?.badgeLabel&&t?.data?.badgeClass)return{label:t.data.badgeLabel,class:t.data.badgeClass};if(e==="message"&&t?.data?.role==="toolResult")return{label:"TOOL RESULT",class:"badge-tool"};if(e==="session.model_change")return{label:"MODEL CHANGE",class:"badge-session"};if(e==="session.truncation")return{label:"TRUNCATION",class:"badge-truncation"};if(e==="session.compaction_start"||e==="session.compaction_complete")return{label:"COMPACTION",class:"badge-compaction"};if(e==="system.notification")return{label:"SYSTEM",class:"badge-system"};let s=(e||"").split(".")[0]||"unknown";return{user:{label:"USER",class:"badge-user"},assistant:{label:"ASSISTANT",class:"badge-assistant"},reasoning:{label:"REASONING",class:"badge-reasoning"},turn:{label:"TURN",class:"badge-turn"},tool:{label:"TOOL",class:"badge-tool"},subagent:{label:"SUBAGENT",class:"badge-subagent"},skill:{label:"SKILL",class:"badge-skill"},session:{label:"SESSION",class:"badge-session"},error:{label:"ERROR",class:"badge-error"},abort:{label:"ABORT",class:"badge-error"}}[s]||{label:s.toUpperCase(),class:"badge-info"}},ot=e=>{if(!e.complete)return{icon:"\u23F3",color:"tool-status-running",text:""};let t=e.complete.data||{};return t.error||t.isError?{icon:"\u274C",color:"tool-status-error",text:""}:{icon:"\u2713",color:"tool-status-success",text:""}},it=e=>{if(!e.complete?.data?.error)return"";let t=e.complete.data.error;if(typeof t=="object"&&t.message)return t.message;if(typeof t=="string"){try{let a=JSON.parse(t);if(a.message)return a.message}catch{}return t}return String(t)},rt=e=>{if(!e.complete)return"";let t=new Date(e.start.timestamp).getTime(),s=new Date(e.complete.timestamp).getTime()-t;return s>=100?`${parseFloat((s/1e3).toPrecision(3))}s`:""},Ht=e=>{let t={};if(e.start?.timestamp&&(t.startTime=e.start.timestamp),e.complete?.timestamp&&(t.endTime=e.complete.timestamp),t.startTime&&t.endTime){let a=new Date(t.endTime).getTime()-new Date(t.startTime).getTime();a>=0&&(t.duration=`${parseFloat((a/1e3).toPrecision(3))}s (${a}ms)`)}return t},lt=e=>{if(!e.start)return"";let t=e.start.data?.arguments||{},a=e.start.data?.toolName||e.tool||"",s="";if(a==="bash"||a==="exec")s=t.command||t.description||"";else if(a==="ask_user")s=t.question||t.message||"";else if(a==="read"||a==="write"||a==="edit")s=t.file_path||t.path||"";else if(a==="view")s=t.path||t.file||"";else if(a==="create")s=t.path||t.name||"";else if(a==="report_intent")s=t.intent||t.message||"";else if(a==="web_search")s=t.query||"";else if(a==="web_fetch")s=t.url||"";else if(a==="browser"){let o=t.action||"",i=t.targetUrl||t.url||"";s=i?`${o} ${i}`:o}else s=t.description||t.command||t.message||t.path||t.file_path||t.query||"";return s&&s.length>200&&(s=s.substring(0,200)+"..."),s},dt=e=>e.data?.tools&&e.data.tools.length>0,ct=e=>e.data?.tools&&Array.isArray(e.data.tools)?e.data.tools.filter(t=>t&&typeof t=="object"&&t.name).map(t=>{let a=t.result!==void 0||t.status==="completed"||t.status==="error",s={};if(t.startTime&&(s.startTime=t.startTime),t.endTime&&(s.endTime=t.endTime),s.startTime&&s.endTime){let o=new Date(s.endTime).getTime()-new Date(s.startTime).getTime();o>=0&&(s.duration=`${parseFloat((o/1e3).toPrecision(3))}s (${o}ms)`)}return{tool:t.name,timing:s,start:{timestamp:t.startTime,data:{toolName:t.name,arguments:t.input||t.arguments||{}}},complete:a?{timestamp:t.endTime,data:{result:t.result,error:t.status==="error"?t.error:null}}:null}}):[],me=["#58a6ff","#f0883e","#a371f7","#3fb950","#f778ba","#79c0ff","#d29922","#56d4dd"],ut=e=>{let t=0;for(let a=0;a<e.length;a++){let s=e.charCodeAt(a);t=(t<<5)-t+s,t=t&t}return t},Se=e=>{let{ownerMap:t,subagentInfo:a}=G.value;if(e.type==="subagent.started"||e.type==="subagent.completed"||e.type==="subagent.failed"){let i=e.data?.toolCallId;if(i&&a.has(i)){let r=a.get(i);return{name:r.name,toolCallId:i,colorIndex:r.colorIndex}}return null}if(e._subagent){let i=e._subagent.id,r=e._subagent.name;if(a.has(i)){let d=a.get(i);return{name:d.name,toolCallId:i,colorIndex:d.colorIndex}}return{name:r,toolCallId:i,colorIndex:Math.abs(ut(i))}}if(e.data?.subAgentId){let i=e.data.subAgentId,r=a.get(i);if(r)return{name:r.name,toolCallId:i,colorIndex:r.colorIndex}}let s=t.get(e.stableId);if(!s)return null;let o=a.get(s);return o?{name:o.name,toolCallId:s,colorIndex:o.colorIndex}:null},mt=e=>{let t=Se(e);return t?me[t.colorIndex%me.length]:null},gt=e=>{if(window.trackClick){let t=we.value.find(a=>a.type===e);window.trackClick("EventFilterClicked",{filterType:e,filterLabel:t?t.label:e,sessionId:h.value})}R.value=e},pt=e=>{A.value=e,Z.value=!1,de.value="",e&&(R.value="all"),window.trackClick&&window.trackClick("SubagentSelected",{subagent:e,sessionId:h.value})},Ie=e=>{P.value="",R.value="all",A.value=null,he.value=e.id,Vue.nextTick(()=>{if(k.value){let t=H.value.findIndex(a=>a.virtualIndex===e.index);if(t>=0){let a=s=>{s<=0||!k.value||(k.value.scrollToItem(t),setTimeout(()=>a(s-1),100))};setTimeout(()=>a(3),50)}}})},vt=()=>{if(!k.value)return;let e=t=>{t<=0||!k.value||(k.value.scrollToItem(0),setTimeout(()=>e(t-1),100))};e(3)},ft=()=>{if(!k.value)return;let e=H.value.length-1,t=a=>{a<=0||!k.value||(k.value.scrollToItem(e),setTimeout(()=>t(a-1),100))};t(5)},Ee=e=>{window.trackClick&&window.trackClick("TurnClicked",{turnNumber:e,sessionId:h.value});let t=W.value.find(a=>a.id===e);if(t){let a=`UserReq${t.userReqNumber}_Turn${t.id}`,s=`${window.location.pathname}?eventType=assistant.turn_start&eventName=${a}`;window.history.pushState({},"",s),Ie(t)}},bt=e=>{if(!e)return"";let t=e.replace(/\/$/,"").split("/");return t[t.length-1]||e},ht=e=>{let t=W.value.find(s=>s.index===e);if(!t)return"?";let a=t.originalTurnId??t.id;return t.userReqNumber>0?`${t.userReqNumber} - Turn ${a}`:`Turn ${a}`},Tt=e=>W.value.find(a=>a.index===e)?.duration||null,Me=e=>{let t=document.createElement("div");return t.textContent=e,t.innerHTML},yt=e=>e?new Date(e).toLocaleString():"N/A",kt=async()=>{console.log("[Export] exportSession called"),window.trackClick&&window.trackClick("ExportClicked",{sessionId:h.value}),le.value=!0;try{console.log("[Export] Fetching:",`/session/${h.value}/export`);let e=await fetch(`/session/${h.value}/export`);if(console.log("[Export] Response received:",e.status,e.ok),console.log("[Export] Response received:",e.status,e.ok),!e.ok)throw new Error("Share failed");console.log("[Export] Creating blob...");let t=await e.blob();console.log("[Export] Blob size:",t.size,"type:",t.type);let a=window.URL.createObjectURL(t);console.log("[Export] Creating download link...");let s=document.createElement("a");s.href=a,s.download=`session-${h.value}.zip`,document.body.appendChild(s),s.click(),console.log("[Export] Download triggered"),window.URL.revokeObjectURL(a),document.body.removeChild(s),console.log("[Export] Showing success feedback...");let o="\u{1F4E4} Share Session",i="\u2713 Downloaded!",r=document.querySelector(".export-btn");r&&(r.textContent=i,r.style.background="#238636",console.log("[Export] Button text updated to:",r.textContent),setTimeout(()=>{r.textContent=o,r.style.background="",console.log("[Export] Button text restored")},2e3))}catch(e){console.error("[Export] Share session error:",e),alert("Failed to share session: "+e.message)}finally{le.value=!1,console.log("[Export] Export complete")}},Ne=e=>{let t=document.querySelector(".filter-type-wrapper");t&&!t.contains(e.target)&&(ce.value=!1)},Re=e=>{e.ctrlKey&&e.key==="b"&&(e.preventDefault(),Y.value=!Y.value)};l(()=>{document.removeEventListener("click",Ne),window.removeEventListener("keydown",Re),j&&(clearTimeout(j),j=null),ee&&(ee(),ee=null),D.value={},L.value={},E.clear()}),n(async()=>{document.addEventListener("click",Ne),document.addEventListener("click",()=>{Z.value=!1});try{console.log("[Navigation] Starting event loading...");let t=await fetch(`/api/sessions/${h.value}/events`);if(!t.ok)throw new Error(`Failed to load events: ${t.statusText}`);let a=await t.json();if(Array.isArray(a))O.value=a;else if(a.events&&Array.isArray(a.events))O.value=a.events,console.log("[Navigation] Pagination:",a.pagination);else throw new Error("Invalid response format");if(console.log("[Navigation] Events loaded:",O.value.length),O.value.length>0){let d=O.value[O.value.length-1],c=d.timestamp||d.time||d.data?.timestamp;c&&(w.value.updated=new Date(c))}let s=new URLSearchParams(window.location.search),o=s.get("eventType"),i=s.get("eventName"),r=s.get("eventTimestamp");console.log("[Navigation] URL params:",o,i,r),o&&i&&(console.log("[Navigation] Waiting for Vue to render..."),Vue.nextTick(()=>{console.log("[Navigation] nextTick - flatEvents count:",S.value?.length);let d=null;if(o==="assistant.turn_start"){let c=i.match(/UserReq(\d+)_Turn(\d+)/);if(c){let T=parseInt(c[2],10);if(!isNaN(T)){console.log("[Navigation] Jumping to turn:",T),Ee(T);return}}}else o==="subagent.started"?(console.log("[Navigation] Searching for subagent:",i,"timestamp:",r),r&&(d=S.value.find(c=>c.type==="subagent.started"&&c.timestamp===r)),d||(d=S.value.find(c=>c.type==="subagent.started"&&(c.data?.agentDisplayName===i||c.data?.agentName===i||c.data?.label===i))),console.log("[Navigation] Target event found:",d?"YES":"NO","virtualIndex:",d?.virtualIndex)):d=S.value.find(c=>c.type===o);if(d){let c=H.value.findIndex(T=>T.virtualIndex===d.virtualIndex);if(console.log("[Navigation] Target in filteredEvents at index:",c),c>=0&&k.value){console.log("[Navigation] Scrolling to index:",c);let T=y=>{y<=0||!k.value||(k.value.scrollToItem(c),setTimeout(()=>T(y-1),100))};setTimeout(()=>T(3),50)}else console.log("[Navigation] Failed - targetIndex:",c,"scrollerRef:",!!k.value)}else console.log("[Navigation] Target event not found")}))}catch(t){console.error("Error loading events:",t),xe.value=t.message}finally{ke.value=!1}window.addEventListener("keydown",Re),window.marked&&marked.setOptions({breaks:!0,gfm:!0});let e=()=>{if(!k.value)return;let t=null;if(k.value.$el&&typeof k.value.$el.querySelector=="function"?t=k.value.$el.querySelector(".vue-recycle-scroller"):k.value.querySelector&&typeof k.value.querySelector=="function"&&(t=k.value.querySelector(".vue-recycle-scroller")),t||(t=document.querySelector(".vue-recycle-scroller")),t){let a=t.scrollTop,s=t.clientHeight,o=80,i=Math.floor(a/o),r=Math.ceil(s/o),d=Math.min(i+r,H.value.length),c=Math.max(1,i+1),T=Math.max(1,d);Te.value={start:Math.min(c,T),end:T}}};setTimeout(()=>{e();let t=document.querySelector(".vue-recycle-scroller");t&&(t.addEventListener("scroll",e),ee=()=>{t.removeEventListener("scroll",e)})},500)});let K=m([]),ge=m([]),J=m(!1),M=m([]),_=m(""),pe=m(null),N=m(""),F=m(!1),te=m([]),Ae=m(0),xt=e=>!e||e===0?"0":e<1e3?e.toString():Math.floor(e/1e3)+"K",wt=e=>{if(!e||e===0)return"0s";let t=Math.floor(e/1e3);if(t<60)return(e/1e3).toFixed(1)+"s";let a=Math.floor(t/60),s=t%60;return`${a}m ${s}s`},Ct=b(()=>{if(!w.value.usage||!w.value.usage.modelMetrics)return 0;let e=0;for(let t in w.value.usage.modelMetrics){let a=w.value.usage.modelMetrics[t].usage;a&&(e+=(a.inputTokens||0)+(a.outputTokens||0))}return e}),St=b(()=>{if(!w.value.usage||!w.value.usage.modelMetrics)return 0;let e=0;for(let t in w.value.usage.modelMetrics)e+=w.value.usage.modelMetrics[t].requests?.count||0;return e}),It=b(()=>!w.value.usage||!w.value.usage.modelMetrics?0:Object.keys(w.value.usage.modelMetrics).length),Et=e=>{let t=w.value.usage?.modelMetrics[e];return!t||!t.usage?null:x(t.usage)},Mt=e=>{let t=w.value.usage?.modelMetrics[e];return!t||!t.usage?0:f(t.usage)},Nt=b(()=>{let e=new Map;for(let t of S.value)if(t.data?.tools&&Array.isArray(t.data.tools))for(let a of t.data.tools)a&&a.name&&e.set(a.name,(e.get(a.name)||0)+1);return Array.from(e,([t,a])=>({name:t,count:a})).sort((t,a)=>a.count-t.count)}),Rt=e=>e==null?"":e+" premium",De=["#3b82f6","#10b981","#f59e0b","#ef4444","#8b5cf6","#ec4899","#06b6d4","#f97316"],At=e=>{let t=0;for(let a=0;a<e.length;a++)t=e.charCodeAt(a)+((t<<5)-t);return De[Math.abs(t)%De.length]},Dt=async()=>{try{let e=await fetch(`/api/sessions/${h.value}/tags`);if(e.ok){let t=await e.json();K.value=t.tags||[]}}catch(e){console.error("Error loading tags:",e)}},Le=async()=>{try{let e=await fetch("/api/tags");if(e.ok){let t=await e.json();ge.value=t.tags||[]}}catch(e){console.error("Error loading all tags:",e)}},Lt=async e=>{try{window.trackClick&&e.filter(s=>!K.value.includes(s)).forEach(s=>{window.trackClick("TagAdded",{sessionId:h.value,tag:s})});let t=await fetch(`/api/sessions/${h.value}/tags`,{method:"PUT",headers:{"Content-Type":"application/json"},body:JSON.stringify({tags:e})});if(t.ok){let a=await t.json();return K.value=a.tags||[],N.value="",!0}else{let a=await t.json();return N.value=a.error||"Failed to save tags",!1}}catch(t){return console.error("Error saving tags:",t),N.value="Network error",!1}},Ot=()=>{M.value=[...K.value],J.value=!0,N.value="",setTimeout(()=>{pe.value&&pe.value.focus()},10)},_t=()=>{J.value=!1,M.value=[],_.value="",F.value=!1,N.value=""},Oe=()=>{let e=_.value.trim().toLowerCase();if(e){if(e.length>30){N.value="Tag must be 30 characters or less";return}if(M.value.length>=10){N.value="Maximum 10 tags per session";return}if(M.value.includes(e)){N.value="Tag already added",_.value="";return}M.value.push(e),_.value="",F.value=!1,N.value=""}},$t=e=>{M.value=M.value.filter(t=>t!==e),N.value=""},qt=()=>{let e=_.value.trim().toLowerCase();if(!e){F.value=!1,te.value=[];return}let t=ge.value.filter(a=>a.toLowerCase().includes(e)&&!M.value.includes(a)).slice(0,5);t.length>0?(F.value=!0,te.value=t,Ae.value=0):(F.value=!1,te.value=[])},Ut=e=>{_.value=e,Oe()},Ft=async()=>{setTimeout(async()=>{if(!J.value)return;await Lt(M.value)&&(J.value=!1,M.value=[],_.value="",F.value=!1,await Le())},200)};return n(async()=>{await Dt(),await Le()}),{sessionId:h,metadata:w,exporting:le,sidebarCollapsed:Y,expandedTools:D,expandedContent:L,expansionCount:He,currentFilter:R,searchText:P,currentTurnIndex:he,scrollerRef:k,visibleRange:Te,loadedEvents:O,eventsLoading:ke,eventsError:xe,flatEvents:S,filteredEvents:H,eventCounts:Pe,filters:we,turns:W,userReqs:We,truncateText:Ge,formatTime:Xe,formatToolTime:Ye,formatDateTime:yt,renderMarkdown:Qe,highlightSearchText:et,toggleTool:Ze,toggleContent:tt,isContentTooLong:at,truncateContent:st,getBadgeInfo:nt,getToolStatus:ot,getToolErrorMessage:it,getToolDuration:rt,getToolCommand:lt,hasTools:dt,getToolGroups:ct,getSubagentInfo:Se,getSubagentColor:mt,subagentOwnership:G,setFilter:gt,selectSubagent:pt,selectedSubagent:A,subagentList:ue,filteredSubagentList:Ke,subagentDropdownOpen:Z,subagentSearchQuery:de,subagentSearchRef:ye,subagentTokenUsage:Je,SUBAGENT_COLORS:me,typeFilterOpen:ce,activeFilterCount:Be,clearAllFilters:ze,scrollToTurn:Ie,scrollToTop:vt,scrollToBottom:ft,jumpToTurn:Ee,getTurnNumber:ht,getTurnDuration:Tt,repoBasename:bt,escapeHtml:Me,exportSession:kt,searchResultCount:je,sessionTags:K,allTags:ge,tagsEditing:J,editingTags:M,tagInputValue:_,tagInputRef:pe,tagsError:N,showAutocomplete:F,autocompleteOptions:te,autocompleteSelectedIndex:Ae,getTagColor:At,startEditTags:Ot,cancelEditTags:_t,addTag:Oe,removeTagFromEdit:$t,updateAutocomplete:qt,selectAutocompleteOption:Ut,saveTagsOnBlur:Ft,formatTokens:xt,formatDuration:wt,formatCost:Rt,totalTokens:Ct,totalRequests:St,totalModels:It,getDisplayUsageInputTokens:Mt,getModelCacheHitRatio:Et,toolCallingSummary:Nt}},template:`
11
11
  <div class="container">
12
12
  <div class="header">
13
13
  <a href="/" class="home-btn">\u2190 Back to Home</a>
@@ -16,7 +16,7 @@
16
16
  </h1>
17
17
  <div style="display: flex; gap: 10px;">
18
18
  <a :href="'/session/' + sessionId + '/time-analyze'" class="time-analyze-btn" @click="trackClick && trackClick('TimeAnalyzeClicked', { sessionId: sessionId })">\u23F1 Analysis</a>
19
- <button @click="exportSession" class="export-btn" :disabled="exporting">
19
+ <button @click="exportSession" class="export-btn" :disabled="exporting" v-if="!metadata.source || !['vscode', 'modernize'].includes(metadata.source)">
20
20
  {{ exporting ? '\u23F3 Sharing...' : '\u{1F4E4} Share Session' }}
21
21
  </button>
22
22
  </div>
@@ -60,6 +60,10 @@
60
60
  <td>Model</td>
61
61
  <td>{{ metadata.model }}</td>
62
62
  </tr>
63
+ <tr v-if="metadata.agentName">
64
+ <td>Agent</td>
65
+ <td>\u{1F916} {{ metadata.agentName }}</td>
66
+ </tr>
63
67
  <tr v-if="metadata.repo">
64
68
  <td>Repo</td>
65
69
  <td>{{ metadata.repo }}</td>
@@ -313,18 +317,53 @@
313
317
 
314
318
  <div class="filter-bar-divider"></div>
315
319
 
316
- <!-- Subagent selector -->
317
- <div v-if="subagentList.length > 0" class="subagent-selector">
318
- <select
319
- :value="selectedSubagent || ''"
320
- @change="selectSubagent($event.target.value || null)"
321
- class="subagent-dropdown"
320
+ <!-- Subagent selector (rich dropdown with search) -->
321
+ <div v-if="subagentList.length > 0" class="subagent-selector" style="position:relative">
322
+ <button
323
+ class="subagent-dropdown-trigger"
324
+ @click.stop="subagentDropdownOpen = !subagentDropdownOpen"
322
325
  >
323
- <option value="">\u{1F916} All Agents</option>
324
- <option v-for="sa in subagentList" :key="sa.toolCallId" :value="sa.toolCallId">
325
- \u{1F916} {{ sa.name }}
326
- </option>
327
- </select>
326
+ <span class="subagent-trigger-icon">\u{1F916}</span>
327
+ <span class="subagent-trigger-label">{{ selectedSubagent ? (subagentList.find(s => s.toolCallId === selectedSubagent)?.name || 'Agent') : 'All Agents' }}</span>
328
+ <span class="subagent-trigger-arrow">\u25BE</span>
329
+ </button>
330
+ <div v-if="subagentDropdownOpen" class="subagent-dropdown-panel" @click.stop>
331
+ <input
332
+ class="subagent-search-input"
333
+ v-model="subagentSearchQuery"
334
+ placeholder="Search agents..."
335
+ ref="subagentSearchRef"
336
+ @keydown.escape="subagentDropdownOpen = false"
337
+ />
338
+ <div class="subagent-dropdown-list">
339
+ <div
340
+ class="subagent-dropdown-item"
341
+ :class="{ active: !selectedSubagent }"
342
+ @click="selectSubagent(null)"
343
+ >
344
+ <div class="subagent-item-name">\u{1F916} All Agents</div>
345
+ </div>
346
+ <div
347
+ v-for="sa in filteredSubagentList"
348
+ :key="sa.toolCallId"
349
+ class="subagent-dropdown-item"
350
+ :class="{ active: selectedSubagent === sa.toolCallId }"
351
+ @click="selectSubagent(sa.toolCallId)"
352
+ >
353
+ <div class="subagent-item-color" :style="{ background: SUBAGENT_COLORS[sa.colorIndex % SUBAGENT_COLORS.length] }"></div>
354
+ <div class="subagent-item-body">
355
+ <div class="subagent-item-name">{{ sa.name }}</div>
356
+ <div v-if="sa.meta.taskName || sa.meta.agentType || sa.meta.model" class="subagent-item-meta">
357
+ <span v-if="sa.meta.taskName" class="subagent-meta-tag">{{ sa.meta.taskName }}</span>
358
+ <span v-if="sa.meta.agentType" class="subagent-meta-tag dim">{{ sa.meta.agentType }}</span>
359
+ <span v-if="sa.meta.model" class="subagent-meta-tag dim">{{ sa.meta.model }}</span>
360
+ </div>
361
+ <div v-if="sa.meta.agentDescription" class="subagent-item-desc">{{ sa.meta.agentDescription }}</div>
362
+ </div>
363
+ </div>
364
+ <div v-if="filteredSubagentList.length === 0" class="subagent-dropdown-empty">No matches</div>
365
+ </div>
366
+ </div>
328
367
  <span v-if="subagentTokenUsage" class="subagent-usage-badge">
329
368
  {{ subagentTokenUsage.eventCount }} events \xB7 {{ formatDuration(subagentTokenUsage.durationMs) }}
330
369
  </span>
@@ -440,6 +479,7 @@
440
479
  <div class="subagent-divider-line-left" :style="{ background: getSubagentColor(item) || '#58a6ff' }"></div>
441
480
  <span class="subagent-divider-text" :style="{ color: getSubagentColor(item) || '#58a6ff', borderColor: getSubagentColor(item) || '#58a6ff', background: (getSubagentColor(item) || '#58a6ff') + '1a' }">
442
481
  \u{1F916} {{ item.data?.agentDisplayName || item.data?.agentName || 'SubAgent' }}
482
+ <span v-if="subagentOwnership.subagentInfo.get(item.data?.toolCallId)?.meta?.model" class="subagent-divider-model">\xB7 {{ subagentOwnership.subagentInfo.get(item.data?.toolCallId).meta.model }}</span>
443
483
  {{ item.type === 'subagent.started' ? 'Start \u25B6' : item.type === 'subagent.completed' ? 'Complete \u2713' : 'Failed \u2717' }}
444
484
  </span>
445
485
  <div class="subagent-divider-line-right" :style="{ background: getSubagentColor(item) || '#58a6ff' }"></div>
@@ -465,7 +505,7 @@
465
505
  :title="'Filter to ' + getSubagentInfo(item).name"
466
506
  @click.stop="selectSubagent(getSubagentInfo(item).toolCallId)"
467
507
  >\u{1F916} {{ getSubagentInfo(item).name }}</span>
468
- <span v-if="metadata.source !== 'vscode'" class="event-timestamp">{{ formatTime(item.timestamp) }}</span>
508
+ <span class="event-timestamp">{{ formatTime(item.timestamp) }}</span>
469
509
  </div>
470
510
 
471
511
  <!-- Abort event: show reason -->
@@ -553,6 +593,39 @@
553
593
  </div>
554
594
  </div>
555
595
 
596
+ <!-- Hook event: compact summary with collapsible args/result -->
597
+ <div v-else-if="item.data?.hookType" class="hook-content">
598
+ <div class="hook-summary">
599
+ <span style="color: #8b949e;">{{ item.data.hookType }}</span>
600
+ <span v-if="item.data.hookToolName" style="color: #8b949e;"> \u2192 </span>
601
+ <span v-if="item.data.hookToolName" style="color: #c9d1d9;">{{ item.data.hookToolName }}</span>
602
+ <span v-if="item.data.hookDurationMs != null" style="color: #7d8590; margin-left: 8px;">{{ item.data.hookDurationMs }}ms</span>
603
+ <span v-if="item.data.hookSuccess === true" style="color: #3fb950; margin-left: 4px;">\u2713</span>
604
+ <span v-if="item.data.hookSuccess === false" style="color: #ff7b72; margin-left: 4px;">\u2717</span>
605
+ </div>
606
+ <div v-if="item.data.hookArgs && Object.keys(item.data.hookArgs).length > 0" class="hook-section">
607
+ <div class="hook-section-header" @click="toggleContent('hook-args-' + item.stableId)">
608
+ <span class="tool-expand-icon">{{ expandedContent['hook-args-' + item.stableId] ? '\u25BC' : '\u25B6' }}</span>
609
+ <span style="color: #8b949e;">Arguments</span>
610
+ </div>
611
+ <div v-if="expandedContent['hook-args-' + item.stableId]" class="hook-section-body">
612
+ <pre>{{ JSON.stringify(item.data.hookArgs, null, 2) }}</pre>
613
+ </div>
614
+ </div>
615
+ <div v-if="item.data.hookResult" class="hook-section">
616
+ <div class="hook-section-header" @click="toggleContent('hook-result-' + item.stableId)">
617
+ <span class="tool-expand-icon">{{ expandedContent['hook-result-' + item.stableId] ? '\u25BC' : '\u25B6' }}</span>
618
+ <span style="color: #8b949e;">Result</span>
619
+ </div>
620
+ <div v-if="expandedContent['hook-result-' + item.stableId]" class="hook-section-body">
621
+ <pre>{{ item.data.hookResult }}</pre>
622
+ </div>
623
+ </div>
624
+ <div v-if="item.data.hookError" style="color: #ff7b72; margin-top: 4px;">
625
+ Error: {{ item.data.hookError }}
626
+ </div>
627
+ </div>
628
+
556
629
  <!-- Regular content (unified format from server) -->
557
630
  <div v-else-if="item.data?.message || item.data?.text || item.data?.content || item.data?.transformedContent">
558
631
  <div
@@ -675,4 +748,4 @@
675
748
  </div>
676
749
 
677
750
  </div>
678
- `});console.log("Mounting Vue app to #app..."),console.log("App config:",P.config),console.log("Target element:",document.getElementById("app"));try{let p=P.mount("#app");console.log("Vue app mounted successfully!",p?"Instance created":"No instance"),console.log("VM type:",typeof p,"Has exportSession:",typeof p?.exportSession),console.log("VM keys:",p?Object.keys(p).slice(0,10):"NO_VM"),console.log("#app innerHTML length:",document.getElementById("app").innerHTML.length),console.log("#app first 100 chars:",document.getElementById("app").innerHTML.substring(0,100))}catch(p){console.error("Mount failed:",p),console.error("Error stack:",p.stack)}})();})();
751
+ `});console.log("Mounting Vue app to #app..."),console.log("App config:",ve.config),console.log("Target element:",document.getElementById("app"));try{let h=ve.mount("#app");console.log("Vue app mounted successfully!",h?"Instance created":"No instance"),console.log("VM type:",typeof h,"Has exportSession:",typeof h?.exportSession),console.log("VM keys:",h?Object.keys(h).slice(0,10):"NO_VM"),console.log("#app innerHTML length:",document.getElementById("app").innerHTML.length),console.log("#app first 100 chars:",document.getElementById("app").innerHTML.substring(0,100))}catch(h){console.error("Mount failed:",h),console.error("Error stack:",h.stack)}})();})();