ledung 1.4.0 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +3 -0
- package/README.md +3 -1
- package/dist/cli.js +714 -32
- package/dist/main.js +311 -228
- package/npm-shrinkwrap.json +2 -2
- package/package.json +2 -2
- package/web/dist/assets/{highlightCore-g6NEEnZr.js → highlightCore-CGEYh7VF.js} +1 -1
- package/web/dist/assets/{index-D8eK9o3f.css → index-1KospU2G.css} +1 -1
- package/web/dist/assets/{index-DcsDS7Ir.js → index-Cti8k_M1.js} +6 -6
- package/web/dist/index.html +2 -2
|
@@ -85,7 +85,7 @@ ${n.stderr.replace(/\s+$/,``)}`}):null]}),(0,V.jsx)(`div`,{className:`shell-foot
|
|
|
85
85
|
`).length)=>e.length<=262144&&t<=8e3;function tv(e){let t=[],n=[],r=``;for(let i of e.split(/(<span[^>]*>|<\/span>|\n)/))i&&(i===`
|
|
86
86
|
`?(t.push(r+`</span>`.repeat(n.length)),r=n.join(``)):i.startsWith(`<span`)?(n.push(i),r+=i):(i===`</span>`&&n.pop(),r+=i));return t.push(r+`</span>`.repeat(n.length)),t}function nv(e,t){let n=$_(e.path);if(!t||!n)return null;let r=e.hunks.flatMap(e=>e.lines);if(!ev(r.map(e=>e.text).join(`
|
|
87
87
|
`),r.length))return null;let i=new Map;for(let r of e.hunks)for(let e of[r.lines.filter(e=>e.kind!==`del`),r.lines.filter(e=>e.kind===`del`)]){if(!e.length)continue;let r=t(e.map(e=>e.text).join(`
|
|
88
|
-
`),n);e.forEach((e,t)=>i.set(e,r[t]??``))}return i}var rv=null;function iv(){return rv??=X_(()=>import(`./highlightCore-
|
|
88
|
+
`),n);e.forEach((e,t)=>i.set(e,r[t]??``))}return i}var rv=null;function iv(){return rv??=X_(()=>import(`./highlightCore-CGEYh7VF.js`).then(e=>e.highlight),[]),rv}function av(){let[e,t]=(0,v.useState)(null);return(0,v.useEffect)(()=>{let e=!0;return iv().then(n=>e&&t({fn:n}),()=>{}),()=>{e=!1}},[]),e?.fn??null}function ov(e){let t=e.lastIndexOf(`/`);return t===-1?``:e.slice(0,t)}function sv({text:e,path:t}){let n=e.replace(/\n$/,``).split(`
|
|
89
89
|
`),r=av(),i=$_(t),a=(0,v.useMemo)(()=>r&&i&&ev(e,n.length)?r(n.join(`
|
|
90
90
|
`),i):null,[r,i,e]);return(0,V.jsx)(`pre`,{className:`file-text numbered hl`,style:{"--ln-width":`${String(n.length).length+1}ch`},children:(0,V.jsx)(`code`,{children:a?a.map((e,t)=>(0,V.jsx)(`span`,{className:`ln-row`,dangerouslySetInnerHTML:{__html:`${e}\n`}},t)):n.map((e,t)=>(0,V.jsxs)(`span`,{className:`ln-row`,children:[e,`
|
|
91
91
|
`]},t))})})}function cv(e){let t=e.stack[e.stack.length-1],[n,r]=(0,v.useState)(null),[i,a]=(0,v.useState)(null),[o,s]=(0,v.useState)(!1),c=Cf(t);return(0,v.useEffect)(()=>{if(s(!1),c)return;let n=!0;return r(null),a(null),R.file(e.sessionId,t,e.folder).then(e=>n&&r(e),e=>n&&a(e.message)),()=>{n=!1}},[e.sessionId,t,c,e.folder]),(0,V.jsxs)(`aside`,{className:`file-panel`,"aria-label":`File`,children:[(0,V.jsxs)(`header`,{className:`file-head`,children:[(e.stack.length>1||e.backToPane)&&(0,V.jsx)(`button`,{className:`small`,onClick:e.onBack,children:e.backToPane&&e.stack.length===1?`‹ Files`:`Back`}),(0,V.jsx)(`span`,{className:`file-path`,title:!c&&n?.path||t,children:!c&&n?.path||t}),c&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>s(!o),children:o?`Fit to panel`:`Full size`}),!c&&n&&(0,V.jsx)(Df,{text:n.content,label:`Copy all`}),(0,V.jsx)(`button`,{className:`small`,onClick:e.onClose,"aria-label":`Close`,children:`Close`})]}),(0,V.jsxs)(`div`,{className:`file-body`,children:[!c&&i&&(0,V.jsx)(`p`,{className:`error`,children:i}),c&&(0,V.jsx)(Tf,{sessionId:e.sessionId,path:t,folder:e.folder,full:o,onClick:()=>s(!o)},t),!c&&!n&&!i&&(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`}),!c&&n?.kind===`markdown`&&(0,V.jsx)(jf,{text:n.content,baseDir:ov(n.path),onOpenFile:e.onOpen,sessionId:e.sessionId}),!c&&n?.kind===`text`&&(0,V.jsx)(sv,{text:n.content,path:n.path})]})]})}var lv=300;function uv(e){let t=e.replace(/\t/g,` `).trim();return t.length>lv?`${t.slice(0,lv)}…`:t}function dv(e,t){let n=[...new Set(e.map(e=>e.commit.slice(0,7)))];return[`${e.length} line comment${e.length===1?``:`s`} on ${t} at ${n.join(`, `)}:`,...e.map((e,t)=>{let n=e.side===`old`?`-`:`+`,r=`${e.path}:${e.line}${e.side===`old`?` (old)`:``}`,i=e.body.split(`
|
|
@@ -100,9 +100,9 @@ ${n.stderr.replace(/\s+$/,``)}`}):null]}),(0,V.jsx)(`div`,{className:`shell-foot
|
|
|
100
100
|
`),`
|
|
101
101
|
`,(0,V.jsx)(`span`,{className:`boat-water`,children:d[3]})]}),r]}),(0,V.jsx)(`span`,{className:`boat-marks`,"aria-hidden":`true`,children:t.map((t,r)=>(0,V.jsx)(`span`,{className:r+1===e?`on`:void 0,style:{"--at":(O_(r+1,a)+.5)/96},onClick:e=>{e.preventDefault(),n(r+1)},children:t},t))})]})}var yb={workflow:`workflow`,computer:`this computer`,"workflow+computer":`workflow, changed on this computer`};function bb(){let[e,t]=(0,v.useState)(null),[n,r]=(0,v.useState)(null);(0,v.useEffect)(()=>{R.profiles().then(t,e=>r(e.message))},[]);let i=(e?.groups.length??0)>1;return(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Session profiles`}),(0,V.jsx)($p,{kind:`config`})]}),(0,V.jsx)(`p`,{className:`muted`,children:`What managers and sessions get of your own Claude Code setup. A workflow's profiles file comes first; a profile of the same name in this computer's config changes it field by field. Read when each session starts.`}),n&&(0,V.jsx)(`p`,{className:`error`,children:n}),e?.groups.map(e=>(0,V.jsxs)(`div`,{className:`profiles-group`,children:[i&&(0,V.jsx)(`h4`,{children:e.workflow===null?`Chats and projects without a workflow's profiles`:`Workflow "${e.workflow}"`}),e.file&&(0,V.jsxs)(`p`,{className:`muted`,children:[`From `,(0,V.jsx)(`code`,{children:e.file})]}),e.warning&&(0,V.jsx)(`div`,{className:`board-warning`,role:`alert`,children:e.warning}),(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Profile`}),(0,V.jsx)(`th`,{children:`From`}),(0,V.jsx)(`th`,{children:`About`})]})}),(0,V.jsxs)(`tbody`,{children:[(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{children:`full`}),(0,V.jsx)(`td`,{children:`built in`}),(0,V.jsx)(`td`,{className:`muted`,children:`Everything you have set up, as outside Ledung.`})]}),e.profiles.map(e=>(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{children:e.name}),(0,V.jsx)(`td`,{children:yb[e.source]}),(0,V.jsxs)(`td`,{className:`muted`,children:[e.about??``,e.allow.length>0&&(0,V.jsxs)(`div`,{children:[`Allows without asking: `,e.allow.map((e,t)=>(0,V.jsxs)(`span`,{children:[t?`, `:``,(0,V.jsx)(`code`,{children:e})]},e))]}),e.mcp.length>0&&(0,V.jsxs)(`div`,{children:[`Runs MCP servers: `,e.mcp.map((e,t)=>(0,V.jsxs)(`span`,{children:[t?`, `:``,(0,V.jsx)(`code`,{children:e})]},e))]})]})]},e.name))]})]}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Default for managers: `,e.defaults.manager??`full`,` · for sessions: `,e.defaults.session??`full`,e.pluginsOff.length>0&&(0,V.jsxs)(V.Fragment,{children:[` · plugins off where installed: `,e.pluginsOff.join(`, `)]})]})]},e.workflow??``))]})}var xb={installed:`your installed Claude Code`,path:`the Claude Code the config names`,bundled:`the copy that came with Ledung`};function Sb(e){return e.filter(e=>e.status!==`ended`).map(e=>({id:e.id,title:e.title,project:e.project,runs:e.runner===`docker`?`the container's own`:e.claudeProgram?xb[e.claudeProgram.kind]:`not recorded (started before Ledung recorded it)`,path:e.runner===`docker`?null:e.claudeProgram?.path??null,version:e.claudeVersion}))}function Cb(e,t){let n=[t.getHours(),t.getMinutes(),t.getSeconds()].map(e=>String(e).padStart(2,`0`)).join(`:`);return e?`Checked again at ${n}: still the same.`:`Checked again at ${n}: no problem found.`}function wb(e){return e.split("`").flatMap((e,t)=>t%2?[{kind:`code`,text:e}]:e.split(/(https:\/\/[^\s,)]+[^\s,).])/).filter(Boolean).map(e=>({kind:/^https:\/\//.test(e)?`link`:`text`,text:e})))}function Tb({check:e,primary:t=!0}){let[n,r]=(0,v.useState)(!1),[i,a]=(0,v.useState)(null),o=async()=>{r(!0),a(null);try{a(Cb(await e(),new Date))}catch(e){a(`Couldn't check: ${e.message}`)}finally{r(!1)}};return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`button`,{className:t?`small primary`:`small`,disabled:n,"aria-busy":n,onClick:()=>void o(),children:n?`Checking…`:`Check again`}),i&&(0,V.jsx)(`span`,{className:`muted`,role:`status`,children:i})]})}function Eb({text:e}){return(0,V.jsx)(V.Fragment,{children:wb(e).map((e,t)=>e.kind===`code`?(0,V.jsx)(`code`,{children:e.text},t):e.kind===`link`?(0,V.jsx)(`a`,{href:e.text,target:`_blank`,rel:`noreferrer`,children:e.text},t):e.text)})}function Db({looked:e}){return(0,V.jsxs)(`details`,{className:`looked`,children:[(0,V.jsxs)(`summary`,{children:[`Where Ledung looked (`,e.length,`)`]}),(0,V.jsx)(`ul`,{className:`mono`,children:e.map(e=>(0,V.jsx)(`li`,{children:e},e))})]})}var Ob=e=>e.charAt(0).toUpperCase()+e.slice(1);function kb({sessions:e}){let[t,n]=(0,v.useState)(null),[r,i]=(0,v.useState)(null),a=()=>R.claudeCode().then(e=>(n(e),i(null),e),e=>{throw i(e.message),e});(0,v.useEffect)(()=>{a().catch(()=>{})},[]);let o=Sb(e),s=t?.program;return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Claude Code`}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Ledung runs your Claude Code: the `,(0,V.jsx)(`code`,{children:`claude`}),` on the PATH or where its installer puts it, else the Claude desktop app's own copy`,t?.required&&(0,V.jsxs)(V.Fragment,{children:[`, version `,t.required,` or newer (the one Ledung's Agent SDK was built for)`]}),`. Without it, sessions don't start. A running session keeps the program it started with.`]}),r&&(0,V.jsx)(`p`,{className:`error`,children:r}),t?.problem&&(0,V.jsx)(`div`,{className:`board-warning`,role:`alert`,children:(0,V.jsx)(Eb,{text:t.problem})}),t&&(0,V.jsx)(`table`,{className:`plain`,children:(0,V.jsxs)(`tbody`,{children:[(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`New sessions run`}),(0,V.jsx)(`td`,{children:s?(0,V.jsxs)(V.Fragment,{children:[Ob(s.app?`the Claude desktop app's own Claude Code`:xb[s.kind]),` `,s.version&&(0,V.jsxs)(V.Fragment,{children:[`· `,s.version]}),(0,V.jsx)(`div`,{className:`muted mono`,children:s.path})]}):`Nothing: sessions don't start`})]}),t.installed&&t.installed.path!==s?.path&&(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Found`}),(0,V.jsxs)(`td`,{children:[Ob(t.installed.app?`the Claude desktop app's own Claude Code`:xb[t.installed.kind]),` · `,t.installed.version??`version unknown`,(0,V.jsx)(`div`,{className:`muted mono`,children:t.installed.path})]})]})]})}),t?.looked&&t.looked.length>0&&(0,V.jsx)(Db,{looked:t.looked}),(0,V.jsx)(`p`,{children:(0,V.jsx)(Tb,{primary:!1,check:async()=>!!(await a()).problem})}),o.length>0&&(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`h4`,{children:`Running sessions`}),(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Session`}),(0,V.jsx)(`th`,{children:`Runs`}),(0,V.jsx)(`th`,{children:`Version`})]})}),(0,V.jsx)(`tbody`,{children:o.map(e=>(0,V.jsxs)(`tr`,{children:[(0,V.jsxs)(`td`,{children:[e.title,(0,V.jsx)(`div`,{className:`muted`,children:e.project})]}),(0,V.jsxs)(`td`,{children:[Ob(e.runs),e.path&&(0,V.jsx)(`div`,{className:`muted mono`,children:e.path})]}),(0,V.jsx)(`td`,{className:`mono`,children:e.version??``})]},e.id))})]})]})]})}function Ab(e){if(!e)return{label:`Remote: off`,detail:`Not on a relay: join one with a code below, or set "remote" in the config.`};switch(e.state){case`connected`:return{label:`Remote: connected`,detail:`Through the relay as ${e.publicName}.`};case`connecting`:return{label:`Remote: connecting…`,detail:`To the relay, as ${e.publicName}.`};case`reconnecting`:return{label:`Remote: reconnecting`,detail:e.error}}}var jb=7,Mb=864e5;function Nb(e,t){let n=e.validUntil?new Date(e.validUntil).toLocaleString():null,r=e.nextTry?new Date(e.nextTry).toLocaleTimeString():null,i=e.validUntil!==null&&e.validUntil-t<jb*Mb,a=n?` The one in use is valid until ${n}.`:``;switch(e.state){case`valid`:return{label:`Certificate valid until ${n}`,detail:i?`Fewer than ${jb} days left: it renews while Ledung is connected to the relay.`:null,warn:i,copy:!1};case`offline`:return{label:`Certificate: none yet`,detail:`Ledung orders one once it is connected to the relay.`,warn:!0,copy:!1};case`waiting-caa`:return{label:`Waiting for the CAA record`,detail:`Add this record to the DNS for the name. Ledung looks it up every minute${r?` (next at ${r})`:``} and orders as soon as it names this account.${e.error?` ${e.error}`:``}${a}`,warn:!n||i,copy:!0};case`ordering`:return{label:n?`Renewing the certificate…`:`Getting a certificate…`,detail:a.trim()||null,warn:!1,copy:!1};case`failed`:return{label:n?`Renewal failed`:`Getting a certificate failed`,detail:`${e.error??``}${r?` Trying again at ${r}.`:``}${a}`.trim()||null,warn:!0,copy:!1}}}var Pb=function(e,t){let n=e,r=Ib[t],i=null,a=0,o=null,s=[],c={},l=function(e,t){a=n*4+17,i=function(e){let t=Array(e);for(let n=0;n<e;n+=1){t[n]=Array(e);for(let r=0;r<e;r+=1)t[n][r]=null}return t}(a),u(0,0),u(a-7,0),u(0,a-7),p(),f(),h(e,t),n>=7&&m(e),o??=v(n,r,s),g(o,t)},u=function(e,t){for(let n=-1;n<=7;n+=1)if(!(e+n<=-1||a<=e+n))for(let r=-1;r<=7;r+=1)t+r<=-1||a<=t+r||(0<=n&&n<=6&&(r==0||r==6)||0<=r&&r<=6&&(n==0||n==6)||2<=n&&n<=4&&2<=r&&r<=4?i[e+n][t+r]=!0:i[e+n][t+r]=!1)},d=function(){let e=0,t=0;for(let n=0;n<8;n+=1){l(!0,n);let r=Rb.getLostPoint(c);(n==0||e>r)&&(e=r,t=n)}return t},f=function(){for(let e=8;e<a-8;e+=1)i[e][6]??(i[e][6]=e%2==0);for(let e=8;e<a-8;e+=1)i[6][e]??(i[6][e]=e%2==0)},p=function(){let e=Rb.getPatternPosition(n);for(let t=0;t<e.length;t+=1)for(let n=0;n<e.length;n+=1){let r=e[t],a=e[n];if(i[r][a]==null)for(let e=-2;e<=2;e+=1)for(let t=-2;t<=2;t+=1)e==-2||e==2||t==-2||t==2||e==0&&t==0?i[r+e][a+t]=!0:i[r+e][a+t]=!1}},m=function(e){let t=Rb.getBCHTypeNumber(n);for(let n=0;n<18;n+=1){let r=!e&&(t>>n&1)==1;i[Math.floor(n/3)][n%3+a-8-3]=r}for(let n=0;n<18;n+=1){let r=!e&&(t>>n&1)==1;i[n%3+a-8-3][Math.floor(n/3)]=r}},h=function(e,t){let n=r<<3|t,o=Rb.getBCHTypeInfo(n);for(let t=0;t<15;t+=1){let n=!e&&(o>>t&1)==1;t<6?i[t][8]=n:t<8?i[t+1][8]=n:i[a-15+t][8]=n}for(let t=0;t<15;t+=1){let n=!e&&(o>>t&1)==1;t<8?i[8][a-t-1]=n:t<9?i[8][15-t-1+1]=n:i[8][15-t-1]=n}i[a-8][8]=!e},g=function(e,t){let n=-1,r=a-1,o=7,s=0,c=Rb.getMaskFunction(t);for(let t=a-1;t>0;t-=2)for(t==6&&--t;;){for(let n=0;n<2;n+=1)if(i[r][t-n]==null){let a=!1;s<e.length&&(a=(e[s]>>>o&1)==1),c(r,t-n)&&(a=!a),i[r][t-n]=a,--o,o==-1&&(s+=1,o=7)}if(r+=n,r<0||a<=r){r-=n,n=-n;break}}},_=function(e,t){let n=0,r=0,i=0,a=Array(t.length),o=Array(t.length);for(let s=0;s<t.length;s+=1){let c=t[s].dataCount,l=t[s].totalCount-c;r=Math.max(r,c),i=Math.max(i,l),a[s]=Array(c);for(let t=0;t<a[s].length;t+=1)a[s][t]=255&e.getBuffer()[t+n];n+=c;let u=Rb.getErrorCorrectPolynomial(l),d=Bb(a[s],u.getLength()-1).mod(u);o[s]=Array(u.getLength()-1);for(let e=0;e<o[s].length;e+=1){let t=e+d.getLength()-o[s].length;o[s][e]=t>=0?d.getAt(t):0}}let s=0;for(let e=0;e<t.length;e+=1)s+=t[e].totalCount;let c=Array(s),l=0;for(let e=0;e<r;e+=1)for(let n=0;n<t.length;n+=1)e<a[n].length&&(c[l]=a[n][e],l+=1);for(let e=0;e<i;e+=1)for(let n=0;n<t.length;n+=1)e<o[n].length&&(c[l]=o[n][e],l+=1);return c},v=function(e,t,n){let r=Vb.getRSBlocks(e,t),i=Hb();for(let t=0;t<n.length;t+=1){let r=n[t];i.put(r.getMode(),4),i.put(r.getLength(),Rb.getLengthInBits(r.getMode(),e)),r.write(i)}let a=0;for(let e=0;e<r.length;e+=1)a+=r[e].dataCount;if(i.getLengthInBits()>a*8)throw`code length overflow. (`+i.getLengthInBits()+`>`+a*8+`)`;for(i.getLengthInBits()+4<=a*8&&i.put(0,4);i.getLengthInBits()%8!=0;)i.putBit(!1);for(;!(i.getLengthInBits()>=a*8||(i.put(236,8),i.getLengthInBits()>=a*8));)i.put(17,8);return _(i,r)};c.addData=function(e,t){t||=`Byte`;let n=null;switch(t){case`Numeric`:n=Ub(e);break;case`Alphanumeric`:n=Wb(e);break;case`Byte`:n=Gb(e);break;case`Kanji`:n=Kb(e);break;default:throw`mode:`+t}s.push(n),o=null},c.isDark=function(e,t){if(e<0||a<=e||t<0||a<=t)throw e+`,`+t;return i[e][t]},c.getModuleCount=function(){return a},c.make=function(){if(n<1){let e=1;for(;e<40;e++){let t=Vb.getRSBlocks(e,r),n=Hb();for(let t=0;t<s.length;t++){let r=s[t];n.put(r.getMode(),4),n.put(r.getLength(),Rb.getLengthInBits(r.getMode(),e)),r.write(n)}let i=0;for(let e=0;e<t.length;e++)i+=t[e].dataCount;if(n.getLengthInBits()<=i*8)break}n=e}l(!1,d())},c.createTableTag=function(e,t){e||=2,t=t===void 0?e*4:t;let n=``;n+=`<table style="`,n+=` border-width: 0px; border-style: none;`,n+=` border-collapse: collapse;`,n+=` padding: 0px; margin: `+t+`px;`,n+=`">`,n+=`<tbody>`;for(let t=0;t<c.getModuleCount();t+=1){n+=`<tr>`;for(let r=0;r<c.getModuleCount();r+=1)n+=`<td style="`,n+=` border-width: 0px; border-style: none;`,n+=` border-collapse: collapse;`,n+=` padding: 0px; margin: 0px;`,n+=` width: `+e+`px;`,n+=` height: `+e+`px;`,n+=` background-color: `,n+=c.isDark(t,r)?`#000000`:`#ffffff`,n+=`;`,n+=`"/>`;n+=`</tr>`}return n+=`</tbody>`,n+=`</table>`,n},c.createSvgTag=function(e,t,n,r){let i={};typeof arguments[0]==`object`&&(i=arguments[0],e=i.cellSize,t=i.margin,n=i.alt,r=i.title),e||=2,t=t===void 0?e*4:t,n=typeof n==`string`?{text:n}:n||{},n.text=n.text||null,n.id=n.text?n.id||`qrcode-description`:null,r=typeof r==`string`?{text:r}:r||{},r.text=r.text||null,r.id=r.text?r.id||`qrcode-title`:null;let a=c.getModuleCount()*e+t*2,o,s,l,u,d=``,f;for(f=`l`+e+`,0 0,`+e+` -`+e+`,0 0,-`+e+`z `,d+=`<svg version="1.1" xmlns="http://www.w3.org/2000/svg"`,d+=i.scalable?``:` width="`+a+`px" height="`+a+`px"`,d+=` viewBox="0 0 `+a+` `+a+`" `,d+=` preserveAspectRatio="xMinYMin meet"`,d+=r.text||n.text?` role="img" aria-labelledby="`+y([r.id,n.id].join(` `).trim())+`"`:``,d+=`>`,d+=r.text?`<title id="`+y(r.id)+`">`+y(r.text)+`</title>`:``,d+=n.text?`<description id="`+y(n.id)+`">`+y(n.text)+`</description>`:``,d+=`<rect width="100%" height="100%" fill="white" cx="0" cy="0"/>`,d+=`<path d="`,l=0;l<c.getModuleCount();l+=1)for(u=l*e+t,o=0;o<c.getModuleCount();o+=1)c.isDark(l,o)&&(s=o*e+t,d+=`M`+s+`,`+u+f);return d+=`" stroke="transparent" fill="black"/>`,d+=`</svg>`,d},c.createDataURL=function(e,t){e||=2,t=t===void 0?e*4:t;let n=c.getModuleCount()*e+t*2,r=t,i=n-t;return Zb(n,n,function(t,n){if(r<=t&&t<i&&r<=n&&n<i){let i=Math.floor((t-r)/e),a=Math.floor((n-r)/e);return+!c.isDark(a,i)}return 1})},c.createImgTag=function(e,t,n){e||=2,t=t===void 0?e*4:t;let r=c.getModuleCount()*e+t*2,i=``;return i+=`<img`,i+=` src="`,i+=c.createDataURL(e,t),i+=`"`,i+=` width="`,i+=r,i+=`"`,i+=` height="`,i+=r,i+=`"`,n&&(i+=` alt="`,i+=y(n),i+=`"`),i+=`/>`,i};let y=function(e){let t=``;for(let n=0;n<e.length;n+=1){let r=e.charAt(n);switch(r){case`<`:t+=`<`;break;case`>`:t+=`>`;break;case`&`:t+=`&`;break;case`"`:t+=`"`;break;default:t+=r}}return t},b=function(e){e=e===void 0?2:e;let t=c.getModuleCount()*1+e*2,n=e,r=t-e,i,a,o,s,l,u={"██":`█`,"█ ":`▀`," █":`▄`," ":` `},d={"██":`▀`,"█ ":`▀`," █":` `," ":` `},f=``;for(i=0;i<t;i+=2){for(o=Math.floor((i-n)/1),s=Math.floor((i+1-n)/1),a=0;a<t;a+=1)l=`█`,n<=a&&a<r&&n<=i&&i<r&&c.isDark(o,Math.floor((a-n)/1))&&(l=` `),n<=a&&a<r&&n<=i+1&&i+1<r&&c.isDark(s,Math.floor((a-n)/1))?l+=` `:l+=`█`,f+=e<1&&i+1>=r?d[l]:u[l];f+=`
|
|
102
102
|
`}return t%2&&e>0?f.substring(0,f.length-t-1)+Array(t+1).join(`▀`):f.substring(0,f.length-1)};return c.createASCII=function(e,t){if(e||=1,e<2)return b(t);--e,t=t===void 0?e*2:t;let n=c.getModuleCount()*e+t*2,r=t,i=n-t,a,o,s,l,u=Array(e+1).join(`██`),d=Array(e+1).join(` `),f=``,p=``;for(a=0;a<n;a+=1){for(s=Math.floor((a-r)/e),p=``,o=0;o<n;o+=1)l=1,r<=o&&o<i&&r<=a&&a<i&&c.isDark(s,Math.floor((o-r)/e))&&(l=0),p+=l?u:d;for(s=0;s<e;s+=1)f+=p+`
|
|
103
|
-
`}return f.substring(0,f.length-1)},c.renderTo2dContext=function(e,t){t||=2;let n=c.getModuleCount();for(let r=0;r<n;r++)for(let i=0;i<n;i++)e.fillStyle=c.isDark(r,i)?`black`:`white`,e.fillRect(i*t,r*t,t,t)},c};Pb.stringToBytes=function(e){let t=[];for(let n=0;n<e.length;n+=1){let r=e.charCodeAt(n);t.push(r&255)}return t},Pb.createStringToBytes=function(e,t){let n=function(){let n=Yb(e),r=function(){let e=n.read();if(e==-1)throw`eof`;return e},i=0,a={};for(;;){let e=n.read();if(e==-1)break;let t=r(),o=r(),s=r(),c=String.fromCharCode(e<<8|t);a[c]=o<<8|s,i+=1}if(i!=t)throw i+` != `+t;return a}();return function(e){let t=[];for(let r=0;r<e.length;r+=1){let i=e.charCodeAt(r);if(i<128)t.push(i);else{let i=n[e.charAt(r)];typeof i==`number`?(i&255)==i?t.push(i):(t.push(i>>>8),t.push(i&255)):t.push(63)}}return t}};var Fb={MODE_NUMBER:1,MODE_ALPHA_NUM:2,MODE_8BIT_BYTE:4,MODE_KANJI:8},Ib={L:1,M:0,Q:3,H:2},Lb={PATTERN000:0,PATTERN001:1,PATTERN010:2,PATTERN011:3,PATTERN100:4,PATTERN101:5,PATTERN110:6,PATTERN111:7},Rb=function(){let e=[[],[6,18],[6,22],[6,26],[6,30],[6,34],[6,22,38],[6,24,42],[6,26,46],[6,28,50],[6,30,54],[6,32,58],[6,34,62],[6,26,46,66],[6,26,48,70],[6,26,50,74],[6,30,54,78],[6,30,56,82],[6,30,58,86],[6,34,62,90],[6,28,50,72,94],[6,26,50,74,98],[6,30,54,78,102],[6,28,54,80,106],[6,32,58,84,110],[6,30,58,86,114],[6,34,62,90,118],[6,26,50,74,98,122],[6,30,54,78,102,126],[6,26,52,78,104,130],[6,30,56,82,108,134],[6,34,60,86,112,138],[6,30,58,86,114,142],[6,34,62,90,118,146],[6,30,54,78,102,126,150],[6,24,50,76,102,128,154],[6,28,54,80,106,132,158],[6,32,58,84,110,136,162],[6,26,54,82,110,138,166],[6,30,58,86,114,142,170]],t=1335,n=7973,r={},i=function(e){let t=0;for(;e!=0;)t+=1,e>>>=1;return t};return r.getBCHTypeInfo=function(e){let n=e<<10;for(;i(n)-i(t)>=0;)n^=t<<i(n)-i(t);return(e<<10|n)^21522},r.getBCHTypeNumber=function(e){let t=e<<12;for(;i(t)-i(n)>=0;)t^=n<<i(t)-i(n);return e<<12|t},r.getPatternPosition=function(t){return e[t-1]},r.getMaskFunction=function(e){switch(e){case Lb.PATTERN000:return function(e,t){return(e+t)%2==0};case Lb.PATTERN001:return function(e,t){return e%2==0};case Lb.PATTERN010:return function(e,t){return t%3==0};case Lb.PATTERN011:return function(e,t){return(e+t)%3==0};case Lb.PATTERN100:return function(e,t){return(Math.floor(e/2)+Math.floor(t/3))%2==0};case Lb.PATTERN101:return function(e,t){return e*t%2+e*t%3==0};case Lb.PATTERN110:return function(e,t){return(e*t%2+e*t%3)%2==0};case Lb.PATTERN111:return function(e,t){return(e*t%3+(e+t)%2)%2==0};default:throw`bad maskPattern:`+e}},r.getErrorCorrectPolynomial=function(e){let t=Bb([1],0);for(let n=0;n<e;n+=1)t=t.multiply(Bb([1,zb.gexp(n)],0));return t},r.getLengthInBits=function(e,t){if(1<=t&&t<10)switch(e){case Fb.MODE_NUMBER:return 10;case Fb.MODE_ALPHA_NUM:return 9;case Fb.MODE_8BIT_BYTE:return 8;case Fb.MODE_KANJI:return 8;default:throw`mode:`+e}else if(t<27)switch(e){case Fb.MODE_NUMBER:return 12;case Fb.MODE_ALPHA_NUM:return 11;case Fb.MODE_8BIT_BYTE:return 16;case Fb.MODE_KANJI:return 10;default:throw`mode:`+e}else if(t<41)switch(e){case Fb.MODE_NUMBER:return 14;case Fb.MODE_ALPHA_NUM:return 13;case Fb.MODE_8BIT_BYTE:return 16;case Fb.MODE_KANJI:return 12;default:throw`mode:`+e}else throw`type:`+t},r.getLostPoint=function(e){let t=e.getModuleCount(),n=0;for(let r=0;r<t;r+=1)for(let i=0;i<t;i+=1){let a=0,o=e.isDark(r,i);for(let n=-1;n<=1;n+=1)if(!(r+n<0||t<=r+n))for(let s=-1;s<=1;s+=1)i+s<0||t<=i+s||(n!=0||s!=0)&&o==e.isDark(r+n,i+s)&&(a+=1);a>5&&(n+=3+a-5)}for(let r=0;r<t-1;r+=1)for(let i=0;i<t-1;i+=1){let t=0;e.isDark(r,i)&&(t+=1),e.isDark(r+1,i)&&(t+=1),e.isDark(r,i+1)&&(t+=1),e.isDark(r+1,i+1)&&(t+=1),(t==0||t==4)&&(n+=3)}for(let r=0;r<t;r+=1)for(let i=0;i<t-6;i+=1)e.isDark(r,i)&&!e.isDark(r,i+1)&&e.isDark(r,i+2)&&e.isDark(r,i+3)&&e.isDark(r,i+4)&&!e.isDark(r,i+5)&&e.isDark(r,i+6)&&(n+=40);for(let r=0;r<t;r+=1)for(let i=0;i<t-6;i+=1)e.isDark(i,r)&&!e.isDark(i+1,r)&&e.isDark(i+2,r)&&e.isDark(i+3,r)&&e.isDark(i+4,r)&&!e.isDark(i+5,r)&&e.isDark(i+6,r)&&(n+=40);let r=0;for(let n=0;n<t;n+=1)for(let i=0;i<t;i+=1)e.isDark(i,n)&&(r+=1);let i=Math.abs(100*r/t/t-50)/5;return n+=i*10,n},r}(),zb=function(){let e=Array(256),t=Array(256);for(let t=0;t<8;t+=1)e[t]=1<<t;for(let t=8;t<256;t+=1)e[t]=e[t-4]^e[t-5]^e[t-6]^e[t-8];for(let n=0;n<255;n+=1)t[e[n]]=n;let n={};return n.glog=function(e){if(e<1)throw`glog(`+e+`)`;return t[e]},n.gexp=function(t){for(;t<0;)t+=255;for(;t>=256;)t-=255;return e[t]},n}(),Bb=function(e,t){if(e.length===void 0)throw e.length+`/`+t;let n=function(){let n=0;for(;n<e.length&&e[n]==0;)n+=1;let r=Array(e.length-n+t);for(let t=0;t<e.length-n;t+=1)r[t]=e[t+n];return r}(),r={};return r.getAt=function(e){return n[e]},r.getLength=function(){return n.length},r.multiply=function(e){let t=Array(r.getLength()+e.getLength()-1);for(let n=0;n<r.getLength();n+=1)for(let i=0;i<e.getLength();i+=1)t[n+i]^=zb.gexp(zb.glog(r.getAt(n))+zb.glog(e.getAt(i)));return Bb(t,0)},r.mod=function(e){if(r.getLength()-e.getLength()<0)return r;let t=zb.glog(r.getAt(0))-zb.glog(e.getAt(0)),n=Array(r.getLength());for(let e=0;e<r.getLength();e+=1)n[e]=r.getAt(e);for(let r=0;r<e.getLength();r+=1)n[r]^=zb.gexp(zb.glog(e.getAt(r))+t);return Bb(n,0).mod(e)},r},Vb=function(){let e=[[1,26,19],[1,26,16],[1,26,13],[1,26,9],[1,44,34],[1,44,28],[1,44,22],[1,44,16],[1,70,55],[1,70,44],[2,35,17],[2,35,13],[1,100,80],[2,50,32],[2,50,24],[4,25,9],[1,134,108],[2,67,43],[2,33,15,2,34,16],[2,33,11,2,34,12],[2,86,68],[4,43,27],[4,43,19],[4,43,15],[2,98,78],[4,49,31],[2,32,14,4,33,15],[4,39,13,1,40,14],[2,121,97],[2,60,38,2,61,39],[4,40,18,2,41,19],[4,40,14,2,41,15],[2,146,116],[3,58,36,2,59,37],[4,36,16,4,37,17],[4,36,12,4,37,13],[2,86,68,2,87,69],[4,69,43,1,70,44],[6,43,19,2,44,20],[6,43,15,2,44,16],[4,101,81],[1,80,50,4,81,51],[4,50,22,4,51,23],[3,36,12,8,37,13],[2,116,92,2,117,93],[6,58,36,2,59,37],[4,46,20,6,47,21],[7,42,14,4,43,15],[4,133,107],[8,59,37,1,60,38],[8,44,20,4,45,21],[12,33,11,4,34,12],[3,145,115,1,146,116],[4,64,40,5,65,41],[11,36,16,5,37,17],[11,36,12,5,37,13],[5,109,87,1,110,88],[5,65,41,5,66,42],[5,54,24,7,55,25],[11,36,12,7,37,13],[5,122,98,1,123,99],[7,73,45,3,74,46],[15,43,19,2,44,20],[3,45,15,13,46,16],[1,135,107,5,136,108],[10,74,46,1,75,47],[1,50,22,15,51,23],[2,42,14,17,43,15],[5,150,120,1,151,121],[9,69,43,4,70,44],[17,50,22,1,51,23],[2,42,14,19,43,15],[3,141,113,4,142,114],[3,70,44,11,71,45],[17,47,21,4,48,22],[9,39,13,16,40,14],[3,135,107,5,136,108],[3,67,41,13,68,42],[15,54,24,5,55,25],[15,43,15,10,44,16],[4,144,116,4,145,117],[17,68,42],[17,50,22,6,51,23],[19,46,16,6,47,17],[2,139,111,7,140,112],[17,74,46],[7,54,24,16,55,25],[34,37,13],[4,151,121,5,152,122],[4,75,47,14,76,48],[11,54,24,14,55,25],[16,45,15,14,46,16],[6,147,117,4,148,118],[6,73,45,14,74,46],[11,54,24,16,55,25],[30,46,16,2,47,17],[8,132,106,4,133,107],[8,75,47,13,76,48],[7,54,24,22,55,25],[22,45,15,13,46,16],[10,142,114,2,143,115],[19,74,46,4,75,47],[28,50,22,6,51,23],[33,46,16,4,47,17],[8,152,122,4,153,123],[22,73,45,3,74,46],[8,53,23,26,54,24],[12,45,15,28,46,16],[3,147,117,10,148,118],[3,73,45,23,74,46],[4,54,24,31,55,25],[11,45,15,31,46,16],[7,146,116,7,147,117],[21,73,45,7,74,46],[1,53,23,37,54,24],[19,45,15,26,46,16],[5,145,115,10,146,116],[19,75,47,10,76,48],[15,54,24,25,55,25],[23,45,15,25,46,16],[13,145,115,3,146,116],[2,74,46,29,75,47],[42,54,24,1,55,25],[23,45,15,28,46,16],[17,145,115],[10,74,46,23,75,47],[10,54,24,35,55,25],[19,45,15,35,46,16],[17,145,115,1,146,116],[14,74,46,21,75,47],[29,54,24,19,55,25],[11,45,15,46,46,16],[13,145,115,6,146,116],[14,74,46,23,75,47],[44,54,24,7,55,25],[59,46,16,1,47,17],[12,151,121,7,152,122],[12,75,47,26,76,48],[39,54,24,14,55,25],[22,45,15,41,46,16],[6,151,121,14,152,122],[6,75,47,34,76,48],[46,54,24,10,55,25],[2,45,15,64,46,16],[17,152,122,4,153,123],[29,74,46,14,75,47],[49,54,24,10,55,25],[24,45,15,46,46,16],[4,152,122,18,153,123],[13,74,46,32,75,47],[48,54,24,14,55,25],[42,45,15,32,46,16],[20,147,117,4,148,118],[40,75,47,7,76,48],[43,54,24,22,55,25],[10,45,15,67,46,16],[19,148,118,6,149,119],[18,75,47,31,76,48],[34,54,24,34,55,25],[20,45,15,61,46,16]],t=function(e,t){let n={};return n.totalCount=e,n.dataCount=t,n},n={},r=function(t,n){switch(n){case Ib.L:return e[(t-1)*4+0];case Ib.M:return e[(t-1)*4+1];case Ib.Q:return e[(t-1)*4+2];case Ib.H:return e[(t-1)*4+3];default:return}};return n.getRSBlocks=function(e,n){let i=r(e,n);if(i===void 0)throw`bad rs block @ typeNumber:`+e+`/errorCorrectionLevel:`+n;let a=i.length/3,o=[];for(let e=0;e<a;e+=1){let n=i[e*3+0],r=i[e*3+1],a=i[e*3+2];for(let e=0;e<n;e+=1)o.push(t(r,a))}return o},n}(),Hb=function(){let e=[],t=0,n={};return n.getBuffer=function(){return e},n.getAt=function(t){let n=Math.floor(t/8);return(e[n]>>>7-t%8&1)==1},n.put=function(e,t){for(let r=0;r<t;r+=1)n.putBit((e>>>t-r-1&1)==1)},n.getLengthInBits=function(){return t},n.putBit=function(n){let r=Math.floor(t/8);e.length<=r&&e.push(0),n&&(e[r]|=128>>>t%8),t+=1},n},Ub=function(e){let t=Fb.MODE_NUMBER,n=e,r={};r.getMode=function(){return t},r.getLength=function(e){return n.length},r.write=function(e){let t=n,r=0;for(;r+2<t.length;)e.put(i(t.substring(r,r+3)),10),r+=3;r<t.length&&(t.length-r==1?e.put(i(t.substring(r,r+1)),4):t.length-r==2&&e.put(i(t.substring(r,r+2)),7))};let i=function(e){let t=0;for(let n=0;n<e.length;n+=1)t=t*10+a(e.charAt(n));return t},a=function(e){if(`0`<=e&&e<=`9`)return e.charCodeAt(0)-48;throw`illegal char :`+e};return r},Wb=function(e){let t=Fb.MODE_ALPHA_NUM,n=e,r={};r.getMode=function(){return t},r.getLength=function(e){return n.length},r.write=function(e){let t=n,r=0;for(;r+1<t.length;)e.put(i(t.charAt(r))*45+i(t.charAt(r+1)),11),r+=2;r<t.length&&e.put(i(t.charAt(r)),6)};let i=function(e){if(`0`<=e&&e<=`9`)return e.charCodeAt(0)-48;if(`A`<=e&&e<=`Z`)return e.charCodeAt(0)-65+10;switch(e){case` `:return 36;case`$`:return 37;case`%`:return 38;case`*`:return 39;case`+`:return 40;case`-`:return 41;case`.`:return 42;case`/`:return 43;case`:`:return 44;default:throw`illegal char :`+e}};return r},Gb=function(e){let t=Fb.MODE_8BIT_BYTE,n=Pb.stringToBytes(e),r={};return r.getMode=function(){return t},r.getLength=function(e){return n.length},r.write=function(e){for(let t=0;t<n.length;t+=1)e.put(n[t],8)},r},Kb=function(e){let t=Fb.MODE_KANJI,n=Pb.stringToBytes;(function(e,t){let r=n(e);if(r.length!=2||(r[0]<<8|r[1])!=t)throw`sjis not supported.`})(`友`,38726);let r=n(e),i={};return i.getMode=function(){return t},i.getLength=function(e){return~~(r.length/2)},i.write=function(e){let t=r,n=0;for(;n+1<t.length;){let r=(255&t[n])<<8|255&t[n+1];if(33088<=r&&r<=40956)r-=33088;else if(57408<=r&&r<=60351)r-=49472;else throw`illegal char at `+(n+1)+`/`+r;r=(r>>>8&255)*192+(r&255),e.put(r,13),n+=2}if(n<t.length)throw`illegal char at `+(n+1)},i},qb=function(){let e=[],t={};return t.writeByte=function(t){e.push(t&255)},t.writeShort=function(e){t.writeByte(e),t.writeByte(e>>>8)},t.writeBytes=function(e,n,r){n||=0,r||=e.length;for(let i=0;i<r;i+=1)t.writeByte(e[i+n])},t.writeString=function(e){for(let n=0;n<e.length;n+=1)t.writeByte(e.charCodeAt(n))},t.toByteArray=function(){return e},t.toString=function(){let t=``;t+=`[`;for(let n=0;n<e.length;n+=1)n>0&&(t+=`,`),t+=e[n];return t+=`]`,t},t},Jb=function(){let e=0,t=0,n=0,r=``,i={},a=function(e){r+=String.fromCharCode(o(e&63))},o=function(e){if(e<0)throw`n:`+e;if(e<26)return 65+e;if(e<52)return 97+(e-26);if(e<62)return 48+(e-52);if(e==62)return 43;if(e==63)return 47;throw`n:`+e};return i.writeByte=function(r){for(e=e<<8|r&255,t+=8,n+=1;t>=6;)a(e>>>t-6),t-=6},i.flush=function(){if(t>0&&(a(e<<6-t),e=0,t=0),n%3!=0){let e=3-n%3;for(let t=0;t<e;t+=1)r+=`=`}},i.toString=function(){return r},i},Yb=function(e){let t=e,n=0,r=0,i=0,a={};a.read=function(){for(;i<8;){if(n>=t.length){if(i==0)return-1;throw`unexpected end of file./`+i}let e=t.charAt(n);if(n+=1,e==`=`)return i=0,-1;e.match(/^\s$/)||(r=r<<6|o(e.charCodeAt(0)),i+=6)}let e=r>>>i-8&255;return i-=8,e};let o=function(e){if(65<=e&&e<=90)return e-65;if(97<=e&&e<=122)return e-97+26;if(48<=e&&e<=57)return e-48+52;if(e==43)return 62;if(e==47)return 63;throw`c:`+e};return a},Xb=function(e,t){let n=e,r=t,i=Array(e*t),a={};a.setPixel=function(e,t,r){i[t*n+e]=r},a.write=function(e){e.writeString(`GIF87a`),e.writeShort(n),e.writeShort(r),e.writeByte(128),e.writeByte(0),e.writeByte(0),e.writeByte(0),e.writeByte(0),e.writeByte(0),e.writeByte(255),e.writeByte(255),e.writeByte(255),e.writeString(`,`),e.writeShort(0),e.writeShort(0),e.writeShort(n),e.writeShort(r),e.writeByte(0);let t=s(2);e.writeByte(2);let i=0;for(;t.length-i>255;)e.writeByte(255),e.writeBytes(t,i,255),i+=255;e.writeByte(t.length-i),e.writeBytes(t,i,t.length-i),e.writeByte(0),e.writeString(`;`)};let o=function(e){let t=e,n=0,r=0,i={};return i.write=function(e,i){if(e>>>i)throw`length over`;for(;n+i>=8;)t.writeByte(255&(e<<n|r)),i-=8-n,e>>>=8-n,r=0,n=0;r=e<<n|r,n+=i},i.flush=function(){n>0&&t.writeByte(r)},i},s=function(e){let t=1<<e,n=(1<<e)+1,r=e+1,a=c();for(let e=0;e<t;e+=1)a.add(String.fromCharCode(e));a.add(String.fromCharCode(t)),a.add(String.fromCharCode(n));let s=qb(),l=o(s);l.write(t,r);let u=0,d=String.fromCharCode(i[u]);for(u+=1;u<i.length;){let e=String.fromCharCode(i[u]);u+=1,a.contains(d+e)?d+=e:(l.write(a.indexOf(d),r),a.size()<4095&&(a.size()==1<<r&&(r+=1),a.add(d+e)),d=e)}return l.write(a.indexOf(d),r),l.write(n,r),l.flush(),s.toByteArray()},c=function(){let e={},t=0,n={};return n.add=function(r){if(n.contains(r))throw`dup key:`+r;e[r]=t,t+=1},n.size=function(){return t},n.indexOf=function(t){return e[t]},n.contains=function(t){return e[t]!==void 0},n};return a},Zb=function(e,t,n){let r=Xb(e,t);for(let i=0;i<t;i+=1)for(let t=0;t<e;t+=1)r.setPixel(t,i,n(t,i));let i=qb();r.write(i);let a=Jb(),o=i.toByteArray();for(let e=0;e<o.length;e+=1)a.writeByte(o[e]);return a.flush(),`data:image/gif;base64,`+a};Pb.stringToBytes;var Qb=/^[0-9A-Z $%*+\-./:]*$/,$b=.3,ex=e=>e.toUpperCase();function tx(e){let t=Pb(0,`H`);t.addData(e,Qb.test(e)?`Alphanumeric`:`Byte`),t.make();let n=t.getModuleCount(),r=Math.floor(n*$b);r%2==0&&r--;let i=(n-r)/2,a=(e,t)=>e>=i&&e<i+r&&t>=i&&t<i+r;return{n,dark:(e,n)=>!a(e,n)&&t.isDark(e,n),logo:{from:i,size:r}}}function nx(e){return e.secure&&e.serviceWorker&&e.pushManager?`yes`:/iPhone|iPad|iPod/.test(e.userAgent)&&!e.standalone?`home-screen`:`no`}var rx=()=>nx({secure:window.isSecureContext,serviceWorker:`serviceWorker`in navigator,pushManager:`PushManager`in window,userAgent:navigator.userAgent,standalone:navigator.standalone===!0||matchMedia(`(display-mode: standalone)`).matches});function ix(e){let t=e.replace(/-/g,`+`).replace(/_/g,`/`).padEnd(Math.ceil(e.length/4)*4,`=`);return Uint8Array.from(atob(t),e=>e.charCodeAt(0))}function ax(e,t){return!e||e.byteLength!==t.length?!1:new Uint8Array(e).every((e,n)=>e===t[n])}async function ox(){return await navigator.serviceWorker.register(`/sw.js`,{scope:`/`}),navigator.serviceWorker.ready}async function sx(){if((Notification.permission===`granted`?`granted`:await Notification.requestPermission())!==`granted`)throw Error(`Notifications are blocked for Ledung here. Allow them in the settings for it, then switch this on again.`);let{publicKey:e}=await R.pushState(),t=await ox(),n=ix(e),r=await t.pushManager.getSubscription();r&&!ax(r.options.applicationServerKey,n)&&(await r.unsubscribe(),r=null),r??=await t.pushManager.subscribe({userVisibleOnly:!0,applicationServerKey:n}),await R.pushOn(r.toJSON())}async function cx(){await R.pushOff(),await(await(await navigator.serviceWorker.getRegistration(`/`))?.pushManager.getSubscription())?.unsubscribe()}async function lx(){let{on:e}=await R.pushState();return e?!!await(await navigator.serviceWorker.getRegistration(`/`))?.pushManager.getSubscription():!1}function ux(e){return e?`Pushes for this computer come through the first tab: on the phone, switch on push notifications in Settings there, under Phones. They say this computer's name, and tapping one opens this tab.`:`Pushes for this computer come through the first tab once the two computers are linked (Settings → Linked computers); then, on the phone, switch them on in Settings there, under Phones.`}var dx=e=>e?new Date(e).toLocaleString():`never`;function fx({text:e}){let{n:t,dark:n,logo:r}=tx(e),i=[];for(let e=0;e<t;e++)for(let r=0;r<t;r++)n(e,r)&&i.push(`M${r+4},${e+4}h1v1h-1z`);let a=r.from+4+.5,o=r.size-1;return(0,V.jsxs)(`svg`,{className:`qr`,viewBox:`0 0 ${t+8} ${t+8}`,width:220,height:220,role:`img`,"aria-label":`QR code of the pairing link`,children:[(0,V.jsx)(`rect`,{width:t+8,height:t+8,fill:`#fff`}),(0,V.jsx)(`path`,{d:i.join(``),fill:`#000`}),(0,V.jsx)(`image`,{href:`/icon.svg?v=2`,x:a,y:a,width:o,height:o})]})}function px({run:e,linked:t=!1}){let[n,r]=(0,v.useState)(null);return(0,v.useEffect)(()=>{R.thisDevice().then(r,()=>r({remote:!1}))},[]),n?(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Phones`}),n.remote?(0,V.jsx)(mx,{device:n.device,mayAddPasskey:n.mayAddPasskey,unlockedUntil:n.unlockedUntil,linked:t,run:e,onChange:()=>R.thisDevice().then(r)}):(0,V.jsx)(vx,{run:e})]}):null}function mx(e){let{device:t,unlockedUntil:n}=e,[r,i]=(0,v.useState)(Date.now());(0,v.useEffect)(()=>{let e=setInterval(()=>i(Date.now()),15e3);return()=>clearInterval(e)},[]);let a=n!==null&&n>r,o=t.kind===`computer`;return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`This device is paired as `,(0,V.jsx)(`b`,{children:t.name}),o?`, a computer`:``,`. Devices are listed and removed in Settings on the computer Ledung runs on.`]}),t.passkey&&o?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Its passkey is set up: allowing a sensitive call from here asks for it (Touch ID or Windows Hello) each time.`}),(0,V.jsx)(`p`,{children:a?(0,V.jsx)(V.Fragment,{children:`🔓 Logged on: changes need nothing more until you log out, or until 14 days without use.`}):(0,V.jsx)(V.Fragment,{children:`🔒 Logged off: from here you can look, not change anything. Log on with the passkey; it lasts until you log out.`})}),a?(0,V.jsx)(`button`,{onClick:()=>void e.run(async()=>{await R.logOutDevice(),e.onChange()}),children:`Log out`}):(0,V.jsx)(`button`,{onClick:()=>void e.run(async()=>{await R.unlockDevice(),e.onChange()}),children:`Log on`}),Vt()&&(0,V.jsx)(gx,{linked:e.linked})]}):t.passkey?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Its passkey is set up: allowing a sensitive call or writing to a manager from here asks for it (Face ID or fingerprint) each time.`}),(0,V.jsx)(`p`,{children:a?(0,V.jsxs)(V.Fragment,{children:[`🔓 Unlocked for changes until `,new Date(n).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`}),`.`]}):(0,V.jsx)(V.Fragment,{children:`🔒 Locked: from here you can look, not change anything. Unlocking takes the passkey once and lasts 30 minutes.`})}),!a&&(0,V.jsx)(`button`,{onClick:()=>void e.run(async()=>{await R.unlockDevice(),e.onChange()}),children:`Unlock`}),Vt()?(0,V.jsx)(gx,{linked:e.linked}):(0,V.jsx)(_x,{run:e.run,onChange:e.onChange})]}):e.mayAddPasskey&&Vt()?(0,V.jsx)(hx,{run:e.run,onChange:e.onChange}):e.mayAddPasskey?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Set up a passkey now: without it this device can only look, and every change waits for the computer. This is possible in the first 10 minutes after pairing.`}),(0,V.jsx)(`button`,{onClick:()=>void e.run(async()=>{await R.addPasskey(),e.onChange()}),children:`Set up passkey`})]}):(0,V.jsx)(`p`,{className:`muted`,children:`No passkey: this device can only look; changes wait for the computer. To add one, pair this device again from Settings on the computer.`})]})}function hx({run:e,onChange:t}){let[n,r]=(0,v.useState)(null);return(0,v.useEffect)(()=>{if(!n)return;let e=setInterval(()=>{R.thisDevice().then(e=>{e.remote&&e.device.passkey&&t()},()=>{}),Date.now()>n.expiresAt&&r(null)},2e3);return()=>clearInterval(e)},[n,t]),(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Set up a passkey now: without it this device can only look. It is made in a window of its own (here inside another computer's page the browser may not make one), and works here afterwards. This is possible in the first 10 minutes after pairing.`}),n?(0,V.jsxs)(`p`,{children:[(0,V.jsx)(`a`,{className:`button-link`,href:n.url,target:`_blank`,rel:`noopener noreferrer`,children:`Open the passkey window`}),` `,(0,V.jsx)(`span`,{className:`muted`,children:`· then come back here`})]}):(0,V.jsx)(`button`,{onClick:()=>void e(async()=>r(await R.passkeyEnrolLink())),children:`Set up passkey`})]})}function gx({linked:e}){return(0,V.jsx)(`p`,{className:`muted push-switch framed-push`,children:ux(e)})}function _x({run:e,onChange:t}){let n=rx(),[r,i]=(0,v.useState)(null);if((0,v.useEffect)(()=>{n===`yes`&&lx().then(i,()=>i(!1))},[n]),n===`home-screen`)return(0,V.jsx)(`p`,{className:`muted push-switch`,children:`Push notifications on an iPhone need Ledung on the Home Screen: Share → Add to Home Screen, then open it from there and switch them on here.`});if(n===`no`)return(0,V.jsx)(`p`,{className:`muted push-switch`,children:`This browser can't get push notifications.`});if(r===null)return null;let a=n=>void e(async()=>{try{await(n?sx():cx()),i(n)}finally{t()}});return(0,V.jsxs)(`div`,{className:`push-switch`,children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`A notification on this phone when something new waits for you, even with Ledung closed`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r,onChange:e=>a(e.target.checked)}),` Push notifications to this phone`]}),(0,V.jsx)(`p`,{className:`muted`,children:`When something new waits for you on this computer. It says which computer and what kind of item, never the text: that loads when you open it.`})]})}function vx({run:e}){let[t,n]=(0,v.useState)(null),[r,i]=(0,v.useState)(null),[a,o]=(0,v.useState)(Date.now()),s=()=>R.devices().then(e=>{n(e),i(t=>t&&e.devices.length>t.before?null:t)},()=>{});if((0,v.useEffect)(()=>{s()},[]),(0,v.useEffect)(()=>{if(!r)return;let e=setInterval(()=>{o(Date.now()),s()},2e3);return()=>clearInterval(e)},[r]),!t)return null;if(!t.publicName)return(0,V.jsx)(`p`,{className:`muted`,children:`Reaching Ledung from a phone anywhere needs a relay: set "remote" with its "publicName" in the config. Then phones are paired here.`});let c=r&&r.expiresAt>a?r:null;return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`Phones, and other computers' Ledung pages (their tab for this computer), that reach this Ledung at https://`,t.publicName,`. Only a paired device gets in there; the sign-in link does not work there. A phone unlocks for 30 minutes at a time; a computer stays logged on until it logs out.`]}),t.devices.length===0&&(0,V.jsx)(`p`,{className:`muted`,children:`No paired devices.`}),t.devices.map(t=>(0,V.jsxs)(`div`,{className:`device-row`,children:[(0,V.jsxs)(`span`,{children:[(0,V.jsx)(`b`,{children:t.name}),` `,(0,V.jsxs)(`span`,{className:`muted`,children:[`· `,t.kind===`computer`?`computer`:`phone`,` · paired `,t.pairedVia?`through the link from ${t.pairedVia} `:``,dx(t.createdAt),` · last used `,dx(t.lastUsedAt),` · `,t.passkey?`passkey added ${dx(t.passkeyAt)}`:`no passkey`]})]}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e(async()=>{await R.revokeDevice(t.id),await s()}),children:`Revoke`})]},t.id)),c?(0,V.jsxs)(`div`,{className:`pairing`,children:[c.kind===`phone`&&(0,V.jsx)(fx,{text:ex(c.url)}),c.kind===`computer`?(0,V.jsxs)(`p`,{className:`muted`,children:[`On the other computer, click this computer's tab and type the code, or the link, into the field there. It works once, for `,Math.max(0,Math.ceil((c.expiresAt-a)/6e4)),` more minute(s). Then set up the passkey there and log on: it stays logged on until you log out.`]}):(0,V.jsxs)(`p`,{className:`muted`,children:[`Scan it with the phone, or open this link on it. It works once, for `,Math.max(0,Math.ceil((c.expiresAt-a)/6e4)),` more minute(s). Then set up the passkey on the phone, in its Settings → Remote & devices → Phones.`]}),c.kind===`computer`&&(0,V.jsx)(`p`,{className:`pair-code`,children:(0,V.jsx)(`b`,{children:new URL(c.url).pathname.split(`/`).pop().toUpperCase()})}),(0,V.jsx)(`code`,{className:`pair-link`,children:c.url})]}):(0,V.jsx)(`p`,{className:`device-pair-buttons`,children:[`phone`,`computer`].map(n=>(0,V.jsx)(`button`,{onClick:()=>void e(async()=>{let e=await R.pairDevice(n);o(Date.now()),i({...e,before:t.devices.length})}),children:n===`phone`?`Pair a phone`:`Pair a computer`},n))})]})}var yx=e=>e?new Date(e).toLocaleString():`never`;function bx({run:e}){let t=B(),[n,r]=(0,v.useState)(null),[i,a]=(0,v.useState)(null),[o,s]=(0,v.useState)(``),[c,l]=(0,v.useState)(``),[u,d]=(0,v.useState)(Date.now()),f=()=>R.links().then(e=>{r(e),a(t=>t&&e.links.length>t.before?null:t)},()=>r(null));if((0,v.useEffect)(()=>{f()},[]),(0,v.useEffect)(()=>{if(!i)return;let e=setInterval(()=>{d(Date.now()),f()},2e3);return()=>clearInterval(e)},[i]),!n)return null;let p=i&&i.expiresAt>u?i:null;return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Linked computers`}),n.problem?(0,V.jsx)(`p`,{className:`muted`,children:n.problem}):(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Your other computers' Ledungs this one is linked with. Their managers will reach this computer's managers as if they ran here; the link goes end to end through the relay, which can't read it.`}),n.links.length===0&&(0,V.jsx)(`p`,{className:`muted`,children:`No linked computers.`}),n.links.map(t=>(0,V.jsxs)(`div`,{className:`device-row`,children:[(0,V.jsxs)(`span`,{children:[(0,V.jsx)(`b`,{children:t.name}),` `,(0,V.jsxs)(`span`,{className:`muted`,children:[`· `,t.publicName,` · linked `,yx(t.linkedAt),` · last heard from `,yx(t.lastUsedAt)]})]}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e(async()=>{await R.unlink(t.id),await f()}),children:`Unlink`})]},t.id)),p?(0,V.jsxs)(`div`,{className:`pairing`,children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`Paste this in Settings → Linked computers on the other computer. It works once, for `,Math.max(0,Math.ceil((p.expiresAt-u)/6e4)),` more minute(s).`]}),(0,V.jsx)(`code`,{className:`pair-link`,children:p.code}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void navigator.clipboard?.writeText(p.code),children:`Copy`})]}):(0,V.jsx)(`button`,{onClick:()=>void e(async()=>{let e=await R.linkCode();d(Date.now()),a({...e,before:n.links.length})}),children:`Link a computer`}),(0,V.jsxs)(`div`,{className:`link-join`,children:[(0,V.jsx)(`p`,{className:`muted`,children:`Or link with a code made on the other computer:`}),(0,V.jsx)(`input`,{type:`text`,...t,value:o,placeholder:`name.example.com/…`,"aria-label":`Link code from the other computer`,onChange:e=>s(e.target.value)}),(0,V.jsx)(`input`,{type:`text`,...t,value:c,maxLength:40,placeholder:`Its name here, e.g. PC`,"aria-label":`Name for the other computer`,onChange:e=>l(e.target.value)}),(0,V.jsx)(`button`,{disabled:!o.trim(),onClick:()=>void e(async()=>{await R.joinLink(o.trim(),c.trim()),s(``),l(``),await f()}),children:`Link`})]})]})]})}function xx({computers:e,run:t}){return e.length?(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Computers`}),(0,V.jsx)(`p`,{className:`muted`,children:e.length>1?`The tabs at the top of the page, this computer first. A name or colour changed here is this Ledung's; the config's are where they start.`:`Tabs show at the top of the page when the config lists more than one computer. The name is also the remote frame's label.`}),e.map(e=>(0,V.jsx)(Sx,{computer:e,run:t},e.id))]}):null}function Sx({computer:e,run:t}){let n=B(),[r,i]=(0,v.useState)(e.name);(0,v.useEffect)(()=>i(e.name),[e.name]);let a=e.name!==e.config.name||e.colour!==e.config.colour,o=r.trim()!==e.name,s=()=>t(()=>R.editComputer(e.id,{name:r.trim()||null})),c=e.here?`${e.name} (this computer)`:e.name;return(0,V.jsxs)(`div`,{className:`computer-row`,role:`group`,"aria-label":`Computer ${c}`,children:[(0,V.jsxs)(`div`,{className:`computer-name`,children:[(0,V.jsx)(`input`,{type:`text`,...n,value:r,maxLength:24,"aria-label":`Name of ${c}`,onChange:e=>i(e.target.value),onKeyDown:e=>{e.key===`Enter`&&o&&s()}}),o&&(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void s(),children:`Save`}),e.here&&(0,V.jsx)(`span`,{className:`muted`,children:`This computer`}),a&&!o&&(0,V.jsx)(`button`,{className:`small`,title:`Back to ${e.config.name} in ${Et[e.config.colour].label.toLowerCase()}, as the config has it`,onClick:()=>void t(()=>R.editComputer(e.id,{name:null,colour:null})),children:`Use the config's`})]}),(0,V.jsx)(`div`,{className:`swatches`,children:Ot.map(n=>(0,V.jsx)(`button`,{type:`button`,className:`swatch${e.colour===n?` on`:``}`,"aria-pressed":e.colour===n,title:Et[n].label,"aria-label":`${c}: ${Et[n].label}`,onClick:()=>void t(()=>R.editComputer(e.id,{colour:n})),children:(0,V.jsx)(fp,{colour:n,children:`●`})},n))})]})}function Cx(e){let t=/^(\d+)\.(\d+)\.0$/.exec(e);return t?t[2]===`0`?`v${t[1]}`:`v${t[1]}.${t[2]}`:`v${e}`}var wx=new Set,Tx=ft(localStorage),Ex=e=>{Tx=e;for(let e of wx)e()};window.addEventListener(`storage`,e=>{(e.key===`ledung.statusDot`||e.key===null)&&Ex(ft(localStorage))});var Dx=e=>(wx.add(e),()=>{wx.delete(e)}),Ox=()=>Tx;function kx(){return[(0,v.useSyncExternalStore)(Dx,Ox),e=>{pt(un,e),Ex(e)}]}var Ax=new Set,jx=St(localStorage),Mx=e=>{jx=e;for(let e of Ax)e()};window.addEventListener(`storage`,e=>{(e.key===`ledung.compactSidebar`||e.key===null)&&Mx(St(localStorage))});var Nx=e=>(Ax.add(e),()=>{Ax.delete(e)}),Px=()=>jx;function Fx(){return[(0,v.useSyncExternalStore)(Nx,Px),e=>{Ct(un,e),Mx(e)}]}var Ix=new Set,Lx=gt(localStorage),Rx=e=>{Lx=e;for(let e of Ix)e()};window.addEventListener(`storage`,e=>{(e.key===`ledung.archivedLink`||e.key===null)&&Rx(gt(localStorage))});var zx=e=>(Ix.add(e),()=>{Ix.delete(e)}),Bx=()=>Lx;function Vx(){return[(0,v.useSyncExternalStore)(zx,Bx),e=>{_t(un,e),Rx(e)}]}var Hx=`ledung.installDismissed`,Ux=(e,t)=>/Macintosh/.test(e)&&/Safari\//.test(e)&&!/Chrome|Chromium|CriOS|Edg|OPR|Firefox|FxiOS/.test(e)&&t<=1,Wx=(e,t)=>/iPhone|iPad|iPod/.test(e)||/Macintosh/.test(e)&&t>1,Gx=e=>/Chrome|Chromium|Edg\//.test(e);function Kx(e){return e.standalone||e.installed?{kind:`none`}:e.framed?{kind:`none`,reason:`Install this computer's own page, opened in a tab of its own.`}:e.offer?{kind:`button`}:e.refused?{kind:`none`,reason:`Refused for now. Reload the page to be offered it again.`}:Ux(e.userAgent,e.maxTouchPoints)?{kind:`dock`}:Wx(e.userAgent,e.maxTouchPoints)?{kind:`none`,reason:`On an iPhone or iPad, use Share → Add to Home Screen in Safari.`}:e.secure?Gx(e.userAgent)?{kind:`none`,reason:`The browser isn't offering to install this page: it is installed already, or not allowed here. The install icon in the address bar says which.`}:{kind:`none`,reason:`This browser can't install pages as apps; Edge, Chrome and Safari on macOS can.`}:{kind:`none`,reason:`Browsers offer installing only a page at 127.0.0.1 or over HTTPS; this one is plain http.`}}function qx(e){try{return e.getItem(Hx)===`1`}catch{return!1}}function Jx(e){try{e.setItem(Hx,`1`)}catch{}}var Yx=(e,t)=>!t&&e.kind!==`none`,Xx=matchMedia(`(display-mode: standalone)`),Zx=null,Qx=!1,$x=!1,eS=qx(localStorage),tS=new Set,nS=()=>Kx({standalone:Xx.matches||navigator.standalone===!0,installed:Qx,offer:Zx!==null,refused:$x,framed:Vt(),secure:window.isSecureContext,userAgent:navigator.userAgent,maxTouchPoints:navigator.maxTouchPoints??0}),rS={install:nS(),notice:!1},iS=()=>{let e=nS();rS={install:e,notice:Yx(e,eS)};for(let e of tS)e()};rS.notice=Yx(rS.install,eS),window.addEventListener(`beforeinstallprompt`,e=>{e.preventDefault(),Zx=e,$x=!1,iS()}),window.addEventListener(`appinstalled`,()=>{Qx=!0,Zx=null,iS()}),Xx.addEventListener(`change`,iS),window.addEventListener(`storage`,e=>{(e.key===`ledung.installDismissed`||e.key===null)&&(eS=qx(localStorage),iS())});var aS=e=>(tS.add(e),()=>{tS.delete(e)}),oS=()=>rS;async function sS(){let e=Zx;e&&(Zx=null,await e.prompt(),(await e.userChoice).outcome===`accepted`?Qx=!0:$x=!0,iS())}var cS=()=>{Jx(localStorage),eS=!0,iS()};function lS(){return{...(0,v.useSyncExternalStore)(aS,oS),onInstall:sS,onDismiss:cS}}var uS=(0,V.jsxs)(V.Fragment,{children:[`In Safari, choose `,(0,V.jsx)(`b`,{children:`File → Add to Dock`}),`.`]});function dS({app:e,run:t}){return(0,V.jsxs)(`div`,{className:`banner install`,children:[(0,V.jsxs)(`span`,{children:[`Ledung can run as an app, in a window of its own.`,e.install.kind===`dock`&&(0,V.jsxs)(V.Fragment,{children:[` `,uS]})]}),e.install.kind===`button`&&(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void t(e.onInstall),children:`Install as app`}),(0,V.jsx)(`button`,{className:`small`,onClick:e.onDismiss,children:`Not now`})]})}function fS({run:e}){let t=lS(),{install:n}=t;return n.kind===`none`&&!n.reason?null:(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`App`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(`p`,{className:`muted`,children:`Ledung in a window of its own, with its own icon, instead of a browser tab.`}),n.kind===`button`&&(0,V.jsx)(`button`,{className:`primary`,onClick:()=>void e(t.onInstall),children:`Install as app`}),n.kind===`dock`&&(0,V.jsx)(`p`,{children:uS}),n.kind===`none`&&(0,V.jsx)(`p`,{className:`muted`,children:n.reason})]})}function pS(e,t){return!!e&&!t&&e.available&&!e.asked&&e.places.length>0&&!e.places.some(e=>e.present)}function mS(e){let t=e.places.map(e=>e.label);return t.length>1?`${t.slice(0,-1).join(`, `)} and ${t[t.length-1]}`:t[0]??``}function hS(e){return e.kind===`mac`?`Add a Ledung icon to ${mS(e)}?`:`Add a Ledung icon to your ${mS(e)}?`}var gS={desktop:`on your Desktop`,"start-menu":`in the Start menu`,applications:`in Applications`};function _S(e){let t=e.places.map(e=>gS[e.id]??`in ${e.label}`);return`A Ledung icon ${t.length>1?`${t.slice(0,-1).join(`, `)} and ${t[t.length-1]}`:t[0]??``}.`}var vS=`It opens this page, and starts Ledung first if it isn't running.`,yS=null,bS=null,xS=new Set,SS=e=>{yS=e;for(let e of xS)e()};function CS(){return bS??=R.shortcuts().then(SS,()=>SS(null)),bS}var wS=e=>(xS.add(e),()=>{xS.delete(e)});function TS(){return(0,v.useEffect)(()=>void CS(),[]),{view:(0,v.useSyncExternalStore)(wS,()=>yS),act:async e=>SS(await R.shortcutsAct(e))}}function ES({run:e}){let{view:t,act:n}=TS(),[r,i]=(0,v.useState)(!1);if(!t||!pS(t,Vt()))return null;let a=t=>e(async()=>{await n(t),r&&await n(`sign-in-on`)});return(0,V.jsxs)(`div`,{className:`banner install`,children:[(0,V.jsxs)(`span`,{children:[hS(t),` `,vS]}),t.signIn.available&&!t.signIn.on&&(0,V.jsxs)(`label`,{className:`toggle`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r,onChange:e=>i(e.target.checked)}),` `,t.signIn.label]}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void a(`add`),children:`Yes`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void a(`decline`),children:`No`})]})}function DS({run:e}){let{view:t,act:n}=TS();if(!t)return null;let r=t.places.filter(e=>!e.present),i=t.places.filter(e=>e.present);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Shortcuts`}),t.available?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[_S(t),` `,vS,` Ledung then runs in the background, with no window; Stop Ledung below stops it.`]}),(0,V.jsx)(`ul`,{className:`shortcut-places`,children:t.places.map(e=>(0,V.jsxs)(`li`,{children:[(0,V.jsx)(`b`,{children:e.label}),` `,(0,V.jsx)(`span`,{className:`muted`,children:e.present?`added`:`not there`})]},e.id))}),(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[r.length>0&&(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void e(()=>n(`add`)),children:`Add shortcuts`}),i.length>0&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e(()=>n(`remove`)),children:`Remove`})]})]}):(0,V.jsx)(`p`,{className:`muted`,children:t.reason})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Start at sign-in`}),t.signIn.available?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:t.signIn.file??void 0,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:t.signIn.on,onChange:t=>void e(()=>n(t.target.checked?`sign-in-on`:`sign-in-off`))}),` `,t.signIn.label]}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Ledung starts in the background, without opening its page; open it with the icon or the `,(0,V.jsx)(`code`,{children:`ledung`}),` command. Only for you, and no administrator rights are needed.`]})]}):(0,V.jsx)(`p`,{className:`muted`,children:t.signIn.reason})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Log`}),(0,V.jsxs)(`p`,{className:`muted`,children:[t.log.active?`This Ledung runs in the background; what it says goes to`:`Started in the background, Ledung writes what it says to`,` `,(0,V.jsx)(`code`,{children:t.log.file}),t.log.active?`.`:`. This one was started in a terminal or window, so it says it there.`]})]})]})}function OS(){let{view:e}=TS(),[t,n]=(0,v.useState)(`idle`);return!e||Vt()?null:(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Stop Ledung`}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Stops Ledung and its sessions; resume a session after the next start to continue it. Start Ledung again with its icon or the `,(0,V.jsx)(`code`,{children:`ledung`}),` command.`]}),t===`stopped`?(0,V.jsx)(`p`,{children:`Ledung has stopped. This page stays as it was until Ledung runs again.`}):t===`confirming`?(0,V.jsxs)(`span`,{className:`restart-confirm`,children:[(0,V.jsx)(`span`,{className:`muted`,children:`Running sessions stop.`}),(0,V.jsx)(`button`,{className:`small primary`,onClick:async()=>{try{await R.stopLedung(),n(`stopped`)}catch{n(`failed`)}},children:`Stop Ledung`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>n(`idle`),children:`Cancel`})]}):(0,V.jsxs)(`span`,{className:`restart-confirm`,children:[t===`failed`&&(0,V.jsx)(`span`,{className:`restart-problem`,children:`Ledung refused to stop.`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>n(`confirming`),children:`Stop Ledung`})]})]})}function kS(e){return!e||!e.email&&!e.organization?`not seen yet: shown after its first session starts`:[e.email,e.organization,e.plan].filter(Boolean).join(` · `)+(e.seenAt?` (seen ${Eg(e.seenAt)})`:``)}function AS(e){let t=B(),[n,r]=(0,v.useState)(``),[i,a]=(0,v.useState)(``),[o,s]=(0,v.useState)(null),c=t=>[...e.projects.filter(e=>e.account===t).map(e=>e.name),...e.choices.chats===t?[`chats`]:[]].join(`, `)||`no project`,l=t=>(0,V.jsxs)(`select`,{value:e.choices[t]??``,onChange:n=>void e.run(()=>R.setAccountChoices({[t]:n.target.value||null})),children:[(0,V.jsx)(`option`,{value:``,children:`default: this computer's own login`}),e.accounts.map(e=>(0,V.jsxs)(`option`,{value:e.name,children:[e.name,e.email?` (${e.email})`:``]},e.name))]});return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Accounts`}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Each project uses one account, for its manager and all its sessions; chats use the one chosen below. Ledung never moves work between accounts. Accounts can also be listed under `,(0,V.jsx)(`span`,{className:`mono`,children:`claudeAccounts`}),` in the config file (see ledung.config.example.json).`]}),e.configFileProblems.map(e=>(0,V.jsx)(`div`,{className:`banner`,children:e},e)),(0,V.jsxs)(`div`,{children:[(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Account`}),(0,V.jsx)(`th`,{children:`Logged in as`}),(0,V.jsx)(`th`,{children:`Used by`}),(0,V.jsx)(`th`,{})]})}),(0,V.jsxs)(`tbody`,{children:[(0,V.jsxs)(`tr`,{children:[(0,V.jsxs)(`td`,{children:[(0,V.jsx)(`strong`,{children:`default`}),(0,V.jsx)(`div`,{className:`muted`,children:`this computer's own Claude Code login`})]}),(0,V.jsx)(`td`,{children:kS(e.defaultIdentity)}),(0,V.jsx)(`td`,{children:c(null)}),(0,V.jsx)(`td`,{})]}),e.accounts.map(t=>(0,V.jsxs)(`tr`,{children:[(0,V.jsxs)(`td`,{children:[(0,V.jsx)(`strong`,{children:t.name}),t.whatItIsFor&&(0,V.jsx)(`div`,{children:t.whatItIsFor}),t.inConfigFile&&(0,V.jsx)(`div`,{className:`muted`,children:`set in the config file: to remove it for good, take it out there too, or it comes back at the next start`}),(0,V.jsxs)(`div`,{className:`muted`,children:[`sign-in folder `,(0,V.jsx)(`span`,{className:`mono`,children:t.configDir})]}),(0,V.jsxs)(`div`,{className:`muted`,children:[`in containers `,(0,V.jsx)(`span`,{className:`mono`,children:t.containerDir??`~/.ledung-accounts/${t.name}`})]})]}),(0,V.jsx)(`td`,{children:kS(t)}),(0,V.jsx)(`td`,{children:c(t.name)}),(0,V.jsxs)(`td`,{className:`account-actions`,children:[(0,V.jsx)(`button`,{className:`small`,disabled:e.remote,title:e.remote?`Only on the computer Ledung runs on`:`Show ${t.configDir}`,onClick:()=>void e.run(()=>R.openAccountFolder(t.name)),children:`Open folder`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e.run(()=>R.removeAccount(t.name)),children:`Remove`})]})]},t.name))]})]}),(0,V.jsxs)(`div`,{className:`form`,children:[(0,V.jsxs)(`label`,{children:[`Account for chats `,(0,V.jsx)(`span`,{className:`muted`,children:`(new chats run on it; a running chat keeps its account until it restarts)`}),l(`chats`)]}),(0,V.jsxs)(`label`,{children:[`Account for new projects `,(0,V.jsx)(`span`,{className:`muted`,children:`(chosen for you in Add project)`}),l(`newProjects`)]})]}),(0,V.jsx)(`h4`,{children:`Add an account`}),(0,V.jsxs)(`div`,{className:`form`,children:[(0,V.jsxs)(`label`,{children:[`Name `,(0,V.jsx)(`span`,{className:`muted`,children:`(e.g. personal, work)`}),(0,V.jsx)(`input`,{...t,value:n,onChange:e=>r(e.target.value),maxLength:32})]}),(0,V.jsxs)(`label`,{children:[`Sign-in folder in containers `,(0,V.jsx)(`span`,{className:`muted`,children:`(optional; default ~/.ledung-accounts/<name> in the container user's home, or a mounted folder so the sign-in survives a rebuild)`}),(0,V.jsx)(`input`,{...t,value:i,onChange:e=>a(e.target.value),className:`mono`,placeholder:`~/.ledung-accounts/name`})]}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Ledung makes a folder for this account's Claude Code sign-in, and only that: conversations, memory, skills and settings stay the same for every account, so moving a project to another account changes only whose plan and limits it uses. After adding it, sign in once with Claude Code's own `,(0,V.jsx)(`span`,{className:`mono`,children:`/login`}),` as shown (for a container project, inside the container). Ledung never sees or keeps a sign-in token.`]}),(0,V.jsx)(`button`,{className:`primary`,disabled:!n.trim(),onClick:()=>void e.run(async()=>{s(await R.addAccount({name:n.trim(),...i.trim()?{containerDir:i.trim()}:{}})),a(``),r(``)}),children:`Add account`})]}),o&&(0,V.jsxs)(`div`,{className:`banner`,children:[`Added `,(0,V.jsx)(`strong`,{children:o.name}),`. Choose it in a project's settings (⚙ next to the project), or above for chats and new projects.`,` `,`Now sign in once. In PowerShell:`,(0,V.jsx)(`pre`,{className:`mono`,children:`$env:CLAUDE_SECURESTORAGE_CONFIG_DIR="${o.configDir}"; claude`}),`(on macOS or Linux: `,(0,V.jsxs)(`span`,{className:`mono`,children:[`CLAUDE_SECURESTORAGE_CONFIG_DIR="`,o.configDir,`" claude`]}),`), then type `,(0,V.jsx)(`span`,{className:`mono`,children:`/login`}),` and sign in with this account. For a container project, the same inside the container:`,(0,V.jsx)(`pre`,{className:`mono`,children:`docker exec -it <container> sh -c 'CLAUDE_SECURESTORAGE_CONFIG_DIR=${(o.containerDir??`~/.ledung-accounts/${o.name}`).replace(/^~\//,`$HOME/`)} exec claude'`})]})]})]})}var jS=4e3,MS=[`Ctrl`,`Alt`,`Shift`,`Cmd`],NS=/^(?:(?:Ctrl|Alt|Shift|Cmd)\+)+(?:[A-Z]|[0-9])$/;function PS(e){let t=/^(?:Key([A-Z])|Digit([0-9]))$/.exec(e.code);if(!t)return null;let n=[e.ctrlKey&&`Ctrl`,e.altKey&&`Alt`,e.shiftKey&&`Shift`,e.metaKey&&`Cmd`].filter(Boolean);return n.length?`${n.join(`+`)}+${t[1]??t[2]}`:null}function FS(e){if(!NS.test(e))return!1;let t=e.split(`+`).slice(0,-1);return t.every((e,n)=>n===0||MS.indexOf(e)>MS.indexOf(t[n-1]))}function IS(e,t){if(!t)return e;let n={Ctrl:`⌃`,Alt:`⌥`,Shift:`⇧`,Cmd:`⌘`},r=e.split(`+`);return r.slice(0,-1).map(e=>n[e]??e).join(``)+r[r.length-1]}function LS(e,t,n){if(!FS(e))return{refused:`A keybind is Ctrl, Alt or Cmd with a letter or a digit.`};let r=new Set(e.split(`+`).slice(0,-1)),i=e.split(`+`).pop(),a=/^[0-9]$/.test(i),o=t.find(t=>t.key===e&&t.id!==n);return o?{refused:`“${o.name}” has this keybind.`}:!r.has(`Ctrl`)&&!r.has(`Alt`)&&!r.has(`Cmd`)?{refused:`Shift alone types; add Ctrl or Alt.`}:r.has(`Cmd`)?{refused:`Cmd keys belong to the browser and the Mac, and Windows has none.`}:r.has(`Ctrl`)&&r.has(`Alt`)?{refused:`Ctrl+Alt is AltGr on Windows, which types @, { and [ on many keyboards.`}:e===`Ctrl+O`?{refused:`Ctrl+O shows and hides tool calls in Ledung.`}:r.has(`Ctrl`)&&!a?{refused:`${e} is the browser's or the message box's (new tab, copy, find, developer tools…).`}:r.has(`Ctrl`)&&!r.has(`Shift`)?{warning:`On Windows and Linux ${e} switches browser tabs: there it does nothing.`}:r.has(`Alt`)&&!r.has(`Shift`)&&[`D`,`E`,`F`].includes(i)?{refused:`${e} opens the browser's menu or address bar on Windows.`}:r.has(`Alt`)?{warning:`On a Mac ⌥ types a character with this key (⌥2 is @ on a Swedish keyboard): the keybind takes it away there.${a&&!r.has(`Shift`)?` On Linux Alt+1–9 switch browser tabs.`:``}`}:null}function RS(e,t,n=3){let r=[];for(let i of`123456789`){let a=`Ctrl+Shift+${i}`;if(LS(a,e,t)||r.push(a),r.length===n)break}return r}function zS(e,t){return e.filter(e=>e.project===null||e.project===t)}var BS=[`issue`,`branch`,`pr`,`project`,`session`];function VS(e,t){let n=t.branch?/(?:^|[/_-])(\d+)(?=$|[/_-])/.exec(t.branch)?.[1]:void 0,r={issue:t.tickets[0]?.id??(n?`#${n}`:void 0),branch:t.branch??void 0,pr:t.pr?`#${t.pr.number}`:void 0,project:S(t.project),session:t.title},i=[];return{text:e.replace(/\{(issue|branch|pr|project|session)\}/g,(e,t)=>{let n=r[t];return n===void 0?(i.includes(t)||i.push(t),e):n}),missing:i}}function HS(e,t,n){return!(n?!e.send:e.send)||t.missing.length||t.text.trimStart().startsWith(`!`)?`insert`:`send`}function US(e,t,n){let r=e.slice(),[i]=r.splice(t,1);return r.splice(n,0,i),r}function WS(e){if(e.length>50)return`At most 50 macros.`;let t=new Set,n=new Map;for(let r of e){if(!/^[a-z0-9-]{1,40}$/.test(r.id)||t.has(r.id))return`A macro has no id of its own.`;t.add(r.id);let e=r.name.trim();if(!e||e.length>40)return`A macro's name is 1 to 40 characters.`;if(!r.text.trim()||r.text.length>4e3)return`“${e}”: the text is 1 to ${jS} characters.`;if(!r.chip&&!r.key)return`“${e}” has neither a chip nor a keybind, so nothing could use it.`;if(r.key!==null){let t=LS(r.key,[],null);if(t&&`refused`in t)return`“${e}”: ${t.refused}`;let i=n.get(r.key);if(i)return`“${e}” and “${i}” have the same keybind.`;n.set(r.key,e)}}return null}var GS=()=>typeof navigator<`u`&&/Mac|iPhone|iPad/.test(navigator.platform||navigator.userAgent);function KS(e,t){let n=e.send?`Sends`:`Puts in the message box`,r=e.key?` · ${IS(e.key,t)}`:``;return`${n}: ${e.text}${r}\nShift+click: ${e.send?`put it in the message box`:`send it`}`}function qS(e){let t=e.macros.filter(e=>e.chip),n=e.macros.filter(e=>!e.chip),r=(0,v.useRef)(null),i=(0,v.useRef)(null),[a,o]=(0,v.useState)(t.length),[s,c]=(0,v.useState)(!1),l=GS();if((0,v.useLayoutEffect)(()=>{let e=r.current;if(!e)return;let t=()=>{let t=[...e.children],n=t[0]?.offsetTop??0;o(t.filter(e=>e.offsetTop===n).length)};t();let n=new ResizeObserver(t);return n.observe(e),()=>n.disconnect()},[t.map(e=>e.id+e.name).join(`|`)]),(0,v.useEffect)(()=>{if(!s)return;let e=e=>{(e instanceof KeyboardEvent?e.key===`Escape`:!i.current?.contains(e.target))&&c(!1)};return document.addEventListener(`pointerdown`,e),document.addEventListener(`keydown`,e),()=>{document.removeEventListener(`pointerdown`,e),document.removeEventListener(`keydown`,e)}},[s]),!e.macros.length)return null;let u=[...t.slice(a),...n],d=(t,n)=>{c(!1),e.onUse(t,n)};return(0,V.jsxs)(`span`,{className:`macro-bar`,ref:i,children:[(0,V.jsx)(`span`,{className:`macro-chips`,ref:r,children:t.map((e,t)=>(0,V.jsxs)(`button`,{className:`board-chip macro-chip`,title:KS(e,l),tabIndex:t<a?0:-1,"aria-hidden":t<a?void 0:!0,onClick:t=>d(e,t.shiftKey),children:[e.name,e.send&&(0,V.jsx)(`span`,{className:`macro-send`,"aria-label":`sends`,children:` ↵`})]},e.id))}),(0,V.jsx)(`button`,{className:`board-chip macro-chip macro-more${s?` on`:``}`,"aria-expanded":s,"aria-haspopup":`menu`,title:u.length?`${u.length} more macro${u.length===1?``:`s`}`:`Edit macros`,onClick:()=>c(e=>!e),children:u.length?`+${u.length}`:`+`}),s&&(0,V.jsxs)(`div`,{className:`macro-menu`,role:`menu`,children:[u.map(e=>(0,V.jsxs)(`button`,{role:`menuitem`,title:KS(e,l),onClick:t=>d(e,t.shiftKey),children:[(0,V.jsxs)(`span`,{children:[e.name,e.send&&(0,V.jsx)(`span`,{className:`macro-send`,children:` ↵`})]}),e.key?(0,V.jsx)(`kbd`,{children:IS(e.key,l)}):(0,V.jsx)(`span`,{})]},e.id)),u.length>0&&(0,V.jsx)(`hr`,{}),(0,V.jsx)(`button`,{role:`menuitem`,className:`muted`,onClick:()=>{c(!1),e.onEdit()},children:`Edit macros…`})]})]})}var JS=()=>`m-${Date.now().toString(36)}-${Math.random().toString(36).slice(2,7)}`,YS=(e,t)=>e!==null&&e!==`~chats`&&!t.some(t=>t.name===e),XS=(e,t)=>e===null?`Global`:`${S(e)}${YS(e,t)?` (removed)`:``}`;function ZS(e){let[t,n]=(0,v.useState)(null),[r,i]=(0,v.useState)(null),a=GS(),o=t=>e.run(()=>R.setMacros(t)),s=t&&e.macros.some(e=>e.id===t.id)?t.id:null;return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`div`,{className:`settings-h`,children:(0,V.jsx)(`h3`,{children:`Macros`})}),(0,V.jsx)(`p`,{className:`muted`,children:`Text you send often, as a chip in a session's info bar, a keybind, or both. Kept by Ledung, so your phone and other browsers have them too.`}),e.macros.length>0&&(0,V.jsx)(`ul`,{className:`macro-list`,children:e.macros.map((t,c)=>(0,V.jsxs)(`li`,{className:`${t.id===s?`on`:``}${r===c?` dragged`:``}`,draggable:!0,onDragStart:()=>i(c),onDragEnd:()=>i(null),onDragOver:e=>e.preventDefault(),onDrop:t=>{t.preventDefault(),r!==null&&r!==c&&o(US(e.macros,r,c)),i(null)},children:[t.chip?(0,V.jsxs)(`span`,{className:`board-chip macro-chip static`,children:[t.name,t.send&&(0,V.jsx)(`span`,{className:`macro-send`,children:` ↵`})]}):(0,V.jsxs)(`span`,{className:`macro-keyonly`,title:`No chip: this one is on its keybind only`,children:[t.name,t.send&&(0,V.jsx)(`span`,{className:`macro-send`,children:` ↵`}),` `,(0,V.jsx)(`span`,{className:`muted`,children:`· keybind only`})]}),(0,V.jsx)(`span`,{className:`mono macro-text`,title:t.text,children:t.text}),(0,V.jsx)(`span`,{className:`muted macro-what`,children:t.send?`Sends`:`Inserts`}),t.key?(0,V.jsx)(`kbd`,{children:IS(t.key,a)}):(0,V.jsx)(`span`,{className:`muted macro-nokey`,children:`no key`}),(0,V.jsx)(`span`,{className:`chip macro-scope`,title:XS(t.project,e.projects),children:XS(t.project,e.projects)}),(0,V.jsx)(`span`,{className:`macro-move`,title:`Drag to reorder`,"aria-hidden":!0,children:`⋮⋮`}),(0,V.jsxs)(`span`,{className:`macro-row-buttons`,children:[c>0&&(0,V.jsx)(`button`,{className:`small macro-up`,title:`Move up`,"aria-label":`Move ${t.name} up`,onClick:()=>void o(US(e.macros,c,c-1)),children:`↑`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>n({...t}),children:`Edit`})]})]},t.id))}),t?(0,V.jsx)(QS,{draft:t,macros:e.macros,projects:e.projects,mac:a,isNew:!s,onCancel:()=>n(null),onSave:async t=>{let r=s?e.macros.map(e=>e.id===t.id?t:e):[...e.macros,t];await o(r),n(null)},onDelete:s?async()=>{await o(e.macros.filter(e=>e.id!==t.id)),n(null)}:void 0},t.id):(0,V.jsx)(`button`,{className:`primary`,onClick:()=>n({id:JS(),name:``,text:``,send:!1,key:null,chip:!0,project:null}),children:`Add macro`})]})}function QS(e){let[t,n]=(0,v.useState)(e.draft),[r,i]=(0,v.useState)(e.draft.key!==null),[a,o]=(0,v.useState)(!1),s=B(),c=e=>n(t=>({...t,...e})),l=r?t.key:null,u=l?LS(l,e.macros,t.id):null,d={...t,key:l},f=WS([d]),p=RS(e.macros,t.id),m=!t.name.trim()||!t.text.trim()||r&&!t.key||!!u&&`refused`in u||!!f;return(0,V.jsxs)(`div`,{className:`form macro-form`,children:[(0,V.jsx)(`h4`,{children:e.isNew?`New macro`:`Edit “${e.draft.name}”`}),(0,V.jsxs)(`label`,{children:[`Name`,(0,V.jsx)(`input`,{...s,value:t.name,maxLength:40,placeholder:`Run checks`,onChange:e=>c({name:e.target.value})})]}),(0,V.jsxs)(`label`,{children:[`Text`,(0,V.jsx)(`textarea`,{...s,rows:3,value:t.text,placeholder:`Run the checks and tell me what fails.`,onChange:e=>c({text:e.target.value})}),(0,V.jsxs)(`span`,{className:`muted macro-hint`,children:[`Placeholders: `,BS.map(e=>(0,V.jsxs)(`code`,{children:[`{${e}}`,` `]},e)),`filled from the session. One it has no value for is not sent: the text goes into the message box instead.`]})]}),(0,V.jsxs)(`div`,{className:`field`,children:[(0,V.jsx)(`span`,{children:`When used`}),(0,V.jsxs)(`span`,{className:`segmented macro-seg`,children:[(0,V.jsx)(`button`,{className:`small${t.send?``:` on`}`,"aria-pressed":!t.send,onClick:()=>c({send:!1}),children:`Put it in the message box`}),(0,V.jsx)(`button`,{className:`small${t.send?` on`:``}`,"aria-pressed":t.send,onClick:()=>c({send:!0}),children:`Send it at once`})]}),(0,V.jsx)(`span`,{className:`muted macro-hint`,children:`Shift+click a chip for the other one. A text starting with ! always goes into the box.`})]}),(0,V.jsxs)(`label`,{children:[`Where`,(0,V.jsxs)(`select`,{value:t.project??``,onChange:e=>c({project:e.target.value||null}),children:[(0,V.jsx)(`option`,{value:``,children:`Global (every project)`}),e.projects.map(e=>(0,V.jsx)(`option`,{value:e.name,children:e.name},e.name)),YS(e.draft.project,e.projects)&&(0,V.jsx)(`option`,{value:e.draft.project,children:XS(e.draft.project,e.projects)}),(0,V.jsx)(`option`,{value:x,children:`Chats`})]})]}),(0,V.jsxs)(`label`,{className:`toggle macro-switch`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:t.chip,onChange:e=>c({chip:e.target.checked})}),` Show as a chip in the info bar`]}),(0,V.jsxs)(`label`,{className:`toggle macro-switch`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r,onChange:e=>{i(e.target.checked),e.target.checked&&!t.key&&c({key:p[0]??null})}}),` Keybind`]}),r&&(0,V.jsxs)(`div`,{className:`macro-sub`,children:[(0,V.jsxs)(`span`,{className:`macro-keyrow`,children:[(0,V.jsx)(`input`,{...s,className:`mono macro-keyin${u&&`refused`in u?` bad`:``}`,readOnly:!0,"aria-label":`Keybind`,value:a?`Press the keys…`:t.key?IS(t.key,e.mac):``,onFocus:()=>o(!0),onBlur:()=>o(!1),onKeyDown:e=>{if(e.key===`Tab`||e.key===`Escape`)return;e.preventDefault();let t=PS(e.nativeEvent);t&&(c({key:t}),e.target.blur())}}),(0,V.jsx)(`span`,{className:`muted macro-hint`,children:a?`Ctrl, Alt or Cmd with a letter or a digit`:`Click the box, then press the keys.`})]}),u&&`refused`in u&&(0,V.jsx)(`span`,{className:`macro-conflict`,role:`alert`,children:u.refused}),u&&`warning`in u&&(0,V.jsx)(`span`,{className:`macro-warning`,children:u.warning}),u&&p.length>0&&(0,V.jsxs)(`span`,{className:`macro-hint`,children:[`Free: `,p.map(t=>(0,V.jsx)(`button`,{className:`link macro-free`,onClick:()=>c({key:t}),children:(0,V.jsx)(`kbd`,{children:IS(t,e.mac)})},t))]}),!u&&(0,V.jsx)(`span`,{className:`muted macro-hint`,children:`Works in the message box too. A phone has no keys: there it is in the info bar's + menu.`})]}),!t.chip&&!r&&(0,V.jsx)(`span`,{className:`macro-conflict`,children:`With neither a chip nor a keybind nothing could use it.`}),(0,V.jsxs)(`div`,{className:`macro-keyrow`,children:[(0,V.jsx)(`button`,{className:`primary`,disabled:m,onClick:()=>void e.onSave(d),children:`Save`}),(0,V.jsx)(`button`,{onClick:e.onCancel,children:`Cancel`}),e.onDelete&&(0,V.jsx)(`button`,{className:`deny macro-delete`,onClick:()=>void e.onDelete(),children:`Delete`})]})]})}function $S(e){let t=Bp(im),n=xp(e.view,t),r={update:Mp(e.update.view),remote:Ap(e.remote),notifications:e.notify.possible&&!e.notify.on&&!Vt()?`off`:``};return(0,V.jsx)(em,{groups:gp,current:n,words:r,narrow:t,onOpen:t=>e.onOpen(t===null?`settings`:vp(t)),children:n!==null&&(0,V.jsx)(eC,{group:n,...e})})}function eC(e){switch(e.group){case`update`:{let t=jp(e.update.view);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Update Ledung`}),t.update&&(0,V.jsx)(`p`,{className:`muted`,children:t.update}),(0,V.jsx)(fC,{update:e.update})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Restart Ledung`}),(0,V.jsx)(`p`,{className:`muted`,children:t.restart}),!!e.config?.restartFor.length&&(0,V.jsx)(`p`,{className:`config-restart`,children:nC(e.config)}),e.canRestart?(0,V.jsx)(Qp,{hellos:e.hellos}):(0,V.jsx)(`span`,{className:`muted`,title:`This Ledung was started by an older launcher. Restart it once from its console window (Ctrl+C, then Ledung.cmd).`,children:`Restart: from console`})]}),(0,V.jsx)(OS,{}),(0,V.jsx)(DS,{run:e.run})]})}case`claude`:return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(AS,{accounts:e.accounts,choices:e.accountChoices,defaultIdentity:e.defaultIdentity,configFileProblems:e.accountProblems,projects:e.projects,run:e.run,remote:e.throughPublicName}),(0,V.jsx)(jy,{accounts:e.accounts,usageStops:e.usageStops,run:e.run}),(0,V.jsx)(kb,{sessions:e.sessions}),(0,V.jsx)(Ff,{accounts:e.accounts,run:e.run})]});case`sessions`:return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(dp,{run:e.run}),(0,V.jsx)(bb,{})]});case`macros`:return(0,V.jsx)(ZS,{macros:e.macros,projects:e.projects,run:e.run});case`remote`:return(0,V.jsx)(tC,{...e});case`look`:return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Appearance`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(lC,{})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Typing`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(aC,{})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Sidebar`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(oC,{}),(0,V.jsx)(sC,{}),(0,V.jsx)(cC,{})]}),(0,V.jsx)(fS,{run:e.run})]});case`notifications`:return(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Notifications`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(iC,{notify:e.notify,linked:e.computers.some(e=>e.linked)})]});case`config`:return e.config?(0,V.jsx)(rC,{config:e.config}):(0,V.jsx)(`p`,{className:`muted`,children:`…`});default:return(0,V.jsx)(gC,{source:e.source,update:e.update})}}function tC(e){let[t,n]=(0,v.useState)(void 0),[r,i]=(0,v.useState)(null);(0,v.useEffect)(()=>{R.relayAdmin().then(n,()=>n(null))},[]);let a=kp({remote:e.remote,relaySetUp:t?Zv(t):null,boardConfigured:!!e.board?.configured}),o=t&&(0,V.jsx)(Xv,{view:t,onView:n,run:e.run,newComputers:e.newComputers}),s=e.projects[0]?.name,c=[{id:`remote`,name:`Remote access`,state:a.remote,why:`Reach this Ledung from your phone, anywhere, through a relay.`,form:(0,V.jsx)(mC,{remote:e.remote}),primary:!0},{id:`phones`,name:`Phones`,state:a.phones,why:``},{id:`linked`,name:`Linked computers`,state:a.linked,why:``},{id:`relay`,name:`Run a relay`,state:a.relay,why:`Only if you host a relay for other people.`,form:o},{id:`board`,name:`Message board`,state:a.board,why:s?`Off in every project; turn it on in a project's tab.`:`Off; each project turns it on in its own tab.`,go:s?{label:`Projects ›`,view:Tp(s,`board`)}:void 0}].filter(e=>e.state===`off`||e.state===`needs`);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(xx,{computers:e.computers,run:e.run}),a.remote===`on`&&(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Remote access`}),(0,V.jsx)(mC,{remote:e.remote})]}),a.phones===`on`&&(0,V.jsx)(px,{run:e.run,linked:e.computers.some(e=>e.linked)},e.remote?.publicName??`none`),a.linked===`on`&&(0,V.jsx)(bx,{run:e.run},`linked-${e.remote?.publicName??`none`}-${e.remote?.tls??``}`),a.relay===`on`&&(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Relay`}),o]}),a.board===`on`&&(0,V.jsx)(Tn,{board:e.board}),c.length>0&&(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Not set up`}),c.map(t=>r===t.id&&t.state===`off`&&t.form?(0,V.jsxs)(`div`,{className:`offline-open`,role:`group`,"aria-label":t.name,children:[(0,V.jsxs)(`h4`,{children:[(0,V.jsx)(`span`,{children:t.name}),(0,V.jsx)(`button`,{className:`small`,"aria-label":`Close ${t.name}`,title:`Close`,onClick:()=>i(null),children:`✕`})]}),t.form]},t.id):(0,V.jsxs)(`div`,{className:`offline${t.state===`needs`?` needs`:``}`,children:[(0,V.jsx)(`span`,{className:`offline-name`,children:t.name}),(0,V.jsx)(`span`,{className:`offline-why`,children:t.state===`needs`?`Needs remote access first.`:t.why}),t.state===`off`&&t.form&&(0,V.jsx)(`button`,{className:`small${t.primary?` primary`:``}`,onClick:()=>i(t.id),children:`Set up ›`}),t.state===`off`&&t.go&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>e.onOpen(t.go.view),children:t.go.label})]},t.id))]})]})}function nC(e){return`Restart Ledung to apply: ${e.restartFor.join(`, `)}`}function rC(e){let t=e.config,n=new Date(t.readAt).toLocaleString(void 0,{dateStyle:`medium`,timeStyle:`short`});return(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Config file`}),(0,V.jsx)($p,{kind:`config`})]}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Ledung reads `,(0,V.jsx)(`code`,{children:t.file}),` again whenever it changes. Most settings apply at once, to new and resumed sessions; running sessions keep what they started with. A few, such as the port and the network, need Restart Ledung.`]}),(0,V.jsx)(`p`,{children:t.reloaded?`Last reloaded ${n}.`:`Read at start, ${n}; not changed since.`}),t.problem&&(0,V.jsxs)(`p`,{className:`config-problem`,role:`alert`,children:[`The last change was not applied, the settings in use stay: `,t.problem]}),!!t.restartFor.length&&(0,V.jsx)(`p`,{className:`config-restart`,children:nC(t)})]})}function iC({notify:e,linked:t}){return Vt()?(0,V.jsx)(gx,{linked:t}):e.possible?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`A browser notification when something new needs your answer and this page is in the background`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e.on,onChange:t=>void e.set(t.target.checked)}),` Send notifications when an agent is waiting for you`]}),(0,V.jsx)(`p`,{className:`muted`,children:`While a Ledung page is open in this browser.`}),e.denied&&(0,V.jsx)(`p`,{className:`muted`,children:`The browser blocks notifications for this page. Allow them in the browser's site settings (the icon left of the address), then switch this on again.`})]}):(0,V.jsx)(`p`,{className:`muted`,children:`Notifications work when this page is opened on this computer at 127.0.0.1.`})}function aC(){let[e,t]=_n();return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`Off: the browser doesn't correct words as you type. Spell checking and automatic capitals are left to the browser either way`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e,onChange:e=>t(e.target.checked)}),` Autocorrect`]}),(0,V.jsx)(`p`,{className:`muted`,children:`Off: words stay as you type them in the message box, answers and every other text field. Spell checking and capitals are the browser's own either way.`})]})}function oC(){let[e,t]=kx();return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`The coloured dot left of each session in the sidebar; the ship shows much the same`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e,onChange:e=>t(e.target.checked)}),` Status dot`]}),(0,V.jsx)(`p`,{className:`muted`,children:`Off: no dot on the session rows; hover a row for its status, and an ended session's name is faded.`})]})}function sC(){let[e,t]=Vx();return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`The Archived (N) entry under each project in the sidebar, which opens its archived sessions`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e,onChange:e=>t(e.target.checked)}),` Show "Archived" in the sidebar`]}),(0,V.jsx)(`p`,{className:`muted`,children:`Off: no Archived entry under the projects; switch it back on to open their archived sessions.`})]})}function cC(){let[e,t]=Fx(),n=bt.find(t=>t.step===e).label;return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`compact-slider`,title:`Less padding and fewer rows on each session in the sidebar; the ship always stays`,children:[(0,V.jsx)(`span`,{children:`Compact sidebar`}),(0,V.jsx)(vb,{step:e,labels:bt.map(e=>e.label),onPick:e=>t(e),children:(0,V.jsx)(`input`,{type:`range`,min:1,max:bt.length,step:1,value:e,list:`compact-steps`,"aria-valuetext":n,onChange:e=>t(Number(e.target.value))})})]}),(0,V.jsx)(`datalist`,{id:`compact-steps`,children:bt.map(e=>(0,V.jsx)(`option`,{value:e.step,label:e.label},e.step))}),(0,V.jsx)(`p`,{className:`muted`,children:`Each step takes more off the session cards: tighter padding and no date and time, then only the name, the ship and the badge, with a small "+" for a new session. Hover a card for what it no longer shows.`})]})}function lC(){let[e,t]=(0,v.useState)(()=>ot(localStorage)),n=e=>{t(e),st(un,e),ct(document.documentElement,e)};return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`div`,{className:`seg-control`,role:`group`,"aria-label":`Colour scheme`,children:rt.map(t=>(0,V.jsx)(`button`,{className:e===t.id?`on`:``,"aria-pressed":e===t.id,onClick:()=>n(t.id),children:t.label},t.id))}),(0,V.jsx)(`p`,{className:`muted`,children:`System follows the computer's light or dark setting.`})]})}var uC=e=>e?e.slice(0,7):`unknown commit`,dC={waiting:`○`,running:`…`,done:`✓`,failed:`✗`};function fC({update:e}){let{view:t,error:n,act:r}=e,[i,a]=(0,v.useState)(!1);if(n)return(0,V.jsx)(`p`,{className:`restart-problem`,children:n});if(!t)return(0,V.jsx)(`p`,{className:`muted`,children:`…`});if(t.npm)return(0,V.jsx)(pC,{update:e});if(!t.available)return(0,V.jsx)(`p`,{className:`muted`,children:t.reason});let o=t.checking||t.updating||t.restarting,s=t.check,c=!!s&&!s.upToDate&&!t.updating&&!t.restarting;return(0,V.jsxs)(`div`,{className:`update-panel`,children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`Running `,t.running?.commit?(0,V.jsx)(`code`,{children:uC(t.running.commit)}):`an unknown commit (its source is not a git clone)`,`, built from `,(0,V.jsx)(`code`,{children:t.running?.source}),`.`]}),(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[(0,V.jsx)(`button`,{className:`small`,disabled:o,onClick:()=>{a(!1),r(R.updateCheck)},children:t.checking?`Checking…`:`Check for updates`}),s&&!t.checking&&(s.upToDate?(0,V.jsxs)(`span`,{className:`update-ok`,children:[`Up to date (`,uC(s.latest),`)`]}):(0,V.jsxs)(`span`,{children:[s.behind,` new change`,s.behind===1?``:`s`,` on main (`,uC(s.latest),`)`,s.commitKnown?``:`, counted from the source folder`]}))]}),t.checkError&&(0,V.jsx)(`pre`,{className:`update-output restart-problem`,children:t.checkError}),s&&!s.upToDate&&s.changes.length>0&&(0,V.jsx)(`ul`,{className:`update-changes`,children:s.changes.map((e,t)=>(0,V.jsx)(`li`,{children:e},t))}),c&&!t.canRestart&&(0,V.jsx)(`p`,{className:`muted`,children:`Updating ends in a restart, and this Ledung was started by an older launcher. Restart it once from its console window first.`}),c&&t.canRestart&&(i?(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[(0,V.jsx)(`span`,{className:`muted`,children:`Pull main, npm install, npm run release, then restart. Sessions keep running.`}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>{a(!1),r(R.update)},children:`Update now`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>a(!1),children:`Cancel`})]}):(0,V.jsx)(`div`,{className:`restart-confirm`,children:(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>a(!0),children:`Update Ledung`})})),t.steps.length>0&&(0,V.jsx)(`ol`,{className:`update-steps`,children:t.steps.map(e=>(0,V.jsxs)(`li`,{className:`update-step ${e.state}`,children:[(0,V.jsx)(`span`,{className:`update-mark`,children:dC[e.state]}),` `,e.label,e.state===`failed`&&e.output&&(0,V.jsx)(`pre`,{className:`update-output`,children:e.output})]},e.label))}),t.refused&&(0,V.jsx)(`p`,{className:`restart-problem`,children:t.refused}),t.restarting&&(0,V.jsx)(`p`,{className:`muted`,children:`The new release is built. Restarting into it…`})]})}function pC({update:e}){let{view:t,act:n}=e,[r,i]=(0,v.useState)(!1);if(!t?.npm)return null;let a=t.checking||t.updating||t.restarting,o=t.npmCheck&&t.npmCheck.channel===(t.channel??`public`)?t.npmCheck:null,s=!!o?.offered&&!o.upToDate&&!t.updating&&!t.restarting,c=_C[t.channel??`public`];return(0,V.jsxs)(`div`,{className:`update-panel`,children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`Running Ledung `,(0,V.jsx)(`code`,{children:Cx(t.npm.version)}),`, installed from npm, on the `,c,` channel (Settings → About).`]}),(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[(0,V.jsx)(`button`,{className:`small`,disabled:a,onClick:()=>{i(!1),n(R.updateCheck)},children:t.checking?`Checking…`:`Check for updates`}),o&&!t.checking&&(o.offered?o.upToDate?(0,V.jsxs)(`span`,{className:`update-ok`,children:[`Up to date (`,c,`: `,Cx(o.offered),`)`]}):(0,V.jsxs)(`span`,{children:[Cx(o.offered),` is out on `,c]}):(0,V.jsxs)(`span`,{children:[`npm has no `,c,` version yet`]}))]}),t.checkError&&(0,V.jsx)(`pre`,{className:`update-output restart-problem`,children:t.checkError}),s&&!t.canRestart&&(0,V.jsx)(`p`,{className:`muted`,children:t.reason}),s&&t.canRestart&&(r?(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[(0,V.jsxs)(`span`,{className:`muted`,children:[`npm install -g ledung@`,o.offered,`, then restart. Sessions keep running.`]}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>{i(!1),n(R.update)},children:`Update now`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>i(!1),children:`Cancel`})]}):(0,V.jsx)(`div`,{className:`restart-confirm`,children:(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>i(!0),children:`Update Ledung`})})),t.steps.length>0&&(0,V.jsx)(`ol`,{className:`update-steps`,children:t.steps.map((e,t)=>(0,V.jsxs)(`li`,{className:`update-step ${e.state}`,children:[(0,V.jsx)(`span`,{className:`update-mark`,children:dC[e.state]}),` `,e.label,e.state===`failed`&&e.output&&(0,V.jsx)(`pre`,{className:`update-output`,children:e.output})]},t))}),t.refused&&(0,V.jsx)(`p`,{className:`restart-problem`,children:t.refused}),t.restarting&&(0,V.jsx)(`p`,{className:`muted`,children:`The new version is installed. Restarting into it…`}),!t.steps.length&&!s&&(0,V.jsx)(`p`,{className:`muted`,children:t.reason})]})}function mC(e){let t=Ab(e.remote);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`remote-state ${e.remote?.state??`off`}`,children:t.label}),t.detail&&(0,V.jsx)(`p`,{className:`muted`,children:t.detail}),e.remote?.tls&&(0,V.jsx)(`p`,{className:`remote-tls`,children:e.remote.tls}),e.remote?.certificate&&(0,V.jsx)(hC,{cert:e.remote.certificate}),(0,V.jsx)(Yv,{remote:e.remote})]})}function hC({cert:e}){let t=Nb(e,Date.now()),[n,r]=(0,v.useState)(!1),[i,a]=(0,v.useState)(null);return(0,V.jsxs)(`div`,{className:`remote-certificate`,children:[(0,V.jsx)(`p`,{className:t.warn?`remote-tls`:`remote-state connected`,children:t.label}),t.detail&&(0,V.jsx)(`p`,{className:`muted`,children:t.detail}),t.copy&&e.accountUrl&&(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`ACME account (`,e.acme,`): `,(0,V.jsx)(`code`,{children:e.accountUrl}),` `,(0,V.jsx)(Df,{text:e.accountUrl})]}),e.record&&(0,V.jsxs)(`p`,{className:`muted`,children:[`CAA record: `,(0,V.jsx)(`code`,{className:`remote-record`,children:e.record}),` `,(0,V.jsx)(Df,{text:e.record})]}),(0,V.jsx)(`div`,{className:`restart-confirm`,children:(0,V.jsx)(`button`,{className:`small`,disabled:n,onClick:()=>{r(!0),a(null),R.certificateCheck().catch(e=>a(e.message)).finally(()=>r(!1))},children:n?`Checking…`:`Check now`})})]}),i&&(0,V.jsx)(`p`,{className:`restart-problem`,children:i})]})}function gC({source:e,update:t}){return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`About`}),(0,V.jsx)(`p`,{className:`muted`,children:`Ledung is free software under the GNU Affero General Public License, version 3, with an additional permission for Anthropic's software; a commercial license is also available.`}),(0,V.jsxs)(`p`,{className:`muted`,children:[`It runs Anthropic's Claude Agent SDK and Claude Code, installed from npm under `,(0,V.jsx)(`a`,{href:`https://code.claude.com/docs/en/legal-and-compliance`,target:`_blank`,rel:`noreferrer`,children:`Anthropic's own terms`}),`. They are not covered by Ledung's license.`]}),e&&(0,V.jsxs)(`p`,{className:`muted`,children:[`Running `,(0,V.jsx)(`code`,{children:e.version}),`. `,(0,V.jsx)(`a`,{href:e.url,target:`_blank`,rel:`noreferrer`,children:`Source`})]}),t.view&&(0,V.jsx)(vC,{update:t})]})}var _C={public:`Public`,dev:`Dev`};function vC({update:e}){let t=e.view,n=t.channel??`public`;return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`h3`,{children:`Update channel`}),(0,V.jsx)(`div`,{className:`restart-confirm`,role:`radiogroup`,"aria-label":`Update channel`,children:[`public`,`dev`].map(r=>(0,V.jsxs)(`label`,{children:[(0,V.jsx)(`input`,{type:`radio`,name:`update-channel`,checked:n===r,disabled:t.updating||t.restarting,onChange:()=>e.act(()=>R.updateChannel(r))}),` `,_C[r]]},r))}),(0,V.jsxs)(`p`,{className:`muted`,children:[n===`dev`?`Dev: updates to dev builds, made after changes are merged and before a public release, as well as public releases.`:`Public: updates to public releases only, as npm install -g ledung gets them.`,` `,t.npm?`Check for updates is under Update & restart.`:`This Ledung updates from main in the folder it was built from, so the channel applies only once it is installed from npm.`]})]})}var yC=(e,t)=>`bt:${e}#${t}`;function bC(e){let t=/^bt:([^#]+)#(.+)$/.exec(e??``);return t?{repo:t[1],id:t[2]}:null}var xC=(e,t)=>`#/board/${e}/${encodeURIComponent(t)}`;function SC(e){let t=/^#\/board\/([A-Za-z0-9_.-]+\/[A-Za-z0-9_.-]+)\/([^/]+)$/.exec(e);if(!t)return null;try{return{repo:t[1],id:decodeURIComponent(t[2])}}catch{return null}}function CC(e,t){return e.mine?`this Ledung's manager of project ${e.fromProject??`unknown`}`:e.viaLedung?`@${e.author}'s Ledung${e.fromProject?`, project ${e.fromProject}`:``}`:`typed on ${t} by @${e.author}`}function wC(e){let t=e.deliveries.map(t=>{switch(t.kind){case`wake`:return{text:`woke ${t.project}`,level:`ok`,project:t.project};case`quiet`:return{text:`quiet to ${t.project}`,level:`quiet`,project:t.project};case`channel`:return{text:`channel, ${t.project}`,level:`quiet`,project:t.project};case`ignored`:return{text:`not delivered to ${t.project}: its allowlist does not name @${e.author}`,level:`warn`,project:t.project}}});return t.length?t:e.status===`sent`?[{text:`sent from this Ledung`,level:`none`}]:e.status===`ignored`?[{text:`not delivered: no project here allows @${e.author}; only the id was kept, not the text`,level:`warn`}]:e.status===`quiet`?[{text:`not delivered: it reached no manager (no front desk, or the project's board is off)`,level:`warn`}]:[{text:`not for this Ledung`,level:`none`}]}var TC={project:``,repo:``,unreadOnly:!1,notDelivered:!1},EC=e=>e.dropped+e.refused+e.unsent>0,DC=(e,t=``)=>t?e.unread[t]??0:Object.values(e.unread).reduce((e,t)=>e+t,0);function OC(e,t){return e.filter(e=>(!t.repo||e.repo===t.repo)&&(!t.project||e.projects.includes(t.project))&&(!t.unreadOnly||DC(e,t.project)>0)&&(!t.notDelivered||EC(e)))}var kC=e=>e&&/^https:\/\//.test(e)?e:null;function AC(e,t){let[n,r]=(0,v.useState)({data:null,error:null});return(0,v.useEffect)(()=>{let t=!0;return e().then(e=>t&&r({data:e,error:null}),e=>t&&r(t=>({data:t.data,error:e.message}))),()=>{t=!1}},t),n}var jC=TC,MC=e=>e.length>4?`${e.slice(0,4).join(`, `)} +${e.length-4}`:e.join(`, `);function NC(e){let{data:t,error:n}=AC(()=>R.boardThreads(),[e.board]),[r,i]=(0,v.useState)(jC),a=e=>i(t=>jC={...t,...e}),o=(0,v.useMemo)(()=>Object.keys(e.board?.projects??{}).filter(t=>e.board.projects[t].repo).sort(),[e.board]),s=(e.board?.boards??[]).map(e=>e.repo),c=(0,v.useMemo)(()=>OC(t?.threads??[],r),[t,r]),l=r.project||r.repo||r.unreadOnly||r.notDelivered;return(0,V.jsxs)(`div`,{className:`waiting-view board-view`,children:[(0,V.jsxs)(`header`,{className:`session-head`,children:[(0,V.jsxs)(`div`,{className:`session-head-text`,children:[(0,V.jsx)(`h2`,{children:`Board`}),(0,V.jsx)(`div`,{className:`muted`,children:`Read-only. The managers' messages with other people's Ledungs, newest first. Looking here posts nothing and marks nothing read.`})]}),(0,V.jsx)(`div`,{className:`session-corner`,children:(0,V.jsx)(`button`,{className:`small`,onClick:e.onOpenSettings,children:`Board settings`})})]}),(0,V.jsxs)(`div`,{className:`board-filters`,role:`group`,"aria-label":`Filter threads`,children:[o.length>1&&(0,V.jsxs)(`label`,{children:[`Project`,(0,V.jsxs)(`select`,{value:r.project,onChange:e=>a({project:e.target.value}),children:[(0,V.jsx)(`option`,{value:``,children:`All projects`}),o.map(e=>(0,V.jsx)(`option`,{value:e,children:e},e))]})]}),s.length>1&&(0,V.jsxs)(`label`,{children:[`Board`,(0,V.jsxs)(`select`,{value:r.repo,onChange:e=>a({repo:e.target.value}),children:[(0,V.jsx)(`option`,{value:``,children:`All boards`}),s.map(e=>(0,V.jsx)(`option`,{value:e,children:e},e))]})]}),(0,V.jsxs)(`label`,{className:`toggle`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r.unreadOnly,onChange:e=>a({unreadOnly:e.target.checked})}),` Unread only`]}),(0,V.jsxs)(`label`,{className:`toggle`,title:`Threads with a post that reached no manager: dropped (sender not allowed), refused by a project's allowlist, or for nobody's inbox`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r.notDelivered,onChange:e=>a({notDelivered:e.target.checked})}),` Not delivered`]}),l&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>{jC=TC,i(TC)},children:`Clear filters`})]}),(0,V.jsxs)(`div`,{className:`waiting-list board-list`,children:[n&&(0,V.jsx)(`p`,{className:`board-error`,children:n}),!t&&!n&&(0,V.jsx)(`p`,{className:`muted`,children:`Reading the board…`}),t&&c.length===0&&(0,V.jsx)(`p`,{className:`muted`,children:l?`No thread matches these filters.`:`No threads yet. Posts from the board appear here once Ledung has seen them.`}),c.map(t=>(0,V.jsx)(PC,{t,filters:r,onOpen:e.onOpen,showRepo:s.length>1},`${t.repo}#${t.id}`)),t?.truncated&&(0,V.jsxs)(`p`,{className:`muted`,children:[`Only the `,t.threads.length,` most recent threads are listed.`]})]})]})}function PC({t:e,filters:t,onOpen:n,showRepo:r}){let i=DC(e,t.project),a=[e.dropped?`${e.dropped} dropped (sender not allowed)`:``,e.refused?`${e.refused} refused by a project's allowlist`:``,e.unsent?`${e.unsent} reached no manager`:``].filter(Boolean),o=e.last,s=o?o.mine?`${o.fromProject??`this Ledung`}`:o.viaLedung?`@${o.author}'s Ledung`:`@${o.author}`:``;return(0,V.jsxs)(`button`,{className:`board-thread-card${i?` unread`:``}`,onClick:()=>n(yC(e.repo,e.id)),children:[(0,V.jsxs)(`span`,{className:`board-thread-top`,children:[(0,V.jsxs)(`span`,{className:`board-thread-title`,children:[i>0&&(0,V.jsx)(`span`,{className:`unread-dot`,"aria-label":`unread`}),e.onlyDropped?`Thread ${e.id} (dropped posts only)`:e.title]}),(0,V.jsx)(`span`,{className:`muted board-thread-time`,children:Eg(e.updatedAt)})]}),(0,V.jsxs)(`span`,{className:`board-thread-meta muted`,children:[(0,V.jsx)(`span`,{className:`mono`,children:r?`${e.repo} #${e.id}`:`#${e.id}`}),e.participants.length>0&&(0,V.jsxs)(V.Fragment,{children:[` · `,MC(e.participants)]})]}),(0,V.jsxs)(`span`,{className:`board-thread-chips`,children:[i>0&&(0,V.jsxs)(`span`,{className:`chip accent`,children:[i,` unread`]}),e.projects.map(e=>(0,V.jsx)(`span`,{className:`chip`,children:e},e)),a.map(e=>(0,V.jsx)(`span`,{className:`chip warn`,children:e},e))]}),o&&(0,V.jsxs)(`span`,{className:`board-thread-last`,children:[(0,V.jsxs)(`strong`,{children:[s,`:`]}),` `,o.text||`(empty)`]})]})}function FC(e){let{data:t,error:n}=AC(()=>R.boardThread(e.repo,e.id),[e.repo,e.id,e.board]),r=t=>e.projects.find(e=>e.name===t)?.managerId??null,i=kC(t?.url??null);return(0,V.jsxs)(`div`,{className:`waiting-view board-view`,children:[(0,V.jsxs)(`header`,{className:`session-head`,children:[(0,V.jsxs)(`div`,{className:`session-head-text`,children:[(0,V.jsx)(`h2`,{children:t&&!t.missing?t.title:`Thread ${e.id}`}),(0,V.jsxs)(`div`,{className:`muted`,children:[(0,V.jsxs)(`span`,{className:`mono`,children:[e.repo,` #`,e.id]}),t&&t.participants.length>0&&(0,V.jsxs)(V.Fragment,{children:[` · `,MC(t.participants)]})]})]}),(0,V.jsx)(`div`,{className:`session-corner`,children:(0,V.jsx)(`button`,{className:`small`,onClick:e.onBack,children:`← Board`})})]}),(0,V.jsxs)(`div`,{className:`waiting-list board-thread-page`,children:[(0,V.jsxs)(`p`,{className:`muted board-readonly`,children:[`Read-only: nothing is posted from here and opening this does not mark anything read.`,i&&(0,V.jsxs)(V.Fragment,{children:[` `,(0,V.jsxs)(`a`,{href:i,target:`_blank`,rel:`noopener noreferrer`,children:[`Open the thread on `,t?.service??`the board`]}),`.`]})]}),n&&(0,V.jsx)(`p`,{className:`board-error`,children:n}),!t&&!n&&(0,V.jsx)(`p`,{className:`muted`,children:`Reading the thread…`}),t?.missing&&(0,V.jsx)(`p`,{className:`muted`,children:`Ledung holds no posts of this thread. It may be older than the board's first check here, or on a board no project here uses.`}),t?.truncated&&(0,V.jsxs)(`p`,{className:`muted`,children:[`Only the latest `,t.posts.length,` posts are shown.`]}),t?.posts.map(n=>(0,V.jsx)(LC,{p:n,service:t.service,managerOf:r,onOpen:e.onOpen},n.id))]})]})}function IC({files:e}){return(0,V.jsx)(`ul`,{className:`board-attachments`,children:e.map((e,t)=>{let n=e.size>=1048576?`${(e.size/1048576).toFixed(1)} MB`:`${Math.max(1,Math.round(e.size/1024))} KB`,r=`${e.name} · ${e.kind===`text`?`text`:e.kind.toUpperCase()} · ${n}`;if(e.file&&e.kind!==`text`){let n=wf(``,e.file);return(0,V.jsxs)(`li`,{children:[(0,V.jsx)(`a`,{href:n,target:`_blank`,rel:`noopener noreferrer`,children:(0,V.jsx)(`img`,{src:n,alt:e.name})}),(0,V.jsx)(`span`,{children:r})]},t)}let i=e.pruned?`pruned`:e.error?`not fetched: ${e.error}`:`in the board cache`;return(0,V.jsx)(`li`,{className:`muted`,children:(0,V.jsxs)(`span`,{children:[r,` · `,i]})},t)})})}function LC({p:e,service:t,managerOf:n,onOpen:r}){let i=e.mine?`out`:e.viaLedung?`ledung`:`typed`,a=e.deliveries.some(e=>!e.read),o=kC(e.url);return(0,V.jsxs)(`div`,{className:`msg board-post board-post-card ${i}${e.text===null?` dropped`:``}${a?` unread`:``}`,children:[(0,V.jsxs)(`div`,{className:`msg-meta`,children:[(0,V.jsx)(`span`,{className:`who`,children:CC(e,t)}),a&&(0,V.jsx)(`span`,{className:`chip accent`,children:`unread`}),(0,V.jsx)(`time`,{className:`time`,children:Eg(e.at)}),o&&(0,V.jsxs)(`a`,{className:`board-post-link`,href:o,target:`_blank`,rel:`noopener noreferrer`,children:[`on `,t]})]}),e.recipients.length>0&&(0,V.jsxs)(`div`,{className:`board-thread`,children:[`To `,e.recipients.join(`, `)]}),e.text===null?(0,V.jsxs)(`div`,{className:`msg-body muted`,children:[`Dropped: no project here allows @`,e.author,`, so Ledung kept only that this post exists, not its text.`]}):(0,V.jsx)(`div`,{className:`msg-body plain`,children:e.text}),e.attachments.length>0&&(0,V.jsx)(IC,{files:e.attachments}),(0,V.jsx)(`ul`,{className:`board-delivery-list`,children:wC(e).map((e,t)=>{let i=e.project?n(e.project):null;return(0,V.jsxs)(`li`,{className:`delivery-${e.level}`,children:[e.text,i&&(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsxs)(`button`,{className:`link`,onClick:()=>r(i),children:[e.project,`'s manager chat`]})]})]},t)})})]})}var RC=80;function zC({value:e,onSave:t,onDone:n,label:r}){let i=B(),[a,o]=(0,v.useState)(e),s=a.replace(/\s+/g,` `).trim();return(0,V.jsx)(`input`,{...i,className:`name-editor`,"aria-label":r,autoFocus:!0,maxLength:RC,value:a,onFocus:e=>e.currentTarget.select(),onChange:e=>o(e.target.value),onClick:e=>e.stopPropagation(),onBlur:n,onKeyDown:r=>{if(r.stopPropagation(),r.key===`Escape`)n();else if(r.key===`Enter`&&!r.nativeEvent.isComposing){if(r.preventDefault(),!s)return;s===e?n():t(s).then(n)}}})}function BC(e,t){return VC(e)-VC(t)||(e.position!==null&&t.position!==null?e.position-t.position:t.createdAt-e.createdAt)}function VC(e){return e.position===null?e.status===`ended`?2:0:1}function HC(e,t,n){let r=e.indexOf(t);if(r<0)return e;let i=e.filter(e=>e!==t),a=Math.max(0,Math.min(i.length,n>r?n-1:n));return[...i.slice(0,a),t,...i.slice(a)]}function UC(e,t){let n=e.findIndex(e=>t<e);return n<0?e.length:n}function WC(e,t,n){let r=e.indexOf(t);return n===r||n===r+1}var GC=5,KC=450,qC=8,JC=28;function YC(e){let t=(0,v.useRef)(null),[n,r]=(0,v.useState)(null),i=(0,v.useRef)(null),a=(0,v.useRef)(null),o=(0,v.useRef)(!1),s=(0,v.useRef)(e);s.current=e;let c=(0,v.useRef)(null),l=e=>[...t.current?.querySelectorAll(`[data-drag]`)??[]].filter(t=>t.dataset.drag===e),u=(e,t)=>t===`projects`?e.closest(`.project-group`)??e:e,d=(e,n,r)=>{let i=l(e.group),a=i.find(t=>t.dataset.dragId===e.id),o=(e.group===`projects`?t.current:a?.closest(`.project-group`))?.getBoundingClientRect();if(!o||n<o.left||n>o.right||r<o.top||r>o.bottom)return null;let s=UC(i.map(t=>{let n=u(t,e.group).getBoundingClientRect();return n.top+n.height/2}),r);return WC(i.map(e=>e.dataset.dragId),e.id,s)?null:s},f=e=>{let t=a.current;i.current?.timer&&clearTimeout(i.current.timer),i.current=null,a.current=null,c.current?.(),c.current=null,document.body.classList.remove(`sidebar-dragging`),r(null),t&&(o.current=!0,setTimeout(()=>{o.current=!1},0),e&&t.slot!==null&&s.current(t.group,HC(l(t.group).map(e=>e.dataset.dragId),t.id,t.slot)))},p=e=>{a.current={group:e.group,id:e.id,slot:null},document.body.classList.add(`sidebar-dragging`),r(a.current),e.touch&&navigator.vibrate?.(10)},m=e=>{let n=t.current;if(!n)return;let r=n.scrollHeight>n.clientHeight?n:n.closest(`.sidebar`);if(!r)return;let i=r.getBoundingClientRect();e<i.top+JC?r.scrollBy(0,-10):e>i.bottom-JC&&r.scrollBy(0,10)};return(0,v.useEffect)(()=>{let e=t.current;if(!e)return;let n=e=>{a.current&&e.preventDefault()};return e.addEventListener(`touchmove`,n,{passive:!1}),()=>{e.removeEventListener(`touchmove`,n),c.current?.()}},[]),{nav:t,drag:n,handlers:{onPointerDown:e=>{if(e.button!==0||i.current)return;let n=e.target.closest(`[data-drag]`);if(!n||!t.current?.contains(n))return;let o=e.pointerType===`touch`,s={pointerId:e.pointerId,x:e.clientX,y:e.clientY,group:n.dataset.drag,id:n.dataset.dragId,touch:o,timer:null};if(i.current=s,o)s.timer=window.setTimeout(()=>{s.timer=null,i.current===s&&p(s)},KC);else try{n.setPointerCapture(e.pointerId)}catch{}let l=e=>{if(e.pointerId!==s.pointerId)return;let t=Math.hypot(e.clientX-s.x,e.clientY-s.y);if(!a.current){if(s.touch){t>qC&&f(!1);return}if(t<GC)return;p(s)}let n=a.current,i=d(n,e.clientX,e.clientY);i!==n.slot&&(a.current={...n,slot:i},r(a.current)),m(e.clientY)},u=e=>{e.pointerId===s.pointerId&&f(!0)},h=e=>{e.pointerId===s.pointerId&&f(!1)},g=e=>{e.key===`Escape`&&a.current&&(e.preventDefault(),e.stopPropagation(),f(!1))};window.addEventListener(`pointermove`,l),window.addEventListener(`pointerup`,u),window.addEventListener(`pointercancel`,h),document.addEventListener(`keydown`,g,!0),c.current=()=>{window.removeEventListener(`pointermove`,l),window.removeEventListener(`pointerup`,u),window.removeEventListener(`pointercancel`,h),document.removeEventListener(`keydown`,g,!0)}},onClickCapture:e=>{o.current&&(e.preventDefault(),e.stopPropagation())},onContextMenu:e=>{(i.current?.touch||a.current)&&e.preventDefault()}}}}var XC=`ledung.sidebar.folded`,ZC=`ledung.sidebar.foldedSessions`,QC=(e,t,n)=>({count:(e?.count??0)+1,pending:(e?.pending??0)+(n[t.s.id]??0),working:(e?.working??!1)||ut(t.s)===`running`});function $C(e,t){let n=[],r=null,i=null,a=null;return e.forEach((o,s)=>{o.depth===0&&(i=o.s.id,a=null);let c=t.folded||o.depth>0&&i!==null&&t.foldedSessions.includes(i),l=o.depth===0&&e[s+1]?.depth===1;if(!c||o.s.id===t.openId){let e={...o,...c?{drag:null}:{},folds:l,folded:l&&t.foldedSessions.includes(o.s.id),hidden:null};n.push(e),o.depth===0&&(a=e)}else t.folded?r=QC(r,o,t.pending):a&&(a.hidden=QC(a.hidden,o,t.pending))}),t.folded&&!r&&(r={count:0,pending:0,working:!1}),{rows:n,project:r}}function ew(e,t){try{let n=JSON.parse(e.getItem(t)??`[]`);return Array.isArray(n)?n.filter(e=>typeof e==`string`):[]}catch{return[]}}function tw(e,t,n){try{n.length?e.setItem(t,JSON.stringify(n)):e.removeItem(t)}catch{}}var nw=e=>ew(e,XC),rw=(e,t)=>tw(e,XC,t),iw=e=>ew(e,ZC),aw=(e,t)=>tw(e,ZC,t);function ow(e,t,n=()=>!0){let r=e.filter(e=>e!==t&&n(e));return e.includes(t)?r:[...r,t]}function sw(e,t){let n=[e.container,e.host===`github.com`?null:e.host].filter(Boolean).join(`, `),r=e=>e.toLocaleString(`en-US`),i=e.polling===`slow`?` · PRs checked every 10 min`:e.polling===`stopped`?` · PRs not checked until then`:``;return`GitHub${n?` (${n})`:``}: ${r(e.remaining)} of ${r(e.limit)} left until ${t(e.resetAt)}${i}`}function cw(e,t){return e.filter(e=>e.resetAt>t)}function lw(e){return e.polling===`stopped`?`critical`:e.polling===`slow`?`warning`:``}var uw=[`settings`,`accounts`,`add`,`chats`],dw=e=>!!e&&(uw.includes(e)||/^(settings|chats):/.test(e));function fw(e,t,n){return dw(n)?dw(e)?{depth:t.depth+1,root:t.root}:{depth:1,root:!1}:{depth:0,root:!1}}function pw(e){return e.depth>0&&!e.root?{back:e.depth}:{start:!0}}var mw=e=>e.key===`Escape`&&!e.defaultPrevented&&!e.isComposing,hw=e=>e===null?`phone-list`:`phone-pane`;function gw(e){return e?.ledungFromList===!0?{back:1}:{open:null}}var _w=e=>e?null:`overview`,vw=e=>`ledung.draft.${e}`;function yw(e,t){try{return e.getItem(vw(t))??``}catch{return``}}function bw(e,t,n){try{n?e.setItem(vw(t),n):e.removeItem(vw(t))}catch{}}function xw(e,t=localStorage){let[n,r]=(0,v.useState)(()=>yw(t,e)),i=(0,v.useRef)(n),a=(0,v.useRef)(n);(0,v.useEffect)(()=>{i.current=n});let o=(0,v.useCallback)(()=>{i.current!==a.current&&(a.current=i.current,bw(t,e,i.current))},[t,e]);return(0,v.useEffect)(()=>{if(n===a.current)return;let e=setTimeout(o,300);return()=>clearTimeout(e)},[n,o]),(0,v.useEffect)(()=>{let e=()=>{document.visibilityState===`hidden`&&o()};return window.addEventListener(`pagehide`,o),document.addEventListener(`visibilitychange`,e),()=>{window.removeEventListener(`pagehide`,o),document.removeEventListener(`visibilitychange`,e),o()}},[o]),[n,r]}function Sw(e){let t=(0,v.useRef)(e);return(0,v.useLayoutEffect)(()=>{t.current=e}),(0,v.useCallback)((...e)=>t.current(...e),[])}function Cw(e){let t=e.status===`ended`,n=!t&&e.status!==`stopping`;return{menu:[...e.role===`manager`?[`away`]:[],`permissions`,...e.role===`session`?[`priority`]:[],`toolCalls`,`usage`,...n?[`pause`,`stop`]:[],...e.claudeVersion?[`version`]:[]],header:[...e.status===`queued`?[`startNow`]:[],...e.clearDue!=null&&!t?[`clear`]:[],...e.compacting&&!t?[`compacting`]:[],...t&&e.claudeSessionId?[`resume`]:[],...t&&e.role===`session`?[`archive`]:[]]}}var ww=e=>e.status!==`ended`&&e.status!==`stopping`,Tw={connected:`connected`,failed:`failed`,"needs-auth":`needs sign-in`,pending:`starting`,disabled:`disabled`},Ew=e=>e.status===`running`||e.status===`waiting`,Dw=e=>e.ctrlKey&&!e.metaKey&&!e.altKey&&!e.shiftKey&&!e.isComposing&&(/^[a-z]$/i.test(e.key)?e.key.toLowerCase()===`o`:e.code===`KeyO`),Ow=e=>e.key===`Escape`&&!e.defaultPrevented&&!e.isComposing;function kw(e){return`${e<10?e.toFixed(1):Math.round(e)} ${e>=.95&&e<1.05?`core`:`cores`}`}function Aw(e){return e>=1024**3?`${(e/1024**3).toFixed(e>=10*1024**3?0:1)} GB`:e>=1024**2?`${Math.round(e/1024**2)} MB`:`${Math.round(e/1024)} KB`}function jw(e){let t=Math.round(e/1e3);return t<60?`${t} s`:t<3600?`${Math.round(t/60)} min`:`${(t/3600).toFixed(1)} h`}var Mw={normal:`Normal`,high:`High`,critical:`Critical`};function Nw({label:e,used:t,total:n,text:r}){let i=n>0?t/n:0,a=i>=.95?`critical`:i>=.8?`warning`:`good`,o={good:`●`,warning:`▲`,critical:`■`}[a];return(0,V.jsxs)(`div`,{className:`limit`,title:`${e}: ${r}${a===`good`?``:a===`warning`?` (busy)`:` (full)`}`,children:[(0,V.jsxs)(`div`,{className:`limit-head`,children:[(0,V.jsx)(`span`,{children:e}),(0,V.jsxs)(`span`,{className:`limit-status ${a}`,children:[o,` `,Math.round(i*100),`%`]})]}),(0,V.jsx)(`div`,{className:`limit-track`,children:(0,V.jsx)(`div`,{className:`limit-fill ${a}`,style:{width:`${Math.min(100,i*100)}%`}})}),(0,V.jsx)(`div`,{className:`limit-sub muted`,children:r})]})}function Pw(e){let t=e.machine,[n,r]=(0,v.useState)(``);if((0,v.useEffect)(()=>r(t?String(t.limit):``),[t?.limit]),!t)return null;let i=()=>{let i=Number(n);i!==t.limit&&e.run(()=>R.setLimit(i)).finally(()=>r(String(t.limit)))},a=t=>e.sessions.find(e=>e.id===t)?.title??`a session`;return(0,V.jsxs)(`section`,{className:`machine`,"aria-label":`Machine`,children:[(0,V.jsxs)(`div`,{className:`limits`,children:[(0,V.jsx)(Nw,{label:`CPU`,used:t.cores,total:t.cpus,text:`${kw(t.cores)} of ${t.cpus}`}),(0,V.jsx)(Nw,{label:`Memory`,used:t.memUsed,total:t.memTotal,text:`${Aw(t.memUsed)} of ${Aw(t.memTotal)}`}),t.docker&&(0,V.jsx)(Nw,{label:`Docker memory`,used:t.docker.memUsed,total:t.docker.memTotal,text:`${Aw(t.docker.memUsed)} of ${Aw(t.docker.memTotal)} · ${kw(t.docker.cores)}`})]}),(0,V.jsxs)(`div`,{className:`machine-working`,children:[(0,V.jsxs)(`span`,{children:[(0,V.jsx)(`strong`,{children:t.working}),` of `]}),(0,V.jsx)(`input`,{type:`number`,min:1,max:100,value:n,"aria-label":`How many sessions may work at once`,title:`How many sessions may work at the same time. Managers don't count.`,onChange:e=>r(e.target.value),onBlur:i,onKeyDown:e=>e.key===`Enter`&&e.target.blur()}),(0,V.jsxs)(`span`,{children:[` working`,t.line.length?` · ${t.line.length} waiting`:``]})]}),t.line.length>0&&(0,V.jsx)(`ol`,{className:`machine-line`,children:t.line.map(t=>{let n=e.sessions.find(e=>e.id===t);return(0,V.jsxs)(`li`,{children:[(0,V.jsx)(`button`,{className:`link`,onClick:()=>e.onOpen(t),children:a(t)}),n&&n.priority!==`normal`&&(0,V.jsx)(`span`,{className:`chip prio-${n.priority}`,children:Mw[n.priority]}),(0,V.jsx)(`button`,{className:`small`,title:`Start this turn now, above the limit`,onClick:()=>void e.run(()=>R.startNow(t)),children:`Start now`})]},t)})})]})}function Fw({sessionId:e}){let[t,n]=(0,v.useState)(null);if((0,v.useEffect)(()=>{let t=!0,r=()=>R.turns(e).then(e=>t&&n(e),()=>{});r();let i=setInterval(r,15e3);return()=>{t=!1,clearInterval(i)}},[e]),!t)return null;if(!t.length)return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`h3`,{children:`Machine use per turn`}),(0,V.jsx)(`p`,{className:`muted`,children:`No turns measured yet.`})]});let r=t.slice(-60);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`h3`,{children:`CPU per turn`}),(0,V.jsx)(Iw,{values:r.map(e=>({value:e.peakCores,label:`${new Date(e.startedAt).toLocaleTimeString()}: peak ${kw(e.peakCores)}, average ${kw(e.avgCores)}`})),format:kw}),(0,V.jsx)(`h3`,{children:`Memory per turn`}),(0,V.jsx)(Iw,{values:r.map(e=>({value:e.peakMem,label:`${new Date(e.startedAt).toLocaleTimeString()}: peak ${Aw(e.peakMem)}`})),format:Aw}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain calls`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Started`}),(0,V.jsx)(`th`,{className:`num`,children:`Took`}),(0,V.jsx)(`th`,{className:`num`,children:`Avg CPU`}),(0,V.jsx)(`th`,{className:`num`,children:`Peak CPU`}),(0,V.jsx)(`th`,{className:`num`,children:`Peak memory`}),(0,V.jsx)(`th`,{children:`Commands`})]})}),(0,V.jsx)(`tbody`,{children:t.slice().reverse().map(e=>(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{className:`nowrap`,children:new Date(e.startedAt).toLocaleTimeString()}),(0,V.jsx)(`td`,{className:`num`,children:jw(e.durationMs)}),(0,V.jsx)(`td`,{className:`num`,children:e.avgCores.toFixed(2)}),(0,V.jsx)(`td`,{className:`num`,children:e.peakCores.toFixed(2)}),(0,V.jsx)(`td`,{className:`num`,children:Aw(e.peakMem)}),(0,V.jsx)(`td`,{className:`mono`,children:e.commands.join(`, `)||(0,V.jsx)(`span`,{className:`muted`,children:`none`})})]},e.startedAt))})]})})]})}function Iw({values:e,format:t}){let n=Math.max(...e.map(e=>e.value),0);return(0,V.jsxs)(`div`,{className:`mini-bars`,role:`img`,"aria-label":`Highest: ${t(n)}`,children:[(0,V.jsx)(`span`,{className:`mini-max muted`,children:t(n)}),e.map((e,t)=>(0,V.jsx)(`div`,{className:`mini-col`,title:e.label,children:(0,V.jsx)(`div`,{className:`mini-bar`,style:{height:`${n>0?Math.max(2,e.value/n*100):0}%`}})},t))]})}function Lw(){let[e,t]=(0,v.useState)(null);return(0,v.useEffect)(()=>{R.typicalCosts(30).then(t,()=>t([]))},[]),(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h2`,{children:`Typical machine use per turn`}),(0,V.jsx)(`p`,{className:`muted`,children:`Last 30 days, sessions only (not managers): what a turn that ran each kind of command usually used. Ledung learns these; they don't decide anything yet.`}),e?e.length?(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Project`}),(0,V.jsx)(`th`,{children:`Command`}),(0,V.jsx)(`th`,{className:`num`,children:`Turns`}),(0,V.jsx)(`th`,{className:`num`,children:`Avg CPU`}),(0,V.jsx)(`th`,{className:`num`,children:`Peak CPU`}),(0,V.jsx)(`th`,{className:`num`,children:`Peak memory`}),(0,V.jsx)(`th`,{className:`num`,children:`Duration`})]})}),(0,V.jsx)(`tbody`,{children:e.slice(0,50).map(e=>(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{children:S(e.project)}),(0,V.jsx)(`td`,{className:`mono`,children:e.command||(0,V.jsx)(`span`,{className:`muted`,children:`no commands`})}),(0,V.jsx)(`td`,{className:`num`,children:e.turns}),(0,V.jsx)(`td`,{className:`num`,children:kw(e.avgCores)}),(0,V.jsx)(`td`,{className:`num`,children:kw(e.peakCores)}),(0,V.jsx)(`td`,{className:`num`,children:Aw(e.peakMem)}),(0,V.jsx)(`td`,{className:`num`,children:jw(e.durationMs)})]},`${e.project} ${e.command}`))})]})}):(0,V.jsx)(`p`,{className:`muted`,children:`No turns measured yet.`}):(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`})]})}function Rw(e,t){let n=e=>`${Math.round(e/1e3)}k`;return`${n(e)}${t?` of ${n(t)}`:``}`}var zw={...lt,waiting:`Needs an answer`};function Bw(e){return e.contextTokens&&e.contextWindow?e.contextTokens/e.contextWindow:null}function Vw(e){let t=new Set(e.sessions.map(e=>e.id)),n=e=>e.status!==`ended`,r=e.sessions.filter(r=>(!r.parentId||!t.has(r.parentId))&&(n(r)||e.sessions.some(e=>e.parentId===r.id&&n(e)))),i=(e,t)=>Number(t.role===`manager`)-Number(e.role===`manager`)||t.createdAt-e.createdAt,a=r.sort(i).flatMap(t=>[t,...e.sessions.filter(e=>e.parentId===t.id&&n(e)).sort(i)]),o=e.sessions.filter(e=>e.status===`ended`).length;return(0,V.jsx)(`div`,{className:`overview`,children:(0,V.jsxs)(`div`,{className:`overview-list`,children:[(0,V.jsxs)(`div`,{className:`muted`,children:[e.overview?`${Wy(e.overview.todayTokens)} tokens today`:``,o?` · ${o} ended session${o===1?``:`s`} not shown`:``]}),!a.length&&(0,V.jsx)(`p`,{className:`muted`,children:`No sessions are running.`}),a.map(n=>{let r=e.overview?.sessions[n.id],i=Bw(n),a=!!n.parentId&&t.has(n.parentId);return(0,V.jsxs)(`div`,{role:`button`,tabIndex:0,className:`overview-card${a?` child`:``}`,onClick:()=>e.onOpenSession(n.id),onKeyDown:t=>{(t.key===`Enter`||t.key===` `)&&(t.preventDefault(),e.onOpenSession(n.id))},children:[(0,V.jsxs)(`div`,{className:`overview-top`,children:[(0,V.jsx)(`span`,{className:`dot ${ut(n)}`}),(0,V.jsxs)(`span`,{className:`overview-title`,children:[n.role===`manager`&&(0,V.jsx)(`span`,{className:`chip`,children:`Manager`}),` `,n.title]}),e.waitingBySession[n.id]?(0,V.jsx)(`span`,{className:`badge`,children:e.waitingBySession[n.id]}):null]}),(0,V.jsxs)(`div`,{className:`overview-facts`,children:[(0,V.jsxs)(`span`,{children:[zw[n.status],e.machine&&e.machine.line.includes(n.id)?`: number ${e.machine.line.indexOf(n.id)+1}`:``,n.paused?` · paused`:``]}),n.priority!==`normal`&&(0,V.jsx)(`span`,{className:`chip prio-${n.priority}`,title:n.priorityNote??void 0,children:Mw[n.priority]}),e.machine?.sessions[n.id]&&(0,V.jsxs)(`span`,{title:`CPU and memory of everything this session runs`,children:[kw(e.machine.sessions[n.id].cores),` · `,Aw(e.machine.sessions[n.id].memBytes)]}),(0,V.jsx)(`span`,{children:S(n.project)}),n.branch&&(0,V.jsx)(`span`,{className:`mono`,children:n.branch}),n.pr&&(0,V.jsx)(`a`,{href:n.pr.url,target:`_blank`,rel:`noreferrer noopener`,onClick:e=>e.stopPropagation(),title:`${n.pr.title} — checks ${n.pr.checks}`,children:qy(n.pr)}),n.tickets.map(e=>(0,V.jsx)(`a`,{href:e.url,target:`_blank`,rel:`noreferrer noopener`,onClick:e=>e.stopPropagation(),children:e.id},e.id)),r&&(0,V.jsxs)(`span`,{title:`Tokens today / in total`,children:[Wy(r.today),` today · `,Wy(r.total),` total · `,Gy(r.costTotal)]}),n.contextTokens!=null&&(0,V.jsxs)(`span`,{className:i!=null&&i>.8?`ctx-high`:``,title:`How full the context window is, and its size in tokens`,children:[`context `,i==null?``:`${Ky(i)} · `,Rw(n.contextTokens,n.contextWindow)]}),n.backgroundTasks>0&&(0,V.jsxs)(`span`,{children:[n.backgroundTasks,` in background`]})]}),r?.lastReply&&(0,V.jsxs)(`div`,{className:`overview-last`,children:[(0,V.jsx)(`span`,{className:`muted`,children:r.lastReplyAt?Eg(r.lastReplyAt):``}),` `,r.lastReply.split(`
|
|
104
|
-
`)[0]]})]},n.id)})]})})}function Hw({sessionId:e,onClose:t}){let[n,r]=(0,v.useState)(null),[i,a]=(0,v.useState)(null);(0,v.useEffect)(()=>{let t=!0,n=()=>R.sessionUsage(e).then(e=>t&&r(e),e=>t&&a(e.message));n();let i=setInterval(n,15e3);return()=>{t=!1,clearInterval(i)}},[e]);let o=(0,v.useMemo)(()=>Zy(`model`,n?.models??[]),[n?.models]),s=n?.totals,c=n?n.calls.slice(-120):[];return(0,V.jsxs)(`aside`,{className:`file-panel`,"aria-label":`Usage`,children:[(0,V.jsxs)(`header`,{className:`file-head`,children:[(0,V.jsx)(`span`,{className:`file-path`,children:`Usage of this session`}),(0,V.jsx)(`button`,{className:`small`,onClick:t,children:`Close`})]}),(0,V.jsxs)(`div`,{className:`file-body`,children:[i&&(0,V.jsx)(`p`,{className:`error`,children:i}),!n&&!i&&(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`}),n&&s&&(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`div`,{className:`tiles`,children:[(0,V.jsx)(tb,{label:`Tokens`,value:Wy(s.tokens),sub:`${s.calls} model calls`}),(0,V.jsx)(tb,{label:`API-equivalent cost`,value:Gy(s.cost)}),(0,V.jsx)(tb,{label:`Cache read share`,value:s.tokens?Ky(s.cacheRead/s.tokens):`—`}),(0,V.jsx)(tb,{label:`In subagents`,value:s.tokens?Ky(s.subagentTokens/s.tokens):`—`})]}),(0,V.jsx)(`h3`,{children:`Tokens per model call`}),(0,V.jsx)(Qy,{items:[...n.models.map(e=>({label:e,color:o(e)})),...n.calls.some(e=>e.subagent)?[{label:`subagent call`,color:`var(--s-other)`,textured:!0}]:[]]}),(0,V.jsx)(eb,{height:120,columns:c.map(e=>({label:new Date(e.at).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`,second:`2-digit`}),short:new Date(e.at).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`}),values:{[e.model]:e.tokens},textured:!!e.subagent,note:[e.compaction?`Compaction`:``,e.subagent?`Subagent: ${e.subagent}`:``,`Started by: ${Xy[e.trigger]??e.trigger}`].filter(Boolean).join(` · `)})),series:n.models.map(e=>({key:e,label:e,color:o(e)})),emptyText:`No model calls recorded yet.`}),(0,V.jsx)(Fw,{sessionId:e}),(0,V.jsx)(`h3`,{children:`Model calls`}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain calls`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Time`}),(0,V.jsx)(`th`,{children:`Model`}),(0,V.jsx)(`th`,{className:`num`,children:`Input`}),(0,V.jsx)(`th`,{className:`num`,children:`Cache write`}),(0,V.jsx)(`th`,{className:`num`,children:`Cache read`}),(0,V.jsx)(`th`,{className:`num`,children:`Output`}),(0,V.jsx)(`th`,{className:`num`,children:`Thinking`}),(0,V.jsx)(`th`,{className:`num`,children:`Tokens`}),(0,V.jsx)(`th`,{className:`num`,children:`Cache %`}),(0,V.jsx)(`th`,{className:`num`,children:`Cost`}),(0,V.jsx)(`th`,{className:`num`,children:`Running`}),(0,V.jsx)(`th`,{children:`Who`})]})}),(0,V.jsx)(`tbody`,{children:(()=>{let e=0;return n.calls.map((t,n)=>(e+=t.cost??0,(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{className:`nowrap`,children:new Date(t.at).toLocaleTimeString()}),(0,V.jsxs)(`td`,{className:`nowrap`,children:[(0,V.jsx)(`span`,{className:`viz-swatch`,style:{background:o(t.model)}}),` `,t.model]}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.input)}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.cacheWrite)}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.cacheRead)}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.output)}),(0,V.jsx)(`td`,{className:`num muted`,children:t.thinking?`~${Wy(t.thinking)}`:``}),(0,V.jsx)(`td`,{className:`num strong`,children:Wy(t.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:t.tokens?Ky(t.cacheRead/t.tokens):``}),(0,V.jsx)(`td`,{className:`num`,children:Gy(t.cost)}),(0,V.jsx)(`td`,{className:`num muted`,children:Gy(e)}),(0,V.jsx)(`td`,{className:`muted nowrap`,children:t.subagent?`subagent: ${t.subagent}`:Xy[t.trigger]??t.trigger})]},n)))})()})]})})]})]})]})}var Uw=864e5,Ww=Uw;function Gw(e,t){return t.fingerprint??`${e.login}/${e.computerId}/${t.label}`}var Kw=e=>e.input+e.cacheWrite+e.cacheRead+e.output;function qw(e){return e.entries.find(e=>e.own)?.login??null}function Jw(e,t){let n=qw(e);return e.entries.flatMap(e=>e.state===`ok`&&e.file&&(!t||e.file.login===n)?[e.file]:[])}function Yw(e){return e.flatMap(e=>e.accounts.map(t=>({file:e,account:t,key:Gw(e,t)})))}function Xw(e,t,n){if(e===`all`)return null;let r;if(e===`week`){let e=Yw(t).flatMap(({account:e})=>e.limits.filter(e=>e.kind===`seven_day`&&e.resetsAt&&e.resetsAt>n).map(e=>e.resetsAt-Py.seven_day));r=e.length?Math.min(...e):n-6*Uw}else r=n-(Number(e.replace(`d`,``))-1)*Uw;return Zw(r)}function Zw(e){let t=new Date(e);return`${t.getFullYear()}-${String(t.getMonth()+1).padStart(2,`0`)}-${String(t.getDate()).padStart(2,`0`)}`}function Qw(e,t,n){let r=e=>!n||n(e.model),i=e.hourly.filter(r),a=i.length?Math.min(...i.map(e=>e.t)):1/0,o=0;for(let e of i)e.t+36e5>t&&(o+=e.cost);let s=Zw(t),c=Number.isFinite(a)?Zw(a):null;for(let t of e.daily)!r(t)||t.t<s||c&&t.t>=c||(o+=t.cost);return o}function $w(e){let t=/^seven_day_(opus|sonnet|haiku|fable)$/.exec(e)?.[1];return t?e=>e.toLowerCase().includes(t):void 0}var eT=[`five_hour`,`seven_day`,`seven_day_opus`,`seven_day_sonnet`];function tT(e,t){let n=new Map;for(let t of Yw(e)){let e=n.get(t.key);e?e.push(t):n.set(t.key,[t])}let r=[];for(let[e,i]of n){let n=[...i].sort((e,t)=>t.file.asOf-e.file.asOf)[0],a=[...new Set(i.flatMap(e=>e.account.limits.map(e=>e.kind)))].filter(e=>e!==`overage`&&e!==`seven_day_overage_included`).sort((e,t)=>(eT.indexOf(e)+1||99)-(eT.indexOf(t)+1||99)||e.localeCompare(t)).map(e=>{let n=i.flatMap(t=>t.account.limits.filter(t=>t.kind===e)).sort((e,t)=>t.seenAt-e.seenAt)[0],r=n?{...n,at:n.seenAt}:null,a=r?Vy(r,t):!1,o=Py[e]??Py.seven_day,s=r?.resetsAt&&!a?r.resetsAt-o:t-o,c=i.map(t=>({computer:t.file.computer,computerId:t.file.computerId,login:t.file.login,cost:Qw(t.account,s,$w(e))})),l=c.reduce((e,t)=>e+t.cost,0);return{kind:e,reading:r,reset:a,pace:r&&!a&&r.utilization!=null?Fy(e.startsWith(`seven_day`)?`seven_day`:e,r.utilization,r.resetsAt,t):null,shares:c.filter(e=>e.cost>0).map(e=>({...e,share:e.cost/l})).sort((e,t)=>t.cost-e.cost)}});r.push({fingerprint:e,label:n.account.label,rows:a,people:[...new Set(i.map(e=>e.file.login))].sort(),computers:[...new Set(i.map(e=>e.file.computer))].sort()})}return r.sort((e,t)=>e.label.localeCompare(t.label))}function nT(e,t,n){return e===`person`?t.file.login:e===`account`?t.account.label:e===`computer`?t.file.computer:e===`model`?n.model:n.project}function rT(e,t,n,r){let i=new Map,a=new Set;for(let r of Yw(e))for(let e of r.account.daily){if(n&&e.t<n)continue;let o=nT(t,r,e);a.add(o);let s=i.get(e.t)??Object.create(null);s[o]=(s[o]??0)+Kw(e),i.set(e.t,s)}let o=n??[...i.keys()].sort()[0],s=Zw(r),c=[];if(o)for(let e=new Date(`${o}T12:00:00`);Zw(e.getTime())<=s;e.setDate(e.getDate()+1)){let t=Zw(e.getTime());c.push({day:t,values:i.get(t)??Object.create(null)})}return{keys:[...a].sort(),columns:c}}function iT(e,t,n){return Yw(e).map(({file:e,account:r,key:i})=>{let a=r.daily.filter(e=>!t||e.t>=t);return{login:e.login,account:r.label,fingerprint:i,computer:e.computer,computerId:e.computerId,tokens:a.reduce((e,t)=>e+Kw(t),0),cost:a.reduce((e,t)=>e+t.cost,0),asOf:e.asOf,stale:n-e.asOf>Ww}}).sort((e,t)=>e.login.localeCompare(t.login)||e.account.localeCompare(t.account)||e.computer.localeCompare(t.computer))}var aT=[[`week`,`Since weekly reset`],[`7d`,`7 days`],[`30d`,`30 days`],[`90d`,`90 days`],[`all`,`All time`]],oT=[[`person`,`person`],[`account`,`account`],[`computer`,`computer`],[`model`,`model`],[`project`,`project`]],sT={five_hour:`5-hour`,seven_day:`Weekly`,seven_day_opus:`Weekly Opus`,seven_day_sonnet:`Weekly Sonnet`},cT={allowed:{cls:`good`,icon:`●`,label:`OK`},allowed_warning:{cls:`warning`,icon:`▲`,label:`Close to the limit`},rejected:{cls:`critical`,icon:`■`,label:`Limit reached`}};function lT(e,t){return Object.hasOwn(e,t)?e[t]:void 0}function uT(){let[e,t]=(0,v.useState)(null),[n,r]=(0,v.useState)(null);return(0,v.useEffect)(()=>{let e=!0,n=()=>R.sharedUsage().then(n=>e&&(t(n),r(null)),t=>e&&r(t.message));n();let i=setInterval(n,6e4);return()=>{e=!1,clearInterval(i)}},[]),n&&!e?(0,V.jsx)(`p`,{className:`error`,children:n}):e?(0,V.jsx)(dT,{view:e,now:Date.now()}):(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`})}function dT({view:e,now:t,initialMine:n=!1}){let[r,i]=(0,v.useState)(n),[a,o]=(0,v.useState)(`week`),[s,c]=(0,v.useState)(`person`),l=qw(e),u=(0,v.useMemo)(()=>Jw(e,r),[e,r]),d=Xw(a,u,t),f=(0,v.useMemo)(()=>tT(u,t),[u,t]),p=(0,v.useMemo)(()=>rT(u,s,d,t),[u,s,d,t]),m=(0,v.useMemo)(()=>iT(u,d,t),[u,d,t]),h=Zy(`project`,[...new Set(Jw(e,!1).map(e=>e.computerId))]),g=Zy(s===`model`?`model`:`project`,p.keys);if(!e.repo)return(0,V.jsx)(`p`,{className:`muted`,children:`Nothing is published here yet. Switch on Publish usage in Settings to share this computer's usage and read everyone else's.`});let _=p.keys.map(e=>({key:e,label:e,color:g(e)})),y=p.columns.map(e=>({label:new Date(`${e.day}T12:00:00`).toLocaleDateString([],{weekday:`short`,day:`numeric`,month:`short`}),short:new Date(`${e.day}T12:00:00`).toLocaleDateString([],{weekday:`short`,day:`numeric`}),values:e.values}));return(0,V.jsxs)(`div`,{className:`shared-usage`,children:[(0,V.jsxs)(`div`,{className:`filters`,children:[(0,V.jsxs)(`label`,{children:[`Period `,(0,V.jsx)(`select`,{value:a,onChange:e=>o(e.target.value),children:aT.map(([e,t])=>(0,V.jsx)(`option`,{value:e,children:t},e))})]}),(0,V.jsxs)(`label`,{className:`shared-mine`,title:l?`Only ${l}'s own computers`:`Mine needs this computer to publish its usage too`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r,disabled:!l,onChange:e=>i(e.target.checked)}),` Mine`]})]}),e.error&&(0,V.jsxs)(`p`,{className:`error`,children:[`Could not read the shared usage just now: `,e.error,e.entries.length?` Showing the last files read.`:``]}),e.entries.filter(e=>e.state!==`ok`&&(!r||e.login===l)).map(e=>(0,V.jsxs)(`p`,{className:`shared-note warning`,children:[e.computer??`A computer`,e.login?` (${e.login})`:``,e.state===`newer`?` publishes usage in a newer format: update Ledung to see it.`:` published a usage file Ledung cannot read${e.reason?` (${e.reason})`:``}.`]},e.id)),!u.length&&(0,V.jsx)(`p`,{className:`muted`,children:r?`None of your computers has published yet.`:`No computer has published yet.`}),f.length>0&&(0,V.jsx)(`div`,{className:`shared-cards`,children:f.map(e=>(0,V.jsx)(fT,{card:e,now:t,color:h},e.fingerprint))}),u.length>0&&(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsxs)(`div`,{className:`viz-card-head`,children:[(0,V.jsx)(`h3`,{children:`Daily tokens`}),(0,V.jsxs)(`div`,{className:`seg-control shared-stack`,role:`group`,"aria-label":`Stack by`,children:[(0,V.jsx)(`span`,{className:`muted`,children:`by`}),oT.map(([e,t])=>(0,V.jsx)(`button`,{className:s===e?`on`:``,onClick:()=>c(e),children:t},e))]})]}),(0,V.jsx)(Qy,{items:_}),(0,V.jsx)(eb,{columns:y,series:_})]}),m.length>0&&(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsx)(`h3`,{children:`Who's who`}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Person`}),(0,V.jsx)(`th`,{children:`Account`}),(0,V.jsx)(`th`,{children:`Computer`}),(0,V.jsx)(`th`,{className:`num`,children:`Tokens`}),(0,V.jsx)(`th`,{className:`num`,children:`Cost`}),(0,V.jsx)(`th`,{children:`Last published`})]})}),(0,V.jsx)(`tbody`,{children:m.map((e,n)=>{let r=m[n-1],i=r?.login===e.login;return(0,V.jsxs)(`tr`,{className:e.stale?`shared-stale`:``,children:[(0,V.jsx)(`td`,{children:i?``:e.login}),(0,V.jsx)(`td`,{children:i&&r?.fingerprint===e.fingerprint?``:e.account}),(0,V.jsxs)(`td`,{className:`nowrap`,children:[(0,V.jsx)(`span`,{className:`viz-swatch`,style:{background:h(e.computerId)}}),` `,e.computer]}),(0,V.jsx)(`td`,{className:`num`,children:Wy(e.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:Gy(e.cost)}),(0,V.jsxs)(`td`,{className:`nowrap`,children:[Hy({at:e.asOf,resetsAt:null},t).replace(/^as of /,``),e.stale&&(0,V.jsx)(`span`,{className:`shared-stale-mark`,title:`No publish for over a day`,children:` · stale`})]})]},`${e.computerId}-${e.fingerprint}`)})})]})})]})]})}function fT({card:e,now:t,color:n}){return(0,V.jsxs)(`section`,{className:`card viz-card shared-card`,children:[(0,V.jsx)(`h3`,{children:e.label}),(0,V.jsxs)(`div`,{className:`muted shared-card-who`,children:[e.people.join(`, `),` · `,e.computers.length,` computer`,e.computers.length===1?``:`s`]}),!e.rows.some(e=>e.reading)&&(0,V.jsx)(`div`,{className:`muted`,children:`no data yet`}),e.rows.map(e=>{let r=lT(sT,e.kind)??e.kind;if(!e.reading)return null;if(e.reset)return(0,V.jsxs)(`div`,{className:`shared-limit limit-reset`,title:`${r}: the window has reset since the last reading (${Hy(e.reading,t)}).`,children:[(0,V.jsxs)(`div`,{className:`limit-head`,children:[(0,V.jsx)(`span`,{children:r}),(0,V.jsx)(`span`,{className:`limit-status`,children:`reset`})]}),(0,V.jsx)(`div`,{className:`limit-sub muted`,children:(0,V.jsx)(`span`,{children:`no reading since the reset`})})]},e.kind);let i=e.reading.utilization,a=Uy(e.reading,t),o=Math.min(100,(i??0)*100),s=lT(cT,e.reading.status)??{cls:`good`,icon:`●`,label:e.reading.status},c=e.shares.map(e=>`${e.computer} (${e.login}): ${Ky(e.share)}, ${Gy(e.cost)}`).join(`
|
|
105
|
-
`);return(0,V.jsxs)(`div`,{className:`shared-limit`,children:[(0,V.jsxs)(`div`,{className:`limit-head`,children:[(0,V.jsx)(`span`,{children:r}),(0,V.jsxs)(`span`,{className:`limit-status ${s.cls}`,title:s.label,children:[s.icon,` `,i==null?s.label:Ky(i)]})]}),(0,V.jsx)(`div`,{className:`limit-track shared-track`,title:c||`No use recorded in this window`,children:(0,V.jsx)(`div`,{className:`shared-fill`,style:{width:`${o}%`},children:e.shares.length?e.shares.map(e=>(0,V.jsx)(`div`,{className:`shared-seg`,style:{flexGrow:e.share,background:n(e.computerId)}},e.computerId)):(0,V.jsx)(`div`,{className:`shared-seg limit-fill ${s.cls}`,style:{flexGrow:1}})})}),(0,V.jsxs)(`div`,{className:`limit-sub muted`,children:[(0,V.jsx)(`span`,{children:e.shares.map(e=>`${e.computer} ${Ky(e.share)}`).join(` · `)}),(0,V.jsxs)(`span`,{className:`limit-forecast${e.pace!=null&&e.pace>=1?` over`:``}`,children:[`≈ `,e.pace==null?`—`:Ky(e.pace),` by reset`]})]}),a&&(0,V.jsx)(`div`,{className:`limit-sub limit-age`,children:a})]},e.kind)})]})}function pT(){return(0,V.jsx)(`div`,{className:`usage-body`,children:(0,V.jsx)(uT,{})})}var mT=[[`week`,`Since weekly reset`],[`7d`,`7 days`],[`30d`,`30 days`],[`90d`,`90 days`],[`all`,`All time`]];function hT(e){return new Date(`${e}T12:00:00`).toLocaleDateString([],{weekday:`short`,day:`numeric`})}var gT=[[`computer`,`This computer`],[`shared`,`Shared`],[`sessions`,`Sessions`]];function _T(e){let[t,n]=(0,v.useState)(`computer`),r=e.sessionsOpen?`sessions`:t,i=t=>{t===`sessions`?e.sessionsOpen||e.onSessions(!0):(n(t),e.sessionsOpen&&e.onSessions(!1))};return(0,V.jsxs)(`div`,{className:`usage`,children:[(0,V.jsx)(`header`,{className:`session-head`,children:(0,V.jsx)(`div`,{className:`session-head-text`,children:(0,V.jsx)(`h2`,{children:`Usage`})})}),(0,V.jsx)(`div`,{className:`pane-tabs`,role:`tablist`,"aria-label":`Usage`,children:gT.map(([e,t])=>(0,V.jsx)(`button`,{role:`tab`,"aria-selected":r===e,className:r===e?`on`:``,onClick:()=>i(e),children:t},e))}),r===`computer`?(0,V.jsx)(vT,{onOpenSession:e.onOpenSession}):r===`shared`?(0,V.jsx)(pT,{}):(0,V.jsx)(Vw,{sessions:e.sessions,overview:e.overview,machine:e.machine,waitingBySession:e.waitingBySession,onOpenSession:e.onOpenSession})]})}function vT({onOpenSession:e}){let[t,n]=(0,v.useState)({period:`week`}),[r,i]=(0,v.useState)(null),[a,o]=(0,v.useState)(null),[s,c]=(0,v.useState)(`model`),[l,u]=(0,v.useState)({});(0,v.useEffect)(()=>{let e=!0;R.usage(t).then(t=>e&&i(t),t=>e&&o(t.message));let n=setInterval(()=>R.usage(t).then(t=>e&&i(t),()=>{}),3e4);return()=>{e=!1,clearInterval(n)}},[t]);let d=(0,v.useMemo)(()=>({model:Zy(`model`,r?.options.models??[]),project:Zy(`project`,r?.options.projects??[]),trigger:Zy(`trigger`,Yy)}),[r?.options.models,r?.options.projects]);if(a)return(0,V.jsx)(`div`,{className:`usage-body`,children:(0,V.jsx)(`p`,{className:`error`,children:a})});if(!r)return(0,V.jsx)(`div`,{className:`usage-body`,children:(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`})});let f=e=>n(t=>({...t,...e})),p=r.totals,m=(s===`model`?r.models:s===`project`?[...new Set(r.daily.flatMap(e=>Object.keys(e.byProject)))].sort():Yy.filter(e=>r.daily.some(t=>t.byTrigger[e]))).map(e=>({key:e,label:s===`trigger`?Xy[e]??e:e,color:d[s](e)})),h=r.daily.map(e=>({label:new Date(`${e.day}T12:00:00`).toLocaleDateString([],{weekday:`short`,day:`numeric`,month:`short`}),short:hT(e.day),values:s===`model`?e.byModel:s===`project`?e.byProject:e.byTrigger})),g=t.project||t.model||t.branch||t.role||t.trigger||t.account;return(0,V.jsxs)(`div`,{className:`usage-body`,children:[(0,V.jsxs)(`div`,{className:`muted`,children:[`Since `,new Date(r.since||Date.now()).toLocaleString([],{dateStyle:`medium`,timeStyle:`short`}),r.since===0?` (all time)`:``]}),(0,V.jsxs)(`div`,{className:`filters`,children:[(0,V.jsxs)(`label`,{children:[`Period `,(0,V.jsx)(`select`,{value:t.period,onChange:e=>f({period:e.target.value}),children:mT.map(([e,t])=>(0,V.jsx)(`option`,{value:e,children:t},e))})]}),(0,V.jsxs)(`label`,{children:[`Project `,(0,V.jsxs)(`select`,{value:t.project??``,onChange:e=>f({project:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),r.options.projects.map(e=>(0,V.jsx)(`option`,{value:e,children:S(e)},e))]})]}),(r.options.accounts?.length??0)>1&&(0,V.jsxs)(`label`,{children:[`Account `,(0,V.jsxs)(`select`,{value:t.account??``,onChange:e=>f({account:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),r.options.accounts.map(e=>(0,V.jsx)(`option`,{children:e},e))]})]}),(0,V.jsxs)(`label`,{children:[`Model `,(0,V.jsxs)(`select`,{value:t.model??``,onChange:e=>f({model:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),r.options.models.map(e=>(0,V.jsx)(`option`,{children:e},e))]})]}),(0,V.jsxs)(`label`,{children:[`Branch `,(0,V.jsxs)(`select`,{value:t.branch??``,onChange:e=>f({branch:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),r.options.branches.map(e=>(0,V.jsx)(`option`,{children:e},e))]})]}),(0,V.jsxs)(`label`,{children:[`Role `,(0,V.jsxs)(`select`,{value:t.role??``,onChange:e=>f({role:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),(0,V.jsx)(`option`,{value:`manager`,children:`Managers`}),(0,V.jsx)(`option`,{value:`session`,children:`Sessions`})]})]}),(0,V.jsxs)(`label`,{children:[`Started by `,(0,V.jsxs)(`select`,{value:t.trigger??``,onChange:e=>f({trigger:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),Yy.map(e=>(0,V.jsx)(`option`,{value:e,children:Xy[e]},e))]})]}),g&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>n({period:t.period}),children:`Clear filters`})]}),(0,V.jsxs)(`div`,{className:`tiles`,children:[(0,V.jsx)(tb,{label:`Tokens`,value:Wy(p.tokens),sub:`${Wy(p.output)} output`}),(0,V.jsx)(tb,{label:`API-equivalent cost`,value:Gy(p.cost),sub:`not what a plan charges`}),(0,V.jsx)(tb,{label:`Model calls`,value:p.calls.toLocaleString(),sub:`${p.sessions} session${p.sessions===1?``:`s`}`}),(0,V.jsx)(tb,{label:`Cache read share`,value:p.tokens?Ky(p.cacheRead/p.tokens):`—`,sub:`higher is cheaper`}),(0,V.jsx)(tb,{label:`In subagents`,value:p.tokens?Ky(p.subagentTokens/p.tokens):`—`})]}),(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsxs)(`div`,{className:`viz-card-head`,children:[(0,V.jsx)(`h3`,{children:`Daily tokens`}),(0,V.jsx)(`div`,{className:`seg-control`,role:`group`,"aria-label":`Split by`,children:[`model`,`project`,`trigger`].map(e=>(0,V.jsx)(`button`,{className:s===e?`on`:``,onClick:()=>c(e),children:e===`trigger`?`started by`:`by ${e}`},e))})]}),(0,V.jsx)(Qy,{items:m}),(0,V.jsx)(eb,{columns:h,series:m})]}),(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsx)(`h3`,{children:`Project × model`}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`matrix`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Project`}),r.models.map(e=>(0,V.jsxs)(`th`,{className:`num`,children:[(0,V.jsx)(`span`,{className:`viz-swatch`,style:{background:d.model(e)}}),` `,e]},e)),(0,V.jsx)(`th`,{className:`num`,children:`Total`}),(0,V.jsx)(`th`,{className:`num`,children:`Cost`}),(0,V.jsx)(`th`,{className:`num`,title:`Share of tokens used by subagents`,children:`Sub`})]})}),(0,V.jsx)(`tbody`,{children:r.matrix.map(e=>(0,V.jsxs)(v.Fragment,{children:[(0,V.jsxs)(`tr`,{className:`matrix-row`,children:[(0,V.jsxs)(`td`,{children:[e.roles.length>1&&(0,V.jsx)(`button`,{className:`caret`,"aria-label":`Show roles`,onClick:()=>u(t=>({...t,[e.project]:!t[e.project]})),children:l[e.project]?`▾`:`▸`}),(0,V.jsx)(`button`,{className:`link`,onClick:()=>f({project:e.project}),children:S(e.project)})]}),r.models.map(t=>(0,V.jsx)(`td`,{className:`num`,children:e.byModel[t]?Wy(e.byModel[t]):``},t)),(0,V.jsx)(`td`,{className:`num strong`,children:Wy(e.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:Gy(e.cost)}),(0,V.jsx)(`td`,{className:`num muted`,children:e.subagentShare?Ky(e.subagentShare):``})]}),l[e.project]&&e.roles.map(e=>(0,V.jsxs)(`tr`,{className:`matrix-sub`,children:[(0,V.jsxs)(`td`,{children:[`↳ `,e.role===`manager`?`managers`:`sessions`]}),r.models.map(t=>(0,V.jsx)(`td`,{className:`num`,children:e.byModel[t]?Wy(e.byModel[t]):``},t)),(0,V.jsx)(`td`,{className:`num`,children:Wy(e.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:Gy(e.cost)}),(0,V.jsx)(`td`,{className:`num muted`,children:e.subagentShare?Ky(e.subagentShare):``})]},e.role))]},e.project))})]})})]}),(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsx)(`h3`,{children:`Recent sessions`}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Last call`}),(0,V.jsx)(`th`,{children:`Session`}),(0,V.jsx)(`th`,{children:`Project`}),(0,V.jsx)(`th`,{children:`Branch`}),(0,V.jsx)(`th`,{children:`Models`}),(0,V.jsx)(`th`,{className:`num`,children:`Calls`}),(0,V.jsx)(`th`,{className:`num`,children:`Tokens`}),(0,V.jsx)(`th`,{className:`num`,children:`Cost`}),(0,V.jsx)(`th`,{className:`num`,children:`Sub`})]})}),(0,V.jsx)(`tbody`,{children:r.recent.map(t=>(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{className:`nowrap`,children:Eg(t.lastAt)}),(0,V.jsx)(`td`,{children:(0,V.jsxs)(`button`,{className:`link`,onClick:()=>e(t.sessionId),children:[t.role===`manager`?`Manager · `:``,t.title]})}),(0,V.jsx)(`td`,{children:S(t.project)}),(0,V.jsx)(`td`,{className:`muted`,children:t.branch??``}),(0,V.jsx)(`td`,{className:`muted`,children:t.models.join(`, `)}),(0,V.jsx)(`td`,{className:`num`,children:t.calls}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:Gy(t.cost)}),(0,V.jsx)(`td`,{className:`num muted`,children:t.subagentShare?Ky(t.subagentShare):``})]},t.sessionId))})]})})]}),(0,V.jsx)(Lw,{})]})}function yT(e){try{return sm(localStorage.getItem(`ledung.sidebar.${e}`))}catch{return null}}function bT(e,t){try{t==null?localStorage.removeItem(`ledung.sidebar.${e}`):localStorage.setItem(`ledung.sidebar.${e}`,String(t))}catch{}}function xT(){let[e,t]=(0,v.useState)(()=>window.matchMedia(im).matches),[n,r]=(0,v.useState)({w:window.innerWidth,h:window.innerHeight}),[i,a]=(0,v.useState)(()=>({width:yT(`width`),height:yT(`height`)})),o=e?`height`:`width`;(0,v.useEffect)(()=>{let e=window.matchMedia(im),n=()=>{t(e.matches),r({w:window.innerWidth,h:window.innerHeight})};return e.addEventListener(`change`,n),window.addEventListener(`resize`,n),()=>{e.removeEventListener(`change`,n),window.removeEventListener(`resize`,n)}},[]);let{min:s,max:c,def:l}=am(o,e?n.h:n.w),u=om(i[o]??l,s,c);(0,v.useEffect)(()=>{document.querySelector(`.app`)?.style.setProperty(e?`--sidebar-h`:`--sidebar-w`,`${u}px`)},[u,e]);let d=e=>{bT(o,e),a(t=>({...t,[o]:e}))};return(0,V.jsx)(`div`,{className:`sidebar-resizer ${e?`horizontal`:`vertical`}`,role:`separator`,"aria-label":`Resize the sidebar`,"aria-orientation":e?`horizontal`:`vertical`,"aria-valuenow":u,"aria-valuemin":s,"aria-valuemax":c,tabIndex:0,title:`Drag to resize, double-click to reset`,onPointerDown:e=>{e.button===0&&(e.currentTarget.setPointerCapture(e.pointerId),e.preventDefault())},onPointerMove:t=>{if(!t.currentTarget.hasPointerCapture(t.pointerId))return;let n=t.currentTarget.parentElement.getBoundingClientRect();d(om(e?t.clientY-n.top:t.clientX-n.left,s,c))},onDoubleClick:()=>d(null),onKeyDown:e=>{let t=cm(e.key,o,u,s,c);t!=null&&(e.preventDefault(),d(t))}})}var ST=`ledung.composer.height`,CT=.75;function wT(e,t,n,r,i,a){return Math.ceil(Math.max(e,t*n+r+i,a))}function TT(e,t,n){return{min:e,max:Math.max(e,Math.floor(t*CT-n))}}function ET(e,t,n,r,i){return om(e+(t-n),r,i)}function DT(e,t,n,r){return e===`ArrowUp`?om(t+20,n,r):e===`ArrowDown`?om(t-20,n,r):e===`Home`?n:e===`End`?r:null}function OT(e){try{return sm(e.getItem(ST))}catch{return null}}function kT(e,t){try{t==null?e.removeItem(ST):e.setItem(ST,String(t))}catch{}}function AT(){try{return localStorage}catch{return null}}function jT(){let e=(0,v.useRef)(null),t=(0,v.useRef)(null),[n,r]=(0,v.useState)(()=>{let e=AT();return e?OT(e):null}),[i,a]=(0,v.useState)(null),o=(0,v.useCallback)(()=>{let n=e.current,r=t.current,i=n?.parentElement;if(!n||!r||!i)return null;let a=getComputedStyle(n),o=parseFloat(a.paddingTop)+parseFloat(a.paddingBottom)+parseFloat(a.borderTopWidth)+parseFloat(a.borderBottomWidth),s=getComputedStyle(r),c=parseFloat(s.lineHeight)||parseFloat(s.fontSize)*1.2,l=n.querySelector(`.composer-buttons`)?.offsetHeight??0;return TT(wT(parseFloat(s.minHeight)||0,c,r.rows,parseFloat(s.paddingTop)+parseFloat(s.paddingBottom),parseFloat(s.borderTopWidth)+parseFloat(s.borderBottomWidth),l),i.clientHeight,o)},[]);(0,v.useLayoutEffect)(()=>{let t=e.current?.parentElement;if(!t)return;let n=()=>a(o());n();let r=new ResizeObserver(n);return r.observe(t),()=>r.disconnect()},[o]);let s=n==null?null:i?om(n,i.min,i.max):n,c=e=>{let t=AT();t&&kT(t,e),r(e)},l=(0,v.useRef)(null),u=e=>{e.button===0&&t.current&&(e.currentTarget.setPointerCapture(e.pointerId),e.preventDefault(),l.current={y:e.clientY,h:t.current.offsetHeight},a(o()))},d=e=>{let t=l.current;t&&i&&e.currentTarget.hasPointerCapture(e.pointerId)&&c(ET(t.h,t.y,e.clientY,i.min,i.max))},f=()=>{l.current=null},p=(0,V.jsx)(`div`,{className:`composer-grip`,role:`separator`,"aria-label":`Resize the message box`,"aria-orientation":`horizontal`,"aria-valuenow":s??void 0,"aria-valuemin":i?.min,"aria-valuemax":i?.max,tabIndex:0,title:`Drag up to make the message box taller, double-click to reset`,onPointerDown:u,onPointerMove:d,onPointerUp:f,onPointerCancel:f,onDoubleClick:()=>c(null),onKeyDown:e=>{let n=o();if(!n||!t.current)return;let r=DT(e.key,t.current.offsetHeight,n.min,n.max);r!=null&&(e.preventDefault(),c(r))}});return{box:e,area:t,style:s==null?void 0:{height:s},grip:p}}function MT(e,t){let n=new Set(e.map(e=>e.id)),r=t.filter(e=>!n.has(e.id));return r.length?[...e,...r].sort((e,t)=>e.id-t.id):e}async function NT(e,t){let n=[];for(let r=e;;){let e=await t(r);n.push(...e);let i=e.at(-1)?.id??r;if(e.length<500||i<=r)return n;r=i}}function PT(e){let[t,n]=(0,v.useState)(`connecting`),[r,i]=(0,v.useState)(!1),[a,o]=(0,v.useState)([]),[s,c]=(0,v.useState)([]),[l,u]=(0,v.useState)({}),[d,f]=(0,v.useState)([]),[p,m]=(0,v.useState)(!1),[h,g]=(0,v.useState)(!1),[_,y]=(0,v.useState)(0),[b,x]=(0,v.useState)(!1),[S,C]=(0,v.useState)(`you`),[w,T]=(0,v.useState)(null),[E,D]=(0,v.useState)({}),[O,k]=(0,v.useState)([]),[ee,A]=(0,v.useState)([]),[j,M]=(0,v.useState)([]),[te,N]=(0,v.useState)([]),[P,ne]=(0,v.useState)(null),[re,ie]=(0,v.useState)([]),[ae,oe]=(0,v.useState)([]),[se,ce]=(0,v.useState)(null),[le,ue]=(0,v.useState)(null),[de,fe]=(0,v.useState)(null),[pe,me]=(0,v.useState)([]),[he,F]=(0,v.useState)({chats:null,newProjects:null}),[I,ge]=(0,v.useState)([`full`]),[_e,ve]=(0,v.useState)(null),[ye,be]=(0,v.useState)(`Git Bash`),[xe,Se]=(0,v.useState)(null),[Ce,we]=(0,v.useState)(null),[Te,De]=(0,v.useState)([]),[Oe,ke]=(0,v.useState)(null),[Me,Ne]=(0,v.useState)(null),[Pe,L]=(0,v.useState)([]),[Fe,Ie]=(0,v.useState)([]),[Le,Re]=(0,v.useState)([]),[ze,Be]=(0,v.useState)(!1),[Ve,He]=(0,v.useState)(null),Ue=(0,v.useRef)(null),We=(0,v.useRef)(e);We.current=e;let Ge=(0,v.useRef)({sessionId:null,messages:[]});Ge.current.messages=d;let Ke=(0,v.useCallback)(async e=>{let t=await R.messages(e);We.current===e&&(Ge.current={sessionId:e,messages:t},f(t),m(t.length>=500))},[]),qe=(0,v.useCallback)(async e=>{let t=Ge.current,n=t.messages.at(-1);if(t.sessionId!==e||!n)return Ke(e);let r=await NT(n.id,t=>R.messagesAfter(e,t));We.current===e&&f(e=>MT(e,r))},[Ke]),Je=(0,v.useCallback)(async()=>{let e=We.current,t=d[0];if(!e||!t)return;let n=await R.messages(e,t.id);We.current===e&&(f(e=>[...n,...e]),m(n.length>=500))},[d]);return(0,v.useEffect)(()=>{Ge.current={sessionId:null,messages:[]},f([]),m(!1),e&&Ke(e).catch(()=>{})},[e,Ke]),(0,v.useEffect)(()=>{let e=null,t=500,r=!1,a,s=()=>{n(`connecting`),e=je(`${location.protocol===`https:`?`wss`:`ws`}://${location.host}/ws`),e.onopen=()=>{t=500,n(`open`)},e.onclose=()=>{n(`closed`),r||(a=setTimeout(s,t=Math.min(t*2,1e4)))},e.onmessage=e=>{let t=JSON.parse(e.data);switch(t.type){case`hello`:Ue.current===null?Ue.current=t.build:Ue.current!==t.build&&x(!0),Ee(t.pageKey??null),y(e=>e+1),i(!0),g(t.canRestart),C(t.userName),T(t.source??null),D(Object.fromEntries(t.questions.map(e=>[e.id,e]))),k(t.limits),A(t.usageStops??[]),M(t.macros??[]),fe(t.away??null),o(t.sessions),c(t.projects),we(t.board??null),De(t.github??[]),ge(t.profiles??[`full`]),ve(t.lockdownB??null),be(t.bangShell??`Git Bash`),ke(t.remote??null),Ne(t.chats??null),L(t.computers??[]),Ie(t.newComputers??[]),Re(t.linkPairings??[]),Be(t.throughPublicName??!1),He(t.config??null),u(Object.fromEntries(t.permissions.map(e=>[e.id,e]))),We.current&&qe(We.current).catch(()=>{}),R.machine().then(ue,()=>{}),R.accounts().then(e=>{me(e.accounts),Se(e.defaultIdentity),F(e.choices),N(e.signedOut??[]),ne(e.claudeProblem??null),ie(e.claudeLooked??[]),oe(e.configFileProblems??[])},()=>{});break;case`session`:o(e=>e.findIndex(e=>e.id===t.session.id)===-1?[t.session,...e]:e.map(e=>e.id===t.session.id?t.session:e));break;case`limits`:k(t.limits);break;case`macros`:M(t.macros);break;case`usageStops`:A(t.usageStops);break;case`config`:He(t.config);break;case`projects`:c(t.projects);break;case`accounts`:me(t.accounts),Se(t.defaultIdentity),F(t.choices),N(t.signedOut??[]),ne(t.claudeProblem??null),ie(t.claudeLooked??[]),oe(t.configFileProblems??[]);break;case`board`:we(t.board);break;case`github`:De(t.github);break;case`remote`:ke(t.remote);break;case`newComputers`:Ie(t.computers);break;case`linkPairings`:Re(t.pairings);break;case`chats`:Ne(t.chats);break;case`computers`:L(t.computers);break;case`machine`:ue(t.machine);break;case`away`:fe(t.away);break;case`question`:D(e=>({...e,[t.question.id]:t.question}));break;case`permission`:u(e=>({...e,[t.permission.id]:t.permission}));break;case`message`:t.message.sessionId===We.current&&f(e=>e.some(e=>e.id===t.message.id)?e:[...e,t.message])}}};return s(),Ae(()=>{r||(clearTimeout(a),e&&(e.onopen=e.onclose=e.onmessage=null,e.close()),t=500,s())}),()=>{r=!0,Ae(null),clearTimeout(a),e?.close()}},[qe]),(0,v.useEffect)(()=>{let e=!0,t=()=>R.overview().then(t=>e&&ce(t),()=>{});t();let n=setInterval(t,2e4);return()=>{e=!1,clearInterval(n)}},[]),{connection:t,loaded:r,canRestart:h,hellos:_,updated:b,userName:S,source:w,questions:E,limits:O,usageStops:ee,macros:j,signedOut:te,claudeProblem:P,claudeLooked:re,accountProblems:ae,overview:se,machine:le,away:de,accounts:pe,accountChoices:he,defaultIdentity:xe,board:Ce,github:Te,remote:Oe,computers:Pe,newComputers:Fe,linkPairings:Le,throughPublicName:ze,configStatus:Ve,chats:Me,profiles:I,lockdownB:_e,bangShell:ye,sessions:a,projects:s,permissions:l,messages:d,hasEarlier:p,loadEarlier:Je}}var FT=(e,t=140)=>{let n=e.split(`
|
|
106
|
-
`).map(e=>e.trim()).find(Boolean)??``;return n.length>t?`${n.slice(0,t-1)}…`:n},IT=e=>typeof e==`string`?e:``;function LT(e){let t=e.input.questions;return FT(IT(Array.isArray(t)?t[0]?.question:void 0)||e.title||IT(e.input.command)||IT(e.input.file_path)||e.reason||``)}function RT(e,t,n){return[...e.filter(ny).map(e=>({id:`q${e.id}`,sessionId:e.sessionId,title:`Question from ${n(e.sessionId)}`,body:FT(e.question)})),...t.filter(ry).map(e=>{let t=LT(e);return{id:`p${e.id}`,sessionId:e.sessionId,title:e.toolName===`AskUserQuestion`?`Question from ${n(e.sessionId)}`:`Permission: ${e.toolName} in ${n(e.sessionId)}`,body:e.sensitive?`Sensitive${t?`: ${t}`:``}`:t}})]}var zT={five_hour:`5-hour`,seven_day:`weekly`};function BT(e){return e.filter(e=>e.holding).map(e=>({id:`stop:${e.account}:${e.kind}:${e.resetsAt??``}`,sessionId:`settings`,title:`Usage stop reached: ${zT[e.kind]??e.kind} ${e.percent}%`,body:`New turns${e.account==="default"?``:` on account ${e.account}`} are held until you lift it in Settings${e.resetsAt?` or the window resets`:``}.`}))}function VT(e,t){let n=new Set(t.map(e=>e.id));return e?{show:t.filter(t=>!e.has(t.id)),close:[...e].filter(e=>!n.has(e)),open:n}:{show:[],close:[],open:n}}var HT=()=>window.isSecureContext&&`Notification`in window,UT=`ledung.notify`,WT=()=>{try{return localStorage.getItem(UT)===`1`}catch{return!1}};function GT(e){let t=HT(),[n,r]=(0,v.useState)(WT),[i,a]=(0,v.useState)(t?Notification.permission:`default`),o=t&&n&&i===`granted`,s=(0,v.useRef)(null),c=(0,v.useRef)(new Map),l=(0,v.useRef)(e.onOpenSession);return l.current=e.onOpenSession,(0,v.useEffect)(()=>{if(!e.loaded)return;let t=VT(s.current,[...RT(e.questions,e.permissions,t=>e.sessions.find(e=>e.id===t)?.title??`a session`),...BT(e.usageStops)]);s.current=t.open;for(let e of t.close)c.current.get(e)?.close(),c.current.delete(e);if(!(!o||!document.hidden&&document.hasFocus()))for(let e of t.show)try{let t=new Notification(e.title,{body:e.body,tag:e.id});t.onclick=()=>{window.focus(),l.current(e.sessionId),t.close()},t.onclose=()=>{c.current.get(e.id)===t&&c.current.delete(e.id)},c.current.set(e.id,t)}catch{}},[e.loaded,e.questions,e.permissions,e.sessions,e.usageStops,o]),{possible:t,on:o,denied:t&&i===`denied`,set:async e=>{if(!e){r(!1);try{localStorage.setItem(UT,`0`)}catch{}return}let t=Notification.permission===`granted`?`granted`:await Notification.requestPermission();a(t);let n=t===`granted`;r(n);try{localStorage.setItem(UT,n?`1`:`0`)}catch{}}}}function KT(e,t){return e.key!==`Enter`||e.isComposing?!1:t?e.ctrlKey||e.metaKey:!e.shiftKey}var qT=80;function JT(e,t,n){if(Math.abs(n-1)>.01)return 0;let r=Math.round(e-t);return r>=qT?r:0}var YT=new Set([`button`,`checkbox`,`color`,`file`,`hidden`,`image`,`radio`,`range`,`reset`,`submit`]);function XT(e){if(!e)return!1;if(e.isContentEditable)return!0;let t=e.tagName.toUpperCase();return e.readOnly||e.disabled?!1:t===`TEXTAREA`||t===`INPUT`&&!YT.has((e.type??`text`).toLowerCase())}var ZT=400;function QT(e){let t=e.visualViewport;if(!t)return;let n=e.document,r=n.documentElement,i=0,a=()=>{let a=XT(n.activeElement)?JT(r.clientHeight,t.height,t.scale):0;a!==i&&(i=a,a?r.style.setProperty(`--kb`,`${a}px`):r.style.removeProperty(`--kb`)),a&&(e.scrollY>0||t.offsetTop>0)&&e.scrollTo(0,0)},o=()=>{e.setTimeout(a,0),e.setTimeout(a,ZT)};t.addEventListener(`resize`,a),t.addEventListener(`scroll`,a),n.addEventListener(`focusin`,o),n.addEventListener(`focusout`,o),n.addEventListener(`visibilitychange`,o);for(let t of[`resize`,`orientationchange`,`focus`,`pageshow`])e.addEventListener(t,o);a()}var $T=(0,V.jsxs)(`svg`,{viewBox:`0 0 16 16`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.6`,"aria-hidden":`true`,children:[(0,V.jsx)(`circle`,{cx:`8`,cy:`8`,r:`6.5`}),(0,V.jsx)(`path`,{d:`M1.5 8h13M8 1.5c2 2 2.6 4 2.6 6.5S10 12.5 8 14.5M8 1.5C6 3.5 5.4 5.5 5.4 8S6 12.5 8 14.5`})]});function eE(e){return(0,V.jsxs)(V.Fragment,{children:[$T,`Remote`,e&&(0,V.jsxs)(`span`,{className:`long`,children:[`\xA0`,`· `,e]})]})}function tE({frame:e,shown:t=null,onShow:n,waiting:r=0}){let{tabs:i,remote:a,here:o}=e;return i?(0,V.jsxs)(`nav`,{className:`ctabs`,"aria-label":`Computers`,children:[i.map(e=>{let i=Ut(e,t,r),a=i?(0,V.jsx)(`span`,{className:`badge`,title:`${i} waiting for you on ${e.name}`,"aria-label":`${i} waiting for you`,children:i}):null,o=(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`span`,{className:`sw`,"aria-hidden":`true`}),(0,V.jsx)(`span`,{className:`nm`,children:e.name}),a]}),s=e.here?t===null:t===e.id;return e.here?s||!n?(0,V.jsx)(`span`,{className:`ctab on`,style:Bt(e),"aria-current":`page`,children:o},e.id):(0,V.jsx)(`button`,{type:`button`,className:`ctab`,style:Bt(e),onClick:()=>n(null),children:o},e.id):e.url?(0,V.jsx)(`a`,{className:`ctab${s?` on`:``}`,style:Bt(e),href:e.url,target:`_blank`,rel:`noopener noreferrer`,title:`${e.name}'s Ledung, ${new URL(e.url).host}`,"aria-current":s?`page`:void 0,onClick:t=>{n&&Ht(t)&&(t.preventDefault(),n(e.id))},children:o},e.id):null}),(0,V.jsx)(`span`,{className:`spacer`}),a&&(0,V.jsx)(`span`,{className:`remote-tag`,role:`status`,children:eE(o?.name)})]}):a?(0,V.jsx)(`div`,{className:`remote-band`,role:`status`,children:eE(o?.name)}):null}function nE({computers:e,opened:t,shown:n,throughPublicName:r=!1,framed:i=!1}){let[a,o]=(0,v.useState)({}),[s,c]=(0,v.useState)({}),l=(0,v.useRef)({}),u=(0,v.useRef)({}),d=e.filter(e=>!e.here&&e.url&&t.includes(e.id));(0,v.useEffect)(()=>{let e=e=>{for(let t of d)tn({data:e.data,origin:e.origin,fromFrame:e.source===l.current[t.id]?.contentWindow},{id:t.id,url:t.url},localStorage,t=>e.source.postMessage(t,e.origin))&&(clearTimeout(u.current[t.id]),c(e=>({...e,[t.id]:`paired`})))};return window.addEventListener(`message`,e),()=>window.removeEventListener(`message`,e)}),(0,v.useEffect)(()=>()=>Object.values(u.current).forEach(clearTimeout),[]);let f=e=>{clearTimeout(u.current[e.id]),c(t=>({...t,[e.id]:`unknown`})),l.current[e.id]?.contentWindow?.postMessage(Ft(),new URL(e.url).origin),u.current[e.id]=setTimeout(()=>c(t=>({...t,[e.id]:`not-paired`})),jt)};return d.length?(0,V.jsx)(V.Fragment,{children:d.map(e=>(0,V.jsxs)(`div`,{className:`cframe-box`,hidden:n!==e.id,children:[Pt(e,r,i,s[e.id]??`unknown`)&&!a[e.id]&&(0,V.jsx)(rE,{computer:e,onCode:t=>o(n=>({...n,[e.id]:t}))}),a[e.id]?(0,V.jsx)(`iframe`,{className:`cframe`,style:Bt(e),src:a[e.id],title:`${e.name}'s Ledung`,allow:`publickey-credentials-get; publickey-credentials-create`},`pairing`):(0,V.jsx)(`iframe`,{className:`cframe`,style:Bt(e),src:e.url,title:`${e.name}'s Ledung`,allow:`publickey-credentials-get; publickey-credentials-create`,ref:t=>{l.current[e.id]=t},onLoad:()=>f(e)},`page`)]},e.id))}):null}function rE({computer:e,onCode:t}){let[n,r]=(0,v.useState)(`offer`),[i,a]=(0,v.useState)(null);return(0,V.jsxs)(`div`,{className:`cframe-bar`,style:Bt(e),role:n===`offer`?void 0:`alertdialog`,"aria-label":`Pair through the link with ${e.name}`,children:[n===`offer`?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`span`,{children:[`Not paired with `,e.name,` in this tab? It is linked with this computer.`]}),(0,V.jsx)(`button`,{type:`button`,className:`small`,onClick:()=>r(`confirm`),children:`Pair through the link`})]}):(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`span`,{children:[`Pair this browser with `,(0,V.jsx)(`b`,{children:e.name}),` through the link? It can then look at `,e.name,`'s sessions, and change nothing until it sets up its passkey and logs on there with Touch ID or Windows Hello. `,e.name,` shows the pairing.`]}),(0,V.jsx)(`button`,{type:`button`,className:`small`,disabled:n===`busy`,onClick:()=>{r(`busy`),a(null),R.linkDevicePair(e.id).then(({url:e})=>t(e),e=>{a(e.message),r(`offer`)})},children:n===`busy`?`Pairing…`:`Pair`}),(0,V.jsx)(`button`,{type:`button`,className:`small`,disabled:n===`busy`,onClick:()=>r(`offer`),children:`Cancel`})]}),i&&(0,V.jsx)(`span`,{className:`restart-problem`,children:i})]})}function iE(e,t){(0,v.useEffect)(()=>{if(t)return;let n=()=>{let t=zt(location.hash);t&&(history.replaceState(history.state,``,location.pathname+location.search),e(t))};return n(),window.addEventListener(`hashchange`,n),()=>window.removeEventListener(`hashchange`,n)},[])}var aE=`Removed projects`;function oE(e,t,n){return t===aE?!n.has(e.project)&&e.project!==`~chats`:e.project===t}var sE=Vt();sE&&window.addEventListener(`message`,e=>{let t=It(e.data,e.source===window.parent);t&&window.parent.postMessage(t,e.origin)});var cE={default:`Ask`,acceptEdits:`Accept edits`,auto:`Auto`,plan:`Plan`},lE={default:`Every action that needs permission asks you.`,acceptEdits:`File edits go through; commands still ask you.`,auto:`Routine actions are approved automatically; you are asked about the rest.`,plan:`Read-only: Claude plans but changes nothing.`},uE=[`waiting`,`usage`,`overview`,`board`,`settings`,`add`,`accounts`,`chat`,`chats`],dE=e=>!!e&&!uE.includes(e)&&!e.includes(`:`);function fE(){let e=location.hash.match(/^#\/waiting\/q\/(\d+)$/);if(e)return`q:${e[1]}`;let t=SC(location.hash);if(t)return yC(t.repo,t.id);let n=location.hash.match(/^#\/(waiting|usage|overview|board|settings|add|accounts|chat|chats)$/);if(n)return n[1];let r=location.hash.match(/^#\/(settings|chats)\/([a-z]+)$/);if(r)return`${r[1]}:${r[2]}`;let i=location.hash.match(/^#\/ps\/([^/]+)\/([a-z]+)$/);if(i)return`ps:${decodeURIComponent(i[1])}/${i[2]}`;let a=location.hash.match(/^#\/(p|ps|a)\/(.+)$/);return a?`${a[1]}:${decodeURIComponent(a[2])}`:(bg(location.hash)??Sg(location.hash))?.sessionId??null}function pE(e){if(!e)return``;if(uE.includes(e))return`#/${e}`;let t=bC(e);if(t)return xC(t.repo,t.id);if(e.startsWith(`q:`))return`#/waiting/q/${e.slice(2)}`;if(e.startsWith(`settings:`))return`#/settings/${e.slice(9)}`;if(e.startsWith(`chats:`))return`#/chats/${e.slice(6)}`;let n=wp(e);if(n?.project!=null&&n.group)return`#/ps/${encodeURIComponent(n.project)}/${n.group}`;let r=e.match(/^(p|ps|a):(.+)$/);return r?`#/${r[1]}/${encodeURIComponent(r[2])}`:`#/s/${e}`}var mE=()=>history.state??{},hE=()=>Number(mE().ledungDesk??0),gE=()=>mE().ledungDeskRoot===!0;function _E(e){Kh(e)&&mE().ledungDesk===void 0&&history.replaceState({...mE(),ledungDesk:0,ledungDeskRoot:!0},``)}function vE(){let e=history.state??{};return{depth:Number(e.ledungSettings??0),root:e.ledungSettingsRoot===!0}}function yE(e){dw(e)&&(history.state??{}).ledungSettings===void 0&&history.replaceState({...history.state??{},ledungSettings:1,ledungSettingsRoot:!0},``)}var bE=`ledung.waitingSidebar`;function xE(e){try{return localStorage.getItem(`ledung.technical.${e}`)===`1`}catch{return!1}}function SE(){let[e,t]=(0,v.useState)(fE()),[n,r]=(0,v.useState)(location.hash),i=PT(dE(e)?e:null),[a,o]=(0,v.useState)(null),[s,c]=(0,v.useState)(null),[l,u]=(0,v.useState)([]);iE(e=>{c(e),u(t=>t.includes(e)?t:[...t,e])},sE),(0,v.useEffect)(()=>{_E(fE()),yE(fE());let e=()=>{_E(fE()),yE(fE()),t(fE()),r(location.hash)};return window.addEventListener(`hashchange`,e),()=>window.removeEventListener(`hashchange`,e)},[]);let d=n=>{let i=pE(n);if(i!==location.hash){let t=qh(e,{depth:hE(),root:gE()},n),r=fw(e,vE(),n);location.hash=i,history.replaceState({...history.state??{},ledungDesk:t.depth,ledungDeskRoot:t.root,ledungSettings:r.depth,ledungSettingsRoot:r.root,ledungFromList:e===null},``)}t(n),r(location.hash)},f=e=>{history.replaceState(history.state,``,pE(e)),t(e),r(location.hash)},p=(n,a)=>{let o=i.questions[n];if(!o)return;let s=e===`waiting`?`queue`:e?.startsWith(`q:`)?i.questions[Number(e.slice(2))]?.shots?`shots`:`question`:void 0,c=a??vg(o);location.hash=yg(c,n),history.replaceState({...history.state??{},ledungDesk:0,ledungDeskRoot:!1,ledungFrom:s},``),t(c),r(location.hash)},m=(n,a)=>{let o=e===`waiting`?`queue`:e?.startsWith(`q:`)?i.questions[Number(e.slice(2))]?.shots?`shots`:`question`:void 0;location.hash=xg(n,a),history.replaceState({...history.state??{},ledungDesk:0,ledungDeskRoot:!1,ledungFrom:o},``),t(n),r(location.hash)},h=()=>{let e=hE();e>0&&!gE()?history.go(-e):d(_w(window.matchMedia(im).matches))},g=()=>{`back`in gw(history.state)?history.back():d(null)},_=()=>{`back`in Jh(hE())?history.back():d(`waiting`)},y=()=>{let e=pw(vE());`back`in e?history.go(-e.back):d(null)},b=dw(e),x=(0,v.useRef)(y);x.current=y,(0,v.useEffect)(()=>{if(!b)return;let e=e=>{mw(e)&&(e.preventDefault(),x.current())};return document.addEventListener(`keydown`,e),()=>document.removeEventListener(`keydown`,e)},[b]),(0,v.useEffect)(()=>{let e=e=>{if(e.button!==3&&e.button!==4)return;let t=location.href,n=e.button===3;setTimeout(()=>{location.href===t&&(n?history.back():history.forward())},100)};return window.addEventListener(`mouseup`,e),()=>window.removeEventListener(`mouseup`,e)},[]);let[C,w]=(0,v.useState)(()=>{try{return localStorage.getItem(bE)===`hidden`}catch{return!1}}),T=()=>{w(!C);try{localStorage.setItem(bE,C?`shown`:`hidden`)}catch{}},E=Kh(e)&&C,D=(0,v.useMemo)(()=>Object.values(i.questions).sort((e,t)=>t.id-e.id),[i.questions]),O=(0,v.useMemo)(()=>Object.values(i.permissions),[i.permissions]),k=iy(D,O)+i.newComputers.length+i.linkPairings.length,ee=lS(),A=GT({loaded:i.loaded,questions:D,permissions:O,sessions:i.sessions,usageStops:i.usageStops,onOpenSession:d});(0,v.useEffect)(()=>{document.title=k?`(${k}) Project Ledung`:`Project Ledung`},[k]);let j=(0,v.useMemo)(()=>{let e={};for(let t of O)t.status===`pending`&&(e[t.sessionId]=(e[t.sessionId]??0)+1);for(let t of D)t.status===`open`&&(e[t.sessionId]=(e[t.sessionId]??0)+1);return e},[O,D]),M=i.sessions.find(t=>t.id===e)??null,te=Op(e),N=te?.startsWith(`ps:`)?i.projects.find(e=>e.name===te.slice(3)):void 0,P=te===`ledung`?t=>(0,V.jsx)($S,{view:e,update:t,run:oe,board:i.board,remote:i.remote,throughPublicName:i.throughPublicName,newComputers:i.newComputers,projects:i.projects,computers:i.computers,sessions:i.sessions,accounts:i.accounts,accountChoices:i.accountChoices,defaultIdentity:i.defaultIdentity,accountProblems:i.accountProblems,usageStops:i.usageStops,macros:i.macros,canRestart:i.canRestart,source:i.source,config:i.configStatus,hellos:i.hellos,notify:A,onOpen:d}):te===`add`?()=>(0,V.jsx)(qm,{run:oe,accounts:i.accounts,defaultAccount:i.accountChoices.newProjects,profiles:i.profiles,lockdownB:i.lockdownB,onAdded:e=>d(e.managerId??`p:${e.name}`)}):te===`chats`?()=>(0,V.jsx)(Qm,{view:e,chats:i.chats,run:oe,onOpen:d}):N?()=>(0,V.jsx)(Jm,{view:e,board:i.board,projects:i.projects,project:N,run:oe,accounts:i.accounts,profiles:N.profileNames??i.profiles,lockdownB:i.lockdownB,onOpen:d,onRemoved:()=>d(null),onRenamed:f},N.name):null,[ne,re]=(0,v.useState)(()=>{try{return localStorage.getItem(`ledung.limitAccount`)}catch{return null}}),ie=Ry(e,i.sessions,i.projects,ne),ae=ie.account;(0,v.useEffect)(()=>{if(ie.remember&&ie.account!==ne){re(ie.account);try{localStorage.setItem(`ledung.limitAccount`,ie.account)}catch{}}},[ie.remember,ie.account,ne]);let oe=async e=>{o(null);try{await e()}catch(e){o(e.message)}},se=(0,V.jsxs)(V.Fragment,{children:[i.updated&&(0,V.jsxs)(`div`,{className:`banner updated`,children:[(0,V.jsx)(`span`,{children:`Ledung was updated — reload`}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>location.reload(),children:`Reload`})]}),i.away&&gb(i.away,M)&&(0,V.jsx)(pb,{away:i.away,run:oe}),ee.notice&&(0,V.jsx)(dS,{app:ee,run:oe}),(0,V.jsx)(ES,{run:oe}),i.usageStops.filter(e=>e.holding).map(e=>(0,V.jsxs)(`div`,{className:`banner updated`,children:[(0,V.jsx)(`span`,{children:ky(e)}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void oe(()=>R.liftUsageStop(e.account,e.kind)),children:`Lift`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>d(bp(`usageStop`)),children:`Settings`})]},`${e.account}:${e.kind}`)),i.claudeProblem&&(0,V.jsxs)(`div`,{className:`banner updated signin`,role:`alert`,children:[(0,V.jsx)(`span`,{children:(0,V.jsx)(Eb,{text:i.claudeProblem})}),(0,V.jsx)(Tb,{check:async()=>!!(await R.checkSignIn()).claudeProblem}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>d(bp(`claudeProblem`)),children:`Settings`}),i.claudeLooked.length>0&&(0,V.jsx)(Db,{looked:i.claudeLooked})]}),i.configStatus?.problem&&(0,V.jsxs)(`div`,{className:`banner updated signin`,role:`alert`,children:[(0,V.jsxs)(`span`,{children:[`The config file was changed but not applied: `,i.configStatus.problem]}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>d(bp(`configProblem`)),children:`Settings`})]}),i.signedOut.map(e=>(0,V.jsxs)(`div`,{className:`banner updated signin`,children:[(0,V.jsx)(`span`,{children:e.help.split("`").map((e,t)=>t%2?(0,V.jsx)(`code`,{children:e},t):e)}),(0,V.jsx)(Tb,{check:async()=>!!(await R.checkSignIn()).signedOut?.some(t=>t.account===e.account)}),e.account!=="default"&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>d(`settings:claude`),children:`Accounts`})]},`signin:${e.account}`)),a&&(0,V.jsxs)(`div`,{className:`banner error`,onClick:()=>o(null),children:[a,` `,(0,V.jsx)(`span`,{className:`muted`,children:`(click to dismiss)`})]})]}),ce=At(i.computers,i.throughPublicName,sE),le=Rt(i.computers,s);return(0,V.jsxs)(`div`,{className:`page${ce.remote?` remote`:``}`,style:Bt(ce.here),children:[(0,V.jsx)(tE,{frame:ce,shown:le,onShow:e=>{c(e),e&&!l.includes(e)&&u(t=>[...t,e])},waiting:k}),(0,V.jsx)(nE,{computers:i.computers,opened:l,shown:le,throughPublicName:i.throughPublicName,framed:sE}),(0,V.jsxs)(`div`,{className:`app ${hw(e)}${E?` no-sidebar`:``}`,hidden:le!==null,children:[e===null&&(0,V.jsx)(`div`,{className:`phone-banners`,children:se}),(0,V.jsx)(CE,{sessions:i.sessions,projects:i.projects,chats:i.chats,pending:j,waiting:k,limits:i.limits,usageStops:i.usageStops,github:i.github,stripAccount:ae,overview:i.overview,machine:i.machine,run:oe,openId:e,onOpen:d,onCloseSettings:y,profiles:i.profiles,onStart:(e,t)=>oe(async()=>d((await R.start(e,t)).id)),connection:i.connection,board:i.board}),!E&&(0,V.jsx)(xT,{}),(0,V.jsxs)(`main`,{className:`main`,children:[se,e!==null&&!M&&(0,V.jsx)(`div`,{className:`phone-bar`,children:(0,V.jsx)(`button`,{className:`phone-back`,onClick:g,children:`← List`})}),e===`usage`||e===`overview`?(0,V.jsx)(_T,{sessionsOpen:e===`overview`,onSessions:e=>d(e?`overview`:`usage`),sessions:i.sessions,overview:i.overview,machine:i.machine,waitingBySession:j,onOpenSession:d}):Kh(e)?(0,V.jsx)(sy,{questions:D,permissions:O,sessions:i.sessions,projects:i.projects,chats:i.chats,userName:i.userName,questionId:e?.startsWith(`q:`)?Number(e.slice(2)):null,onOpenQuestion:e=>d(e===null?`waiting`:`q:${e}`),onOpenSession:d,onGoToConversation:p,onGoToMessage:m,onClose:h,onLeaveShots:_,sidebarHidden:C,onToggleSidebar:T,newComputers:i.newComputers,linkPairings:i.linkPairings,run:oe}):e===`board`?(0,V.jsx)(NC,{board:i.board,onOpen:d,onOpenSettings:()=>d(`settings`)}):bC(e)?(0,V.jsx)(FC,{repo:bC(e).repo,id:bC(e).id,board:i.board,projects:i.projects,onOpen:d,onBack:()=>d(`board`)},e):P?(0,V.jsx)(Vp,{view:e,projects:i.projects,source:i.source,canRestart:i.canRestart,hellos:i.hellos,onOpen:d,children:P}):e===`chat`?(0,V.jsx)(Zm,{chats:i.chats,profiles:i.profiles,run:oe,onStarted:d}):e?.startsWith(`a:`)?(0,V.jsx)(cb,{title:S(e.slice(2)),sessions:i.sessions.filter(t=>t.archivedAt&&oE(t,e.slice(2),new Set(i.projects.map(e=>e.name)))),overview:i.overview,run:oe,onOpenSession:d},e):e?.startsWith(`p:`)&&i.projects.some(t=>t.name===e.slice(2))?(0,V.jsx)(Ym,{project:i.projects.find(t=>t.name===e.slice(2)),run:oe,onStarted:d},e):M?(0,V.jsx)(wE,{session:M,ledung:i,pendingCount:j[M.id]??0,run:oe,focusQuestion:bg(n)?.questionId??null,focusMessage:Sg(n)?.messageId??null,cameFrom:mE().ledungFrom??null,onOpenQuestion:e=>d(`q:${e}`),onOpenBoardThread:(e,t)=>d(yC(e,t)),onBack:g},M.id):(0,V.jsxs)(`div`,{className:`empty`,children:[(0,V.jsx)(`h1`,{children:`Project Ledung`}),(0,V.jsx)(`p`,{children:i.projects.length?`Open a project on the left to talk to its manager.`:`No projects yet. Add one to start talking to its manager.`}),(0,V.jsxs)(`div`,{className:`empty-actions`,children:[!i.projects.length&&(0,V.jsx)(`button`,{className:`primary`,onClick:()=>d(`add`),children:`Add a project`}),(0,V.jsx)(`button`,{onClick:()=>d(`chat`),children:`New chat`}),(0,V.jsx)(`button`,{onClick:()=>d(`settings`),children:`Settings`})]})]})]})]})]})}function CE(e){let t=e.sessions.filter(e=>!e.archivedAt),n=e=>t.filter(t=>t.parentId===e).sort(BC),r=new Set(e.projects.map(e=>e.name)),i=(e,t,r)=>[{s:e,depth:0,drag:t},...n(e.id).map(t=>({s:t,depth:1,drag:r?`c:${e.id}`:null}))],a=(e,n,r)=>{let a=new Set(t.filter(e).map(e=>e.id)),o=n?t.find(e=>e.id===n):void 0,s=t.filter(t=>e(t)&&t.id!==n&&(!t.parentId||!a.has(t.parentId))).sort(BC);return[...o?i(o,null,!!r):[],...s.flatMap(e=>i(e,r?`t:${r}`:null,!!r))]},o=[{name:x,project:null,rows:a(e=>e.project===x,null,x)},...e.projects.map(e=>({name:e.name,project:e,rows:a(t=>t.project===e.name,e.managerId,e.name)})),{name:aE,project:null,rows:a(e=>!r.has(e.project)&&e.project!==`~chats`,null,null)}].map(t=>({...t,archived:e.sessions.filter(e=>e.archivedAt&&oE(e,t.name,r)).length})).filter(e=>e.project||e.name===`~chats`||e.rows.length||e.archived),[s,c]=(0,v.useState)(()=>nw(localStorage)),[l,u]=(0,v.useState)(()=>iw(localStorage)),d=e=>c(t=>{let n=ow(t,e,e=>e===aE||e===`~chats`||r.has(e));return rw(localStorage,n),n}),f=e=>u(n=>{let r=ow(n,e,e=>t.some(t=>t.id===e));return aw(localStorage,r),r}),p=(e,t)=>e&&e.count>0&&(0,V.jsxs)(`span`,{className:`hidden-count${e.working?` working`:``}`,title:`${e.count} ${t} hidden${e.working?`, at least one working`:``}`,children:[e.working&&(0,V.jsx)(`span`,{className:`dot running`}),`+`,e.count]}),[m,h]=(0,v.useState)(null),[g,_]=(0,v.useState)(null),[y,b]=(0,v.useState)(``),S=(t,n)=>{if(n.length<=1)return e.onStart(t);b(``),h(m===t?null:t)},{nav:C,drag:w,handlers:T}=YC((t,n)=>void e.run(()=>t===`projects`?R.orderProjects(n):R.orderSessions(n))),E=e=>{if(!w||w.slot===null||w.group===`projects`)return null;let t=e.filter(e=>e.drag===w.group);return t.length?w.slot<t.length?{before:t[w.slot].s.id}:{after:w.group.startsWith(`t:`)?e[e.length-1].s.id:t[t.length-1].s.id}:null},D=o.filter(e=>e.project).map(e=>e.name),O=w?.group===`projects`&&w.slot!==null?w.slot<D.length?{before:D[w.slot]}:{after:D[D.length-1]}:null,k=(0,V.jsx)(`div`,{className:`drop-marker${w?.group.startsWith(`c:`)?` child`:``}`,"aria-hidden":`true`}),[ee]=kx(),[A]=Fx(),j=wt(A),[M]=Vx(),te=({s:t,depth:n,drag:r,hidden:i,folds:a,folded:o})=>{let s=`${Eg(t.createdAt)}${t.backgroundTasks>0?` · ${t.backgroundTasks} in background`:``}`,c=(()=>{let n=e.overview?.sessions[t.id]?.today??0,r=t.role===`manager`?e.sessions.filter(e=>e.parentId===t.id).reduce((t,n)=>t+(e.overview?.sessions[n.id]?.today??0),n):n,i=Bw(t),a=t.status===`ended`?void 0:e.machine?.sessions[t.id],o=e.machine?.line.indexOf(t.id)??-1;return[t.project===`~chats`&&t.workDir?`in ${t.workDir.split(/[\\/]/).filter(Boolean).pop()}`:``,o>=0?`number ${o+1} in line`:``,t.paused?`paused`:``,t.priority===`normal`?``:Mw[t.priority].toLowerCase(),a&&(a.cores>=.05||a.memBytes>0)?`${kw(a.cores)} · ${Aw(a.memBytes)}`:``,r?`${Wy(r)}${t.role===`manager`&&r!==n?` team`:``} today`:``,i!=null&&t.status!==`ended`?`ctx ${Ky(i)}`:``,t.pr?qy(t.pr):t.branch??``].filter(Boolean).join(` · `)})();return(0,V.jsxs)(`div`,{className:`session-row`,children:[a&&(0,V.jsx)(`button`,{className:`fold-caret session-caret`,"aria-expanded":!o,"aria-label":`${o?`Unfold`:`Fold`} the sessions of ${t.title}`,title:o?`Show the sessions it runs`:`Fold the sessions it runs away`,onClick:()=>f(t.id),children:o?`▸`:`▾`}),g===t.id?(0,V.jsx)(`div`,{className:`session-item renaming${t.id===e.openId?` open`:``}${n?` child`:``}`,children:(0,V.jsx)(zC,{value:t.title,label:`New name for ${t.title}`,onDone:()=>_(null),onSave:n=>e.run(()=>R.rename(t.id,n))})}):(0,V.jsxs)(`button`,{className:`session-item${t.id===e.openId?` open`:``}${n?` child`:``}${w?.id===t.id?` dragging`:``}${mt(ee,t).ended?` ended-row`:``}`,title:Tt(A,mt(ee,t).tooltip,s,c),onClick:()=>e.onOpen(t.id),onDoubleClick:()=>_(t.id),"data-drag":r??void 0,"data-drag-id":r?t.id:void 0,children:[mt(ee,t).dot&&(0,V.jsx)(`span`,{className:`dot ${ut(t)}`,title:lt[t.status]}),(0,V.jsxs)(`span`,{className:`session-text`,children:[(0,V.jsxs)(`span`,{className:`session-title`,children:[t.role===`manager`&&(0,V.jsx)(`span`,{className:`chip`,children:`Manager`}),` `,(0,V.jsx)(fp,{colour:hp(t,Mv(e.projects,e.chats)),children:t.title})]}),j.time&&(0,V.jsx)(`span`,{className:`session-sub`,children:s}),j.usage&&c&&(0,V.jsx)(`span`,{className:`session-sub usage-line`,children:c})]}),(()=>{let n=j_(t,e.sessions);return n&&(0,V.jsx)(`span`,{className:`session-ship ${ut(t)}`,children:(0,V.jsx)(B_,{mode:n,width:10,sizeButton:!1,hideWhenSunk:!0,maxSize:j.shipMax})})})(),p(i,i?.count===1?`sub-session`:`sub-sessions`),(e.pending[t.id]??0)+(i?.pending??0)?(0,V.jsx)(`span`,{className:`badge`,children:(e.pending[t.id]??0)+(i?.pending??0)}):null]})]})},N=Fe(e.connection);return(0,V.jsxs)(`aside`,{className:`sidebar`,children:[(0,V.jsx)(ob,{account:e.stripAccount,limits:e.limits,stops:e.usageStops,run:e.run}),cw(e.github,Date.now()).map(e=>(0,V.jsx)(`div`,{className:`github-budget muted ${lw(e)}`,title:`What is left of the GitHub budget Ledung's pull request checks use (the worst of GitHub's readings). Under 20 % left they run every 10 minutes, under 5 % not until the reset.`,children:sw(e,e=>new Date(e).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`}))},`${e.container??``} ${e.host}`)),(0,V.jsx)(Pw,{machine:e.machine,sessions:e.sessions,onOpen:e.onOpen,run:e.run}),(0,V.jsxs)(`button`,{className:`waiting-entry${Kh(e.openId)?` open`:``}${e.waiting?` has-items`:``}`,onClick:()=>e.onOpen(`waiting`),children:[(0,V.jsx)(`span`,{children:`Waiting for you`}),e.waiting?(0,V.jsx)(`span`,{className:`badge`,children:e.waiting}):(0,V.jsx)(`span`,{className:`muted`,children:`nothing`})]}),(0,V.jsxs)(`nav`,{className:`session-list`,"data-compact":A>1?A:void 0,ref:C,...T,children:[!e.projects.length&&(0,V.jsx)(`p`,{className:`muted project-empty`,children:`No projects yet. Add one in Settings (⚙ below).`}),o.map(t=>({...t,isFolded:s.includes(t.name),view:$C(t.rows,{foldedSessions:l,folded:s.includes(t.name),openId:e.openId,pending:e.pending})})).map(t=>(0,V.jsxs)(v.Fragment,{children:[O?.before===t.name&&k,(0,V.jsx)(`div`,{className:`project-group${w?.group===`projects`&&w.id===t.name?` dragging`:``}`,children:(0,V.jsxs)($f,{level:qf(t.project),children:[(0,V.jsxs)(`div`,{className:`project-row`,children:[(0,V.jsx)(`button`,{className:`fold-caret`,"aria-expanded":!t.isFolded,"aria-label":`${t.isFolded?`Unfold`:`Fold`} ${t.name}`,title:t.isFolded?`Show its sessions`:`Fold its sessions away`,onClick:()=>d(t.name),children:t.isFolded?`▸`:`▾`}),t.project?(0,V.jsx)(`button`,{className:`project-name${e.openId===`p:${t.name}`||t.project.managerId&&e.openId===t.project.managerId?` open`:``}`,title:`${t.project.where}${t.project.managerId?``:` · manager not started yet`}`,onClick:()=>e.onOpen(t.project.managerId??`p:${t.name}`),"data-drag":`projects`,"data-drag-id":t.name,children:(()=>{let e=By(t.project.account),n=(0,V.jsx)(fp,{colour:t.project.colours.manager,children:t.name});return e?(0,V.jsxs)(`span`,{className:`project-name-stack`,children:[(0,V.jsx)(`span`,{className:`project-account`,title:`Runs on the Claude account ${e}`,children:e}),(0,V.jsx)(`span`,{className:`project-name-text`,children:n})]}):n})()}):t.name===`~chats`?(0,V.jsx)(`button`,{className:`project-name${e.openId===`chat`?` open`:``}`,title:`Sessions of your own with no project, workflow or manager`,onClick:()=>e.onOpen(`chat`),children:(0,V.jsx)(fp,{colour:e.chats?.colour??null,children:`Chats`})}):(0,V.jsx)(`span`,{className:`project-name muted`,children:t.name}),p(t.view.project,t.view.project?.count===1?`session`:`sessions`),t.view.project?.pending?(0,V.jsx)(`span`,{className:`badge`,children:t.view.project.pending}):null,t.name===`~chats`&&(0,V.jsxs)(`span`,{className:`project-actions`,children:[j.plusOnly?(0,V.jsx)(`button`,{className:`mini`,title:`New chat`,"aria-label":`New chat`,onClick:()=>e.onOpen(`chat`),children:`+`}):(0,V.jsx)(`button`,{className:`small`,title:`A Claude Code session of your own, with no project`,onClick:()=>e.onOpen(`chat`),children:`+ Chat`}),(0,V.jsx)(`button`,{className:`${j.plusOnly?`mini cog`:`small`}${Op(e.openId)===`chats`?` on`:``}`,title:`Chats settings`,"aria-label":`Settings of chats`,onClick:()=>e.onOpen(`chats`),children:`⚙`})]}),t.project&&(0,V.jsxs)(`span`,{className:`project-actions`,children:[j.plusOnly?(0,V.jsx)(`button`,{className:`mini`,title:`New session in ${t.name}`,"aria-label":`New session in ${t.name}`,onClick:()=>S(t.name,t.project?.profileNames??e.profiles),children:`+`}):(0,V.jsx)(`button`,{className:`small`,title:`A session of your own in this project, outside its manager`,onClick:()=>S(t.name,t.project?.profileNames??e.profiles),children:`+ Session`}),(0,V.jsx)(`button`,{className:`${j.plusOnly?`mini cog`:`small`}${Op(e.openId)===`ps:${t.name}`?` on`:``}`,title:`Project settings`,"aria-label":`Settings of ${t.name}`,onClick:()=>e.onOpen(`ps:${t.name}`),children:`⚙`})]})]}),t.project&&m===t.name&&(0,V.jsxs)(`div`,{className:`start-row`,children:[(0,V.jsxs)(`select`,{"aria-label":`Profile for a new session in ${t.name}`,value:y,onChange:e=>b(e.target.value),title:`Its session profile: what it gets of your own plugins, MCP servers, tools and settings`,children:[(0,V.jsx)(`option`,{value:``,children:t.project.profiles.session?`Project's: ${t.project.profiles.session}`:`Project's profile`}),(t.project.profileNames??e.profiles).map(e=>(0,V.jsx)(`option`,{value:e,children:e},e))]}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>{h(null),e.onStart(t.name,y||void 0)},children:`Start`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>h(null),children:`Cancel`})]}),(()=>{let e=E(t.view.rows);return t.view.rows.map(t=>(0,V.jsxs)(v.Fragment,{children:[e?.before===t.s.id&&k,te(t),e?.after===t.s.id&&k]},t.s.id))})(),vt(M,t.archived,t.isFolded)&&(0,V.jsxs)(`button`,{className:`archived-link${e.openId===`a:${t.name}`?` open`:``}`,onClick:()=>e.onOpen(`a:${t.name}`),children:[`Archived (`,t.archived,`)`]})]})}),O?.after===t.name&&k]},t.name))]}),(0,V.jsxs)(`div`,{className:`connection ${e.connection}`,children:[(0,V.jsx)(`button`,{className:`icon settings-cog${dw(e.openId)?` on`:``}`,title:dw(e.openId)?`Close settings (Esc)`:`Settings: accounts, restart Ledung, add a project`,"aria-label":dw(e.openId)?`Close settings`:`Settings`,"aria-pressed":dw(e.openId),onClick:()=>dw(e.openId)?e.onCloseSettings():e.onOpen(`settings`),children:`⚙`}),(0,V.jsxs)(`span`,{className:`footer-chips`,children:[(0,V.jsxs)(`button`,{className:`board-chip usage-chip${Ie(e.board)?``:` ${N.className}`}${e.openId===`usage`||e.openId===`overview`?` on`:``}`,title:`${Ie(e.board)?``:`${N.text} `}Usage: tokens per day, project and model, shared usage, and every live session`,"aria-pressed":e.openId===`usage`||e.openId===`overview`,onClick:()=>e.onOpen(`usage`),children:[`Usage`,e.overview?` · ${Wy(e.overview.todayTokens)} today`:``]}),(0,V.jsx)(yn,{board:e.board,open:e.openId===`board`||!!bC(e.openId),connection:N,onClick:()=>e.onOpen(`board`)})]})]})]})}function wE(e){let{session:t,ledung:n,run:r}=e,[i,a]=(0,v.useState)(()=>xE(t.id)),[o,s]=(0,v.useState)([]),[c,l]=(0,v.useState)(!1),[u,d]=(0,v.useState)(!1),[f,p]=(0,v.useState)(!1);(0,v.useEffect)(()=>p(!1),[t.id]);let m=(0,v.useRef)(null),h=(0,v.useCallback)((e,t,n)=>{let r=n.length>2e3?`${n.slice(0,2e3)}…`:n;m.current?.(`> ${e}, ${Eg(t)}:\n${r.split(`
|
|
103
|
+
`}return f.substring(0,f.length-1)},c.renderTo2dContext=function(e,t){t||=2;let n=c.getModuleCount();for(let r=0;r<n;r++)for(let i=0;i<n;i++)e.fillStyle=c.isDark(r,i)?`black`:`white`,e.fillRect(i*t,r*t,t,t)},c};Pb.stringToBytes=function(e){let t=[];for(let n=0;n<e.length;n+=1){let r=e.charCodeAt(n);t.push(r&255)}return t},Pb.createStringToBytes=function(e,t){let n=function(){let n=Yb(e),r=function(){let e=n.read();if(e==-1)throw`eof`;return e},i=0,a={};for(;;){let e=n.read();if(e==-1)break;let t=r(),o=r(),s=r(),c=String.fromCharCode(e<<8|t);a[c]=o<<8|s,i+=1}if(i!=t)throw i+` != `+t;return a}();return function(e){let t=[];for(let r=0;r<e.length;r+=1){let i=e.charCodeAt(r);if(i<128)t.push(i);else{let i=n[e.charAt(r)];typeof i==`number`?(i&255)==i?t.push(i):(t.push(i>>>8),t.push(i&255)):t.push(63)}}return t}};var Fb={MODE_NUMBER:1,MODE_ALPHA_NUM:2,MODE_8BIT_BYTE:4,MODE_KANJI:8},Ib={L:1,M:0,Q:3,H:2},Lb={PATTERN000:0,PATTERN001:1,PATTERN010:2,PATTERN011:3,PATTERN100:4,PATTERN101:5,PATTERN110:6,PATTERN111:7},Rb=function(){let e=[[],[6,18],[6,22],[6,26],[6,30],[6,34],[6,22,38],[6,24,42],[6,26,46],[6,28,50],[6,30,54],[6,32,58],[6,34,62],[6,26,46,66],[6,26,48,70],[6,26,50,74],[6,30,54,78],[6,30,56,82],[6,30,58,86],[6,34,62,90],[6,28,50,72,94],[6,26,50,74,98],[6,30,54,78,102],[6,28,54,80,106],[6,32,58,84,110],[6,30,58,86,114],[6,34,62,90,118],[6,26,50,74,98,122],[6,30,54,78,102,126],[6,26,52,78,104,130],[6,30,56,82,108,134],[6,34,60,86,112,138],[6,30,58,86,114,142],[6,34,62,90,118,146],[6,30,54,78,102,126,150],[6,24,50,76,102,128,154],[6,28,54,80,106,132,158],[6,32,58,84,110,136,162],[6,26,54,82,110,138,166],[6,30,58,86,114,142,170]],t=1335,n=7973,r={},i=function(e){let t=0;for(;e!=0;)t+=1,e>>>=1;return t};return r.getBCHTypeInfo=function(e){let n=e<<10;for(;i(n)-i(t)>=0;)n^=t<<i(n)-i(t);return(e<<10|n)^21522},r.getBCHTypeNumber=function(e){let t=e<<12;for(;i(t)-i(n)>=0;)t^=n<<i(t)-i(n);return e<<12|t},r.getPatternPosition=function(t){return e[t-1]},r.getMaskFunction=function(e){switch(e){case Lb.PATTERN000:return function(e,t){return(e+t)%2==0};case Lb.PATTERN001:return function(e,t){return e%2==0};case Lb.PATTERN010:return function(e,t){return t%3==0};case Lb.PATTERN011:return function(e,t){return(e+t)%3==0};case Lb.PATTERN100:return function(e,t){return(Math.floor(e/2)+Math.floor(t/3))%2==0};case Lb.PATTERN101:return function(e,t){return e*t%2+e*t%3==0};case Lb.PATTERN110:return function(e,t){return(e*t%2+e*t%3)%2==0};case Lb.PATTERN111:return function(e,t){return(e*t%3+(e+t)%2)%2==0};default:throw`bad maskPattern:`+e}},r.getErrorCorrectPolynomial=function(e){let t=Bb([1],0);for(let n=0;n<e;n+=1)t=t.multiply(Bb([1,zb.gexp(n)],0));return t},r.getLengthInBits=function(e,t){if(1<=t&&t<10)switch(e){case Fb.MODE_NUMBER:return 10;case Fb.MODE_ALPHA_NUM:return 9;case Fb.MODE_8BIT_BYTE:return 8;case Fb.MODE_KANJI:return 8;default:throw`mode:`+e}else if(t<27)switch(e){case Fb.MODE_NUMBER:return 12;case Fb.MODE_ALPHA_NUM:return 11;case Fb.MODE_8BIT_BYTE:return 16;case Fb.MODE_KANJI:return 10;default:throw`mode:`+e}else if(t<41)switch(e){case Fb.MODE_NUMBER:return 14;case Fb.MODE_ALPHA_NUM:return 13;case Fb.MODE_8BIT_BYTE:return 16;case Fb.MODE_KANJI:return 12;default:throw`mode:`+e}else throw`type:`+t},r.getLostPoint=function(e){let t=e.getModuleCount(),n=0;for(let r=0;r<t;r+=1)for(let i=0;i<t;i+=1){let a=0,o=e.isDark(r,i);for(let n=-1;n<=1;n+=1)if(!(r+n<0||t<=r+n))for(let s=-1;s<=1;s+=1)i+s<0||t<=i+s||(n!=0||s!=0)&&o==e.isDark(r+n,i+s)&&(a+=1);a>5&&(n+=3+a-5)}for(let r=0;r<t-1;r+=1)for(let i=0;i<t-1;i+=1){let t=0;e.isDark(r,i)&&(t+=1),e.isDark(r+1,i)&&(t+=1),e.isDark(r,i+1)&&(t+=1),e.isDark(r+1,i+1)&&(t+=1),(t==0||t==4)&&(n+=3)}for(let r=0;r<t;r+=1)for(let i=0;i<t-6;i+=1)e.isDark(r,i)&&!e.isDark(r,i+1)&&e.isDark(r,i+2)&&e.isDark(r,i+3)&&e.isDark(r,i+4)&&!e.isDark(r,i+5)&&e.isDark(r,i+6)&&(n+=40);for(let r=0;r<t;r+=1)for(let i=0;i<t-6;i+=1)e.isDark(i,r)&&!e.isDark(i+1,r)&&e.isDark(i+2,r)&&e.isDark(i+3,r)&&e.isDark(i+4,r)&&!e.isDark(i+5,r)&&e.isDark(i+6,r)&&(n+=40);let r=0;for(let n=0;n<t;n+=1)for(let i=0;i<t;i+=1)e.isDark(i,n)&&(r+=1);let i=Math.abs(100*r/t/t-50)/5;return n+=i*10,n},r}(),zb=function(){let e=Array(256),t=Array(256);for(let t=0;t<8;t+=1)e[t]=1<<t;for(let t=8;t<256;t+=1)e[t]=e[t-4]^e[t-5]^e[t-6]^e[t-8];for(let n=0;n<255;n+=1)t[e[n]]=n;let n={};return n.glog=function(e){if(e<1)throw`glog(`+e+`)`;return t[e]},n.gexp=function(t){for(;t<0;)t+=255;for(;t>=256;)t-=255;return e[t]},n}(),Bb=function(e,t){if(e.length===void 0)throw e.length+`/`+t;let n=function(){let n=0;for(;n<e.length&&e[n]==0;)n+=1;let r=Array(e.length-n+t);for(let t=0;t<e.length-n;t+=1)r[t]=e[t+n];return r}(),r={};return r.getAt=function(e){return n[e]},r.getLength=function(){return n.length},r.multiply=function(e){let t=Array(r.getLength()+e.getLength()-1);for(let n=0;n<r.getLength();n+=1)for(let i=0;i<e.getLength();i+=1)t[n+i]^=zb.gexp(zb.glog(r.getAt(n))+zb.glog(e.getAt(i)));return Bb(t,0)},r.mod=function(e){if(r.getLength()-e.getLength()<0)return r;let t=zb.glog(r.getAt(0))-zb.glog(e.getAt(0)),n=Array(r.getLength());for(let e=0;e<r.getLength();e+=1)n[e]=r.getAt(e);for(let r=0;r<e.getLength();r+=1)n[r]^=zb.gexp(zb.glog(e.getAt(r))+t);return Bb(n,0).mod(e)},r},Vb=function(){let e=[[1,26,19],[1,26,16],[1,26,13],[1,26,9],[1,44,34],[1,44,28],[1,44,22],[1,44,16],[1,70,55],[1,70,44],[2,35,17],[2,35,13],[1,100,80],[2,50,32],[2,50,24],[4,25,9],[1,134,108],[2,67,43],[2,33,15,2,34,16],[2,33,11,2,34,12],[2,86,68],[4,43,27],[4,43,19],[4,43,15],[2,98,78],[4,49,31],[2,32,14,4,33,15],[4,39,13,1,40,14],[2,121,97],[2,60,38,2,61,39],[4,40,18,2,41,19],[4,40,14,2,41,15],[2,146,116],[3,58,36,2,59,37],[4,36,16,4,37,17],[4,36,12,4,37,13],[2,86,68,2,87,69],[4,69,43,1,70,44],[6,43,19,2,44,20],[6,43,15,2,44,16],[4,101,81],[1,80,50,4,81,51],[4,50,22,4,51,23],[3,36,12,8,37,13],[2,116,92,2,117,93],[6,58,36,2,59,37],[4,46,20,6,47,21],[7,42,14,4,43,15],[4,133,107],[8,59,37,1,60,38],[8,44,20,4,45,21],[12,33,11,4,34,12],[3,145,115,1,146,116],[4,64,40,5,65,41],[11,36,16,5,37,17],[11,36,12,5,37,13],[5,109,87,1,110,88],[5,65,41,5,66,42],[5,54,24,7,55,25],[11,36,12,7,37,13],[5,122,98,1,123,99],[7,73,45,3,74,46],[15,43,19,2,44,20],[3,45,15,13,46,16],[1,135,107,5,136,108],[10,74,46,1,75,47],[1,50,22,15,51,23],[2,42,14,17,43,15],[5,150,120,1,151,121],[9,69,43,4,70,44],[17,50,22,1,51,23],[2,42,14,19,43,15],[3,141,113,4,142,114],[3,70,44,11,71,45],[17,47,21,4,48,22],[9,39,13,16,40,14],[3,135,107,5,136,108],[3,67,41,13,68,42],[15,54,24,5,55,25],[15,43,15,10,44,16],[4,144,116,4,145,117],[17,68,42],[17,50,22,6,51,23],[19,46,16,6,47,17],[2,139,111,7,140,112],[17,74,46],[7,54,24,16,55,25],[34,37,13],[4,151,121,5,152,122],[4,75,47,14,76,48],[11,54,24,14,55,25],[16,45,15,14,46,16],[6,147,117,4,148,118],[6,73,45,14,74,46],[11,54,24,16,55,25],[30,46,16,2,47,17],[8,132,106,4,133,107],[8,75,47,13,76,48],[7,54,24,22,55,25],[22,45,15,13,46,16],[10,142,114,2,143,115],[19,74,46,4,75,47],[28,50,22,6,51,23],[33,46,16,4,47,17],[8,152,122,4,153,123],[22,73,45,3,74,46],[8,53,23,26,54,24],[12,45,15,28,46,16],[3,147,117,10,148,118],[3,73,45,23,74,46],[4,54,24,31,55,25],[11,45,15,31,46,16],[7,146,116,7,147,117],[21,73,45,7,74,46],[1,53,23,37,54,24],[19,45,15,26,46,16],[5,145,115,10,146,116],[19,75,47,10,76,48],[15,54,24,25,55,25],[23,45,15,25,46,16],[13,145,115,3,146,116],[2,74,46,29,75,47],[42,54,24,1,55,25],[23,45,15,28,46,16],[17,145,115],[10,74,46,23,75,47],[10,54,24,35,55,25],[19,45,15,35,46,16],[17,145,115,1,146,116],[14,74,46,21,75,47],[29,54,24,19,55,25],[11,45,15,46,46,16],[13,145,115,6,146,116],[14,74,46,23,75,47],[44,54,24,7,55,25],[59,46,16,1,47,17],[12,151,121,7,152,122],[12,75,47,26,76,48],[39,54,24,14,55,25],[22,45,15,41,46,16],[6,151,121,14,152,122],[6,75,47,34,76,48],[46,54,24,10,55,25],[2,45,15,64,46,16],[17,152,122,4,153,123],[29,74,46,14,75,47],[49,54,24,10,55,25],[24,45,15,46,46,16],[4,152,122,18,153,123],[13,74,46,32,75,47],[48,54,24,14,55,25],[42,45,15,32,46,16],[20,147,117,4,148,118],[40,75,47,7,76,48],[43,54,24,22,55,25],[10,45,15,67,46,16],[19,148,118,6,149,119],[18,75,47,31,76,48],[34,54,24,34,55,25],[20,45,15,61,46,16]],t=function(e,t){let n={};return n.totalCount=e,n.dataCount=t,n},n={},r=function(t,n){switch(n){case Ib.L:return e[(t-1)*4+0];case Ib.M:return e[(t-1)*4+1];case Ib.Q:return e[(t-1)*4+2];case Ib.H:return e[(t-1)*4+3];default:return}};return n.getRSBlocks=function(e,n){let i=r(e,n);if(i===void 0)throw`bad rs block @ typeNumber:`+e+`/errorCorrectionLevel:`+n;let a=i.length/3,o=[];for(let e=0;e<a;e+=1){let n=i[e*3+0],r=i[e*3+1],a=i[e*3+2];for(let e=0;e<n;e+=1)o.push(t(r,a))}return o},n}(),Hb=function(){let e=[],t=0,n={};return n.getBuffer=function(){return e},n.getAt=function(t){let n=Math.floor(t/8);return(e[n]>>>7-t%8&1)==1},n.put=function(e,t){for(let r=0;r<t;r+=1)n.putBit((e>>>t-r-1&1)==1)},n.getLengthInBits=function(){return t},n.putBit=function(n){let r=Math.floor(t/8);e.length<=r&&e.push(0),n&&(e[r]|=128>>>t%8),t+=1},n},Ub=function(e){let t=Fb.MODE_NUMBER,n=e,r={};r.getMode=function(){return t},r.getLength=function(e){return n.length},r.write=function(e){let t=n,r=0;for(;r+2<t.length;)e.put(i(t.substring(r,r+3)),10),r+=3;r<t.length&&(t.length-r==1?e.put(i(t.substring(r,r+1)),4):t.length-r==2&&e.put(i(t.substring(r,r+2)),7))};let i=function(e){let t=0;for(let n=0;n<e.length;n+=1)t=t*10+a(e.charAt(n));return t},a=function(e){if(`0`<=e&&e<=`9`)return e.charCodeAt(0)-48;throw`illegal char :`+e};return r},Wb=function(e){let t=Fb.MODE_ALPHA_NUM,n=e,r={};r.getMode=function(){return t},r.getLength=function(e){return n.length},r.write=function(e){let t=n,r=0;for(;r+1<t.length;)e.put(i(t.charAt(r))*45+i(t.charAt(r+1)),11),r+=2;r<t.length&&e.put(i(t.charAt(r)),6)};let i=function(e){if(`0`<=e&&e<=`9`)return e.charCodeAt(0)-48;if(`A`<=e&&e<=`Z`)return e.charCodeAt(0)-65+10;switch(e){case` `:return 36;case`$`:return 37;case`%`:return 38;case`*`:return 39;case`+`:return 40;case`-`:return 41;case`.`:return 42;case`/`:return 43;case`:`:return 44;default:throw`illegal char :`+e}};return r},Gb=function(e){let t=Fb.MODE_8BIT_BYTE,n=Pb.stringToBytes(e),r={};return r.getMode=function(){return t},r.getLength=function(e){return n.length},r.write=function(e){for(let t=0;t<n.length;t+=1)e.put(n[t],8)},r},Kb=function(e){let t=Fb.MODE_KANJI,n=Pb.stringToBytes;(function(e,t){let r=n(e);if(r.length!=2||(r[0]<<8|r[1])!=t)throw`sjis not supported.`})(`友`,38726);let r=n(e),i={};return i.getMode=function(){return t},i.getLength=function(e){return~~(r.length/2)},i.write=function(e){let t=r,n=0;for(;n+1<t.length;){let r=(255&t[n])<<8|255&t[n+1];if(33088<=r&&r<=40956)r-=33088;else if(57408<=r&&r<=60351)r-=49472;else throw`illegal char at `+(n+1)+`/`+r;r=(r>>>8&255)*192+(r&255),e.put(r,13),n+=2}if(n<t.length)throw`illegal char at `+(n+1)},i},qb=function(){let e=[],t={};return t.writeByte=function(t){e.push(t&255)},t.writeShort=function(e){t.writeByte(e),t.writeByte(e>>>8)},t.writeBytes=function(e,n,r){n||=0,r||=e.length;for(let i=0;i<r;i+=1)t.writeByte(e[i+n])},t.writeString=function(e){for(let n=0;n<e.length;n+=1)t.writeByte(e.charCodeAt(n))},t.toByteArray=function(){return e},t.toString=function(){let t=``;t+=`[`;for(let n=0;n<e.length;n+=1)n>0&&(t+=`,`),t+=e[n];return t+=`]`,t},t},Jb=function(){let e=0,t=0,n=0,r=``,i={},a=function(e){r+=String.fromCharCode(o(e&63))},o=function(e){if(e<0)throw`n:`+e;if(e<26)return 65+e;if(e<52)return 97+(e-26);if(e<62)return 48+(e-52);if(e==62)return 43;if(e==63)return 47;throw`n:`+e};return i.writeByte=function(r){for(e=e<<8|r&255,t+=8,n+=1;t>=6;)a(e>>>t-6),t-=6},i.flush=function(){if(t>0&&(a(e<<6-t),e=0,t=0),n%3!=0){let e=3-n%3;for(let t=0;t<e;t+=1)r+=`=`}},i.toString=function(){return r},i},Yb=function(e){let t=e,n=0,r=0,i=0,a={};a.read=function(){for(;i<8;){if(n>=t.length){if(i==0)return-1;throw`unexpected end of file./`+i}let e=t.charAt(n);if(n+=1,e==`=`)return i=0,-1;e.match(/^\s$/)||(r=r<<6|o(e.charCodeAt(0)),i+=6)}let e=r>>>i-8&255;return i-=8,e};let o=function(e){if(65<=e&&e<=90)return e-65;if(97<=e&&e<=122)return e-97+26;if(48<=e&&e<=57)return e-48+52;if(e==43)return 62;if(e==47)return 63;throw`c:`+e};return a},Xb=function(e,t){let n=e,r=t,i=Array(e*t),a={};a.setPixel=function(e,t,r){i[t*n+e]=r},a.write=function(e){e.writeString(`GIF87a`),e.writeShort(n),e.writeShort(r),e.writeByte(128),e.writeByte(0),e.writeByte(0),e.writeByte(0),e.writeByte(0),e.writeByte(0),e.writeByte(255),e.writeByte(255),e.writeByte(255),e.writeString(`,`),e.writeShort(0),e.writeShort(0),e.writeShort(n),e.writeShort(r),e.writeByte(0);let t=s(2);e.writeByte(2);let i=0;for(;t.length-i>255;)e.writeByte(255),e.writeBytes(t,i,255),i+=255;e.writeByte(t.length-i),e.writeBytes(t,i,t.length-i),e.writeByte(0),e.writeString(`;`)};let o=function(e){let t=e,n=0,r=0,i={};return i.write=function(e,i){if(e>>>i)throw`length over`;for(;n+i>=8;)t.writeByte(255&(e<<n|r)),i-=8-n,e>>>=8-n,r=0,n=0;r=e<<n|r,n+=i},i.flush=function(){n>0&&t.writeByte(r)},i},s=function(e){let t=1<<e,n=(1<<e)+1,r=e+1,a=c();for(let e=0;e<t;e+=1)a.add(String.fromCharCode(e));a.add(String.fromCharCode(t)),a.add(String.fromCharCode(n));let s=qb(),l=o(s);l.write(t,r);let u=0,d=String.fromCharCode(i[u]);for(u+=1;u<i.length;){let e=String.fromCharCode(i[u]);u+=1,a.contains(d+e)?d+=e:(l.write(a.indexOf(d),r),a.size()<4095&&(a.size()==1<<r&&(r+=1),a.add(d+e)),d=e)}return l.write(a.indexOf(d),r),l.write(n,r),l.flush(),s.toByteArray()},c=function(){let e={},t=0,n={};return n.add=function(r){if(n.contains(r))throw`dup key:`+r;e[r]=t,t+=1},n.size=function(){return t},n.indexOf=function(t){return e[t]},n.contains=function(t){return e[t]!==void 0},n};return a},Zb=function(e,t,n){let r=Xb(e,t);for(let i=0;i<t;i+=1)for(let t=0;t<e;t+=1)r.setPixel(t,i,n(t,i));let i=qb();r.write(i);let a=Jb(),o=i.toByteArray();for(let e=0;e<o.length;e+=1)a.writeByte(o[e]);return a.flush(),`data:image/gif;base64,`+a};Pb.stringToBytes;var Qb=/^[0-9A-Z $%*+\-./:]*$/,$b=.3,ex=e=>e.toUpperCase();function tx(e){let t=Pb(0,`H`);t.addData(e,Qb.test(e)?`Alphanumeric`:`Byte`),t.make();let n=t.getModuleCount(),r=Math.floor(n*$b);r%2==0&&r--;let i=(n-r)/2,a=(e,t)=>e>=i&&e<i+r&&t>=i&&t<i+r;return{n,dark:(e,n)=>!a(e,n)&&t.isDark(e,n),logo:{from:i,size:r}}}function nx(e){return e.secure&&e.serviceWorker&&e.pushManager?`yes`:/iPhone|iPad|iPod/.test(e.userAgent)&&!e.standalone?`home-screen`:`no`}var rx=()=>nx({secure:window.isSecureContext,serviceWorker:`serviceWorker`in navigator,pushManager:`PushManager`in window,userAgent:navigator.userAgent,standalone:navigator.standalone===!0||matchMedia(`(display-mode: standalone)`).matches});function ix(e){let t=e.replace(/-/g,`+`).replace(/_/g,`/`).padEnd(Math.ceil(e.length/4)*4,`=`);return Uint8Array.from(atob(t),e=>e.charCodeAt(0))}function ax(e,t){return!e||e.byteLength!==t.length?!1:new Uint8Array(e).every((e,n)=>e===t[n])}async function ox(){return await navigator.serviceWorker.register(`/sw.js`,{scope:`/`}),navigator.serviceWorker.ready}async function sx(){if((Notification.permission===`granted`?`granted`:await Notification.requestPermission())!==`granted`)throw Error(`Notifications are blocked for Ledung here. Allow them in the settings for it, then switch this on again.`);let{publicKey:e}=await R.pushState(),t=await ox(),n=ix(e),r=await t.pushManager.getSubscription();r&&!ax(r.options.applicationServerKey,n)&&(await r.unsubscribe(),r=null),r??=await t.pushManager.subscribe({userVisibleOnly:!0,applicationServerKey:n}),await R.pushOn(r.toJSON())}async function cx(){await R.pushOff(),await(await(await navigator.serviceWorker.getRegistration(`/`))?.pushManager.getSubscription())?.unsubscribe()}async function lx(){let{on:e}=await R.pushState();return e?!!await(await navigator.serviceWorker.getRegistration(`/`))?.pushManager.getSubscription():!1}function ux(e){return e?`Pushes for this computer come through the first tab: on the phone, switch on push notifications in Settings there, under Phones. They say this computer's name, and tapping one opens this tab.`:`Pushes for this computer come through the first tab once the two computers are linked (Settings → Linked computers); then, on the phone, switch them on in Settings there, under Phones.`}var dx=e=>e?new Date(e).toLocaleString():`never`;function fx({text:e}){let{n:t,dark:n,logo:r}=tx(e),i=[];for(let e=0;e<t;e++)for(let r=0;r<t;r++)n(e,r)&&i.push(`M${r+4},${e+4}h1v1h-1z`);let a=r.from+4+.5,o=r.size-1;return(0,V.jsxs)(`svg`,{className:`qr`,viewBox:`0 0 ${t+8} ${t+8}`,width:220,height:220,role:`img`,"aria-label":`QR code of the pairing link`,children:[(0,V.jsx)(`rect`,{width:t+8,height:t+8,fill:`#fff`}),(0,V.jsx)(`path`,{d:i.join(``),fill:`#000`}),(0,V.jsx)(`image`,{href:`/icon.svg?v=2`,x:a,y:a,width:o,height:o})]})}function px({run:e,linked:t=!1}){let[n,r]=(0,v.useState)(null);return(0,v.useEffect)(()=>{R.thisDevice().then(r,()=>r({remote:!1}))},[]),n?(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Phones`}),n.remote?(0,V.jsx)(mx,{device:n.device,mayAddPasskey:n.mayAddPasskey,unlockedUntil:n.unlockedUntil,linked:t,run:e,onChange:()=>R.thisDevice().then(r)}):(0,V.jsx)(vx,{run:e})]}):null}function mx(e){let{device:t,unlockedUntil:n}=e,[r,i]=(0,v.useState)(Date.now());(0,v.useEffect)(()=>{let e=setInterval(()=>i(Date.now()),15e3);return()=>clearInterval(e)},[]);let a=n!==null&&n>r,o=t.kind===`computer`;return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`This device is paired as `,(0,V.jsx)(`b`,{children:t.name}),o?`, a computer`:``,`. Devices are listed and removed in Settings on the computer Ledung runs on.`]}),t.passkey&&o?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Its passkey is set up: allowing a sensitive call from here asks for it (Touch ID or Windows Hello) each time.`}),(0,V.jsx)(`p`,{children:a?(0,V.jsx)(V.Fragment,{children:`🔓 Logged on: changes need nothing more until you log out, or until 14 days without use.`}):(0,V.jsx)(V.Fragment,{children:`🔒 Logged off: from here you can look, not change anything. Log on with the passkey; it lasts until you log out.`})}),a?(0,V.jsx)(`button`,{onClick:()=>void e.run(async()=>{await R.logOutDevice(),e.onChange()}),children:`Log out`}):(0,V.jsx)(`button`,{onClick:()=>void e.run(async()=>{await R.unlockDevice(),e.onChange()}),children:`Log on`}),Vt()&&(0,V.jsx)(gx,{linked:e.linked})]}):t.passkey?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Its passkey is set up: allowing a sensitive call or writing to a manager from here asks for it (Face ID or fingerprint) each time.`}),(0,V.jsx)(`p`,{children:a?(0,V.jsxs)(V.Fragment,{children:[`🔓 Unlocked for changes until `,new Date(n).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`}),`.`]}):(0,V.jsx)(V.Fragment,{children:`🔒 Locked: from here you can look, not change anything. Unlocking takes the passkey once and lasts 30 minutes.`})}),!a&&(0,V.jsx)(`button`,{onClick:()=>void e.run(async()=>{await R.unlockDevice(),e.onChange()}),children:`Unlock`}),Vt()?(0,V.jsx)(gx,{linked:e.linked}):(0,V.jsx)(_x,{run:e.run,onChange:e.onChange})]}):e.mayAddPasskey&&Vt()?(0,V.jsx)(hx,{run:e.run,onChange:e.onChange}):e.mayAddPasskey?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Set up a passkey now: without it this device can only look, and every change waits for the computer. This is possible in the first 10 minutes after pairing.`}),(0,V.jsx)(`button`,{onClick:()=>void e.run(async()=>{await R.addPasskey(),e.onChange()}),children:`Set up passkey`})]}):(0,V.jsx)(`p`,{className:`muted`,children:`No passkey: this device can only look; changes wait for the computer. To add one, pair this device again from Settings on the computer.`})]})}function hx({run:e,onChange:t}){let[n,r]=(0,v.useState)(null);return(0,v.useEffect)(()=>{if(!n)return;let e=setInterval(()=>{R.thisDevice().then(e=>{e.remote&&e.device.passkey&&t()},()=>{}),Date.now()>n.expiresAt&&r(null)},2e3);return()=>clearInterval(e)},[n,t]),(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Set up a passkey now: without it this device can only look. It is made in a window of its own (here inside another computer's page the browser may not make one), and works here afterwards. This is possible in the first 10 minutes after pairing.`}),n?(0,V.jsxs)(`p`,{children:[(0,V.jsx)(`a`,{className:`button-link`,href:n.url,target:`_blank`,rel:`noopener noreferrer`,children:`Open the passkey window`}),` `,(0,V.jsx)(`span`,{className:`muted`,children:`· then come back here`})]}):(0,V.jsx)(`button`,{onClick:()=>void e(async()=>r(await R.passkeyEnrolLink())),children:`Set up passkey`})]})}function gx({linked:e}){return(0,V.jsx)(`p`,{className:`muted push-switch framed-push`,children:ux(e)})}function _x({run:e,onChange:t}){let n=rx(),[r,i]=(0,v.useState)(null);if((0,v.useEffect)(()=>{n===`yes`&&lx().then(i,()=>i(!1))},[n]),n===`home-screen`)return(0,V.jsx)(`p`,{className:`muted push-switch`,children:`Push notifications on an iPhone need Ledung on the Home Screen: Share → Add to Home Screen, then open it from there and switch them on here.`});if(n===`no`)return(0,V.jsx)(`p`,{className:`muted push-switch`,children:`This browser can't get push notifications.`});if(r===null)return null;let a=n=>void e(async()=>{try{await(n?sx():cx()),i(n)}finally{t()}});return(0,V.jsxs)(`div`,{className:`push-switch`,children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`A notification on this phone when something new waits for you, even with Ledung closed`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r,onChange:e=>a(e.target.checked)}),` Push notifications to this phone`]}),(0,V.jsx)(`p`,{className:`muted`,children:`When something new waits for you on this computer. It says which computer and what kind of item, never the text: that loads when you open it.`})]})}function vx({run:e}){let[t,n]=(0,v.useState)(null),[r,i]=(0,v.useState)(null),[a,o]=(0,v.useState)(Date.now()),s=()=>R.devices().then(e=>{n(e),i(t=>t&&e.devices.length>t.before?null:t)},()=>{});if((0,v.useEffect)(()=>{s()},[]),(0,v.useEffect)(()=>{if(!r)return;let e=setInterval(()=>{o(Date.now()),s()},2e3);return()=>clearInterval(e)},[r]),!t)return null;if(!t.publicName)return(0,V.jsx)(`p`,{className:`muted`,children:`Reaching Ledung from a phone anywhere needs a relay: set "remote" with its "publicName" in the config. Then phones are paired here.`});let c=r&&r.expiresAt>a?r:null;return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`Phones, and other computers' Ledung pages (their tab for this computer), that reach this Ledung at https://`,t.publicName,`. Only a paired device gets in there; the sign-in link does not work there. A phone unlocks for 30 minutes at a time; a computer stays logged on until it logs out.`]}),t.devices.length===0&&(0,V.jsx)(`p`,{className:`muted`,children:`No paired devices.`}),t.devices.map(t=>(0,V.jsxs)(`div`,{className:`device-row`,children:[(0,V.jsxs)(`span`,{children:[(0,V.jsx)(`b`,{children:t.name}),` `,(0,V.jsxs)(`span`,{className:`muted`,children:[`· `,t.kind===`computer`?`computer`:`phone`,` · paired `,t.pairedVia?`through the link from ${t.pairedVia} `:``,dx(t.createdAt),` · last used `,dx(t.lastUsedAt),` · `,t.passkey?`passkey added ${dx(t.passkeyAt)}`:`no passkey`]})]}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e(async()=>{await R.revokeDevice(t.id),await s()}),children:`Revoke`})]},t.id)),c?(0,V.jsxs)(`div`,{className:`pairing`,children:[c.kind===`phone`&&(0,V.jsx)(fx,{text:ex(c.url)}),c.kind===`computer`?(0,V.jsxs)(`p`,{className:`muted`,children:[`On the other computer, click this computer's tab and type the code, or the link, into the field there. It works once, for `,Math.max(0,Math.ceil((c.expiresAt-a)/6e4)),` more minute(s). Then set up the passkey there and log on: it stays logged on until you log out.`]}):(0,V.jsxs)(`p`,{className:`muted`,children:[`Scan it with the phone, or open this link on it. It works once, for `,Math.max(0,Math.ceil((c.expiresAt-a)/6e4)),` more minute(s). Then set up the passkey on the phone, in its Settings → Remote & devices → Phones.`]}),c.kind===`computer`&&(0,V.jsx)(`p`,{className:`pair-code`,children:(0,V.jsx)(`b`,{children:new URL(c.url).pathname.split(`/`).pop().toUpperCase()})}),(0,V.jsx)(`code`,{className:`pair-link`,children:c.url})]}):(0,V.jsx)(`p`,{className:`device-pair-buttons`,children:[`phone`,`computer`].map(n=>(0,V.jsx)(`button`,{onClick:()=>void e(async()=>{let e=await R.pairDevice(n);o(Date.now()),i({...e,before:t.devices.length})}),children:n===`phone`?`Pair a phone`:`Pair a computer`},n))})]})}var yx=e=>e?new Date(e).toLocaleString():`never`;function bx({run:e}){let t=B(),[n,r]=(0,v.useState)(null),[i,a]=(0,v.useState)(null),[o,s]=(0,v.useState)(``),[c,l]=(0,v.useState)(``),[u,d]=(0,v.useState)(Date.now()),f=()=>R.links().then(e=>{r(e),a(t=>t&&e.links.length>t.before?null:t)},()=>r(null));if((0,v.useEffect)(()=>{f()},[]),(0,v.useEffect)(()=>{if(!i)return;let e=setInterval(()=>{d(Date.now()),f()},2e3);return()=>clearInterval(e)},[i]),!n)return null;let p=i&&i.expiresAt>u?i:null;return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Linked computers`}),n.problem?(0,V.jsx)(`p`,{className:`muted`,children:n.problem}):(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`muted`,children:`Your other computers' Ledungs this one is linked with. Their managers will reach this computer's managers as if they ran here; the link goes end to end through the relay, which can't read it.`}),n.links.length===0&&(0,V.jsx)(`p`,{className:`muted`,children:`No linked computers.`}),n.links.map(t=>(0,V.jsxs)(`div`,{className:`device-row`,children:[(0,V.jsxs)(`span`,{children:[(0,V.jsx)(`b`,{children:t.name}),` `,(0,V.jsxs)(`span`,{className:`muted`,children:[`· `,t.publicName,` · linked `,yx(t.linkedAt),` · last heard from `,yx(t.lastUsedAt)]})]}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e(async()=>{await R.unlink(t.id),await f()}),children:`Unlink`})]},t.id)),p?(0,V.jsxs)(`div`,{className:`pairing`,children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`Paste this in Settings → Linked computers on the other computer. It works once, for `,Math.max(0,Math.ceil((p.expiresAt-u)/6e4)),` more minute(s).`]}),(0,V.jsx)(`code`,{className:`pair-link`,children:p.code}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void navigator.clipboard?.writeText(p.code),children:`Copy`})]}):(0,V.jsx)(`button`,{onClick:()=>void e(async()=>{let e=await R.linkCode();d(Date.now()),a({...e,before:n.links.length})}),children:`Link a computer`}),(0,V.jsxs)(`div`,{className:`link-join`,children:[(0,V.jsx)(`p`,{className:`muted`,children:`Or link with a code made on the other computer:`}),(0,V.jsx)(`input`,{type:`text`,...t,value:o,placeholder:`name.example.com/…`,"aria-label":`Link code from the other computer`,onChange:e=>s(e.target.value)}),(0,V.jsx)(`input`,{type:`text`,...t,value:c,maxLength:40,placeholder:`Its name here, e.g. PC`,"aria-label":`Name for the other computer`,onChange:e=>l(e.target.value)}),(0,V.jsx)(`button`,{disabled:!o.trim(),onClick:()=>void e(async()=>{await R.joinLink(o.trim(),c.trim()),s(``),l(``),await f()}),children:`Link`})]})]})]})}function xx({computers:e,run:t}){return e.length?(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Computers`}),(0,V.jsx)(`p`,{className:`muted`,children:e.length>1?`The tabs at the top of the page, this computer first. A name or colour changed here is this Ledung's; the config's are where they start.`:`Tabs show at the top of the page when the config lists more than one computer. The name is also the remote frame's label.`}),e.map(e=>(0,V.jsx)(Sx,{computer:e,run:t},e.id))]}):null}function Sx({computer:e,run:t}){let n=B(),[r,i]=(0,v.useState)(e.name);(0,v.useEffect)(()=>i(e.name),[e.name]);let a=e.name!==e.config.name||e.colour!==e.config.colour,o=r.trim()!==e.name,s=()=>t(()=>R.editComputer(e.id,{name:r.trim()||null})),c=e.here?`${e.name} (this computer)`:e.name;return(0,V.jsxs)(`div`,{className:`computer-row`,role:`group`,"aria-label":`Computer ${c}`,children:[(0,V.jsxs)(`div`,{className:`computer-name`,children:[(0,V.jsx)(`input`,{type:`text`,...n,value:r,maxLength:24,"aria-label":`Name of ${c}`,onChange:e=>i(e.target.value),onKeyDown:e=>{e.key===`Enter`&&o&&s()}}),o&&(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void s(),children:`Save`}),e.here&&(0,V.jsx)(`span`,{className:`muted`,children:`This computer`}),a&&!o&&(0,V.jsx)(`button`,{className:`small`,title:`Back to ${e.config.name} in ${Et[e.config.colour].label.toLowerCase()}, as the config has it`,onClick:()=>void t(()=>R.editComputer(e.id,{name:null,colour:null})),children:`Use the config's`})]}),(0,V.jsx)(`div`,{className:`swatches`,children:Ot.map(n=>(0,V.jsx)(`button`,{type:`button`,className:`swatch${e.colour===n?` on`:``}`,"aria-pressed":e.colour===n,title:Et[n].label,"aria-label":`${c}: ${Et[n].label}`,onClick:()=>void t(()=>R.editComputer(e.id,{colour:n})),children:(0,V.jsx)(fp,{colour:n,children:`●`})},n))})]})}function Cx(e){let t=/^(\d+)\.(\d+)\.0$/.exec(e);return t?t[2]===`0`?`v${t[1]}`:`v${t[1]}.${t[2]}`:`v${e}`}var wx=new Set,Tx=ft(localStorage),Ex=e=>{Tx=e;for(let e of wx)e()};window.addEventListener(`storage`,e=>{(e.key===`ledung.statusDot`||e.key===null)&&Ex(ft(localStorage))});var Dx=e=>(wx.add(e),()=>{wx.delete(e)}),Ox=()=>Tx;function kx(){return[(0,v.useSyncExternalStore)(Dx,Ox),e=>{pt(un,e),Ex(e)}]}var Ax=new Set,jx=St(localStorage),Mx=e=>{jx=e;for(let e of Ax)e()};window.addEventListener(`storage`,e=>{(e.key===`ledung.compactSidebar`||e.key===null)&&Mx(St(localStorage))});var Nx=e=>(Ax.add(e),()=>{Ax.delete(e)}),Px=()=>jx;function Fx(){return[(0,v.useSyncExternalStore)(Nx,Px),e=>{Ct(un,e),Mx(e)}]}var Ix=new Set,Lx=gt(localStorage),Rx=e=>{Lx=e;for(let e of Ix)e()};window.addEventListener(`storage`,e=>{(e.key===`ledung.archivedLink`||e.key===null)&&Rx(gt(localStorage))});var zx=e=>(Ix.add(e),()=>{Ix.delete(e)}),Bx=()=>Lx;function Vx(){return[(0,v.useSyncExternalStore)(zx,Bx),e=>{_t(un,e),Rx(e)}]}var Hx=`ledung.installDismissed`,Ux=(e,t)=>/Macintosh/.test(e)&&/Safari\//.test(e)&&!/Chrome|Chromium|CriOS|Edg|OPR|Firefox|FxiOS/.test(e)&&t<=1,Wx=(e,t)=>/iPhone|iPad|iPod/.test(e)||/Macintosh/.test(e)&&t>1,Gx=e=>/Chrome|Chromium|Edg\//.test(e);function Kx(e){return e.standalone||e.installed?{kind:`none`}:e.framed?{kind:`none`,reason:`Install this computer's own page, opened in a tab of its own.`}:e.offer?{kind:`button`}:e.refused?{kind:`none`,reason:`Refused for now. Reload the page to be offered it again.`}:Ux(e.userAgent,e.maxTouchPoints)?{kind:`dock`}:Wx(e.userAgent,e.maxTouchPoints)?{kind:`none`,reason:`On an iPhone or iPad, use Share → Add to Home Screen in Safari.`}:e.secure?Gx(e.userAgent)?{kind:`none`,reason:`The browser isn't offering to install this page: it is installed already, or not allowed here. The install icon in the address bar says which.`}:{kind:`none`,reason:`This browser can't install pages as apps; Edge, Chrome and Safari on macOS can.`}:{kind:`none`,reason:`Browsers offer installing only a page at 127.0.0.1 or over HTTPS; this one is plain http.`}}function qx(e){try{return e.getItem(Hx)===`1`}catch{return!1}}function Jx(e){try{e.setItem(Hx,`1`)}catch{}}var Yx=(e,t)=>!t&&e.kind!==`none`,Xx=matchMedia(`(display-mode: standalone)`),Zx=null,Qx=!1,$x=!1,eS=qx(localStorage),tS=new Set,nS=()=>Kx({standalone:Xx.matches||navigator.standalone===!0,installed:Qx,offer:Zx!==null,refused:$x,framed:Vt(),secure:window.isSecureContext,userAgent:navigator.userAgent,maxTouchPoints:navigator.maxTouchPoints??0}),rS={install:nS(),notice:!1},iS=()=>{let e=nS();rS={install:e,notice:Yx(e,eS)};for(let e of tS)e()};rS.notice=Yx(rS.install,eS),window.addEventListener(`beforeinstallprompt`,e=>{e.preventDefault(),Zx=e,$x=!1,iS()}),window.addEventListener(`appinstalled`,()=>{Qx=!0,Zx=null,iS()}),Xx.addEventListener(`change`,iS),window.addEventListener(`storage`,e=>{(e.key===`ledung.installDismissed`||e.key===null)&&(eS=qx(localStorage),iS())});var aS=e=>(tS.add(e),()=>{tS.delete(e)}),oS=()=>rS;async function sS(){let e=Zx;e&&(Zx=null,await e.prompt(),(await e.userChoice).outcome===`accepted`?Qx=!0:$x=!0,iS())}var cS=()=>{Jx(localStorage),eS=!0,iS()};function lS(){return{...(0,v.useSyncExternalStore)(aS,oS),onInstall:sS,onDismiss:cS}}var uS=(0,V.jsxs)(V.Fragment,{children:[`In Safari, choose `,(0,V.jsx)(`b`,{children:`File → Add to Dock`}),`.`]});function dS({app:e,run:t}){return(0,V.jsxs)(`div`,{className:`banner install`,children:[(0,V.jsxs)(`span`,{children:[`Ledung can run as an app, in a window of its own.`,e.install.kind===`dock`&&(0,V.jsxs)(V.Fragment,{children:[` `,uS]})]}),e.install.kind===`button`&&(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void t(e.onInstall),children:`Install as app`}),(0,V.jsx)(`button`,{className:`small`,onClick:e.onDismiss,children:`Not now`})]})}function fS({run:e}){let t=lS(),{install:n}=t;return n.kind===`none`&&!n.reason?null:(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`App`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(`p`,{className:`muted`,children:`Ledung in a window of its own, with its own icon, instead of a browser tab.`}),n.kind===`button`&&(0,V.jsx)(`button`,{className:`primary`,onClick:()=>void e(t.onInstall),children:`Install as app`}),n.kind===`dock`&&(0,V.jsx)(`p`,{children:uS}),n.kind===`none`&&(0,V.jsx)(`p`,{className:`muted`,children:n.reason})]})}function pS(e,t){return!!e&&!t&&e.available&&!e.asked&&e.places.length>0&&!e.places.some(e=>e.present)}function mS(e){let t=e.places.map(e=>e.label);return t.length>1?`${t.slice(0,-1).join(`, `)} and ${t[t.length-1]}`:t[0]??``}function hS(e){return e.kind===`mac`?`Add a Ledung icon to ${mS(e)}?`:`Add a Ledung icon to your ${mS(e)}?`}var gS={desktop:`on your Desktop`,"start-menu":`in the Start menu`,applications:`in Applications`};function _S(e){let t=e.places.map(e=>gS[e.id]??`in ${e.label}`);return`A Ledung icon ${t.length>1?`${t.slice(0,-1).join(`, `)} and ${t[t.length-1]}`:t[0]??``}.`}var vS=`It opens this page, and starts Ledung first if it isn't running.`,yS=null,bS=null,xS=new Set,SS=e=>{yS=e;for(let e of xS)e()};function CS(){return bS??=R.shortcuts().then(SS,()=>SS(null)),bS}var wS=e=>(xS.add(e),()=>{xS.delete(e)});function TS(){return(0,v.useEffect)(()=>void CS(),[]),{view:(0,v.useSyncExternalStore)(wS,()=>yS),act:async e=>SS(await R.shortcutsAct(e))}}function ES({run:e}){let{view:t,act:n}=TS(),[r,i]=(0,v.useState)(!1);if(!t||!pS(t,Vt()))return null;let a=t=>e(async()=>{await n(t),r&&await n(`sign-in-on`)});return(0,V.jsxs)(`div`,{className:`banner install`,children:[(0,V.jsxs)(`span`,{children:[hS(t),` `,vS]}),t.signIn.available&&!t.signIn.on&&(0,V.jsxs)(`label`,{className:`toggle`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r,onChange:e=>i(e.target.checked)}),` `,t.signIn.label]}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void a(`add`),children:`Yes`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void a(`decline`),children:`No`})]})}function DS({run:e}){let{view:t,act:n}=TS();if(!t)return null;let r=t.places.filter(e=>!e.present),i=t.places.filter(e=>e.present);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Shortcuts`}),t.available?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[_S(t),` `,vS,` Ledung then runs in the background, with no window; Stop Ledung below stops it.`]}),(0,V.jsx)(`ul`,{className:`shortcut-places`,children:t.places.map(e=>(0,V.jsxs)(`li`,{children:[(0,V.jsx)(`b`,{children:e.label}),` `,(0,V.jsx)(`span`,{className:`muted`,children:e.present?`added`:`not there`})]},e.id))}),(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[r.length>0&&(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void e(()=>n(`add`)),children:`Add shortcuts`}),i.length>0&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e(()=>n(`remove`)),children:`Remove`})]})]}):(0,V.jsx)(`p`,{className:`muted`,children:t.reason})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Start at sign-in`}),t.signIn.available?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:t.signIn.file??void 0,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:t.signIn.on,onChange:t=>void e(()=>n(t.target.checked?`sign-in-on`:`sign-in-off`))}),` `,t.signIn.label]}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Ledung starts in the background, without opening its page; open it with the icon or the `,(0,V.jsx)(`code`,{children:`ledung`}),` command. Only for you, and no administrator rights are needed.`]})]}):(0,V.jsx)(`p`,{className:`muted`,children:t.signIn.reason})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Log`}),(0,V.jsxs)(`p`,{className:`muted`,children:[t.log.active?`This Ledung runs in the background; what it says goes to`:`Started in the background, Ledung writes what it says to`,` `,(0,V.jsx)(`code`,{children:t.log.file}),t.log.active?`.`:`. This one was started in a terminal or window, so it says it there.`]})]})]})}function OS(){let{view:e}=TS(),[t,n]=(0,v.useState)(`idle`);return!e||Vt()?null:(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Stop Ledung`}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Stops Ledung and its sessions; resume a session after the next start to continue it. Start Ledung again with its icon or the `,(0,V.jsx)(`code`,{children:`ledung`}),` command.`]}),t===`stopped`?(0,V.jsx)(`p`,{children:`Ledung has stopped. This page stays as it was until Ledung runs again.`}):t===`confirming`?(0,V.jsxs)(`span`,{className:`restart-confirm`,children:[(0,V.jsx)(`span`,{className:`muted`,children:`Running sessions stop.`}),(0,V.jsx)(`button`,{className:`small primary`,onClick:async()=>{try{await R.stopLedung(),n(`stopped`)}catch{n(`failed`)}},children:`Stop Ledung`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>n(`idle`),children:`Cancel`})]}):(0,V.jsxs)(`span`,{className:`restart-confirm`,children:[t===`failed`&&(0,V.jsx)(`span`,{className:`restart-problem`,children:`Ledung refused to stop.`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>n(`confirming`),children:`Stop Ledung`})]})]})}function kS(e){return e===`token`?`Signed in with a long-lived token`:e===`login`?`Signed in with /login`:e===`key`?`Signed in with an API key`:e===`other`?`Signed in`:`Not signed in, or not checked yet`}function AS(e){return!e||!e.email&&!e.organization?`not seen yet: shown after its first session starts`:[e.email,e.organization,e.plan].filter(Boolean).join(` · `)+(e.seenAt?` (seen ${Eg(e.seenAt)})`:``)}function jS({text:e}){return(0,V.jsxs)(`div`,{className:`sign-in-command`,children:[(0,V.jsx)(`code`,{className:`remote-record`,children:e}),` `,(0,V.jsx)(Df,{text:e})]})}function MS({command:e}){return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`With a long-lived token: get one with `,(0,V.jsx)(`span`,{className:`mono`,children:`claude setup-token`}),`, then run this in your own terminal on this computer and paste it. It goes straight into Claude Code's sign-in; Ledung never receives it.`]}),(0,V.jsx)(jS,{text:e})]})}function NS(e){let t=B(),[n,r]=(0,v.useState)(``),[i,a]=(0,v.useState)(``),[o,s]=(0,v.useState)(null),c=t=>[...e.projects.filter(e=>e.account===t).map(e=>e.name),...e.choices.chats===t?[`chats`]:[]].join(`, `)||`no project`,l=t=>(0,V.jsxs)(`select`,{value:e.choices[t]??``,onChange:n=>void e.run(()=>R.setAccountChoices({[t]:n.target.value||null})),children:[(0,V.jsx)(`option`,{value:``,children:`default: this computer's own login`}),e.accounts.map(e=>(0,V.jsxs)(`option`,{value:e.name,children:[e.name,e.email?` (${e.email})`:``]},e.name))]});return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Accounts`}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Each project uses one account, for its manager and all its sessions; chats use the one chosen below. Ledung never moves work between accounts. Accounts can also be listed under `,(0,V.jsx)(`span`,{className:`mono`,children:`claudeAccounts`}),` in the config file (see ledung.config.example.json).`]}),e.configFileProblems.map(e=>(0,V.jsx)(`div`,{className:`banner`,children:e},e)),(0,V.jsxs)(`div`,{children:[(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Account`}),(0,V.jsx)(`th`,{children:`Logged in as`}),(0,V.jsx)(`th`,{children:`Used by`}),(0,V.jsx)(`th`,{})]})}),(0,V.jsxs)(`tbody`,{children:[(0,V.jsxs)(`tr`,{children:[(0,V.jsxs)(`td`,{children:[(0,V.jsx)(`strong`,{children:`default`}),(0,V.jsx)(`div`,{className:`muted`,children:`this computer's own Claude Code login`})]}),(0,V.jsxs)(`td`,{children:[AS(e.defaultIdentity),(0,V.jsx)(`div`,{className:`muted`,children:kS(e.defaultIdentity?.signInKind)})]}),(0,V.jsx)(`td`,{children:c(null)}),(0,V.jsx)(`td`,{})]}),e.accounts.map(t=>(0,V.jsxs)(v.Fragment,{children:[(0,V.jsxs)(`tr`,{children:[(0,V.jsxs)(`td`,{children:[(0,V.jsx)(`strong`,{children:t.name}),t.whatItIsFor&&(0,V.jsx)(`div`,{children:t.whatItIsFor}),t.inConfigFile&&(0,V.jsx)(`div`,{className:`muted`,children:`set in the config file: to remove it for good, take it out there too, or it comes back at the next start`}),(0,V.jsxs)(`div`,{className:`muted`,children:[`sign-in folder `,(0,V.jsx)(`span`,{className:`mono`,children:t.configDir})]}),(0,V.jsxs)(`div`,{className:`muted`,children:[`in containers `,(0,V.jsx)(`span`,{className:`mono`,children:t.containerDir??`~/.ledung-accounts/${t.name}`})]})]}),(0,V.jsxs)(`td`,{children:[AS(t),(0,V.jsx)(`div`,{className:`muted`,children:kS(t.signInKind)})]}),(0,V.jsx)(`td`,{children:c(t.name)}),(0,V.jsxs)(`td`,{className:`account-actions`,children:[(0,V.jsx)(`button`,{className:`small`,disabled:e.remote,title:e.remote?`Only on the computer Ledung runs on`:`Show ${t.configDir}`,onClick:()=>void e.run(()=>R.openAccountFolder(t.name)),children:`Open folder`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e.run(()=>R.removeAccount(t.name)),children:`Remove`})]})]}),(0,V.jsx)(`tr`,{children:(0,V.jsx)(`td`,{colSpan:4,children:(0,V.jsxs)(`details`,{children:[(0,V.jsx)(`summary`,{className:`muted`,children:`Sign in, or change how it is signed in`}),t.loginCommand&&(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`With Claude Code's own `,(0,V.jsx)(`span`,{className:`mono`,children:`/login`}),`: run this in a terminal on this computer, then type `,(0,V.jsx)(`span`,{className:`mono`,children:`/login`}),`.`]}),(0,V.jsx)(jS,{text:t.loginCommand})]}),t.tokenCommand&&(0,V.jsx)(MS,{command:t.tokenCommand}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Either one replaces the sign-in that is there. For a project in a container, sign in inside the container with `,(0,V.jsx)(`span`,{className:`mono`,children:`/login`}),`.`]})]})})})]},t.name))]})]}),(0,V.jsxs)(`p`,{children:[(0,V.jsx)(`button`,{className:`small`,onClick:()=>void e.run(()=>R.checkSignIn()),children:`Check again`}),` `,(0,V.jsx)(`span`,{className:`muted`,children:`after signing in from a terminal, to see it here`})]}),(0,V.jsxs)(`div`,{className:`form`,children:[(0,V.jsxs)(`label`,{children:[`Account for chats `,(0,V.jsx)(`span`,{className:`muted`,children:`(new chats run on it; a running chat keeps its account until it restarts)`}),l(`chats`)]}),(0,V.jsxs)(`label`,{children:[`Account for new projects `,(0,V.jsx)(`span`,{className:`muted`,children:`(chosen for you in Add project)`}),l(`newProjects`)]})]}),(0,V.jsx)(`h4`,{children:`Add an account`}),(0,V.jsxs)(`div`,{className:`form`,children:[(0,V.jsxs)(`label`,{children:[`Name `,(0,V.jsx)(`span`,{className:`muted`,children:`(e.g. personal, work)`}),(0,V.jsx)(`input`,{...t,value:n,onChange:e=>r(e.target.value),maxLength:32})]}),(0,V.jsxs)(`label`,{children:[`Sign-in folder in containers `,(0,V.jsx)(`span`,{className:`muted`,children:`(optional; default ~/.ledung-accounts/<name> in the container user's home, or a mounted folder so the sign-in survives a rebuild)`}),(0,V.jsx)(`input`,{...t,value:i,onChange:e=>a(e.target.value),className:`mono`,placeholder:`~/.ledung-accounts/name`})]}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Ledung makes a folder for this account's Claude Code sign-in, and only that: conversations, memory, skills and settings stay the same for every account, so moving a project to another account changes only whose plan and limits it uses. After adding it, sign in once with Claude Code's own `,(0,V.jsx)(`span`,{className:`mono`,children:`/login`}),` as shown (for a container project, inside the container), or put in a long-lived token with the command shown. Ledung never sees or keeps a sign-in token.`]}),(0,V.jsx)(`button`,{className:`primary`,disabled:!n.trim(),onClick:()=>void e.run(async()=>{s(await R.addAccount({name:n.trim(),...i.trim()?{containerDir:i.trim()}:{}})),a(``),r(``)}),children:`Add account`})]}),o&&(0,V.jsxs)(`div`,{className:`banner`,children:[`Added `,(0,V.jsx)(`strong`,{children:o.name}),`. Choose it in a project's settings (⚙ next to the project), or above for chats and new projects.`,` `,`Now sign in once. With Claude Code's own `,(0,V.jsx)(`span`,{className:`mono`,children:`/login`}),`: run this in a terminal on this computer, then type `,(0,V.jsx)(`span`,{className:`mono`,children:`/login`}),` and sign in with this account.`,o.loginCommand&&(0,V.jsx)(jS,{text:o.loginCommand}),`For a container project, the same inside the container:`,(0,V.jsx)(`pre`,{className:`mono`,children:`docker exec -it <container> sh -c 'CLAUDE_SECURESTORAGE_CONFIG_DIR=${(o.containerDir??`~/.ledung-accounts/${o.name}`).replace(/^~\//,`$HOME/`)} exec claude'`}),o.tokenCommand&&(0,V.jsx)(MS,{command:o.tokenCommand})]})]})]})}var PS=4e3,FS=[`Ctrl`,`Alt`,`Shift`,`Cmd`],IS=/^(?:(?:Ctrl|Alt|Shift|Cmd)\+)+(?:[A-Z]|[0-9])$/;function LS(e){let t=/^(?:Key([A-Z])|Digit([0-9]))$/.exec(e.code);if(!t)return null;let n=[e.ctrlKey&&`Ctrl`,e.altKey&&`Alt`,e.shiftKey&&`Shift`,e.metaKey&&`Cmd`].filter(Boolean);return n.length?`${n.join(`+`)}+${t[1]??t[2]}`:null}function RS(e){if(!IS.test(e))return!1;let t=e.split(`+`).slice(0,-1);return t.every((e,n)=>n===0||FS.indexOf(e)>FS.indexOf(t[n-1]))}function zS(e,t){if(!t)return e;let n={Ctrl:`⌃`,Alt:`⌥`,Shift:`⇧`,Cmd:`⌘`},r=e.split(`+`);return r.slice(0,-1).map(e=>n[e]??e).join(``)+r[r.length-1]}function BS(e,t,n){if(!RS(e))return{refused:`A keybind is Ctrl, Alt or Cmd with a letter or a digit.`};let r=new Set(e.split(`+`).slice(0,-1)),i=e.split(`+`).pop(),a=/^[0-9]$/.test(i),o=t.find(t=>t.key===e&&t.id!==n);return o?{refused:`“${o.name}” has this keybind.`}:!r.has(`Ctrl`)&&!r.has(`Alt`)&&!r.has(`Cmd`)?{refused:`Shift alone types; add Ctrl or Alt.`}:r.has(`Cmd`)?{refused:`Cmd keys belong to the browser and the Mac, and Windows has none.`}:r.has(`Ctrl`)&&r.has(`Alt`)?{refused:`Ctrl+Alt is AltGr on Windows, which types @, { and [ on many keyboards.`}:e===`Ctrl+O`?{refused:`Ctrl+O shows and hides tool calls in Ledung.`}:r.has(`Ctrl`)&&!a?{refused:`${e} is the browser's or the message box's (new tab, copy, find, developer tools…).`}:r.has(`Ctrl`)&&!r.has(`Shift`)?{warning:`On Windows and Linux ${e} switches browser tabs: there it does nothing.`}:r.has(`Alt`)&&!r.has(`Shift`)&&[`D`,`E`,`F`].includes(i)?{refused:`${e} opens the browser's menu or address bar on Windows.`}:r.has(`Alt`)?{warning:`On a Mac ⌥ types a character with this key (⌥2 is @ on a Swedish keyboard): the keybind takes it away there.${a&&!r.has(`Shift`)?` On Linux Alt+1–9 switch browser tabs.`:``}`}:null}function VS(e,t,n=3){let r=[];for(let i of`123456789`){let a=`Ctrl+Shift+${i}`;if(BS(a,e,t)||r.push(a),r.length===n)break}return r}function HS(e,t){return e.filter(e=>e.project===null||e.project===t)}var US=[`issue`,`branch`,`pr`,`project`,`session`];function WS(e,t){let n=t.branch?/(?:^|[/_-])(\d+)(?=$|[/_-])/.exec(t.branch)?.[1]:void 0,r={issue:t.tickets[0]?.id??(n?`#${n}`:void 0),branch:t.branch??void 0,pr:t.pr?`#${t.pr.number}`:void 0,project:S(t.project),session:t.title},i=[];return{text:e.replace(/\{(issue|branch|pr|project|session)\}/g,(e,t)=>{let n=r[t];return n===void 0?(i.includes(t)||i.push(t),e):n}),missing:i}}function GS(e,t,n){return!(n?!e.send:e.send)||t.missing.length||t.text.trimStart().startsWith(`!`)?`insert`:`send`}function KS(e,t,n){let r=e.slice(),[i]=r.splice(t,1);return r.splice(n,0,i),r}function qS(e){if(e.length>50)return`At most 50 macros.`;let t=new Set,n=new Map;for(let r of e){if(!/^[a-z0-9-]{1,40}$/.test(r.id)||t.has(r.id))return`A macro has no id of its own.`;t.add(r.id);let e=r.name.trim();if(!e||e.length>40)return`A macro's name is 1 to 40 characters.`;if(!r.text.trim()||r.text.length>4e3)return`“${e}”: the text is 1 to ${PS} characters.`;if(!r.chip&&!r.key)return`“${e}” has neither a chip nor a keybind, so nothing could use it.`;if(r.key!==null){let t=BS(r.key,[],null);if(t&&`refused`in t)return`“${e}”: ${t.refused}`;let i=n.get(r.key);if(i)return`“${e}” and “${i}” have the same keybind.`;n.set(r.key,e)}}return null}var JS=()=>typeof navigator<`u`&&/Mac|iPhone|iPad/.test(navigator.platform||navigator.userAgent);function YS(e,t){let n=e.send?`Sends`:`Puts in the message box`,r=e.key?` · ${zS(e.key,t)}`:``;return`${n}: ${e.text}${r}\nShift+click: ${e.send?`put it in the message box`:`send it`}`}function XS(e){let t=e.macros.filter(e=>e.chip),n=e.macros.filter(e=>!e.chip),r=(0,v.useRef)(null),i=(0,v.useRef)(null),[a,o]=(0,v.useState)(t.length),[s,c]=(0,v.useState)(!1),l=JS();if((0,v.useLayoutEffect)(()=>{let e=r.current;if(!e)return;let t=()=>{let t=[...e.children],n=t[0]?.offsetTop??0;o(t.filter(e=>e.offsetTop===n).length)};t();let n=new ResizeObserver(t);return n.observe(e),()=>n.disconnect()},[t.map(e=>e.id+e.name).join(`|`)]),(0,v.useEffect)(()=>{if(!s)return;let e=e=>{(e instanceof KeyboardEvent?e.key===`Escape`:!i.current?.contains(e.target))&&c(!1)};return document.addEventListener(`pointerdown`,e),document.addEventListener(`keydown`,e),()=>{document.removeEventListener(`pointerdown`,e),document.removeEventListener(`keydown`,e)}},[s]),!e.macros.length)return null;let u=[...t.slice(a),...n],d=(t,n)=>{c(!1),e.onUse(t,n)};return(0,V.jsxs)(`span`,{className:`macro-bar`,ref:i,children:[(0,V.jsx)(`span`,{className:`macro-chips`,ref:r,children:t.map((e,t)=>(0,V.jsxs)(`button`,{className:`board-chip macro-chip`,title:YS(e,l),tabIndex:t<a?0:-1,"aria-hidden":t<a?void 0:!0,onClick:t=>d(e,t.shiftKey),children:[e.name,e.send&&(0,V.jsx)(`span`,{className:`macro-send`,"aria-label":`sends`,children:` ↵`})]},e.id))}),(0,V.jsx)(`button`,{className:`board-chip macro-chip macro-more${s?` on`:``}`,"aria-expanded":s,"aria-haspopup":`menu`,title:u.length?`${u.length} more macro${u.length===1?``:`s`}`:`Edit macros`,onClick:()=>c(e=>!e),children:u.length?`+${u.length}`:`+`}),s&&(0,V.jsxs)(`div`,{className:`macro-menu`,role:`menu`,children:[u.map(e=>(0,V.jsxs)(`button`,{role:`menuitem`,title:YS(e,l),onClick:t=>d(e,t.shiftKey),children:[(0,V.jsxs)(`span`,{children:[e.name,e.send&&(0,V.jsx)(`span`,{className:`macro-send`,children:` ↵`})]}),e.key?(0,V.jsx)(`kbd`,{children:zS(e.key,l)}):(0,V.jsx)(`span`,{})]},e.id)),u.length>0&&(0,V.jsx)(`hr`,{}),(0,V.jsx)(`button`,{role:`menuitem`,className:`muted`,onClick:()=>{c(!1),e.onEdit()},children:`Edit macros…`})]})]})}var ZS=()=>`m-${Date.now().toString(36)}-${Math.random().toString(36).slice(2,7)}`,QS=(e,t)=>e!==null&&e!==`~chats`&&!t.some(t=>t.name===e),$S=(e,t)=>e===null?`Global`:`${S(e)}${QS(e,t)?` (removed)`:``}`;function eC(e){let[t,n]=(0,v.useState)(null),[r,i]=(0,v.useState)(null),a=JS(),o=t=>e.run(()=>R.setMacros(t)),s=t&&e.macros.some(e=>e.id===t.id)?t.id:null;return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`div`,{className:`settings-h`,children:(0,V.jsx)(`h3`,{children:`Macros`})}),(0,V.jsx)(`p`,{className:`muted`,children:`Text you send often, as a chip in a session's info bar, a keybind, or both. Kept by Ledung, so your phone and other browsers have them too.`}),e.macros.length>0&&(0,V.jsx)(`ul`,{className:`macro-list`,children:e.macros.map((t,c)=>(0,V.jsxs)(`li`,{className:`${t.id===s?`on`:``}${r===c?` dragged`:``}`,draggable:!0,onDragStart:()=>i(c),onDragEnd:()=>i(null),onDragOver:e=>e.preventDefault(),onDrop:t=>{t.preventDefault(),r!==null&&r!==c&&o(KS(e.macros,r,c)),i(null)},children:[t.chip?(0,V.jsxs)(`span`,{className:`board-chip macro-chip static`,children:[t.name,t.send&&(0,V.jsx)(`span`,{className:`macro-send`,children:` ↵`})]}):(0,V.jsxs)(`span`,{className:`macro-keyonly`,title:`No chip: this one is on its keybind only`,children:[t.name,t.send&&(0,V.jsx)(`span`,{className:`macro-send`,children:` ↵`}),` `,(0,V.jsx)(`span`,{className:`muted`,children:`· keybind only`})]}),(0,V.jsx)(`span`,{className:`mono macro-text`,title:t.text,children:t.text}),(0,V.jsx)(`span`,{className:`muted macro-what`,children:t.send?`Sends`:`Inserts`}),t.key?(0,V.jsx)(`kbd`,{children:zS(t.key,a)}):(0,V.jsx)(`span`,{className:`muted macro-nokey`,children:`no key`}),(0,V.jsx)(`span`,{className:`chip macro-scope`,title:$S(t.project,e.projects),children:$S(t.project,e.projects)}),(0,V.jsx)(`span`,{className:`macro-move`,title:`Drag to reorder`,"aria-hidden":!0,children:`⋮⋮`}),(0,V.jsxs)(`span`,{className:`macro-row-buttons`,children:[c>0&&(0,V.jsx)(`button`,{className:`small macro-up`,title:`Move up`,"aria-label":`Move ${t.name} up`,onClick:()=>void o(KS(e.macros,c,c-1)),children:`↑`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>n({...t}),children:`Edit`})]})]},t.id))}),t?(0,V.jsx)(tC,{draft:t,macros:e.macros,projects:e.projects,mac:a,isNew:!s,onCancel:()=>n(null),onSave:async t=>{let r=s?e.macros.map(e=>e.id===t.id?t:e):[...e.macros,t];await o(r),n(null)},onDelete:s?async()=>{await o(e.macros.filter(e=>e.id!==t.id)),n(null)}:void 0},t.id):(0,V.jsx)(`button`,{className:`primary`,onClick:()=>n({id:ZS(),name:``,text:``,send:!1,key:null,chip:!0,project:null}),children:`Add macro`})]})}function tC(e){let[t,n]=(0,v.useState)(e.draft),[r,i]=(0,v.useState)(e.draft.key!==null),[a,o]=(0,v.useState)(!1),s=B(),c=e=>n(t=>({...t,...e})),l=r?t.key:null,u=l?BS(l,e.macros,t.id):null,d={...t,key:l},f=qS([d]),p=VS(e.macros,t.id),m=!t.name.trim()||!t.text.trim()||r&&!t.key||!!u&&`refused`in u||!!f;return(0,V.jsxs)(`div`,{className:`form macro-form`,children:[(0,V.jsx)(`h4`,{children:e.isNew?`New macro`:`Edit “${e.draft.name}”`}),(0,V.jsxs)(`label`,{children:[`Name`,(0,V.jsx)(`input`,{...s,value:t.name,maxLength:40,placeholder:`Run checks`,onChange:e=>c({name:e.target.value})})]}),(0,V.jsxs)(`label`,{children:[`Text`,(0,V.jsx)(`textarea`,{...s,rows:3,value:t.text,placeholder:`Run the checks and tell me what fails.`,onChange:e=>c({text:e.target.value})}),(0,V.jsxs)(`span`,{className:`muted macro-hint`,children:[`Placeholders: `,US.map(e=>(0,V.jsxs)(`code`,{children:[`{${e}}`,` `]},e)),`filled from the session. One it has no value for is not sent: the text goes into the message box instead.`]})]}),(0,V.jsxs)(`div`,{className:`field`,children:[(0,V.jsx)(`span`,{children:`When used`}),(0,V.jsxs)(`span`,{className:`segmented macro-seg`,children:[(0,V.jsx)(`button`,{className:`small${t.send?``:` on`}`,"aria-pressed":!t.send,onClick:()=>c({send:!1}),children:`Put it in the message box`}),(0,V.jsx)(`button`,{className:`small${t.send?` on`:``}`,"aria-pressed":t.send,onClick:()=>c({send:!0}),children:`Send it at once`})]}),(0,V.jsx)(`span`,{className:`muted macro-hint`,children:`Shift+click a chip for the other one. A text starting with ! always goes into the box.`})]}),(0,V.jsxs)(`label`,{children:[`Where`,(0,V.jsxs)(`select`,{value:t.project??``,onChange:e=>c({project:e.target.value||null}),children:[(0,V.jsx)(`option`,{value:``,children:`Global (every project)`}),e.projects.map(e=>(0,V.jsx)(`option`,{value:e.name,children:e.name},e.name)),QS(e.draft.project,e.projects)&&(0,V.jsx)(`option`,{value:e.draft.project,children:$S(e.draft.project,e.projects)}),(0,V.jsx)(`option`,{value:x,children:`Chats`})]})]}),(0,V.jsxs)(`label`,{className:`toggle macro-switch`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:t.chip,onChange:e=>c({chip:e.target.checked})}),` Show as a chip in the info bar`]}),(0,V.jsxs)(`label`,{className:`toggle macro-switch`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r,onChange:e=>{i(e.target.checked),e.target.checked&&!t.key&&c({key:p[0]??null})}}),` Keybind`]}),r&&(0,V.jsxs)(`div`,{className:`macro-sub`,children:[(0,V.jsxs)(`span`,{className:`macro-keyrow`,children:[(0,V.jsx)(`input`,{...s,className:`mono macro-keyin${u&&`refused`in u?` bad`:``}`,readOnly:!0,"aria-label":`Keybind`,value:a?`Press the keys…`:t.key?zS(t.key,e.mac):``,onFocus:()=>o(!0),onBlur:()=>o(!1),onKeyDown:e=>{if(e.key===`Tab`||e.key===`Escape`)return;e.preventDefault();let t=LS(e.nativeEvent);t&&(c({key:t}),e.target.blur())}}),(0,V.jsx)(`span`,{className:`muted macro-hint`,children:a?`Ctrl, Alt or Cmd with a letter or a digit`:`Click the box, then press the keys.`})]}),u&&`refused`in u&&(0,V.jsx)(`span`,{className:`macro-conflict`,role:`alert`,children:u.refused}),u&&`warning`in u&&(0,V.jsx)(`span`,{className:`macro-warning`,children:u.warning}),u&&p.length>0&&(0,V.jsxs)(`span`,{className:`macro-hint`,children:[`Free: `,p.map(t=>(0,V.jsx)(`button`,{className:`link macro-free`,onClick:()=>c({key:t}),children:(0,V.jsx)(`kbd`,{children:zS(t,e.mac)})},t))]}),!u&&(0,V.jsx)(`span`,{className:`muted macro-hint`,children:`Works in the message box too. A phone has no keys: there it is in the info bar's + menu.`})]}),!t.chip&&!r&&(0,V.jsx)(`span`,{className:`macro-conflict`,children:`With neither a chip nor a keybind nothing could use it.`}),(0,V.jsxs)(`div`,{className:`macro-keyrow`,children:[(0,V.jsx)(`button`,{className:`primary`,disabled:m,onClick:()=>void e.onSave(d),children:`Save`}),(0,V.jsx)(`button`,{onClick:e.onCancel,children:`Cancel`}),e.onDelete&&(0,V.jsx)(`button`,{className:`deny macro-delete`,onClick:()=>void e.onDelete(),children:`Delete`})]})]})}function nC(e){let t=Bp(im),n=xp(e.view,t),r={update:Mp(e.update.view),remote:Ap(e.remote),notifications:e.notify.possible&&!e.notify.on&&!Vt()?`off`:``};return(0,V.jsx)(em,{groups:gp,current:n,words:r,narrow:t,onOpen:t=>e.onOpen(t===null?`settings`:vp(t)),children:n!==null&&(0,V.jsx)(rC,{group:n,...e})})}function rC(e){switch(e.group){case`update`:{let t=jp(e.update.view);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Update Ledung`}),t.update&&(0,V.jsx)(`p`,{className:`muted`,children:t.update}),(0,V.jsx)(hC,{update:e.update})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Restart Ledung`}),(0,V.jsx)(`p`,{className:`muted`,children:t.restart}),!!e.config?.restartFor.length&&(0,V.jsx)(`p`,{className:`config-restart`,children:aC(e.config)}),e.canRestart?(0,V.jsx)(Qp,{hellos:e.hellos}):(0,V.jsx)(`span`,{className:`muted`,title:`This Ledung was started by an older launcher. Restart it once from its console window (Ctrl+C, then Ledung.cmd).`,children:`Restart: from console`})]}),(0,V.jsx)(OS,{}),(0,V.jsx)(DS,{run:e.run})]})}case`claude`:return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(NS,{accounts:e.accounts,choices:e.accountChoices,defaultIdentity:e.defaultIdentity,configFileProblems:e.accountProblems,projects:e.projects,run:e.run,remote:e.throughPublicName}),(0,V.jsx)(jy,{accounts:e.accounts,usageStops:e.usageStops,run:e.run}),(0,V.jsx)(kb,{sessions:e.sessions}),(0,V.jsx)(Ff,{accounts:e.accounts,run:e.run})]});case`sessions`:return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(dp,{run:e.run}),(0,V.jsx)(bb,{})]});case`macros`:return(0,V.jsx)(eC,{macros:e.macros,projects:e.projects,run:e.run});case`remote`:return(0,V.jsx)(iC,{...e});case`look`:return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Appearance`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(fC,{})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Typing`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(cC,{})]}),(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Sidebar`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(lC,{}),(0,V.jsx)(uC,{}),(0,V.jsx)(dC,{})]}),(0,V.jsx)(fS,{run:e.run})]});case`notifications`:return(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Notifications`}),(0,V.jsx)($p,{kind:`browser`})]}),(0,V.jsx)(sC,{notify:e.notify,linked:e.computers.some(e=>e.linked)})]});case`config`:return e.config?(0,V.jsx)(oC,{config:e.config}):(0,V.jsx)(`p`,{className:`muted`,children:`…`});default:return(0,V.jsx)(yC,{source:e.source,update:e.update})}}function iC(e){let[t,n]=(0,v.useState)(void 0),[r,i]=(0,v.useState)(null);(0,v.useEffect)(()=>{R.relayAdmin().then(n,()=>n(null))},[]);let a=kp({remote:e.remote,relaySetUp:t?Zv(t):null,boardConfigured:!!e.board?.configured}),o=t&&(0,V.jsx)(Xv,{view:t,onView:n,run:e.run,newComputers:e.newComputers}),s=e.projects[0]?.name,c=[{id:`remote`,name:`Remote access`,state:a.remote,why:`Reach this Ledung from your phone, anywhere, through a relay.`,form:(0,V.jsx)(_C,{remote:e.remote}),primary:!0},{id:`phones`,name:`Phones`,state:a.phones,why:``},{id:`linked`,name:`Linked computers`,state:a.linked,why:``},{id:`relay`,name:`Run a relay`,state:a.relay,why:`Only if you host a relay for other people.`,form:o},{id:`board`,name:`Message board`,state:a.board,why:s?`Off in every project; turn it on in a project's tab.`:`Off; each project turns it on in its own tab.`,go:s?{label:`Projects ›`,view:Tp(s,`board`)}:void 0}].filter(e=>e.state===`off`||e.state===`needs`);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(xx,{computers:e.computers,run:e.run}),a.remote===`on`&&(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Remote access`}),(0,V.jsx)(_C,{remote:e.remote})]}),a.phones===`on`&&(0,V.jsx)(px,{run:e.run,linked:e.computers.some(e=>e.linked)},e.remote?.publicName??`none`),a.linked===`on`&&(0,V.jsx)(bx,{run:e.run},`linked-${e.remote?.publicName??`none`}-${e.remote?.tls??``}`),a.relay===`on`&&(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Relay`}),o]}),a.board===`on`&&(0,V.jsx)(Tn,{board:e.board}),c.length>0&&(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`Not set up`}),c.map(t=>r===t.id&&t.state===`off`&&t.form?(0,V.jsxs)(`div`,{className:`offline-open`,role:`group`,"aria-label":t.name,children:[(0,V.jsxs)(`h4`,{children:[(0,V.jsx)(`span`,{children:t.name}),(0,V.jsx)(`button`,{className:`small`,"aria-label":`Close ${t.name}`,title:`Close`,onClick:()=>i(null),children:`✕`})]}),t.form]},t.id):(0,V.jsxs)(`div`,{className:`offline${t.state===`needs`?` needs`:``}`,children:[(0,V.jsx)(`span`,{className:`offline-name`,children:t.name}),(0,V.jsx)(`span`,{className:`offline-why`,children:t.state===`needs`?`Needs remote access first.`:t.why}),t.state===`off`&&t.form&&(0,V.jsx)(`button`,{className:`small${t.primary?` primary`:``}`,onClick:()=>i(t.id),children:`Set up ›`}),t.state===`off`&&t.go&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>e.onOpen(t.go.view),children:t.go.label})]},t.id))]})]})}function aC(e){return`Restart Ledung to apply: ${e.restartFor.join(`, `)}`}function oC(e){let t=e.config,n=new Date(t.readAt).toLocaleString(void 0,{dateStyle:`medium`,timeStyle:`short`});return(0,V.jsxs)(`section`,{children:[(0,V.jsxs)(`div`,{className:`settings-h`,children:[(0,V.jsx)(`h3`,{children:`Config file`}),(0,V.jsx)($p,{kind:`config`})]}),(0,V.jsxs)(`p`,{className:`muted`,children:[`Ledung reads `,(0,V.jsx)(`code`,{children:t.file}),` again whenever it changes. Most settings apply at once, to new and resumed sessions; running sessions keep what they started with. A few, such as the port and the network, need Restart Ledung.`]}),(0,V.jsx)(`p`,{children:t.reloaded?`Last reloaded ${n}.`:`Read at start, ${n}; not changed since.`}),t.problem&&(0,V.jsxs)(`p`,{className:`config-problem`,role:`alert`,children:[`The last change was not applied, the settings in use stay: `,t.problem]}),!!t.restartFor.length&&(0,V.jsx)(`p`,{className:`config-restart`,children:aC(t)})]})}function sC({notify:e,linked:t}){return Vt()?(0,V.jsx)(gx,{linked:t}):e.possible?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`A browser notification when something new needs your answer and this page is in the background`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e.on,onChange:t=>void e.set(t.target.checked)}),` Send notifications when an agent is waiting for you`]}),(0,V.jsx)(`p`,{className:`muted`,children:`While a Ledung page is open in this browser.`}),e.denied&&(0,V.jsx)(`p`,{className:`muted`,children:`The browser blocks notifications for this page. Allow them in the browser's site settings (the icon left of the address), then switch this on again.`})]}):(0,V.jsx)(`p`,{className:`muted`,children:`Notifications work when this page is opened on this computer at 127.0.0.1.`})}function cC(){let[e,t]=_n();return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`Off: the browser doesn't correct words as you type. Spell checking and automatic capitals are left to the browser either way`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e,onChange:e=>t(e.target.checked)}),` Autocorrect`]}),(0,V.jsx)(`p`,{className:`muted`,children:`Off: words stay as you type them in the message box, answers and every other text field. Spell checking and capitals are the browser's own either way.`})]})}function lC(){let[e,t]=kx();return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`The coloured dot left of each session in the sidebar; the ship shows much the same`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e,onChange:e=>t(e.target.checked)}),` Status dot`]}),(0,V.jsx)(`p`,{className:`muted`,children:`Off: no dot on the session rows; hover a row for its status, and an ended session's name is faded.`})]})}function uC(){let[e,t]=Vx();return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`toggle`,title:`The Archived (N) entry under each project in the sidebar, which opens its archived sessions`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e,onChange:e=>t(e.target.checked)}),` Show "Archived" in the sidebar`]}),(0,V.jsx)(`p`,{className:`muted`,children:`Off: no Archived entry under the projects; switch it back on to open their archived sessions.`})]})}function dC(){let[e,t]=Fx(),n=bt.find(t=>t.step===e).label;return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`label`,{className:`compact-slider`,title:`Less padding and fewer rows on each session in the sidebar; the ship always stays`,children:[(0,V.jsx)(`span`,{children:`Compact sidebar`}),(0,V.jsx)(vb,{step:e,labels:bt.map(e=>e.label),onPick:e=>t(e),children:(0,V.jsx)(`input`,{type:`range`,min:1,max:bt.length,step:1,value:e,list:`compact-steps`,"aria-valuetext":n,onChange:e=>t(Number(e.target.value))})})]}),(0,V.jsx)(`datalist`,{id:`compact-steps`,children:bt.map(e=>(0,V.jsx)(`option`,{value:e.step,label:e.label},e.step))}),(0,V.jsx)(`p`,{className:`muted`,children:`Each step takes more off the session cards: tighter padding and no date and time, then only the name, the ship and the badge, with a small "+" for a new session. Hover a card for what it no longer shows.`})]})}function fC(){let[e,t]=(0,v.useState)(()=>ot(localStorage)),n=e=>{t(e),st(un,e),ct(document.documentElement,e)};return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`div`,{className:`seg-control`,role:`group`,"aria-label":`Colour scheme`,children:rt.map(t=>(0,V.jsx)(`button`,{className:e===t.id?`on`:``,"aria-pressed":e===t.id,onClick:()=>n(t.id),children:t.label},t.id))}),(0,V.jsx)(`p`,{className:`muted`,children:`System follows the computer's light or dark setting.`})]})}var pC=e=>e?e.slice(0,7):`unknown commit`,mC={waiting:`○`,running:`…`,done:`✓`,failed:`✗`};function hC({update:e}){let{view:t,error:n,act:r}=e,[i,a]=(0,v.useState)(!1);if(n)return(0,V.jsx)(`p`,{className:`restart-problem`,children:n});if(!t)return(0,V.jsx)(`p`,{className:`muted`,children:`…`});if(t.npm)return(0,V.jsx)(gC,{update:e});if(!t.available)return(0,V.jsx)(`p`,{className:`muted`,children:t.reason});let o=t.checking||t.updating||t.restarting,s=t.check,c=!!s&&!s.upToDate&&!t.updating&&!t.restarting;return(0,V.jsxs)(`div`,{className:`update-panel`,children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`Running `,t.running?.commit?(0,V.jsx)(`code`,{children:pC(t.running.commit)}):`an unknown commit (its source is not a git clone)`,`, built from `,(0,V.jsx)(`code`,{children:t.running?.source}),`.`]}),(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[(0,V.jsx)(`button`,{className:`small`,disabled:o,onClick:()=>{a(!1),r(R.updateCheck)},children:t.checking?`Checking…`:`Check for updates`}),s&&!t.checking&&(s.upToDate?(0,V.jsxs)(`span`,{className:`update-ok`,children:[`Up to date (`,pC(s.latest),`)`]}):(0,V.jsxs)(`span`,{children:[s.behind,` new change`,s.behind===1?``:`s`,` on main (`,pC(s.latest),`)`,s.commitKnown?``:`, counted from the source folder`]}))]}),t.checkError&&(0,V.jsx)(`pre`,{className:`update-output restart-problem`,children:t.checkError}),s&&!s.upToDate&&s.changes.length>0&&(0,V.jsx)(`ul`,{className:`update-changes`,children:s.changes.map((e,t)=>(0,V.jsx)(`li`,{children:e},t))}),c&&!t.canRestart&&(0,V.jsx)(`p`,{className:`muted`,children:`Updating ends in a restart, and this Ledung was started by an older launcher. Restart it once from its console window first.`}),c&&t.canRestart&&(i?(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[(0,V.jsx)(`span`,{className:`muted`,children:`Pull main, npm install, npm run release, then restart. Sessions keep running.`}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>{a(!1),r(R.update)},children:`Update now`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>a(!1),children:`Cancel`})]}):(0,V.jsx)(`div`,{className:`restart-confirm`,children:(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>a(!0),children:`Update Ledung`})})),t.steps.length>0&&(0,V.jsx)(`ol`,{className:`update-steps`,children:t.steps.map(e=>(0,V.jsxs)(`li`,{className:`update-step ${e.state}`,children:[(0,V.jsx)(`span`,{className:`update-mark`,children:mC[e.state]}),` `,e.label,e.state===`failed`&&e.output&&(0,V.jsx)(`pre`,{className:`update-output`,children:e.output})]},e.label))}),t.refused&&(0,V.jsx)(`p`,{className:`restart-problem`,children:t.refused}),t.restarting&&(0,V.jsx)(`p`,{className:`muted`,children:`The new release is built. Restarting into it…`})]})}function gC({update:e}){let{view:t,act:n}=e,[r,i]=(0,v.useState)(!1);if(!t?.npm)return null;let a=t.checking||t.updating||t.restarting,o=t.npmCheck&&t.npmCheck.channel===(t.channel??`public`)?t.npmCheck:null,s=!!o?.offered&&!o.upToDate&&!t.updating&&!t.restarting,c=bC[t.channel??`public`];return(0,V.jsxs)(`div`,{className:`update-panel`,children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`Running Ledung `,(0,V.jsx)(`code`,{children:Cx(t.npm.version)}),`, installed from npm, on the `,c,` channel (Settings → About).`]}),(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[(0,V.jsx)(`button`,{className:`small`,disabled:a,onClick:()=>{i(!1),n(R.updateCheck)},children:t.checking?`Checking…`:`Check for updates`}),o&&!t.checking&&(o.offered?o.upToDate?(0,V.jsxs)(`span`,{className:`update-ok`,children:[`Up to date (`,c,`: `,Cx(o.offered),`)`]}):(0,V.jsxs)(`span`,{children:[Cx(o.offered),` is out on `,c]}):(0,V.jsxs)(`span`,{children:[`npm has no `,c,` version yet`]}))]}),t.checkError&&(0,V.jsx)(`pre`,{className:`update-output restart-problem`,children:t.checkError}),s&&!t.canRestart&&(0,V.jsx)(`p`,{className:`muted`,children:t.reason}),s&&t.canRestart&&(r?(0,V.jsxs)(`div`,{className:`restart-confirm`,children:[(0,V.jsxs)(`span`,{className:`muted`,children:[`npm install -g ledung@`,o.offered,`, then restart. Sessions keep running.`]}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>{i(!1),n(R.update)},children:`Update now`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>i(!1),children:`Cancel`})]}):(0,V.jsx)(`div`,{className:`restart-confirm`,children:(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>i(!0),children:`Update Ledung`})})),t.steps.length>0&&(0,V.jsx)(`ol`,{className:`update-steps`,children:t.steps.map((e,t)=>(0,V.jsxs)(`li`,{className:`update-step ${e.state}`,children:[(0,V.jsx)(`span`,{className:`update-mark`,children:mC[e.state]}),` `,e.label,e.state===`failed`&&e.output&&(0,V.jsx)(`pre`,{className:`update-output`,children:e.output})]},t))}),t.refused&&(0,V.jsx)(`p`,{className:`restart-problem`,children:t.refused}),t.restarting&&(0,V.jsx)(`p`,{className:`muted`,children:`The new version is installed. Restarting into it…`}),!t.steps.length&&!s&&(0,V.jsx)(`p`,{className:`muted`,children:t.reason})]})}function _C(e){let t=Ab(e.remote);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`p`,{className:`remote-state ${e.remote?.state??`off`}`,children:t.label}),t.detail&&(0,V.jsx)(`p`,{className:`muted`,children:t.detail}),e.remote?.tls&&(0,V.jsx)(`p`,{className:`remote-tls`,children:e.remote.tls}),e.remote?.certificate&&(0,V.jsx)(vC,{cert:e.remote.certificate}),(0,V.jsx)(Yv,{remote:e.remote})]})}function vC({cert:e}){let t=Nb(e,Date.now()),[n,r]=(0,v.useState)(!1),[i,a]=(0,v.useState)(null);return(0,V.jsxs)(`div`,{className:`remote-certificate`,children:[(0,V.jsx)(`p`,{className:t.warn?`remote-tls`:`remote-state connected`,children:t.label}),t.detail&&(0,V.jsx)(`p`,{className:`muted`,children:t.detail}),t.copy&&e.accountUrl&&(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`p`,{className:`muted`,children:[`ACME account (`,e.acme,`): `,(0,V.jsx)(`code`,{children:e.accountUrl}),` `,(0,V.jsx)(Df,{text:e.accountUrl})]}),e.record&&(0,V.jsxs)(`p`,{className:`muted`,children:[`CAA record: `,(0,V.jsx)(`code`,{className:`remote-record`,children:e.record}),` `,(0,V.jsx)(Df,{text:e.record})]}),(0,V.jsx)(`div`,{className:`restart-confirm`,children:(0,V.jsx)(`button`,{className:`small`,disabled:n,onClick:()=>{r(!0),a(null),R.certificateCheck().catch(e=>a(e.message)).finally(()=>r(!1))},children:n?`Checking…`:`Check now`})})]}),i&&(0,V.jsx)(`p`,{className:`restart-problem`,children:i})]})}function yC({source:e,update:t}){return(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h3`,{children:`About`}),(0,V.jsx)(`p`,{className:`muted`,children:`Ledung is free software under the GNU Affero General Public License, version 3, with an additional permission for Anthropic's software; a commercial license is also available.`}),(0,V.jsxs)(`p`,{className:`muted`,children:[`It runs Anthropic's Claude Agent SDK and Claude Code, installed from npm under `,(0,V.jsx)(`a`,{href:`https://code.claude.com/docs/en/legal-and-compliance`,target:`_blank`,rel:`noreferrer`,children:`Anthropic's own terms`}),`. They are not covered by Ledung's license.`]}),e&&(0,V.jsxs)(`p`,{className:`muted`,children:[`Running `,(0,V.jsx)(`code`,{children:e.version}),`. `,(0,V.jsx)(`a`,{href:e.url,target:`_blank`,rel:`noreferrer`,children:`Source`})]}),t.view&&(0,V.jsx)(xC,{update:t})]})}var bC={public:`Public`,dev:`Dev`};function xC({update:e}){let t=e.view,n=t.channel??`public`;return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`h3`,{children:`Update channel`}),(0,V.jsx)(`div`,{className:`restart-confirm`,role:`radiogroup`,"aria-label":`Update channel`,children:[`public`,`dev`].map(r=>(0,V.jsxs)(`label`,{children:[(0,V.jsx)(`input`,{type:`radio`,name:`update-channel`,checked:n===r,disabled:t.updating||t.restarting,onChange:()=>e.act(()=>R.updateChannel(r))}),` `,bC[r]]},r))}),(0,V.jsxs)(`p`,{className:`muted`,children:[n===`dev`?`Dev: updates to dev builds, made after changes are merged and before a public release, as well as public releases.`:`Public: updates to public releases only, as npm install -g ledung gets them.`,` `,t.npm?`Check for updates is under Update & restart.`:`This Ledung updates from main in the folder it was built from, so the channel applies only once it is installed from npm.`]})]})}var SC=(e,t)=>`bt:${e}#${t}`;function CC(e){let t=/^bt:([^#]+)#(.+)$/.exec(e??``);return t?{repo:t[1],id:t[2]}:null}var wC=(e,t)=>`#/board/${e}/${encodeURIComponent(t)}`;function TC(e){let t=/^#\/board\/([A-Za-z0-9_.-]+\/[A-Za-z0-9_.-]+)\/([^/]+)$/.exec(e);if(!t)return null;try{return{repo:t[1],id:decodeURIComponent(t[2])}}catch{return null}}function EC(e,t){return e.mine?`this Ledung's manager of project ${e.fromProject??`unknown`}`:e.viaLedung?`@${e.author}'s Ledung${e.fromProject?`, project ${e.fromProject}`:``}`:`typed on ${t} by @${e.author}`}function DC(e){let t=e.deliveries.map(t=>{switch(t.kind){case`wake`:return{text:`woke ${t.project}`,level:`ok`,project:t.project};case`quiet`:return{text:`quiet to ${t.project}`,level:`quiet`,project:t.project};case`channel`:return{text:`channel, ${t.project}`,level:`quiet`,project:t.project};case`ignored`:return{text:`not delivered to ${t.project}: its allowlist does not name @${e.author}`,level:`warn`,project:t.project}}});return t.length?t:e.status===`sent`?[{text:`sent from this Ledung`,level:`none`}]:e.status===`ignored`?[{text:`not delivered: no project here allows @${e.author}; only the id was kept, not the text`,level:`warn`}]:e.status===`quiet`?[{text:`not delivered: it reached no manager (no front desk, or the project's board is off)`,level:`warn`}]:[{text:`not for this Ledung`,level:`none`}]}var OC={project:``,repo:``,unreadOnly:!1,notDelivered:!1},kC=e=>e.dropped+e.refused+e.unsent>0,AC=(e,t=``)=>t?e.unread[t]??0:Object.values(e.unread).reduce((e,t)=>e+t,0);function jC(e,t){return e.filter(e=>(!t.repo||e.repo===t.repo)&&(!t.project||e.projects.includes(t.project))&&(!t.unreadOnly||AC(e,t.project)>0)&&(!t.notDelivered||kC(e)))}var MC=e=>e&&/^https:\/\//.test(e)?e:null;function NC(e,t){let[n,r]=(0,v.useState)({data:null,error:null});return(0,v.useEffect)(()=>{let t=!0;return e().then(e=>t&&r({data:e,error:null}),e=>t&&r(t=>({data:t.data,error:e.message}))),()=>{t=!1}},t),n}var PC=OC,FC=e=>e.length>4?`${e.slice(0,4).join(`, `)} +${e.length-4}`:e.join(`, `);function IC(e){let{data:t,error:n}=NC(()=>R.boardThreads(),[e.board]),[r,i]=(0,v.useState)(PC),a=e=>i(t=>PC={...t,...e}),o=(0,v.useMemo)(()=>Object.keys(e.board?.projects??{}).filter(t=>e.board.projects[t].repo).sort(),[e.board]),s=(e.board?.boards??[]).map(e=>e.repo),c=(0,v.useMemo)(()=>jC(t?.threads??[],r),[t,r]),l=r.project||r.repo||r.unreadOnly||r.notDelivered;return(0,V.jsxs)(`div`,{className:`waiting-view board-view`,children:[(0,V.jsxs)(`header`,{className:`session-head`,children:[(0,V.jsxs)(`div`,{className:`session-head-text`,children:[(0,V.jsx)(`h2`,{children:`Board`}),(0,V.jsx)(`div`,{className:`muted`,children:`Read-only. The managers' messages with other people's Ledungs, newest first. Looking here posts nothing and marks nothing read.`})]}),(0,V.jsx)(`div`,{className:`session-corner`,children:(0,V.jsx)(`button`,{className:`small`,onClick:e.onOpenSettings,children:`Board settings`})})]}),(0,V.jsxs)(`div`,{className:`board-filters`,role:`group`,"aria-label":`Filter threads`,children:[o.length>1&&(0,V.jsxs)(`label`,{children:[`Project`,(0,V.jsxs)(`select`,{value:r.project,onChange:e=>a({project:e.target.value}),children:[(0,V.jsx)(`option`,{value:``,children:`All projects`}),o.map(e=>(0,V.jsx)(`option`,{value:e,children:e},e))]})]}),s.length>1&&(0,V.jsxs)(`label`,{children:[`Board`,(0,V.jsxs)(`select`,{value:r.repo,onChange:e=>a({repo:e.target.value}),children:[(0,V.jsx)(`option`,{value:``,children:`All boards`}),s.map(e=>(0,V.jsx)(`option`,{value:e,children:e},e))]})]}),(0,V.jsxs)(`label`,{className:`toggle`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r.unreadOnly,onChange:e=>a({unreadOnly:e.target.checked})}),` Unread only`]}),(0,V.jsxs)(`label`,{className:`toggle`,title:`Threads with a post that reached no manager: dropped (sender not allowed), refused by a project's allowlist, or for nobody's inbox`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r.notDelivered,onChange:e=>a({notDelivered:e.target.checked})}),` Not delivered`]}),l&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>{PC=OC,i(OC)},children:`Clear filters`})]}),(0,V.jsxs)(`div`,{className:`waiting-list board-list`,children:[n&&(0,V.jsx)(`p`,{className:`board-error`,children:n}),!t&&!n&&(0,V.jsx)(`p`,{className:`muted`,children:`Reading the board…`}),t&&c.length===0&&(0,V.jsx)(`p`,{className:`muted`,children:l?`No thread matches these filters.`:`No threads yet. Posts from the board appear here once Ledung has seen them.`}),c.map(t=>(0,V.jsx)(LC,{t,filters:r,onOpen:e.onOpen,showRepo:s.length>1},`${t.repo}#${t.id}`)),t?.truncated&&(0,V.jsxs)(`p`,{className:`muted`,children:[`Only the `,t.threads.length,` most recent threads are listed.`]})]})]})}function LC({t:e,filters:t,onOpen:n,showRepo:r}){let i=AC(e,t.project),a=[e.dropped?`${e.dropped} dropped (sender not allowed)`:``,e.refused?`${e.refused} refused by a project's allowlist`:``,e.unsent?`${e.unsent} reached no manager`:``].filter(Boolean),o=e.last,s=o?o.mine?`${o.fromProject??`this Ledung`}`:o.viaLedung?`@${o.author}'s Ledung`:`@${o.author}`:``;return(0,V.jsxs)(`button`,{className:`board-thread-card${i?` unread`:``}`,onClick:()=>n(SC(e.repo,e.id)),children:[(0,V.jsxs)(`span`,{className:`board-thread-top`,children:[(0,V.jsxs)(`span`,{className:`board-thread-title`,children:[i>0&&(0,V.jsx)(`span`,{className:`unread-dot`,"aria-label":`unread`}),e.onlyDropped?`Thread ${e.id} (dropped posts only)`:e.title]}),(0,V.jsx)(`span`,{className:`muted board-thread-time`,children:Eg(e.updatedAt)})]}),(0,V.jsxs)(`span`,{className:`board-thread-meta muted`,children:[(0,V.jsx)(`span`,{className:`mono`,children:r?`${e.repo} #${e.id}`:`#${e.id}`}),e.participants.length>0&&(0,V.jsxs)(V.Fragment,{children:[` · `,FC(e.participants)]})]}),(0,V.jsxs)(`span`,{className:`board-thread-chips`,children:[i>0&&(0,V.jsxs)(`span`,{className:`chip accent`,children:[i,` unread`]}),e.projects.map(e=>(0,V.jsx)(`span`,{className:`chip`,children:e},e)),a.map(e=>(0,V.jsx)(`span`,{className:`chip warn`,children:e},e))]}),o&&(0,V.jsxs)(`span`,{className:`board-thread-last`,children:[(0,V.jsxs)(`strong`,{children:[s,`:`]}),` `,o.text||`(empty)`]})]})}function RC(e){let{data:t,error:n}=NC(()=>R.boardThread(e.repo,e.id),[e.repo,e.id,e.board]),r=t=>e.projects.find(e=>e.name===t)?.managerId??null,i=MC(t?.url??null);return(0,V.jsxs)(`div`,{className:`waiting-view board-view`,children:[(0,V.jsxs)(`header`,{className:`session-head`,children:[(0,V.jsxs)(`div`,{className:`session-head-text`,children:[(0,V.jsx)(`h2`,{children:t&&!t.missing?t.title:`Thread ${e.id}`}),(0,V.jsxs)(`div`,{className:`muted`,children:[(0,V.jsxs)(`span`,{className:`mono`,children:[e.repo,` #`,e.id]}),t&&t.participants.length>0&&(0,V.jsxs)(V.Fragment,{children:[` · `,FC(t.participants)]})]})]}),(0,V.jsx)(`div`,{className:`session-corner`,children:(0,V.jsx)(`button`,{className:`small`,onClick:e.onBack,children:`← Board`})})]}),(0,V.jsxs)(`div`,{className:`waiting-list board-thread-page`,children:[(0,V.jsxs)(`p`,{className:`muted board-readonly`,children:[`Read-only: nothing is posted from here and opening this does not mark anything read.`,i&&(0,V.jsxs)(V.Fragment,{children:[` `,(0,V.jsxs)(`a`,{href:i,target:`_blank`,rel:`noopener noreferrer`,children:[`Open the thread on `,t?.service??`the board`]}),`.`]})]}),n&&(0,V.jsx)(`p`,{className:`board-error`,children:n}),!t&&!n&&(0,V.jsx)(`p`,{className:`muted`,children:`Reading the thread…`}),t?.missing&&(0,V.jsx)(`p`,{className:`muted`,children:`Ledung holds no posts of this thread. It may be older than the board's first check here, or on a board no project here uses.`}),t?.truncated&&(0,V.jsxs)(`p`,{className:`muted`,children:[`Only the latest `,t.posts.length,` posts are shown.`]}),t?.posts.map(n=>(0,V.jsx)(BC,{p:n,service:t.service,managerOf:r,onOpen:e.onOpen},n.id))]})]})}function zC({files:e}){return(0,V.jsx)(`ul`,{className:`board-attachments`,children:e.map((e,t)=>{let n=e.size>=1048576?`${(e.size/1048576).toFixed(1)} MB`:`${Math.max(1,Math.round(e.size/1024))} KB`,r=`${e.name} · ${e.kind===`text`?`text`:e.kind.toUpperCase()} · ${n}`;if(e.file&&e.kind!==`text`){let n=wf(``,e.file);return(0,V.jsxs)(`li`,{children:[(0,V.jsx)(`a`,{href:n,target:`_blank`,rel:`noopener noreferrer`,children:(0,V.jsx)(`img`,{src:n,alt:e.name})}),(0,V.jsx)(`span`,{children:r})]},t)}let i=e.pruned?`pruned`:e.error?`not fetched: ${e.error}`:`in the board cache`;return(0,V.jsx)(`li`,{className:`muted`,children:(0,V.jsxs)(`span`,{children:[r,` · `,i]})},t)})})}function BC({p:e,service:t,managerOf:n,onOpen:r}){let i=e.mine?`out`:e.viaLedung?`ledung`:`typed`,a=e.deliveries.some(e=>!e.read),o=MC(e.url);return(0,V.jsxs)(`div`,{className:`msg board-post board-post-card ${i}${e.text===null?` dropped`:``}${a?` unread`:``}`,children:[(0,V.jsxs)(`div`,{className:`msg-meta`,children:[(0,V.jsx)(`span`,{className:`who`,children:EC(e,t)}),a&&(0,V.jsx)(`span`,{className:`chip accent`,children:`unread`}),(0,V.jsx)(`time`,{className:`time`,children:Eg(e.at)}),o&&(0,V.jsxs)(`a`,{className:`board-post-link`,href:o,target:`_blank`,rel:`noopener noreferrer`,children:[`on `,t]})]}),e.recipients.length>0&&(0,V.jsxs)(`div`,{className:`board-thread`,children:[`To `,e.recipients.join(`, `)]}),e.text===null?(0,V.jsxs)(`div`,{className:`msg-body muted`,children:[`Dropped: no project here allows @`,e.author,`, so Ledung kept only that this post exists, not its text.`]}):(0,V.jsx)(`div`,{className:`msg-body plain`,children:e.text}),e.attachments.length>0&&(0,V.jsx)(zC,{files:e.attachments}),(0,V.jsx)(`ul`,{className:`board-delivery-list`,children:DC(e).map((e,t)=>{let i=e.project?n(e.project):null;return(0,V.jsxs)(`li`,{className:`delivery-${e.level}`,children:[e.text,i&&(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsxs)(`button`,{className:`link`,onClick:()=>r(i),children:[e.project,`'s manager chat`]})]})]},t)})})]})}var VC=80;function HC({value:e,onSave:t,onDone:n,label:r}){let i=B(),[a,o]=(0,v.useState)(e),s=a.replace(/\s+/g,` `).trim();return(0,V.jsx)(`input`,{...i,className:`name-editor`,"aria-label":r,autoFocus:!0,maxLength:VC,value:a,onFocus:e=>e.currentTarget.select(),onChange:e=>o(e.target.value),onClick:e=>e.stopPropagation(),onBlur:n,onKeyDown:r=>{if(r.stopPropagation(),r.key===`Escape`)n();else if(r.key===`Enter`&&!r.nativeEvent.isComposing){if(r.preventDefault(),!s)return;s===e?n():t(s).then(n)}}})}function UC(e,t){return WC(e)-WC(t)||(e.position!==null&&t.position!==null?e.position-t.position:t.createdAt-e.createdAt)}function WC(e){return e.position===null?e.status===`ended`?2:0:1}function GC(e,t,n){let r=e.indexOf(t);if(r<0)return e;let i=e.filter(e=>e!==t),a=Math.max(0,Math.min(i.length,n>r?n-1:n));return[...i.slice(0,a),t,...i.slice(a)]}function KC(e,t){let n=e.findIndex(e=>t<e);return n<0?e.length:n}function qC(e,t,n){let r=e.indexOf(t);return n===r||n===r+1}var JC=5,YC=450,XC=8,ZC=28;function QC(e){let t=(0,v.useRef)(null),[n,r]=(0,v.useState)(null),i=(0,v.useRef)(null),a=(0,v.useRef)(null),o=(0,v.useRef)(!1),s=(0,v.useRef)(e);s.current=e;let c=(0,v.useRef)(null),l=e=>[...t.current?.querySelectorAll(`[data-drag]`)??[]].filter(t=>t.dataset.drag===e),u=(e,t)=>t===`projects`?e.closest(`.project-group`)??e:e,d=(e,n,r)=>{let i=l(e.group),a=i.find(t=>t.dataset.dragId===e.id),o=(e.group===`projects`?t.current:a?.closest(`.project-group`))?.getBoundingClientRect();if(!o||n<o.left||n>o.right||r<o.top||r>o.bottom)return null;let s=KC(i.map(t=>{let n=u(t,e.group).getBoundingClientRect();return n.top+n.height/2}),r);return qC(i.map(e=>e.dataset.dragId),e.id,s)?null:s},f=e=>{let t=a.current;i.current?.timer&&clearTimeout(i.current.timer),i.current=null,a.current=null,c.current?.(),c.current=null,document.body.classList.remove(`sidebar-dragging`),r(null),t&&(o.current=!0,setTimeout(()=>{o.current=!1},0),e&&t.slot!==null&&s.current(t.group,GC(l(t.group).map(e=>e.dataset.dragId),t.id,t.slot)))},p=e=>{a.current={group:e.group,id:e.id,slot:null},document.body.classList.add(`sidebar-dragging`),r(a.current),e.touch&&navigator.vibrate?.(10)},m=e=>{let n=t.current;if(!n)return;let r=n.scrollHeight>n.clientHeight?n:n.closest(`.sidebar`);if(!r)return;let i=r.getBoundingClientRect();e<i.top+ZC?r.scrollBy(0,-10):e>i.bottom-ZC&&r.scrollBy(0,10)};return(0,v.useEffect)(()=>{let e=t.current;if(!e)return;let n=e=>{a.current&&e.preventDefault()};return e.addEventListener(`touchmove`,n,{passive:!1}),()=>{e.removeEventListener(`touchmove`,n),c.current?.()}},[]),{nav:t,drag:n,handlers:{onPointerDown:e=>{if(e.button!==0||i.current)return;let n=e.target.closest(`[data-drag]`);if(!n||!t.current?.contains(n))return;let o=e.pointerType===`touch`,s={pointerId:e.pointerId,x:e.clientX,y:e.clientY,group:n.dataset.drag,id:n.dataset.dragId,touch:o,timer:null};if(i.current=s,o)s.timer=window.setTimeout(()=>{s.timer=null,i.current===s&&p(s)},YC);else try{n.setPointerCapture(e.pointerId)}catch{}let l=e=>{if(e.pointerId!==s.pointerId)return;let t=Math.hypot(e.clientX-s.x,e.clientY-s.y);if(!a.current){if(s.touch){t>XC&&f(!1);return}if(t<JC)return;p(s)}let n=a.current,i=d(n,e.clientX,e.clientY);i!==n.slot&&(a.current={...n,slot:i},r(a.current)),m(e.clientY)},u=e=>{e.pointerId===s.pointerId&&f(!0)},h=e=>{e.pointerId===s.pointerId&&f(!1)},g=e=>{e.key===`Escape`&&a.current&&(e.preventDefault(),e.stopPropagation(),f(!1))};window.addEventListener(`pointermove`,l),window.addEventListener(`pointerup`,u),window.addEventListener(`pointercancel`,h),document.addEventListener(`keydown`,g,!0),c.current=()=>{window.removeEventListener(`pointermove`,l),window.removeEventListener(`pointerup`,u),window.removeEventListener(`pointercancel`,h),document.removeEventListener(`keydown`,g,!0)}},onClickCapture:e=>{o.current&&(e.preventDefault(),e.stopPropagation())},onContextMenu:e=>{(i.current?.touch||a.current)&&e.preventDefault()}}}}var $C=`ledung.sidebar.folded`,ew=`ledung.sidebar.foldedSessions`,tw=(e,t,n)=>({count:(e?.count??0)+1,pending:(e?.pending??0)+(n[t.s.id]??0),working:(e?.working??!1)||ut(t.s)===`running`});function nw(e,t){let n=[],r=null,i=null,a=null;return e.forEach((o,s)=>{o.depth===0&&(i=o.s.id,a=null);let c=t.folded||o.depth>0&&i!==null&&t.foldedSessions.includes(i),l=o.depth===0&&e[s+1]?.depth===1;if(!c||o.s.id===t.openId){let e={...o,...c?{drag:null}:{},folds:l,folded:l&&t.foldedSessions.includes(o.s.id),hidden:null};n.push(e),o.depth===0&&(a=e)}else t.folded?r=tw(r,o,t.pending):a&&(a.hidden=tw(a.hidden,o,t.pending))}),t.folded&&!r&&(r={count:0,pending:0,working:!1}),{rows:n,project:r}}function rw(e,t){try{let n=JSON.parse(e.getItem(t)??`[]`);return Array.isArray(n)?n.filter(e=>typeof e==`string`):[]}catch{return[]}}function iw(e,t,n){try{n.length?e.setItem(t,JSON.stringify(n)):e.removeItem(t)}catch{}}var aw=e=>rw(e,$C),ow=(e,t)=>iw(e,$C,t),sw=e=>rw(e,ew),cw=(e,t)=>iw(e,ew,t);function lw(e,t,n=()=>!0){let r=e.filter(e=>e!==t&&n(e));return e.includes(t)?r:[...r,t]}function uw(e,t){let n=[e.container,e.host===`github.com`?null:e.host].filter(Boolean).join(`, `),r=e=>e.toLocaleString(`en-US`),i=e.polling===`slow`?` · PRs checked every 10 min`:e.polling===`stopped`?` · PRs not checked until then`:``;return`GitHub${n?` (${n})`:``}: ${r(e.remaining)} of ${r(e.limit)} left until ${t(e.resetAt)}${i}`}function dw(e,t){return e.filter(e=>e.resetAt>t)}function fw(e){return e.polling===`stopped`?`critical`:e.polling===`slow`?`warning`:``}var pw=[`settings`,`accounts`,`add`,`chats`],mw=e=>!!e&&(pw.includes(e)||/^(settings|chats):/.test(e));function hw(e,t,n){return mw(n)?mw(e)?{depth:t.depth+1,root:t.root}:{depth:1,root:!1}:{depth:0,root:!1}}function gw(e){return e.depth>0&&!e.root?{back:e.depth}:{start:!0}}var _w=e=>e.key===`Escape`&&!e.defaultPrevented&&!e.isComposing,vw=e=>e===null?`phone-list`:`phone-pane`;function yw(e){return e?.ledungFromList===!0?{back:1}:{open:null}}var bw=e=>e?null:`overview`,xw=e=>`ledung.draft.${e}`;function Sw(e,t){try{return e.getItem(xw(t))??``}catch{return``}}function Cw(e,t,n){try{n?e.setItem(xw(t),n):e.removeItem(xw(t))}catch{}}function ww(e,t=localStorage){let[n,r]=(0,v.useState)(()=>Sw(t,e)),i=(0,v.useRef)(n),a=(0,v.useRef)(n);(0,v.useEffect)(()=>{i.current=n});let o=(0,v.useCallback)(()=>{i.current!==a.current&&(a.current=i.current,Cw(t,e,i.current))},[t,e]);return(0,v.useEffect)(()=>{if(n===a.current)return;let e=setTimeout(o,300);return()=>clearTimeout(e)},[n,o]),(0,v.useEffect)(()=>{let e=()=>{document.visibilityState===`hidden`&&o()};return window.addEventListener(`pagehide`,o),document.addEventListener(`visibilitychange`,e),()=>{window.removeEventListener(`pagehide`,o),document.removeEventListener(`visibilitychange`,e),o()}},[o]),[n,r]}function Tw(e){let t=(0,v.useRef)(e);return(0,v.useLayoutEffect)(()=>{t.current=e}),(0,v.useCallback)((...e)=>t.current(...e),[])}function Ew(e){let t=e.status===`ended`,n=!t&&e.status!==`stopping`;return{menu:[...e.role===`manager`?[`away`]:[],`permissions`,...e.role===`session`?[`priority`]:[],`toolCalls`,`usage`,...n?[`pause`,`stop`]:[],...e.claudeVersion?[`version`]:[]],header:[...e.status===`queued`?[`startNow`]:[],...e.clearDue!=null&&!t?[`clear`]:[],...e.compacting&&!t?[`compacting`]:[],...t&&e.claudeSessionId?[`resume`]:[],...t&&e.role===`session`?[`archive`]:[]]}}var Dw=e=>e.status!==`ended`&&e.status!==`stopping`,Ow={connected:`connected`,failed:`failed`,"needs-auth":`needs sign-in`,pending:`starting`,disabled:`disabled`},kw=e=>e.status===`running`||e.status===`waiting`,Aw=e=>e.ctrlKey&&!e.metaKey&&!e.altKey&&!e.shiftKey&&!e.isComposing&&(/^[a-z]$/i.test(e.key)?e.key.toLowerCase()===`o`:e.code===`KeyO`),jw=e=>e.key===`Escape`&&!e.defaultPrevented&&!e.isComposing;function Mw(e){return`${e<10?e.toFixed(1):Math.round(e)} ${e>=.95&&e<1.05?`core`:`cores`}`}function Nw(e){return e>=1024**3?`${(e/1024**3).toFixed(e>=10*1024**3?0:1)} GB`:e>=1024**2?`${Math.round(e/1024**2)} MB`:`${Math.round(e/1024)} KB`}function Pw(e){let t=Math.round(e/1e3);return t<60?`${t} s`:t<3600?`${Math.round(t/60)} min`:`${(t/3600).toFixed(1)} h`}var Fw={normal:`Normal`,high:`High`,critical:`Critical`};function Iw({label:e,used:t,total:n,text:r}){let i=n>0?t/n:0,a=i>=.95?`critical`:i>=.8?`warning`:`good`,o={good:`●`,warning:`▲`,critical:`■`}[a];return(0,V.jsxs)(`div`,{className:`limit`,title:`${e}: ${r}${a===`good`?``:a===`warning`?` (busy)`:` (full)`}`,children:[(0,V.jsxs)(`div`,{className:`limit-head`,children:[(0,V.jsx)(`span`,{children:e}),(0,V.jsxs)(`span`,{className:`limit-status ${a}`,children:[o,` `,Math.round(i*100),`%`]})]}),(0,V.jsx)(`div`,{className:`limit-track`,children:(0,V.jsx)(`div`,{className:`limit-fill ${a}`,style:{width:`${Math.min(100,i*100)}%`}})}),(0,V.jsx)(`div`,{className:`limit-sub muted`,children:r})]})}function Lw(e){let t=e.machine,[n,r]=(0,v.useState)(``);if((0,v.useEffect)(()=>r(t?String(t.limit):``),[t?.limit]),!t)return null;let i=()=>{let i=Number(n);i!==t.limit&&e.run(()=>R.setLimit(i)).finally(()=>r(String(t.limit)))},a=t=>e.sessions.find(e=>e.id===t)?.title??`a session`;return(0,V.jsxs)(`section`,{className:`machine`,"aria-label":`Machine`,children:[(0,V.jsxs)(`div`,{className:`limits`,children:[(0,V.jsx)(Iw,{label:`CPU`,used:t.cores,total:t.cpus,text:`${Mw(t.cores)} of ${t.cpus}`}),(0,V.jsx)(Iw,{label:`Memory`,used:t.memUsed,total:t.memTotal,text:`${Nw(t.memUsed)} of ${Nw(t.memTotal)}`}),t.docker&&(0,V.jsx)(Iw,{label:`Docker memory`,used:t.docker.memUsed,total:t.docker.memTotal,text:`${Nw(t.docker.memUsed)} of ${Nw(t.docker.memTotal)} · ${Mw(t.docker.cores)}`})]}),(0,V.jsxs)(`div`,{className:`machine-working`,children:[(0,V.jsxs)(`span`,{children:[(0,V.jsx)(`strong`,{children:t.working}),` of `]}),(0,V.jsx)(`input`,{type:`number`,min:1,max:100,value:n,"aria-label":`How many sessions may work at once`,title:`How many sessions may work at the same time. Managers don't count.`,onChange:e=>r(e.target.value),onBlur:i,onKeyDown:e=>e.key===`Enter`&&e.target.blur()}),(0,V.jsxs)(`span`,{children:[` working`,t.line.length?` · ${t.line.length} waiting`:``]})]}),t.line.length>0&&(0,V.jsx)(`ol`,{className:`machine-line`,children:t.line.map(t=>{let n=e.sessions.find(e=>e.id===t);return(0,V.jsxs)(`li`,{children:[(0,V.jsx)(`button`,{className:`link`,onClick:()=>e.onOpen(t),children:a(t)}),n&&n.priority!==`normal`&&(0,V.jsx)(`span`,{className:`chip prio-${n.priority}`,children:Fw[n.priority]}),(0,V.jsx)(`button`,{className:`small`,title:`Start this turn now, above the limit`,onClick:()=>void e.run(()=>R.startNow(t)),children:`Start now`})]},t)})})]})}function Rw({sessionId:e}){let[t,n]=(0,v.useState)(null);if((0,v.useEffect)(()=>{let t=!0,r=()=>R.turns(e).then(e=>t&&n(e),()=>{});r();let i=setInterval(r,15e3);return()=>{t=!1,clearInterval(i)}},[e]),!t)return null;if(!t.length)return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`h3`,{children:`Machine use per turn`}),(0,V.jsx)(`p`,{className:`muted`,children:`No turns measured yet.`})]});let r=t.slice(-60);return(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`h3`,{children:`CPU per turn`}),(0,V.jsx)(zw,{values:r.map(e=>({value:e.peakCores,label:`${new Date(e.startedAt).toLocaleTimeString()}: peak ${Mw(e.peakCores)}, average ${Mw(e.avgCores)}`})),format:Mw}),(0,V.jsx)(`h3`,{children:`Memory per turn`}),(0,V.jsx)(zw,{values:r.map(e=>({value:e.peakMem,label:`${new Date(e.startedAt).toLocaleTimeString()}: peak ${Nw(e.peakMem)}`})),format:Nw}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain calls`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Started`}),(0,V.jsx)(`th`,{className:`num`,children:`Took`}),(0,V.jsx)(`th`,{className:`num`,children:`Avg CPU`}),(0,V.jsx)(`th`,{className:`num`,children:`Peak CPU`}),(0,V.jsx)(`th`,{className:`num`,children:`Peak memory`}),(0,V.jsx)(`th`,{children:`Commands`})]})}),(0,V.jsx)(`tbody`,{children:t.slice().reverse().map(e=>(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{className:`nowrap`,children:new Date(e.startedAt).toLocaleTimeString()}),(0,V.jsx)(`td`,{className:`num`,children:Pw(e.durationMs)}),(0,V.jsx)(`td`,{className:`num`,children:e.avgCores.toFixed(2)}),(0,V.jsx)(`td`,{className:`num`,children:e.peakCores.toFixed(2)}),(0,V.jsx)(`td`,{className:`num`,children:Nw(e.peakMem)}),(0,V.jsx)(`td`,{className:`mono`,children:e.commands.join(`, `)||(0,V.jsx)(`span`,{className:`muted`,children:`none`})})]},e.startedAt))})]})})]})}function zw({values:e,format:t}){let n=Math.max(...e.map(e=>e.value),0);return(0,V.jsxs)(`div`,{className:`mini-bars`,role:`img`,"aria-label":`Highest: ${t(n)}`,children:[(0,V.jsx)(`span`,{className:`mini-max muted`,children:t(n)}),e.map((e,t)=>(0,V.jsx)(`div`,{className:`mini-col`,title:e.label,children:(0,V.jsx)(`div`,{className:`mini-bar`,style:{height:`${n>0?Math.max(2,e.value/n*100):0}%`}})},t))]})}function Bw(){let[e,t]=(0,v.useState)(null);return(0,v.useEffect)(()=>{R.typicalCosts(30).then(t,()=>t([]))},[]),(0,V.jsxs)(`section`,{children:[(0,V.jsx)(`h2`,{children:`Typical machine use per turn`}),(0,V.jsx)(`p`,{className:`muted`,children:`Last 30 days, sessions only (not managers): what a turn that ran each kind of command usually used. Ledung learns these; they don't decide anything yet.`}),e?e.length?(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Project`}),(0,V.jsx)(`th`,{children:`Command`}),(0,V.jsx)(`th`,{className:`num`,children:`Turns`}),(0,V.jsx)(`th`,{className:`num`,children:`Avg CPU`}),(0,V.jsx)(`th`,{className:`num`,children:`Peak CPU`}),(0,V.jsx)(`th`,{className:`num`,children:`Peak memory`}),(0,V.jsx)(`th`,{className:`num`,children:`Duration`})]})}),(0,V.jsx)(`tbody`,{children:e.slice(0,50).map(e=>(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{children:S(e.project)}),(0,V.jsx)(`td`,{className:`mono`,children:e.command||(0,V.jsx)(`span`,{className:`muted`,children:`no commands`})}),(0,V.jsx)(`td`,{className:`num`,children:e.turns}),(0,V.jsx)(`td`,{className:`num`,children:Mw(e.avgCores)}),(0,V.jsx)(`td`,{className:`num`,children:Mw(e.peakCores)}),(0,V.jsx)(`td`,{className:`num`,children:Nw(e.peakMem)}),(0,V.jsx)(`td`,{className:`num`,children:Pw(e.durationMs)})]},`${e.project} ${e.command}`))})]})}):(0,V.jsx)(`p`,{className:`muted`,children:`No turns measured yet.`}):(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`})]})}function Vw(e,t){let n=e=>`${Math.round(e/1e3)}k`;return`${n(e)}${t?` of ${n(t)}`:``}`}var Hw={...lt,waiting:`Needs an answer`};function Uw(e){return e.contextTokens&&e.contextWindow?e.contextTokens/e.contextWindow:null}function Ww(e){let t=new Set(e.sessions.map(e=>e.id)),n=e=>e.status!==`ended`,r=e.sessions.filter(r=>(!r.parentId||!t.has(r.parentId))&&(n(r)||e.sessions.some(e=>e.parentId===r.id&&n(e)))),i=(e,t)=>Number(t.role===`manager`)-Number(e.role===`manager`)||t.createdAt-e.createdAt,a=r.sort(i).flatMap(t=>[t,...e.sessions.filter(e=>e.parentId===t.id&&n(e)).sort(i)]),o=e.sessions.filter(e=>e.status===`ended`).length;return(0,V.jsx)(`div`,{className:`overview`,children:(0,V.jsxs)(`div`,{className:`overview-list`,children:[(0,V.jsxs)(`div`,{className:`muted`,children:[e.overview?`${Wy(e.overview.todayTokens)} tokens today`:``,o?` · ${o} ended session${o===1?``:`s`} not shown`:``]}),!a.length&&(0,V.jsx)(`p`,{className:`muted`,children:`No sessions are running.`}),a.map(n=>{let r=e.overview?.sessions[n.id],i=Uw(n),a=!!n.parentId&&t.has(n.parentId);return(0,V.jsxs)(`div`,{role:`button`,tabIndex:0,className:`overview-card${a?` child`:``}`,onClick:()=>e.onOpenSession(n.id),onKeyDown:t=>{(t.key===`Enter`||t.key===` `)&&(t.preventDefault(),e.onOpenSession(n.id))},children:[(0,V.jsxs)(`div`,{className:`overview-top`,children:[(0,V.jsx)(`span`,{className:`dot ${ut(n)}`}),(0,V.jsxs)(`span`,{className:`overview-title`,children:[n.role===`manager`&&(0,V.jsx)(`span`,{className:`chip`,children:`Manager`}),` `,n.title]}),e.waitingBySession[n.id]?(0,V.jsx)(`span`,{className:`badge`,children:e.waitingBySession[n.id]}):null]}),(0,V.jsxs)(`div`,{className:`overview-facts`,children:[(0,V.jsxs)(`span`,{children:[Hw[n.status],e.machine&&e.machine.line.includes(n.id)?`: number ${e.machine.line.indexOf(n.id)+1}`:``,n.paused?` · paused`:``]}),n.priority!==`normal`&&(0,V.jsx)(`span`,{className:`chip prio-${n.priority}`,title:n.priorityNote??void 0,children:Fw[n.priority]}),e.machine?.sessions[n.id]&&(0,V.jsxs)(`span`,{title:`CPU and memory of everything this session runs`,children:[Mw(e.machine.sessions[n.id].cores),` · `,Nw(e.machine.sessions[n.id].memBytes)]}),(0,V.jsx)(`span`,{children:S(n.project)}),n.branch&&(0,V.jsx)(`span`,{className:`mono`,children:n.branch}),n.pr&&(0,V.jsx)(`a`,{href:n.pr.url,target:`_blank`,rel:`noreferrer noopener`,onClick:e=>e.stopPropagation(),title:`${n.pr.title} — checks ${n.pr.checks}`,children:qy(n.pr)}),n.tickets.map(e=>(0,V.jsx)(`a`,{href:e.url,target:`_blank`,rel:`noreferrer noopener`,onClick:e=>e.stopPropagation(),children:e.id},e.id)),r&&(0,V.jsxs)(`span`,{title:`Tokens today / in total`,children:[Wy(r.today),` today · `,Wy(r.total),` total · `,Gy(r.costTotal)]}),n.contextTokens!=null&&(0,V.jsxs)(`span`,{className:i!=null&&i>.8?`ctx-high`:``,title:`How full the context window is, and its size in tokens`,children:[`context `,i==null?``:`${Ky(i)} · `,Vw(n.contextTokens,n.contextWindow)]}),n.backgroundTasks>0&&(0,V.jsxs)(`span`,{children:[n.backgroundTasks,` in background`]})]}),r?.lastReply&&(0,V.jsxs)(`div`,{className:`overview-last`,children:[(0,V.jsx)(`span`,{className:`muted`,children:r.lastReplyAt?Eg(r.lastReplyAt):``}),` `,r.lastReply.split(`
|
|
104
|
+
`)[0]]})]},n.id)})]})})}function Gw({sessionId:e,onClose:t}){let[n,r]=(0,v.useState)(null),[i,a]=(0,v.useState)(null);(0,v.useEffect)(()=>{let t=!0,n=()=>R.sessionUsage(e).then(e=>t&&r(e),e=>t&&a(e.message));n();let i=setInterval(n,15e3);return()=>{t=!1,clearInterval(i)}},[e]);let o=(0,v.useMemo)(()=>Zy(`model`,n?.models??[]),[n?.models]),s=n?.totals,c=n?n.calls.slice(-120):[];return(0,V.jsxs)(`aside`,{className:`file-panel`,"aria-label":`Usage`,children:[(0,V.jsxs)(`header`,{className:`file-head`,children:[(0,V.jsx)(`span`,{className:`file-path`,children:`Usage of this session`}),(0,V.jsx)(`button`,{className:`small`,onClick:t,children:`Close`})]}),(0,V.jsxs)(`div`,{className:`file-body`,children:[i&&(0,V.jsx)(`p`,{className:`error`,children:i}),!n&&!i&&(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`}),n&&s&&(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`div`,{className:`tiles`,children:[(0,V.jsx)(tb,{label:`Tokens`,value:Wy(s.tokens),sub:`${s.calls} model calls`}),(0,V.jsx)(tb,{label:`API-equivalent cost`,value:Gy(s.cost)}),(0,V.jsx)(tb,{label:`Cache read share`,value:s.tokens?Ky(s.cacheRead/s.tokens):`—`}),(0,V.jsx)(tb,{label:`In subagents`,value:s.tokens?Ky(s.subagentTokens/s.tokens):`—`})]}),(0,V.jsx)(`h3`,{children:`Tokens per model call`}),(0,V.jsx)(Qy,{items:[...n.models.map(e=>({label:e,color:o(e)})),...n.calls.some(e=>e.subagent)?[{label:`subagent call`,color:`var(--s-other)`,textured:!0}]:[]]}),(0,V.jsx)(eb,{height:120,columns:c.map(e=>({label:new Date(e.at).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`,second:`2-digit`}),short:new Date(e.at).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`}),values:{[e.model]:e.tokens},textured:!!e.subagent,note:[e.compaction?`Compaction`:``,e.subagent?`Subagent: ${e.subagent}`:``,`Started by: ${Xy[e.trigger]??e.trigger}`].filter(Boolean).join(` · `)})),series:n.models.map(e=>({key:e,label:e,color:o(e)})),emptyText:`No model calls recorded yet.`}),(0,V.jsx)(Rw,{sessionId:e}),(0,V.jsx)(`h3`,{children:`Model calls`}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain calls`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Time`}),(0,V.jsx)(`th`,{children:`Model`}),(0,V.jsx)(`th`,{className:`num`,children:`Input`}),(0,V.jsx)(`th`,{className:`num`,children:`Cache write`}),(0,V.jsx)(`th`,{className:`num`,children:`Cache read`}),(0,V.jsx)(`th`,{className:`num`,children:`Output`}),(0,V.jsx)(`th`,{className:`num`,children:`Thinking`}),(0,V.jsx)(`th`,{className:`num`,children:`Tokens`}),(0,V.jsx)(`th`,{className:`num`,children:`Cache %`}),(0,V.jsx)(`th`,{className:`num`,children:`Cost`}),(0,V.jsx)(`th`,{className:`num`,children:`Running`}),(0,V.jsx)(`th`,{children:`Who`})]})}),(0,V.jsx)(`tbody`,{children:(()=>{let e=0;return n.calls.map((t,n)=>(e+=t.cost??0,(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{className:`nowrap`,children:new Date(t.at).toLocaleTimeString()}),(0,V.jsxs)(`td`,{className:`nowrap`,children:[(0,V.jsx)(`span`,{className:`viz-swatch`,style:{background:o(t.model)}}),` `,t.model]}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.input)}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.cacheWrite)}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.cacheRead)}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.output)}),(0,V.jsx)(`td`,{className:`num muted`,children:t.thinking?`~${Wy(t.thinking)}`:``}),(0,V.jsx)(`td`,{className:`num strong`,children:Wy(t.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:t.tokens?Ky(t.cacheRead/t.tokens):``}),(0,V.jsx)(`td`,{className:`num`,children:Gy(t.cost)}),(0,V.jsx)(`td`,{className:`num muted`,children:Gy(e)}),(0,V.jsx)(`td`,{className:`muted nowrap`,children:t.subagent?`subagent: ${t.subagent}`:Xy[t.trigger]??t.trigger})]},n)))})()})]})})]})]})]})}var Kw=864e5,qw=Kw;function Jw(e,t){return t.fingerprint??`${e.login}/${e.computerId}/${t.label}`}var Yw=e=>e.input+e.cacheWrite+e.cacheRead+e.output;function Xw(e){return e.entries.find(e=>e.own)?.login??null}function Zw(e,t){let n=Xw(e);return e.entries.flatMap(e=>e.state===`ok`&&e.file&&(!t||e.file.login===n)?[e.file]:[])}function Qw(e){return e.flatMap(e=>e.accounts.map(t=>({file:e,account:t,key:Jw(e,t)})))}function $w(e,t,n){if(e===`all`)return null;let r;if(e===`week`){let e=Qw(t).flatMap(({account:e})=>e.limits.filter(e=>e.kind===`seven_day`&&e.resetsAt&&e.resetsAt>n).map(e=>e.resetsAt-Py.seven_day));r=e.length?Math.min(...e):n-6*Kw}else r=n-(Number(e.replace(`d`,``))-1)*Kw;return eT(r)}function eT(e){let t=new Date(e);return`${t.getFullYear()}-${String(t.getMonth()+1).padStart(2,`0`)}-${String(t.getDate()).padStart(2,`0`)}`}function tT(e,t,n){let r=e=>!n||n(e.model),i=e.hourly.filter(r),a=i.length?Math.min(...i.map(e=>e.t)):1/0,o=0;for(let e of i)e.t+36e5>t&&(o+=e.cost);let s=eT(t),c=Number.isFinite(a)?eT(a):null;for(let t of e.daily)!r(t)||t.t<s||c&&t.t>=c||(o+=t.cost);return o}function nT(e){let t=/^seven_day_(opus|sonnet|haiku|fable)$/.exec(e)?.[1];return t?e=>e.toLowerCase().includes(t):void 0}var rT=[`five_hour`,`seven_day`,`seven_day_opus`,`seven_day_sonnet`];function iT(e,t){let n=new Map;for(let t of Qw(e)){let e=n.get(t.key);e?e.push(t):n.set(t.key,[t])}let r=[];for(let[e,i]of n){let n=[...i].sort((e,t)=>t.file.asOf-e.file.asOf)[0],a=[...new Set(i.flatMap(e=>e.account.limits.map(e=>e.kind)))].filter(e=>e!==`overage`&&e!==`seven_day_overage_included`).sort((e,t)=>(rT.indexOf(e)+1||99)-(rT.indexOf(t)+1||99)||e.localeCompare(t)).map(e=>{let n=i.flatMap(t=>t.account.limits.filter(t=>t.kind===e)).sort((e,t)=>t.seenAt-e.seenAt)[0],r=n?{...n,at:n.seenAt}:null,a=r?Vy(r,t):!1,o=Py[e]??Py.seven_day,s=r?.resetsAt&&!a?r.resetsAt-o:t-o,c=i.map(t=>({computer:t.file.computer,computerId:t.file.computerId,login:t.file.login,cost:tT(t.account,s,nT(e))})),l=c.reduce((e,t)=>e+t.cost,0);return{kind:e,reading:r,reset:a,pace:r&&!a&&r.utilization!=null?Fy(e.startsWith(`seven_day`)?`seven_day`:e,r.utilization,r.resetsAt,t):null,shares:c.filter(e=>e.cost>0).map(e=>({...e,share:e.cost/l})).sort((e,t)=>t.cost-e.cost)}});r.push({fingerprint:e,label:n.account.label,rows:a,people:[...new Set(i.map(e=>e.file.login))].sort(),computers:[...new Set(i.map(e=>e.file.computer))].sort()})}return r.sort((e,t)=>e.label.localeCompare(t.label))}function aT(e,t,n){return e===`person`?t.file.login:e===`account`?t.account.label:e===`computer`?t.file.computer:e===`model`?n.model:n.project}function oT(e,t,n,r){let i=new Map,a=new Set;for(let r of Qw(e))for(let e of r.account.daily){if(n&&e.t<n)continue;let o=aT(t,r,e);a.add(o);let s=i.get(e.t)??Object.create(null);s[o]=(s[o]??0)+Yw(e),i.set(e.t,s)}let o=n??[...i.keys()].sort()[0],s=eT(r),c=[];if(o)for(let e=new Date(`${o}T12:00:00`);eT(e.getTime())<=s;e.setDate(e.getDate()+1)){let t=eT(e.getTime());c.push({day:t,values:i.get(t)??Object.create(null)})}return{keys:[...a].sort(),columns:c}}function sT(e,t,n){return Qw(e).map(({file:e,account:r,key:i})=>{let a=r.daily.filter(e=>!t||e.t>=t);return{login:e.login,account:r.label,fingerprint:i,computer:e.computer,computerId:e.computerId,tokens:a.reduce((e,t)=>e+Yw(t),0),cost:a.reduce((e,t)=>e+t.cost,0),asOf:e.asOf,stale:n-e.asOf>qw}}).sort((e,t)=>e.login.localeCompare(t.login)||e.account.localeCompare(t.account)||e.computer.localeCompare(t.computer))}var cT=[[`week`,`Since weekly reset`],[`7d`,`7 days`],[`30d`,`30 days`],[`90d`,`90 days`],[`all`,`All time`]],lT=[[`person`,`person`],[`account`,`account`],[`computer`,`computer`],[`model`,`model`],[`project`,`project`]],uT={five_hour:`5-hour`,seven_day:`Weekly`,seven_day_opus:`Weekly Opus`,seven_day_sonnet:`Weekly Sonnet`},dT={allowed:{cls:`good`,icon:`●`,label:`OK`},allowed_warning:{cls:`warning`,icon:`▲`,label:`Close to the limit`},rejected:{cls:`critical`,icon:`■`,label:`Limit reached`}};function fT(e,t){return Object.hasOwn(e,t)?e[t]:void 0}function pT(){let[e,t]=(0,v.useState)(null),[n,r]=(0,v.useState)(null);return(0,v.useEffect)(()=>{let e=!0,n=()=>R.sharedUsage().then(n=>e&&(t(n),r(null)),t=>e&&r(t.message));n();let i=setInterval(n,6e4);return()=>{e=!1,clearInterval(i)}},[]),n&&!e?(0,V.jsx)(`p`,{className:`error`,children:n}):e?(0,V.jsx)(mT,{view:e,now:Date.now()}):(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`})}function mT({view:e,now:t,initialMine:n=!1}){let[r,i]=(0,v.useState)(n),[a,o]=(0,v.useState)(`week`),[s,c]=(0,v.useState)(`person`),l=Xw(e),u=(0,v.useMemo)(()=>Zw(e,r),[e,r]),d=$w(a,u,t),f=(0,v.useMemo)(()=>iT(u,t),[u,t]),p=(0,v.useMemo)(()=>oT(u,s,d,t),[u,s,d,t]),m=(0,v.useMemo)(()=>sT(u,d,t),[u,d,t]),h=Zy(`project`,[...new Set(Zw(e,!1).map(e=>e.computerId))]),g=Zy(s===`model`?`model`:`project`,p.keys);if(!e.repo)return(0,V.jsx)(`p`,{className:`muted`,children:`Nothing is published here yet. Switch on Publish usage in Settings to share this computer's usage and read everyone else's.`});let _=p.keys.map(e=>({key:e,label:e,color:g(e)})),y=p.columns.map(e=>({label:new Date(`${e.day}T12:00:00`).toLocaleDateString([],{weekday:`short`,day:`numeric`,month:`short`}),short:new Date(`${e.day}T12:00:00`).toLocaleDateString([],{weekday:`short`,day:`numeric`}),values:e.values}));return(0,V.jsxs)(`div`,{className:`shared-usage`,children:[(0,V.jsxs)(`div`,{className:`filters`,children:[(0,V.jsxs)(`label`,{children:[`Period `,(0,V.jsx)(`select`,{value:a,onChange:e=>o(e.target.value),children:cT.map(([e,t])=>(0,V.jsx)(`option`,{value:e,children:t},e))})]}),(0,V.jsxs)(`label`,{className:`shared-mine`,title:l?`Only ${l}'s own computers`:`Mine needs this computer to publish its usage too`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:r,disabled:!l,onChange:e=>i(e.target.checked)}),` Mine`]})]}),e.error&&(0,V.jsxs)(`p`,{className:`error`,children:[`Could not read the shared usage just now: `,e.error,e.entries.length?` Showing the last files read.`:``]}),e.entries.filter(e=>e.state!==`ok`&&(!r||e.login===l)).map(e=>(0,V.jsxs)(`p`,{className:`shared-note warning`,children:[e.computer??`A computer`,e.login?` (${e.login})`:``,e.state===`newer`?` publishes usage in a newer format: update Ledung to see it.`:` published a usage file Ledung cannot read${e.reason?` (${e.reason})`:``}.`]},e.id)),!u.length&&(0,V.jsx)(`p`,{className:`muted`,children:r?`None of your computers has published yet.`:`No computer has published yet.`}),f.length>0&&(0,V.jsx)(`div`,{className:`shared-cards`,children:f.map(e=>(0,V.jsx)(hT,{card:e,now:t,color:h},e.fingerprint))}),u.length>0&&(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsxs)(`div`,{className:`viz-card-head`,children:[(0,V.jsx)(`h3`,{children:`Daily tokens`}),(0,V.jsxs)(`div`,{className:`seg-control shared-stack`,role:`group`,"aria-label":`Stack by`,children:[(0,V.jsx)(`span`,{className:`muted`,children:`by`}),lT.map(([e,t])=>(0,V.jsx)(`button`,{className:s===e?`on`:``,onClick:()=>c(e),children:t},e))]})]}),(0,V.jsx)(Qy,{items:_}),(0,V.jsx)(eb,{columns:y,series:_})]}),m.length>0&&(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsx)(`h3`,{children:`Who's who`}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Person`}),(0,V.jsx)(`th`,{children:`Account`}),(0,V.jsx)(`th`,{children:`Computer`}),(0,V.jsx)(`th`,{className:`num`,children:`Tokens`}),(0,V.jsx)(`th`,{className:`num`,children:`Cost`}),(0,V.jsx)(`th`,{children:`Last published`})]})}),(0,V.jsx)(`tbody`,{children:m.map((e,n)=>{let r=m[n-1],i=r?.login===e.login;return(0,V.jsxs)(`tr`,{className:e.stale?`shared-stale`:``,children:[(0,V.jsx)(`td`,{children:i?``:e.login}),(0,V.jsx)(`td`,{children:i&&r?.fingerprint===e.fingerprint?``:e.account}),(0,V.jsxs)(`td`,{className:`nowrap`,children:[(0,V.jsx)(`span`,{className:`viz-swatch`,style:{background:h(e.computerId)}}),` `,e.computer]}),(0,V.jsx)(`td`,{className:`num`,children:Wy(e.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:Gy(e.cost)}),(0,V.jsxs)(`td`,{className:`nowrap`,children:[Hy({at:e.asOf,resetsAt:null},t).replace(/^as of /,``),e.stale&&(0,V.jsx)(`span`,{className:`shared-stale-mark`,title:`No publish for over a day`,children:` · stale`})]})]},`${e.computerId}-${e.fingerprint}`)})})]})})]})]})}function hT({card:e,now:t,color:n}){return(0,V.jsxs)(`section`,{className:`card viz-card shared-card`,children:[(0,V.jsx)(`h3`,{children:e.label}),(0,V.jsxs)(`div`,{className:`muted shared-card-who`,children:[e.people.join(`, `),` · `,e.computers.length,` computer`,e.computers.length===1?``:`s`]}),!e.rows.some(e=>e.reading)&&(0,V.jsx)(`div`,{className:`muted`,children:`no data yet`}),e.rows.map(e=>{let r=fT(uT,e.kind)??e.kind;if(!e.reading)return null;if(e.reset)return(0,V.jsxs)(`div`,{className:`shared-limit limit-reset`,title:`${r}: the window has reset since the last reading (${Hy(e.reading,t)}).`,children:[(0,V.jsxs)(`div`,{className:`limit-head`,children:[(0,V.jsx)(`span`,{children:r}),(0,V.jsx)(`span`,{className:`limit-status`,children:`reset`})]}),(0,V.jsx)(`div`,{className:`limit-sub muted`,children:(0,V.jsx)(`span`,{children:`no reading since the reset`})})]},e.kind);let i=e.reading.utilization,a=Uy(e.reading,t),o=Math.min(100,(i??0)*100),s=fT(dT,e.reading.status)??{cls:`good`,icon:`●`,label:e.reading.status},c=e.shares.map(e=>`${e.computer} (${e.login}): ${Ky(e.share)}, ${Gy(e.cost)}`).join(`
|
|
105
|
+
`);return(0,V.jsxs)(`div`,{className:`shared-limit`,children:[(0,V.jsxs)(`div`,{className:`limit-head`,children:[(0,V.jsx)(`span`,{children:r}),(0,V.jsxs)(`span`,{className:`limit-status ${s.cls}`,title:s.label,children:[s.icon,` `,i==null?s.label:Ky(i)]})]}),(0,V.jsx)(`div`,{className:`limit-track shared-track`,title:c||`No use recorded in this window`,children:(0,V.jsx)(`div`,{className:`shared-fill`,style:{width:`${o}%`},children:e.shares.length?e.shares.map(e=>(0,V.jsx)(`div`,{className:`shared-seg`,style:{flexGrow:e.share,background:n(e.computerId)}},e.computerId)):(0,V.jsx)(`div`,{className:`shared-seg limit-fill ${s.cls}`,style:{flexGrow:1}})})}),(0,V.jsxs)(`div`,{className:`limit-sub muted`,children:[(0,V.jsx)(`span`,{children:e.shares.map(e=>`${e.computer} ${Ky(e.share)}`).join(` · `)}),(0,V.jsxs)(`span`,{className:`limit-forecast${e.pace!=null&&e.pace>=1?` over`:``}`,children:[`≈ `,e.pace==null?`—`:Ky(e.pace),` by reset`]})]}),a&&(0,V.jsx)(`div`,{className:`limit-sub limit-age`,children:a})]},e.kind)})]})}function gT(){return(0,V.jsx)(`div`,{className:`usage-body`,children:(0,V.jsx)(pT,{})})}var _T=[[`week`,`Since weekly reset`],[`7d`,`7 days`],[`30d`,`30 days`],[`90d`,`90 days`],[`all`,`All time`]];function vT(e){return new Date(`${e}T12:00:00`).toLocaleDateString([],{weekday:`short`,day:`numeric`})}var yT=[[`computer`,`This computer`],[`shared`,`Shared`],[`sessions`,`Sessions`]];function bT(e){let[t,n]=(0,v.useState)(`computer`),r=e.sessionsOpen?`sessions`:t,i=t=>{t===`sessions`?e.sessionsOpen||e.onSessions(!0):(n(t),e.sessionsOpen&&e.onSessions(!1))};return(0,V.jsxs)(`div`,{className:`usage`,children:[(0,V.jsx)(`header`,{className:`session-head`,children:(0,V.jsx)(`div`,{className:`session-head-text`,children:(0,V.jsx)(`h2`,{children:`Usage`})})}),(0,V.jsx)(`div`,{className:`pane-tabs`,role:`tablist`,"aria-label":`Usage`,children:yT.map(([e,t])=>(0,V.jsx)(`button`,{role:`tab`,"aria-selected":r===e,className:r===e?`on`:``,onClick:()=>i(e),children:t},e))}),r===`computer`?(0,V.jsx)(xT,{onOpenSession:e.onOpenSession}):r===`shared`?(0,V.jsx)(gT,{}):(0,V.jsx)(Ww,{sessions:e.sessions,overview:e.overview,machine:e.machine,waitingBySession:e.waitingBySession,onOpenSession:e.onOpenSession})]})}function xT({onOpenSession:e}){let[t,n]=(0,v.useState)({period:`week`}),[r,i]=(0,v.useState)(null),[a,o]=(0,v.useState)(null),[s,c]=(0,v.useState)(`model`),[l,u]=(0,v.useState)({});(0,v.useEffect)(()=>{let e=!0;R.usage(t).then(t=>e&&i(t),t=>e&&o(t.message));let n=setInterval(()=>R.usage(t).then(t=>e&&i(t),()=>{}),3e4);return()=>{e=!1,clearInterval(n)}},[t]);let d=(0,v.useMemo)(()=>({model:Zy(`model`,r?.options.models??[]),project:Zy(`project`,r?.options.projects??[]),trigger:Zy(`trigger`,Yy)}),[r?.options.models,r?.options.projects]);if(a)return(0,V.jsx)(`div`,{className:`usage-body`,children:(0,V.jsx)(`p`,{className:`error`,children:a})});if(!r)return(0,V.jsx)(`div`,{className:`usage-body`,children:(0,V.jsx)(`p`,{className:`muted`,children:`Loading…`})});let f=e=>n(t=>({...t,...e})),p=r.totals,m=(s===`model`?r.models:s===`project`?[...new Set(r.daily.flatMap(e=>Object.keys(e.byProject)))].sort():Yy.filter(e=>r.daily.some(t=>t.byTrigger[e]))).map(e=>({key:e,label:s===`trigger`?Xy[e]??e:e,color:d[s](e)})),h=r.daily.map(e=>({label:new Date(`${e.day}T12:00:00`).toLocaleDateString([],{weekday:`short`,day:`numeric`,month:`short`}),short:vT(e.day),values:s===`model`?e.byModel:s===`project`?e.byProject:e.byTrigger})),g=t.project||t.model||t.branch||t.role||t.trigger||t.account;return(0,V.jsxs)(`div`,{className:`usage-body`,children:[(0,V.jsxs)(`div`,{className:`muted`,children:[`Since `,new Date(r.since||Date.now()).toLocaleString([],{dateStyle:`medium`,timeStyle:`short`}),r.since===0?` (all time)`:``]}),(0,V.jsxs)(`div`,{className:`filters`,children:[(0,V.jsxs)(`label`,{children:[`Period `,(0,V.jsx)(`select`,{value:t.period,onChange:e=>f({period:e.target.value}),children:_T.map(([e,t])=>(0,V.jsx)(`option`,{value:e,children:t},e))})]}),(0,V.jsxs)(`label`,{children:[`Project `,(0,V.jsxs)(`select`,{value:t.project??``,onChange:e=>f({project:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),r.options.projects.map(e=>(0,V.jsx)(`option`,{value:e,children:S(e)},e))]})]}),(r.options.accounts?.length??0)>1&&(0,V.jsxs)(`label`,{children:[`Account `,(0,V.jsxs)(`select`,{value:t.account??``,onChange:e=>f({account:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),r.options.accounts.map(e=>(0,V.jsx)(`option`,{children:e},e))]})]}),(0,V.jsxs)(`label`,{children:[`Model `,(0,V.jsxs)(`select`,{value:t.model??``,onChange:e=>f({model:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),r.options.models.map(e=>(0,V.jsx)(`option`,{children:e},e))]})]}),(0,V.jsxs)(`label`,{children:[`Branch `,(0,V.jsxs)(`select`,{value:t.branch??``,onChange:e=>f({branch:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),r.options.branches.map(e=>(0,V.jsx)(`option`,{children:e},e))]})]}),(0,V.jsxs)(`label`,{children:[`Role `,(0,V.jsxs)(`select`,{value:t.role??``,onChange:e=>f({role:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),(0,V.jsx)(`option`,{value:`manager`,children:`Managers`}),(0,V.jsx)(`option`,{value:`session`,children:`Sessions`})]})]}),(0,V.jsxs)(`label`,{children:[`Started by `,(0,V.jsxs)(`select`,{value:t.trigger??``,onChange:e=>f({trigger:e.target.value||void 0}),children:[(0,V.jsx)(`option`,{value:``,children:`All`}),Yy.map(e=>(0,V.jsx)(`option`,{value:e,children:Xy[e]},e))]})]}),g&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>n({period:t.period}),children:`Clear filters`})]}),(0,V.jsxs)(`div`,{className:`tiles`,children:[(0,V.jsx)(tb,{label:`Tokens`,value:Wy(p.tokens),sub:`${Wy(p.output)} output`}),(0,V.jsx)(tb,{label:`API-equivalent cost`,value:Gy(p.cost),sub:`not what a plan charges`}),(0,V.jsx)(tb,{label:`Model calls`,value:p.calls.toLocaleString(),sub:`${p.sessions} session${p.sessions===1?``:`s`}`}),(0,V.jsx)(tb,{label:`Cache read share`,value:p.tokens?Ky(p.cacheRead/p.tokens):`—`,sub:`higher is cheaper`}),(0,V.jsx)(tb,{label:`In subagents`,value:p.tokens?Ky(p.subagentTokens/p.tokens):`—`})]}),(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsxs)(`div`,{className:`viz-card-head`,children:[(0,V.jsx)(`h3`,{children:`Daily tokens`}),(0,V.jsx)(`div`,{className:`seg-control`,role:`group`,"aria-label":`Split by`,children:[`model`,`project`,`trigger`].map(e=>(0,V.jsx)(`button`,{className:s===e?`on`:``,onClick:()=>c(e),children:e===`trigger`?`started by`:`by ${e}`},e))})]}),(0,V.jsx)(Qy,{items:m}),(0,V.jsx)(eb,{columns:h,series:m})]}),(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsx)(`h3`,{children:`Project × model`}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`matrix`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Project`}),r.models.map(e=>(0,V.jsxs)(`th`,{className:`num`,children:[(0,V.jsx)(`span`,{className:`viz-swatch`,style:{background:d.model(e)}}),` `,e]},e)),(0,V.jsx)(`th`,{className:`num`,children:`Total`}),(0,V.jsx)(`th`,{className:`num`,children:`Cost`}),(0,V.jsx)(`th`,{className:`num`,title:`Share of tokens used by subagents`,children:`Sub`})]})}),(0,V.jsx)(`tbody`,{children:r.matrix.map(e=>(0,V.jsxs)(v.Fragment,{children:[(0,V.jsxs)(`tr`,{className:`matrix-row`,children:[(0,V.jsxs)(`td`,{children:[e.roles.length>1&&(0,V.jsx)(`button`,{className:`caret`,"aria-label":`Show roles`,onClick:()=>u(t=>({...t,[e.project]:!t[e.project]})),children:l[e.project]?`▾`:`▸`}),(0,V.jsx)(`button`,{className:`link`,onClick:()=>f({project:e.project}),children:S(e.project)})]}),r.models.map(t=>(0,V.jsx)(`td`,{className:`num`,children:e.byModel[t]?Wy(e.byModel[t]):``},t)),(0,V.jsx)(`td`,{className:`num strong`,children:Wy(e.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:Gy(e.cost)}),(0,V.jsx)(`td`,{className:`num muted`,children:e.subagentShare?Ky(e.subagentShare):``})]}),l[e.project]&&e.roles.map(e=>(0,V.jsxs)(`tr`,{className:`matrix-sub`,children:[(0,V.jsxs)(`td`,{children:[`↳ `,e.role===`manager`?`managers`:`sessions`]}),r.models.map(t=>(0,V.jsx)(`td`,{className:`num`,children:e.byModel[t]?Wy(e.byModel[t]):``},t)),(0,V.jsx)(`td`,{className:`num`,children:Wy(e.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:Gy(e.cost)}),(0,V.jsx)(`td`,{className:`num muted`,children:e.subagentShare?Ky(e.subagentShare):``})]},e.role))]},e.project))})]})})]}),(0,V.jsxs)(`section`,{className:`card viz-card`,children:[(0,V.jsx)(`h3`,{children:`Recent sessions`}),(0,V.jsx)(`div`,{className:`table-scroll`,children:(0,V.jsxs)(`table`,{className:`plain`,children:[(0,V.jsx)(`thead`,{children:(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`th`,{children:`Last call`}),(0,V.jsx)(`th`,{children:`Session`}),(0,V.jsx)(`th`,{children:`Project`}),(0,V.jsx)(`th`,{children:`Branch`}),(0,V.jsx)(`th`,{children:`Models`}),(0,V.jsx)(`th`,{className:`num`,children:`Calls`}),(0,V.jsx)(`th`,{className:`num`,children:`Tokens`}),(0,V.jsx)(`th`,{className:`num`,children:`Cost`}),(0,V.jsx)(`th`,{className:`num`,children:`Sub`})]})}),(0,V.jsx)(`tbody`,{children:r.recent.map(t=>(0,V.jsxs)(`tr`,{children:[(0,V.jsx)(`td`,{className:`nowrap`,children:Eg(t.lastAt)}),(0,V.jsx)(`td`,{children:(0,V.jsxs)(`button`,{className:`link`,onClick:()=>e(t.sessionId),children:[t.role===`manager`?`Manager · `:``,t.title]})}),(0,V.jsx)(`td`,{children:S(t.project)}),(0,V.jsx)(`td`,{className:`muted`,children:t.branch??``}),(0,V.jsx)(`td`,{className:`muted`,children:t.models.join(`, `)}),(0,V.jsx)(`td`,{className:`num`,children:t.calls}),(0,V.jsx)(`td`,{className:`num`,children:Wy(t.tokens)}),(0,V.jsx)(`td`,{className:`num`,children:Gy(t.cost)}),(0,V.jsx)(`td`,{className:`num muted`,children:t.subagentShare?Ky(t.subagentShare):``})]},t.sessionId))})]})})]}),(0,V.jsx)(Bw,{})]})}function ST(e){try{return sm(localStorage.getItem(`ledung.sidebar.${e}`))}catch{return null}}function CT(e,t){try{t==null?localStorage.removeItem(`ledung.sidebar.${e}`):localStorage.setItem(`ledung.sidebar.${e}`,String(t))}catch{}}function wT(){let[e,t]=(0,v.useState)(()=>window.matchMedia(im).matches),[n,r]=(0,v.useState)({w:window.innerWidth,h:window.innerHeight}),[i,a]=(0,v.useState)(()=>({width:ST(`width`),height:ST(`height`)})),o=e?`height`:`width`;(0,v.useEffect)(()=>{let e=window.matchMedia(im),n=()=>{t(e.matches),r({w:window.innerWidth,h:window.innerHeight})};return e.addEventListener(`change`,n),window.addEventListener(`resize`,n),()=>{e.removeEventListener(`change`,n),window.removeEventListener(`resize`,n)}},[]);let{min:s,max:c,def:l}=am(o,e?n.h:n.w),u=om(i[o]??l,s,c);(0,v.useEffect)(()=>{document.querySelector(`.app`)?.style.setProperty(e?`--sidebar-h`:`--sidebar-w`,`${u}px`)},[u,e]);let d=e=>{CT(o,e),a(t=>({...t,[o]:e}))};return(0,V.jsx)(`div`,{className:`sidebar-resizer ${e?`horizontal`:`vertical`}`,role:`separator`,"aria-label":`Resize the sidebar`,"aria-orientation":e?`horizontal`:`vertical`,"aria-valuenow":u,"aria-valuemin":s,"aria-valuemax":c,tabIndex:0,title:`Drag to resize, double-click to reset`,onPointerDown:e=>{e.button===0&&(e.currentTarget.setPointerCapture(e.pointerId),e.preventDefault())},onPointerMove:t=>{if(!t.currentTarget.hasPointerCapture(t.pointerId))return;let n=t.currentTarget.parentElement.getBoundingClientRect();d(om(e?t.clientY-n.top:t.clientX-n.left,s,c))},onDoubleClick:()=>d(null),onKeyDown:e=>{let t=cm(e.key,o,u,s,c);t!=null&&(e.preventDefault(),d(t))}})}var TT=`ledung.composer.height`,ET=.75;function DT(e,t,n,r,i,a){return Math.ceil(Math.max(e,t*n+r+i,a))}function OT(e,t,n){return{min:e,max:Math.max(e,Math.floor(t*ET-n))}}function kT(e,t,n,r,i){return om(e+(t-n),r,i)}function AT(e,t,n,r){return e===`ArrowUp`?om(t+20,n,r):e===`ArrowDown`?om(t-20,n,r):e===`Home`?n:e===`End`?r:null}function jT(e){try{return sm(e.getItem(TT))}catch{return null}}function MT(e,t){try{t==null?e.removeItem(TT):e.setItem(TT,String(t))}catch{}}function NT(){try{return localStorage}catch{return null}}function PT(){let e=(0,v.useRef)(null),t=(0,v.useRef)(null),[n,r]=(0,v.useState)(()=>{let e=NT();return e?jT(e):null}),[i,a]=(0,v.useState)(null),o=(0,v.useCallback)(()=>{let n=e.current,r=t.current,i=n?.parentElement;if(!n||!r||!i)return null;let a=getComputedStyle(n),o=parseFloat(a.paddingTop)+parseFloat(a.paddingBottom)+parseFloat(a.borderTopWidth)+parseFloat(a.borderBottomWidth),s=getComputedStyle(r),c=parseFloat(s.lineHeight)||parseFloat(s.fontSize)*1.2,l=n.querySelector(`.composer-buttons`)?.offsetHeight??0;return OT(DT(parseFloat(s.minHeight)||0,c,r.rows,parseFloat(s.paddingTop)+parseFloat(s.paddingBottom),parseFloat(s.borderTopWidth)+parseFloat(s.borderBottomWidth),l),i.clientHeight,o)},[]);(0,v.useLayoutEffect)(()=>{let t=e.current?.parentElement;if(!t)return;let n=()=>a(o());n();let r=new ResizeObserver(n);return r.observe(t),()=>r.disconnect()},[o]);let s=n==null?null:i?om(n,i.min,i.max):n,c=e=>{let t=NT();t&&MT(t,e),r(e)},l=(0,v.useRef)(null),u=e=>{e.button===0&&t.current&&(e.currentTarget.setPointerCapture(e.pointerId),e.preventDefault(),l.current={y:e.clientY,h:t.current.offsetHeight},a(o()))},d=e=>{let t=l.current;t&&i&&e.currentTarget.hasPointerCapture(e.pointerId)&&c(kT(t.h,t.y,e.clientY,i.min,i.max))},f=()=>{l.current=null},p=(0,V.jsx)(`div`,{className:`composer-grip`,role:`separator`,"aria-label":`Resize the message box`,"aria-orientation":`horizontal`,"aria-valuenow":s??void 0,"aria-valuemin":i?.min,"aria-valuemax":i?.max,tabIndex:0,title:`Drag up to make the message box taller, double-click to reset`,onPointerDown:u,onPointerMove:d,onPointerUp:f,onPointerCancel:f,onDoubleClick:()=>c(null),onKeyDown:e=>{let n=o();if(!n||!t.current)return;let r=AT(e.key,t.current.offsetHeight,n.min,n.max);r!=null&&(e.preventDefault(),c(r))}});return{box:e,area:t,style:s==null?void 0:{height:s},grip:p}}function FT(e,t){let n=new Set(e.map(e=>e.id)),r=t.filter(e=>!n.has(e.id));return r.length?[...e,...r].sort((e,t)=>e.id-t.id):e}async function IT(e,t){let n=[];for(let r=e;;){let e=await t(r);n.push(...e);let i=e.at(-1)?.id??r;if(e.length<500||i<=r)return n;r=i}}function LT(e){let[t,n]=(0,v.useState)(`connecting`),[r,i]=(0,v.useState)(!1),[a,o]=(0,v.useState)([]),[s,c]=(0,v.useState)([]),[l,u]=(0,v.useState)({}),[d,f]=(0,v.useState)([]),[p,m]=(0,v.useState)(!1),[h,g]=(0,v.useState)(!1),[_,y]=(0,v.useState)(0),[b,x]=(0,v.useState)(!1),[S,C]=(0,v.useState)(`you`),[w,T]=(0,v.useState)(null),[E,D]=(0,v.useState)({}),[O,k]=(0,v.useState)([]),[ee,A]=(0,v.useState)([]),[j,M]=(0,v.useState)([]),[te,N]=(0,v.useState)([]),[P,ne]=(0,v.useState)(null),[re,ie]=(0,v.useState)([]),[ae,oe]=(0,v.useState)([]),[se,ce]=(0,v.useState)(null),[le,ue]=(0,v.useState)(null),[de,fe]=(0,v.useState)(null),[pe,me]=(0,v.useState)([]),[he,F]=(0,v.useState)({chats:null,newProjects:null}),[I,ge]=(0,v.useState)([`full`]),[_e,ve]=(0,v.useState)(null),[ye,be]=(0,v.useState)(`Git Bash`),[xe,Se]=(0,v.useState)(null),[Ce,we]=(0,v.useState)(null),[Te,De]=(0,v.useState)([]),[Oe,ke]=(0,v.useState)(null),[Me,Ne]=(0,v.useState)(null),[Pe,L]=(0,v.useState)([]),[Fe,Ie]=(0,v.useState)([]),[Le,Re]=(0,v.useState)([]),[ze,Be]=(0,v.useState)(!1),[Ve,He]=(0,v.useState)(null),Ue=(0,v.useRef)(null),We=(0,v.useRef)(e);We.current=e;let Ge=(0,v.useRef)({sessionId:null,messages:[]});Ge.current.messages=d;let Ke=(0,v.useCallback)(async e=>{let t=await R.messages(e);We.current===e&&(Ge.current={sessionId:e,messages:t},f(t),m(t.length>=500))},[]),qe=(0,v.useCallback)(async e=>{let t=Ge.current,n=t.messages.at(-1);if(t.sessionId!==e||!n)return Ke(e);let r=await IT(n.id,t=>R.messagesAfter(e,t));We.current===e&&f(e=>FT(e,r))},[Ke]),Je=(0,v.useCallback)(async()=>{let e=We.current,t=d[0];if(!e||!t)return;let n=await R.messages(e,t.id);We.current===e&&(f(e=>[...n,...e]),m(n.length>=500))},[d]);return(0,v.useEffect)(()=>{Ge.current={sessionId:null,messages:[]},f([]),m(!1),e&&Ke(e).catch(()=>{})},[e,Ke]),(0,v.useEffect)(()=>{let e=null,t=500,r=!1,a,s=()=>{n(`connecting`),e=je(`${location.protocol===`https:`?`wss`:`ws`}://${location.host}/ws`),e.onopen=()=>{t=500,n(`open`)},e.onclose=()=>{n(`closed`),r||(a=setTimeout(s,t=Math.min(t*2,1e4)))},e.onmessage=e=>{let t=JSON.parse(e.data);switch(t.type){case`hello`:Ue.current===null?Ue.current=t.build:Ue.current!==t.build&&x(!0),Ee(t.pageKey??null),y(e=>e+1),i(!0),g(t.canRestart),C(t.userName),T(t.source??null),D(Object.fromEntries(t.questions.map(e=>[e.id,e]))),k(t.limits),A(t.usageStops??[]),M(t.macros??[]),fe(t.away??null),o(t.sessions),c(t.projects),we(t.board??null),De(t.github??[]),ge(t.profiles??[`full`]),ve(t.lockdownB??null),be(t.bangShell??`Git Bash`),ke(t.remote??null),Ne(t.chats??null),L(t.computers??[]),Ie(t.newComputers??[]),Re(t.linkPairings??[]),Be(t.throughPublicName??!1),He(t.config??null),u(Object.fromEntries(t.permissions.map(e=>[e.id,e]))),We.current&&qe(We.current).catch(()=>{}),R.machine().then(ue,()=>{}),R.accounts().then(e=>{me(e.accounts),Se(e.defaultIdentity),F(e.choices),N(e.signedOut??[]),ne(e.claudeProblem??null),ie(e.claudeLooked??[]),oe(e.configFileProblems??[])},()=>{});break;case`session`:o(e=>e.findIndex(e=>e.id===t.session.id)===-1?[t.session,...e]:e.map(e=>e.id===t.session.id?t.session:e));break;case`limits`:k(t.limits);break;case`macros`:M(t.macros);break;case`usageStops`:A(t.usageStops);break;case`config`:He(t.config);break;case`projects`:c(t.projects);break;case`accounts`:me(t.accounts),Se(t.defaultIdentity),F(t.choices),N(t.signedOut??[]),ne(t.claudeProblem??null),ie(t.claudeLooked??[]),oe(t.configFileProblems??[]);break;case`board`:we(t.board);break;case`github`:De(t.github);break;case`remote`:ke(t.remote);break;case`newComputers`:Ie(t.computers);break;case`linkPairings`:Re(t.pairings);break;case`chats`:Ne(t.chats);break;case`computers`:L(t.computers);break;case`machine`:ue(t.machine);break;case`away`:fe(t.away);break;case`question`:D(e=>({...e,[t.question.id]:t.question}));break;case`permission`:u(e=>({...e,[t.permission.id]:t.permission}));break;case`message`:t.message.sessionId===We.current&&f(e=>e.some(e=>e.id===t.message.id)?e:[...e,t.message])}}};return s(),Ae(()=>{r||(clearTimeout(a),e&&(e.onopen=e.onclose=e.onmessage=null,e.close()),t=500,s())}),()=>{r=!0,Ae(null),clearTimeout(a),e?.close()}},[qe]),(0,v.useEffect)(()=>{let e=!0,t=()=>R.overview().then(t=>e&&ce(t),()=>{});t();let n=setInterval(t,2e4);return()=>{e=!1,clearInterval(n)}},[]),{connection:t,loaded:r,canRestart:h,hellos:_,updated:b,userName:S,source:w,questions:E,limits:O,usageStops:ee,macros:j,signedOut:te,claudeProblem:P,claudeLooked:re,accountProblems:ae,overview:se,machine:le,away:de,accounts:pe,accountChoices:he,defaultIdentity:xe,board:Ce,github:Te,remote:Oe,computers:Pe,newComputers:Fe,linkPairings:Le,throughPublicName:ze,configStatus:Ve,chats:Me,profiles:I,lockdownB:_e,bangShell:ye,sessions:a,projects:s,permissions:l,messages:d,hasEarlier:p,loadEarlier:Je}}var RT=(e,t=140)=>{let n=e.split(`
|
|
106
|
+
`).map(e=>e.trim()).find(Boolean)??``;return n.length>t?`${n.slice(0,t-1)}…`:n},zT=e=>typeof e==`string`?e:``;function BT(e){let t=e.input.questions;return RT(zT(Array.isArray(t)?t[0]?.question:void 0)||e.title||zT(e.input.command)||zT(e.input.file_path)||e.reason||``)}function VT(e,t,n){return[...e.filter(ny).map(e=>({id:`q${e.id}`,sessionId:e.sessionId,title:`Question from ${n(e.sessionId)}`,body:RT(e.question)})),...t.filter(ry).map(e=>{let t=BT(e);return{id:`p${e.id}`,sessionId:e.sessionId,title:e.toolName===`AskUserQuestion`?`Question from ${n(e.sessionId)}`:`Permission: ${e.toolName} in ${n(e.sessionId)}`,body:e.sensitive?`Sensitive${t?`: ${t}`:``}`:t}})]}var HT={five_hour:`5-hour`,seven_day:`weekly`};function UT(e){return e.filter(e=>e.holding).map(e=>({id:`stop:${e.account}:${e.kind}:${e.resetsAt??``}`,sessionId:`settings`,title:`Usage stop reached: ${HT[e.kind]??e.kind} ${e.percent}%`,body:`New turns${e.account==="default"?``:` on account ${e.account}`} are held until you lift it in Settings${e.resetsAt?` or the window resets`:``}.`}))}function WT(e,t){let n=new Set(t.map(e=>e.id));return e?{show:t.filter(t=>!e.has(t.id)),close:[...e].filter(e=>!n.has(e)),open:n}:{show:[],close:[],open:n}}var GT=()=>window.isSecureContext&&`Notification`in window,KT=`ledung.notify`,qT=()=>{try{return localStorage.getItem(KT)===`1`}catch{return!1}};function JT(e){let t=GT(),[n,r]=(0,v.useState)(qT),[i,a]=(0,v.useState)(t?Notification.permission:`default`),o=t&&n&&i===`granted`,s=(0,v.useRef)(null),c=(0,v.useRef)(new Map),l=(0,v.useRef)(e.onOpenSession);return l.current=e.onOpenSession,(0,v.useEffect)(()=>{if(!e.loaded)return;let t=WT(s.current,[...VT(e.questions,e.permissions,t=>e.sessions.find(e=>e.id===t)?.title??`a session`),...UT(e.usageStops)]);s.current=t.open;for(let e of t.close)c.current.get(e)?.close(),c.current.delete(e);if(!(!o||!document.hidden&&document.hasFocus()))for(let e of t.show)try{let t=new Notification(e.title,{body:e.body,tag:e.id});t.onclick=()=>{window.focus(),l.current(e.sessionId),t.close()},t.onclose=()=>{c.current.get(e.id)===t&&c.current.delete(e.id)},c.current.set(e.id,t)}catch{}},[e.loaded,e.questions,e.permissions,e.sessions,e.usageStops,o]),{possible:t,on:o,denied:t&&i===`denied`,set:async e=>{if(!e){r(!1);try{localStorage.setItem(KT,`0`)}catch{}return}let t=Notification.permission===`granted`?`granted`:await Notification.requestPermission();a(t);let n=t===`granted`;r(n);try{localStorage.setItem(KT,n?`1`:`0`)}catch{}}}}function YT(e,t){return e.key!==`Enter`||e.isComposing?!1:t?e.ctrlKey||e.metaKey:!e.shiftKey}var XT=80;function ZT(e,t,n){if(Math.abs(n-1)>.01)return 0;let r=Math.round(e-t);return r>=XT?r:0}var QT=new Set([`button`,`checkbox`,`color`,`file`,`hidden`,`image`,`radio`,`range`,`reset`,`submit`]);function $T(e){if(!e)return!1;if(e.isContentEditable)return!0;let t=e.tagName.toUpperCase();return e.readOnly||e.disabled?!1:t===`TEXTAREA`||t===`INPUT`&&!QT.has((e.type??`text`).toLowerCase())}var eE=400;function tE(e){let t=e.visualViewport;if(!t)return;let n=e.document,r=n.documentElement,i=0,a=()=>{let a=$T(n.activeElement)?ZT(r.clientHeight,t.height,t.scale):0;a!==i&&(i=a,a?r.style.setProperty(`--kb`,`${a}px`):r.style.removeProperty(`--kb`)),a&&(e.scrollY>0||t.offsetTop>0)&&e.scrollTo(0,0)},o=()=>{e.setTimeout(a,0),e.setTimeout(a,eE)};t.addEventListener(`resize`,a),t.addEventListener(`scroll`,a),n.addEventListener(`focusin`,o),n.addEventListener(`focusout`,o),n.addEventListener(`visibilitychange`,o);for(let t of[`resize`,`orientationchange`,`focus`,`pageshow`])e.addEventListener(t,o);a()}var nE=(0,V.jsxs)(`svg`,{viewBox:`0 0 16 16`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.6`,"aria-hidden":`true`,children:[(0,V.jsx)(`circle`,{cx:`8`,cy:`8`,r:`6.5`}),(0,V.jsx)(`path`,{d:`M1.5 8h13M8 1.5c2 2 2.6 4 2.6 6.5S10 12.5 8 14.5M8 1.5C6 3.5 5.4 5.5 5.4 8S6 12.5 8 14.5`})]});function rE(e){return(0,V.jsxs)(V.Fragment,{children:[nE,`Remote`,e&&(0,V.jsxs)(`span`,{className:`long`,children:[`\xA0`,`· `,e]})]})}function iE({frame:e,shown:t=null,onShow:n,waiting:r=0}){let{tabs:i,remote:a,here:o}=e;return i?(0,V.jsxs)(`nav`,{className:`ctabs`,"aria-label":`Computers`,children:[i.map(e=>{let i=Ut(e,t,r),a=i?(0,V.jsx)(`span`,{className:`badge`,title:`${i} waiting for you on ${e.name}`,"aria-label":`${i} waiting for you`,children:i}):null,o=(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(`span`,{className:`sw`,"aria-hidden":`true`}),(0,V.jsx)(`span`,{className:`nm`,children:e.name}),a]}),s=e.here?t===null:t===e.id;return e.here?s||!n?(0,V.jsx)(`span`,{className:`ctab on`,style:Bt(e),"aria-current":`page`,children:o},e.id):(0,V.jsx)(`button`,{type:`button`,className:`ctab`,style:Bt(e),onClick:()=>n(null),children:o},e.id):e.url?(0,V.jsx)(`a`,{className:`ctab${s?` on`:``}`,style:Bt(e),href:e.url,target:`_blank`,rel:`noopener noreferrer`,title:`${e.name}'s Ledung, ${new URL(e.url).host}`,"aria-current":s?`page`:void 0,onClick:t=>{n&&Ht(t)&&(t.preventDefault(),n(e.id))},children:o},e.id):null}),(0,V.jsx)(`span`,{className:`spacer`}),a&&(0,V.jsx)(`span`,{className:`remote-tag`,role:`status`,children:rE(o?.name)})]}):a?(0,V.jsx)(`div`,{className:`remote-band`,role:`status`,children:rE(o?.name)}):null}function aE({computers:e,opened:t,shown:n,throughPublicName:r=!1,framed:i=!1}){let[a,o]=(0,v.useState)({}),[s,c]=(0,v.useState)({}),l=(0,v.useRef)({}),u=(0,v.useRef)({}),d=e.filter(e=>!e.here&&e.url&&t.includes(e.id));(0,v.useEffect)(()=>{let e=e=>{for(let t of d)tn({data:e.data,origin:e.origin,fromFrame:e.source===l.current[t.id]?.contentWindow},{id:t.id,url:t.url},localStorage,t=>e.source.postMessage(t,e.origin))&&(clearTimeout(u.current[t.id]),c(e=>({...e,[t.id]:`paired`})))};return window.addEventListener(`message`,e),()=>window.removeEventListener(`message`,e)}),(0,v.useEffect)(()=>()=>Object.values(u.current).forEach(clearTimeout),[]);let f=e=>{clearTimeout(u.current[e.id]),c(t=>({...t,[e.id]:`unknown`})),l.current[e.id]?.contentWindow?.postMessage(Ft(),new URL(e.url).origin),u.current[e.id]=setTimeout(()=>c(t=>({...t,[e.id]:`not-paired`})),jt)};return d.length?(0,V.jsx)(V.Fragment,{children:d.map(e=>(0,V.jsxs)(`div`,{className:`cframe-box`,hidden:n!==e.id,children:[Pt(e,r,i,s[e.id]??`unknown`)&&!a[e.id]&&(0,V.jsx)(oE,{computer:e,onCode:t=>o(n=>({...n,[e.id]:t}))}),a[e.id]?(0,V.jsx)(`iframe`,{className:`cframe`,style:Bt(e),src:a[e.id],title:`${e.name}'s Ledung`,allow:`publickey-credentials-get; publickey-credentials-create`},`pairing`):(0,V.jsx)(`iframe`,{className:`cframe`,style:Bt(e),src:e.url,title:`${e.name}'s Ledung`,allow:`publickey-credentials-get; publickey-credentials-create`,ref:t=>{l.current[e.id]=t},onLoad:()=>f(e)},`page`)]},e.id))}):null}function oE({computer:e,onCode:t}){let[n,r]=(0,v.useState)(`offer`),[i,a]=(0,v.useState)(null);return(0,V.jsxs)(`div`,{className:`cframe-bar`,style:Bt(e),role:n===`offer`?void 0:`alertdialog`,"aria-label":`Pair through the link with ${e.name}`,children:[n===`offer`?(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`span`,{children:[`Not paired with `,e.name,` in this tab? It is linked with this computer.`]}),(0,V.jsx)(`button`,{type:`button`,className:`small`,onClick:()=>r(`confirm`),children:`Pair through the link`})]}):(0,V.jsxs)(V.Fragment,{children:[(0,V.jsxs)(`span`,{children:[`Pair this browser with `,(0,V.jsx)(`b`,{children:e.name}),` through the link? It can then look at `,e.name,`'s sessions, and change nothing until it sets up its passkey and logs on there with Touch ID or Windows Hello. `,e.name,` shows the pairing.`]}),(0,V.jsx)(`button`,{type:`button`,className:`small`,disabled:n===`busy`,onClick:()=>{r(`busy`),a(null),R.linkDevicePair(e.id).then(({url:e})=>t(e),e=>{a(e.message),r(`offer`)})},children:n===`busy`?`Pairing…`:`Pair`}),(0,V.jsx)(`button`,{type:`button`,className:`small`,disabled:n===`busy`,onClick:()=>r(`offer`),children:`Cancel`})]}),i&&(0,V.jsx)(`span`,{className:`restart-problem`,children:i})]})}function sE(e,t){(0,v.useEffect)(()=>{if(t)return;let n=()=>{let t=zt(location.hash);t&&(history.replaceState(history.state,``,location.pathname+location.search),e(t))};return n(),window.addEventListener(`hashchange`,n),()=>window.removeEventListener(`hashchange`,n)},[])}var cE=`Removed projects`;function lE(e,t,n){return t===cE?!n.has(e.project)&&e.project!==`~chats`:e.project===t}var uE=Vt();uE&&window.addEventListener(`message`,e=>{let t=It(e.data,e.source===window.parent);t&&window.parent.postMessage(t,e.origin)});var dE={default:`Ask`,acceptEdits:`Accept edits`,auto:`Auto`,plan:`Plan`},fE={default:`Every action that needs permission asks you.`,acceptEdits:`File edits go through; commands still ask you.`,auto:`Routine actions are approved automatically; you are asked about the rest.`,plan:`Read-only: Claude plans but changes nothing.`},pE=[`waiting`,`usage`,`overview`,`board`,`settings`,`add`,`accounts`,`chat`,`chats`],mE=e=>!!e&&!pE.includes(e)&&!e.includes(`:`);function hE(){let e=location.hash.match(/^#\/waiting\/q\/(\d+)$/);if(e)return`q:${e[1]}`;let t=TC(location.hash);if(t)return SC(t.repo,t.id);let n=location.hash.match(/^#\/(waiting|usage|overview|board|settings|add|accounts|chat|chats)$/);if(n)return n[1];let r=location.hash.match(/^#\/(settings|chats)\/([a-z]+)$/);if(r)return`${r[1]}:${r[2]}`;let i=location.hash.match(/^#\/ps\/([^/]+)\/([a-z]+)$/);if(i)return`ps:${decodeURIComponent(i[1])}/${i[2]}`;let a=location.hash.match(/^#\/(p|ps|a)\/(.+)$/);return a?`${a[1]}:${decodeURIComponent(a[2])}`:(bg(location.hash)??Sg(location.hash))?.sessionId??null}function gE(e){if(!e)return``;if(pE.includes(e))return`#/${e}`;let t=CC(e);if(t)return wC(t.repo,t.id);if(e.startsWith(`q:`))return`#/waiting/q/${e.slice(2)}`;if(e.startsWith(`settings:`))return`#/settings/${e.slice(9)}`;if(e.startsWith(`chats:`))return`#/chats/${e.slice(6)}`;let n=wp(e);if(n?.project!=null&&n.group)return`#/ps/${encodeURIComponent(n.project)}/${n.group}`;let r=e.match(/^(p|ps|a):(.+)$/);return r?`#/${r[1]}/${encodeURIComponent(r[2])}`:`#/s/${e}`}var _E=()=>history.state??{},vE=()=>Number(_E().ledungDesk??0),yE=()=>_E().ledungDeskRoot===!0;function bE(e){Kh(e)&&_E().ledungDesk===void 0&&history.replaceState({..._E(),ledungDesk:0,ledungDeskRoot:!0},``)}function xE(){let e=history.state??{};return{depth:Number(e.ledungSettings??0),root:e.ledungSettingsRoot===!0}}function SE(e){mw(e)&&(history.state??{}).ledungSettings===void 0&&history.replaceState({...history.state??{},ledungSettings:1,ledungSettingsRoot:!0},``)}var CE=`ledung.waitingSidebar`;function wE(e){try{return localStorage.getItem(`ledung.technical.${e}`)===`1`}catch{return!1}}function TE(){let[e,t]=(0,v.useState)(hE()),[n,r]=(0,v.useState)(location.hash),i=LT(mE(e)?e:null),[a,o]=(0,v.useState)(null),[s,c]=(0,v.useState)(null),[l,u]=(0,v.useState)([]);sE(e=>{c(e),u(t=>t.includes(e)?t:[...t,e])},uE),(0,v.useEffect)(()=>{bE(hE()),SE(hE());let e=()=>{bE(hE()),SE(hE()),t(hE()),r(location.hash)};return window.addEventListener(`hashchange`,e),()=>window.removeEventListener(`hashchange`,e)},[]);let d=n=>{let i=gE(n);if(i!==location.hash){let t=qh(e,{depth:vE(),root:yE()},n),r=hw(e,xE(),n);location.hash=i,history.replaceState({...history.state??{},ledungDesk:t.depth,ledungDeskRoot:t.root,ledungSettings:r.depth,ledungSettingsRoot:r.root,ledungFromList:e===null},``)}t(n),r(location.hash)},f=e=>{history.replaceState(history.state,``,gE(e)),t(e),r(location.hash)},p=(n,a)=>{let o=i.questions[n];if(!o)return;let s=e===`waiting`?`queue`:e?.startsWith(`q:`)?i.questions[Number(e.slice(2))]?.shots?`shots`:`question`:void 0,c=a??vg(o);location.hash=yg(c,n),history.replaceState({...history.state??{},ledungDesk:0,ledungDeskRoot:!1,ledungFrom:s},``),t(c),r(location.hash)},m=(n,a)=>{let o=e===`waiting`?`queue`:e?.startsWith(`q:`)?i.questions[Number(e.slice(2))]?.shots?`shots`:`question`:void 0;location.hash=xg(n,a),history.replaceState({...history.state??{},ledungDesk:0,ledungDeskRoot:!1,ledungFrom:o},``),t(n),r(location.hash)},h=()=>{let e=vE();e>0&&!yE()?history.go(-e):d(bw(window.matchMedia(im).matches))},g=()=>{`back`in yw(history.state)?history.back():d(null)},_=()=>{`back`in Jh(vE())?history.back():d(`waiting`)},y=()=>{let e=gw(xE());`back`in e?history.go(-e.back):d(null)},b=mw(e),x=(0,v.useRef)(y);x.current=y,(0,v.useEffect)(()=>{if(!b)return;let e=e=>{_w(e)&&(e.preventDefault(),x.current())};return document.addEventListener(`keydown`,e),()=>document.removeEventListener(`keydown`,e)},[b]),(0,v.useEffect)(()=>{let e=e=>{if(e.button!==3&&e.button!==4)return;let t=location.href,n=e.button===3;setTimeout(()=>{location.href===t&&(n?history.back():history.forward())},100)};return window.addEventListener(`mouseup`,e),()=>window.removeEventListener(`mouseup`,e)},[]);let[C,w]=(0,v.useState)(()=>{try{return localStorage.getItem(CE)===`hidden`}catch{return!1}}),T=()=>{w(!C);try{localStorage.setItem(CE,C?`shown`:`hidden`)}catch{}},E=Kh(e)&&C,D=(0,v.useMemo)(()=>Object.values(i.questions).sort((e,t)=>t.id-e.id),[i.questions]),O=(0,v.useMemo)(()=>Object.values(i.permissions),[i.permissions]),k=iy(D,O)+i.newComputers.length+i.linkPairings.length,ee=lS(),A=JT({loaded:i.loaded,questions:D,permissions:O,sessions:i.sessions,usageStops:i.usageStops,onOpenSession:d});(0,v.useEffect)(()=>{document.title=k?`(${k}) Project Ledung`:`Project Ledung`},[k]);let j=(0,v.useMemo)(()=>{let e={};for(let t of O)t.status===`pending`&&(e[t.sessionId]=(e[t.sessionId]??0)+1);for(let t of D)t.status===`open`&&(e[t.sessionId]=(e[t.sessionId]??0)+1);return e},[O,D]),M=i.sessions.find(t=>t.id===e)??null,te=Op(e),N=te?.startsWith(`ps:`)?i.projects.find(e=>e.name===te.slice(3)):void 0,P=te===`ledung`?t=>(0,V.jsx)(nC,{view:e,update:t,run:oe,board:i.board,remote:i.remote,throughPublicName:i.throughPublicName,newComputers:i.newComputers,projects:i.projects,computers:i.computers,sessions:i.sessions,accounts:i.accounts,accountChoices:i.accountChoices,defaultIdentity:i.defaultIdentity,accountProblems:i.accountProblems,usageStops:i.usageStops,macros:i.macros,canRestart:i.canRestart,source:i.source,config:i.configStatus,hellos:i.hellos,notify:A,onOpen:d}):te===`add`?()=>(0,V.jsx)(qm,{run:oe,accounts:i.accounts,defaultAccount:i.accountChoices.newProjects,profiles:i.profiles,lockdownB:i.lockdownB,onAdded:e=>d(e.managerId??`p:${e.name}`)}):te===`chats`?()=>(0,V.jsx)(Qm,{view:e,chats:i.chats,run:oe,onOpen:d}):N?()=>(0,V.jsx)(Jm,{view:e,board:i.board,projects:i.projects,project:N,run:oe,accounts:i.accounts,profiles:N.profileNames??i.profiles,lockdownB:i.lockdownB,onOpen:d,onRemoved:()=>d(null),onRenamed:f},N.name):null,[ne,re]=(0,v.useState)(()=>{try{return localStorage.getItem(`ledung.limitAccount`)}catch{return null}}),ie=Ry(e,i.sessions,i.projects,ne),ae=ie.account;(0,v.useEffect)(()=>{if(ie.remember&&ie.account!==ne){re(ie.account);try{localStorage.setItem(`ledung.limitAccount`,ie.account)}catch{}}},[ie.remember,ie.account,ne]);let oe=async e=>{o(null);try{await e()}catch(e){o(e.message)}},se=(0,V.jsxs)(V.Fragment,{children:[i.updated&&(0,V.jsxs)(`div`,{className:`banner updated`,children:[(0,V.jsx)(`span`,{children:`Ledung was updated — reload`}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>location.reload(),children:`Reload`})]}),i.away&&gb(i.away,M)&&(0,V.jsx)(pb,{away:i.away,run:oe}),ee.notice&&(0,V.jsx)(dS,{app:ee,run:oe}),(0,V.jsx)(ES,{run:oe}),i.usageStops.filter(e=>e.holding).map(e=>(0,V.jsxs)(`div`,{className:`banner updated`,children:[(0,V.jsx)(`span`,{children:ky(e)}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void oe(()=>R.liftUsageStop(e.account,e.kind)),children:`Lift`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>d(bp(`usageStop`)),children:`Settings`})]},`${e.account}:${e.kind}`)),i.claudeProblem&&(0,V.jsxs)(`div`,{className:`banner updated signin`,role:`alert`,children:[(0,V.jsx)(`span`,{children:(0,V.jsx)(Eb,{text:i.claudeProblem})}),(0,V.jsx)(Tb,{check:async()=>!!(await R.checkSignIn()).claudeProblem}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>d(bp(`claudeProblem`)),children:`Settings`}),i.claudeLooked.length>0&&(0,V.jsx)(Db,{looked:i.claudeLooked})]}),i.configStatus?.problem&&(0,V.jsxs)(`div`,{className:`banner updated signin`,role:`alert`,children:[(0,V.jsxs)(`span`,{children:[`The config file was changed but not applied: `,i.configStatus.problem]}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>d(bp(`configProblem`)),children:`Settings`})]}),i.signedOut.map(e=>(0,V.jsxs)(`div`,{className:`banner updated signin`,children:[(0,V.jsx)(`span`,{children:e.help.split("`").map((e,t)=>t%2?(0,V.jsx)(`code`,{children:e},t):e)}),(0,V.jsx)(Tb,{check:async()=>!!(await R.checkSignIn()).signedOut?.some(t=>t.account===e.account)}),e.account!=="default"&&(0,V.jsx)(`button`,{className:`small`,onClick:()=>d(`settings:claude`),children:`Accounts`})]},`signin:${e.account}`)),a&&(0,V.jsxs)(`div`,{className:`banner error`,onClick:()=>o(null),children:[a,` `,(0,V.jsx)(`span`,{className:`muted`,children:`(click to dismiss)`})]})]}),ce=At(i.computers,i.throughPublicName,uE),le=Rt(i.computers,s);return(0,V.jsxs)(`div`,{className:`page${ce.remote?` remote`:``}`,style:Bt(ce.here),children:[(0,V.jsx)(iE,{frame:ce,shown:le,onShow:e=>{c(e),e&&!l.includes(e)&&u(t=>[...t,e])},waiting:k}),(0,V.jsx)(aE,{computers:i.computers,opened:l,shown:le,throughPublicName:i.throughPublicName,framed:uE}),(0,V.jsxs)(`div`,{className:`app ${vw(e)}${E?` no-sidebar`:``}`,hidden:le!==null,children:[e===null&&(0,V.jsx)(`div`,{className:`phone-banners`,children:se}),(0,V.jsx)(EE,{sessions:i.sessions,projects:i.projects,chats:i.chats,pending:j,waiting:k,limits:i.limits,usageStops:i.usageStops,github:i.github,stripAccount:ae,overview:i.overview,machine:i.machine,run:oe,openId:e,onOpen:d,onCloseSettings:y,profiles:i.profiles,onStart:(e,t)=>oe(async()=>d((await R.start(e,t)).id)),connection:i.connection,board:i.board}),!E&&(0,V.jsx)(wT,{}),(0,V.jsxs)(`main`,{className:`main`,children:[se,e!==null&&!M&&(0,V.jsx)(`div`,{className:`phone-bar`,children:(0,V.jsx)(`button`,{className:`phone-back`,onClick:g,children:`← List`})}),e===`usage`||e===`overview`?(0,V.jsx)(bT,{sessionsOpen:e===`overview`,onSessions:e=>d(e?`overview`:`usage`),sessions:i.sessions,overview:i.overview,machine:i.machine,waitingBySession:j,onOpenSession:d}):Kh(e)?(0,V.jsx)(sy,{questions:D,permissions:O,sessions:i.sessions,projects:i.projects,chats:i.chats,userName:i.userName,questionId:e?.startsWith(`q:`)?Number(e.slice(2)):null,onOpenQuestion:e=>d(e===null?`waiting`:`q:${e}`),onOpenSession:d,onGoToConversation:p,onGoToMessage:m,onClose:h,onLeaveShots:_,sidebarHidden:C,onToggleSidebar:T,newComputers:i.newComputers,linkPairings:i.linkPairings,run:oe}):e===`board`?(0,V.jsx)(IC,{board:i.board,onOpen:d,onOpenSettings:()=>d(`settings`)}):CC(e)?(0,V.jsx)(RC,{repo:CC(e).repo,id:CC(e).id,board:i.board,projects:i.projects,onOpen:d,onBack:()=>d(`board`)},e):P?(0,V.jsx)(Vp,{view:e,projects:i.projects,source:i.source,canRestart:i.canRestart,hellos:i.hellos,onOpen:d,children:P}):e===`chat`?(0,V.jsx)(Zm,{chats:i.chats,profiles:i.profiles,run:oe,onStarted:d}):e?.startsWith(`a:`)?(0,V.jsx)(cb,{title:S(e.slice(2)),sessions:i.sessions.filter(t=>t.archivedAt&&lE(t,e.slice(2),new Set(i.projects.map(e=>e.name)))),overview:i.overview,run:oe,onOpenSession:d},e):e?.startsWith(`p:`)&&i.projects.some(t=>t.name===e.slice(2))?(0,V.jsx)(Ym,{project:i.projects.find(t=>t.name===e.slice(2)),run:oe,onStarted:d},e):M?(0,V.jsx)(DE,{session:M,ledung:i,pendingCount:j[M.id]??0,run:oe,focusQuestion:bg(n)?.questionId??null,focusMessage:Sg(n)?.messageId??null,cameFrom:_E().ledungFrom??null,onOpenQuestion:e=>d(`q:${e}`),onOpenBoardThread:(e,t)=>d(SC(e,t)),onBack:g},M.id):(0,V.jsxs)(`div`,{className:`empty`,children:[(0,V.jsx)(`h1`,{children:`Project Ledung`}),(0,V.jsx)(`p`,{children:i.projects.length?`Open a project on the left to talk to its manager.`:`No projects yet. Add one to start talking to its manager.`}),(0,V.jsxs)(`div`,{className:`empty-actions`,children:[!i.projects.length&&(0,V.jsx)(`button`,{className:`primary`,onClick:()=>d(`add`),children:`Add a project`}),(0,V.jsx)(`button`,{onClick:()=>d(`chat`),children:`New chat`}),(0,V.jsx)(`button`,{onClick:()=>d(`settings`),children:`Settings`})]})]})]})]})]})}function EE(e){let t=e.sessions.filter(e=>!e.archivedAt),n=e=>t.filter(t=>t.parentId===e).sort(UC),r=new Set(e.projects.map(e=>e.name)),i=(e,t,r)=>[{s:e,depth:0,drag:t},...n(e.id).map(t=>({s:t,depth:1,drag:r?`c:${e.id}`:null}))],a=(e,n,r)=>{let a=new Set(t.filter(e).map(e=>e.id)),o=n?t.find(e=>e.id===n):void 0,s=t.filter(t=>e(t)&&t.id!==n&&(!t.parentId||!a.has(t.parentId))).sort(UC);return[...o?i(o,null,!!r):[],...s.flatMap(e=>i(e,r?`t:${r}`:null,!!r))]},o=[{name:x,project:null,rows:a(e=>e.project===x,null,x)},...e.projects.map(e=>({name:e.name,project:e,rows:a(t=>t.project===e.name,e.managerId,e.name)})),{name:cE,project:null,rows:a(e=>!r.has(e.project)&&e.project!==`~chats`,null,null)}].map(t=>({...t,archived:e.sessions.filter(e=>e.archivedAt&&lE(e,t.name,r)).length})).filter(e=>e.project||e.name===`~chats`||e.rows.length||e.archived),[s,c]=(0,v.useState)(()=>aw(localStorage)),[l,u]=(0,v.useState)(()=>sw(localStorage)),d=e=>c(t=>{let n=lw(t,e,e=>e===cE||e===`~chats`||r.has(e));return ow(localStorage,n),n}),f=e=>u(n=>{let r=lw(n,e,e=>t.some(t=>t.id===e));return cw(localStorage,r),r}),p=(e,t)=>e&&e.count>0&&(0,V.jsxs)(`span`,{className:`hidden-count${e.working?` working`:``}`,title:`${e.count} ${t} hidden${e.working?`, at least one working`:``}`,children:[e.working&&(0,V.jsx)(`span`,{className:`dot running`}),`+`,e.count]}),[m,h]=(0,v.useState)(null),[g,_]=(0,v.useState)(null),[y,b]=(0,v.useState)(``),S=(t,n)=>{if(n.length<=1)return e.onStart(t);b(``),h(m===t?null:t)},{nav:C,drag:w,handlers:T}=QC((t,n)=>void e.run(()=>t===`projects`?R.orderProjects(n):R.orderSessions(n))),E=e=>{if(!w||w.slot===null||w.group===`projects`)return null;let t=e.filter(e=>e.drag===w.group);return t.length?w.slot<t.length?{before:t[w.slot].s.id}:{after:w.group.startsWith(`t:`)?e[e.length-1].s.id:t[t.length-1].s.id}:null},D=o.filter(e=>e.project).map(e=>e.name),O=w?.group===`projects`&&w.slot!==null?w.slot<D.length?{before:D[w.slot]}:{after:D[D.length-1]}:null,k=(0,V.jsx)(`div`,{className:`drop-marker${w?.group.startsWith(`c:`)?` child`:``}`,"aria-hidden":`true`}),[ee]=kx(),[A]=Fx(),j=wt(A),[M]=Vx(),te=({s:t,depth:n,drag:r,hidden:i,folds:a,folded:o})=>{let s=`${Eg(t.createdAt)}${t.backgroundTasks>0?` · ${t.backgroundTasks} in background`:``}`,c=(()=>{let n=e.overview?.sessions[t.id]?.today??0,r=t.role===`manager`?e.sessions.filter(e=>e.parentId===t.id).reduce((t,n)=>t+(e.overview?.sessions[n.id]?.today??0),n):n,i=Uw(t),a=t.status===`ended`?void 0:e.machine?.sessions[t.id],o=e.machine?.line.indexOf(t.id)??-1;return[t.project===`~chats`&&t.workDir?`in ${t.workDir.split(/[\\/]/).filter(Boolean).pop()}`:``,o>=0?`number ${o+1} in line`:``,t.paused?`paused`:``,t.priority===`normal`?``:Fw[t.priority].toLowerCase(),a&&(a.cores>=.05||a.memBytes>0)?`${Mw(a.cores)} · ${Nw(a.memBytes)}`:``,r?`${Wy(r)}${t.role===`manager`&&r!==n?` team`:``} today`:``,i!=null&&t.status!==`ended`?`ctx ${Ky(i)}`:``,t.pr?qy(t.pr):t.branch??``].filter(Boolean).join(` · `)})();return(0,V.jsxs)(`div`,{className:`session-row`,children:[a&&(0,V.jsx)(`button`,{className:`fold-caret session-caret`,"aria-expanded":!o,"aria-label":`${o?`Unfold`:`Fold`} the sessions of ${t.title}`,title:o?`Show the sessions it runs`:`Fold the sessions it runs away`,onClick:()=>f(t.id),children:o?`▸`:`▾`}),g===t.id?(0,V.jsx)(`div`,{className:`session-item renaming${t.id===e.openId?` open`:``}${n?` child`:``}`,children:(0,V.jsx)(HC,{value:t.title,label:`New name for ${t.title}`,onDone:()=>_(null),onSave:n=>e.run(()=>R.rename(t.id,n))})}):(0,V.jsxs)(`button`,{className:`session-item${t.id===e.openId?` open`:``}${n?` child`:``}${w?.id===t.id?` dragging`:``}${mt(ee,t).ended?` ended-row`:``}`,title:Tt(A,mt(ee,t).tooltip,s,c),onClick:()=>e.onOpen(t.id),onDoubleClick:()=>_(t.id),"data-drag":r??void 0,"data-drag-id":r?t.id:void 0,children:[mt(ee,t).dot&&(0,V.jsx)(`span`,{className:`dot ${ut(t)}`,title:lt[t.status]}),(0,V.jsxs)(`span`,{className:`session-text`,children:[(0,V.jsxs)(`span`,{className:`session-title`,children:[t.role===`manager`&&(0,V.jsx)(`span`,{className:`chip`,children:`Manager`}),` `,(0,V.jsx)(fp,{colour:hp(t,Mv(e.projects,e.chats)),children:t.title})]}),j.time&&(0,V.jsx)(`span`,{className:`session-sub`,children:s}),j.usage&&c&&(0,V.jsx)(`span`,{className:`session-sub usage-line`,children:c})]}),(()=>{let n=j_(t,e.sessions);return n&&(0,V.jsx)(`span`,{className:`session-ship ${ut(t)}`,children:(0,V.jsx)(B_,{mode:n,width:10,sizeButton:!1,hideWhenSunk:!0,maxSize:j.shipMax})})})(),p(i,i?.count===1?`sub-session`:`sub-sessions`),(e.pending[t.id]??0)+(i?.pending??0)?(0,V.jsx)(`span`,{className:`badge`,children:(e.pending[t.id]??0)+(i?.pending??0)}):null]})]})},N=Fe(e.connection);return(0,V.jsxs)(`aside`,{className:`sidebar`,children:[(0,V.jsx)(ob,{account:e.stripAccount,limits:e.limits,stops:e.usageStops,run:e.run}),dw(e.github,Date.now()).map(e=>(0,V.jsx)(`div`,{className:`github-budget muted ${fw(e)}`,title:`What is left of the GitHub budget Ledung's pull request checks use (the worst of GitHub's readings). Under 20 % left they run every 10 minutes, under 5 % not until the reset.`,children:uw(e,e=>new Date(e).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`}))},`${e.container??``} ${e.host}`)),(0,V.jsx)(Lw,{machine:e.machine,sessions:e.sessions,onOpen:e.onOpen,run:e.run}),(0,V.jsxs)(`button`,{className:`waiting-entry${Kh(e.openId)?` open`:``}${e.waiting?` has-items`:``}`,onClick:()=>e.onOpen(`waiting`),children:[(0,V.jsx)(`span`,{children:`Waiting for you`}),e.waiting?(0,V.jsx)(`span`,{className:`badge`,children:e.waiting}):(0,V.jsx)(`span`,{className:`muted`,children:`nothing`})]}),(0,V.jsxs)(`nav`,{className:`session-list`,"data-compact":A>1?A:void 0,ref:C,...T,children:[!e.projects.length&&(0,V.jsx)(`p`,{className:`muted project-empty`,children:`No projects yet. Add one in Settings (⚙ below).`}),o.map(t=>({...t,isFolded:s.includes(t.name),view:nw(t.rows,{foldedSessions:l,folded:s.includes(t.name),openId:e.openId,pending:e.pending})})).map(t=>(0,V.jsxs)(v.Fragment,{children:[O?.before===t.name&&k,(0,V.jsx)(`div`,{className:`project-group${w?.group===`projects`&&w.id===t.name?` dragging`:``}`,children:(0,V.jsxs)($f,{level:qf(t.project),children:[(0,V.jsxs)(`div`,{className:`project-row`,children:[(0,V.jsx)(`button`,{className:`fold-caret`,"aria-expanded":!t.isFolded,"aria-label":`${t.isFolded?`Unfold`:`Fold`} ${t.name}`,title:t.isFolded?`Show its sessions`:`Fold its sessions away`,onClick:()=>d(t.name),children:t.isFolded?`▸`:`▾`}),t.project?(0,V.jsx)(`button`,{className:`project-name${e.openId===`p:${t.name}`||t.project.managerId&&e.openId===t.project.managerId?` open`:``}`,title:`${t.project.where}${t.project.managerId?``:` · manager not started yet`}`,onClick:()=>e.onOpen(t.project.managerId??`p:${t.name}`),"data-drag":`projects`,"data-drag-id":t.name,children:(()=>{let e=By(t.project.account),n=(0,V.jsx)(fp,{colour:t.project.colours.manager,children:t.name});return e?(0,V.jsxs)(`span`,{className:`project-name-stack`,children:[(0,V.jsx)(`span`,{className:`project-account`,title:`Runs on the Claude account ${e}`,children:e}),(0,V.jsx)(`span`,{className:`project-name-text`,children:n})]}):n})()}):t.name===`~chats`?(0,V.jsx)(`button`,{className:`project-name${e.openId===`chat`?` open`:``}`,title:`Sessions of your own with no project, workflow or manager`,onClick:()=>e.onOpen(`chat`),children:(0,V.jsx)(fp,{colour:e.chats?.colour??null,children:`Chats`})}):(0,V.jsx)(`span`,{className:`project-name muted`,children:t.name}),p(t.view.project,t.view.project?.count===1?`session`:`sessions`),t.view.project?.pending?(0,V.jsx)(`span`,{className:`badge`,children:t.view.project.pending}):null,t.name===`~chats`&&(0,V.jsxs)(`span`,{className:`project-actions`,children:[j.plusOnly?(0,V.jsx)(`button`,{className:`mini`,title:`New chat`,"aria-label":`New chat`,onClick:()=>e.onOpen(`chat`),children:`+`}):(0,V.jsx)(`button`,{className:`small`,title:`A Claude Code session of your own, with no project`,onClick:()=>e.onOpen(`chat`),children:`+ Chat`}),(0,V.jsx)(`button`,{className:`${j.plusOnly?`mini cog`:`small`}${Op(e.openId)===`chats`?` on`:``}`,title:`Chats settings`,"aria-label":`Settings of chats`,onClick:()=>e.onOpen(`chats`),children:`⚙`})]}),t.project&&(0,V.jsxs)(`span`,{className:`project-actions`,children:[j.plusOnly?(0,V.jsx)(`button`,{className:`mini`,title:`New session in ${t.name}`,"aria-label":`New session in ${t.name}`,onClick:()=>S(t.name,t.project?.profileNames??e.profiles),children:`+`}):(0,V.jsx)(`button`,{className:`small`,title:`A session of your own in this project, outside its manager`,onClick:()=>S(t.name,t.project?.profileNames??e.profiles),children:`+ Session`}),(0,V.jsx)(`button`,{className:`${j.plusOnly?`mini cog`:`small`}${Op(e.openId)===`ps:${t.name}`?` on`:``}`,title:`Project settings`,"aria-label":`Settings of ${t.name}`,onClick:()=>e.onOpen(`ps:${t.name}`),children:`⚙`})]})]}),t.project&&m===t.name&&(0,V.jsxs)(`div`,{className:`start-row`,children:[(0,V.jsxs)(`select`,{"aria-label":`Profile for a new session in ${t.name}`,value:y,onChange:e=>b(e.target.value),title:`Its session profile: what it gets of your own plugins, MCP servers, tools and settings`,children:[(0,V.jsx)(`option`,{value:``,children:t.project.profiles.session?`Project's: ${t.project.profiles.session}`:`Project's profile`}),(t.project.profileNames??e.profiles).map(e=>(0,V.jsx)(`option`,{value:e,children:e},e))]}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>{h(null),e.onStart(t.name,y||void 0)},children:`Start`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>h(null),children:`Cancel`})]}),(()=>{let e=E(t.view.rows);return t.view.rows.map(t=>(0,V.jsxs)(v.Fragment,{children:[e?.before===t.s.id&&k,te(t),e?.after===t.s.id&&k]},t.s.id))})(),vt(M,t.archived,t.isFolded)&&(0,V.jsxs)(`button`,{className:`archived-link${e.openId===`a:${t.name}`?` open`:``}`,onClick:()=>e.onOpen(`a:${t.name}`),children:[`Archived (`,t.archived,`)`]})]})}),O?.after===t.name&&k]},t.name))]}),(0,V.jsxs)(`div`,{className:`connection ${e.connection}`,children:[(0,V.jsx)(`button`,{className:`icon settings-cog${mw(e.openId)?` on`:``}`,title:mw(e.openId)?`Close settings (Esc)`:`Settings: accounts, restart Ledung, add a project`,"aria-label":mw(e.openId)?`Close settings`:`Settings`,"aria-pressed":mw(e.openId),onClick:()=>mw(e.openId)?e.onCloseSettings():e.onOpen(`settings`),children:`⚙`}),(0,V.jsxs)(`span`,{className:`footer-chips`,children:[(0,V.jsxs)(`button`,{className:`board-chip usage-chip${Ie(e.board)?``:` ${N.className}`}${e.openId===`usage`||e.openId===`overview`?` on`:``}`,title:`${Ie(e.board)?``:`${N.text} `}Usage: tokens per day, project and model, shared usage, and every live session`,"aria-pressed":e.openId===`usage`||e.openId===`overview`,onClick:()=>e.onOpen(`usage`),children:[`Usage`,e.overview?` · ${Wy(e.overview.todayTokens)} today`:``]}),(0,V.jsx)(yn,{board:e.board,open:e.openId===`board`||!!CC(e.openId),connection:N,onClick:()=>e.onOpen(`board`)})]})]})]})}function DE(e){let{session:t,ledung:n,run:r}=e,[i,a]=(0,v.useState)(()=>wE(t.id)),[o,s]=(0,v.useState)([]),[c,l]=(0,v.useState)(!1),[u,d]=(0,v.useState)(!1),[f,p]=(0,v.useState)(!1);(0,v.useEffect)(()=>p(!1),[t.id]);let m=(0,v.useRef)(null),h=(0,v.useCallback)((e,t,n)=>{let r=n.length>2e3?`${n.slice(0,2e3)}…`:n;m.current?.(`> ${e}, ${Eg(t)}:\n${r.split(`
|
|
107
107
|
`).map(e=>`> ${e}`).join(`
|
|
108
|
-
`)}\n\n`)},[]),[g,_]=(0,v.useState)(!1),[y,b]=(0,v.useState)(null),x=(0,v.useCallback)(e=>{l(!1),_(!1),b(null),s(t=>[...t,e])},[]),S=(0,v.useMemo)(()=>Object.values(n.questions),[n.questions]),C=()=>{l(!1),s([]),b(null),_(e=>!e)},w=t.status===`ended`,T=Cw(t),E=qf(n.projects.find(e=>e.name===t.project)),D=(0,v.useMemo)(()=>Nv(t,Mv(n.projects,n.chats)),[t.project,t.role,n.projects,n.chats]),O=(0,v.useCallback)(()=>r(n.loadEarlier),[n.loadEarlier]),k=(0,v.useCallback)(e=>n.sessions.find(t=>t.id===e)?.title??`unknown`,[n.sessions]),ee=Sw(e.onOpenQuestion),A=n.board?.projects[t.project]?.repo,j=Sw(t=>e.onOpenBoardThread(A,t)),M=()=>{a(e=>{try{localStorage.setItem(`ledung.technical.${t.id}`,e?`0`:`1`)}catch{}return!e})},te=!(t.status===`stopping`||t.status===`ended`&&!t.claudeSessionId),N=(0,v.useMemo)(()=>te?zS(n.macros??[],t.project):[],[n.macros,t.project,te]),P=Sw((e,n)=>{let i=VS(e.text,t);HS(e,i,n)===`send`?r(()=>R.send(t.id,i.text)):m.current?.(i.text)});return(0,v.useEffect)(()=>{let e=N.filter(e=>e.key);if(!e.length)return;let t=t=>{if(t.repeat||t.isComposing||t.defaultPrevented)return;let n=PS(t),r=n&&e.find(e=>e.key===n);r&&(t.preventDefault(),P(r,!1))};return window.addEventListener(`keydown`,t),()=>window.removeEventListener(`keydown`,t)},[N]),(0,v.useEffect)(()=>{let e=e=>{Dw(e)&&(e.preventDefault(),M())};return window.addEventListener(`keydown`,e),()=>window.removeEventListener(`keydown`,e)},[t.id]),(0,V.jsxs)($f,{level:E,fill:!0,children:[(0,V.jsxs)(`header`,{className:`session-head${u?` details`:``}`,children:[(0,V.jsx)(`button`,{className:`phone-back`,"aria-label":`Back to the list`,title:`Back to the list`,onClick:e.onBack,children:`←`}),(0,V.jsxs)(`div`,{className:`session-head-text`,onClick:e=>{e.target.closest(`a, button`)||d(e=>!e)},children:[(0,V.jsxs)(`h2`,{children:[(0,V.jsx)(`span`,{className:`dot ${ut(t)} phone-dot`,title:lt[t.status]}),t.role===`manager`&&(0,V.jsx)(`span`,{className:`chip`,children:`Manager`}),` `,f?(0,V.jsx)(zC,{value:t.title,label:`New name for ${t.title}`,onDone:()=>p(!1),onSave:e=>r(()=>R.rename(t.id,e))}):(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(fp,{colour:hp(t,Mv(n.projects,n.chats)),children:t.title}),(0,V.jsx)(`button`,{className:`icon rename`,title:`Rename`,"aria-label":`Rename ${t.title}`,onClick:()=>p(!0),children:`✎`})]})]}),t.parentId&&(0,V.jsxs)(`div`,{className:`muted started-by`,children:[`Started by`,` `,(0,V.jsx)(`button`,{className:`link`,onClick:()=>location.hash=`#/s/${t.parentId}`,children:n.sessions.find(e=>e.id===t.parentId)?.title??`a manager`})]}),(0,V.jsxs)(`div`,{className:`muted`,children:[(0,V.jsx)(`span`,{className:`dot ${ut(t)}`}),` `,lt[t.status],t.status===`queued`&&n.machine&&n.machine.line.includes(t.id)?`: number ${n.machine.line.indexOf(t.id)+1} in line`:``,t.paused?` · Paused`:``,t.priority===`normal`?null:(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`span`,{className:`chip prio-${t.priority}`,title:t.priorityNote??void 0,children:Mw[t.priority]})]}),n.machine?.sessions[t.id]&&!w?` · ${kw(n.machine.sessions[t.id].cores)} · ${Aw(n.machine.sessions[t.id].memBytes)}`:``,t.status===`ended`&&t.endReason?` · ${t.endReason}`:``,` · `,t.project===`~chats`?`Chat`:t.project,E?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsxs)(`span`,{className:`chip lock ${E.toLowerCase()}`,title:Gf[E],children:[`Lockdown `,E]})]}):null,t.workDir?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsxs)(`span`,{className:`mono`,title:t.project===`~chats`?`Works in ${t.workDir}`:`Works in ${t.workDir}, not the project folder`,children:[`in `,t.workDir.split(/[\\/]/).filter(Boolean).pop()]})]}):null,t.account?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`span`,{className:`chip`,title:`The Claude account this session runs under`,children:t.account})]}):null,t.model?` · ${t.model}`:``,t.profile&&t.profile!==`full`?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`span`,{className:`chip`,title:`Its session profile: what it gets of your own plugins, MCP servers and tools`,children:t.profile})]}):null,t.backgroundTasks>0?` · ${t.backgroundTasks} background task(s)`:``,t.branch?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`span`,{className:`mono`,children:t.branch})]}):null,t.pr?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`a`,{href:t.pr.url,target:`_blank`,rel:`noreferrer noopener`,title:`${t.pr.title} — checks ${t.pr.checks}`,children:qy(t.pr)})]}):null,t.tickets.map(e=>(0,V.jsxs)(`span`,{children:[` · `,(0,V.jsx)(`a`,{href:e.url,target:`_blank`,rel:`noreferrer noopener`,children:e.id})]},e.id)),t.remoteControl?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(AE,{rc:t.remoteControl})]}):null]})]}),(0,V.jsx)(TE,{before:(0,V.jsx)(`button`,{className:`small files-toggle${g?` on`:``}`,"aria-pressed":g,title:`This session's files and what it changed (a test feature)`,onClick:C,children:`Files`}),session:t,project:n.projects.find(e=>e.name===t.project)??null,away:n.away,run:r,showTechnical:i,onToggleTechnical:M,usage:n.overview?.sessions[t.id]?.total??null,showUsage:c,onToggleUsage:()=>{s([]),_(!1),b(null),l(e=>!e)}}),T.header.length>0&&(0,V.jsxs)(`div`,{className:`session-actions`,children:[T.header.includes(`startNow`)&&(0,V.jsx)(`button`,{className:`primary`,title:`Start this turn now, above the limit on working sessions`,onClick:()=>r(()=>R.startNow(t.id)),children:`Start now`}),T.header.includes(`clear`)&&(0,V.jsx)(OE,{due:t.clearDue,onCancel:()=>r(()=>R.cancelClear(t.id))}),T.header.includes(`compacting`)&&(0,V.jsx)(kE,{compacting:t.compacting,by:t.compacting.requester===t.id?`the session itself`:`manager "${n.sessions.find(e=>e.id===t.compacting.requester)?.title??`a manager`}"`}),T.header.includes(`resume`)&&(0,V.jsx)(`button`,{className:`primary`,onClick:()=>r(()=>R.resume(t.id)),children:`Resume`}),T.header.includes(`archive`)&&(t.archivedAt?(0,V.jsx)(`button`,{title:`Back into the sidebar, still ended`,onClick:()=>r(()=>R.unarchive(t.id)),children:`Unarchive`}):(0,V.jsx)(`button`,{title:`Out of the sidebar, listed under the project's Archived; nothing is deleted`,onClick:()=>r(()=>R.archive(t.id)),children:`Archive`}))]})]}),e.cameFrom&&(0,V.jsxs)(`div`,{className:`came-from`,children:[(0,V.jsxs)(`button`,{className:`small`,onClick:()=>history.back(),children:[`← Back to `,e.cameFrom===`question`?`the question`:e.cameFrom===`shots`?`the screenshots`:`the queue`]}),(0,V.jsx)(`span`,{className:`muted`,children:`You came from Waiting for you; the browser's Back goes there too.`})]}),(0,V.jsxs)(`div`,{className:`session-body`,children:[(0,V.jsxs)(`div`,{className:`chat-column`,children:[(0,V.jsx)(jg,{messages:n.messages,permissions:n.permissions,showTechnical:i,hasEarlier:n.hasEarlier,onLoadEarlier:O,onOpenFile:x,questions:n.questions,userName:n.userName,onQuote:h,titleOf:k,sessionId:t.id,focusQuestion:e.focusQuestion,focusMessage:e.focusMessage??null,onOpenQuestion:ee,onOpenBoardThread:A?j:void 0,tint:D}),(0,V.jsx)(W_,{session:t,sessions:n.sessions,messages:n.messages,extra:(0,V.jsx)(qS,{macros:N,onUse:P,onEdit:()=>location.hash=`#/settings/macros`},t.id)},t.id),(0,V.jsx)(DE,{session:t,tint:D,run:r,quoteInto:m,bangShell:n.bangShell})]}),c&&(0,V.jsx)(Hw,{sessionId:t.id,onClose:()=>l(!1)}),o.length>0&&(0,V.jsx)(cv,{sessionId:t.id,stack:o,onOpen:x,onBack:()=>s(e=>e.slice(0,-1)),onClose:()=>s([])}),g&&(0,V.jsx)(Sv,{session:t,sessions:n.sessions,questions:S,userName:n.userName,hidden:y!==null,onOpenFile:(e,t)=>b({stack:[e],folder:t}),onOpenQuestion:e.onOpenQuestion,onClose:()=>_(!1)}),g&&y&&(0,V.jsx)(cv,{sessionId:t.id,stack:y.stack,folder:y.folder,backToPane:!0,onOpen:e=>b(t=>t&&{...t,stack:[...t.stack,e]}),onBack:()=>b(e=>e&&e.stack.length>1?{...e,stack:e.stack.slice(0,-1)}:null),onClose:()=>{b(null),_(!1)}})]})]})}function TE(e){let{session:t,run:n}=e,[r,i]=(0,v.useState)(!1),a=(0,v.useRef)(null),o=(0,v.useRef)(null),s=(0,v.useRef)(null),c=Cw(t).menu,l=t.status===`ended`,u=e=>()=>{i(!1),e()};return(0,v.useEffect)(()=>{if(!r)return;o.current?.querySelector(`select:not(:disabled), input, button`)?.focus();let e=e=>{a.current?.contains(e.target)||i(!1)},t=e=>{Ow(e)&&(e.preventDefault(),i(!1),s.current?.focus())};return document.addEventListener(`pointerdown`,e),document.addEventListener(`keydown`,t,!0),()=>{document.removeEventListener(`pointerdown`,e),document.removeEventListener(`keydown`,t,!0)}},[r]),(0,V.jsxs)(`div`,{className:`session-corner`,ref:a,children:[e.before,t.role===`manager`&&e.away&&(0,V.jsx)(fb,{away:e.away,onClick:()=>i(!0)}),(0,V.jsx)(`button`,{ref:s,className:`icon settings-cog${r?` on`:``}`,title:`Session settings: ${t.role===`manager`?`away, `:``}permissions, tool calls, usage, pause and stop`,"aria-label":`Session settings`,"aria-haspopup":`dialog`,"aria-expanded":r,"aria-controls":r?`session-menu`:void 0,onClick:()=>i(!r),children:`⚙`}),r&&(0,V.jsxs)(`div`,{className:`session-menu`,id:`session-menu`,role:`dialog`,"aria-label":`Session settings`,ref:o,children:[c.includes(`away`)&&(0,V.jsxs)(`div`,{className:`menu-row away-row`,children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`Away`}),(0,V.jsx)(hb,{away:e.away,run:n})]}),c.includes(`permissions`)&&(0,V.jsxs)(`label`,{className:`mode menu-row`,title:lE[t.permissionMode],children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`Permissions`}),(0,V.jsx)(`select`,{value:t.permissionMode,disabled:l||t.status===`stopping`,onChange:e=>n(()=>R.setPermissionMode(t.id,e.target.value)),children:b.map(e=>(0,V.jsx)(`option`,{value:e,title:lE[e],children:cE[e]},e))})]}),c.includes(`priority`)&&(0,V.jsxs)(`label`,{className:`mode menu-row`,title:t.priorityNote??`Who goes first when sessions wait for a free place`,children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`Priority`}),(0,V.jsx)(`select`,{value:t.priority,disabled:l,onChange:e=>n(()=>R.setPriority(t.id,e.target.value)),children:C.map(e=>(0,V.jsx)(`option`,{value:e,children:Mw[e]},e))})]}),c.includes(`toolCalls`)&&(0,V.jsxs)(`label`,{className:`toggle menu-row`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e.showTechnical,onChange:e.onToggleTechnical}),` Show tool calls`,(0,V.jsx)(`kbd`,{title:`Works anywhere on this page, the message box included`,children:`Ctrl+O`})]}),c.includes(`usage`)&&(0,V.jsxs)(`button`,{className:`menu-row${e.showUsage?` on`:``}`,onClick:u(e.onToggleUsage),children:[`Usage`,e.usage==null?``:` · ${Wy(e.usage)}`]}),(c.includes(`pause`)||c.includes(`stop`))&&(0,V.jsxs)(`div`,{className:`menu-row menu-buttons`,children:[c.includes(`pause`)&&(0,V.jsx)(`button`,{title:t.paused?`Let it go on`:`The command running now finishes; the next tool call waits, and no new turn starts`,onClick:u(()=>void n(()=>R.setPaused(t.id,!t.paused))),children:t.paused?`Resume`:`Pause`}),c.includes(`stop`)&&(0,V.jsx)(`button`,{onClick:u(()=>void n(()=>R.stop(t.id))),children:`Stop`})]}),ww(t)&&(0,V.jsx)(EE,{sessionId:t.id}),c.includes(`version`)&&(0,V.jsxs)(`div`,{className:`menu-row menu-info`,children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`Claude Code`}),(0,V.jsx)(`span`,{className:`mono`,children:t.claudeVersion})]})]})]})}function EE({sessionId:e}){let[t,n]=(0,v.useState)(null),[r,i]=(0,v.useState)(null),[a,o]=(0,v.useState)(null);(0,v.useEffect)(()=>{let t=!0;return R.mcpServers(e).then(e=>t&&n(e),e=>t&&i(e.message)),()=>{t=!1}},[e]);let s=async t=>{o(t),i(null);try{n(await R.reconnectMcp(e,t))}catch(e){i(e.message)}finally{o(null)}};return(0,V.jsxs)(`div`,{className:`menu-row mcp-row`,children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`MCP servers`}),t===null&&!r&&(0,V.jsx)(`span`,{className:`muted`,children:`Asking Claude Code…`}),t?.length===0&&(0,V.jsx)(`span`,{className:`muted`,children:`None.`}),!!t?.length&&(0,V.jsx)(`ul`,{className:`mcp-servers`,children:t.map(e=>(0,V.jsxs)(`li`,{title:[e.version,e.tools?`${e.tools} tool${e.tools===1?``:`s`}`:``,e.error].filter(Boolean).join(` · `)||void 0,children:[(0,V.jsx)(`span`,{className:`dot mcp-${e.status}`}),(0,V.jsx)(`span`,{className:`mono`,children:e.name}),(0,V.jsx)(`span`,{className:`muted`,children:Tw[e.status]??e.status}),e.canReconnect?(0,V.jsx)(`button`,{className:`small`,disabled:a!==null,onClick:()=>void s(e.name),children:a===e.name?`Reconnecting…`:`Reconnect`}):(0,V.jsx)(`span`,{className:`muted`,title:`Ledung's own tool server, inside Ledung`,children:`Ledung's`})]},e.name))}),r&&(0,V.jsx)(`span`,{className:`error`,children:r})]})}function DE({session:e,tint:t,run:n,quoteInto:r,bangShell:i}){let a=B(),[o,s]=xw(e.id),c=e.status===`ended`&&!!e.claudeSessionId,l=e.status===`ended`&&!c||e.status===`stopping`,u=Ew(e),{box:d,area:f,style:p,grip:m}=jT();(0,v.useEffect)(()=>(r.current=e=>{s(t=>t.trim()?`${t.trimEnd()}\n\n${e}`:e),f.current?.focus()},()=>{r.current=null}),[]),(0,v.useEffect)(()=>{e.project===`~chats`&&e.title===`New chat`&&!e.claudeSessionId&&f.current?.focus()},[e.id]);let[h,g]=(0,v.useState)(null),_=eh(o),y=async(t,r)=>{let i=o;s(``),g(null),await n(async()=>{try{await R.shell(e.id,t,r)}catch(e){throw s(i),e}})},b=async()=>{let t=o;t.trim()&&(_?await n(async()=>{let t=await R.shellCheck(e.id,_);if(t.refused)throw Error(t.refused);t.rule?g({command:_,rule:t.rule}):await y(_,!1)}):(s(``),await n(async()=>{try{await R.send(e.id,t)}catch(e){throw s(t),e}})))};return(0,V.jsxs)(`div`,{className:`composer${t?` tinted`:``}`,style:t,ref:d,children:[m,(e.shell||h||_)&&(0,V.jsxs)(`div`,{className:`bang-strips`,children:[e.shell&&(0,V.jsxs)(`div`,{className:`bang-running`,role:`status`,children:[(0,V.jsxs)(`span`,{children:[`Running `,(0,V.jsxs)(`code`,{children:[`!`,e.shell.command]}),`…`]}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void n(()=>R.shellStop(e.id)),children:`Stop`})]}),h&&(0,V.jsxs)(`div`,{className:`bang-ask`,role:`alert`,children:[(0,V.jsx)(`span`,{children:th(h.rule)}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void y(h.command,!0),children:`Run`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>g(null),children:`Cancel`})]}),_&&!h&&(0,V.jsx)(`div`,{className:`bang-hint muted`,children:nh(i,e.runner)})]}),(0,V.jsx)(`textarea`,{...a,ref:f,style:p,value:o,disabled:l,placeholder:l?`This session has ended.`:c?`This session has ended; sending a message resumes it.`:og()?`Message Claude`:`Message Claude (Enter to send, Shift+Enter for a new line)`,onChange:e=>{s(e.target.value),g(null)},onKeyDown:e=>{KT({key:e.key,shiftKey:e.shiftKey,ctrlKey:e.ctrlKey,metaKey:e.metaKey,isComposing:e.nativeEvent.isComposing},og())&&(e.preventDefault(),b())},rows:3}),(0,V.jsxs)(`div`,{className:`composer-buttons`,children:[(0,V.jsx)(`button`,{className:`stop-sign`,"aria-label":`Interrupt`,title:u?`Interrupt`:`Interrupt: nothing to interrupt now`,disabled:!u,onClick:()=>void n(()=>R.interrupt(e.id)),children:`STOP`}),(0,V.jsx)(`button`,{className:`primary`,disabled:l||!o.trim()||!!_&&!!e.shell,onClick:()=>void b(),children:_?`Run`:`Send`})]})]})}function OE({due:e,onCancel:t}){let[n,r]=(0,v.useState)(Date.now());(0,v.useEffect)(()=>{let e=setInterval(()=>r(Date.now()),500);return()=>clearInterval(e)},[]);let i=Math.max(0,Math.ceil((e-n)/1e3));return(0,V.jsxs)(`span`,{className:`clear-countdown`,role:`status`,children:[i>0?`Clearing the conversation in ${i} s`:`Clearing the conversation…`,` `,(0,V.jsx)(`button`,{className:`primary`,title:`Keep the conversation; whoever asked for the clear is told`,onClick:t,children:`Cancel clear`})]})}function kE({compacting:e,by:t}){let[n,r]=(0,v.useState)(Date.now());(0,v.useEffect)(()=>{let e=setInterval(()=>r(Date.now()),1e3);return()=>clearInterval(e)},[]);let i=Math.max(0,Math.floor((n-e.startedAt)/1e3)),a=`${Math.floor(i/60)}:${String(i%60).padStart(2,`0`)}`,o=`Compact requested by ${t}${e.note?`. Note for the summary: ${e.note}`:``}`;return(0,V.jsxs)(`span`,{className:`compacting`,role:`status`,title:o,children:[`Compacting… `,a,e.note&&(0,V.jsxs)(`span`,{className:`compacting-note`,children:[`Note from `,t,`: `,e.note]})]})}function AE({rc:e}){if(e.state===`unavailable`)return(0,V.jsx)(`span`,{title:e.error??void 0,children:`Remote Control unavailable`});if(!e.url)return(0,V.jsx)(`span`,{children:`Remote Control starting…`});let t=e.bridge?` (bridge ${e.bridge})`:``;return(0,V.jsx)(`a`,{href:e.url,target:`_blank`,rel:`noreferrer noopener`,title:`Remote Control on${t}: this manager in the Claude app or on claude.ai`,children:`Remote Control`})}var jE=e=>e?.name===`NotAllowedError`?Error(ye):e;function ME(e){return e.failed?{title:e.failed===`The passkey check was cancelled.`?`The passkey check was cancelled`:`The passkey check didn't go through`,body:[...e.failed===`The passkey check was cancelled.`?[]:[e.failed],`Nothing was changed. Try again to get the Face ID or fingerprint prompt back.`],go:`Try again`}:e.kind===`unlock`?{title:`Unlock this device`,body:[`This device is locked. Next comes a Face ID, fingerprint, Touch ID or Windows Hello check that unlocks it for changes: for 30 minutes on a phone; a computer stays logged on until you log out.`,`A sensitive permission is also signed on its own, so then a second check follows straight after the first.`],go:`Continue`}:{title:`Sign with your passkey`,body:[`Sensitive permissions are signed one by one: next comes a Face ID or fingerprint check for this one.`,`When this device is locked it asks twice: first to unlock it, then to sign.`],go:`Continue`}}var NE=e=>{let t=``;for(let n of new Uint8Array(e))t+=String.fromCharCode(n);return btoa(t).replace(/\+/g,`-`).replace(/\//g,`_`).replace(/=+$/,``)},PE=e=>{let t=atob(e.replace(/-/g,`+`).replace(/_/g,`/`)+`=`.repeat((4-e.length%4)%4)),n=new Uint8Array(t.length);for(let e=0;e<t.length;e++)n[e]=t.charCodeAt(e);return n};async function FE(e){let t=await navigator.credentials.get({publicKey:{challenge:PE(e.challenge),rpId:e.rpId,timeout:e.timeout,userVerification:`required`,allowCredentials:(e.allowCredentials??[]).map(e=>({type:`public-key`,id:PE(e.id)}))}}).catch(e=>{throw jE(e)});if(!t)throw Error(ye);let n=t.response,r={id:t.id,rawId:NE(t.rawId),type:t.type,clientExtensionResults:{},response:{clientDataJSON:NE(n.clientDataJSON),authenticatorData:NE(n.authenticatorData),signature:NE(n.signature),...n.userHandle?{userHandle:NE(n.userHandle)}:{}}};return NE(new TextEncoder().encode(JSON.stringify(r)))}async function IE(e){let t=e.user,n=await navigator.credentials.create({publicKey:{challenge:PE(e.challenge),rp:e.rp,user:{id:PE(t.id),name:t.name,displayName:t.displayName},pubKeyCredParams:e.pubKeyCredParams,timeout:e.timeout,attestation:`none`,authenticatorSelection:{residentKey:`discouraged`,userVerification:`required`}}});if(!n)throw Error(`Setting up the passkey was cancelled.`);let r=n.response;return{id:n.id,rawId:NE(n.rawId),type:n.type,clientExtensionResults:{},response:{clientDataJSON:NE(r.clientDataJSON),attestationObject:NE(r.attestationObject),transports:r.getTransports?.()??[]}}}var LE={sign:FE,create:IE};function RE(){let[e,t]=(0,v.useState)([]);(0,v.useEffect)(()=>(xe(e=>new Promise(n=>t(t=>[...t,{step:e,answer:n}]))),()=>xe(null)),[]);let n=e[0];if(!n)return null;let r=ME(n.step),i=e=>{t(e=>e.slice(1)),n.answer(e)};return(0,V.jsx)(`div`,{className:`passkey-backdrop`,children:(0,V.jsxs)(`div`,{className:`passkey-dialog`,role:`alertdialog`,"aria-modal":`true`,"aria-labelledby":`passkey-title`,children:[(0,V.jsx)(`h3`,{id:`passkey-title`,children:r.title}),r.body.map(e=>(0,V.jsx)(`p`,{children:e},e)),(0,V.jsxs)(`div`,{className:`passkey-actions`,children:[(0,V.jsx)(`button`,{onClick:()=>i(!1),children:`Cancel`}),(0,V.jsx)(`button`,{className:`primary`,autoFocus:!0,onClick:()=>i(!0),children:r.go})]})]})})}_e(LE),ct(document.documentElement,ot(localStorage)),window.addEventListener(`storage`,e=>{e.key===`ledung.theme`?ct(document.documentElement,at(e.newValue)):e.key===null&&ct(document.documentElement,ot(localStorage))}),dn(),QT(window),(0,y.createRoot)(document.getElementById(`root`)).render((0,V.jsxs)(v.StrictMode,{children:[(0,V.jsx)(SE,{}),(0,V.jsx)(RE,{})]}));export{o as n,l as r,tv as t};
|
|
108
|
+
`)}\n\n`)},[]),[g,_]=(0,v.useState)(!1),[y,b]=(0,v.useState)(null),x=(0,v.useCallback)(e=>{l(!1),_(!1),b(null),s(t=>[...t,e])},[]),S=(0,v.useMemo)(()=>Object.values(n.questions),[n.questions]),C=()=>{l(!1),s([]),b(null),_(e=>!e)},w=t.status===`ended`,T=Ew(t),E=qf(n.projects.find(e=>e.name===t.project)),D=(0,v.useMemo)(()=>Nv(t,Mv(n.projects,n.chats)),[t.project,t.role,n.projects,n.chats]),O=(0,v.useCallback)(()=>r(n.loadEarlier),[n.loadEarlier]),k=(0,v.useCallback)(e=>n.sessions.find(t=>t.id===e)?.title??`unknown`,[n.sessions]),ee=Tw(e.onOpenQuestion),A=n.board?.projects[t.project]?.repo,j=Tw(t=>e.onOpenBoardThread(A,t)),M=()=>{a(e=>{try{localStorage.setItem(`ledung.technical.${t.id}`,e?`0`:`1`)}catch{}return!e})},te=!(t.status===`stopping`||t.status===`ended`&&!t.claudeSessionId),N=(0,v.useMemo)(()=>te?HS(n.macros??[],t.project):[],[n.macros,t.project,te]),P=Tw((e,n)=>{let i=WS(e.text,t);GS(e,i,n)===`send`?r(()=>R.send(t.id,i.text)):m.current?.(i.text)});return(0,v.useEffect)(()=>{let e=N.filter(e=>e.key);if(!e.length)return;let t=t=>{if(t.repeat||t.isComposing||t.defaultPrevented)return;let n=LS(t),r=n&&e.find(e=>e.key===n);r&&(t.preventDefault(),P(r,!1))};return window.addEventListener(`keydown`,t),()=>window.removeEventListener(`keydown`,t)},[N]),(0,v.useEffect)(()=>{let e=e=>{Aw(e)&&(e.preventDefault(),M())};return window.addEventListener(`keydown`,e),()=>window.removeEventListener(`keydown`,e)},[t.id]),(0,V.jsxs)($f,{level:E,fill:!0,children:[(0,V.jsxs)(`header`,{className:`session-head${u?` details`:``}`,children:[(0,V.jsx)(`button`,{className:`phone-back`,"aria-label":`Back to the list`,title:`Back to the list`,onClick:e.onBack,children:`←`}),(0,V.jsxs)(`div`,{className:`session-head-text`,onClick:e=>{e.target.closest(`a, button`)||d(e=>!e)},children:[(0,V.jsxs)(`h2`,{children:[(0,V.jsx)(`span`,{className:`dot ${ut(t)} phone-dot`,title:lt[t.status]}),t.role===`manager`&&(0,V.jsx)(`span`,{className:`chip`,children:`Manager`}),` `,f?(0,V.jsx)(HC,{value:t.title,label:`New name for ${t.title}`,onDone:()=>p(!1),onSave:e=>r(()=>R.rename(t.id,e))}):(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(fp,{colour:hp(t,Mv(n.projects,n.chats)),children:t.title}),(0,V.jsx)(`button`,{className:`icon rename`,title:`Rename`,"aria-label":`Rename ${t.title}`,onClick:()=>p(!0),children:`✎`})]})]}),t.parentId&&(0,V.jsxs)(`div`,{className:`muted started-by`,children:[`Started by`,` `,(0,V.jsx)(`button`,{className:`link`,onClick:()=>location.hash=`#/s/${t.parentId}`,children:n.sessions.find(e=>e.id===t.parentId)?.title??`a manager`})]}),(0,V.jsxs)(`div`,{className:`muted`,children:[(0,V.jsx)(`span`,{className:`dot ${ut(t)}`}),` `,lt[t.status],t.status===`queued`&&n.machine&&n.machine.line.includes(t.id)?`: number ${n.machine.line.indexOf(t.id)+1} in line`:``,t.paused?` · Paused`:``,t.priority===`normal`?null:(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`span`,{className:`chip prio-${t.priority}`,title:t.priorityNote??void 0,children:Fw[t.priority]})]}),n.machine?.sessions[t.id]&&!w?` · ${Mw(n.machine.sessions[t.id].cores)} · ${Nw(n.machine.sessions[t.id].memBytes)}`:``,t.status===`ended`&&t.endReason?` · ${t.endReason}`:``,` · `,t.project===`~chats`?`Chat`:t.project,E?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsxs)(`span`,{className:`chip lock ${E.toLowerCase()}`,title:Gf[E],children:[`Lockdown `,E]})]}):null,t.workDir?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsxs)(`span`,{className:`mono`,title:t.project===`~chats`?`Works in ${t.workDir}`:`Works in ${t.workDir}, not the project folder`,children:[`in `,t.workDir.split(/[\\/]/).filter(Boolean).pop()]})]}):null,t.account?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`span`,{className:`chip`,title:`The Claude account this session runs under`,children:t.account})]}):null,t.model?` · ${t.model}`:``,t.profile&&t.profile!==`full`?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`span`,{className:`chip`,title:`Its session profile: what it gets of your own plugins, MCP servers and tools`,children:t.profile})]}):null,t.backgroundTasks>0?` · ${t.backgroundTasks} background task(s)`:``,t.branch?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`span`,{className:`mono`,children:t.branch})]}):null,t.pr?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(`a`,{href:t.pr.url,target:`_blank`,rel:`noreferrer noopener`,title:`${t.pr.title} — checks ${t.pr.checks}`,children:qy(t.pr)})]}):null,t.tickets.map(e=>(0,V.jsxs)(`span`,{children:[` · `,(0,V.jsx)(`a`,{href:e.url,target:`_blank`,rel:`noreferrer noopener`,children:e.id})]},e.id)),t.remoteControl?(0,V.jsxs)(V.Fragment,{children:[` · `,(0,V.jsx)(NE,{rc:t.remoteControl})]}):null]})]}),(0,V.jsx)(OE,{before:(0,V.jsx)(`button`,{className:`small files-toggle${g?` on`:``}`,"aria-pressed":g,title:`This session's files and what it changed (a test feature)`,onClick:C,children:`Files`}),session:t,project:n.projects.find(e=>e.name===t.project)??null,away:n.away,run:r,showTechnical:i,onToggleTechnical:M,usage:n.overview?.sessions[t.id]?.total??null,showUsage:c,onToggleUsage:()=>{s([]),_(!1),b(null),l(e=>!e)}}),T.header.length>0&&(0,V.jsxs)(`div`,{className:`session-actions`,children:[T.header.includes(`startNow`)&&(0,V.jsx)(`button`,{className:`primary`,title:`Start this turn now, above the limit on working sessions`,onClick:()=>r(()=>R.startNow(t.id)),children:`Start now`}),T.header.includes(`clear`)&&(0,V.jsx)(jE,{due:t.clearDue,onCancel:()=>r(()=>R.cancelClear(t.id))}),T.header.includes(`compacting`)&&(0,V.jsx)(ME,{compacting:t.compacting,by:t.compacting.requester===t.id?`the session itself`:`manager "${n.sessions.find(e=>e.id===t.compacting.requester)?.title??`a manager`}"`}),T.header.includes(`resume`)&&(0,V.jsx)(`button`,{className:`primary`,onClick:()=>r(()=>R.resume(t.id)),children:`Resume`}),T.header.includes(`archive`)&&(t.archivedAt?(0,V.jsx)(`button`,{title:`Back into the sidebar, still ended`,onClick:()=>r(()=>R.unarchive(t.id)),children:`Unarchive`}):(0,V.jsx)(`button`,{title:`Out of the sidebar, listed under the project's Archived; nothing is deleted`,onClick:()=>r(()=>R.archive(t.id)),children:`Archive`}))]})]}),e.cameFrom&&(0,V.jsxs)(`div`,{className:`came-from`,children:[(0,V.jsxs)(`button`,{className:`small`,onClick:()=>history.back(),children:[`← Back to `,e.cameFrom===`question`?`the question`:e.cameFrom===`shots`?`the screenshots`:`the queue`]}),(0,V.jsx)(`span`,{className:`muted`,children:`You came from Waiting for you; the browser's Back goes there too.`})]}),(0,V.jsxs)(`div`,{className:`session-body`,children:[(0,V.jsxs)(`div`,{className:`chat-column`,children:[(0,V.jsx)(jg,{messages:n.messages,permissions:n.permissions,showTechnical:i,hasEarlier:n.hasEarlier,onLoadEarlier:O,onOpenFile:x,questions:n.questions,userName:n.userName,onQuote:h,titleOf:k,sessionId:t.id,focusQuestion:e.focusQuestion,focusMessage:e.focusMessage??null,onOpenQuestion:ee,onOpenBoardThread:A?j:void 0,tint:D}),(0,V.jsx)(W_,{session:t,sessions:n.sessions,messages:n.messages,extra:(0,V.jsx)(XS,{macros:N,onUse:P,onEdit:()=>location.hash=`#/settings/macros`},t.id)},t.id),(0,V.jsx)(AE,{session:t,tint:D,run:r,quoteInto:m,bangShell:n.bangShell})]}),c&&(0,V.jsx)(Gw,{sessionId:t.id,onClose:()=>l(!1)}),o.length>0&&(0,V.jsx)(cv,{sessionId:t.id,stack:o,onOpen:x,onBack:()=>s(e=>e.slice(0,-1)),onClose:()=>s([])}),g&&(0,V.jsx)(Sv,{session:t,sessions:n.sessions,questions:S,userName:n.userName,hidden:y!==null,onOpenFile:(e,t)=>b({stack:[e],folder:t}),onOpenQuestion:e.onOpenQuestion,onClose:()=>_(!1)}),g&&y&&(0,V.jsx)(cv,{sessionId:t.id,stack:y.stack,folder:y.folder,backToPane:!0,onOpen:e=>b(t=>t&&{...t,stack:[...t.stack,e]}),onBack:()=>b(e=>e&&e.stack.length>1?{...e,stack:e.stack.slice(0,-1)}:null),onClose:()=>{b(null),_(!1)}})]})]})}function OE(e){let{session:t,run:n}=e,[r,i]=(0,v.useState)(!1),a=(0,v.useRef)(null),o=(0,v.useRef)(null),s=(0,v.useRef)(null),c=Ew(t).menu,l=t.status===`ended`,u=e=>()=>{i(!1),e()};return(0,v.useEffect)(()=>{if(!r)return;o.current?.querySelector(`select:not(:disabled), input, button`)?.focus();let e=e=>{a.current?.contains(e.target)||i(!1)},t=e=>{jw(e)&&(e.preventDefault(),i(!1),s.current?.focus())};return document.addEventListener(`pointerdown`,e),document.addEventListener(`keydown`,t,!0),()=>{document.removeEventListener(`pointerdown`,e),document.removeEventListener(`keydown`,t,!0)}},[r]),(0,V.jsxs)(`div`,{className:`session-corner`,ref:a,children:[e.before,t.role===`manager`&&e.away&&(0,V.jsx)(fb,{away:e.away,onClick:()=>i(!0)}),(0,V.jsx)(`button`,{ref:s,className:`icon settings-cog${r?` on`:``}`,title:`Session settings: ${t.role===`manager`?`away, `:``}permissions, tool calls, usage, pause and stop`,"aria-label":`Session settings`,"aria-haspopup":`dialog`,"aria-expanded":r,"aria-controls":r?`session-menu`:void 0,onClick:()=>i(!r),children:`⚙`}),r&&(0,V.jsxs)(`div`,{className:`session-menu`,id:`session-menu`,role:`dialog`,"aria-label":`Session settings`,ref:o,children:[c.includes(`away`)&&(0,V.jsxs)(`div`,{className:`menu-row away-row`,children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`Away`}),(0,V.jsx)(hb,{away:e.away,run:n})]}),c.includes(`permissions`)&&(0,V.jsxs)(`label`,{className:`mode menu-row`,title:fE[t.permissionMode],children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`Permissions`}),(0,V.jsx)(`select`,{value:t.permissionMode,disabled:l||t.status===`stopping`,onChange:e=>n(()=>R.setPermissionMode(t.id,e.target.value)),children:b.map(e=>(0,V.jsx)(`option`,{value:e,title:fE[e],children:dE[e]},e))})]}),c.includes(`priority`)&&(0,V.jsxs)(`label`,{className:`mode menu-row`,title:t.priorityNote??`Who goes first when sessions wait for a free place`,children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`Priority`}),(0,V.jsx)(`select`,{value:t.priority,disabled:l,onChange:e=>n(()=>R.setPriority(t.id,e.target.value)),children:C.map(e=>(0,V.jsx)(`option`,{value:e,children:Fw[e]},e))})]}),c.includes(`toolCalls`)&&(0,V.jsxs)(`label`,{className:`toggle menu-row`,children:[(0,V.jsx)(`input`,{type:`checkbox`,checked:e.showTechnical,onChange:e.onToggleTechnical}),` Show tool calls`,(0,V.jsx)(`kbd`,{title:`Works anywhere on this page, the message box included`,children:`Ctrl+O`})]}),c.includes(`usage`)&&(0,V.jsxs)(`button`,{className:`menu-row${e.showUsage?` on`:``}`,onClick:u(e.onToggleUsage),children:[`Usage`,e.usage==null?``:` · ${Wy(e.usage)}`]}),(c.includes(`pause`)||c.includes(`stop`))&&(0,V.jsxs)(`div`,{className:`menu-row menu-buttons`,children:[c.includes(`pause`)&&(0,V.jsx)(`button`,{title:t.paused?`Let it go on`:`The command running now finishes; the next tool call waits, and no new turn starts`,onClick:u(()=>void n(()=>R.setPaused(t.id,!t.paused))),children:t.paused?`Resume`:`Pause`}),c.includes(`stop`)&&(0,V.jsx)(`button`,{onClick:u(()=>void n(()=>R.stop(t.id))),children:`Stop`})]}),Dw(t)&&(0,V.jsx)(kE,{sessionId:t.id}),c.includes(`version`)&&(0,V.jsxs)(`div`,{className:`menu-row menu-info`,children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`Claude Code`}),(0,V.jsx)(`span`,{className:`mono`,children:t.claudeVersion})]})]})]})}function kE({sessionId:e}){let[t,n]=(0,v.useState)(null),[r,i]=(0,v.useState)(null),[a,o]=(0,v.useState)(null);(0,v.useEffect)(()=>{let t=!0;return R.mcpServers(e).then(e=>t&&n(e),e=>t&&i(e.message)),()=>{t=!1}},[e]);let s=async t=>{o(t),i(null);try{n(await R.reconnectMcp(e,t))}catch(e){i(e.message)}finally{o(null)}};return(0,V.jsxs)(`div`,{className:`menu-row mcp-row`,children:[(0,V.jsx)(`span`,{className:`menu-label`,children:`MCP servers`}),t===null&&!r&&(0,V.jsx)(`span`,{className:`muted`,children:`Asking Claude Code…`}),t?.length===0&&(0,V.jsx)(`span`,{className:`muted`,children:`None.`}),!!t?.length&&(0,V.jsx)(`ul`,{className:`mcp-servers`,children:t.map(e=>(0,V.jsxs)(`li`,{title:[e.version,e.tools?`${e.tools} tool${e.tools===1?``:`s`}`:``,e.error].filter(Boolean).join(` · `)||void 0,children:[(0,V.jsx)(`span`,{className:`dot mcp-${e.status}`}),(0,V.jsx)(`span`,{className:`mono`,children:e.name}),(0,V.jsx)(`span`,{className:`muted`,children:Ow[e.status]??e.status}),e.canReconnect?(0,V.jsx)(`button`,{className:`small`,disabled:a!==null,onClick:()=>void s(e.name),children:a===e.name?`Reconnecting…`:`Reconnect`}):(0,V.jsx)(`span`,{className:`muted`,title:`Ledung's own tool server, inside Ledung`,children:`Ledung's`})]},e.name))}),r&&(0,V.jsx)(`span`,{className:`error`,children:r})]})}function AE({session:e,tint:t,run:n,quoteInto:r,bangShell:i}){let a=B(),[o,s]=ww(e.id),c=e.status===`ended`&&!!e.claudeSessionId,l=e.status===`ended`&&!c||e.status===`stopping`,u=kw(e),{box:d,area:f,style:p,grip:m}=PT();(0,v.useEffect)(()=>(r.current=e=>{s(t=>t.trim()?`${t.trimEnd()}\n\n${e}`:e),f.current?.focus()},()=>{r.current=null}),[]),(0,v.useEffect)(()=>{e.project===`~chats`&&e.title===`New chat`&&!e.claudeSessionId&&f.current?.focus()},[e.id]);let[h,g]=(0,v.useState)(null),_=eh(o),y=async(t,r)=>{let i=o;s(``),g(null),await n(async()=>{try{await R.shell(e.id,t,r)}catch(e){throw s(i),e}})},b=async()=>{let t=o;t.trim()&&(_?await n(async()=>{let t=await R.shellCheck(e.id,_);if(t.refused)throw Error(t.refused);t.rule?g({command:_,rule:t.rule}):await y(_,!1)}):(s(``),await n(async()=>{try{await R.send(e.id,t)}catch(e){throw s(t),e}})))};return(0,V.jsxs)(`div`,{className:`composer${t?` tinted`:``}`,style:t,ref:d,children:[m,(e.shell||h||_)&&(0,V.jsxs)(`div`,{className:`bang-strips`,children:[e.shell&&(0,V.jsxs)(`div`,{className:`bang-running`,role:`status`,children:[(0,V.jsxs)(`span`,{children:[`Running `,(0,V.jsxs)(`code`,{children:[`!`,e.shell.command]}),`…`]}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>void n(()=>R.shellStop(e.id)),children:`Stop`})]}),h&&(0,V.jsxs)(`div`,{className:`bang-ask`,role:`alert`,children:[(0,V.jsx)(`span`,{children:th(h.rule)}),(0,V.jsx)(`button`,{className:`small primary`,onClick:()=>void y(h.command,!0),children:`Run`}),(0,V.jsx)(`button`,{className:`small`,onClick:()=>g(null),children:`Cancel`})]}),_&&!h&&(0,V.jsx)(`div`,{className:`bang-hint muted`,children:nh(i,e.runner)})]}),(0,V.jsx)(`textarea`,{...a,ref:f,style:p,value:o,disabled:l,placeholder:l?`This session has ended.`:c?`This session has ended; sending a message resumes it.`:og()?`Message Claude`:`Message Claude (Enter to send, Shift+Enter for a new line)`,onChange:e=>{s(e.target.value),g(null)},onKeyDown:e=>{YT({key:e.key,shiftKey:e.shiftKey,ctrlKey:e.ctrlKey,metaKey:e.metaKey,isComposing:e.nativeEvent.isComposing},og())&&(e.preventDefault(),b())},rows:3}),(0,V.jsxs)(`div`,{className:`composer-buttons`,children:[(0,V.jsx)(`button`,{className:`stop-sign`,"aria-label":`Interrupt`,title:u?`Interrupt`:`Interrupt: nothing to interrupt now`,disabled:!u,onClick:()=>void n(()=>R.interrupt(e.id)),children:`STOP`}),(0,V.jsx)(`button`,{className:`primary`,disabled:l||!o.trim()||!!_&&!!e.shell,onClick:()=>void b(),children:_?`Run`:`Send`})]})]})}function jE({due:e,onCancel:t}){let[n,r]=(0,v.useState)(Date.now());(0,v.useEffect)(()=>{let e=setInterval(()=>r(Date.now()),500);return()=>clearInterval(e)},[]);let i=Math.max(0,Math.ceil((e-n)/1e3));return(0,V.jsxs)(`span`,{className:`clear-countdown`,role:`status`,children:[i>0?`Clearing the conversation in ${i} s`:`Clearing the conversation…`,` `,(0,V.jsx)(`button`,{className:`primary`,title:`Keep the conversation; whoever asked for the clear is told`,onClick:t,children:`Cancel clear`})]})}function ME({compacting:e,by:t}){let[n,r]=(0,v.useState)(Date.now());(0,v.useEffect)(()=>{let e=setInterval(()=>r(Date.now()),1e3);return()=>clearInterval(e)},[]);let i=Math.max(0,Math.floor((n-e.startedAt)/1e3)),a=`${Math.floor(i/60)}:${String(i%60).padStart(2,`0`)}`,o=`Compact requested by ${t}${e.note?`. Note for the summary: ${e.note}`:``}`;return(0,V.jsxs)(`span`,{className:`compacting`,role:`status`,title:o,children:[`Compacting… `,a,e.note&&(0,V.jsxs)(`span`,{className:`compacting-note`,children:[`Note from `,t,`: `,e.note]})]})}function NE({rc:e}){if(e.state===`unavailable`)return(0,V.jsx)(`span`,{title:e.error??void 0,children:`Remote Control unavailable`});if(!e.url)return(0,V.jsx)(`span`,{children:`Remote Control starting…`});let t=e.bridge?` (bridge ${e.bridge})`:``;return(0,V.jsx)(`a`,{href:e.url,target:`_blank`,rel:`noreferrer noopener`,title:`Remote Control on${t}: this manager in the Claude app or on claude.ai`,children:`Remote Control`})}var PE=e=>e?.name===`NotAllowedError`?Error(ye):e;function FE(e){return e.failed?{title:e.failed===`The passkey check was cancelled.`?`The passkey check was cancelled`:`The passkey check didn't go through`,body:[...e.failed===`The passkey check was cancelled.`?[]:[e.failed],`Nothing was changed. Try again to get the Face ID or fingerprint prompt back.`],go:`Try again`}:e.kind===`unlock`?{title:`Unlock this device`,body:[`This device is locked. Next comes a Face ID, fingerprint, Touch ID or Windows Hello check that unlocks it for changes: for 30 minutes on a phone; a computer stays logged on until you log out.`,`A sensitive permission is also signed on its own, so then a second check follows straight after the first.`],go:`Continue`}:{title:`Sign with your passkey`,body:[`Sensitive permissions are signed one by one: next comes a Face ID or fingerprint check for this one.`,`When this device is locked it asks twice: first to unlock it, then to sign.`],go:`Continue`}}var IE=e=>{let t=``;for(let n of new Uint8Array(e))t+=String.fromCharCode(n);return btoa(t).replace(/\+/g,`-`).replace(/\//g,`_`).replace(/=+$/,``)},LE=e=>{let t=atob(e.replace(/-/g,`+`).replace(/_/g,`/`)+`=`.repeat((4-e.length%4)%4)),n=new Uint8Array(t.length);for(let e=0;e<t.length;e++)n[e]=t.charCodeAt(e);return n};async function RE(e){let t=await navigator.credentials.get({publicKey:{challenge:LE(e.challenge),rpId:e.rpId,timeout:e.timeout,userVerification:`required`,allowCredentials:(e.allowCredentials??[]).map(e=>({type:`public-key`,id:LE(e.id)}))}}).catch(e=>{throw PE(e)});if(!t)throw Error(ye);let n=t.response,r={id:t.id,rawId:IE(t.rawId),type:t.type,clientExtensionResults:{},response:{clientDataJSON:IE(n.clientDataJSON),authenticatorData:IE(n.authenticatorData),signature:IE(n.signature),...n.userHandle?{userHandle:IE(n.userHandle)}:{}}};return IE(new TextEncoder().encode(JSON.stringify(r)))}async function zE(e){let t=e.user,n=await navigator.credentials.create({publicKey:{challenge:LE(e.challenge),rp:e.rp,user:{id:LE(t.id),name:t.name,displayName:t.displayName},pubKeyCredParams:e.pubKeyCredParams,timeout:e.timeout,attestation:`none`,authenticatorSelection:{residentKey:`discouraged`,userVerification:`required`}}});if(!n)throw Error(`Setting up the passkey was cancelled.`);let r=n.response;return{id:n.id,rawId:IE(n.rawId),type:n.type,clientExtensionResults:{},response:{clientDataJSON:IE(r.clientDataJSON),attestationObject:IE(r.attestationObject),transports:r.getTransports?.()??[]}}}var BE={sign:RE,create:zE};function VE(){let[e,t]=(0,v.useState)([]);(0,v.useEffect)(()=>(xe(e=>new Promise(n=>t(t=>[...t,{step:e,answer:n}]))),()=>xe(null)),[]);let n=e[0];if(!n)return null;let r=FE(n.step),i=e=>{t(e=>e.slice(1)),n.answer(e)};return(0,V.jsx)(`div`,{className:`passkey-backdrop`,children:(0,V.jsxs)(`div`,{className:`passkey-dialog`,role:`alertdialog`,"aria-modal":`true`,"aria-labelledby":`passkey-title`,children:[(0,V.jsx)(`h3`,{id:`passkey-title`,children:r.title}),r.body.map(e=>(0,V.jsx)(`p`,{children:e},e)),(0,V.jsxs)(`div`,{className:`passkey-actions`,children:[(0,V.jsx)(`button`,{onClick:()=>i(!1),children:`Cancel`}),(0,V.jsx)(`button`,{className:`primary`,autoFocus:!0,onClick:()=>i(!0),children:r.go})]})]})})}_e(BE),ct(document.documentElement,ot(localStorage)),window.addEventListener(`storage`,e=>{e.key===`ledung.theme`?ct(document.documentElement,at(e.newValue)):e.key===null&&ct(document.documentElement,ot(localStorage))}),dn(),tE(window),(0,y.createRoot)(document.getElementById(`root`)).render((0,V.jsxs)(v.StrictMode,{children:[(0,V.jsx)(TE,{}),(0,V.jsx)(VE,{})]}));export{o as n,l as r,tv as t};
|