@burtson-labs/bandit-stealth-cli 1.7.157 → 1.7.158

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.
Files changed (2) hide show
  1. package/dist/cli.js +2 -2
  2. package/package.json +1 -1
package/dist/cli.js CHANGED
@@ -1269,7 +1269,7 @@ ${(()=>{let H=`Bandit insights \u2014 ${new Date(s).toISOString().slice(0,10)}`,
1269
1269
  <h1>You're signed in.</h1>
1270
1270
  <p>Bandit picked up your session. You can close this tab and return to your terminal.</p>
1271
1271
  </div>
1272
- </body></html>`;t(jbr,"startLoopbackListener");t(Lbr,"openBrowser");t($br,"buildDefaultDeviceLabel");t(Bbr,"runOAuthSignIn")});var Iue=Ot((J4r,zbr)=>{zbr.exports={name:"@burtson-labs/bandit-stealth-cli",version:"1.7.157",description:"Bandit \u2014 a local-first AI coding agent for your terminal. Same runtime as the Bandit Stealth VS Code / Cursor extension.",keywords:["ai","agent","cli","coding-agent","llm","ollama","local-first","bandit","burtson-labs","terminal","repl","developer-tools"],homepage:"https://burtson.ai",bugs:{email:"team@burtson.ai"},license:"MIT",author:{name:"Burtson Labs",email:"team@burtson.ai",url:"https://burtson.ai"},bin:{bandit:"./dist/cli.js"},main:"dist/cli.js",files:["dist/cli.js","README.md","LICENSE"],engines:{node:">=20"},publishConfig:{access:"public"},scripts:{typecheck:"tsc -p tsconfig.json --noEmit",build:"node build.mjs","build:publish":"node build.mjs --publish",dev:"node build.mjs --watch",start:"node dist/cli.js",smoke:"node build.mjs && node dist/__smoke__/smoke.js",integration:"node build.mjs && node dist/__integration__/ollama.js",eval:"node build.mjs && node dist/__eval__/eval.js",benchmark:"node build.mjs && node dist/__eval__/benchmark.js","gen-logo":"node scripts/gen-logo.mjs","preview-banner":"node scripts/preview-banner.mjs",clean:"rm -rf dist",prepack:"node scripts/prepack.mjs",postpack:"node scripts/postpack.mjs",prepublishOnly:"pnpm run clean && pnpm run typecheck && pnpm run build:publish"},dependencies:{"pdf-parse":"^2.4.5"},devDependencies:{"@burtson-labs/agent-core":"workspace:*","@burtson-labs/host-kit":"workspace:*","@burtson-labs/stealth-core-runtime":"workspace:*","@types/node":"^20.11.0","@types/pdf-parse":"^1.1.5","@types/pngjs":"^6.0.5",esbuild:"^0.28.0",pngjs:"^7.0.0",typescript:"^5.4.0"}}});var vSr={};module.exports=pet(vSr);var Cm=hu(require("fs")),Aue=hu(require("os")),Kp=hu(require("path")),h9=hu(require("readline")),Nue=hu(require("child_process")),Xp=hu(ZV()),o1=hu(uOe());var KF=hu(require("fs")),fOe=hu(require("os")),w6=hu(require("path")),cZ=hu(require("child_process"));function pb(a){return a==="~"?fOe.homedir():a.startsWith("~/")?w6.join(fOe.homedir(),a.slice(2)):a}t(pb,"expandHome");var l9=16*1024,oZ=32*1024,Uft=1e4,Cvr=3e4,_Oe=200,dOe=new Set(["node_modules",".git","dist","build","out",".next",".turbo","coverage","target","__pycache__",".venv","venv"]);function Pvr(a){let s=t(d=>{let f=d.match(/^(.*?)\{([^}]+)\}(.*)$/);if(!f)return[d];let[,y,x,P]=f;return x.split(",").map(M=>`${y}${M.trim()}${P}`)},"braceExpand"),c=a.match(/^([^*{}]+?)\/\*\*\/(.+)$/);if(c){let[,d,f]=c;return{includes:s(f),subDir:d}}return{includes:s(a),subDir:""}}t(Pvr,"expandGlobForGrep");var XF=class{constructor(s,c,d={}){this.workspaceRoot=s;this.languageAdapters=c;this.options=d;this._readFiles=new Set;this.customRepoRoots=d.customRepoRoots&&d.customRepoRoots.length>0?d.customRepoRoots:void 0}static{t(this,"CliToolExecutionContext")}markFileRead(s){this._readFiles.add(pb(s))}hasFileBeenRead(s){return this._readFiles.has(pb(s))}async readFile(s){return KF.promises.readFile(pb(s),"utf-8")}async writeFile(s,c){let d=pb(s);if(this.options.approveWrite&&!await this.options.approveWrite(d,c))throw new Error(`Write to ${d} rejected by user`);await KF.promises.mkdir(w6.dirname(d),{recursive:!0}),await KF.promises.writeFile(d,c,"utf-8")}async listFiles(s,c){let d=pb(c??this.workspaceRoot),f=Evr(s),y=[];return await qft(d,d,f,y),y.slice(0,_Oe).sort()}async listDirectoryEntries(s){let c=pb(s),d=await KF.promises.readdir(c,{withFileTypes:!0}),f=[];for(let y of d){if(y.name.startsWith("."))continue;let x=y.isDirectory();if(y.isSymbolicLink())try{x=(await KF.promises.stat(w6.join(c,y.name))).isDirectory()}catch{x=!1}f.push(x?`${y.name}/`:y.name)}return f.sort()}async searchCode(s,c,d){let f=pb(c??this.workspaceRoot);return this.runRipgrep(s,f,d).catch(()=>this.runGrep(s,f,d))}async runCommand(s,c,d){let f=c.map(pb),y=d?pb(d):this.workspaceRoot,x={...process.env};if((s.split(/[\\/]/).pop()??s)==="gh")for(let M of["GITHUB_TOKEN","GH_TOKEN"]){let L=x[M];typeof L=="string"&&L.trim()===""&&delete x[M]}return new Promise(M=>{let L="",J="",H=cZ.spawn(s,f,{cwd:y,shell:process.platform==="win32",env:x}),q=setTimeout(()=>{H.kill("SIGTERM"),M({stdout:L.slice(0,oZ),stderr:J+`
1272
+ </body></html>`;t(jbr,"startLoopbackListener");t(Lbr,"openBrowser");t($br,"buildDefaultDeviceLabel");t(Bbr,"runOAuthSignIn")});var Iue=Ot((J4r,zbr)=>{zbr.exports={name:"@burtson-labs/bandit-stealth-cli",version:"1.7.158",description:"Bandit \u2014 a local-first AI coding agent for your terminal. Same runtime as the Bandit Stealth VS Code / Cursor extension.",keywords:["ai","agent","cli","coding-agent","llm","ollama","local-first","bandit","burtson-labs","terminal","repl","developer-tools"],homepage:"https://burtson.ai",bugs:{email:"team@burtson.ai"},license:"MIT",author:{name:"Burtson Labs",email:"team@burtson.ai",url:"https://burtson.ai"},bin:{bandit:"./dist/cli.js"},main:"dist/cli.js",files:["dist/cli.js","README.md","LICENSE"],engines:{node:">=20"},publishConfig:{access:"public"},scripts:{typecheck:"tsc -p tsconfig.json --noEmit",build:"node build.mjs","build:publish":"node build.mjs --publish",dev:"node build.mjs --watch",start:"node dist/cli.js",smoke:"node build.mjs && node dist/__smoke__/smoke.js",integration:"node build.mjs && node dist/__integration__/ollama.js",eval:"node build.mjs && node dist/__eval__/eval.js",benchmark:"node build.mjs && node dist/__eval__/benchmark.js","gen-logo":"node scripts/gen-logo.mjs","preview-banner":"node scripts/preview-banner.mjs",clean:"rm -rf dist",prepack:"node scripts/prepack.mjs",postpack:"node scripts/postpack.mjs",prepublishOnly:"pnpm run clean && pnpm run typecheck && pnpm run build:publish"},dependencies:{"pdf-parse":"^2.4.5"},devDependencies:{"@burtson-labs/agent-core":"workspace:*","@burtson-labs/host-kit":"workspace:*","@burtson-labs/stealth-core-runtime":"workspace:*","@types/node":"^20.11.0","@types/pdf-parse":"^1.1.5","@types/pngjs":"^6.0.5",esbuild:"^0.28.0",pngjs:"^7.0.0",typescript:"^5.4.0"}}});var vSr={};module.exports=pet(vSr);var Cm=hu(require("fs")),Aue=hu(require("os")),Kp=hu(require("path")),h9=hu(require("readline")),Nue=hu(require("child_process")),Xp=hu(ZV()),o1=hu(uOe());var KF=hu(require("fs")),fOe=hu(require("os")),w6=hu(require("path")),cZ=hu(require("child_process"));function pb(a){return a==="~"?fOe.homedir():a.startsWith("~/")?w6.join(fOe.homedir(),a.slice(2)):a}t(pb,"expandHome");var l9=16*1024,oZ=32*1024,Uft=1e4,Cvr=3e4,_Oe=200,dOe=new Set(["node_modules",".git","dist","build","out",".next",".turbo","coverage","target","__pycache__",".venv","venv"]);function Pvr(a){let s=t(d=>{let f=d.match(/^(.*?)\{([^}]+)\}(.*)$/);if(!f)return[d];let[,y,x,P]=f;return x.split(",").map(M=>`${y}${M.trim()}${P}`)},"braceExpand"),c=a.match(/^([^*{}]+?)\/\*\*\/(.+)$/);if(c){let[,d,f]=c;return{includes:s(f),subDir:d}}return{includes:s(a),subDir:""}}t(Pvr,"expandGlobForGrep");var XF=class{constructor(s,c,d={}){this.workspaceRoot=s;this.languageAdapters=c;this.options=d;this._readFiles=new Set;this.customRepoRoots=d.customRepoRoots&&d.customRepoRoots.length>0?d.customRepoRoots:void 0}static{t(this,"CliToolExecutionContext")}markFileRead(s){this._readFiles.add(pb(s))}hasFileBeenRead(s){return this._readFiles.has(pb(s))}async readFile(s){return KF.promises.readFile(pb(s),"utf-8")}async writeFile(s,c){let d=pb(s);if(this.options.approveWrite&&!await this.options.approveWrite(d,c))throw new Error(`Write to ${d} rejected by user`);await KF.promises.mkdir(w6.dirname(d),{recursive:!0}),await KF.promises.writeFile(d,c,"utf-8")}async listFiles(s,c){let d=pb(c??this.workspaceRoot),f=Evr(s),y=[];return await qft(d,d,f,y),y.slice(0,_Oe).sort()}async listDirectoryEntries(s){let c=pb(s),d=await KF.promises.readdir(c,{withFileTypes:!0}),f=[];for(let y of d){if(y.name.startsWith("."))continue;let x=y.isDirectory();if(y.isSymbolicLink())try{x=(await KF.promises.stat(w6.join(c,y.name))).isDirectory()}catch{x=!1}f.push(x?`${y.name}/`:y.name)}return f.sort()}async searchCode(s,c,d){let f=pb(c??this.workspaceRoot);return this.runRipgrep(s,f,d).catch(()=>this.runGrep(s,f,d))}async runCommand(s,c,d){let f=c.map(pb),y=d?pb(d):this.workspaceRoot,x={...process.env};if((s.split(/[\\/]/).pop()??s)==="gh")for(let M of["GITHUB_TOKEN","GH_TOKEN"]){let L=x[M];typeof L=="string"&&L.trim()===""&&delete x[M]}return new Promise(M=>{let L="",J="",H=cZ.spawn(s,f,{cwd:y,shell:process.platform==="win32",env:x}),q=setTimeout(()=>{H.kill("SIGTERM"),M({stdout:L.slice(0,oZ),stderr:J+`
1273
1273
  [process timed out]`,exitCode:124})},Cvr),ve=process.stdout.isTTY===!0,ye=t((Ce,gt)=>{if(!ve)return;(gt?process.stderr:process.stdout).write("\r\x1B[2K\x1B[2m"+Ce+"\x1B[0m")},"writeLive");H.stdout?.on("data",Ce=>{let gt=Ce.toString();L+=gt,ye(gt,!1),L.length>oZ&&H.kill("SIGTERM")}),H.stderr?.on("data",Ce=>{let gt=Ce.toString();J+=gt,ye(gt,!0)}),H.on("close",Ce=>{clearTimeout(q);let gt=L.slice(0,oZ);if(Ce===0&&/Operation cancelled/i.test(gt)&&/(create-vite|create-react-app|create-next|create-svelte|create-astro|create-remix|@clack)/i.test(`${s} ${f.join(" ")} ${gt}`)){let bt=[s,...f].join(" ");M({stdout:gt,stderr:`Interactive scaffolder detected \u2014 \`${s}\` aborted with "Operation cancelled" because Bandit captures stdout/stderr (no TTY on stdin) and modern scaffolders refuse to start without one. Tell the user to run this directly in their shell: \`!${bt}\`. The \`!\`-prefix runs through their terminal with real stdin, so the scaffolder's prompts work. After they finish, you can pick up from the resulting filesystem state. Do NOT retry the same command \u2014 it will loop forever.`,exitCode:1});return}M({stdout:gt,stderr:J.slice(0,4*1024),exitCode:Ce??0})}),H.on("error",Ce=>{if(clearTimeout(q),Ce.code==="ENOENT"){M({stdout:"",stderr:`spawn ${s} ENOENT \u2014 '${s}' not found on PATH. Verify the tool is installed (\`which ${s}\` in a fresh terminal). If you use nvm/asdf/volta, your shim PATH may not be inherited; relaunching this CLI from the same terminal session that has \`${s}\` on PATH usually fixes it.`,exitCode:127});return}M({stdout:"",stderr:Ce.message,exitCode:1})})})}async watchCommand(s,c,d,f){let y=c.map(pb),x=d?pb(d):this.workspaceRoot;return new Promise(P=>{let M="",L="",J=!1,H=!1,q=cZ.spawn(s,y,{cwd:x,shell:process.platform==="win32",env:{...process.env}}),ve=t(vt=>{H||(H=!0,P({stdout:M.slice(0,oZ),stderr:L.slice(0,4*1024),exitCode:vt,endedEarly:J}))},"finish"),ye=setTimeout(()=>{try{q.kill("SIGTERM")}catch{}let vt=setTimeout(()=>{try{q.kill("SIGKILL")}catch{}ve(null)},1e3);q.once("close",bt=>{clearTimeout(vt),ve(typeof bt=="number"?bt:null)})},f),Ce=process.stdout.isTTY===!0,gt=t((vt,bt)=>{if(!Ce)return;(bt?process.stderr:process.stdout).write("\r\x1B[2K\x1B[2m"+vt+"\x1B[0m")},"writeLive");q.stdout?.on("data",vt=>{let bt=vt.toString();if(M+=bt,gt(bt,!1),M.length>oZ)try{q.kill("SIGTERM")}catch{}}),q.stderr?.on("data",vt=>{let bt=vt.toString();L+=bt,gt(bt,!0)}),q.on("close",vt=>{H||(clearTimeout(ye),J=!0,ve(typeof vt=="number"?vt:null))}),q.on("error",vt=>{H||(clearTimeout(ye),J=!0,L+=vt.message,ve(1))})})}runRipgrep(s,c,d){return new Promise((f,y)=>{let x=["--color=never","--line-number","--max-count=25","--max-filesize=1M",...[...dOe].map(J=>["--glob",`!${J}`]).flat()];d&&x.push("--glob",d),x.push(s,c);let P="",M=cZ.spawn("rg",x,{shell:!1}),L=setTimeout(()=>{M.kill("SIGTERM"),f(P.slice(0,l9))},Uft);M.stdout?.on("data",J=>{P+=J.toString(),P.length>l9&&M.kill("SIGTERM")}),M.on("close",J=>{clearTimeout(L),J!=null&&J>=2&&P.length===0?y(new Error(`rg exited with code ${J}`)):f(P.slice(0,l9))}),M.on("error",y)})}runGrep(s,c,d){return new Promise((f,y)=>{let x=[...dOe].map(ye=>["--exclude-dir",ye]).flat(),P=d?Pvr(d):{includes:[],subDir:""},M=P.includes.flatMap(ye=>["--include",ye]),L=P.subDir?`${c}/${P.subDir}`:c,J=["-rn","-E","--color=never",...x,...M,s,L],H="",q=cZ.spawn("grep",J,{shell:!1}),ve=setTimeout(()=>{q.kill("SIGTERM"),f(H.slice(0,l9))},Uft);q.stdout?.on("data",ye=>{H+=ye.toString(),H.length>l9&&q.kill("SIGTERM")}),q.on("close",ye=>{clearTimeout(ve),ye!=null&&ye>=2&&H.length===0?y(new Error(`grep exited with code ${ye}`)):f(H.slice(0,l9))}),q.on("error",y)})}};function Evr(a){let s=Dvr(a);return c=>s.test(c.replace(/\\/g,"/"))}t(Evr,"compileGlob");function Dvr(a){let s="^";for(let c=0;c<a.length;c++){let d=a[c];if(d==="*")a[c+1]==="*"?(s+=".*",c++,a[c+1]==="/"&&c++):s+="[^/]*";else if(d==="?")s+="[^/]";else if(d==="{"){let f=a.indexOf("}",c);if(f===-1){s+="\\{";continue}let y=a.slice(c+1,f).split(",").map(Ivr).join("|");s+=`(?:${y})`,c=f}else/[.+^$()|\\]/.test(d)?s+="\\"+d:s+=d}return s+="$",new RegExp(s)}t(Dvr,"globToRegex");function Ivr(a){return a.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")}t(Ivr,"escapeRegex");async function qft(a,s,c,d){if(d.length>=_Oe)return;let f;try{f=await KF.promises.readdir(a,{withFileTypes:!0})}catch{return}for(let y of f){if(d.length>=_Oe)return;if(dOe.has(y.name))continue;let x=w6.join(a,y.name),P=w6.relative(s,x);y.isDirectory()?await qft(x,s,c,d):y.isFile()&&c(P)&&d.push(x)}}t(qft,"walk");var Wft=hu(require("child_process")),rE=hu(require("fs")),Vft=hu(require("os")),pOe=hu(require("path")),Zft=hu(require("crypto"));function mOe(){let a=Zft.randomBytes(4).toString("hex");return pOe.join(Vft.tmpdir(),`bandit-paste-${Date.now()}-${a}.png`)}t(mOe,"freshTempPath");function lue(a,s,c={}){try{let d=Wft.spawnSync(a,s,{...c,encoding:void 0});return{stdout:Buffer.isBuffer(d.stdout)?d.stdout:Buffer.from(d.stdout??""),code:d.status}}catch{return{stdout:Buffer.alloc(0),code:null}}}t(lue,"tryExec");async function uue(){return process.platform==="darwin"?Avr():process.platform==="linux"?Nvr():process.platform==="win32"?Ovr():null}t(uue,"readClipboardImage");function Avr(){let a=mOe(),s=`set pngData to (the clipboard as \xABclass PNGf\xBB)
1274
1274
  set outFile to (open for access (POSIX file "${a}") with write permission)
1275
1275
  write pngData to outFile
@@ -1302,7 +1302,7 @@ close access outFile`,{code:c}=lue("osascript",["-e",s]);if(c!==0){try{rE.unlink
1302
1302
 
1303
1303
  [truncated \u2014 full text is ${L.length} chars across ${J} pages]`:L;return{output:`PDF: ${c} (${J} pages)
1304
1304
 
1305
- ${q}`,isError:!1}}catch(M){return{output:`Failed to parse PDF "${c}": ${M instanceof Error?M.message:String(M)}`,isError:!0}}finally{try{P.destroy()}catch{}}}};var l_t=["\u280B","\u2819","\u2839","\u2838","\u283C","\u2834","\u2826","\u2827","\u2807","\u280F"],u9=["working on it","I'm so on this","don't threaten me with a good time","rolling up my sleeves","say less","on it like a bonnet","warming up the engines","let me cook","loading the brain cells","give me a sec","doing the thing","rummaging through the codebase","putting it together","thinking thoughts","wrenching on it","all hands on deck","in the zone","deep in the weeds","consulting the rubber duck","getting the gang together","untangling the spaghetti","calculating the vibes","reading the room","spinning up the brain","channeling my inner Linus","checking the oracle","reticulating splines","asking the elder gods","doing my best","mid-yeet","summoning the daemons","buffering thoughts","polishing the prose","putting on the chef hat","almost there","this is fine","Bandit at work","loading\u2026trust me","convening the council","diving in","sharpening the axe","popping the hood","stirring the pot","consulting the docs","tracing the call graph","decoding the matrix"],due=class{constructor(){this.handle=null;this.verbHandle=null;this.frame=0;this.label="";this.startedAt=0;this.tokens=0}static{t(this,"Spinner")}start(s){if(this.stop(),this.label=s,this.startedAt=Date.now(),!process.stdout.isTTY){process.stdout.write(me.dim(`${s}\u2026
1305
+ ${q}`,isError:!1}}catch(M){return{output:`Failed to parse PDF "${c}": ${M instanceof Error?M.message:String(M)}`,isError:!0}}finally{try{P.destroy()}catch{}}}};var l_t=["\u280B","\u2819","\u2839","\u2838","\u283C","\u2834","\u2826","\u2827","\u2807","\u280F"],u9=["working on it","I'm so on this","don't threaten me with a good time","rolling up my sleeves","say less","on it like a bonnet","warming up the engines","let me cook","loading the brain cells","give me a sec","doing the thing","rummaging through the codebase","putting it together","thinking thoughts","wrenching on it","all hands on deck","in the zone","deep in the weeds","consulting the rubber duck","getting the gang together","untangling the spaghetti","calculating the vibes","reading the room","spinning up the brain","channeling my inner Linus","checking the oracle","reticulating splines","asking the elder gods","doing my best","mid-yeet","summoning the daemons","buffering thoughts","polishing the prose","putting on the chef hat","almost there","this is fine","Bandit at work","loading\u2026trust me","convening the council","diving in","sharpening the axe","popping the hood","stirring the pot","consulting the docs","tracing the call graph","decoding the matrix","trust the process","no thoughts, just code","vibes are immaculate","this one's for the timeline","lock in","we ball","absolutely cooking","they don't pay me enough for this","they pay me too much for this","she's compiling, sir","do not perceive me","I have done a tiny crime","manifesting clean output","writing checks my context can cash","negotiating with the parser","bullying the type system","feeding the linter","appeasing the gods of CI","rebooting my will to live","running on hopes and caffeine","hold my keystrokes","I read the README this time","I did not read the README","speedrunning best practices","speedrunning worst practices","this will work or be deeply funny","Stack Overflow is a friend, actually","found the off-by-one","found another off-by-one","I'll just refactor real quick","narrator: it was not real quick","yeeting the YAML","wrestling regex","fluent in stack traces","don't @ me","don't @ me, I'm thinking","Bandit's brain go brrr","in my final form","approaching critical mass","let him cook","in there like swimwear","send tweet","I do this for fun, sometimes","the duck and I are talking","the duck has notes","we're gonna make it (probably)","calibrating the snark","queueing up a hot take","shipping is a feature","vibe-checking the diff","going through it","you good? I'm good","smol model big dreams","do not interrupt the bit","writing love letters to the compiler","asking for forgiveness, not permission","filing a Linear ticket against reality","reading minds (yours, the model's, mine)"],due=class{constructor(){this.handle=null;this.verbHandle=null;this.frame=0;this.label="";this.startedAt=0;this.tokens=0}static{t(this,"Spinner")}start(s){if(this.stop(),this.label=s,this.startedAt=Date.now(),!process.stdout.isTTY){process.stdout.write(me.dim(`${s}\u2026
1306
1306
  `));return}u_t(),this.handle=setInterval(()=>this.render(),80)}startThinking(){this.stop();let s=t(()=>u9[Math.floor(Math.random()*u9.length)],"pick");if(this.label=s(),this.startedAt=Date.now(),!process.stdout.isTTY){process.stdout.write(me.dim(`${this.label}\u2026
1307
1307
  `));return}u_t(),this.handle=setInterval(()=>this.render(!0),80),this.verbHandle=setInterval(()=>{let c=s();c===this.label&&u9.length>1&&(c=u9[(u9.indexOf(this.label)+1)%u9.length]),this.label=c},2500)}update(s){this.label=s}setTokens(s){this.tokens=Math.max(0,Math.floor(s))}stop(){this.handle&&(clearInterval(this.handle),this.handle=null),this.verbHandle&&(clearInterval(this.verbHandle),this.verbHandle=null),process.stdout.isTTY&&(process.stdout.write("\r\x1B[2K"),Uvr())}render(s=!1){let c=this.startedAt>0?Date.now()-this.startedAt:0,d="";if(c>=3e3){let y=Math.floor(c/1e3);d=y>=60?` \xB7 ${Math.floor(y/60)}m${y%60}s`:` \xB7 ${y}s`}let f="";this.tokens>=100&&(f=this.tokens>=1e3?` \xB7 ~${(this.tokens/1e3).toFixed(1)}K tokens`:` \xB7 ~${this.tokens} tokens`),process.stdout.write("\r\x1B[2K"+me.accent(l_t[this.frame])+" "+me.dim(this.label+(s?"\u2026":"")+d+f)),this.frame=(this.frame+1)%l_t.length}},pue=class{constructor(){this.startedAt=0;this.tokens=0;this.active=!1}static{t(this,"StreamFooter")}start(){this.active||(this.active=!0,this.startedAt=Date.now(),this.tokens=0)}setTokens(s){this.tokens=Math.max(0,Math.floor(s))}stop(){if(!this.active||(this.active=!1,this.tokens<50&&!process.stdout.isTTY))return;let s=Date.now()-this.startedAt,c=Math.floor(s/1e3),d=c>=60?`${Math.floor(c/60)}m${c%60}s`:`${c}s`,f=this.tokens>=1e3?`~${(this.tokens/1e3).toFixed(1)}K tokens`:`~${this.tokens} tokens`;this.tokens>=50&&process.stdout.write(`
1308
1308
  `+me.dim(` ${me.accent("\u2192")} ${f} \xB7 ${d}`)+`
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@burtson-labs/bandit-stealth-cli",
3
- "version": "1.7.157",
3
+ "version": "1.7.158",
4
4
  "description": "Bandit — a local-first AI coding agent for your terminal. Same runtime as the Bandit Stealth VS Code / Cursor extension.",
5
5
  "keywords": [
6
6
  "ai",