tmux-weblink 2.2.12 → 2.2.13

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.
@@ -5,7 +5,7 @@ var un=/\x1b\](?:10|11|110|111|104)(?:;[^\x07\x1b]*)?\x1b?(?:\\|\x07)/g;function
5
5
  `).then(()=>{ke();try{l?.close()}catch{}});return}if(o.type==="auth.ok"){o.token&&localStorage.setItem("tmux-web-token",o.token),ie=1e3,K(),q({type:"resize",cols:s.cols,rows:s.rows}),T();return}if(o.type==="auth.failed"){if(o.permanentLock||o.retryAfterMs&&o.retryAfterMs>6e4){localStorage.removeItem("tmux-web-token"),location.href="/login?error="+encodeURIComponent(o.message);return}return}if(o.type==="snapshot"&&typeof o.data=="string"){let d=Ke(ue(o.data));xe=[d],G="",U=typeof o.lines=="number"?o.lines:n.terminal.initialLines,S="live",s.reset(),K(),q({type:"resize",cols:s.cols,rows:s.rows}),s.write(d).then(()=>s.scrollToBottom());return}if(o.type==="window_changed"&&typeof o.activeIndex=="number"){let d=new URL(location.href);d.searchParams.get("window")!==String(o.activeIndex)&&(d.searchParams.set("window",String(o.activeIndex)),history.replaceState(history.state,"",d)),window.dispatchEvent(new CustomEvent("tmux:windows",{detail:o.windows}));return}if(o.type==="history"&&typeof o.data=="string"){o.lines>0&&o.data?(xe.unshift(Ke(o.data)),U+=o.lines,Ut(!0,o.lines).finally(()=>{se=!1})):se=!1;return}if(o.type==="data"&&typeof o.data=="string"){let d=Ke(ue(o.data));if(S==="connecting"){S="live",G=d,s.write(d);return}S==="live"&&(G+=d,s.write(d))}}let Ce=!1;function it(){if(Ce)return;let i=_t,o=localStorage.getItem("tmux-web-token");o&&(i+=(i.includes("?")?"&":"?")+"token="+encodeURIComponent(o)),i+=(i.includes("?")?"&":"?")+"cols="+s.cols+"&rows="+s.rows,l=new WebSocket(i),l.onopen=()=>{S="connecting",U=0,se=!1,xe=[],G="",s.reset(),ie=1e3},l.onmessage=d=>{typeof d.data=="string"&&qt(d.data)},l.onclose=()=>{j||(S="connecting",!Ce&&setTimeout(()=>{ie=Math.min(ie*2,1e4),!j&&!Ce&&it()},ie))},l.onerror=()=>l?.close()}function ae(i){q({type:"input",data:i})}function K(){return s.fit()}function ke(){e.classList.remove("terminal-pending")}function T(){r&&cancelAnimationFrame(r),c&&clearTimeout(c),K(),r=requestAnimationFrame(()=>{r=0,K()&&ke()}),c=setTimeout(()=>{K()&&ke()},120)}function Kt(){T(),setTimeout(T,50),setTimeout(T,150),setTimeout(T,300)}function at(i){return typeof i=="string"&&i.startsWith("image/")}function ot(i){return i?.files?.length?i.files[0]??null:null}function Vt(i){if(!i?.items)return null;for(let o=0;o<i.items.length;o++){let d=i.items[o];if(d?.kind==="file"&&at(d.type))return d.getAsFile()}return null}async function Xt(i){let o=new FormData,d=i instanceof File&&i.name?i.name:"upload";o.append("file",i,d);let p=localStorage.getItem("tmux-web-token"),w={};p&&(w.Authorization="Bearer "+p);let I=await fetch(Yt,{method:"POST",body:o,headers:w});if(!I.ok){let _="upload failed";try{let Be=await I.json();Be.error&&(_=Be.error)}catch{}throw new Error(_)}let V=await I.json();if(!V.path)throw new Error("no path in response");return V.path}async function Oe(i){try{let o=await Xt(i);ae(o)}catch{}}s.onData(i=>ae(i)),s.onResize(({cols:i,rows:o})=>q({type:"resize",cols:i,rows:o})),s.onScroll(()=>{S!=="live"||se||!s.isNearScrollbackTop()||(se=!0,q({type:"load_history",before:U}))});let oe=!1,le=!1,b=null,E=null,re=document.createElement("div");re.className="terminal-copy-banner",re.innerHTML='<strong>Copy mode</strong><span class="hint">drag to copy \xB7 Esc exits</span>',re.hidden=!0,e.appendChild(re);let $=document.createElement("div");$.className="terminal-copy-banner terminal-copy-toast",$.textContent="Copied",$.hidden=!0,e.appendChild($);function lt(i,o){let d=e.querySelector(".xterm-screen, canvas"),p=(d&&d.getBoundingClientRect().width>0?d:e).getBoundingClientRect(),w=p.height>0&&s.rows>0?p.height/s.rows:18,I=p.width>0&&s.cols>0?p.width/s.cols:9;return{row:Math.max(0,Math.min(s.rows-1,Math.floor((o-p.top)/w))),col:Math.max(0,Math.min(s.cols-1,Math.floor((i-p.left)/I)))}}async function Se(i){if(!i)return;try{if(navigator.clipboard?.writeText){await navigator.clipboard.writeText(i);return}}catch{}let o=document.createElement("textarea");o.value=i,o.style.position="fixed",o.style.opacity="0",o.style.pointerEvents="none",document.body.appendChild(o),o.focus(),o.select();try{document.execCommand("copy")}catch{}o.remove()}let ce;function Te(){$.hidden=!1,ce&&clearTimeout(ce),ce=setTimeout(()=>{$.hidden=!0},1e3)}function ee(i){oe=i,re.hidden=!i,e.classList.toggle("terminal-copy-mode-active",i),i&&s.focus()}function rt(){ee(!oe)}function Jt(i){j||i.button!==0||le||(oe||i.shiftKey)&&(i.preventDefault(),i.stopPropagation(),le=!0,b=lt(i.clientX,i.clientY),E=b,s.selectCells(b.col,b.row,E.col,E.row),document.addEventListener("mousemove",Ue,!0),document.addEventListener("mouseup",qe,!0))}function Ue(i){j||!le||!b||(i.preventDefault(),i.stopPropagation(),E=lt(i.clientX,i.clientY),s.selectCells(b.col,b.row,E.col,E.row))}function qe(i){if(j||!le||!b||!E)return;i.preventDefault(),i.stopPropagation(),document.removeEventListener("mousemove",Ue,!0),document.removeEventListener("mouseup",qe,!0),le=!1;let o=s.getCellsText(b.col,b.row,E.col,E.row);b=null,E=null,s.clearSelection(),ee(!1),o&&($.textContent="\u5DF2\u590D\u5236",Se(o).then(Te)),s.focus()}e.addEventListener("mousedown",Jt,!0),document.addEventListener("keydown",Qt,!0);function Qt(i){if(!(j||!s.isFocused()||i.defaultPrevented||i.isComposing)){if(oe){if(i.key==="Escape"){i.preventDefault(),i.stopPropagation(),b=null,E=null,s.clearSelection(),ee(!1);return}if(i.key==="Enter"||(i.ctrlKey||i.metaKey)&&i.code==="KeyC"){i.preventDefault(),i.stopPropagation(),Se(s.getScreenText()).then(Te),ee(!1);return}}if(i.altKey&&i.code==="KeyC"&&!i.ctrlKey&&!i.metaKey){if(i.preventDefault(),i.stopPropagation(),b&&E){let o=s.getCellsText(b.col,b.row,E.col,E.row);b=null,E=null,s.clearSelection(),ee(!1),o&&($.textContent="Copied",Se(o).then(Te))}else{let o=s.getSelection();o?(s.clearSelection(),$.textContent="Copied",Se(o).then(Te)):rt()}return}if((i.ctrlKey||i.metaKey)&&i.code==="KeyV"){i.preventDefault(),i.stopPropagation(),(async()=>{try{if(navigator.clipboard?.read){let o=await navigator.clipboard.read();for(let d of o)for(let p of d.types)if(at(p)){let w=await d.getType(p);await Oe(w);return}}}catch{}try{let o=await navigator.clipboard?.readText();o&&s.pasteText(ct(o))}catch{}})();return}}}let Me=0;function ct(i){return i.split(`\r
6
6
  `).join(`
7
7
  `).split(`
8
- `).join("\r")}async function Zt(i){let o=Vt(i.clipboardData);if(o){i.preventDefault(),i.stopPropagation();let w=Date.now();if(w-Me<50)return;Me=w,await Oe(o);return}let d=i.clipboardData?.getData("text/plain");if(!d)return;i.preventDefault(),i.stopPropagation();let p=Date.now();p-Me<50||(Me=p,s.pasteText(ct(d)))}let de=0;function Gt(i){i.preventDefault(),de++,ot(i.dataTransfer)&&e.classList.add("terminal-drag-over")}function en(i){i.preventDefault(),i.dataTransfer&&(i.dataTransfer.dropEffect="copy")}function tn(i){i.preventDefault(),de--,de<=0&&(de=0,e.classList.remove("terminal-drag-over"))}async function nn(i){i.preventDefault(),de=0,e.classList.remove("terminal-drag-over");let o=ot(i.dataTransfer);o&&await Oe(o)}function dt(i){!Wt||i.key!=="Escape"||oe||i.defaultPrevented||i.repeat||i.metaKey||i.ctrlKey||i.altKey||s.isFocused()&&(i.preventDefault(),i.stopPropagation(),ae("\x1B"))}e.addEventListener("paste",Zt),e.addEventListener("dragenter",Gt),e.addEventListener("dragover",en),e.addEventListener("dragleave",tn),e.addEventListener("drop",nn),document.addEventListener("keydown",dt,!0);function sn(i){if(i.touches.length!==1){a=null;return}let o=i.touches[0];if(!o)return;P();let d=o.clientX-e.getBoundingClientRect().left<e.clientWidth*.4?"tui":"history";a={startX:o.clientX,startY:o.clientY,lastX:o.clientX,lastY:o.clientY,lastT:performance.now(),velocity:0,scrolling:!1,zone:d,tuiAccum:0},i.stopPropagation()}function an(i){if(!a||i.touches.length!==1)return;let o=i.touches[0];if(!o)return;let d=o.clientY-a.startY,p=o.clientX-a.startX;if(!a.scrolling){if(Math.abs(d)<8||Math.abs(d)<Math.abs(p))return;a.scrolling=!0,Z=Date.now()+500}i.preventDefault(),i.stopPropagation();let w=performance.now(),I=o.clientY-a.lastY;if(a.zone==="tui"){a.tuiAccum+=I;let _=e.querySelector(".xterm-rows > div"),Be=_?_.getBoundingClientRect().height:16,mt=Math.max(24,Be*1.2);for(;Math.abs(a.tuiAccum)>=mt;)ae(a.tuiAccum>0?"\x1B[6~":"\x1B[5~"),a.tuiAccum-=Math.sign(a.tuiAccum)*mt;a.lastX=o.clientX,a.lastY=o.clientY,a.lastT=w;return}let V=w-a.lastT;V>0&&(a.velocity=I/V),cn(-I),a.lastX=o.clientX,a.lastY=o.clientY,a.lastT=w}function on(i){if(!a)return;let o=a.scrolling,d=a.zone,p=a.velocity;if(a=null,i.stopPropagation(),!o){s.focus();return}Z=Date.now()+500,i.preventDefault(),d!=="tui"&&p&&We(p)}function ln(i){a=null,P(),i.stopPropagation()}function rn(i){i.pointerType==="touch"&&Date.now()<Z&&(i.preventDefault(),i.stopPropagation())}function cn(i){let o=e.querySelector(".xterm-rows > div"),d=o?o.getBoundingClientRect().height:16,p=d>0?Math.round(i/d):i>0?1:-1;p===0&&(p=i>0?1:-1),s.scrollLines(p)}e.addEventListener("touchstart",sn,{passive:!0,capture:!0}),e.addEventListener("touchmove",an,{passive:!1,capture:!0}),e.addEventListener("touchend",on,{passive:!1,capture:!0}),e.addEventListener("touchcancel",ln,{passive:!0,capture:!0}),e.addEventListener("pointerup",rn,!0);function ut(){T()}window.addEventListener("resize",ut),window.visualViewport?.addEventListener("resize",T),window.visualViewport?.addEventListener("scroll",T);let pt=new ResizeObserver(()=>T());pt.observe(e),document.fonts?.ready.then(()=>{T(),setTimeout(T,50),setTimeout(T,200)}),e.addEventListener("focusin",Kt,!0);async function dn(){if(document.fonts?.ready)try{await Promise.race([document.fonts.ready,new Promise(i=>setTimeout(i,1e3))])}catch{}}return requestAnimationFrame(()=>{K()&&ke(),(async()=>(await dn(),K()&&q({type:"resize",cols:s.cols,rows:s.rows}),it(),T()))()}),{destroy(){if(j=!0,P(),ee(!1),ce&&clearTimeout(ce),document.removeEventListener("mousemove",Ue,!0),document.removeEventListener("mouseup",qe,!0),l){try{l.close(1e3,"session switch")}catch{}l=void 0}e.innerHTML="",e.classList.remove("terminal-pending"),window.removeEventListener("resize",ut),pt.disconnect(),document.removeEventListener("keydown",dt,!0)},focus(){s.focus()},sendInput(i){ae(i)},toggleCopyMode(){rt()}}})()}var pe=window.__TMUX_WEB_SHELL__,v=null,g=null,me=typeof window.__TMUX_WEB_SCOPE__?.agentId=="string"?window.__TMUX_WEB_SCOPE__.agentId:null,M=me;window.__tmuxWebScopeAgent=me;var Ve="sessions",Y="",De="",Ae="",ft="";function x(e){return M?"/a/"+encodeURIComponent(M)+e:e}var f=document.getElementById("sidebar-content"),X=document.getElementById("main-placeholder"),D=document.getElementById("terminal-container"),fe=document.getElementById("file-editor"),vn=document.getElementById("fe-path"),F=document.getElementById("fe-status"),he=document.getElementById("fe-content"),J=document.getElementById("fe-save"),gn=document.getElementById("fe-delete"),yn=document.getElementById("fe-back"),ht=document.getElementById("fe-new-name"),wn=document.getElementById("fe-new-btn"),Xe=document.getElementById("settings-backdrop"),vt=document.getElementById("settings-popover"),gt=document.querySelector(".sidebar");function bn(){return window.matchMedia("(max-width: 640px)").matches}function Je(){bn()&&gt.classList.add("collapsed")}function yt(){gt.classList.remove("collapsed")}document.getElementById("mode-sessions").addEventListener("click",()=>{yt(),wt("sessions")}),document.getElementById("mode-files").addEventListener("click",()=>{yt(),wt("files")});function wt(e){Ve=e,document.querySelectorAll(".mode-btn").forEach(n=>n.classList.remove("active"));let t=document.getElementById(e==="sessions"?"mode-sessions":"mode-files");t&&t.classList.add("active"),e==="sessions"?(Qe="",W()):Fn()}var Qe="";async function W(){if(Ve!=="sessions")return;try{let t=await(await fetch("/api/sidebar/sessions")).json(),n=JSON.stringify({recent:t.recent,agents:t.agents,tombstones:t.tombstones});if(n===Qe)return;Qe=n,kn(t)}catch{f.innerHTML+='<div class="file-tree-empty">Failed to load sessions</div>'}let e=document.getElementById("ns-btn");e&&e.addEventListener("click",()=>{let t=window.__openNewSessionModal;typeof t=="function"?t():document.getElementById("new-session-modal")?.classList.add("open")}),st()}var bt="tmux-web-sidebar-group-collapsed";function Lt(){try{return new Set(JSON.parse(localStorage.getItem(bt)||"[]"))}catch{return new Set}}function Ln(e){try{localStorage.setItem(bt,JSON.stringify([...e]))}catch{}}function En(e,t,n){if(!e)return"\u2026";let s=n&&(e===n||e.startsWith(n+"/"))?"~"+e.slice(n.length):e,l=s.split("/").filter(Boolean);if(l.length===0)return e;for(let r=1;r<=l.length;r++){let c=l.slice(-r).join("/");if(!t.some(a=>!a||a===e?!1:(n&&(a===n||a.startsWith(n+"/"))?"~"+a.slice(n.length):a).split("/").filter(Boolean).slice(-r).join("/")===c))return c}return s}function Et(e,t,n,s=!0){let l=new Map;for(let a of e){let u=a.path||"";l.has(u)||l.set(u,[]),l.get(u).push(a)}let r=[...l.keys()],c=Lt();for(let[a,u]of l){let m=En(a,r,t),k=c.has(a),L=document.createElement("div");L.className="session-group-header"+(k?" collapsed":""),L.title=a||"No working directory",L.innerHTML=`<span class="sg-folder">&#128193;</span><span class="sg-label">${h(m)}</span>`,L.addEventListener("click",()=>{let B=Lt(),P=L.nextElementSibling;B.has(a)?(B.delete(a),L.classList.remove("collapsed"),P?.classList.remove("collapsed")):(B.add(a),L.classList.add("collapsed"),P?.classList.add("collapsed")),Ln(B)});let H=document.createElement("div");H.className="session-group-body"+(k?" collapsed":"");for(let B of u)H.appendChild(n?xn(B,n,s):Cn(B));f.appendChild(L),f.appendChild(H)}}function xn(e,t,n){let s=document.createElement("div");return s.className="session-item"+(e.name===g&&M===t?" active":"")+(n?"":" session-offline"),s.setAttribute("data-session",e.name),s.setAttribute("data-agent",t),s.innerHTML=`<svg viewBox="0 0 24 24" fill="currentColor"><path d="${e.attached?"M19 4H5a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2V6a2 2 0 0 0-2-2zm0 14H5V6h14v12z":"M4 6h16v2H4V6zm0 5h16v2H4v-2zm0 5h16v2H4v-2z"}"></svg>
8
+ `).join("\r")}async function Zt(i){let o=Vt(i.clipboardData);if(o){i.preventDefault(),i.stopPropagation();let w=Date.now();if(w-Me<50)return;Me=w,await Oe(o);return}let d=i.clipboardData?.getData("text/plain");if(!d)return;i.preventDefault(),i.stopPropagation();let p=Date.now();p-Me<50||(Me=p,s.pasteText(ct(d)))}let de=0;function Gt(i){i.preventDefault(),de++,ot(i.dataTransfer)&&e.classList.add("terminal-drag-over")}function en(i){i.preventDefault(),i.dataTransfer&&(i.dataTransfer.dropEffect="copy")}function tn(i){i.preventDefault(),de--,de<=0&&(de=0,e.classList.remove("terminal-drag-over"))}async function nn(i){i.preventDefault(),de=0,e.classList.remove("terminal-drag-over");let o=ot(i.dataTransfer);o&&await Oe(o)}function dt(i){!Wt||i.key!=="Escape"||oe||i.defaultPrevented||i.repeat||i.metaKey||i.ctrlKey||i.altKey||s.isFocused()&&(i.preventDefault(),i.stopPropagation(),ae("\x1B"))}e.addEventListener("paste",Zt),e.addEventListener("dragenter",Gt),e.addEventListener("dragover",en),e.addEventListener("dragleave",tn),e.addEventListener("drop",nn),document.addEventListener("keydown",dt,!0);function sn(i){if(i.touches.length!==1){a=null;return}let o=i.touches[0];if(!o)return;P();let d=o.clientX-e.getBoundingClientRect().left<e.clientWidth*.4?"tui":"history";a={startX:o.clientX,startY:o.clientY,lastX:o.clientX,lastY:o.clientY,lastT:performance.now(),velocity:0,scrolling:!1,zone:d,tuiAccum:0},i.stopPropagation()}function an(i){if(!a||i.touches.length!==1)return;let o=i.touches[0];if(!o)return;let d=o.clientY-a.startY,p=o.clientX-a.startX;if(!a.scrolling){if(Math.abs(d)<8||Math.abs(d)<Math.abs(p))return;a.scrolling=!0,Z=Date.now()+500}i.preventDefault(),i.stopPropagation();let w=performance.now(),I=o.clientY-a.lastY;if(a.zone==="tui"){a.tuiAccum+=I;let _=e.querySelector(".xterm-rows > div"),Be=_?_.getBoundingClientRect().height:16,mt=Math.max(24,Be*1.2);for(;Math.abs(a.tuiAccum)>=mt;)ae(a.tuiAccum>0?"\x1B[5~":"\x1B[6~"),a.tuiAccum-=Math.sign(a.tuiAccum)*mt;a.lastX=o.clientX,a.lastY=o.clientY,a.lastT=w;return}let V=w-a.lastT;V>0&&(a.velocity=I/V),cn(-I),a.lastX=o.clientX,a.lastY=o.clientY,a.lastT=w}function on(i){if(!a)return;let o=a.scrolling,d=a.zone,p=a.velocity;if(a=null,i.stopPropagation(),!o){s.focus();return}Z=Date.now()+500,i.preventDefault(),d!=="tui"&&p&&We(p)}function ln(i){a=null,P(),i.stopPropagation()}function rn(i){i.pointerType==="touch"&&Date.now()<Z&&(i.preventDefault(),i.stopPropagation())}function cn(i){let o=e.querySelector(".xterm-rows > div"),d=o?o.getBoundingClientRect().height:16,p=d>0?Math.round(i/d):i>0?1:-1;p===0&&(p=i>0?1:-1),s.scrollLines(p)}e.addEventListener("touchstart",sn,{passive:!0,capture:!0}),e.addEventListener("touchmove",an,{passive:!1,capture:!0}),e.addEventListener("touchend",on,{passive:!1,capture:!0}),e.addEventListener("touchcancel",ln,{passive:!0,capture:!0}),e.addEventListener("pointerup",rn,!0);function ut(){T()}window.addEventListener("resize",ut),window.visualViewport?.addEventListener("resize",T),window.visualViewport?.addEventListener("scroll",T);let pt=new ResizeObserver(()=>T());pt.observe(e),document.fonts?.ready.then(()=>{T(),setTimeout(T,50),setTimeout(T,200)}),e.addEventListener("focusin",Kt,!0);async function dn(){if(document.fonts?.ready)try{await Promise.race([document.fonts.ready,new Promise(i=>setTimeout(i,1e3))])}catch{}}return requestAnimationFrame(()=>{K()&&ke(),(async()=>(await dn(),K()&&q({type:"resize",cols:s.cols,rows:s.rows}),it(),T()))()}),{destroy(){if(j=!0,P(),ee(!1),ce&&clearTimeout(ce),document.removeEventListener("mousemove",Ue,!0),document.removeEventListener("mouseup",qe,!0),l){try{l.close(1e3,"session switch")}catch{}l=void 0}e.innerHTML="",e.classList.remove("terminal-pending"),window.removeEventListener("resize",ut),pt.disconnect(),document.removeEventListener("keydown",dt,!0)},focus(){s.focus()},sendInput(i){ae(i)},toggleCopyMode(){rt()}}})()}var pe=window.__TMUX_WEB_SHELL__,v=null,g=null,me=typeof window.__TMUX_WEB_SCOPE__?.agentId=="string"?window.__TMUX_WEB_SCOPE__.agentId:null,M=me;window.__tmuxWebScopeAgent=me;var Ve="sessions",Y="",De="",Ae="",ft="";function x(e){return M?"/a/"+encodeURIComponent(M)+e:e}var f=document.getElementById("sidebar-content"),X=document.getElementById("main-placeholder"),D=document.getElementById("terminal-container"),fe=document.getElementById("file-editor"),vn=document.getElementById("fe-path"),F=document.getElementById("fe-status"),he=document.getElementById("fe-content"),J=document.getElementById("fe-save"),gn=document.getElementById("fe-delete"),yn=document.getElementById("fe-back"),ht=document.getElementById("fe-new-name"),wn=document.getElementById("fe-new-btn"),Xe=document.getElementById("settings-backdrop"),vt=document.getElementById("settings-popover"),gt=document.querySelector(".sidebar");function bn(){return window.matchMedia("(max-width: 640px)").matches}function Je(){bn()&&gt.classList.add("collapsed")}function yt(){gt.classList.remove("collapsed")}document.getElementById("mode-sessions").addEventListener("click",()=>{yt(),wt("sessions")}),document.getElementById("mode-files").addEventListener("click",()=>{yt(),wt("files")});function wt(e){Ve=e,document.querySelectorAll(".mode-btn").forEach(n=>n.classList.remove("active"));let t=document.getElementById(e==="sessions"?"mode-sessions":"mode-files");t&&t.classList.add("active"),e==="sessions"?(Qe="",W()):Fn()}var Qe="";async function W(){if(Ve!=="sessions")return;try{let t=await(await fetch("/api/sidebar/sessions")).json(),n=JSON.stringify({recent:t.recent,agents:t.agents,tombstones:t.tombstones});if(n===Qe)return;Qe=n,kn(t)}catch{f.innerHTML+='<div class="file-tree-empty">Failed to load sessions</div>'}let e=document.getElementById("ns-btn");e&&e.addEventListener("click",()=>{let t=window.__openNewSessionModal;typeof t=="function"?t():document.getElementById("new-session-modal")?.classList.add("open")}),st()}var bt="tmux-web-sidebar-group-collapsed";function Lt(){try{return new Set(JSON.parse(localStorage.getItem(bt)||"[]"))}catch{return new Set}}function Ln(e){try{localStorage.setItem(bt,JSON.stringify([...e]))}catch{}}function En(e,t,n){if(!e)return"\u2026";let s=n&&(e===n||e.startsWith(n+"/"))?"~"+e.slice(n.length):e,l=s.split("/").filter(Boolean);if(l.length===0)return e;for(let r=1;r<=l.length;r++){let c=l.slice(-r).join("/");if(!t.some(a=>!a||a===e?!1:(n&&(a===n||a.startsWith(n+"/"))?"~"+a.slice(n.length):a).split("/").filter(Boolean).slice(-r).join("/")===c))return c}return s}function Et(e,t,n,s=!0){let l=new Map;for(let a of e){let u=a.path||"";l.has(u)||l.set(u,[]),l.get(u).push(a)}let r=[...l.keys()],c=Lt();for(let[a,u]of l){let m=En(a,r,t),k=c.has(a),L=document.createElement("div");L.className="session-group-header"+(k?" collapsed":""),L.title=a||"No working directory",L.innerHTML=`<span class="sg-folder">&#128193;</span><span class="sg-label">${h(m)}</span>`,L.addEventListener("click",()=>{let B=Lt(),P=L.nextElementSibling;B.has(a)?(B.delete(a),L.classList.remove("collapsed"),P?.classList.remove("collapsed")):(B.add(a),L.classList.add("collapsed"),P?.classList.add("collapsed")),Ln(B)});let H=document.createElement("div");H.className="session-group-body"+(k?" collapsed":"");for(let B of u)H.appendChild(n?xn(B,n,s):Cn(B));f.appendChild(L),f.appendChild(H)}}function xn(e,t,n){let s=document.createElement("div");return s.className="session-item"+(e.name===g&&M===t?" active":"")+(n?"":" session-offline"),s.setAttribute("data-session",e.name),s.setAttribute("data-agent",t),s.innerHTML=`<svg viewBox="0 0 24 24" fill="currentColor"><path d="${e.attached?"M19 4H5a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2V6a2 2 0 0 0-2-2zm0 14H5V6h14v12z":"M4 6h16v2H4V6zm0 5h16v2H4v-2zm0 5h16v2H4v-2z"}"></svg>
9
9
  <span>${h(e.name)}</span>${n?"":'<span class="meta">offline</span>'}`,n&&s.addEventListener("click",l=>{l.target.closest(".session-edit-btn")||ve(e.name,t)}),s}function Cn(e){let t=document.createElement("div");t.className="session-item"+(e.name===g&&!M?" active":""),t.setAttribute("data-session",e.name),t.innerHTML=`<svg viewBox="0 0 24 24" fill="currentColor"><path d="${e.attached?"M19 4H5a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2V6a2 2 0 0 0-2-2zm0 14H5V6h14v12z":"M4 6h16v2H4V6zm0 5h16v2H4v-2zm0 5h16v2H4v-2z"}"></svg>
10
10
  <span>${h(e.name)}</span>
11
11
  <button class="session-edit-btn" data-session="${h(e.name)}" title="Edit session"><svg viewBox="0 0 24 24" fill="currentColor" width="14" height="14"><path d="M3 17.25V21h3.75L17.81 9.94l-3.75-3.75L3 17.25zM20.71 7.04a1 1 0 000-1.41l-2.34-2.34a1 1 0 00-1.41 0l-1.83 1.83 3.75 3.75 1.83-1.83z"/></svg></button>
@@ -5,4 +5,4 @@ const Rt=/\x1b\](?:10|11|110|111|104)(?:;[^\x07\x1b]*)?\x1b?(?:\\|\x07)/g;functi
5
5
  `).then(()=>{W();try{l?.close()}catch{}});return}if(e.type==="auth.ok"){e.token&&localStorage.setItem("tmux-web-token",e.token),z=1e3,S(),L({type:"resize",cols:n.cols,rows:n.rows}),y();return}if(e.type==="auth.failed"){if(e.permanentLock||e.retryAfterMs&&e.retryAfterMs>6e4){localStorage.removeItem("tmux-web-token"),location.href="/login?error="+encodeURIComponent(e.message);return}return}if(e.type==="snapshot"&&typeof e.data=="string"){const i=nt(N(e.data));H=[i],A="",M=typeof e.lines=="number"?e.lines:r.terminal.initialLines,g="live",n.reset(),S(),L({type:"resize",cols:n.cols,rows:n.rows}),n.write(i).then(()=>n.scrollToBottom());return}if(e.type==="window_changed"&&typeof e.activeIndex=="number"){const i=new URL(location.href);i.searchParams.get("window")!==String(e.activeIndex)&&(i.searchParams.set("window",String(e.activeIndex)),history.replaceState(history.state,"",i)),window.dispatchEvent(new CustomEvent("tmux:windows",{detail:e.windows}));return}if(e.type==="history"&&typeof e.data=="string"){e.lines>0&&e.data?(H.unshift(nt(e.data)),M+=e.lines,xt(!0,e.lines).finally(()=>{F=!1})):F=!1;return}if(e.type==="data"&&typeof e.data=="string"){const i=nt(N(e.data));if(g==="connecting"){g="live",A=i,n.write(i);return}g==="live"&&(A+=i,n.write(i))}}let j=!1;function it(){if(j)return;let t=wt;const e=localStorage.getItem("tmux-web-token");e&&(t+=(t.includes("?")?"&":"?")+"token="+encodeURIComponent(e)),t+=(t.includes("?")?"&":"?")+"cols="+n.cols+"&rows="+n.rows,l=new WebSocket(t),l.onopen=()=>{g="connecting",M=0,F=!1,H=[],A="",n.reset(),z=1e3},l.onmessage=i=>{typeof i.data=="string"&&Tt(i.data)},l.onclose=()=>{b||(g="connecting",!j&&setTimeout(()=>{z=Math.min(z*2,1e4),!b&&!j&&it()},z))},l.onerror=()=>l?.close()}function B(t){L({type:"input",data:t})}function S(){return n.fit()}function W(){s.classList.remove("terminal-pending")}function y(){d&&cancelAnimationFrame(d),m&&clearTimeout(m),S(),d=requestAnimationFrame(()=>{d=0,S()&&W()}),m=setTimeout(()=>{S()&&W()},120)}function bt(){y(),setTimeout(y,50),setTimeout(y,150),setTimeout(y,300)}function rt(t){return typeof t=="string"&&t.startsWith("image/")}function st(t){return t?.files?.length?t.files[0]??null:null}function Et(t){if(!t?.items)return null;for(let e=0;e<t.items.length;e++){const i=t.items[e];if(i?.kind==="file"&&rt(i.type))return i.getAsFile()}return null}async function Mt(t){const e=new FormData,i=t instanceof File&&t.name?t.name:"upload";e.append("file",t,i);const c=localStorage.getItem("tmux-web-token"),u={};c&&(u.Authorization="Bearer "+c);const v=await fetch(gt,{method:"POST",body:e,headers:u});if(!v.ok){let C="upload failed";try{const D=await v.json();D.error&&(C=D.error)}catch{}throw new Error(C)}const x=await v.json();if(!x.path)throw new Error("no path in response");return x.path}async function Z(t){try{const e=await Mt(t);B(e)}catch{}}n.onData(t=>B(t)),n.onResize(({cols:t,rows:e})=>L({type:"resize",cols:t,rows:e})),n.onScroll(()=>{g!=="live"||F||!n.isNearScrollbackTop()||(F=!0,L({type:"load_history",before:M}))});let K=!1,X=!1,p=null,w=null;const R=document.createElement("div");R.className="terminal-copy-banner",R.innerHTML='<strong>Copy mode</strong><span class="hint">drag to copy \xB7 Esc exits</span>',R.hidden=!0,s.appendChild(R);const T=document.createElement("div");T.className="terminal-copy-banner terminal-copy-toast",T.textContent="Copied",T.hidden=!0,s.appendChild(T);function at(t,e){const i=s.querySelector(".xterm-screen, canvas"),u=(i&&i.getBoundingClientRect().width>0?i:s).getBoundingClientRect(),v=u.height>0&&n.rows>0?u.height/n.rows:18,x=u.width>0&&n.cols>0?u.width/n.cols:9;return{row:Math.max(0,Math.min(n.rows-1,Math.floor((e-u.top)/v))),col:Math.max(0,Math.min(n.cols-1,Math.floor((t-u.left)/x)))}}async function V(t){if(!t)return;try{if(navigator.clipboard?.writeText){await navigator.clipboard.writeText(t);return}}catch{}const e=document.createElement("textarea");e.value=t,e.style.position="fixed",e.style.opacity="0",e.style.pointerEvents="none",document.body.appendChild(e),e.focus(),e.select();try{document.execCommand("copy")}catch{}e.remove()}let O;function J(){T.hidden=!1,O&&clearTimeout(O),O=setTimeout(()=>{T.hidden=!0},1e3)}function Y(t){K=t,R.hidden=!t,s.classList.toggle("terminal-copy-mode-active",t),t&&n.focus()}function lt(){Y(!K)}function Lt(t){b||t.button!==0||X||(K||t.shiftKey)&&(t.preventDefault(),t.stopPropagation(),X=!0,p=at(t.clientX,t.clientY),w=p,n.selectCells(p.col,p.row,w.col,w.row),document.addEventListener("mousemove",tt,!0),document.addEventListener("mouseup",et,!0))}function tt(t){b||!X||!p||(t.preventDefault(),t.stopPropagation(),w=at(t.clientX,t.clientY),n.selectCells(p.col,p.row,w.col,w.row))}function et(t){if(b||!X||!p||!w)return;t.preventDefault(),t.stopPropagation(),document.removeEventListener("mousemove",tt,!0),document.removeEventListener("mouseup",et,!0),X=!1;const e=n.getCellsText(p.col,p.row,w.col,w.row);p=null,w=null,n.clearSelection(),Y(!1),e&&(T.textContent="\u5DF2\u590D\u5236",V(e).then(J)),n.focus()}s.addEventListener("mousedown",Lt,!0),document.addEventListener("keydown",St,!0);function St(t){if(!(b||!n.isFocused()||t.defaultPrevented||t.isComposing)){if(K){if(t.key==="Escape"){t.preventDefault(),t.stopPropagation(),p=null,w=null,n.clearSelection(),Y(!1);return}if(t.key==="Enter"||(t.ctrlKey||t.metaKey)&&t.code==="KeyC"){t.preventDefault(),t.stopPropagation(),V(n.getScreenText()).then(J),Y(!1);return}}if(t.altKey&&t.code==="KeyC"&&!t.ctrlKey&&!t.metaKey){if(t.preventDefault(),t.stopPropagation(),p&&w){const e=n.getCellsText(p.col,p.row,w.col,w.row);p=null,w=null,n.clearSelection(),Y(!1),e&&(T.textContent="Copied",V(e).then(J))}else{const e=n.getSelection();e?(n.clearSelection(),T.textContent="Copied",V(e).then(J)):lt()}return}if((t.ctrlKey||t.metaKey)&&t.code==="KeyV"){t.preventDefault(),t.stopPropagation(),(async()=>{try{if(navigator.clipboard?.read){const e=await navigator.clipboard.read();for(const i of e)for(const c of i.types)if(rt(c)){const u=await i.getType(c);await Z(u);return}}}catch{}try{const e=await navigator.clipboard?.readText();e&&n.pasteText(ct(e))}catch{}})();return}}}let G=0;function ct(t){return t.split(`\r
6
6
  `).join(`
7
7
  `).split(`
8
- `).join("\r")}async function Ct(t){const e=Et(t.clipboardData);if(e){t.preventDefault(),t.stopPropagation();const u=Date.now();if(u-G<50)return;G=u,await Z(e);return}const i=t.clipboardData?.getData("text/plain");if(!i)return;t.preventDefault(),t.stopPropagation();const c=Date.now();c-G<50||(G=c,n.pasteText(ct(i)))}let q=0;function Dt(t){t.preventDefault(),q++,st(t.dataTransfer)&&s.classList.add("terminal-drag-over")}function Pt(t){t.preventDefault(),t.dataTransfer&&(t.dataTransfer.dropEffect="copy")}function It(t){t.preventDefault(),q--,q<=0&&(q=0,s.classList.remove("terminal-drag-over"))}async function kt(t){t.preventDefault(),q=0,s.classList.remove("terminal-drag-over");const e=st(t.dataTransfer);e&&await Z(e)}function ut(t){!yt||t.key!=="Escape"||K||t.defaultPrevented||t.repeat||t.metaKey||t.ctrlKey||t.altKey||n.isFocused()&&(t.preventDefault(),t.stopPropagation(),B("\x1B"))}s.addEventListener("paste",Ct),s.addEventListener("dragenter",Dt),s.addEventListener("dragover",Pt),s.addEventListener("dragleave",It),s.addEventListener("drop",kt),document.addEventListener("keydown",ut,!0);function At(t){if(t.touches.length!==1){a=null;return}const e=t.touches[0];if(!e)return;I();const i=e.clientX-s.getBoundingClientRect().left<s.clientWidth*.4?"tui":"history";a={startX:e.clientX,startY:e.clientY,lastX:e.clientX,lastY:e.clientY,lastT:performance.now(),velocity:0,scrolling:!1,zone:i,tuiAccum:0},t.stopPropagation()}function Yt(t){if(!a||t.touches.length!==1)return;const e=t.touches[0];if(!e)return;const i=e.clientY-a.startY,c=e.clientX-a.startX;if(!a.scrolling){if(Math.abs(i)<8||Math.abs(i)<Math.abs(c))return;a.scrolling=!0,k=Date.now()+500}t.preventDefault(),t.stopPropagation();const u=performance.now(),v=e.clientY-a.lastY;if(a.zone==="tui"){a.tuiAccum+=v;const C=s.querySelector(".xterm-rows > div"),D=C?C.getBoundingClientRect().height:16,mt=Math.max(24,D*1.2);for(;Math.abs(a.tuiAccum)>=mt;)B(a.tuiAccum>0?"\x1B[6~":"\x1B[5~"),a.tuiAccum-=Math.sign(a.tuiAccum)*mt;a.lastX=e.clientX,a.lastY=e.clientY,a.lastT=u;return}const x=u-a.lastT;x>0&&(a.velocity=v/x),Kt(-v),a.lastX=e.clientX,a.lastY=e.clientY,a.lastT=u}function Ft(t){if(!a)return;const e=a.scrolling,i=a.zone,c=a.velocity;if(a=null,t.stopPropagation(),!e){n.focus();return}k=Date.now()+500,t.preventDefault(),i!=="tui"&&c&&Q(c)}function zt(t){a=null,I(),t.stopPropagation()}function Bt(t){t.pointerType==="touch"&&Date.now()<k&&(t.preventDefault(),t.stopPropagation())}function Kt(t){const e=s.querySelector(".xterm-rows > div"),i=e?e.getBoundingClientRect().height:16;let c=i>0?Math.round(t/i):t>0?1:-1;c===0&&(c=t>0?1:-1),n.scrollLines(c)}s.addEventListener("touchstart",At,{passive:!0,capture:!0}),s.addEventListener("touchmove",Yt,{passive:!1,capture:!0}),s.addEventListener("touchend",Ft,{passive:!1,capture:!0}),s.addEventListener("touchcancel",zt,{passive:!0,capture:!0}),s.addEventListener("pointerup",Bt,!0);function ft(){y()}window.addEventListener("resize",ft),window.visualViewport?.addEventListener("resize",y),window.visualViewport?.addEventListener("scroll",y);const dt=new ResizeObserver(()=>y());dt.observe(s),document.fonts?.ready.then(()=>{y(),setTimeout(y,50),setTimeout(y,200)}),s.addEventListener("focusin",bt,!0);async function Xt(){if(document.fonts?.ready)try{await Promise.race([document.fonts.ready,new Promise(t=>setTimeout(t,1e3))])}catch{}}return requestAnimationFrame(()=>{S()&&W(),(async()=>(await Xt(),S()&&L({type:"resize",cols:n.cols,rows:n.rows}),it(),y()))()}),{destroy(){if(b=!0,I(),Y(!1),O&&clearTimeout(O),document.removeEventListener("mousemove",tt,!0),document.removeEventListener("mouseup",et,!0),l){try{l.close(1e3,"session switch")}catch{}l=void 0}s.innerHTML="",s.classList.remove("terminal-pending"),window.removeEventListener("resize",ft),dt.disconnect(),document.removeEventListener("keydown",ut,!0)},focus(){n.focus()},sendInput(t){B(t)},toggleCopyMode(){lt()}}})()}export{Nt as initTerminal,nt as stripAltScreenSequences};
8
+ `).join("\r")}async function Ct(t){const e=Et(t.clipboardData);if(e){t.preventDefault(),t.stopPropagation();const u=Date.now();if(u-G<50)return;G=u,await Z(e);return}const i=t.clipboardData?.getData("text/plain");if(!i)return;t.preventDefault(),t.stopPropagation();const c=Date.now();c-G<50||(G=c,n.pasteText(ct(i)))}let q=0;function Dt(t){t.preventDefault(),q++,st(t.dataTransfer)&&s.classList.add("terminal-drag-over")}function Pt(t){t.preventDefault(),t.dataTransfer&&(t.dataTransfer.dropEffect="copy")}function It(t){t.preventDefault(),q--,q<=0&&(q=0,s.classList.remove("terminal-drag-over"))}async function kt(t){t.preventDefault(),q=0,s.classList.remove("terminal-drag-over");const e=st(t.dataTransfer);e&&await Z(e)}function ut(t){!yt||t.key!=="Escape"||K||t.defaultPrevented||t.repeat||t.metaKey||t.ctrlKey||t.altKey||n.isFocused()&&(t.preventDefault(),t.stopPropagation(),B("\x1B"))}s.addEventListener("paste",Ct),s.addEventListener("dragenter",Dt),s.addEventListener("dragover",Pt),s.addEventListener("dragleave",It),s.addEventListener("drop",kt),document.addEventListener("keydown",ut,!0);function At(t){if(t.touches.length!==1){a=null;return}const e=t.touches[0];if(!e)return;I();const i=e.clientX-s.getBoundingClientRect().left<s.clientWidth*.4?"tui":"history";a={startX:e.clientX,startY:e.clientY,lastX:e.clientX,lastY:e.clientY,lastT:performance.now(),velocity:0,scrolling:!1,zone:i,tuiAccum:0},t.stopPropagation()}function Yt(t){if(!a||t.touches.length!==1)return;const e=t.touches[0];if(!e)return;const i=e.clientY-a.startY,c=e.clientX-a.startX;if(!a.scrolling){if(Math.abs(i)<8||Math.abs(i)<Math.abs(c))return;a.scrolling=!0,k=Date.now()+500}t.preventDefault(),t.stopPropagation();const u=performance.now(),v=e.clientY-a.lastY;if(a.zone==="tui"){a.tuiAccum+=v;const C=s.querySelector(".xterm-rows > div"),D=C?C.getBoundingClientRect().height:16,mt=Math.max(24,D*1.2);for(;Math.abs(a.tuiAccum)>=mt;)B(a.tuiAccum>0?"\x1B[5~":"\x1B[6~"),a.tuiAccum-=Math.sign(a.tuiAccum)*mt;a.lastX=e.clientX,a.lastY=e.clientY,a.lastT=u;return}const x=u-a.lastT;x>0&&(a.velocity=v/x),Kt(-v),a.lastX=e.clientX,a.lastY=e.clientY,a.lastT=u}function Ft(t){if(!a)return;const e=a.scrolling,i=a.zone,c=a.velocity;if(a=null,t.stopPropagation(),!e){n.focus();return}k=Date.now()+500,t.preventDefault(),i!=="tui"&&c&&Q(c)}function zt(t){a=null,I(),t.stopPropagation()}function Bt(t){t.pointerType==="touch"&&Date.now()<k&&(t.preventDefault(),t.stopPropagation())}function Kt(t){const e=s.querySelector(".xterm-rows > div"),i=e?e.getBoundingClientRect().height:16;let c=i>0?Math.round(t/i):t>0?1:-1;c===0&&(c=t>0?1:-1),n.scrollLines(c)}s.addEventListener("touchstart",At,{passive:!0,capture:!0}),s.addEventListener("touchmove",Yt,{passive:!1,capture:!0}),s.addEventListener("touchend",Ft,{passive:!1,capture:!0}),s.addEventListener("touchcancel",zt,{passive:!0,capture:!0}),s.addEventListener("pointerup",Bt,!0);function ft(){y()}window.addEventListener("resize",ft),window.visualViewport?.addEventListener("resize",y),window.visualViewport?.addEventListener("scroll",y);const dt=new ResizeObserver(()=>y());dt.observe(s),document.fonts?.ready.then(()=>{y(),setTimeout(y,50),setTimeout(y,200)}),s.addEventListener("focusin",bt,!0);async function Xt(){if(document.fonts?.ready)try{await Promise.race([document.fonts.ready,new Promise(t=>setTimeout(t,1e3))])}catch{}}return requestAnimationFrame(()=>{S()&&W(),(async()=>(await Xt(),S()&&L({type:"resize",cols:n.cols,rows:n.rows}),it(),y()))()}),{destroy(){if(b=!0,I(),Y(!1),O&&clearTimeout(O),document.removeEventListener("mousemove",tt,!0),document.removeEventListener("mouseup",et,!0),l){try{l.close(1e3,"session switch")}catch{}l=void 0}s.innerHTML="",s.classList.remove("terminal-pending"),window.removeEventListener("resize",ft),dt.disconnect(),document.removeEventListener("keydown",ut,!0)},focus(){n.focus()},sendInput(t){B(t)},toggleCopyMode(){lt()}}})()}export{Nt as initTerminal,nt as stripAltScreenSequences};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "tmux-weblink",
3
- "version": "2.2.12",
3
+ "version": "2.2.13",
4
4
  "description": "Access your tmux sessions from the browser. A continuation of tmux-web and persalink.",
5
5
  "type": "module",
6
6
  "bin": {