@typhons/sandbox-tools 0.5.6 → 0.5.8
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/check-claude-active.js +4 -4
- package/package.json +1 -1
- package/stop-agents.js +5 -4
package/check-claude-active.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import{execSync as
|
|
3
|
-
`)
|
|
4
|
-
`);for(let
|
|
5
|
-
`);for(let
|
|
2
|
+
import{execSync as g}from"child_process";import f from"fs";import{setTimeout as D}from"timers/promises";import{execSync as b}from"child_process";function m(e){let t="";try{t=b(`pgrep -x ${e} 2>/dev/null`,{encoding:"utf8"})}catch{}return t.split(`
|
|
3
|
+
`).map(o=>o.trim()).filter(Boolean)}var a=30,x=1,T=100,M=!1,v=!1,r=process.argv.slice(2);for(let e=0;e<r.length;e++)r[e]==="--json"?M=!0:r[e]==="--threshold"?a=parseInt(r[++e],10):r[e]==="--daemon"&&(v=!0);function E(){try{let e=g('find /home -name "*.jsonl" -path "*/.claude/projects/*" ! -path "*/subagents/*" -printf "%T@ %p\\n" 2>/dev/null | sort -rn | head -1',{encoding:"utf8"}).trim();if(e){let t=parseInt(e.split(" ")[0],10);return Math.floor(Date.now()/1e3)-t}}catch{}return-1}function B(){let e=-1,t=["/home/*/.codex/log/codex-tui.log","/root/.codex/log/codex-tui.log"];for(let o of t)try{let n=g(`ls ${o} 2>/dev/null`,{encoding:"utf8"}).trim().split(`
|
|
4
|
+
`);for(let l of n)if(l)try{let i=f.statSync(l),s=Math.floor(Date.now()/1e3)-Math.floor(i.mtimeMs/1e3);(e===-1||s<e)&&(e=s)}catch{}}catch{}return e}function O(e){let t=0;for(let o of e)try{let n=g(`pgrep -P ${o} 2>/dev/null`,{encoding:"utf8"}).trim().split(`
|
|
5
|
+
`);for(let l of n)if(l)try{if(f.readFileSync(`/proc/${l}/cmdline`,"utf8").replace(/\0/g," ").includes("check-claude-active"))continue;t++}catch{t++}}catch{}return t}function w(e){try{let o=f.readFileSync(`/proc/${e}/io`,"utf8").match(/^rchar:\s*(\d+)/m);return o?parseInt(o[1],10):0}catch{return 0}}async function N(){let e=m("claude"),t=m("codex"),o=E(),n=B(),l=o>=0&&o<a||n>=0&&n<a,i=O(e),s=O(t),$=i>0||s>0,y=[...e,...t],_=y.map(w);await D(x*1e3);let A=y.map(w),I=0,S=0;for(let c=0;c<e.length;c++)I+=Math.max(0,A[c]-_[c]);for(let c=0;c<t.length;c++)S+=Math.max(0,A[e.length+c]-_[e.length+c]);let d=Math.max(I,S),u=d>T,h=l||$||u,p=e.length&&t.length?"both":e.length?"claude":t.length?"codex":"none";return M||v?console.log(JSON.stringify({active:h,agent:p,claude_pids:e.map(c=>parseInt(c,10)),codex_pids:t.map(c=>parseInt(c,10)),claude_jsonl_age:o,codex_log_age:n,log_active:l,children:i+s,io_delta:d,io_active:u})):!e.length&&!t.length?console.log("Agents: not running"):h?(console.log(`Agent: ACTIVE (${p}; ${e.length} claude + ${t.length} codex)`),l&&(o>=0&&o<a&&console.log(` Claude JSONL written ${o}s ago`),n>=0&&n<a&&console.log(` Codex log written ${n}s ago`)),$&&console.log(` ${i} claude + ${s} codex child process(es)`),u&&console.log(` I/O: ${d} bytes read in ${x}s`)):(console.log(`Agent: idle (${p}; ${e.length} claude + ${t.length} codex running, waiting for user)`),e.length&&console.log(` Claude JSONL last written ${o}s ago`),t.length&&console.log(` Codex log last written ${n}s ago`),console.log(" No child processes"),console.log(` I/O: ${d} bytes in ${x}s`)),h}function C(){try{return f.readFileSync("/run/e2b/.DEVBOX_NAME","utf8").trim()}catch{}return""}if(v){let e=process.env.E2B_HTTP_DOMAIN||"d.typhons.dev";for(console.log(`[agent-keepalive] domain=${e} interval=30s`);;){if(await N()){let o=C();if(o){let n=`https://${o}.${e}:49999/`;try{g(`curl -sf -o /dev/null -w '%{http_code}' --max-time 5 "${n}" 2>/dev/null`,{encoding:"utf8"})}catch{}}else console.log("[agent-keepalive] no devbox name available yet, skipping ping")}await D(29e3)}}else{let e=await N();process.exit(e?0:1)}
|
package/package.json
CHANGED
package/stop-agents.js
CHANGED
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import{execSync as
|
|
2
|
+
import{execSync as s}from"child_process";import p from"fs";import{execSync as d}from"child_process";function r(n){let o="";try{o=d(`pgrep -x ${n} 2>/dev/null`,{encoding:"utf8"})}catch{}return o.split(`
|
|
3
|
+
`).map(t=>t.trim()).filter(Boolean)}function c(n){console.log(`[stop-agents] ${n}`)}function l(n,o){let t;try{t=p.readlinkSync(`/proc/${o}/fd/0`)}catch{}if(!t||!t.startsWith("/dev/pts/")){c(`${n} (pid ${o}) has no PTY (fd/0 -> ${t}), skipping`);return}c(`Injecting Escape into ${n} (pid ${o}, tty ${t})`);try{s(`sudo python3 -c "
|
|
3
4
|
import fcntl, os, struct
|
|
4
|
-
fd = os.open('${
|
|
5
|
+
fd = os.open('${t}', os.O_WRONLY)
|
|
5
6
|
fcntl.ioctl(fd, 0x5412, struct.pack('b', 0x1b))
|
|
6
7
|
os.close(fd)
|
|
7
|
-
"`,{stdio:"ignore"}),
|
|
8
|
-
`);for(let i of
|
|
8
|
+
"`,{stdio:"ignore"}),c(`Escape injected for ${n} (pid ${o})`)}catch{c(`TIOCSTI failed for ${n} (pid ${o}), falling back to SIGINT-ing children`);try{let e=s(`pgrep -P ${o} 2>/dev/null`,{encoding:"utf8"}).trim().split(`
|
|
9
|
+
`);for(let i of e)if(i)try{process.kill(parseInt(i),"SIGINT")}catch{}}catch{}}}function f(n,o){let t=r(o);if(t.length===0){c(`No ${n} process found`);return}c(`Found ${t.length} ${n} instance${t.length===1?"":"s"}: ${t.join(", ")}`);for(let e of t)l(n,e)}f("Claude Code","claude");f("Codex","codex");c("Done");
|