openfox 1.6.6 → 1.6.7

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.
@@ -154,7 +154,7 @@ async function runCli(options) {
154
154
  if (!configExists) {
155
155
  await runNetworkSetup(mode);
156
156
  }
157
- const { runServe } = await import("./serve-PLWVGFNJ.js");
157
+ const { runServe } = await import("./serve-3FZYXWSF.js");
158
158
  await runServe({
159
159
  mode,
160
160
  port: values.port ? parseInt(values.port) : void 0,
@@ -167,4 +167,4 @@ async function runCli(options) {
167
167
  export {
168
168
  runCli
169
169
  };
170
- //# sourceMappingURL=chunk-DBDUBKRJ.js.map
170
+ //# sourceMappingURL=chunk-OXDIZH3I.js.map
@@ -5544,7 +5544,7 @@ function createTerminalRoutes() {
5544
5544
  }
5545
5545
 
5546
5546
  // src/constants.ts
5547
- var VERSION = "1.6.6";
5547
+ var VERSION = "1.6.7";
5548
5548
 
5549
5549
  // src/server/index.ts
5550
5550
  var __dirname2 = dirname5(fileURLToPath4(import.meta.url));
@@ -6433,4 +6433,4 @@ export {
6433
6433
  createServerHandle,
6434
6434
  createServer
6435
6435
  };
6436
- //# sourceMappingURL=chunk-3XEAHQIB.js.map
6436
+ //# sourceMappingURL=chunk-ZEGMET66.js.map
package/dist/cli/dev.js CHANGED
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  runCli
4
- } from "../chunk-DBDUBKRJ.js";
4
+ } from "../chunk-OXDIZH3I.js";
5
5
  import {
6
6
  logger
7
7
  } from "../chunk-PNBH3RAX.js";
package/dist/cli/index.js CHANGED
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  runCli
4
- } from "../chunk-DBDUBKRJ.js";
4
+ } from "../chunk-OXDIZH3I.js";
5
5
  import {
6
6
  logger
7
7
  } from "../chunk-PNBH3RAX.js";
package/dist/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "openfox",
3
- "version": "1.6.6",
3
+ "version": "1.6.7",
4
4
  "description": "Local-LLM-first agentic coding assistant",
5
5
  "type": "module",
6
6
  "bin": {
@@ -6,7 +6,7 @@ import {
6
6
  import {
7
7
  VERSION,
8
8
  createServer
9
- } from "./chunk-3XEAHQIB.js";
9
+ } from "./chunk-ZEGMET66.js";
10
10
  import "./chunk-QDEKU5RL.js";
11
11
  import "./chunk-7H3O5YYX.js";
12
12
  import "./chunk-JAFNVZWY.js";
@@ -188,4 +188,4 @@ async function runServe(options) {
188
188
  export {
189
189
  runServe
190
190
  };
191
- //# sourceMappingURL=serve-PLWVGFNJ.js.map
191
+ //# sourceMappingURL=serve-3FZYXWSF.js.map
@@ -1,7 +1,7 @@
1
1
  import {
2
2
  createServer,
3
3
  createServerHandle
4
- } from "../chunk-3XEAHQIB.js";
4
+ } from "../chunk-ZEGMET66.js";
5
5
  import "../chunk-QDEKU5RL.js";
6
6
  import "../chunk-7H3O5YYX.js";
7
7
  import "../chunk-JAFNVZWY.js";
@@ -81,7 +81,7 @@ WARNING: This link could potentially be dangerous`)){const y=window.open();if(y)
81
81
  w-[300px] bg-bg-secondary border-r border-border flex flex-col
82
82
  transition-all duration-300 ease-in-out
83
83
  ${r?"translate-x-0":"-translate-x-full"}
84
- `,children:[o.jsxs("div",{className:"p-4 border-b border-border flex gap-2",children:[o.jsx(An,{href:`/p/${e}/new`,className:"flex-1 block text-center rounded font-medium transition-colors bg-accent-primary/25 text-white hover:bg-accent-primary/40 px-3 py-1.5 text-sm","data-testid":"sidebar-new-session-button",children:"+ New Session"}),o.jsx(Ka,{items:[{label:"Edit project settings",onClick:()=>u(!0)},{label:"Delete all sessions",onClick:_,danger:!0}],trigger:o.jsx("button",{className:"flex-shrink-0 p-2.5 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary transition-colors",title:"Options",children:o.jsxs("svg",{className:"w-4 h-4",fill:"currentColor",viewBox:"0 0 24 24",children:[o.jsx("circle",{cx:"12",cy:"5",r:"2"}),o.jsx("circle",{cx:"12",cy:"12",r:"2"}),o.jsx("circle",{cx:"12",cy:"19",r:"2"})]})})}),i&&o.jsx("button",{onClick:i,className:"md:hidden flex-shrink-0 p-2.5 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary transition-colors",title:"Close sidebar",children:o.jsx("svg",{className:"w-4 h-4",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M6 18L18 6M6 6l12 12"})})})]}),k&&o.jsx(BS,{isOpen:c,onClose:()=>u(!1),project:k}),o.jsx("div",{className:"flex-1 overflow-y-auto",children:y.length===0?o.jsx("div",{className:"p-4 text-center text-text-muted text-xs",children:"No sessions"}):o.jsxs(o.Fragment,{children:[o.jsx("div",{className:"divide-y divide-border",children:zS(y,l,f,v,e)}),S&&o.jsx("div",{className:"p-4 text-center text-text-muted text-xs",children:"Loading more..."}),o.jsx("div",{ref:C,className:"h-px"})]})})]})]})}function zS(e,r,i,s,c){const u=db(e);return Array.from(u).map(([p,l])=>{const f=l[0];return f?o.jsxs("div",{children:[o.jsx("div",{className:"px-4 py-2 bg-bg-tertiary/30 text-text-muted text-xs font-medium",children:ub(f.updatedAt)}),l.map(d=>{const g=(r==null?void 0:r.id)===d.id,m=i.includes(d.id),x=d.isRunning;return o.jsx("div",{className:`w-full px-4 py-3 text-left hover:bg-bg-tertiary/50 transition-colors group ${g?"bg-bg-tertiary":""}`,children:o.jsxs(An,{href:`/p/${c}/s/${d.id}`,className:`block ${g?"text-accent-primary":"text-text-primary"} hover:text-accent-primary`,children:[o.jsxs("div",{className:"flex justify-between items-center mb-1",children:[o.jsx("span",{className:`font-medium truncate text-sm ${g?"text-accent-primary":"text-text-primary"}`,children:d.title??d.id.slice(0,6)}),o.jsx(Ka,{items:[{label:"Delete session",onClick:S=>s(d.id,S),danger:!0}],trigger:o.jsx("button",{onClick:S=>S.preventDefault(),className:"p-1.5 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary transition-all",title:"Options",children:o.jsxs("svg",{className:"w-4 h-4",fill:"currentColor",viewBox:"0 0 24 24",children:[o.jsx("circle",{cx:"12",cy:"5",r:"2"}),o.jsx("circle",{cx:"12",cy:"12",r:"2"}),o.jsx("circle",{cx:"12",cy:"19",r:"2"})]})})})]}),o.jsxs("div",{className:"flex items-center gap-2 mt-1",children:[x?o.jsxs("svg",{"aria-label":"Session running",className:"w-3 h-3 text-blue-400 animate-spin flex-shrink-0",viewBox:"0 0 24 24",fill:"none",children:[o.jsx("title",{children:"Running"}),o.jsx("circle",{className:"opacity-30",cx:"12",cy:"12",r:"9",stroke:"currentColor",strokeWidth:"3"}),o.jsx("path",{d:"M21 12a9 9 0 00-9-9",stroke:"currentColor",strokeWidth:"3",strokeLinecap:"round"})]}):m&&!g?o.jsx("span",{"aria-label":"Unread activity",title:"Unread activity",className:"w-2 h-2 rounded-full bg-amber-400 flex-shrink-0"}):null,o.jsx("span",{className:"text-text-muted text-xs flex-shrink-0",children:gh(d.updatedAt)}),o.jsxs("span",{className:"text-text-muted text-xs flex-shrink-0",children:[d.messageCount," messages"]})]})]})},d.id)})]},p):null})}const Cx=["⠋","⠙","⠹","⠸","⠼","⠴"];function HS(){var l;const e=Ut(f=>f.currentProject),r=Ee(f=>f.currentSession),i=ob(),s=!1,c=P.useRef(0),u=P.useRef(null);P.useEffect(()=>(i?(u.current=window.setInterval(()=>{c.current=(c.current+1)%Cx.length,p()},150),p()):(u.current&&(clearInterval(u.current),u.current=null),p()),()=>{u.current&&(clearInterval(u.current),u.current=null)}),[i,e,r,s]);const p=()=>{var m;const d=(m=r==null?void 0:r.metadata)==null?void 0:m.title,g=i?`${Cx[c.current]} `:"";e&&d?document.title=`${g}${e.name} - ${d} | OpenFox`:e?document.title=`${g}${e.name} | OpenFox`:document.title=`${g}OpenFox`};return typeof window<"u"&&((l=r==null?void 0:r.metadata)!=null&&l.title)&&window.document.documentElement.setAttribute("data-session-title",r.metadata.title),null}const Pl=P.forwardRef(({className:e="",...r},i)=>o.jsx("input",{ref:i,className:`bg-bg-tertiary border border-border rounded px-3 py-2 text-text-primary placeholder-text-muted focus:outline-none focus:ring-2 focus:ring-accent-primary/50 focus:border-accent-primary ${e}`,...r}));Pl.displayName="Input";function PS({isOpen:e,onClose:r,projectName:i,onConfirm:s}){const c=()=>{s(),r()};return o.jsx(un,{isOpen:e,onClose:r,title:"Delete Project",size:"sm",children:o.jsxs("div",{className:"space-y-4",children:[o.jsxs("p",{className:"text-text-secondary",children:["This will permanently delete the project ",o.jsx("span",{className:"font-semibold text-text-primary",children:i})," and all its sessions from OpenFox. The project files on disk will remain untouched."]}),o.jsxs("div",{className:"flex justify-end gap-2",children:[o.jsx(dt,{variant:"secondary",onClick:r,children:"Cancel"}),o.jsx(dt,{variant:"danger",onClick:c,children:"Delete"})]})]})})}function FS(e){return!e||e.trim()===""?{valid:!1,error:"Project name cannot be empty"}:/^[a-zA-Z0-9._-]+$/.test(e)?{valid:!0}:{valid:!1,error:"Project name can only contain letters, numbers, hyphens, underscores, and dots"}}function US({isOpen:e,onClose:r}){const[,i]=ar(),[s,c]=P.useState(""),[u,p]=P.useState(null),[l,f]=P.useState(!1),[d,g]=P.useState(""),m=P.useRef(null);P.useEffect(()=>{e&&(ye("/api/config").then(C=>C.json()).then(C=>{C.workdir&&g(C.workdir)}),c(""),p(null),f(!1),setTimeout(()=>{var C;(C=m.current)==null||C.focus()},100))},[e]);const x=P.useCallback(async C=>{C.preventDefault();const b=FS(s);if(!b.valid){p(b.error);return}f(!0),p(null);const y=`${d}/${s}`;try{const v=await ye("/api/projects",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({name:s,workdir:y})});if(!v.ok){const A=await v.json().catch(()=>({}));throw new Error(A.error||"Failed to create project")}const j=(await v.json()).project;r(),i(`/p/${j.id}`)}catch(v){p(v instanceof Error?v.message:"Failed to create project"),f(!1)}},[s,i,r,d]),S=P.useCallback(()=>{c(""),p(null),r()},[r]),k=s?`${d}/${s}`:"";return o.jsx(un,{isOpen:e,onClose:S,title:"Create New Project",size:"sm",children:o.jsxs("form",{onSubmit:x,className:"space-y-4",children:[o.jsxs("div",{children:[o.jsx("label",{htmlFor:"project-name",className:"block text-sm font-medium text-text-secondary mb-2",children:"Project Name"}),o.jsx(Pl,{ref:m,id:"project-name",value:s,onChange:C=>{c(C.target.value),p(null)},placeholder:"my-project",disabled:l,className:"w-full"}),s&&o.jsxs("div",{className:"mt-2 text-xs text-text-muted",children:["Full path: ",o.jsx("span",{className:"font-mono",children:k})]}),u&&o.jsx("div",{className:"mt-3 p-3 bg-accent-error/10 border border-accent-error/30 rounded text-sm text-accent-error",children:u})]}),o.jsxs("div",{className:"flex justify-end gap-2",children:[o.jsx(dt,{type:"button",variant:"secondary",onClick:S,disabled:l,children:"Cancel"}),o.jsx(dt,{type:"submit",variant:"primary",disabled:l||!s.trim(),className:"min-w-[100px]",children:l?o.jsxs("span",{className:"flex items-center gap-2",children:[o.jsxs("svg",{className:"animate-spin h-4 w-4",fill:"none",viewBox:"0 0 24 24",children:[o.jsx("circle",{className:"opacity-25",cx:"12",cy:"12",r:"10",stroke:"currentColor",strokeWidth:"4"}),o.jsx("path",{className:"opacity-75",fill:"currentColor",d:"M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"})]}),"Creating..."]}):"Create"})]})]})})}const $S={sm:"w-4 h-4",md:"w-8 h-8",lg:"w-12 h-12"};function Fl({size:e="md",className:r=""}){return o.jsx("div",{className:`animate-spin border-2 border-accent-primary border-t-transparent rounded-full ${$S[e]} ${r}`})}function qS({text:e,...r}){return o.jsxs("div",{className:"text-center",children:[o.jsx(Fl,{...r,className:"mx-auto mb-4"}),e&&o.jsx("div",{className:"text-text-secondary",children:e})]})}function fb({onSelect:e,onClose:r,initialPath:i}){const[s,c]=P.useState(null),[u,p]=P.useState(!0),l=P.useCallback(async k=>{p(!0);try{const C=k?`/api/directories?path=${encodeURIComponent(k)}`:"/api/directories",y=await(await ye(C)).json();c(y)}catch(C){console.error("Failed to load directories:",C)}finally{p(!1)}},[]);P.useEffect(()=>{l(i)},[i,l]);const f=k=>{l(k)},d=k=>{e(k)},m=((s==null?void 0:s.current)??"").split("/").filter(Boolean),S=m.map((k,C)=>({name:k,path:"/"+m.slice(0,C+1).join("/")}));return o.jsx("div",{className:"fixed inset-0 z-50 flex items-center justify-center p-4 bg-black/50",onClick:r,children:o.jsxs("div",{className:"bg-bg-secondary border border-border rounded-lg w-full max-w-2xl max-h-[80vh] flex flex-col",onClick:k=>k.stopPropagation(),children:[o.jsxs("div",{className:"p-4 border-b border-border flex items-center justify-between",children:[o.jsx("h2",{className:"text-lg font-semibold text-text-primary",children:"Select Folder"}),o.jsx("button",{onClick:r,className:"p-1 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary",children:o.jsx("svg",{className:"w-5 h-5",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M6 18L18 6M6 6l12 12"})})})]}),s&&o.jsx("div",{className:"px-3 py-2 bg-bg-tertiary/30 border-b border-border",children:o.jsxs("div",{className:"flex items-center text-xs overflow-x-auto",children:[S.map((k,C)=>o.jsxs("span",{className:"flex items-center shrink-0",children:[o.jsx("span",{className:"text-text-muted",children:"/"}),o.jsx("button",{onClick:()=>f(k.path),className:`px-1 ${C===S.length-1?"text-accent-primary font-medium":"text-text-secondary hover:text-accent-primary"}`,children:k.name})]},k.path)),S.length===0&&o.jsx("button",{onClick:()=>f("/"),className:"text-text-muted hover:text-accent-primary",children:"/"})]})}),o.jsx("div",{className:"flex-1 overflow-y-auto",children:u?o.jsx("div",{className:"p-8 text-center",children:o.jsx(Fl,{size:"sm"})}):o.jsxs("div",{className:"divide-y divide-border",children:[(s==null?void 0:s.parent)&&o.jsxs("button",{onClick:()=>f(s.parent),className:"w-full p-3 flex items-center gap-3 hover:bg-bg-tertiary/50 text-text-muted",children:[o.jsx("svg",{className:"w-5 h-5",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M15 19l-7-7 7-7"})}),o.jsx("span",{children:".."})]}),s==null?void 0:s.directories.map(k=>o.jsxs("div",{className:"group flex items-center gap-2 hover:bg-bg-tertiary/50",children:[o.jsxs("button",{onClick:()=>f(k.path),className:"flex-1 p-3 flex items-center gap-3 text-left",children:[o.jsx("svg",{className:"w-5 h-5 text-accent-primary",fill:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{d:"M10 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V8c0-1.1-.9-2-2-2h-8l-2-2z"})}),o.jsx("span",{children:k.name})]}),o.jsx("button",{onClick:()=>d(k.path),className:"px-3 py-1 text-xs bg-accent-primary/10 text-accent-primary rounded opacity-0 group-hover:opacity-100 transition-opacity mr-3",children:"Select"})]},k.path)),(s==null?void 0:s.directories.length)===0&&o.jsx("div",{className:"p-8 text-center text-text-muted text-sm",children:"No subdirectories"})]})}),o.jsxs("div",{className:"p-4 border-t border-border space-y-2",children:[(s==null?void 0:s.current)&&o.jsx("button",{onClick:()=>d(s.current),className:"w-full px-4 py-2 bg-accent-primary text-white rounded-lg font-medium hover:bg-accent-primary/90 transition-colors",children:"Select this folder"}),o.jsx("button",{onClick:r,className:"w-full text-center text-text-muted hover:text-text-secondary text-sm",children:"Cancel"})]})]})})}function WS({isOpen:e,onClose:r}){const[,i]=ar(),[s,c]=P.useState(!1),[u,p]=P.useState(""),[l,f]=P.useState(null),[d,g]=P.useState(!1),[m,x]=P.useState(null),S=Ut(R=>R.projects),k=Ut(R=>R.createProject),C=Ut(R=>R.listProjects),b=Ut(R=>R.deleteProject),[y,v]=P.useState(null),[_,j]=P.useState(-1),[A,N]=P.useState(null),[L,T]=P.useState(!1),I=P.useRef([]);P.useEffect(()=>{ye("/api/config").then(R=>R.json()).then(R=>{R.workdir&&x(R.workdir)})},[]);const z=P.useCallback(async R=>{g(!0);try{const D=R?`/api/directories?path=${encodeURIComponent(R)}`:m?`/api/directories?path=${encodeURIComponent(m)}`:"/api/directories",W=await(await ye(D)).json();f(W)}catch(D){console.error("Failed to load directories:",D)}finally{g(!1)}},[m]);P.useEffect(()=>{e&&m&&(z(m),C())},[e,m,z,C]);const V=(l==null?void 0:l.directories.filter(R=>u===""||R.name.toLowerCase().includes(u.toLowerCase())))??[],Y=[...l!=null&&l.parent&&!u?[{type:"parent",path:l.parent,name:".."}]:[],...V.map(R=>({type:"directory",path:R.path,name:R.name}))],$=R=>{i(`/p/${R}`),r()},F=(R,D)=>{D.stopPropagation(),N(R)},B=()=>{A&&(b(A.id),N(null))},q=R=>{const D=R.split("/").filter(Boolean).pop()??"";k(D,R),C(),v(R)};P.useEffect(()=>{if(y){const R=S.find(D=>D.workdir===y);R&&(i(`/p/${R.id}`),r(),v(null))}},[S,y,i,r]),P.useEffect(()=>{j(Y.length>0?0:-1)},[u,Y.length]);const X=R=>{p(""),z(R)},J=P.useCallback(R=>{if(!e)return;if(R.key==="Escape"){r();return}if(!["ArrowDown","ArrowUp","Enter"].includes(R.key))return;const D=document.activeElement;if(!(!D||D.tagName!=="INPUT")){if(R.preventDefault(),R.key==="ArrowDown")j(O=>{const W=O+1;return W>=Y.length?0:W});else if(R.key==="ArrowUp")j(O=>{const W=O-1;return W<0?Y.length-1:W});else if(R.key==="Enter"&&_>=0&&_<Y.length){const O=Y[_];(O==null?void 0:O.type)==="parent"?X(O.path):O&&q(O.path)}}},[e,Y.length,_,X,q,r]);return P.useEffect(()=>{if(e)return document.addEventListener("keydown",J),()=>document.removeEventListener("keydown",J)},[e,J]),P.useEffect(()=>{_>=0&&I.current[_]&&I.current[_].scrollIntoView({behavior:"smooth",block:"nearest"})},[_]),e?o.jsxs("div",{className:"fixed inset-0 z-50 flex items-center justify-center p-4 bg-black/50",children:[o.jsxs("div",{className:"bg-bg-secondary border border-border rounded-lg w-full max-w-[90vw] md:max-w-4xl max-h-[90vh] flex flex-col",children:[o.jsxs("div",{className:"p-4 border-b border-border flex items-center justify-between",children:[o.jsx("h2",{className:"text-lg font-semibold text-text-primary",children:"Open Project"}),o.jsx("button",{onClick:r,className:"p-1 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary transition-colors",children:o.jsx("svg",{className:"w-5 h-5",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M6 18L18 6M6 6l12 12"})})})]}),o.jsxs("div",{className:"flex-1 flex overflow-hidden min-h-[400px]",children:[o.jsxs("div",{className:"w-1/2 border-r border-border flex flex-col",children:[o.jsx("div",{className:"p-3 border-b border-border bg-bg-tertiary/30",children:o.jsx("h3",{className:"font-medium text-sm text-text-secondary",children:"Recent Projects"})}),o.jsx("div",{className:"flex-1 overflow-y-auto",children:S.length===0?o.jsx("div",{className:"p-4 text-center text-text-muted text-sm",children:"No recent projects"}):o.jsx("div",{className:"divide-y divide-border",children:S.map(R=>o.jsxs("div",{className:"group flex items-center gap-3 p-3 hover:bg-bg-tertiary/50 transition-colors",children:[o.jsxs("button",{onClick:()=>$(R.id),className:"flex-1 flex items-center gap-3 text-left",children:[o.jsx("svg",{className:"w-5 h-5 text-accent-primary",fill:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{d:"M10 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V8c0-1.1-.9-2-2-2h-8l-2-2z"})}),o.jsxs("div",{className:"flex-1 min-w-0",children:[o.jsx("div",{className:"font-medium truncate",children:R.name}),o.jsx("div",{className:"text-xs text-text-muted truncate",children:R.workdir})]})]}),o.jsx("button",{onClick:D=>F(R,D),className:"opacity-0 group-hover:opacity-100 text-accent-error/70 hover:text-accent-error p-1 transition-opacity",title:"Delete project",children:o.jsx("svg",{className:"w-4 h-4",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M6 18L18 6M6 6l12 12"})})})]},R.id))})})]}),o.jsxs("div",{className:"w-1/2 flex flex-col",children:[o.jsxs("div",{className:"p-3 border-b border-border bg-bg-tertiary/30 flex items-center justify-between",children:[o.jsx("h3",{className:"font-medium text-sm text-text-secondary",children:"Browse Projects"}),o.jsx("button",{onClick:()=>T(!0),className:"text-xs text-accent-primary hover:underline",children:"Open in dialog"})]}),o.jsx("div",{className:"p-3 border-b border-border",children:o.jsx(Pl,{value:u,onChange:R=>p(R.target.value),placeholder:"Filter directories...",className:"w-full"})}),o.jsx("div",{className:"flex-1 overflow-y-auto",children:d?o.jsx("div",{className:"p-8 text-center text-text-muted",children:o.jsx("div",{className:"animate-spin w-5 h-5 border-2 border-accent-primary border-t-transparent rounded-full mx-auto"})}):Y.length===0?o.jsx("div",{className:"p-8 text-center text-text-muted text-sm",children:u?"No matching directories":"No subdirectories"}):o.jsx("div",{className:"divide-y divide-border",children:Y.map((R,D)=>o.jsxs("button",{ref:O=>{I.current[D]=O},onClick:()=>R.type==="parent"?X(R.path):q(R.path),className:`w-full p-3 flex items-center gap-3 text-left transition-colors ${D===_?"bg-accent-primary/20 text-accent-primary":"hover:bg-bg-tertiary/50"}`,children:[o.jsx("svg",{className:"w-5 h-5",fill:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{d:"M10 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V8c0-1.1-.9-2-2-2h-8l-2-2z"})}),o.jsx("span",{className:"flex-1",children:R.name})]},R.path))})})]})]}),o.jsxs("div",{className:"p-4 border-t border-border flex justify-between gap-2",children:[o.jsx(dt,{variant:"secondary",onClick:()=>c(!0),children:"Create Project"}),o.jsx(dt,{variant:"secondary",onClick:r,children:"Cancel"})]})]}),s&&o.jsx(US,{isOpen:s,onClose:()=>c(!1)}),A&&o.jsx(PS,{isOpen:!0,onClose:()=>N(null),projectName:A.name,onConfirm:B}),L&&o.jsx(fb,{initialPath:m??void 0,onSelect:R=>{q(R),T(!1)},onClose:()=>T(!1)})]}):null}function GS(){const[e,r]=P.useState(!1),i=Ee(g=>g.sessions),s=Ut(g=>g.projects),c=Ut(g=>g.listProjects),u=Ee(g=>g.listSessions),p=Ee(g=>g.connectionStatus);P.useEffect(()=>{p==="connected"&&(c(),u())},[p,c,u]);const l=[...s].sort((g,m)=>{const x=i.filter(b=>b.workdir.startsWith(g.workdir)),S=i.filter(b=>b.workdir.startsWith(m.workdir)),k=x.length>0?new Date(x.reduce((b,y)=>new Date(y.updatedAt)>new Date(b.updatedAt)?y:b).updatedAt).getTime():new Date(g.updatedAt).getTime();return(S.length>0?new Date(S.reduce((b,y)=>new Date(y.updatedAt)>new Date(b.updatedAt)?y:b).updatedAt).getTime():new Date(m.updatedAt).getTime())-k}),f=g=>{const m=s.find(x=>x.id===g);return m?i.filter(x=>x.workdir.startsWith(m.workdir)).sort((x,S)=>new Date(S.updatedAt).getTime()-new Date(x.updatedAt).getTime()).slice(0,5):[]},d=()=>{r(!0)};return o.jsxs("div",{className:"flex-1 flex flex-col overflow-y-auto",children:[o.jsxs("div",{className:"max-w-5xl mx-auto w-full p-4 md:p-8",children:[o.jsxs("div",{className:"mb-6 md:mb-8 flex items-center justify-between",children:[o.jsxs("div",{children:[o.jsx("h1",{className:"text-3xl font-bold text-accent-primary",children:"OpenFox"}),o.jsx("p",{className:"text-text-secondary",children:"Local LLM-powered coding assistant with contract-driven execution"})]}),o.jsx(dt,{variant:"primary",onClick:d,children:"Open Project"})]}),l.map(g=>{const m=f(g.id);return o.jsx("div",{className:"mb-6 md:mb-8",children:o.jsxs("div",{className:"bg-bg-secondary border border-border rounded-lg overflow-hidden",children:[o.jsxs("div",{className:"p-3 md:p-4 border-b border-border flex items-center justify-between gap-2",children:[o.jsxs(An,{href:`/p/${g.id}`,className:"flex items-center gap-2 cursor-pointer hover:opacity-80 transition-opacity flex-1",children:[o.jsx("svg",{className:"w-5 h-5 text-accent-primary flex-shrink-0",fill:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{d:"M10 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V8c0-1.1-.9-2-2-2h-8l-2-2z"})}),o.jsx("span",{className:"text-text-primary font-semibold",children:g.name})]}),o.jsx(An,{href:`/p/${g.id}/new`,className:"rounded font-medium transition-colors bg-accent-primary/25 text-white hover:bg-accent-primary/40 px-1.5 py-1 text-xs",children:"+ New Session"})]}),o.jsx("div",{className:"divide-y divide-border",children:m.length>0?m.map(x=>{const S=s.find(C=>x.workdir.startsWith(C.workdir)),k=S?`/p/${S.id}/s/${x.id}`:"#";return o.jsx(An,{href:k,className:"block p-3 md:p-4 hover:bg-bg-tertiary/50 cursor-pointer transition-colors",children:o.jsxs("div",{className:"flex items-center justify-between gap-2",children:[o.jsx("div",{className:"flex items-center gap-3 flex-1 min-w-0",children:o.jsx("div",{className:"flex-1 min-w-0",children:o.jsx("div",{className:"text-sm text-text-muted truncate",children:x.title??x.id.slice(0,8)})})}),o.jsxs("div",{className:"flex items-center gap-2 flex-shrink-0",children:[o.jsx("span",{className:"text-text-muted text-xs",children:AS(x.updatedAt)}),o.jsxs("span",{className:"text-text-muted text-xs",children:[x.messageCount," msgs"]})]})]})},x.id)}):o.jsx("div",{className:"p-3 md:p-4 text-text-muted text-sm",children:"No sessions yet"})})]})},g.id)}),l.length===0&&o.jsx("div",{className:"text-center py-12 text-text-muted",children:"No projects yet. Open a project to get started."})]}),e&&o.jsx(WS,{isOpen:e,onClose:()=>r(!1)})]})}function VS(){const[,e]=mh("/p/:projectId/new"),[,r]=ar(),i=e==null?void 0:e.projectId,s=Ee(c=>c.createSession);return P.useEffect(()=>{i&&(async()=>{const u=await s(i);r(u?`/p/${i}/s/${u.id}`:`/p/${i}`)})()},[i,s,r]),o.jsx("div",{className:"flex-1 flex items-center justify-center",children:o.jsx(Fl,{})})}function YS(){const e=Ut(r=>r.currentProject);return o.jsx("div",{className:"h-full flex flex-col items-center justify-center p-8 text-center",children:o.jsxs("div",{className:"max-w-md",children:[o.jsx("h2",{className:"text-xl font-semibold text-text-primary mb-2",children:(e==null?void 0:e.name)??"Project"}),o.jsx("p",{className:"text-text-secondary mb-6",children:"No session selected"}),o.jsxs("div",{className:"flex flex-col gap-3",children:[e&&o.jsx(An,{href:`/p/${e.id}/new`,className:"block w-full rounded font-medium transition-colors bg-accent-primary/25 text-white hover:bg-accent-primary/40 px-3 py-2 text-center",children:"Create New Session"}),o.jsx("p",{className:"text-sm text-text-muted",children:"Or select an existing session from the sidebar"})]})]})})}const Ta=e=>Math.round(e*10)/10;function Xd(e){return{providerId:e.providerId,providerName:e.providerName,backend:e.backend,model:e.model}}function KS(e){return`${e.providerId}::${e.model}`}function XS(e){return`${e.providerName} > ${e.model}`}function kx(e){let r=0,i=0,s=0,c=0,u=0,p=0;const l=[],f=[];let d=0;for(const[x,S]of e.entries()){const k=S.stats,C=Xd(k);r+=k.totalTime,i+=k.toolTime,s+=k.prefillTokens,c+=k.generationTokens;const b=k.prefillSpeed>0?k.prefillTokens/k.prefillSpeed:0,y=k.generationSpeed>0?k.generationTokens/k.generationSpeed:0;u+=b,p+=y,l.push({messageId:S.id,timestamp:S.timestamp,...C,mode:k.mode,responseIndex:x+1,prefillTokens:k.prefillTokens,generationTokens:k.generationTokens,prefillSpeed:k.prefillSpeed,generationSpeed:k.generationSpeed,totalTime:k.totalTime,aiTime:k.totalTime-k.toolTime,toolTime:k.toolTime});const v=k.llmCalls??[];for(const _ of v)d+=1,f.push({messageId:S.id,timestamp:_.timestamp??S.timestamp,providerId:_.providerId,providerName:_.providerName,backend:_.backend,model:_.model,mode:k.mode,responseIndex:x+1,sessionCallIndex:d,callIndex:_.callIndex,promptTokens:_.promptTokens,completionTokens:_.completionTokens,ttft:_.ttft,completionTime:_.completionTime,prefillSpeed:_.prefillSpeed,generationSpeed:_.generationSpeed,totalTime:_.totalTime})}const g=u>0?Ta(s/u):0,m=p>0?Ta(c/p):0;return{totalTime:Ta(r),aiTime:Ta(r-i),toolTime:Ta(i),prefillTokens:s,generationTokens:c,avgPrefillSpeed:g,avgGenerationSpeed:m,responseCount:e.length,llmCallCount:f.length,dataPoints:l,callDataPoints:f}}function ZS(e){const r=e.filter(c=>c.stats!==void 0&&c.stats!==null).sort((c,u)=>new Date(c.timestamp).getTime()-new Date(u.timestamp).getTime());if(r.length===0)return null;const i=new Map;for(const c of r){const u=KS(Xd(c.stats)),p=i.get(u)??[];i.set(u,[...p,c])}const s=Array.from(i.entries()).map(([c,u])=>{const p=Xd(u[0].stats),l=kx(u);return{...p,key:c,label:XS(p),...l}});return{...kx(r),modelGroups:s}}function QS(e){return P.useMemo(()=>ZS(e),[e])}function JS(e){const[r,i]=P.useState(null),[s,c]=P.useState(!0),[u,p]=P.useState(null),l=e||"";return P.useEffect(()=>{if(!l){c(!1);return}let f=!0,d=null;const g=async()=>{try{const x=await(await ye(`/api/branch?workdir=${encodeURIComponent(l)}`)).json();f&&(i(x.branch),p(x.error||null),c(!1))}catch(m){f&&(p(m instanceof Error?m.message:"Failed to fetch branch"),c(!1))}};return g(),d=setInterval(g,3e3),()=>{f=!1,d&&clearInterval(d)}},[l]),{branch:r,loading:s,error:u}}function Tl(e){return e.toLocaleString("en-US").replace(/,/g," ")}function Ex(e){return e>=1e3?`${(e/1e3).toFixed(1)}k`:e.toFixed(1)}function ew(e){if(e<60)return`${e.toFixed(1)}s`;const r=Math.floor(e/60),i=Math.round(e%60);return`${r}m${i}s`}const tw="modulepreload",nw=function(e){return"/"+e},jx={},rw=function(r,i,s){let c=Promise.resolve();if(i&&i.length>0){let p=function(d){return Promise.all(d.map(g=>Promise.resolve(g).then(m=>({status:"fulfilled",value:m}),m=>({status:"rejected",reason:m}))))};document.getElementsByTagName("link");const l=document.querySelector("meta[property=csp-nonce]"),f=(l==null?void 0:l.nonce)||(l==null?void 0:l.getAttribute("nonce"));c=p(i.map(d=>{if(d=nw(d),d in jx)return;jx[d]=!0;const g=d.endsWith(".css"),m=g?'[rel="stylesheet"]':"";if(document.querySelector(`link[href="${d}"]${m}`))return;const x=document.createElement("link");if(x.rel=g?"stylesheet":tw,g||(x.as="script"),x.crossOrigin="",x.href=d,f&&x.setAttribute("nonce",f),document.head.appendChild(x),g)return new Promise((S,k)=>{x.addEventListener("load",S),x.addEventListener("error",()=>k(new Error(`Unable to preload CSS for ${d}`)))})}))}function u(p){const l=new Event("vite:preloadError",{cancelable:!0});if(l.payload=p,window.dispatchEvent(l),!l.defaultPrevented)throw p}return c.then(p=>{for(const l of p||[])l.status==="rejected"&&u(l.reason);return r().catch(u)})},Nx=["▁","▂","▃","▄","▅","▆","▇","█"];function iw(e,r,i){if(i===r)return 4;const s=(e-r)/(i-r);return Math.min(7,Math.max(0,Math.round(s*7)))}function sw(e,r){if(e===r){const c=Math.max(Math.abs(e)*.05,1);return{minY:e-c,maxY:r+c}}const i=r-e,s=Math.max(i*.1,.1);return{minY:e-s,maxY:r+s}}function aw(e,r){if(e.length===0||r<=0)return{blocks:"",minX:0,maxX:0,minY:0,maxY:0};const i=[...e].sort((m,x)=>m.x-x.x),s=i[0].x,c=i[i.length-1].x,u=Math.min(...i.map(m=>m.y)),p=Math.max(...i.map(m=>m.y)),{minY:l,maxY:f}=sw(u,p),d=Array.from({length:r},()=>" "),g=new Map;for(const m of i){const x=c===s?0:Math.round((m.x-s)/(c-s)*(r-1)),S=g.get(x)??[];g.set(x,[...S,m.y])}for(const[m,x]of g){const S=Math.max(...x);d[m]=Nx[iw(S,l,f)]??Nx[0]}return{blocks:d.join(""),minX:s,maxX:c,minY:l,maxY:f}}function Tx(e){return e>=1e6?`${(e/1e6).toFixed(1)}M`:e>=1e3?`${(e/1e3).toFixed(1)}k`:e.toFixed(1)}function Ax({data:e,width:r=60,height:i=78,label:s,xLabel:c,yLabel:u,showAxes:p=!0,formatY:l=Tx,formatX:f=Tx}){const d=P.useMemo(()=>{const g=aw(e,r),m=Math.max(r*6,240),x=10,S=8,C=[...e].sort((_,j)=>_.x-j.x).map(_=>{const j=g.maxX===g.minX?m/2:x+(_.x-g.minX)/(g.maxX-g.minX)*(m-x*2),A=g.maxY===g.minY?i/2:S+(g.maxY-_.y)/(g.maxY-g.minY)*(i-S*2);return{..._,cx:j,cy:A,leftPercent:j/m*100,topPercent:A/i*100}}),b=C.map((_,j)=>`${j===0?"M":"L"} ${_.cx.toFixed(1)} ${_.cy.toFixed(1)}`).join(" "),v=[g.maxY,(g.maxY+g.minY)/2,g.minY].map(_=>({value:_,y:g.maxY===g.minY?i/2:S+(g.maxY-_)/(g.maxY-g.minY)*(i-S*2)}));return{...g,chartWidth:m,points:C,path:b,gridLines:v}},[e,i,r]);return e.length===0?o.jsxs("div",{className:"font-mono text-text-muted text-xs",children:[s&&o.jsx("div",{className:"mb-1",children:s}),o.jsx("div",{children:"No data"})]}):o.jsxs("div",{className:"font-mono text-xs",children:[s&&o.jsx("div",{className:"text-text-secondary mb-2",children:s}),o.jsxs("div",{className:"flex gap-3",children:[p&&o.jsx("div",{className:"w-12 h-[78px] flex flex-col justify-between text-right text-text-muted",children:d.gridLines.map(g=>o.jsx("span",{children:l(g.value)},`${g.value}-${g.y}`))}),o.jsx("div",{className:"flex-1 min-w-0",children:o.jsxs("div",{className:"relative h-[78px]",children:[o.jsxs("svg",{viewBox:`0 0 ${d.chartWidth} ${i}`,className:"w-full h-[78px] overflow-visible",preserveAspectRatio:"none","aria-hidden":"true",children:[d.gridLines.map(g=>o.jsx("line",{x1:"0",x2:d.chartWidth,y1:g.y,y2:g.y,stroke:"currentColor",strokeDasharray:"3 4",className:"text-border/60"},`grid-${g.y}`)),d.points.map(g=>o.jsx("line",{x1:g.cx,x2:g.cx,y1:i-4,y2:g.cy,stroke:"currentColor",className:"text-border/40"},`guide-${g.cx}-${g.cy}`)),d.points.length>1&&o.jsx("path",{d:d.path,fill:"none",stroke:"currentColor",strokeWidth:"2",strokeLinecap:"round",strokeLinejoin:"round",className:"text-accent-primary/45"})]}),d.points.map(g=>o.jsx("div",{className:"absolute -translate-x-1/2 -translate-y-1/2",style:{left:`${g.leftPercent}%`,top:`${g.topPercent}%`},title:`${f(g.x)} -> ${l(g.y)}`,children:o.jsx("div",{className:"w-2.5 h-2.5 rounded-full bg-accent-primary/20 flex items-center justify-center",children:o.jsx("div",{className:"w-1.5 h-1.5 rounded-full bg-accent-primary"})})},`point-${g.x}-${g.y}`))]})})]}),p&&o.jsxs("div",{className:"flex items-start gap-3 text-text-muted mt-1",children:[o.jsx("span",{className:"w-12"}),o.jsxs("span",{className:"flex-1 flex justify-between",children:[o.jsx("span",{children:f(d.minX)}),o.jsx("span",{children:c}),o.jsx("span",{children:f(d.maxX)})]})]}),u&&p&&o.jsx("div",{className:"text-text-muted mt-1 text-center",children:u})]})}function ow({data:e,prefillLabel:r="Prefill Speed (tok/s) by Response",generationLabel:i="Generation Speed (tok/s) by Response",xLabel:s="response",width:c=60}){const u=e.map(l=>({x:l.x,y:l.ppSpeed})),p=e.map(l=>({x:l.x,y:l.tgSpeed}));return o.jsxs("div",{className:"space-y-5",children:[o.jsx(Ax,{data:u,width:c,label:r,xLabel:s}),o.jsx(Ax,{data:p,width:c,label:i,xLabel:s})]})}function lw(e){const r=new Map;for(const i of e.callDataPoints){const s=r.get(i.messageId)??[];r.set(i.messageId,[...s,i])}return e.dataPoints.map(i=>{const s=[...r.get(i.messageId)??[]].sort((c,u)=>c.callIndex-u.callIndex);return{...i,callCount:s.length,calls:s,isExpandable:s.length>1}})}function cw(e){return{mode:"responses",xLabel:"response",prefillLabel:"Prefill Speed (tok/s) by Response",generationLabel:"Generation Speed (tok/s) by Response",points:e.dataPoints.map(r=>({x:r.responseIndex,ppSpeed:r.prefillSpeed,tgSpeed:r.generationSpeed}))}}function uw(e){return{mode:"calls",xLabel:"context",prefillLabel:"Prefill Speed (tok/s) vs Context",generationLabel:"Generation Speed (tok/s) vs Context",points:e.callDataPoints.map(r=>({x:r.promptTokens,ppSpeed:r.prefillSpeed,tgSpeed:r.generationSpeed}))}}function dw(e){return e.callDataPoints.length>0?uw(e):cw(e)}function kd(e){if(e<60)return`${e.toFixed(1)}s`;const r=Math.floor(e/60),i=e%60;return`${r}m ${i.toFixed(0)}s`}function Ni(e){return e>=1e6?`${(e/1e6).toFixed(1)}M`:e>=1e3?`${(e/1e3).toFixed(1)}k`:e.toString()}function Ia(e){return e>=1e3?`${(e/1e3).toFixed(1)}k`:e.toFixed(1)}function hw(e){if(e.length===0)return"0 ctx";const r=Math.min(...e),i=Math.max(...e);return r===i?`${Ni(r)} ctx`:`${Ni(r)}-${Ni(i)} ctx`}function Al(e){return`${Ia(e)} t/s`}function pb(e){try{return new Date(e).toLocaleTimeString("en-US",{hour12:!1})}catch{return e}}function fw(e){return{exportedAt:new Date().toISOString(),providerId:e.providerId,providerName:e.providerName,backend:e.backend,model:e.model,label:e.label,summary:{totalTime:e.totalTime,aiTime:e.aiTime,toolTime:e.toolTime,prefillTokens:e.prefillTokens,generationTokens:e.generationTokens,avgPrefillSpeed:e.avgPrefillSpeed,avgGenerationSpeed:e.avgGenerationSpeed,responseCount:e.responseCount,llmCallCount:e.llmCallCount},responses:e.dataPoints.map(r=>({responseIndex:r.responseIndex,timestamp:r.timestamp,mode:r.mode,prefillTokens:r.prefillTokens,generationTokens:r.generationTokens,prefillSpeed:r.prefillSpeed,generationSpeed:r.generationSpeed,totalTime:r.totalTime,aiTime:r.aiTime,toolTime:r.toolTime})),llmCalls:e.callDataPoints.map(r=>({sessionCallIndex:r.sessionCallIndex,responseIndex:r.responseIndex,callIndex:r.callIndex,timestamp:r.timestamp,mode:r.mode,promptTokens:r.promptTokens,completionTokens:r.completionTokens,ttft:r.ttft,completionTime:r.completionTime,prefillSpeed:r.prefillSpeed,generationSpeed:r.generationSpeed,totalTime:r.totalTime}))}}function pw({isOpen:e,onClose:r,stats:i}){const s=P.useRef(null),[c,u]=P.useState({}),[p,l]=P.useState(()=>{var k;return((k=i.modelGroups[0])==null?void 0:k.key)??""});P.useEffect(()=>{var k;i.modelGroups.some(C=>C.key===p)||l(((k=i.modelGroups[0])==null?void 0:k.key)??"")},[p,i.modelGroups]);const f=P.useMemo(()=>i.modelGroups.find(k=>k.key===p)??i.modelGroups[0],[p,i.modelGroups]),d=P.useMemo(()=>f?lw(f):[],[f]),g=P.useMemo(()=>f?dw(f):{mode:"responses",xLabel:"response",prefillLabel:"",generationLabel:"",points:[]},[f]),m=P.useCallback(k=>{u(C=>({...C,[k]:!C[k]}))},[]),x=P.useCallback(()=>{if(!f)return;const k=fw(f);navigator.clipboard.writeText(JSON.stringify(k,null,2)).catch(C=>console.error("Failed to copy:",C))},[f]),S=P.useCallback(async()=>{if(s.current)try{const k=(await rw(async()=>{const{default:y}=await import("./html2canvas.esm-QH1iLAAe.js");return{default:y}},[])).default,C=await k(s.current,{backgroundColor:"#1a1a1a",scale:2}),b=document.createElement("a");b.download=`openfox-stats-${new Date().toISOString().slice(0,10)}.png`,b.href=C.toDataURL("image/png"),b.click()}catch(k){console.error("Failed to export PNG:",k),x()}},[x]);return o.jsx(un,{isOpen:e,onClose:r,title:"Session Stats",size:"lg",children:o.jsxs("div",{ref:s,className:"space-y-6",children:[o.jsx("section",{children:o.jsx("div",{className:"flex flex-wrap gap-2",children:i.modelGroups.map(k=>o.jsx("button",{onClick:()=>l(k.key),className:`px-3 py-1.5 rounded border text-xs transition-colors ${k.key===(f==null?void 0:f.key)?"border-accent-primary bg-accent-primary/10 text-accent-primary":"border-border text-text-muted hover:text-text-primary hover:bg-bg-tertiary/40"}`,title:k.label,children:k.label},k.key))})}),f&&o.jsxs("section",{children:[o.jsx("h3",{className:"text-sm font-semibold text-text-secondary mb-3 uppercase tracking-wide",children:"Summary"}),o.jsxs("div",{className:"grid grid-cols-2 md:grid-cols-5 gap-4",children:[o.jsx(Er,{label:"AI Time",value:kd(f.aiTime)}),o.jsx(Er,{label:"Total Time",value:kd(f.totalTime)}),o.jsx(Er,{label:"Tool Time",value:kd(f.toolTime)}),o.jsx(Er,{label:"Responses",value:f.responseCount.toString()}),o.jsx(Er,{label:"LLM Calls",value:f.llmCallCount.toString()})]}),o.jsxs("div",{className:"grid grid-cols-2 md:grid-cols-4 gap-4 mt-3",children:[o.jsx(Er,{label:"Prefill Tokens",value:Ni(f.prefillTokens),subValue:`@ ${Ia(f.avgPrefillSpeed)} tok/s`}),o.jsx(Er,{label:"Gen Tokens",value:Ni(f.generationTokens),subValue:`@ ${Ia(f.avgGenerationSpeed)} tok/s`}),o.jsx(Er,{label:"Avg PP Speed",value:`${Ia(f.avgPrefillSpeed)}`,subValue:"tok/s"}),o.jsx(Er,{label:"Avg TG Speed",value:`${Ia(f.avgGenerationSpeed)}`,subValue:"tok/s"})]})]}),f&&g.points.length>1&&o.jsxs("section",{children:[o.jsxs("div",{className:"flex items-center justify-between mb-3",children:[o.jsx("h3",{className:"text-sm font-semibold text-text-secondary uppercase tracking-wide",children:"Performance Progression"}),o.jsxs("div",{className:"flex items-center gap-2",children:[o.jsx("button",{onClick:x,className:"px-2 py-1 text-xs text-text-muted hover:text-text-primary hover:bg-bg-tertiary rounded transition-colors",children:"Copy JSON"}),o.jsx("button",{onClick:S,className:"px-2 py-1 text-xs text-text-muted hover:text-text-primary hover:bg-bg-tertiary rounded transition-colors",children:"Save PNG"})]})]}),o.jsx("div",{className:"bg-bg-tertiary/50 rounded p-4",children:o.jsx(ow,{data:g.points,width:50,prefillLabel:g.prefillLabel,generationLabel:g.generationLabel,xLabel:g.xLabel})})]}),f&&o.jsxs("section",{children:[o.jsxs("h3",{className:"text-sm font-semibold text-text-secondary mb-3 uppercase tracking-wide",children:["Response Log (",f.responseCount," responses)"]}),o.jsx("div",{className:"overflow-y-auto bg-bg-tertiary/30 rounded",children:o.jsxs("table",{className:"w-full table-fixed border-separate border-spacing-0 text-xs",children:[o.jsxs("colgroup",{children:[o.jsx("col",{className:"w-[7%]"}),o.jsx("col",{className:"w-[14%]"}),o.jsx("col",{className:"w-[10%]"}),o.jsx("col",{className:"w-[14%]"}),o.jsx("col",{className:"w-[14%]"}),o.jsx("col",{className:"w-[14%]"}),o.jsx("col",{className:"w-[11%]"}),o.jsx("col",{className:"w-[2%]"})]}),o.jsx("thead",{children:o.jsxs("tr",{className:"text-[10px] uppercase tracking-wide text-text-muted/80",children:[o.jsx("th",{className:"px-3 py-2 text-center font-medium",children:"#"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"At"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"Time"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"Context"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"PP t/s"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"TG t/s"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"Calls"}),o.jsx("th",{className:"px-2 py-2"})]})}),o.jsx("tbody",{children:d.map((k,C)=>o.jsxs(P.Fragment,{children:[o.jsx(mw,{row:k,index:C,isExpanded:c[k.messageId]??!1,onToggle:k.isExpandable?()=>m(k.messageId):void 0}),(c[k.messageId]??!1)&&k.calls.map((b,y)=>o.jsx(gw,{dataPoint:b,index:y},`${b.messageId}-${b.callIndex}`))]},k.messageId))})]})})]})]})})}function Er({label:e,value:r,subValue:i}){return o.jsxs("div",{className:"bg-bg-tertiary/50 rounded p-3",children:[o.jsx("div",{className:"text-text-muted text-xs mb-1",children:e}),o.jsx("div",{className:"text-text-primary text-lg font-semibold",children:r}),i&&o.jsx("div",{className:"text-text-muted text-xs",children:i})]})}function mw({row:e,index:r,isExpanded:i,onToggle:s}){const c=e.calls.length>0?hw(e.calls.map(u=>u.promptTokens)):`${Ni(e.prefillTokens)} ctx`;return o.jsxs("tr",{onClick:s,className:`${r%2===0?"bg-bg-tertiary/20":""} ${s?"cursor-pointer hover:bg-bg-tertiary/35 transition-colors":""}`,children:[o.jsx("td",{className:"px-3 py-2 text-center text-text-muted align-middle",children:e.responseIndex}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted font-mono align-middle whitespace-nowrap",children:pb(e.timestamp)}),o.jsxs("td",{className:"px-2 py-2 text-center text-text-muted align-middle whitespace-nowrap",children:[e.totalTime.toFixed(1),"s"]}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:c.replace(/ ctx$/,"")}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Al(e.prefillSpeed)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Al(e.generationSpeed)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted font-mono align-middle whitespace-nowrap",children:e.callCount}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted align-middle whitespace-nowrap",children:e.isExpandable?i?"v":">":""})]})}function gw({dataPoint:e,index:r}){return o.jsxs("tr",{className:`${r%2===0?"bg-bg-tertiary/10":"bg-bg-tertiary/5"}`,children:[o.jsxs("td",{className:"px-3 py-2 pl-6 text-center text-text-muted align-middle border-l border-border/60",children:["c",e.callIndex]}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted font-mono align-middle whitespace-nowrap",children:pb(e.timestamp)}),o.jsxs("td",{className:"px-2 py-2 text-center text-text-muted align-middle whitespace-nowrap",children:[e.totalTime.toFixed(1),"s"]}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Ni(e.promptTokens)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Al(e.prefillSpeed)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Al(e.generationSpeed)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted font-mono align-middle whitespace-nowrap",children:e.callIndex}),o.jsx("td",{className:"px-2 py-2"})]})}const xw={pending:{icon:"○",color:"text-text-muted",label:"Pending"},in_progress:{icon:"●",color:"text-accent-warning",label:"In Progress",animate:!0},completed:{icon:"◉",color:"text-purple-400",label:"Completed"},passed:{icon:"✓",color:"text-accent-success",label:"Passed"},failed:{icon:"✗",color:"text-accent-error",label:"Failed"}},vw=P.memo(function({criteria:r}){if(r.length===0)return o.jsx("div",{className:"text-text-muted text-sm text-center py-2",children:"No criteria yet"});const i={pending:0,in_progress:0,completed:0,passed:0,failed:0};for(const c of r){const u=c.status.type;u in i&&i[u]++}const s=Object.keys(i).filter(c=>i[c]>0);return o.jsxs("div",{className:"space-y-1",children:[o.jsxs("div",{className:"flex items-center gap-2 text-sm",children:[o.jsx("span",{className:"font-semibold text-text-primary",children:"Total:"}),o.jsx("span",{className:"text-text-secondary",children:r.length})]}),o.jsx("div",{className:"space-y-1",children:s.map(c=>{const u=xw[c];return o.jsxs("div",{className:"flex items-center gap-2 text-sm",children:[o.jsx("span",{className:`${u.color} ${u.animate?"animate-pulse":""} text-sm leading-tight`,children:u.icon}),o.jsxs("span",{className:"text-text-muted",children:[u.label,":"]}),o.jsx("span",{className:"text-text-primary font-medium",children:i[c]})]},c)})})]})});function bw({isOpen:e,onClose:r}){const i=ir(S=>S.config),s=ir(S=>S.saveConfig),[c,u]=P.useState(""),[p,l]=P.useState(""),[f,d]=P.useState(!1),[g,m]=P.useState(!1);P.useEffect(()=>{e&&(u((i==null?void 0:i.command)??""),l((i==null?void 0:i.url)??""),d((i==null?void 0:i.hotReload)??!1))},[e,i]);const x=async()=>{!c.trim()||!p.trim()||(m(!0),await s({command:c.trim(),url:p.trim(),hotReload:f}),m(!1),r())};return o.jsx(un,{isOpen:e,onClose:r,title:"Dev Server Config",size:"sm",children:o.jsxs("div",{className:"space-y-4",children:[o.jsxs("div",{children:[o.jsx("label",{className:"block text-xs text-text-secondary mb-1",children:"Command"}),o.jsx("input",{className:"input w-full",type:"text",value:c,onChange:S=>u(S.target.value),placeholder:"npm run dev"})]}),o.jsxs("div",{children:[o.jsx("label",{className:"block text-xs text-text-secondary mb-1",children:"Dev URL"}),o.jsx("input",{className:"input w-full",type:"text",value:p,onChange:S=>l(S.target.value),placeholder:"http://localhost:3000"})]}),o.jsxs("div",{className:"flex items-center gap-2",children:[o.jsx("input",{type:"checkbox",id:"hotReload",checked:f,onChange:S=>d(S.target.checked),className:"rounded border-border bg-bg-tertiary"}),o.jsx("label",{htmlFor:"hotReload",className:"text-xs text-text-secondary",children:"Hot Reload"})]}),o.jsxs("div",{className:"flex justify-end gap-2 pt-2",children:[o.jsx("button",{className:"btn btn-secondary",onClick:r,children:"Cancel"}),o.jsx("button",{className:"btn btn-primary",onClick:x,disabled:g||!c.trim()||!p.trim(),children:g?"Saving...":"Save"})]})]})})}const Dx={30:"text-black",31:"text-red-400",32:"text-accent-success",33:"text-accent-warning",34:"text-blue-400",35:"text-purple-400",36:"text-cyan-400",37:"text-gray-300",90:"text-gray-500",91:"text-red-500",92:"text-green-500",93:"text-yellow-400",94:"text-blue-500",95:"text-pink-400",96:"text-cyan-500",97:"text-white"},yw={40:"bg-black",41:"bg-red-900",42:"bg-green-900",43:"bg-yellow-900",44:"bg-blue-900",45:"bg-purple-900",46:"bg-cyan-900",47:"bg-gray-700"},Lx={1:"font-bold",2:"opacity-75",4:"underline",7:"bg-bg-secondary"},_w="text-text-primary";function Sw(e){const r=[],i=/\x1b\[([0-9;]+)m/g;let s=0,c="text-text-primary",u;try{for(;(u=i.exec(e))!==null;){if(u.index>s){const d=e.slice(s,u.index);d&&r.push({text:d,className:c})}const p=u[1];if(!p)continue;const l=p.split(";").map(Number);if(l.length===0||l[0]===0){c="text-text-primary";continue}const f=[];for(const d of l)if(d>=30&&d<=37){const g=Dx[d];g&&f.push(g)}else if(d>=40&&d<=47){const g=yw[d];g&&f.push(g)}else if(d>=90&&d<=97){const g=Dx[d];g&&f.push(g)}else if(d in Lx){const g=Lx[d];g&&f.push(g)}else d===39?f.push(_w):d===49&&(c=c.split(" ").filter(g=>!g.startsWith("bg-")).join(" "));f.length>0&&(c=f.join(" ")),s=i.lastIndex}if(s<e.length){const p=e.slice(s);p&&r.push({text:p,className:c})}return r}catch(p){return console.warn("ANSI parsing failed, stripping codes:",p),[{text:ww(e),className:"text-text-primary"}]}}function ww(e){return e.replace(/\x1b\[([0-9;]+)m/g,"")}function Ns(e){var i,s;const r=Sw(e);return r.length===1&&((i=r[0])==null?void 0:i.className)==="text-text-primary"?(s=r[0])==null?void 0:s.text:r.map((c,u)=>ln.createElement("span",{key:u,className:c.className},c.text))}const Cw=P.memo(function({logs:r,onClose:i}){const s=P.useRef(null);return P.useEffect(()=>{const c=u=>{u.key==="Escape"&&i()};return window.addEventListener("keydown",c),()=>window.removeEventListener("keydown",c)},[i]),P.useEffect(()=>{s.current&&(s.current.scrollTop=s.current.scrollHeight)},[r]),o.jsx("div",{className:"fixed inset-0 z-50 flex items-center justify-center bg-black/60",onClick:i,children:o.jsxs("div",{className:"relative w-[90vw] h-[90vh] bg-bg-primary rounded-lg border border-border flex flex-col",onClick:c=>c.stopPropagation(),children:[o.jsxs("div",{className:"flex items-center justify-between p-3 border-b border-border",children:[o.jsx("h3",{className:"text-sm font-semibold text-text-primary",children:"Dev Server Logs"}),o.jsx("button",{onClick:i,className:"p-1.5 rounded hover:bg-bg-tertiary transition-colors text-text-muted",children:o.jsx("svg",{className:"w-5 h-5",viewBox:"0 0 20 20",fill:"currentColor",children:o.jsx("path",{fillRule:"evenodd",d:"M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z",clipRule:"evenodd"})})})]}),o.jsx("pre",{ref:s,className:"flex-1 overflow-auto p-4 text-sm font-mono text-text-primary",children:r.length===0?o.jsx("span",{className:"text-text-muted",children:"No output yet"}):r.map((c,u)=>o.jsx("span",{className:c.stream==="stderr"?"text-accent-warning":"",children:Ns(c.content)},u))})]})})}),kw=P.memo(function({logs:r,anchorRef:i,isHiding:s,onExpand:c,onClose:u}){const[p,l]=P.useState(null),f=P.useRef(null);return P.useEffect(()=>{var g;const d=(g=i.current)==null?void 0:g.getBoundingClientRect();d&&l({bottom:window.innerHeight-d.bottom,right:window.innerWidth-d.right,width:d.width,height:d.height})},[i]),P.useEffect(()=>{f.current&&(f.current.scrollTop=f.current.scrollHeight)},[r]),p?o.jsxs("div",{className:"relative",children:[o.jsx("pre",{ref:f,className:"fixed z-50 text-sm font-mono text-text-primary bg-bg-primary p-2 rounded border border-border overflow-auto transition-all duration-150 ease-out select-text",style:{bottom:p.bottom,right:p.right,width:p.width*2,maxHeight:p.height*3,transformOrigin:"bottom right",transform:s?"scale(0.01)":"scale(1)",opacity:s?0:1},children:r.map((d,g)=>o.jsx("span",{className:d.stream==="stderr"?"text-accent-warning":"",children:Ns(d.content)},g))}),o.jsx("button",{onClick:()=>{u(),c()},className:"fixed z-50 px-2 py-1 rounded text-xs font-medium bg-accent-primary/30 text-white hover:bg-accent-primary/50 transition-colors duration-150",style:{bottom:p.bottom+8,right:p.right+8},children:"Expand"})]}):null}),Ew=P.memo(function({workdir:r}){const i=ir(z=>z.setWorkdir),s=ir(z=>z.status),c=ir(z=>z.config),u=ir(z=>z.logs),p=ir(z=>z.start),l=ir(z=>z.stop),f=ir(z=>z.fetchLogs),[d,g]=P.useState(!1),[m,x]=P.useState(!1),[S,k]=P.useState(!1),[C,b]=P.useState(!1),y=P.useRef(null),v=P.useRef(null),_=P.useRef(null),j=P.useRef(null),A=(s==null?void 0:s.state)??"off",N=c!==null,L=A==="running"||A==="warning";P.useEffect(()=>{i(r??null)},[r,i]),P.useEffect(()=>{L&&f()},[L,f]),P.useEffect(()=>{_.current&&L&&(_.current.scrollTop=_.current.scrollHeight)},[u,L]);const T=()=>{L?l():p()},I=o.jsx("svg",{className:"w-4 h-4",viewBox:"0 0 16 16",fill:"currentColor",children:o.jsx("path",{d:"M8 0a8.2 8.2 0 0 1 .701.031C9.444.095 9.99.645 10.16 1.29l.288 1.107c.018.066.079.158.212.224.231.114.454.243.668.386.123.082.233.09.299.071l1.1-.303c.652-.18 1.37.008 1.755.653a8.043 8.043 0 0 1 .683 1.18c.227.568.096 1.26-.378 1.726l-.812.804a.312.312 0 0 0-.081.283c.024.166.04.335.04.507s-.016.341-.04.507a.312.312 0 0 0 .08.283l.813.804c.474.466.605 1.158.378 1.726a8.07 8.07 0 0 1-.683 1.18c-.385.645-1.103.833-1.755.653l-1.1-.303c-.066-.019-.176-.011-.299.071a5.1 5.1 0 0 1-.668.386c-.133.066-.194.158-.211.224l-.29 1.107c-.168.645-.714 1.196-1.458 1.26a8.094 8.094 0 0 1-1.402 0c-.744-.064-1.29-.615-1.458-1.26l-.29-1.107a.426.426 0 0 0-.211-.224 5.11 5.11 0 0 1-.668-.386c-.123-.082-.233-.09-.299-.071l-1.1.303c-.652.18-1.37-.008-1.755-.653a8.044 8.044 0 0 1-.683-1.18c-.227-.568-.096-1.26.378-1.726l.812-.804a.312.312 0 0 0 .081-.283A5.18 5.18 0 0 1 2.3 8c0-.172.016-.341.04-.507a.312.312 0 0 0-.08-.283l-.813-.804C.973 5.94.842 5.248 1.069 4.68c.181-.452.395-.882.683-1.18.385-.645 1.103-.833 1.755-.653l1.1.303c.066.019.176.011.299-.071.214-.143.437-.272.668-.386a.426.426 0 0 0 .211-.224l.29-1.107C6.009.645 6.556.095 7.299.03 7.53.01 7.764 0 8 0Zm0 5.5a2.5 2.5 0 1 0 0 5 2.5 2.5 0 0 0 0-5Z"})});return o.jsxs("div",{className:"mt-2 pt-3 border-t border-border space-y-3",children:[o.jsxs("div",{className:"flex items-center justify-between",children:[o.jsxs("div",{className:"flex items-center gap-2",children:[o.jsx("span",{className:`inline-block w-2.5 h-2.5 rounded-full flex-shrink-0 ${A==="running"?"bg-accent-success":A==="warning"?"bg-accent-warning":A==="error"?"bg-accent-error":"bg-text-muted"}`}),o.jsx("h3",{className:"text-sm font-semibold text-text-primary",children:"Dev Server"})]}),o.jsx("button",{onClick:()=>g(!0),className:"p-1.5 rounded hover:bg-bg-tertiary transition-colors text-text-muted",title:"Configure dev server",children:I})]}),N?o.jsxs(o.Fragment,{children:[A==="running"||A==="warning"?o.jsxs("div",{className:"flex gap-2",children:[o.jsxs("button",{onClick:T,className:"flex-1 flex items-center justify-center gap-1.5 rounded font-medium text-sm px-3 py-1.5 bg-bg-tertiary text-text-primary hover:bg-border transition-colors",children:[o.jsx("svg",{className:"w-4 h-4",viewBox:"0 0 16 16",fill:"currentColor",children:o.jsx("rect",{x:"3",y:"3",width:"10",height:"10",rx:"1"})}),"Stop"]}),(s==null?void 0:s.url)&&o.jsxs("button",{onClick:()=>window.open((s==null?void 0:s.url)??"","_blank"),className:"flex-1 flex items-center justify-center gap-1.5 rounded font-medium text-sm px-3 py-1.5 bg-accent-primary/25 text-white hover:bg-accent-primary/40 transition-colors",title:s.url,children:[o.jsxs("svg",{className:"w-4 h-4",viewBox:"0 0 16 16",fill:"none",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round",children:[o.jsx("path",{d:"M6.5 3.5H3a1 1 0 0 0-1 1V13a1 1 0 0 0 1 1h8.5a1 1 0 0 0 1-1V9.5"}),o.jsx("path",{d:"M9.5 2h4.5v4.5"}),o.jsx("path",{d:"M14 2L7.5 8.5"})]}),"Open"]})]}):o.jsx("button",{onClick:T,className:"w-full rounded font-medium text-sm px-3 py-1.5 bg-accent-primary/25 text-white hover:bg-accent-primary/40 transition-colors",children:"Start"}),L&&o.jsxs("div",{ref:j,className:"relative",onMouseEnter:()=>{v.current&&clearTimeout(v.current),y.current=setTimeout(()=>{k(!0),b(!1)},500)},onMouseLeave:()=>{y.current&&clearTimeout(y.current),b(!0),v.current=setTimeout(()=>k(!1),150)},children:[o.jsx("pre",{ref:_,className:"text-sm bg-bg-primary p-2 rounded overflow-auto max-h-[200px] border border-border",children:u.length===0?o.jsx("span",{className:"text-text-muted",children:"No output yet"}):u.map((z,V)=>o.jsx("span",{className:z.stream==="stderr"?"text-accent-warning":"",children:Ns(z.content)},V))}),(S||C)&&j.current&&Hl.createPortal(o.jsx(kw,{logs:u,anchorRef:j,isHiding:C,onExpand:()=>x(!0),onClose:()=>k(!1)}),document.body)]})]}):o.jsx("button",{onClick:()=>g(!0),className:"w-full rounded font-medium text-sm px-3 py-1.5 bg-bg-tertiary text-text-muted hover:bg-border transition-colors",children:"Configure"}),o.jsx(bw,{isOpen:d,onClose:()=>g(!1)}),m&&o.jsx(Cw,{logs:u,onClose:()=>x(!1)})]})}),jw=P.memo(function({isOpen:r,onClose:i,processName:s,logs:c}){const u=P.useRef(null);return P.useEffect(()=>{const p=l=>{l.key==="Escape"&&i()};if(r)return window.addEventListener("keydown",p),()=>window.removeEventListener("keydown",p)},[r,i]),P.useEffect(()=>{u.current&&r&&(u.current.scrollTop=u.current.scrollHeight)},[c,r]),r?o.jsx("div",{className:"fixed inset-0 z-50 flex items-center justify-center bg-black/60",onClick:i,children:o.jsxs("div",{className:"relative w-[90vw] h-[90vh] bg-bg-primary rounded-lg border border-border flex flex-col",onClick:p=>p.stopPropagation(),children:[o.jsxs("div",{className:"flex items-center justify-between p-3 border-b border-border",children:[o.jsx("h3",{className:"text-sm font-semibold text-text-primary truncate",children:s}),o.jsx("button",{onClick:i,className:"p-1.5 rounded hover:bg-bg-tertiary transition-colors text-text-muted",children:o.jsx("svg",{className:"w-5 h-5",viewBox:"0 0 20 20",fill:"currentColor",children:o.jsx("path",{fillRule:"evenodd",d:"M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z",clipRule:"evenodd"})})})]}),o.jsx("pre",{ref:u,className:"flex-1 overflow-auto p-4 text-sm font-mono text-text-primary whitespace-pre-wrap",children:c.length===0?o.jsx("span",{className:"text-text-muted",children:"No output yet"}):c.map((p,l)=>o.jsx("span",{className:p.stream==="stderr"?"text-accent-warning":"",children:Ns(p.content)},l))})]})}):null}),Nw=P.memo(function({sessionId:r}){var S;const i=Ba(k=>k.processes),s=Ba(k=>k.stopProcess),[c,u]=P.useState(null),[p,l]=P.useState([]),f=i.filter(k=>k.status!=="exited"),d=f.filter(k=>k.status==="running").length;if(i.length===0)return null;const g=k=>{switch(k){case"running":return"bg-accent-success";case"starting":return"bg-accent-warning";case"stopping":return"bg-accent-warning";case"exited":return"bg-text-muted";default:return"bg-text-muted"}},m=k=>{const C=Ba.getState().logs[k]??[];l(C.map(b=>({content:b.content,stream:b.stream}))),u(k)},x=k=>{r&&s(k,r)};return o.jsxs("div",{className:"mt-2 pt-3 border-t border-border space-y-3",children:[o.jsx("div",{className:"flex items-center justify-between",children:o.jsxs("div",{className:"flex items-center gap-2",children:[o.jsx("span",{className:"inline-block w-2.5 h-2.5 rounded-full flex-shrink-0 bg-accent-primary"}),o.jsx("h3",{className:"text-sm font-semibold text-text-primary",children:"Background"}),o.jsxs("span",{className:"text-xs text-text-muted",children:["(",d," running)"]})]})}),o.jsx("div",{className:"space-y-2",children:f.map(k=>o.jsx("div",{className:"border border-border rounded p-2",children:o.jsxs("div",{className:"flex items-center justify-between",children:[o.jsxs("div",{className:"flex items-center gap-2 min-w-0 flex-1",children:[o.jsx("span",{className:`inline-block w-2 h-2 rounded-full flex-shrink-0 ${g(k.status)}`}),o.jsx("span",{className:"text-sm text-text-primary truncate",title:k.name,children:k.name}),o.jsxs("span",{className:"text-xs text-text-muted",children:["[",k.status,"]"]})]}),o.jsxs("div",{className:"flex gap-1 ml-2",children:[o.jsx("button",{onClick:()=>m(k.id),className:"px-2 py-1 text-xs rounded bg-bg-tertiary hover:bg-border text-text-secondary transition-colors",title:"View logs",children:"Logs"}),o.jsx("button",{onClick:()=>x(k.id),className:"px-2 py-1 text-xs rounded bg-bg-tertiary hover:bg-accent-error/20 text-text-secondary hover:text-accent-error transition-colors",title:"Stop process",children:"Stop"})]})]})},k.id))}),c&&o.jsx(jw,{isOpen:!!c,onClose:()=>{u(null),l([])},processName:((S=f.find(k=>k.id===c))==null?void 0:S.name)??"",logs:p})]})});function Rx({summary:e,messages:r,workdir:i}){const[s,c]=P.useState(!1),u=QS(r),{branch:p}=JS(i),l=jt(d=>d.version),f=Ee(d=>d.currentSession);return o.jsxs("div",{className:"flex flex-col h-full",children:[u&&o.jsxs("div",{className:"mb-4",children:[o.jsx("button",{onClick:()=>c(!0),className:"w-full flex items-center justify-center px-3 py-2 rounded bg-bg-tertiary hover:bg-bg-secondary transition-colors",title:"View detailed response and call-level stats",children:o.jsxs("div",{className:"flex items-center gap-2 text-sm text-text-muted",children:[o.jsx("span",{className:"text-text-secondary",children:ew(u.aiTime)}),o.jsx("span",{className:"w-px h-3 bg-border"}),o.jsx("span",{className:"text-text-secondary",children:Ex(u.avgPrefillSpeed)}),o.jsx("span",{children:"pp"}),o.jsx("span",{className:"w-px h-3 bg-border"}),o.jsx("span",{className:"text-text-secondary",children:Ex(u.avgGenerationSpeed)}),o.jsx("span",{children:"tg"})]})}),o.jsx(pw,{isOpen:s,onClose:()=>c(!1),stats:u})]}),o.jsxs("div",{className:"flex flex-col flex-1 overflow-y-auto",children:[o.jsx("div",{className:"flex items-center justify-between mb-2",children:o.jsx("h3",{className:"text-sm font-semibold text-text-primary",children:"Summary"})}),e?o.jsx("p",{className:"text-sm text-text-primary leading-relaxed",children:e}):o.jsx("div",{className:"text-text-muted text-sm text-center py-2",children:"No summary yet"}),o.jsxs("div",{className:"mt-4",children:[o.jsx("h3",{className:"text-sm font-semibold text-text-primary mb-2",children:"Progress"}),o.jsx(vw,{criteria:(f==null?void 0:f.criteria)??[]})]})]}),p&&o.jsxs("div",{className:"mt-4 flex items-center gap-2 text-sm",children:[o.jsx("svg",{className:"w-4 h-4 flex-shrink-0 text-text-muted",viewBox:"0 0 16 16",fill:"currentColor",children:o.jsx("path",{d:"M9.5 3.25a2.25 2.25 0 1 1 3 2.122V6A2.5 2.5 0 0 1 10 8.5H6a1 1 0 0 0-1 1v1.128a2.251 2.251 0 1 1-1.5 0V5.372a2.25 2.25 0 1 1 1.5 0v1.836A2.493 2.493 0 0 1 6 7h4a1 1 0 0 0 1-1v-.628A2.25 2.25 0 0 1 9.5 3.25Zm-6 0a.75.75 0 1 0 1.5 0 .75.75 0 0 0-1.5 0Zm8.25-.75a.75.75 0 1 0 0 1.5.75.75 0 0 0 0-1.5ZM4.25 12a.75.75 0 1 0 0 1.5.75.75 0 0 0 0-1.5Z"})}),o.jsx("span",{className:"truncate text-text-secondary",title:p,children:p})]}),o.jsx(Ew,{workdir:i}),o.jsx(Nw,{sessionId:f==null?void 0:f.id}),l&&o.jsxs("div",{className:"mt-4 pt-4 border-t border-border text-center text-xs text-text-muted",children:[o.jsx("a",{href:"https://github.com/co-l/openfox",target:"_blank",rel:"noopener noreferrer",className:"hover:text-accent-primary transition-colors",children:"OpenFox"})," - ",o.jsxs("span",{children:["v",l]})]})]})}function Tw({children:e,criteriaSidebarOpen:r=!0,onCriteriaSidebarToggle:i,messages:s}){const c=Ee(u=>u.currentSession);return o.jsxs("div",{className:"relative h-full overflow-hidden",children:[r&&o.jsx("div",{className:"fixed md:hidden inset-0 bg-black/50 z-40",onClick:i}),o.jsxs("div",{className:"flex h-full",children:[o.jsx("div",{className:"flex-1 min-w-0 flex flex-col overflow-hidden",children:e}),r?o.jsx("aside",{className:"hidden md:block w-[320px] shrink-0 border-l border-border p-4 overflow-y-auto bg-bg-secondary",children:o.jsx(Rx,{summary:(c==null?void 0:c.summary)??null,messages:s,workdir:c==null?void 0:c.workdir})}):o.jsx("aside",{className:"hidden md:block w-0 shrink-0 overflow-hidden border-l-0"}),o.jsx("aside",{className:`
84
+ `,children:[o.jsxs("div",{className:"p-4 border-b border-border flex gap-2",children:[o.jsx(An,{href:`/p/${e}/new`,className:"flex-1 block text-center rounded font-medium transition-colors bg-accent-primary/25 text-white hover:bg-accent-primary/40 px-3 py-1.5 text-sm","data-testid":"sidebar-new-session-button",children:"+ New Session"}),o.jsx(Ka,{items:[{label:"Edit project settings",onClick:()=>u(!0)},{label:"Delete all sessions",onClick:_,danger:!0}],trigger:o.jsx("button",{className:"flex-shrink-0 p-2.5 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary transition-colors",title:"Options",children:o.jsxs("svg",{className:"w-4 h-4",fill:"currentColor",viewBox:"0 0 24 24",children:[o.jsx("circle",{cx:"12",cy:"5",r:"2"}),o.jsx("circle",{cx:"12",cy:"12",r:"2"}),o.jsx("circle",{cx:"12",cy:"19",r:"2"})]})})}),i&&o.jsx("button",{onClick:i,className:"md:hidden flex-shrink-0 p-2.5 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary transition-colors",title:"Close sidebar",children:o.jsx("svg",{className:"w-4 h-4",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M6 18L18 6M6 6l12 12"})})})]}),k&&o.jsx(BS,{isOpen:c,onClose:()=>u(!1),project:k}),o.jsx("div",{className:"flex-1 overflow-y-auto",children:y.length===0?o.jsx("div",{className:"p-4 text-center text-text-muted text-xs",children:"No sessions"}):o.jsxs(o.Fragment,{children:[o.jsx("div",{className:"divide-y divide-border",children:zS(y,l,f,v,e)}),S&&o.jsx("div",{className:"p-4 text-center text-text-muted text-xs",children:"Loading more..."}),o.jsx("div",{ref:C,className:"h-px"})]})})]})]})}function zS(e,r,i,s,c){const u=db(e);return Array.from(u).map(([p,l])=>{const f=l[0];return f?o.jsxs("div",{children:[o.jsx("div",{className:"px-4 py-2 bg-bg-tertiary/30 text-text-muted text-xs font-medium",children:ub(f.updatedAt)}),l.map(d=>{const g=(r==null?void 0:r.id)===d.id,m=i.includes(d.id),x=d.isRunning;return o.jsx("div",{className:`w-full px-4 py-3 text-left hover:bg-bg-tertiary/50 transition-colors group ${g?"bg-bg-tertiary":""}`,children:o.jsxs(An,{href:`/p/${c}/s/${d.id}`,className:`block ${g?"text-accent-primary":"text-text-primary"} hover:text-accent-primary`,children:[o.jsxs("div",{className:"flex justify-between items-center mb-1",children:[o.jsx("span",{className:`font-medium truncate text-sm ${g?"text-accent-primary":"text-text-primary"}`,children:d.title??d.id.slice(0,6)}),o.jsx(Ka,{items:[{label:"Delete session",onClick:S=>s(d.id,S),danger:!0}],trigger:o.jsx("button",{onClick:S=>S.preventDefault(),className:"p-1.5 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary transition-all",title:"Options",children:o.jsxs("svg",{className:"w-4 h-4",fill:"currentColor",viewBox:"0 0 24 24",children:[o.jsx("circle",{cx:"12",cy:"5",r:"2"}),o.jsx("circle",{cx:"12",cy:"12",r:"2"}),o.jsx("circle",{cx:"12",cy:"19",r:"2"})]})})})]}),o.jsxs("div",{className:"flex items-center gap-2 mt-1",children:[x?o.jsxs("svg",{"aria-label":"Session running",className:"w-3 h-3 text-blue-400 animate-spin flex-shrink-0",viewBox:"0 0 24 24",fill:"none",children:[o.jsx("title",{children:"Running"}),o.jsx("circle",{className:"opacity-30",cx:"12",cy:"12",r:"9",stroke:"currentColor",strokeWidth:"3"}),o.jsx("path",{d:"M21 12a9 9 0 00-9-9",stroke:"currentColor",strokeWidth:"3",strokeLinecap:"round"})]}):m&&!g?o.jsx("span",{"aria-label":"Unread activity",title:"Unread activity",className:"w-2 h-2 rounded-full bg-amber-400 flex-shrink-0"}):null,o.jsx("span",{className:"text-text-muted text-xs flex-shrink-0",children:gh(d.updatedAt)}),o.jsxs("span",{className:"text-text-muted text-xs flex-shrink-0",children:[d.messageCount," messages"]})]})]})},d.id)})]},p):null})}const Cx=["⠋","⠙","⠹","⠸","⠼","⠴"];function HS(){var l;const e=Ut(f=>f.currentProject),r=Ee(f=>f.currentSession),i=ob(),s=!1,c=P.useRef(0),u=P.useRef(null);P.useEffect(()=>(i?(u.current=window.setInterval(()=>{c.current=(c.current+1)%Cx.length,p()},150),p()):(u.current&&(clearInterval(u.current),u.current=null),p()),()=>{u.current&&(clearInterval(u.current),u.current=null)}),[i,e,r,s]);const p=()=>{var m;const d=(m=r==null?void 0:r.metadata)==null?void 0:m.title,g=i?`${Cx[c.current]} `:"";e&&d?document.title=`${g}${e.name} - ${d} | OpenFox`:e?document.title=`${g}${e.name} | OpenFox`:document.title=`${g}OpenFox`};return typeof window<"u"&&((l=r==null?void 0:r.metadata)!=null&&l.title)&&window.document.documentElement.setAttribute("data-session-title",r.metadata.title),null}const Pl=P.forwardRef(({className:e="",...r},i)=>o.jsx("input",{ref:i,className:`bg-bg-tertiary border border-border rounded px-3 py-2 text-text-primary placeholder-text-muted focus:outline-none focus:ring-2 focus:ring-accent-primary/50 focus:border-accent-primary ${e}`,...r}));Pl.displayName="Input";function PS({isOpen:e,onClose:r,projectName:i,onConfirm:s}){const c=()=>{s(),r()};return o.jsx(un,{isOpen:e,onClose:r,title:"Delete Project",size:"sm",children:o.jsxs("div",{className:"space-y-4",children:[o.jsxs("p",{className:"text-text-secondary",children:["This will permanently delete the project ",o.jsx("span",{className:"font-semibold text-text-primary",children:i})," and all its sessions from OpenFox. The project files on disk will remain untouched."]}),o.jsxs("div",{className:"flex justify-end gap-2",children:[o.jsx(dt,{variant:"secondary",onClick:r,children:"Cancel"}),o.jsx(dt,{variant:"danger",onClick:c,children:"Delete"})]})]})})}function FS(e){return!e||e.trim()===""?{valid:!1,error:"Project name cannot be empty"}:/^[a-zA-Z0-9._-]+$/.test(e)?{valid:!0}:{valid:!1,error:"Project name can only contain letters, numbers, hyphens, underscores, and dots"}}function US({isOpen:e,onClose:r}){const[,i]=ar(),[s,c]=P.useState(""),[u,p]=P.useState(null),[l,f]=P.useState(!1),[d,g]=P.useState(""),m=P.useRef(null);P.useEffect(()=>{e&&(ye("/api/config").then(C=>C.json()).then(C=>{C.workdir&&g(C.workdir)}),c(""),p(null),f(!1),setTimeout(()=>{var C;(C=m.current)==null||C.focus()},100))},[e]);const x=P.useCallback(async C=>{C.preventDefault();const b=FS(s);if(!b.valid){p(b.error);return}f(!0),p(null);const y=`${d}/${s}`;try{const v=await ye("/api/projects",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({name:s,workdir:y})});if(!v.ok){const A=await v.json().catch(()=>({}));throw new Error(A.error||"Failed to create project")}const j=(await v.json()).project;r(),i(`/p/${j.id}`)}catch(v){p(v instanceof Error?v.message:"Failed to create project"),f(!1)}},[s,i,r,d]),S=P.useCallback(()=>{c(""),p(null),r()},[r]),k=s?`${d}/${s}`:"";return o.jsx(un,{isOpen:e,onClose:S,title:"Create New Project",size:"sm",children:o.jsxs("form",{onSubmit:x,className:"space-y-4",children:[o.jsxs("div",{children:[o.jsx("label",{htmlFor:"project-name",className:"block text-sm font-medium text-text-secondary mb-2",children:"Project Name"}),o.jsx(Pl,{ref:m,id:"project-name",value:s,onChange:C=>{c(C.target.value),p(null)},placeholder:"my-project",disabled:l,className:"w-full"}),s&&o.jsxs("div",{className:"mt-2 text-xs text-text-muted",children:["Full path: ",o.jsx("span",{className:"font-mono",children:k})]}),u&&o.jsx("div",{className:"mt-3 p-3 bg-accent-error/10 border border-accent-error/30 rounded text-sm text-accent-error",children:u})]}),o.jsxs("div",{className:"flex justify-end gap-2",children:[o.jsx(dt,{type:"button",variant:"secondary",onClick:S,disabled:l,children:"Cancel"}),o.jsx(dt,{type:"submit",variant:"primary",disabled:l||!s.trim(),className:"min-w-[100px]",children:l?o.jsxs("span",{className:"flex items-center gap-2",children:[o.jsxs("svg",{className:"animate-spin h-4 w-4",fill:"none",viewBox:"0 0 24 24",children:[o.jsx("circle",{className:"opacity-25",cx:"12",cy:"12",r:"10",stroke:"currentColor",strokeWidth:"4"}),o.jsx("path",{className:"opacity-75",fill:"currentColor",d:"M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"})]}),"Creating..."]}):"Create"})]})]})})}const $S={sm:"w-4 h-4",md:"w-8 h-8",lg:"w-12 h-12"};function Fl({size:e="md",className:r=""}){return o.jsx("div",{className:`animate-spin border-2 border-accent-primary border-t-transparent rounded-full ${$S[e]} ${r}`})}function qS({text:e,...r}){return o.jsxs("div",{className:"text-center",children:[o.jsx(Fl,{...r,className:"mx-auto mb-4"}),e&&o.jsx("div",{className:"text-text-secondary",children:e})]})}function fb({onSelect:e,onClose:r,initialPath:i}){const[s,c]=P.useState(null),[u,p]=P.useState(!0),l=P.useCallback(async k=>{p(!0);try{const C=k?`/api/directories?path=${encodeURIComponent(k)}`:"/api/directories",y=await(await ye(C)).json();c(y)}catch(C){console.error("Failed to load directories:",C)}finally{p(!1)}},[]);P.useEffect(()=>{l(i)},[i,l]);const f=k=>{l(k)},d=k=>{e(k)},m=((s==null?void 0:s.current)??"").split("/").filter(Boolean),S=m.map((k,C)=>({name:k,path:"/"+m.slice(0,C+1).join("/")}));return o.jsx("div",{className:"fixed inset-0 z-50 flex items-center justify-center p-4 bg-black/50",onClick:r,children:o.jsxs("div",{className:"bg-bg-secondary border border-border rounded-lg w-full max-w-2xl max-h-[80vh] flex flex-col",onClick:k=>k.stopPropagation(),children:[o.jsxs("div",{className:"p-4 border-b border-border flex items-center justify-between",children:[o.jsx("h2",{className:"text-lg font-semibold text-text-primary",children:"Select Folder"}),o.jsx("button",{onClick:r,className:"p-1 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary",children:o.jsx("svg",{className:"w-5 h-5",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M6 18L18 6M6 6l12 12"})})})]}),s&&o.jsx("div",{className:"px-3 py-2 bg-bg-tertiary/30 border-b border-border",children:o.jsxs("div",{className:"flex items-center text-xs overflow-x-auto",children:[S.map((k,C)=>o.jsxs("span",{className:"flex items-center shrink-0",children:[o.jsx("span",{className:"text-text-muted",children:"/"}),o.jsx("button",{onClick:()=>f(k.path),className:`px-1 ${C===S.length-1?"text-accent-primary font-medium":"text-text-secondary hover:text-accent-primary"}`,children:k.name})]},k.path)),S.length===0&&o.jsx("button",{onClick:()=>f("/"),className:"text-text-muted hover:text-accent-primary",children:"/"})]})}),o.jsx("div",{className:"flex-1 overflow-y-auto",children:u?o.jsx("div",{className:"p-8 text-center",children:o.jsx(Fl,{size:"sm"})}):o.jsxs("div",{className:"divide-y divide-border",children:[(s==null?void 0:s.parent)&&o.jsxs("button",{onClick:()=>f(s.parent),className:"w-full p-3 flex items-center gap-3 hover:bg-bg-tertiary/50 text-text-muted",children:[o.jsx("svg",{className:"w-5 h-5",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M15 19l-7-7 7-7"})}),o.jsx("span",{children:".."})]}),s==null?void 0:s.directories.map(k=>o.jsxs("div",{className:"group flex items-center gap-2 hover:bg-bg-tertiary/50",children:[o.jsxs("button",{onClick:()=>f(k.path),className:"flex-1 p-3 flex items-center gap-3 text-left",children:[o.jsx("svg",{className:"w-5 h-5 text-accent-primary",fill:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{d:"M10 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V8c0-1.1-.9-2-2-2h-8l-2-2z"})}),o.jsx("span",{children:k.name})]}),o.jsx("button",{onClick:()=>d(k.path),className:"px-3 py-1 text-xs bg-accent-primary/10 text-accent-primary rounded opacity-0 group-hover:opacity-100 transition-opacity mr-3",children:"Select"})]},k.path)),(s==null?void 0:s.directories.length)===0&&o.jsx("div",{className:"p-8 text-center text-text-muted text-sm",children:"No subdirectories"})]})}),o.jsxs("div",{className:"p-4 border-t border-border space-y-2",children:[(s==null?void 0:s.current)&&o.jsx("button",{onClick:()=>d(s.current),className:"w-full px-4 py-2 bg-accent-primary text-white rounded-lg font-medium hover:bg-accent-primary/90 transition-colors",children:"Select this folder"}),o.jsx("button",{onClick:r,className:"w-full text-center text-text-muted hover:text-text-secondary text-sm",children:"Cancel"})]})]})})}function WS({isOpen:e,onClose:r}){const[,i]=ar(),[s,c]=P.useState(!1),[u,p]=P.useState(""),[l,f]=P.useState(null),[d,g]=P.useState(!1),[m,x]=P.useState(null),S=Ut(R=>R.projects),k=Ut(R=>R.createProject),C=Ut(R=>R.listProjects),b=Ut(R=>R.deleteProject),[y,v]=P.useState(null),[_,j]=P.useState(-1),[A,N]=P.useState(null),[L,T]=P.useState(!1),I=P.useRef([]);P.useEffect(()=>{ye("/api/config").then(R=>R.json()).then(R=>{R.workdir&&x(R.workdir)})},[]);const z=P.useCallback(async R=>{g(!0);try{const D=R?`/api/directories?path=${encodeURIComponent(R)}`:m?`/api/directories?path=${encodeURIComponent(m)}`:"/api/directories",W=await(await ye(D)).json();f(W)}catch(D){console.error("Failed to load directories:",D)}finally{g(!1)}},[m]);P.useEffect(()=>{e&&m&&(z(m),C())},[e,m,z,C]);const V=(l==null?void 0:l.directories.filter(R=>u===""||R.name.toLowerCase().includes(u.toLowerCase())))??[],Y=[...l!=null&&l.parent&&!u?[{type:"parent",path:l.parent,name:".."}]:[],...V.map(R=>({type:"directory",path:R.path,name:R.name}))],$=R=>{i(`/p/${R}`),r()},F=(R,D)=>{D.stopPropagation(),N(R)},B=()=>{A&&(b(A.id),N(null))},q=R=>{const D=R.split("/").filter(Boolean).pop()??"";k(D,R),C(),v(R)};P.useEffect(()=>{if(y){const R=S.find(D=>D.workdir===y);R&&(i(`/p/${R.id}`),r(),v(null))}},[S,y,i,r]),P.useEffect(()=>{j(Y.length>0?0:-1)},[u,Y.length]);const X=R=>{p(""),z(R)},J=P.useCallback(R=>{if(!e)return;if(R.key==="Escape"){r();return}if(!["ArrowDown","ArrowUp","Enter"].includes(R.key))return;const D=document.activeElement;if(!(!D||D.tagName!=="INPUT")){if(R.preventDefault(),R.key==="ArrowDown")j(O=>{const W=O+1;return W>=Y.length?0:W});else if(R.key==="ArrowUp")j(O=>{const W=O-1;return W<0?Y.length-1:W});else if(R.key==="Enter"&&_>=0&&_<Y.length){const O=Y[_];(O==null?void 0:O.type)==="parent"?X(O.path):O&&q(O.path)}}},[e,Y.length,_,X,q,r]);return P.useEffect(()=>{if(e)return document.addEventListener("keydown",J),()=>document.removeEventListener("keydown",J)},[e,J]),P.useEffect(()=>{_>=0&&I.current[_]&&I.current[_].scrollIntoView({behavior:"smooth",block:"nearest"})},[_]),e?o.jsxs("div",{className:"fixed inset-0 z-50 flex items-center justify-center p-4 bg-black/50",children:[o.jsxs("div",{className:"bg-bg-secondary border border-border rounded-lg w-full max-w-[90vw] md:max-w-4xl max-h-[90vh] flex flex-col",children:[o.jsxs("div",{className:"p-4 border-b border-border flex items-center justify-between",children:[o.jsx("h2",{className:"text-lg font-semibold text-text-primary",children:"Open Project"}),o.jsx("button",{onClick:r,className:"p-1 rounded hover:bg-bg-tertiary text-text-muted hover:text-text-primary transition-colors",children:o.jsx("svg",{className:"w-5 h-5",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M6 18L18 6M6 6l12 12"})})})]}),o.jsxs("div",{className:"flex-1 flex overflow-hidden min-h-[400px]",children:[o.jsxs("div",{className:"w-1/2 border-r border-border flex flex-col",children:[o.jsx("div",{className:"p-3 border-b border-border bg-bg-tertiary/30",children:o.jsx("h3",{className:"font-medium text-sm text-text-secondary",children:"Recent Projects"})}),o.jsx("div",{className:"flex-1 overflow-y-auto",children:S.length===0?o.jsx("div",{className:"p-4 text-center text-text-muted text-sm",children:"No recent projects"}):o.jsx("div",{className:"divide-y divide-border",children:S.map(R=>o.jsxs("div",{className:"group flex items-center gap-3 p-3 hover:bg-bg-tertiary/50 transition-colors",children:[o.jsxs("button",{onClick:()=>$(R.id),className:"flex-1 flex items-center gap-3 text-left",children:[o.jsx("svg",{className:"w-5 h-5 text-accent-primary",fill:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{d:"M10 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V8c0-1.1-.9-2-2-2h-8l-2-2z"})}),o.jsxs("div",{className:"flex-1 min-w-0",children:[o.jsx("div",{className:"font-medium truncate",children:R.name}),o.jsx("div",{className:"text-xs text-text-muted truncate",children:R.workdir})]})]}),o.jsx("button",{onClick:D=>F(R,D),className:"opacity-0 group-hover:opacity-100 text-accent-error/70 hover:text-accent-error p-1 transition-opacity",title:"Delete project",children:o.jsx("svg",{className:"w-4 h-4",fill:"none",stroke:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M6 18L18 6M6 6l12 12"})})})]},R.id))})})]}),o.jsxs("div",{className:"w-1/2 flex flex-col",children:[o.jsxs("div",{className:"p-3 border-b border-border bg-bg-tertiary/30 flex items-center justify-between",children:[o.jsx("h3",{className:"font-medium text-sm text-text-secondary",children:"Browse Projects"}),o.jsx("button",{onClick:()=>T(!0),className:"text-xs text-accent-primary hover:underline",children:"Open in dialog"})]}),o.jsx("div",{className:"p-3 border-b border-border",children:o.jsx(Pl,{value:u,onChange:R=>p(R.target.value),placeholder:"Filter directories...",className:"w-full"})}),o.jsx("div",{className:"flex-1 overflow-y-auto",children:d?o.jsx("div",{className:"p-8 text-center text-text-muted",children:o.jsx("div",{className:"animate-spin w-5 h-5 border-2 border-accent-primary border-t-transparent rounded-full mx-auto"})}):Y.length===0?o.jsx("div",{className:"p-8 text-center text-text-muted text-sm",children:u?"No matching directories":"No subdirectories"}):o.jsx("div",{className:"divide-y divide-border",children:Y.map((R,D)=>o.jsxs("button",{ref:O=>{I.current[D]=O},onClick:()=>R.type==="parent"?X(R.path):q(R.path),className:`w-full p-3 flex items-center gap-3 text-left transition-colors ${D===_?"bg-accent-primary/20 text-accent-primary":"hover:bg-bg-tertiary/50"}`,children:[o.jsx("svg",{className:"w-5 h-5",fill:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{d:"M10 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V8c0-1.1-.9-2-2-2h-8l-2-2z"})}),o.jsx("span",{className:"flex-1",children:R.name})]},R.path))})})]})]}),o.jsxs("div",{className:"p-4 border-t border-border flex justify-between gap-2",children:[o.jsx(dt,{variant:"secondary",onClick:()=>c(!0),children:"Create Project"}),o.jsx(dt,{variant:"secondary",onClick:r,children:"Cancel"})]})]}),s&&o.jsx(US,{isOpen:s,onClose:()=>c(!1)}),A&&o.jsx(PS,{isOpen:!0,onClose:()=>N(null),projectName:A.name,onConfirm:B}),L&&o.jsx(fb,{initialPath:m??void 0,onSelect:R=>{q(R),T(!1)},onClose:()=>T(!1)})]}):null}function GS(){const[e,r]=P.useState(!1),i=Ee(g=>g.sessions),s=Ut(g=>g.projects),c=Ut(g=>g.listProjects),u=Ee(g=>g.listSessions),p=Ee(g=>g.connectionStatus);P.useEffect(()=>{p==="connected"&&(c(),u())},[p,c,u]);const l=[...s].sort((g,m)=>{const x=i.filter(b=>b.workdir.startsWith(g.workdir)),S=i.filter(b=>b.workdir.startsWith(m.workdir)),k=x.length>0?new Date(x.reduce((b,y)=>new Date(y.updatedAt)>new Date(b.updatedAt)?y:b).updatedAt).getTime():new Date(g.updatedAt).getTime();return(S.length>0?new Date(S.reduce((b,y)=>new Date(y.updatedAt)>new Date(b.updatedAt)?y:b).updatedAt).getTime():new Date(m.updatedAt).getTime())-k}),f=g=>{const m=s.find(x=>x.id===g);return m?i.filter(x=>x.workdir.startsWith(m.workdir)).sort((x,S)=>new Date(S.updatedAt).getTime()-new Date(x.updatedAt).getTime()).slice(0,5):[]},d=()=>{r(!0)};return o.jsxs("div",{className:"flex-1 flex flex-col overflow-y-auto",children:[o.jsxs("div",{className:"max-w-5xl mx-auto w-full p-4 md:p-8",children:[o.jsxs("div",{className:"mb-6 md:mb-8 flex items-center justify-between",children:[o.jsxs("div",{children:[o.jsx("h1",{className:"text-3xl font-bold text-accent-primary",children:"OpenFox"}),o.jsx("p",{className:"text-text-secondary",children:"Local LLM-powered coding assistant with contract-driven execution"})]}),o.jsx(dt,{variant:"primary",onClick:d,children:"Open Project"})]}),l.map(g=>{const m=f(g.id);return o.jsx("div",{className:"mb-6 md:mb-8",children:o.jsxs("div",{className:"bg-bg-secondary border border-border rounded-lg overflow-hidden",children:[o.jsxs("div",{className:"p-3 md:p-4 border-b border-border flex items-center justify-between gap-2",children:[o.jsxs(An,{href:`/p/${g.id}`,className:"flex items-center gap-2 cursor-pointer hover:opacity-80 transition-opacity flex-1",children:[o.jsx("svg",{className:"w-5 h-5 text-accent-primary flex-shrink-0",fill:"currentColor",viewBox:"0 0 24 24",children:o.jsx("path",{d:"M10 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V8c0-1.1-.9-2-2-2h-8l-2-2z"})}),o.jsx("span",{className:"text-text-primary font-semibold",children:g.name})]}),o.jsx(An,{href:`/p/${g.id}/new`,className:"rounded font-medium transition-colors bg-accent-primary/25 text-white hover:bg-accent-primary/40 px-1.5 py-1 text-xs",children:"+ New Session"})]}),o.jsx("div",{className:"divide-y divide-border",children:m.length>0?m.map(x=>{const S=s.find(C=>x.workdir.startsWith(C.workdir)),k=S?`/p/${S.id}/s/${x.id}`:"#";return o.jsx(An,{href:k,className:"block p-3 md:p-4 hover:bg-bg-tertiary/50 cursor-pointer transition-colors",children:o.jsxs("div",{className:"flex items-center justify-between gap-2",children:[o.jsx("div",{className:"flex items-center gap-3 flex-1 min-w-0",children:o.jsx("div",{className:"flex-1 min-w-0",children:o.jsx("div",{className:"text-sm text-text-muted truncate",children:x.title??x.id.slice(0,8)})})}),o.jsxs("div",{className:"flex items-center gap-2 flex-shrink-0",children:[o.jsx("span",{className:"text-text-muted text-xs",children:AS(x.updatedAt)}),o.jsxs("span",{className:"text-text-muted text-xs",children:[x.messageCount," msgs"]})]})]})},x.id)}):o.jsx("div",{className:"p-3 md:p-4 text-text-muted text-sm",children:"No sessions yet"})})]})},g.id)}),l.length===0&&o.jsx("div",{className:"text-center py-12 text-text-muted",children:"No projects yet. Open a project to get started."})]}),e&&o.jsx(WS,{isOpen:e,onClose:()=>r(!1)})]})}function VS(){const[,e]=mh("/p/:projectId/new"),[,r]=ar(),i=e==null?void 0:e.projectId,s=Ee(c=>c.createSession);return P.useEffect(()=>{i&&(async()=>{const u=await s(i);r(u?`/p/${i}/s/${u.id}`:`/p/${i}`)})()},[i,s,r]),o.jsx("div",{className:"flex-1 flex items-center justify-center",children:o.jsx(Fl,{})})}function YS(){const e=Ut(r=>r.currentProject);return o.jsx("div",{className:"h-full flex flex-col items-center justify-center p-8 text-center",children:o.jsxs("div",{className:"max-w-md",children:[o.jsx("h2",{className:"text-xl font-semibold text-text-primary mb-2",children:(e==null?void 0:e.name)??"Project"}),o.jsx("p",{className:"text-text-secondary mb-6",children:"No session selected"}),o.jsxs("div",{className:"flex flex-col gap-3",children:[e&&o.jsx(An,{href:`/p/${e.id}/new`,className:"block w-full rounded font-medium transition-colors bg-accent-primary/25 text-white hover:bg-accent-primary/40 px-3 py-2 text-center",children:"Create New Session"}),o.jsx("p",{className:"text-sm text-text-muted",children:"Or select an existing session from the sidebar"})]})]})})}const Ta=e=>Math.round(e*10)/10;function Xd(e){return{providerId:e.providerId,providerName:e.providerName,backend:e.backend,model:e.model}}function KS(e){return`${e.providerId}::${e.model}`}function XS(e){return`${e.providerName} > ${e.model}`}function kx(e){let r=0,i=0,s=0,c=0,u=0,p=0;const l=[],f=[];let d=0;for(const[x,S]of e.entries()){const k=S.stats,C=Xd(k);r+=k.totalTime,i+=k.toolTime,s+=k.prefillTokens,c+=k.generationTokens;const b=k.prefillSpeed>0?k.prefillTokens/k.prefillSpeed:0,y=k.generationSpeed>0?k.generationTokens/k.generationSpeed:0;u+=b,p+=y,l.push({messageId:S.id,timestamp:S.timestamp,...C,mode:k.mode,responseIndex:x+1,prefillTokens:k.prefillTokens,generationTokens:k.generationTokens,prefillSpeed:k.prefillSpeed,generationSpeed:k.generationSpeed,totalTime:k.totalTime,aiTime:k.totalTime-k.toolTime,toolTime:k.toolTime});const v=k.llmCalls??[];for(const _ of v)d+=1,f.push({messageId:S.id,timestamp:_.timestamp??S.timestamp,providerId:_.providerId,providerName:_.providerName,backend:_.backend,model:_.model,mode:k.mode,responseIndex:x+1,sessionCallIndex:d,callIndex:_.callIndex,promptTokens:_.promptTokens,completionTokens:_.completionTokens,ttft:_.ttft,completionTime:_.completionTime,prefillSpeed:_.prefillSpeed,generationSpeed:_.generationSpeed,totalTime:_.totalTime})}const g=u>0?Ta(s/u):0,m=p>0?Ta(c/p):0;return{totalTime:Ta(r),aiTime:Ta(r-i),toolTime:Ta(i),prefillTokens:s,generationTokens:c,avgPrefillSpeed:g,avgGenerationSpeed:m,responseCount:e.length,llmCallCount:f.length,dataPoints:l,callDataPoints:f}}function ZS(e){const r=e.filter(c=>c.stats!==void 0&&c.stats!==null).sort((c,u)=>new Date(c.timestamp).getTime()-new Date(u.timestamp).getTime());if(r.length===0)return null;const i=new Map;for(const c of r){const u=KS(Xd(c.stats)),p=i.get(u)??[];i.set(u,[...p,c])}const s=Array.from(i.entries()).map(([c,u])=>{const p=Xd(u[0].stats),l=kx(u);return{...p,key:c,label:XS(p),...l}});return{...kx(r),modelGroups:s}}function QS(e){return P.useMemo(()=>ZS(e),[e])}function JS(e){const[r,i]=P.useState(null),[s,c]=P.useState(!0),[u,p]=P.useState(null),l=e||"";return P.useEffect(()=>{if(!l){c(!1);return}let f=!0,d=null;const g=async()=>{try{const x=await(await ye(`/api/branch?workdir=${encodeURIComponent(l)}`)).json();f&&(i(x.branch),p(x.error||null),c(!1))}catch(m){f&&(p(m instanceof Error?m.message:"Failed to fetch branch"),c(!1))}};return g(),d=setInterval(g,3e3),()=>{f=!1,d&&clearInterval(d)}},[l]),{branch:r,loading:s,error:u}}function Tl(e){return e.toLocaleString("en-US").replace(/,/g," ")}function Ex(e){return e>=1e3?`${(e/1e3).toFixed(1)}k`:e.toFixed(1)}function ew(e){if(e<60)return`${e.toFixed(1)}s`;const r=Math.floor(e/60),i=Math.round(e%60);return`${r}m${i}s`}const tw="modulepreload",nw=function(e){return"/"+e},jx={},rw=function(r,i,s){let c=Promise.resolve();if(i&&i.length>0){let p=function(d){return Promise.all(d.map(g=>Promise.resolve(g).then(m=>({status:"fulfilled",value:m}),m=>({status:"rejected",reason:m}))))};document.getElementsByTagName("link");const l=document.querySelector("meta[property=csp-nonce]"),f=(l==null?void 0:l.nonce)||(l==null?void 0:l.getAttribute("nonce"));c=p(i.map(d=>{if(d=nw(d),d in jx)return;jx[d]=!0;const g=d.endsWith(".css"),m=g?'[rel="stylesheet"]':"";if(document.querySelector(`link[href="${d}"]${m}`))return;const x=document.createElement("link");if(x.rel=g?"stylesheet":tw,g||(x.as="script"),x.crossOrigin="",x.href=d,f&&x.setAttribute("nonce",f),document.head.appendChild(x),g)return new Promise((S,k)=>{x.addEventListener("load",S),x.addEventListener("error",()=>k(new Error(`Unable to preload CSS for ${d}`)))})}))}function u(p){const l=new Event("vite:preloadError",{cancelable:!0});if(l.payload=p,window.dispatchEvent(l),!l.defaultPrevented)throw p}return c.then(p=>{for(const l of p||[])l.status==="rejected"&&u(l.reason);return r().catch(u)})},Nx=["▁","▂","▃","▄","▅","▆","▇","█"];function iw(e,r,i){if(i===r)return 4;const s=(e-r)/(i-r);return Math.min(7,Math.max(0,Math.round(s*7)))}function sw(e,r){if(e===r){const c=Math.max(Math.abs(e)*.05,1);return{minY:e-c,maxY:r+c}}const i=r-e,s=Math.max(i*.1,.1);return{minY:e-s,maxY:r+s}}function aw(e,r){if(e.length===0||r<=0)return{blocks:"",minX:0,maxX:0,minY:0,maxY:0};const i=[...e].sort((m,x)=>m.x-x.x),s=i[0].x,c=i[i.length-1].x,u=Math.min(...i.map(m=>m.y)),p=Math.max(...i.map(m=>m.y)),{minY:l,maxY:f}=sw(u,p),d=Array.from({length:r},()=>" "),g=new Map;for(const m of i){const x=c===s?0:Math.round((m.x-s)/(c-s)*(r-1)),S=g.get(x)??[];g.set(x,[...S,m.y])}for(const[m,x]of g){const S=Math.max(...x);d[m]=Nx[iw(S,l,f)]??Nx[0]}return{blocks:d.join(""),minX:s,maxX:c,minY:l,maxY:f}}function Tx(e){return e>=1e6?`${(e/1e6).toFixed(1)}M`:e>=1e3?`${(e/1e3).toFixed(1)}k`:e.toFixed(1)}function Ax({data:e,width:r=60,height:i=78,label:s,xLabel:c,yLabel:u,showAxes:p=!0,formatY:l=Tx,formatX:f=Tx}){const d=P.useMemo(()=>{const g=aw(e,r),m=Math.max(r*6,240),x=10,S=8,C=[...e].sort((_,j)=>_.x-j.x).map(_=>{const j=g.maxX===g.minX?m/2:x+(_.x-g.minX)/(g.maxX-g.minX)*(m-x*2),A=g.maxY===g.minY?i/2:S+(g.maxY-_.y)/(g.maxY-g.minY)*(i-S*2);return{..._,cx:j,cy:A,leftPercent:j/m*100,topPercent:A/i*100}}),b=C.map((_,j)=>`${j===0?"M":"L"} ${_.cx.toFixed(1)} ${_.cy.toFixed(1)}`).join(" "),v=[g.maxY,(g.maxY+g.minY)/2,g.minY].map(_=>({value:_,y:g.maxY===g.minY?i/2:S+(g.maxY-_)/(g.maxY-g.minY)*(i-S*2)}));return{...g,chartWidth:m,points:C,path:b,gridLines:v}},[e,i,r]);return e.length===0?o.jsxs("div",{className:"font-mono text-text-muted text-xs",children:[s&&o.jsx("div",{className:"mb-1",children:s}),o.jsx("div",{children:"No data"})]}):o.jsxs("div",{className:"font-mono text-xs",children:[s&&o.jsx("div",{className:"text-text-secondary mb-2",children:s}),o.jsxs("div",{className:"flex gap-3",children:[p&&o.jsx("div",{className:"w-12 h-[78px] flex flex-col justify-between text-right text-text-muted",children:d.gridLines.map(g=>o.jsx("span",{children:l(g.value)},`${g.value}-${g.y}`))}),o.jsx("div",{className:"flex-1 min-w-0",children:o.jsxs("div",{className:"relative h-[78px]",children:[o.jsxs("svg",{viewBox:`0 0 ${d.chartWidth} ${i}`,className:"w-full h-[78px] overflow-visible",preserveAspectRatio:"none","aria-hidden":"true",children:[d.gridLines.map(g=>o.jsx("line",{x1:"0",x2:d.chartWidth,y1:g.y,y2:g.y,stroke:"currentColor",strokeDasharray:"3 4",className:"text-border/60"},`grid-${g.y}`)),d.points.map(g=>o.jsx("line",{x1:g.cx,x2:g.cx,y1:i-4,y2:g.cy,stroke:"currentColor",className:"text-border/40"},`guide-${g.cx}-${g.cy}`)),d.points.length>1&&o.jsx("path",{d:d.path,fill:"none",stroke:"currentColor",strokeWidth:"2",strokeLinecap:"round",strokeLinejoin:"round",className:"text-accent-primary/45"})]}),d.points.map(g=>o.jsx("div",{className:"absolute -translate-x-1/2 -translate-y-1/2",style:{left:`${g.leftPercent}%`,top:`${g.topPercent}%`},title:`${f(g.x)} -> ${l(g.y)}`,children:o.jsx("div",{className:"w-2.5 h-2.5 rounded-full bg-accent-primary/20 flex items-center justify-center",children:o.jsx("div",{className:"w-1.5 h-1.5 rounded-full bg-accent-primary"})})},`point-${g.x}-${g.y}`))]})})]}),p&&o.jsxs("div",{className:"flex items-start gap-3 text-text-muted mt-1",children:[o.jsx("span",{className:"w-12"}),o.jsxs("span",{className:"flex-1 flex justify-between",children:[o.jsx("span",{children:f(d.minX)}),o.jsx("span",{children:c}),o.jsx("span",{children:f(d.maxX)})]})]}),u&&p&&o.jsx("div",{className:"text-text-muted mt-1 text-center",children:u})]})}function ow({data:e,prefillLabel:r="Prefill Speed (tok/s) by Response",generationLabel:i="Generation Speed (tok/s) by Response",xLabel:s="response",width:c=60}){const u=e.map(l=>({x:l.x,y:l.ppSpeed})),p=e.map(l=>({x:l.x,y:l.tgSpeed}));return o.jsxs("div",{className:"space-y-5",children:[o.jsx(Ax,{data:u,width:c,label:r,xLabel:s}),o.jsx(Ax,{data:p,width:c,label:i,xLabel:s})]})}function lw(e){const r=new Map;for(const i of e.callDataPoints){const s=r.get(i.messageId)??[];r.set(i.messageId,[...s,i])}return e.dataPoints.map(i=>{const s=[...r.get(i.messageId)??[]].sort((c,u)=>c.callIndex-u.callIndex);return{...i,callCount:s.length,calls:s,isExpandable:s.length>1}})}function cw(e){return{mode:"responses",xLabel:"response",prefillLabel:"Prefill Speed (tok/s) by Response",generationLabel:"Generation Speed (tok/s) by Response",points:e.dataPoints.map(r=>({x:r.responseIndex,ppSpeed:r.prefillSpeed,tgSpeed:r.generationSpeed}))}}function uw(e){return{mode:"calls",xLabel:"context",prefillLabel:"Prefill Speed (tok/s) vs Context",generationLabel:"Generation Speed (tok/s) vs Context",points:e.callDataPoints.map(r=>({x:r.promptTokens,ppSpeed:r.prefillSpeed,tgSpeed:r.generationSpeed}))}}function dw(e){return e.callDataPoints.length>0?uw(e):cw(e)}function kd(e){if(e<60)return`${e.toFixed(1)}s`;const r=Math.floor(e/60),i=e%60;return`${r}m ${i.toFixed(0)}s`}function Ni(e){return e>=1e6?`${(e/1e6).toFixed(1)}M`:e>=1e3?`${(e/1e3).toFixed(1)}k`:e.toString()}function Ia(e){return e>=1e3?`${(e/1e3).toFixed(1)}k`:e.toFixed(1)}function hw(e){if(e.length===0)return"0 ctx";const r=Math.min(...e),i=Math.max(...e);return r===i?`${Ni(r)} ctx`:`${Ni(r)}-${Ni(i)} ctx`}function Al(e){return`${Ia(e)} t/s`}function pb(e){try{return new Date(e).toLocaleTimeString("en-US",{hour12:!1})}catch{return e}}function fw(e){return{exportedAt:new Date().toISOString(),providerId:e.providerId,providerName:e.providerName,backend:e.backend,model:e.model,label:e.label,summary:{totalTime:e.totalTime,aiTime:e.aiTime,toolTime:e.toolTime,prefillTokens:e.prefillTokens,generationTokens:e.generationTokens,avgPrefillSpeed:e.avgPrefillSpeed,avgGenerationSpeed:e.avgGenerationSpeed,responseCount:e.responseCount,llmCallCount:e.llmCallCount},responses:e.dataPoints.map(r=>({responseIndex:r.responseIndex,timestamp:r.timestamp,mode:r.mode,prefillTokens:r.prefillTokens,generationTokens:r.generationTokens,prefillSpeed:r.prefillSpeed,generationSpeed:r.generationSpeed,totalTime:r.totalTime,aiTime:r.aiTime,toolTime:r.toolTime})),llmCalls:e.callDataPoints.map(r=>({sessionCallIndex:r.sessionCallIndex,responseIndex:r.responseIndex,callIndex:r.callIndex,timestamp:r.timestamp,mode:r.mode,promptTokens:r.promptTokens,completionTokens:r.completionTokens,ttft:r.ttft,completionTime:r.completionTime,prefillSpeed:r.prefillSpeed,generationSpeed:r.generationSpeed,totalTime:r.totalTime}))}}function pw({isOpen:e,onClose:r,stats:i}){const s=P.useRef(null),[c,u]=P.useState({}),[p,l]=P.useState(()=>{var k;return((k=i.modelGroups[0])==null?void 0:k.key)??""});P.useEffect(()=>{var k;i.modelGroups.some(C=>C.key===p)||l(((k=i.modelGroups[0])==null?void 0:k.key)??"")},[p,i.modelGroups]);const f=P.useMemo(()=>i.modelGroups.find(k=>k.key===p)??i.modelGroups[0],[p,i.modelGroups]),d=P.useMemo(()=>f?lw(f):[],[f]),g=P.useMemo(()=>f?dw(f):{mode:"responses",xLabel:"response",prefillLabel:"",generationLabel:"",points:[]},[f]),m=P.useCallback(k=>{u(C=>({...C,[k]:!C[k]}))},[]),x=P.useCallback(()=>{if(!f)return;const k=fw(f);navigator.clipboard.writeText(JSON.stringify(k,null,2)).catch(C=>console.error("Failed to copy:",C))},[f]),S=P.useCallback(async()=>{if(s.current)try{const k=(await rw(async()=>{const{default:y}=await import("./html2canvas.esm-QH1iLAAe.js");return{default:y}},[])).default,C=await k(s.current,{backgroundColor:"#1a1a1a",scale:2}),b=document.createElement("a");b.download=`openfox-stats-${new Date().toISOString().slice(0,10)}.png`,b.href=C.toDataURL("image/png"),b.click()}catch(k){console.error("Failed to export PNG:",k),x()}},[x]);return o.jsx(un,{isOpen:e,onClose:r,title:"Session Stats",size:"lg",children:o.jsxs("div",{ref:s,className:"space-y-6",children:[o.jsx("section",{children:o.jsx("div",{className:"flex flex-wrap gap-2",children:i.modelGroups.map(k=>o.jsx("button",{onClick:()=>l(k.key),className:`px-3 py-1.5 rounded border text-xs transition-colors ${k.key===(f==null?void 0:f.key)?"border-accent-primary bg-accent-primary/10 text-accent-primary":"border-border text-text-muted hover:text-text-primary hover:bg-bg-tertiary/40"}`,title:k.label,children:k.label},k.key))})}),f&&o.jsxs("section",{children:[o.jsx("h3",{className:"text-sm font-semibold text-text-secondary mb-3 uppercase tracking-wide",children:"Summary"}),o.jsxs("div",{className:"grid grid-cols-2 md:grid-cols-5 gap-4",children:[o.jsx(Er,{label:"AI Time",value:kd(f.aiTime)}),o.jsx(Er,{label:"Total Time",value:kd(f.totalTime)}),o.jsx(Er,{label:"Tool Time",value:kd(f.toolTime)}),o.jsx(Er,{label:"Responses",value:f.responseCount.toString()}),o.jsx(Er,{label:"LLM Calls",value:f.llmCallCount.toString()})]}),o.jsxs("div",{className:"grid grid-cols-2 md:grid-cols-4 gap-4 mt-3",children:[o.jsx(Er,{label:"Prefill Tokens",value:Ni(f.prefillTokens),subValue:`@ ${Ia(f.avgPrefillSpeed)} tok/s`}),o.jsx(Er,{label:"Gen Tokens",value:Ni(f.generationTokens),subValue:`@ ${Ia(f.avgGenerationSpeed)} tok/s`}),o.jsx(Er,{label:"Avg PP Speed",value:`${Ia(f.avgPrefillSpeed)}`,subValue:"tok/s"}),o.jsx(Er,{label:"Avg TG Speed",value:`${Ia(f.avgGenerationSpeed)}`,subValue:"tok/s"})]})]}),f&&g.points.length>1&&o.jsxs("section",{children:[o.jsxs("div",{className:"flex items-center justify-between mb-3",children:[o.jsx("h3",{className:"text-sm font-semibold text-text-secondary uppercase tracking-wide",children:"Performance Progression"}),o.jsxs("div",{className:"flex items-center gap-2",children:[o.jsx("button",{onClick:x,className:"px-2 py-1 text-xs text-text-muted hover:text-text-primary hover:bg-bg-tertiary rounded transition-colors",children:"Copy JSON"}),o.jsx("button",{onClick:S,className:"px-2 py-1 text-xs text-text-muted hover:text-text-primary hover:bg-bg-tertiary rounded transition-colors",children:"Save PNG"})]})]}),o.jsx("div",{className:"bg-bg-tertiary/50 rounded p-4",children:o.jsx(ow,{data:g.points,width:50,prefillLabel:g.prefillLabel,generationLabel:g.generationLabel,xLabel:g.xLabel})})]}),f&&o.jsxs("section",{children:[o.jsxs("h3",{className:"text-sm font-semibold text-text-secondary mb-3 uppercase tracking-wide",children:["Response Log (",f.responseCount," responses)"]}),o.jsx("div",{className:"overflow-y-auto bg-bg-tertiary/30 rounded",children:o.jsxs("table",{className:"w-full table-fixed border-separate border-spacing-0 text-xs",children:[o.jsxs("colgroup",{children:[o.jsx("col",{className:"w-[7%]"}),o.jsx("col",{className:"w-[14%]"}),o.jsx("col",{className:"w-[10%]"}),o.jsx("col",{className:"w-[14%]"}),o.jsx("col",{className:"w-[14%]"}),o.jsx("col",{className:"w-[14%]"}),o.jsx("col",{className:"w-[11%]"}),o.jsx("col",{className:"w-[2%]"})]}),o.jsx("thead",{children:o.jsxs("tr",{className:"text-[10px] uppercase tracking-wide text-text-muted/80",children:[o.jsx("th",{className:"px-3 py-2 text-center font-medium",children:"#"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"At"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"Time"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"Context"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"PP t/s"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"TG t/s"}),o.jsx("th",{className:"px-2 py-2 text-center font-medium",children:"Calls"}),o.jsx("th",{className:"px-2 py-2"})]})}),o.jsx("tbody",{children:d.map((k,C)=>o.jsxs(P.Fragment,{children:[o.jsx(mw,{row:k,index:C,isExpanded:c[k.messageId]??!1,onToggle:k.isExpandable?()=>m(k.messageId):void 0}),(c[k.messageId]??!1)&&k.calls.map((b,y)=>o.jsx(gw,{dataPoint:b,index:y},`${b.messageId}-${b.callIndex}`))]},k.messageId))})]})})]})]})})}function Er({label:e,value:r,subValue:i}){return o.jsxs("div",{className:"bg-bg-tertiary/50 rounded p-3",children:[o.jsx("div",{className:"text-text-muted text-xs mb-1",children:e}),o.jsx("div",{className:"text-text-primary text-lg font-semibold",children:r}),i&&o.jsx("div",{className:"text-text-muted text-xs",children:i})]})}function mw({row:e,index:r,isExpanded:i,onToggle:s}){const c=e.calls.length>0?hw(e.calls.map(u=>u.promptTokens)):`${Ni(e.prefillTokens)} ctx`;return o.jsxs("tr",{onClick:s,className:`${r%2===0?"bg-bg-tertiary/20":""} ${s?"cursor-pointer hover:bg-bg-tertiary/35 transition-colors":""}`,children:[o.jsx("td",{className:"px-3 py-2 text-center text-text-muted align-middle",children:e.responseIndex}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted font-mono align-middle whitespace-nowrap",children:pb(e.timestamp)}),o.jsxs("td",{className:"px-2 py-2 text-center text-text-muted align-middle whitespace-nowrap",children:[e.totalTime.toFixed(1),"s"]}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:c.replace(/ ctx$/,"")}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Al(e.prefillSpeed)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Al(e.generationSpeed)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted font-mono align-middle whitespace-nowrap",children:e.callCount}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted align-middle whitespace-nowrap",children:e.isExpandable?i?"v":">":""})]})}function gw({dataPoint:e,index:r}){return o.jsxs("tr",{className:`${r%2===0?"bg-bg-tertiary/10":"bg-bg-tertiary/5"}`,children:[o.jsxs("td",{className:"px-3 py-2 pl-6 text-center text-text-muted align-middle border-l border-border/60",children:["c",e.callIndex]}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted font-mono align-middle whitespace-nowrap",children:pb(e.timestamp)}),o.jsxs("td",{className:"px-2 py-2 text-center text-text-muted align-middle whitespace-nowrap",children:[e.totalTime.toFixed(1),"s"]}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Ni(e.promptTokens)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Al(e.prefillSpeed)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-primary font-mono align-middle whitespace-nowrap",children:Al(e.generationSpeed)}),o.jsx("td",{className:"px-2 py-2 text-center text-text-muted font-mono align-middle whitespace-nowrap",children:e.callIndex}),o.jsx("td",{className:"px-2 py-2"})]})}const xw={pending:{icon:"○",color:"text-text-muted",label:"Pending"},in_progress:{icon:"●",color:"text-accent-warning",label:"In Progress",animate:!0},completed:{icon:"◉",color:"text-purple-400",label:"Completed"},passed:{icon:"✓",color:"text-accent-success",label:"Passed"},failed:{icon:"✗",color:"text-accent-error",label:"Failed"}},vw=P.memo(function({criteria:r}){if(r.length===0)return o.jsx("div",{className:"text-text-muted text-sm text-center py-2",children:"No criteria yet"});const i={pending:0,in_progress:0,completed:0,passed:0,failed:0};for(const c of r){const u=c.status.type;u in i&&i[u]++}const s=Object.keys(i).filter(c=>i[c]>0);return o.jsxs("div",{className:"space-y-1",children:[o.jsxs("div",{className:"flex items-center gap-2 text-sm",children:[o.jsx("span",{className:"font-semibold text-text-primary",children:"Total:"}),o.jsx("span",{className:"text-text-secondary",children:r.length})]}),o.jsx("div",{className:"space-y-1",children:s.map(c=>{const u=xw[c];return o.jsxs("div",{className:"flex items-center gap-2 text-sm",children:[o.jsx("span",{className:`${u.color} ${u.animate?"animate-pulse":""} text-sm leading-tight`,children:u.icon}),o.jsxs("span",{className:"text-text-muted",children:[u.label,":"]}),o.jsx("span",{className:"text-text-primary font-medium",children:i[c]})]},c)})})]})});function bw({isOpen:e,onClose:r}){const i=ir(S=>S.config),s=ir(S=>S.saveConfig),[c,u]=P.useState(""),[p,l]=P.useState(""),[f,d]=P.useState(!1),[g,m]=P.useState(!1);P.useEffect(()=>{e&&(u((i==null?void 0:i.command)??""),l((i==null?void 0:i.url)??""),d((i==null?void 0:i.hotReload)??!1))},[e,i]);const x=async()=>{!c.trim()||!p.trim()||(m(!0),await s({command:c.trim(),url:p.trim(),hotReload:f}),m(!1),r())};return o.jsx(un,{isOpen:e,onClose:r,title:"Dev Server Config",size:"sm",children:o.jsxs("div",{className:"space-y-4",children:[o.jsxs("div",{children:[o.jsx("label",{className:"block text-xs text-text-secondary mb-1",children:"Command"}),o.jsx("input",{className:"input w-full",type:"text",value:c,onChange:S=>u(S.target.value),placeholder:"npm run dev"})]}),o.jsxs("div",{children:[o.jsx("label",{className:"block text-xs text-text-secondary mb-1",children:"Dev URL"}),o.jsx("input",{className:"input w-full",type:"text",value:p,onChange:S=>l(S.target.value),placeholder:"http://localhost:3000"})]}),o.jsxs("div",{className:"flex items-center gap-2",children:[o.jsx("input",{type:"checkbox",id:"hotReload",checked:f,onChange:S=>d(S.target.checked),className:"rounded border-border bg-bg-tertiary"}),o.jsx("label",{htmlFor:"hotReload",className:"text-xs text-text-secondary",children:"Hot Reload"})]}),o.jsxs("div",{className:"flex justify-end gap-2 pt-2",children:[o.jsx("button",{className:"btn btn-secondary",onClick:r,children:"Cancel"}),o.jsx("button",{className:"btn btn-primary",onClick:x,disabled:g||!c.trim()||!p.trim(),children:g?"Saving...":"Save"})]})]})})}const Dx={30:"text-black",31:"text-red-400",32:"text-accent-success",33:"text-accent-warning",34:"text-blue-400",35:"text-purple-400",36:"text-cyan-400",37:"text-gray-300",90:"text-gray-500",91:"text-red-500",92:"text-green-500",93:"text-yellow-400",94:"text-blue-500",95:"text-pink-400",96:"text-cyan-500",97:"text-white"},yw={40:"bg-black",41:"bg-red-900",42:"bg-green-900",43:"bg-yellow-900",44:"bg-blue-900",45:"bg-purple-900",46:"bg-cyan-900",47:"bg-gray-700"},Lx={1:"font-bold",2:"opacity-75",4:"underline",7:"bg-bg-secondary"},_w="text-text-primary";function Sw(e){const r=[],i=/\x1b\[([0-9;]+)m/g;let s=0,c="text-text-primary",u;try{for(;(u=i.exec(e))!==null;){if(u.index>s){const d=e.slice(s,u.index);d&&r.push({text:d,className:c})}const p=u[1];if(!p)continue;const l=p.split(";").map(Number);if(l.length===0||l[0]===0){c="text-text-primary";continue}const f=[];for(const d of l)if(d>=30&&d<=37){const g=Dx[d];g&&f.push(g)}else if(d>=40&&d<=47){const g=yw[d];g&&f.push(g)}else if(d>=90&&d<=97){const g=Dx[d];g&&f.push(g)}else if(d in Lx){const g=Lx[d];g&&f.push(g)}else d===39?f.push(_w):d===49&&(c=c.split(" ").filter(g=>!g.startsWith("bg-")).join(" "));f.length>0&&(c=f.join(" ")),s=i.lastIndex}if(s<e.length){const p=e.slice(s);p&&r.push({text:p,className:c})}return r}catch(p){return console.warn("ANSI parsing failed, stripping codes:",p),[{text:ww(e),className:"text-text-primary"}]}}function ww(e){return e.replace(/\x1b\[([0-9;]+)m/g,"")}function Ns(e){var i,s;const r=Sw(e);return r.length===1&&((i=r[0])==null?void 0:i.className)==="text-text-primary"?(s=r[0])==null?void 0:s.text:r.map((c,u)=>ln.createElement("span",{key:u,className:c.className},c.text))}const Cw=P.memo(function({logs:r,onClose:i}){const s=P.useRef(null);return P.useEffect(()=>{const c=u=>{u.key==="Escape"&&i()};return window.addEventListener("keydown",c),()=>window.removeEventListener("keydown",c)},[i]),P.useEffect(()=>{s.current&&(s.current.scrollTop=s.current.scrollHeight)},[r]),o.jsx("div",{className:"fixed inset-0 z-50 flex items-center justify-center bg-black/60",onClick:i,children:o.jsxs("div",{className:"relative w-[90vw] h-[90vh] bg-bg-primary rounded-lg border border-border flex flex-col",onClick:c=>c.stopPropagation(),children:[o.jsxs("div",{className:"flex items-center justify-between p-3 border-b border-border",children:[o.jsx("h3",{className:"text-sm font-semibold text-text-primary",children:"Dev Server Logs"}),o.jsx("button",{onClick:i,className:"p-1.5 rounded hover:bg-bg-tertiary transition-colors text-text-muted",children:o.jsx("svg",{className:"w-5 h-5",viewBox:"0 0 20 20",fill:"currentColor",children:o.jsx("path",{fillRule:"evenodd",d:"M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z",clipRule:"evenodd"})})})]}),o.jsx("pre",{ref:s,className:"flex-1 overflow-auto p-4 text-sm font-mono text-text-primary",children:r.length===0?o.jsx("span",{className:"text-text-muted",children:"No output yet"}):r.map((c,u)=>o.jsx("span",{className:c.stream==="stderr"?"text-accent-warning":"",children:Ns(c.content)},u))})]})})}),kw=P.memo(function({logs:r,anchorRef:i,isHiding:s,onExpand:c,onClose:u}){const[p,l]=P.useState(null),f=P.useRef(null);return P.useEffect(()=>{var g;const d=(g=i.current)==null?void 0:g.getBoundingClientRect();d&&l({bottom:window.innerHeight-d.bottom,right:window.innerWidth-d.right,width:d.width,height:d.height})},[i]),P.useEffect(()=>{f.current&&(f.current.scrollTop=f.current.scrollHeight)},[r]),p?o.jsxs("div",{className:"relative",children:[o.jsx("pre",{ref:f,className:"fixed z-50 text-sm font-mono text-text-primary bg-bg-primary p-2 rounded border border-border overflow-auto transition-all duration-150 ease-out select-text",style:{bottom:p.bottom,right:p.right,width:p.width*2,maxHeight:p.height*3,transformOrigin:"bottom right",transform:s?"scale(0.01)":"scale(1)",opacity:s?0:1},children:r.map((d,g)=>o.jsx("span",{className:d.stream==="stderr"?"text-accent-warning":"",children:Ns(d.content)},g))}),o.jsx("button",{onClick:()=>{u(),c()},className:"fixed z-50 px-2 py-1 rounded text-xs font-medium bg-accent-primary/30 text-white hover:bg-accent-primary/50 transition-colors duration-150",style:{bottom:p.bottom+8,right:p.right+8},children:"Expand"})]}):null}),Ew=P.memo(function({workdir:r}){const i=ir(z=>z.setWorkdir),s=ir(z=>z.status),c=ir(z=>z.config),u=ir(z=>z.logs),p=ir(z=>z.start),l=ir(z=>z.stop),f=ir(z=>z.fetchLogs),[d,g]=P.useState(!1),[m,x]=P.useState(!1),[S,k]=P.useState(!1),[C,b]=P.useState(!1),y=P.useRef(null),v=P.useRef(null),_=P.useRef(null),j=P.useRef(null),A=(s==null?void 0:s.state)??"off",N=c!==null,L=A==="running"||A==="warning";P.useEffect(()=>{i(r??null)},[r,i]),P.useEffect(()=>{L&&f()},[L,f]),P.useEffect(()=>{_.current&&L&&(_.current.scrollTop=_.current.scrollHeight)},[u,L]);const T=()=>{L?l():p()},I=o.jsx("svg",{className:"w-4 h-4",viewBox:"0 0 16 16",fill:"currentColor",children:o.jsx("path",{d:"M8 0a8.2 8.2 0 0 1 .701.031C9.444.095 9.99.645 10.16 1.29l.288 1.107c.018.066.079.158.212.224.231.114.454.243.668.386.123.082.233.09.299.071l1.1-.303c.652-.18 1.37.008 1.755.653a8.043 8.043 0 0 1 .683 1.18c.227.568.096 1.26-.378 1.726l-.812.804a.312.312 0 0 0-.081.283c.024.166.04.335.04.507s-.016.341-.04.507a.312.312 0 0 0 .08.283l.813.804c.474.466.605 1.158.378 1.726a8.07 8.07 0 0 1-.683 1.18c-.385.645-1.103.833-1.755.653l-1.1-.303c-.066-.019-.176-.011-.299.071a5.1 5.1 0 0 1-.668.386c-.133.066-.194.158-.211.224l-.29 1.107c-.168.645-.714 1.196-1.458 1.26a8.094 8.094 0 0 1-1.402 0c-.744-.064-1.29-.615-1.458-1.26l-.29-1.107a.426.426 0 0 0-.211-.224 5.11 5.11 0 0 1-.668-.386c-.123-.082-.233-.09-.299-.071l-1.1.303c-.652.18-1.37-.008-1.755-.653a8.044 8.044 0 0 1-.683-1.18c-.227-.568-.096-1.26.378-1.726l.812-.804a.312.312 0 0 0 .081-.283A5.18 5.18 0 0 1 2.3 8c0-.172.016-.341.04-.507a.312.312 0 0 0-.08-.283l-.813-.804C.973 5.94.842 5.248 1.069 4.68c.181-.452.395-.882.683-1.18.385-.645 1.103-.833 1.755-.653l1.1.303c.066.019.176.011.299-.071.214-.143.437-.272.668-.386a.426.426 0 0 0 .211-.224l.29-1.107C6.009.645 6.556.095 7.299.03 7.53.01 7.764 0 8 0Zm0 5.5a2.5 2.5 0 1 0 0 5 2.5 2.5 0 0 0 0-5Z"})});return o.jsxs("div",{className:"mt-2 pt-3 border-t border-border space-y-3",children:[o.jsxs("div",{className:"flex items-center justify-between",children:[o.jsxs("div",{className:"flex items-center gap-2",children:[o.jsx("span",{className:`inline-block w-2.5 h-2.5 rounded-full flex-shrink-0 ${A==="running"?"bg-accent-success":A==="warning"?"bg-accent-warning":A==="error"?"bg-accent-error":"bg-text-muted"}`}),o.jsx("h3",{className:"text-sm font-semibold text-text-primary",children:"Dev Server"})]}),o.jsx("button",{onClick:()=>g(!0),className:"p-1.5 rounded hover:bg-bg-tertiary transition-colors text-text-muted",title:"Configure dev server",children:I})]}),N?o.jsxs(o.Fragment,{children:[A==="running"||A==="warning"?o.jsxs("div",{className:"flex gap-2",children:[o.jsxs("button",{onClick:T,className:"flex-1 flex items-center justify-center gap-1.5 rounded font-medium text-sm px-3 py-1.5 bg-bg-tertiary text-text-primary hover:bg-border transition-colors",children:[o.jsx("svg",{className:"w-4 h-4",viewBox:"0 0 16 16",fill:"currentColor",children:o.jsx("rect",{x:"3",y:"3",width:"10",height:"10",rx:"1"})}),"Stop"]}),(s==null?void 0:s.url)&&o.jsxs("a",{href:s.url,target:"_blank",rel:"noopener noreferrer",className:"flex-1 flex items-center justify-center gap-1.5 rounded font-medium text-sm px-3 py-1.5 bg-accent-primary/25 text-white hover:bg-accent-primary/40 transition-colors",title:s.url,children:[o.jsxs("svg",{className:"w-4 h-4",viewBox:"0 0 16 16",fill:"none",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round",children:[o.jsx("path",{d:"M6.5 3.5H3a1 1 0 0 0-1 1V13a1 1 0 0 0 1 1h8.5a1 1 0 0 0 1-1V9.5"}),o.jsx("path",{d:"M9.5 2h4.5v4.5"}),o.jsx("path",{d:"M14 2L7.5 8.5"})]}),"Open"]})]}):o.jsx("button",{onClick:T,className:"w-full rounded font-medium text-sm px-3 py-1.5 bg-accent-primary/25 text-white hover:bg-accent-primary/40 transition-colors",children:"Start"}),L&&o.jsxs("div",{ref:j,className:"relative",onMouseEnter:()=>{v.current&&clearTimeout(v.current),y.current=setTimeout(()=>{k(!0),b(!1)},500)},onMouseLeave:()=>{y.current&&clearTimeout(y.current),b(!0),v.current=setTimeout(()=>k(!1),150)},children:[o.jsx("pre",{ref:_,className:"text-sm bg-bg-primary p-2 rounded overflow-auto max-h-[200px] border border-border",children:u.length===0?o.jsx("span",{className:"text-text-muted",children:"No output yet"}):u.map((z,V)=>o.jsx("span",{className:z.stream==="stderr"?"text-accent-warning":"",children:Ns(z.content)},V))}),(S||C)&&j.current&&Hl.createPortal(o.jsx(kw,{logs:u,anchorRef:j,isHiding:C,onExpand:()=>x(!0),onClose:()=>k(!1)}),document.body)]})]}):o.jsx("button",{onClick:()=>g(!0),className:"w-full rounded font-medium text-sm px-3 py-1.5 bg-bg-tertiary text-text-muted hover:bg-border transition-colors",children:"Configure"}),o.jsx(bw,{isOpen:d,onClose:()=>g(!1)}),m&&o.jsx(Cw,{logs:u,onClose:()=>x(!1)})]})}),jw=P.memo(function({isOpen:r,onClose:i,processName:s,logs:c}){const u=P.useRef(null);return P.useEffect(()=>{const p=l=>{l.key==="Escape"&&i()};if(r)return window.addEventListener("keydown",p),()=>window.removeEventListener("keydown",p)},[r,i]),P.useEffect(()=>{u.current&&r&&(u.current.scrollTop=u.current.scrollHeight)},[c,r]),r?o.jsx("div",{className:"fixed inset-0 z-50 flex items-center justify-center bg-black/60",onClick:i,children:o.jsxs("div",{className:"relative w-[90vw] h-[90vh] bg-bg-primary rounded-lg border border-border flex flex-col",onClick:p=>p.stopPropagation(),children:[o.jsxs("div",{className:"flex items-center justify-between p-3 border-b border-border",children:[o.jsx("h3",{className:"text-sm font-semibold text-text-primary truncate",children:s}),o.jsx("button",{onClick:i,className:"p-1.5 rounded hover:bg-bg-tertiary transition-colors text-text-muted",children:o.jsx("svg",{className:"w-5 h-5",viewBox:"0 0 20 20",fill:"currentColor",children:o.jsx("path",{fillRule:"evenodd",d:"M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z",clipRule:"evenodd"})})})]}),o.jsx("pre",{ref:u,className:"flex-1 overflow-auto p-4 text-sm font-mono text-text-primary whitespace-pre-wrap",children:c.length===0?o.jsx("span",{className:"text-text-muted",children:"No output yet"}):c.map((p,l)=>o.jsx("span",{className:p.stream==="stderr"?"text-accent-warning":"",children:Ns(p.content)},l))})]})}):null}),Nw=P.memo(function({sessionId:r}){var S;const i=Ba(k=>k.processes),s=Ba(k=>k.stopProcess),[c,u]=P.useState(null),[p,l]=P.useState([]),f=i.filter(k=>k.status!=="exited"),d=f.filter(k=>k.status==="running").length;if(i.length===0)return null;const g=k=>{switch(k){case"running":return"bg-accent-success";case"starting":return"bg-accent-warning";case"stopping":return"bg-accent-warning";case"exited":return"bg-text-muted";default:return"bg-text-muted"}},m=k=>{const C=Ba.getState().logs[k]??[];l(C.map(b=>({content:b.content,stream:b.stream}))),u(k)},x=k=>{r&&s(k,r)};return o.jsxs("div",{className:"mt-2 pt-3 border-t border-border space-y-3",children:[o.jsx("div",{className:"flex items-center justify-between",children:o.jsxs("div",{className:"flex items-center gap-2",children:[o.jsx("span",{className:"inline-block w-2.5 h-2.5 rounded-full flex-shrink-0 bg-accent-primary"}),o.jsx("h3",{className:"text-sm font-semibold text-text-primary",children:"Background"}),o.jsxs("span",{className:"text-xs text-text-muted",children:["(",d," running)"]})]})}),o.jsx("div",{className:"space-y-2",children:f.map(k=>o.jsx("div",{className:"border border-border rounded p-2",children:o.jsxs("div",{className:"flex items-center justify-between",children:[o.jsxs("div",{className:"flex items-center gap-2 min-w-0 flex-1",children:[o.jsx("span",{className:`inline-block w-2 h-2 rounded-full flex-shrink-0 ${g(k.status)}`}),o.jsx("span",{className:"text-sm text-text-primary truncate",title:k.name,children:k.name}),o.jsxs("span",{className:"text-xs text-text-muted",children:["[",k.status,"]"]})]}),o.jsxs("div",{className:"flex gap-1 ml-2",children:[o.jsx("button",{onClick:()=>m(k.id),className:"px-2 py-1 text-xs rounded bg-bg-tertiary hover:bg-border text-text-secondary transition-colors",title:"View logs",children:"Logs"}),o.jsx("button",{onClick:()=>x(k.id),className:"px-2 py-1 text-xs rounded bg-bg-tertiary hover:bg-accent-error/20 text-text-secondary hover:text-accent-error transition-colors",title:"Stop process",children:"Stop"})]})]})},k.id))}),c&&o.jsx(jw,{isOpen:!!c,onClose:()=>{u(null),l([])},processName:((S=f.find(k=>k.id===c))==null?void 0:S.name)??"",logs:p})]})});function Rx({summary:e,messages:r,workdir:i}){const[s,c]=P.useState(!1),u=QS(r),{branch:p}=JS(i),l=jt(d=>d.version),f=Ee(d=>d.currentSession);return o.jsxs("div",{className:"flex flex-col h-full",children:[u&&o.jsxs("div",{className:"mb-4",children:[o.jsx("button",{onClick:()=>c(!0),className:"w-full flex items-center justify-center px-3 py-2 rounded bg-bg-tertiary hover:bg-bg-secondary transition-colors",title:"View detailed response and call-level stats",children:o.jsxs("div",{className:"flex items-center gap-2 text-sm text-text-muted",children:[o.jsx("span",{className:"text-text-secondary",children:ew(u.aiTime)}),o.jsx("span",{className:"w-px h-3 bg-border"}),o.jsx("span",{className:"text-text-secondary",children:Ex(u.avgPrefillSpeed)}),o.jsx("span",{children:"pp"}),o.jsx("span",{className:"w-px h-3 bg-border"}),o.jsx("span",{className:"text-text-secondary",children:Ex(u.avgGenerationSpeed)}),o.jsx("span",{children:"tg"})]})}),o.jsx(pw,{isOpen:s,onClose:()=>c(!1),stats:u})]}),o.jsxs("div",{className:"flex flex-col flex-1 overflow-y-auto",children:[o.jsx("div",{className:"flex items-center justify-between mb-2",children:o.jsx("h3",{className:"text-sm font-semibold text-text-primary",children:"Summary"})}),e?o.jsx("p",{className:"text-sm text-text-primary leading-relaxed",children:e}):o.jsx("div",{className:"text-text-muted text-sm text-center py-2",children:"No summary yet"}),o.jsxs("div",{className:"mt-4",children:[o.jsx("h3",{className:"text-sm font-semibold text-text-primary mb-2",children:"Progress"}),o.jsx(vw,{criteria:(f==null?void 0:f.criteria)??[]})]})]}),p&&o.jsxs("div",{className:"mt-4 flex items-center gap-2 text-sm",children:[o.jsx("svg",{className:"w-4 h-4 flex-shrink-0 text-text-muted",viewBox:"0 0 16 16",fill:"currentColor",children:o.jsx("path",{d:"M9.5 3.25a2.25 2.25 0 1 1 3 2.122V6A2.5 2.5 0 0 1 10 8.5H6a1 1 0 0 0-1 1v1.128a2.251 2.251 0 1 1-1.5 0V5.372a2.25 2.25 0 1 1 1.5 0v1.836A2.493 2.493 0 0 1 6 7h4a1 1 0 0 0 1-1v-.628A2.25 2.25 0 0 1 9.5 3.25Zm-6 0a.75.75 0 1 0 1.5 0 .75.75 0 0 0-1.5 0Zm8.25-.75a.75.75 0 1 0 0 1.5.75.75 0 0 0 0-1.5ZM4.25 12a.75.75 0 1 0 0 1.5.75.75 0 0 0 0-1.5Z"})}),o.jsx("span",{className:"truncate text-text-secondary",title:p,children:p})]}),o.jsx(Ew,{workdir:i}),o.jsx(Nw,{sessionId:f==null?void 0:f.id}),l&&o.jsxs("div",{className:"mt-4 pt-4 border-t border-border text-center text-xs text-text-muted",children:[o.jsx("a",{href:"https://github.com/co-l/openfox",target:"_blank",rel:"noopener noreferrer",className:"hover:text-accent-primary transition-colors",children:"OpenFox"})," - ",o.jsxs("span",{children:["v",l]})]})]})}function Tw({children:e,criteriaSidebarOpen:r=!0,onCriteriaSidebarToggle:i,messages:s}){const c=Ee(u=>u.currentSession);return o.jsxs("div",{className:"relative h-full overflow-hidden",children:[r&&o.jsx("div",{className:"fixed md:hidden inset-0 bg-black/50 z-40",onClick:i}),o.jsxs("div",{className:"flex h-full",children:[o.jsx("div",{className:"flex-1 min-w-0 flex flex-col overflow-hidden",children:e}),r?o.jsx("aside",{className:"hidden md:block w-[320px] shrink-0 border-l border-border p-4 overflow-y-auto bg-bg-secondary",children:o.jsx(Rx,{summary:(c==null?void 0:c.summary)??null,messages:s,workdir:c==null?void 0:c.workdir})}):o.jsx("aside",{className:"hidden md:block w-0 shrink-0 overflow-hidden border-l-0"}),o.jsx("aside",{className:`
85
85
  md:hidden
86
86
  p-4 overflow-y-auto bg-bg-secondary
87
87
  transition-all duration-300 ease-in-out
@@ -5,7 +5,7 @@
5
5
  <link rel="icon" type="image/png" href="/assets/openfox.png" />
6
6
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
7
7
  <title>OpenFox</title>
8
- <script type="module" crossorigin src="/assets/index-TAQh3Ryg.js"></script>
8
+ <script type="module" crossorigin src="/assets/index-3k9JFbsu.js"></script>
9
9
  <link rel="stylesheet" crossorigin href="/assets/index-DOwkDgJu.css">
10
10
  <link rel="manifest" href="/manifest.webmanifest"><script id="vite-plugin-pwa:register-sw" src="/registerSW.js"></script></head>
11
11
  <body class="bg-bg-primary text-text-primary font-mono">
package/dist/web/sw.js CHANGED
@@ -1 +1 @@
1
- if(!self.define){let e,s={};const i=(i,n)=>(i=new URL(i+".js",n).href,s[i]||new Promise(s=>{if("document"in self){const e=document.createElement("script");e.src=i,e.onload=s,document.head.appendChild(e)}else e=i,importScripts(i),s()}).then(()=>{let e=s[i];if(!e)throw new Error(`Module ${i} didn’t register its module`);return e}));self.define=(n,r)=>{const t=e||("document"in self?document.currentScript.src:"")||location.href;if(s[t])return;let o={};const l=e=>i(e,t),c={module:{uri:t},exports:o,require:l};s[t]=Promise.all(n.map(e=>c[e]||l(e))).then(e=>(r(...e),o))}}define(["./workbox-8c29f6e4"],function(e){"use strict";self.skipWaiting(),e.clientsClaim(),e.precacheAndRoute([{url:"registerSW.js",revision:"1872c500de691dce40960bb85481de07"},{url:"index.html",revision:"50591a2a74539261c6c1a0c0a0eb67e3"},{url:"assets/index-TAQh3Ryg.js",revision:null},{url:"assets/index-DOwkDgJu.css",revision:null},{url:"assets/html2canvas.esm-QH1iLAAe.js",revision:null},{url:"assets/openfox-192.png",revision:"79feeb86d692c274854e37959a7dae67"},{url:"assets/openfox-512.png",revision:"fee24b214220594b4f595a467e73036e"},{url:"manifest.webmanifest",revision:"c25f372c782e623ab1e768a8dfe350ca"}],{}),e.cleanupOutdatedCaches(),e.registerRoute(new e.NavigationRoute(e.createHandlerBoundToURL("index.html")))});
1
+ if(!self.define){let e,s={};const i=(i,n)=>(i=new URL(i+".js",n).href,s[i]||new Promise(s=>{if("document"in self){const e=document.createElement("script");e.src=i,e.onload=s,document.head.appendChild(e)}else e=i,importScripts(i),s()}).then(()=>{let e=s[i];if(!e)throw new Error(`Module ${i} didn’t register its module`);return e}));self.define=(n,r)=>{const t=e||("document"in self?document.currentScript.src:"")||location.href;if(s[t])return;let o={};const l=e=>i(e,t),u={module:{uri:t},exports:o,require:l};s[t]=Promise.all(n.map(e=>u[e]||l(e))).then(e=>(r(...e),o))}}define(["./workbox-8c29f6e4"],function(e){"use strict";self.skipWaiting(),e.clientsClaim(),e.precacheAndRoute([{url:"registerSW.js",revision:"1872c500de691dce40960bb85481de07"},{url:"index.html",revision:"be1f3ab19c6abd90b808cb7e7e283070"},{url:"assets/index-DOwkDgJu.css",revision:null},{url:"assets/index-3k9JFbsu.js",revision:null},{url:"assets/html2canvas.esm-QH1iLAAe.js",revision:null},{url:"assets/openfox-192.png",revision:"79feeb86d692c274854e37959a7dae67"},{url:"assets/openfox-512.png",revision:"fee24b214220594b4f595a467e73036e"},{url:"manifest.webmanifest",revision:"c25f372c782e623ab1e768a8dfe350ca"}],{}),e.cleanupOutdatedCaches(),e.registerRoute(new e.NavigationRoute(e.createHandlerBoundToURL("index.html")))});
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "openfox",
3
- "version": "1.6.6",
3
+ "version": "1.6.7",
4
4
  "description": "Local-LLM-first agentic coding assistant",
5
5
  "type": "module",
6
6
  "bin": {