@evolvingmachines/e2b 0.0.67 → 0.0.68
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/dist/index.cjs +3 -3
- package/dist/index.d.cts +9 -1
- package/dist/index.d.ts +9 -1
- package/dist/index.js +3 -3
- package/package.json +2 -2
package/dist/index.cjs
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
'use strict';var codeInterpreter=require('@e2b/code-interpreter'),compareVersions=require('compare-versions');require('fs');var x=class extends Error{feature;provider;reason;constructor(e,t,n){super(`${t} does not support ${e}${n?`: ${n}`:""}`),this.name="SandboxFeatureUnsupportedError",this.feature=e,this.provider=t,this.reason=n;}},m=class extends Error{path;provider;constructor(e,t){super(`${t}: no such file or directory: ${e}`),this.name="SandboxPathNotFoundError",this.path=e,this.provider=t;}},g=class extends Error{sandboxId;provider;state;constructor(e,t,n){super(`${t} sandbox ${e} is not running (${n}); inspect never starts or resumes a sandbox`),this.name="SandboxNotRunningError",this.sandboxId=e,this.provider=t,this.state=n;}};function P(r,e){return !!r&&typeof r=="object"&&r.name===e}function
|
|
1
|
+
'use strict';var codeInterpreter=require('@e2b/code-interpreter'),compareVersions=require('compare-versions');require('fs');var x=class extends Error{feature;provider;reason;constructor(e,t,n){super(`${t} does not support ${e}${n?`: ${n}`:""}`),this.name="SandboxFeatureUnsupportedError",this.feature=e,this.provider=t,this.reason=n;}},m=class extends Error{path;provider;constructor(e,t){super(`${t}: no such file or directory: ${e}`),this.name="SandboxPathNotFoundError",this.path=e,this.provider=t;}},g=class extends Error{sandboxId;provider;state;constructor(e,t,n){super(`${t} sandbox ${e} is not running (${n}); inspect never starts or resumes a sandbox`),this.name="SandboxNotRunningError",this.sandboxId=e,this.provider=t,this.state=n;}};function P(r,e){return !!r&&typeof r=="object"&&r.name===e}function V(r){return P(r,"SandboxFeatureUnsupportedError")}function W(r){return P(r,"SandboxPathNotFoundError")}function j(r){return P(r,"SandboxNotRunningError")}function E(r){if(!Number.isInteger(r.offset)||r.offset<0)throw new RangeError(`offset must be a non-negative integer, got ${r.offset}`);if(!Number.isInteger(r.length)||r.length<0)throw new RangeError(`length must be a non-negative integer, got ${r.length}`)}function z(r){return r.padStart(4,"0")}var X=/^(-|[dalTLDpSugct?]+)([-r][-w][-x]){3}$/;function N(r){if(!X.test(r))throw new RangeError(`not a Go file mode string: ${r}`);let e=r.slice(0,-9),t=r.slice(-9),n=e.includes("d")?"dir":e.includes("L")?"symlink":/[DpSc?]/.test(e)?"other":"file",s=(e.includes("u")?2048:0)|(e.includes("g")?1024:0)|(e.includes("t")?512:0);for(let o=0;o<9;o++)t[o]!=="-"&&(s|=1<<8-o);return {type:n,mode:z(s.toString(8))}}function v(r){let e=r instanceof Date?r:typeof r=="number"?new Date(r*1e3):new Date(r);if(Number.isNaN(e.getTime()))throw new RangeError(`not a timestamp: ${String(r)}`);return e.toISOString()}function D(r,e){return r.endsWith("/")?`${r}${e}`:`${r}/${e}`}async function $(r,e,t){if(E(e),e.length===0)return new Uint8Array(0);let n=e.offset+e.length-1,s=await fetch(r,{headers:{Range:`bytes=${e.offset}-${n}`},signal:AbortSignal.timeout(t.timeoutMs)});if(s.status===206){let o=new Uint8Array(await s.arrayBuffer());return o.length>e.length?o.subarray(0,e.length):o}if(s.status===200)return Y(s,e);if(s.status===416)return await s.body?.cancel().catch(()=>{}),new Uint8Array(0);throw await s.body?.cancel().catch(()=>{}),s.status===404?new m(t.path,t.provider):new Error(`${t.provider}: range read of ${t.path} failed (HTTP ${s.status})`)}async function Y(r,e){if(!r.body)return new Uint8Array(0);let t=r.body.getReader(),n=[],s=0,o=0,a=e.offset+e.length;try{for(;;){let{done:c,value:p}=await t.read();if(c)break;let h=s;if(s+=p.length,s>e.offset){let d=Math.max(0,e.offset-h),u=Math.min(p.length,a-h);u>d&&(n.push(p.subarray(d,u)),o+=u-d);}if(s>=a)break}}finally{await t.cancel().catch(()=>{});}let i=new Uint8Array(o),l=0;for(let c of n)i.set(c,l),l+=c.length;return i}var b=3e5,_="0.2.5",ee=new Date(0);function I(r){if(!r||typeof r!="object")return false;if(r.name==="TimeoutError")return true;let e=r.message;return typeof e=="string"&&/timed?\s*out/i.test(e)}var L=100,K=100;function w(r){return r instanceof Date?r.toISOString():String(r)}function q(r){if(typeof r=="string"||r instanceof ArrayBuffer)return r;if(r instanceof Buffer)return new Uint8Array(r).buffer;if(r instanceof Uint8Array)return new Uint8Array(r).buffer;throw new Error(`Unsupported data type for file upload: ${typeof r}. Expected string, Buffer, ArrayBuffer, or Uint8Array.`)}var S=class extends Error{constructor(e){super(e),this.name="E2BResourcesError";}},te="2.25.0",A=class extends Error{constructor(e){super(e),this.name="E2BNetworkUpdateUnsupportedError";}};function R(r){if(r?.outbound==="open"&&r.allowedDestinations?.length)throw new Error("network.allowedDestinations is only valid when outbound is blocked");let e=r?.allowedDestinations??[],t=r?.outbound==="blocked"&&e.length>0;return {allowInternetAccess:r?.outbound!=="blocked"||t,network:t?{denyOut:["0.0.0.0/0"],allowOut:e}:void 0}}var T=class extends Error{constructor(){super("E2B takes no create-time boot command: the sandbox boots its template's own init, and a start command is a template-BUILD field (Template startCmd) this provider never sets. The boot is already inert \u2014 run the process by exec after create, or bake it into the template the `image` names."),this.name="E2BBootCommandError";}},B=class extends Error{constructor(){super("E2B has no idle timeout: its sandbox timeout is an ABSOLUTE lifetime that in-sandbox activity never extends. Use `timeoutMs` for the lifetime, and call setTimeout() to extend a sandbox you know is still working."),this.name="E2BIdleTimeoutError";}},C=class{constructor(e,t){this.sandbox=e;this.defaultUser=t;}async run(e,t){try{let n=await this.sandbox.commands.run(e,{timeoutMs:t?.timeoutMs,envs:t?.envs,cwd:t?.cwd,user:this.defaultUser,onStdout:t?.onStdout,onStderr:t?.onStderr});return {exitCode:n.exitCode,stdout:n.stdout,stderr:n.stderr}}catch(n){if(n&&typeof n=="object"&&"exitCode"in n){let s=n;return {exitCode:s.exitCode,stdout:s.stdout??"",stderr:s.stderr??""}}if(I(n))return {exitCode:124,stdout:"",stderr:n instanceof Error?n.message:"command timed out"};throw n}}async spawn(e,t){let n=await this.sandbox.commands.run(e,{background:true,stdin:t?.stdin??true,timeoutMs:t?.timeoutMs,envs:t?.envs,cwd:t?.cwd,user:this.defaultUser,onStdout:t?.onStdout,onStderr:t?.onStderr});return {processId:String(n.pid),wait:async()=>{try{let s=await n.wait();return {exitCode:s.exitCode,stdout:s.stdout,stderr:s.stderr}}catch(s){if(s&&typeof s=="object"&&"exitCode"in s){let o=s;return {exitCode:o.exitCode,stdout:o.stdout??"",stderr:o.stderr??""}}if(I(s))return {exitCode:124,stdout:"",stderr:s instanceof Error?s.message:"command timed out"};throw s}},kill:()=>this.sandbox.commands.kill(n.pid)}}async list(){return (await this.sandbox.commands.list()).map(t=>({...t,processId:String(t.pid)}))}async connect(e,t){let n=await this.sandbox.commands.connect(Number(e),{onStdout:t?.onStdout,onStderr:t?.onStderr,timeoutMs:t?.timeoutMs});return {processId:String(n.pid),wait:async()=>{try{let s=await n.wait();return {exitCode:s.exitCode,stdout:s.stdout,stderr:s.stderr}}catch(s){if(s&&typeof s=="object"&&"exitCode"in s){let o=s;return {exitCode:o.exitCode,stdout:o.stdout??"",stderr:o.stderr??""}}if(I(s))return {exitCode:124,stdout:"",stderr:s instanceof Error?s.message:"command timed out"};throw s}},kill:()=>this.sandbox.commands.kill(n.pid)}}async sendStdin(e,t){await this.sandbox.commands.sendStdin(Number(e),t);}async kill(e){return this.sandbox.commands.kill(Number(e))}},M=class{constructor(e,t,n){this.sandbox=e;this.defaultUser=t;this.envdVersion=n;}async assertEntryInfo(e){if(this.envdVersion??=(await this.sandbox.getInfo()).envdVersion,compareVersions.compareVersions(this.envdVersion,_)<0)throw new x(e,"e2b",`the sandbox runs envd ${this.envdVersion}; entry permissions, owner, group and mtime need envd ${_} or later (rebuild the template)`)}async read(e){let t=await this.sandbox.files.read(e,{format:"bytes",requestTimeoutMs:b,user:this.defaultUser});if(!t.includes(0))try{return new TextDecoder("utf-8",{fatal:!0,ignoreBOM:!0}).decode(t)}catch{}return t}async write(e,t){await this.sandbox.files.write(e,q(t),{requestTimeoutMs:b,user:this.defaultUser});}async writeBatch(e){let t=e.map(n=>({path:n.path,data:q(n.data)}));await this.sandbox.files.write(t,{requestTimeoutMs:b,user:this.defaultUser});}async makeDir(e){await this.sandbox.files.makeDir(e,{user:this.defaultUser});}async uploadUrl(e,t){return this.sandbox.uploadUrl(e,{user:this.defaultUser,...t?{useSignatureExpiration:t}:{}})}async downloadUrl(e,t){return this.sandbox.downloadUrl(e,{user:this.defaultUser,...t?{useSignatureExpiration:t}:{}})}async exists(e){return this.sandbox.files.exists(e,{user:this.defaultUser})}async list(e){await this.assertEntryInfo("files.list");try{return (await this.sandbox.files.list(e,{user:this.defaultUser})).map(n=>G(n))}catch(t){throw U(t)?new m(e,"e2b"):t}}async stat(e){await this.assertEntryInfo("files.stat");try{return G(await this.sandbox.files.getInfo(e,{user:this.defaultUser}))}catch(t){throw U(t)?new m(e,"e2b"):t}}async readRange(e,t){if(E(t),t.length===0)return new Uint8Array(0);let n=await this.sandbox.downloadUrl(e,{user:this.defaultUser,useSignatureExpiration:Math.ceil(b/1e3)});return $(n,t,{provider:"e2b",path:e,timeoutMs:b})}async remove(e){await this.sandbox.files.remove(e,{user:this.defaultUser});}async rename(e,t){await this.sandbox.files.rename(e,t,{user:this.defaultUser});}async readStream(e){return this.sandbox.files.read(e,{format:"stream",user:this.defaultUser})}async writeStream(e,t){await this.sandbox.files.write(e,t,{user:this.defaultUser});}async writeFromPath(e,t){let{createReadStream:n,statSync:s}=await import('fs'),{Readable:o}=await import('stream'),{randomBytes:a}=await import('crypto'),i=s(t).size,l=`----evolve${a(16).toString("hex")}`,c=Buffer.from(`--${l}\r
|
|
2
2
|
Content-Disposition: form-data; name="file"; filename="blob"\r
|
|
3
3
|
Content-Type: application/octet-stream\r
|
|
4
4
|
\r
|
|
5
5
|
`),p=Buffer.from(`\r
|
|
6
6
|
--${l}--\r
|
|
7
|
-
`);async function*h(){yield c;for await(let d of n(t))yield d;yield p;}try{let d=await this.uploadUrl(e),u=await fetch(d,{method:"POST",body:o.toWeb(o.from(h())),headers:{"Content-Type":`multipart/form-data; boundary=${l}`,"Content-Length":String(c.length+i+p.length)},duplex:"half"});if(!u.ok)throw new Error(`streamed upload to ${e} failed (HTTP ${u.status})`)}catch(d){console.warn(`[e2b] streamed upload of ${t} failed, falling back to a buffered write:`,d instanceof Error?d.message:d);let u=o.toWeb(n(t));await this.writeStream(e,u);}}async watchDir(e,t,n){let s;try{s=await this.sandbox.files.watchDir(e,o=>{let a=o.type==="chmod"?"write":o.type;return t({path:D(e,o.name),type:a})},{recursive:n?.recursive??!1,timeoutMs:0,user:this.defaultUser});}catch(o){throw U(o)?new m(e,"e2b"):o}return {stop:()=>s.stop()}}};function U(r){let e=r&&typeof r=="object"?r.name:void 0;return e==="FileNotFoundError"||e==="NotFoundError"}function
|
|
8
|
-
exports.E2BBootCommandError=
|
|
7
|
+
`);async function*h(){yield c;for await(let d of n(t))yield d;yield p;}try{let d=await this.uploadUrl(e),u=await fetch(d,{method:"POST",body:o.toWeb(o.from(h())),headers:{"Content-Type":`multipart/form-data; boundary=${l}`,"Content-Length":String(c.length+i+p.length)},duplex:"half"});if(!u.ok)throw new Error(`streamed upload to ${e} failed (HTTP ${u.status})`)}catch(d){console.warn(`[e2b] streamed upload of ${t} failed, falling back to a buffered write:`,d instanceof Error?d.message:d);let u=o.toWeb(n(t));await this.writeStream(e,u);}}async watchDir(e,t,n){let s;try{s=await this.sandbox.files.watchDir(e,o=>{let a=o.type==="chmod"?"write":o.type;return t({path:D(e,o.name),type:a})},{recursive:n?.recursive??!1,timeoutMs:0,user:this.defaultUser});}catch(o){throw U(o)?new m(e,"e2b"):o}return {stop:()=>s.stop()}}};function U(r){let e=r&&typeof r=="object"?r.name:void 0;return e==="FileNotFoundError"||e==="NotFoundError"}function G(r){let{type:e,mode:t}=N(r.permissions),n={name:r.name,path:r.path,type:e,size:r.size,mtime:v(r.modifiedTime??ee),mode:t,owner:r.owner,group:r.group};return e==="symlink"&&r.symlinkTarget!==void 0&&r.symlinkTarget!==r.path&&(n.target=r.symlinkTarget),n}var f=class{constructor(e,t,n,s,o){this.sandbox=e;this.apiKey=t;this.apiUrl=n;this.commands=new C(e,s),this.files=new M(e,s,o);}commands;files;lastMetricsAt;get sandboxId(){return this.sandbox.sandboxId}async metrics(){let e=await this.sandbox.getMetrics(this.lastMetricsAt?{start:this.lastMetricsAt}:{}),t;for(let n of e)(!t||n.timestamp.getTime()>t.timestamp.getTime())&&(t=n);return t?(this.lastMetricsAt=t.timestamp,{cpuPct:t.cpuUsedPct,memUsedMb:t.memUsed/k,memTotalMb:t.memTotal/k,diskUsedMb:t.diskUsed/k,sampledAt:v(t.timestamp),source:"e2b:getMetrics"}):null}getHost(e){return Promise.resolve(this.sandbox.getHost(e))}async isRunning(){return this.sandbox.isRunning()}async getInfo(){let e=await this.sandbox.getInfo();return {sandboxId:e.sandboxId,image:e.templateId,name:e.name,metadata:e.metadata??{},startedAt:w(e.startedAt),endAt:e.endAt?w(e.endAt):void 0}}async updateNetwork(e){let t=R(e),n=this.sandbox;if(typeof n.updateNetwork!="function")throw new A(`The installed e2b client cannot change a running sandbox's network policy: Sandbox.updateNetwork requires e2b >= ${te}. Upgrade the e2b dependency (it is pulled in by @e2b/code-interpreter), or create the sandbox with the policy it needs for its whole lifetime.`);await n.updateNetwork({allowInternetAccess:t.allowInternetAccess,...t.network??{}});}async kill(){try{await this.sandbox.kill();}catch{await new Promise(e=>setTimeout(e,500)),await this.sandbox.kill();}}async pause(){await this.sandbox.betaPause({apiKey:this.apiKey,apiUrl:this.apiUrl});}},O=class{providerType="e2b";name="E2B";apiKey;apiUrl;defaultTimeoutMs;templateId;retryCreateRequest;sandboxUsers=new Map;constructor(e){this.apiKey=e.apiKey,this.apiUrl=e.apiUrl,this.defaultTimeoutMs=e.defaultTimeoutMs??36e5,this.templateId=e.templateId,this.retryCreateRequest=e.retryCreateRequest;}async create(e){if(e.bootCommand!==void 0)throw new T;if(e.idleTimeoutMs!==void 0)throw new B;if(e.resources?.gpu!==void 0||e.resources?.gpuTypes!==void 0)throw new S("E2B offers no GPU allocation at any tier \u2014 a `resources.gpu` request cannot be enforced. Run GPU workloads on a provider that reserves GPUs (modal).");if(e.resources&&(e.resources.cpu!==void 0||e.resources.memory!==void 0||e.resources.disk!==void 0))throw new S("E2B cannot size a sandbox at create time: sizing is fixed by the template (Template.build cpuCount/memoryMB; disk is plan-fixed). Build a template with the desired resources and pass it as `image` instead of `resources`.");let t=e.timeoutMs??this.defaultTimeoutMs,n=e.image??this.templateId??"evolve-all";for(let i of e.phaseNetworkPolicies??[])R(i);let s=R(e.network),o=()=>codeInterpreter.Sandbox.create(n,{apiKey:this.apiKey,apiUrl:this.apiUrl,envs:e.envs,metadata:e.metadata,timeoutMs:t,...s}),a=await(this.retryCreateRequest?this.retryCreateRequest(o):o());return e.workingDirectory&&await a.files.makeDir(e.workingDirectory,{user:e.user}),e.user&&this.sandboxUsers.set(a.sandboxId,e.user),new f(a,this.apiKey,this.apiUrl,e.user)}async connect(e,t){let n=await codeInterpreter.Sandbox.connect(e,{apiKey:this.apiKey,apiUrl:this.apiUrl,timeoutMs:t??this.defaultTimeoutMs});return new f(n,this.apiKey,this.apiUrl,this.sandboxUsers.get(e))}async inspect(e,t){let n=await this.fetchSandboxDetail(e);if(n.state!=="running")throw new g(e,"e2b",n.state);let s=F.attach({sandboxId:n.sandboxID,sandboxDomain:n.domain??void 0,envdVersion:n.envdVersion,envdAccessToken:n.envdAccessToken,trafficAccessToken:n.trafficAccessToken??void 0,apiKey:this.apiKey,apiUrl:this.apiUrl});return new f(s,this.apiKey,this.apiUrl,t?.user??this.sandboxUsers.get(e),n.envdVersion)}async fetchSandboxDetail(e){let t=new codeInterpreter.ConnectionConfig({apiKey:this.apiKey,apiUrl:this.apiUrl}),n=await new codeInterpreter.ApiClient(t).api.GET("/sandboxes/{sandboxID}",{params:{path:{sandboxID:e}}});if(n.error?.code===404||!n.data&&!n.error)throw new g(e,"e2b","not found");if(n.error)throw new Error(`E2B refused the sandbox record for ${e}: ${n.error.message??n.error.code}`);return n.data}async list(e){let t=await this.paginate(e);if(t.error&&!t.stoppedAtLimit)throw new Error(t.error);return t.sandboxes}async listAll(e){let{stoppedAtLimit:t,...n}=await this.paginate(e);return n}async paginate(e){let t=e?.limit;return H(codeInterpreter.Sandbox.list({apiKey:this.apiKey,apiUrl:this.apiUrl,query:{state:e?.state,metadata:e?.metadata},limit:t===void 0?L:Math.min(t,L)}),t)}};async function H(r,e){let t=[],n=0,s=new Set;for(;r.hasNext;){if(n>=K)return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:false,error:`sandbox list exceeded ${K} pages`};let o=r.nextToken;if(o!==void 0){if(s.has(o))return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:false,error:"pagination token repeated"};s.add(o);}let a;try{a=await r.nextItems();}catch(i){return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:false,error:`sandbox list failed: ${i instanceof Error?i.message:String(i)}`}}n+=1;for(let i of a){if(e!==void 0&&t.length>=e)return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:true,error:`stopped at the requested limit of ${e} with more sandboxes available`};t.push({sandboxId:i.sandboxId,image:i.templateId,name:i.name,metadata:i.metadata??{},startedAt:w(i.startedAt),endAt:i.endAt?w(i.endAt):void 0});}if(e!==void 0&&t.length>=e&&r.hasNext)return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:true,error:`stopped at the requested limit of ${e} with more sandboxes available`};if(e!==void 0&&t.length>=e)break}return {sandboxes:t,complete:true,pagesFetched:n,stoppedAtLimit:false}}var ce=H,k=1024*1024,F=class r extends codeInterpreter.Sandbox{static attach(e){return new r(e)}};function le(r={}){let e=r.apiKey??process.env.E2B_API_KEY;if(!e)throw new Error("E2B API key required. Set E2B_API_KEY environment variable or pass apiKey in config. Get your key at https://e2b.dev/sign-in");return new O({...r,apiKey:e})}var pe=f;
|
|
8
|
+
exports.E2BBootCommandError=T;exports.E2BCommands=C;exports.E2BFiles=M;exports.E2BIdleTimeoutError=B;exports.E2BNetworkUpdateUnsupportedError=A;exports.E2BProvider=O;exports.E2BResourcesError=S;exports.E2B_MAX_LIST_PAGES=K;exports.E2B_MAX_PAGE_SIZE=L;exports.E2B_MIN_UPDATE_NETWORK_VERSION=te;exports.SandboxFeatureUnsupportedError=x;exports.SandboxNotRunningError=g;exports.SandboxPathNotFoundError=m;exports._testCollectSandboxPages=ce;exports._testE2BSandboxImplCtor=pe;exports.createE2BProvider=le;exports.isSandboxFeatureUnsupportedError=V;exports.isSandboxNotRunningError=j;exports.isSandboxPathNotFoundError=W;
|
package/dist/index.d.cts
CHANGED
|
@@ -267,6 +267,8 @@ interface SandboxCreateOptions {
|
|
|
267
267
|
user?: string;
|
|
268
268
|
/** Home directory used by the SDK for agent config paths; not consumed by the provider. */
|
|
269
269
|
homeDir?: string;
|
|
270
|
+
/** Account the SDK hands its agent config files to; not consumed by the provider. */
|
|
271
|
+
homeOwner?: string;
|
|
270
272
|
}
|
|
271
273
|
/** Options for listing sandboxes */
|
|
272
274
|
interface SandboxListOptions {
|
|
@@ -378,6 +380,8 @@ interface SandboxProvider {
|
|
|
378
380
|
/** The same enumeration for fleet bookkeeping: never throws, reports completeness. */
|
|
379
381
|
listAll(options?: SandboxListOptions): Promise<SandboxListPage>;
|
|
380
382
|
}
|
|
383
|
+
/** Wraps the one request that creates a box, for the SDK to retry a door's 429/503 before any box exists. */
|
|
384
|
+
type CreateRequestRetry = <T>(send: () => Promise<T>) => Promise<T>;
|
|
381
385
|
interface E2BConfig {
|
|
382
386
|
/** E2B API key. Default: reads from E2B_API_KEY env var */
|
|
383
387
|
apiKey?: string;
|
|
@@ -386,6 +390,8 @@ interface E2BConfig {
|
|
|
386
390
|
defaultTimeoutMs?: number;
|
|
387
391
|
/** E2B template ID (default: 'evolve-all'). Create custom templates at https://e2b.dev/docs/sandbox-template */
|
|
388
392
|
templateId?: string;
|
|
393
|
+
/** @internal Resolved by the Evolve SDK for the managed door; unset means the create request is sent once. */
|
|
394
|
+
retryCreateRequest?: CreateRequestRetry;
|
|
389
395
|
}
|
|
390
396
|
/** Internal resolved config with required apiKey */
|
|
391
397
|
interface ResolvedE2BConfig {
|
|
@@ -393,6 +399,7 @@ interface ResolvedE2BConfig {
|
|
|
393
399
|
apiUrl?: string;
|
|
394
400
|
defaultTimeoutMs?: number;
|
|
395
401
|
templateId?: string;
|
|
402
|
+
retryCreateRequest?: CreateRequestRetry;
|
|
396
403
|
}
|
|
397
404
|
declare class E2BCommands implements SandboxCommands {
|
|
398
405
|
private sandbox;
|
|
@@ -499,6 +506,7 @@ declare class E2BProvider implements SandboxProvider {
|
|
|
499
506
|
private readonly apiUrl?;
|
|
500
507
|
private readonly defaultTimeoutMs;
|
|
501
508
|
private readonly templateId?;
|
|
509
|
+
private readonly retryCreateRequest?;
|
|
502
510
|
/**
|
|
503
511
|
* Sandbox user configured at create time, reapplied on connect() (e.g., resume).
|
|
504
512
|
* In-memory only: a connect() from a fresh process runs as the template default
|
|
@@ -594,4 +602,4 @@ type _testE2BSandboxImpl = E2BSandboxImpl;
|
|
|
594
602
|
/** The constructor, for the metrics unit test (a vendor sandbox double goes in). */
|
|
595
603
|
declare const _testE2BSandboxImplCtor: typeof E2BSandboxImpl;
|
|
596
604
|
|
|
597
|
-
export { E2BBootCommandError, E2BCommands, type E2BConfig, E2BFiles, E2BIdleTimeoutError, E2BNetworkUpdateUnsupportedError, E2BProvider, E2BResourcesError, type E2BSandboxPaginator, E2B_MAX_LIST_PAGES, E2B_MAX_PAGE_SIZE, E2B_MIN_UPDATE_NETWORK_VERSION, type FileInfo, type FileRange, type FilesystemEvent, type ProcessInfo, type SandboxCommandHandle, type SandboxCommandResult, type SandboxCommands, type SandboxConnectOptions, type SandboxCreateOptions, SandboxFeatureUnsupportedError, type SandboxFiles, type SandboxInfo, type SandboxInspectOptions, type SandboxInstance, type SandboxListOptions, type SandboxListPage, type SandboxMetrics, SandboxNotRunningError, SandboxPathNotFoundError, type SandboxProvider, type SandboxRunOptions, type SandboxSpawnOptions, type WatchHandle, type WatchOptions, _testCollectSandboxPages, type _testE2BSandboxImpl, _testE2BSandboxImplCtor, createE2BProvider, isSandboxFeatureUnsupportedError, isSandboxNotRunningError, isSandboxPathNotFoundError };
|
|
605
|
+
export { type CreateRequestRetry, E2BBootCommandError, E2BCommands, type E2BConfig, E2BFiles, E2BIdleTimeoutError, E2BNetworkUpdateUnsupportedError, E2BProvider, E2BResourcesError, type E2BSandboxPaginator, E2B_MAX_LIST_PAGES, E2B_MAX_PAGE_SIZE, E2B_MIN_UPDATE_NETWORK_VERSION, type FileInfo, type FileRange, type FilesystemEvent, type ProcessInfo, type SandboxCommandHandle, type SandboxCommandResult, type SandboxCommands, type SandboxConnectOptions, type SandboxCreateOptions, SandboxFeatureUnsupportedError, type SandboxFiles, type SandboxInfo, type SandboxInspectOptions, type SandboxInstance, type SandboxListOptions, type SandboxListPage, type SandboxMetrics, SandboxNotRunningError, SandboxPathNotFoundError, type SandboxProvider, type SandboxRunOptions, type SandboxSpawnOptions, type WatchHandle, type WatchOptions, _testCollectSandboxPages, type _testE2BSandboxImpl, _testE2BSandboxImplCtor, createE2BProvider, isSandboxFeatureUnsupportedError, isSandboxNotRunningError, isSandboxPathNotFoundError };
|
package/dist/index.d.ts
CHANGED
|
@@ -267,6 +267,8 @@ interface SandboxCreateOptions {
|
|
|
267
267
|
user?: string;
|
|
268
268
|
/** Home directory used by the SDK for agent config paths; not consumed by the provider. */
|
|
269
269
|
homeDir?: string;
|
|
270
|
+
/** Account the SDK hands its agent config files to; not consumed by the provider. */
|
|
271
|
+
homeOwner?: string;
|
|
270
272
|
}
|
|
271
273
|
/** Options for listing sandboxes */
|
|
272
274
|
interface SandboxListOptions {
|
|
@@ -378,6 +380,8 @@ interface SandboxProvider {
|
|
|
378
380
|
/** The same enumeration for fleet bookkeeping: never throws, reports completeness. */
|
|
379
381
|
listAll(options?: SandboxListOptions): Promise<SandboxListPage>;
|
|
380
382
|
}
|
|
383
|
+
/** Wraps the one request that creates a box, for the SDK to retry a door's 429/503 before any box exists. */
|
|
384
|
+
type CreateRequestRetry = <T>(send: () => Promise<T>) => Promise<T>;
|
|
381
385
|
interface E2BConfig {
|
|
382
386
|
/** E2B API key. Default: reads from E2B_API_KEY env var */
|
|
383
387
|
apiKey?: string;
|
|
@@ -386,6 +390,8 @@ interface E2BConfig {
|
|
|
386
390
|
defaultTimeoutMs?: number;
|
|
387
391
|
/** E2B template ID (default: 'evolve-all'). Create custom templates at https://e2b.dev/docs/sandbox-template */
|
|
388
392
|
templateId?: string;
|
|
393
|
+
/** @internal Resolved by the Evolve SDK for the managed door; unset means the create request is sent once. */
|
|
394
|
+
retryCreateRequest?: CreateRequestRetry;
|
|
389
395
|
}
|
|
390
396
|
/** Internal resolved config with required apiKey */
|
|
391
397
|
interface ResolvedE2BConfig {
|
|
@@ -393,6 +399,7 @@ interface ResolvedE2BConfig {
|
|
|
393
399
|
apiUrl?: string;
|
|
394
400
|
defaultTimeoutMs?: number;
|
|
395
401
|
templateId?: string;
|
|
402
|
+
retryCreateRequest?: CreateRequestRetry;
|
|
396
403
|
}
|
|
397
404
|
declare class E2BCommands implements SandboxCommands {
|
|
398
405
|
private sandbox;
|
|
@@ -499,6 +506,7 @@ declare class E2BProvider implements SandboxProvider {
|
|
|
499
506
|
private readonly apiUrl?;
|
|
500
507
|
private readonly defaultTimeoutMs;
|
|
501
508
|
private readonly templateId?;
|
|
509
|
+
private readonly retryCreateRequest?;
|
|
502
510
|
/**
|
|
503
511
|
* Sandbox user configured at create time, reapplied on connect() (e.g., resume).
|
|
504
512
|
* In-memory only: a connect() from a fresh process runs as the template default
|
|
@@ -594,4 +602,4 @@ type _testE2BSandboxImpl = E2BSandboxImpl;
|
|
|
594
602
|
/** The constructor, for the metrics unit test (a vendor sandbox double goes in). */
|
|
595
603
|
declare const _testE2BSandboxImplCtor: typeof E2BSandboxImpl;
|
|
596
604
|
|
|
597
|
-
export { E2BBootCommandError, E2BCommands, type E2BConfig, E2BFiles, E2BIdleTimeoutError, E2BNetworkUpdateUnsupportedError, E2BProvider, E2BResourcesError, type E2BSandboxPaginator, E2B_MAX_LIST_PAGES, E2B_MAX_PAGE_SIZE, E2B_MIN_UPDATE_NETWORK_VERSION, type FileInfo, type FileRange, type FilesystemEvent, type ProcessInfo, type SandboxCommandHandle, type SandboxCommandResult, type SandboxCommands, type SandboxConnectOptions, type SandboxCreateOptions, SandboxFeatureUnsupportedError, type SandboxFiles, type SandboxInfo, type SandboxInspectOptions, type SandboxInstance, type SandboxListOptions, type SandboxListPage, type SandboxMetrics, SandboxNotRunningError, SandboxPathNotFoundError, type SandboxProvider, type SandboxRunOptions, type SandboxSpawnOptions, type WatchHandle, type WatchOptions, _testCollectSandboxPages, type _testE2BSandboxImpl, _testE2BSandboxImplCtor, createE2BProvider, isSandboxFeatureUnsupportedError, isSandboxNotRunningError, isSandboxPathNotFoundError };
|
|
605
|
+
export { type CreateRequestRetry, E2BBootCommandError, E2BCommands, type E2BConfig, E2BFiles, E2BIdleTimeoutError, E2BNetworkUpdateUnsupportedError, E2BProvider, E2BResourcesError, type E2BSandboxPaginator, E2B_MAX_LIST_PAGES, E2B_MAX_PAGE_SIZE, E2B_MIN_UPDATE_NETWORK_VERSION, type FileInfo, type FileRange, type FilesystemEvent, type ProcessInfo, type SandboxCommandHandle, type SandboxCommandResult, type SandboxCommands, type SandboxConnectOptions, type SandboxCreateOptions, SandboxFeatureUnsupportedError, type SandboxFiles, type SandboxInfo, type SandboxInspectOptions, type SandboxInstance, type SandboxListOptions, type SandboxListPage, type SandboxMetrics, SandboxNotRunningError, SandboxPathNotFoundError, type SandboxProvider, type SandboxRunOptions, type SandboxSpawnOptions, type WatchHandle, type WatchOptions, _testCollectSandboxPages, type _testE2BSandboxImpl, _testE2BSandboxImplCtor, createE2BProvider, isSandboxFeatureUnsupportedError, isSandboxNotRunningError, isSandboxPathNotFoundError };
|
package/dist/index.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import {Sandbox,ConnectionConfig,ApiClient}from'@e2b/code-interpreter';import {compareVersions}from'compare-versions';import'fs';var x=class extends Error{feature;provider;reason;constructor(e,t,n){super(`${t} does not support ${e}${n?`: ${n}`:""}`),this.name="SandboxFeatureUnsupportedError",this.feature=e,this.provider=t,this.reason=n;}},m=class extends Error{path;provider;constructor(e,t){super(`${t}: no such file or directory: ${e}`),this.name="SandboxPathNotFoundError",this.path=e,this.provider=t;}},g=class extends Error{sandboxId;provider;state;constructor(e,t,n){super(`${t} sandbox ${e} is not running (${n}); inspect never starts or resumes a sandbox`),this.name="SandboxNotRunningError",this.sandboxId=e,this.provider=t,this.state=n;}};function P(r,e){return !!r&&typeof r=="object"&&r.name===e}function
|
|
1
|
+
import {Sandbox,ConnectionConfig,ApiClient}from'@e2b/code-interpreter';import {compareVersions}from'compare-versions';import'fs';var x=class extends Error{feature;provider;reason;constructor(e,t,n){super(`${t} does not support ${e}${n?`: ${n}`:""}`),this.name="SandboxFeatureUnsupportedError",this.feature=e,this.provider=t,this.reason=n;}},m=class extends Error{path;provider;constructor(e,t){super(`${t}: no such file or directory: ${e}`),this.name="SandboxPathNotFoundError",this.path=e,this.provider=t;}},g=class extends Error{sandboxId;provider;state;constructor(e,t,n){super(`${t} sandbox ${e} is not running (${n}); inspect never starts or resumes a sandbox`),this.name="SandboxNotRunningError",this.sandboxId=e,this.provider=t,this.state=n;}};function P(r,e){return !!r&&typeof r=="object"&&r.name===e}function V(r){return P(r,"SandboxFeatureUnsupportedError")}function W(r){return P(r,"SandboxPathNotFoundError")}function j(r){return P(r,"SandboxNotRunningError")}function E(r){if(!Number.isInteger(r.offset)||r.offset<0)throw new RangeError(`offset must be a non-negative integer, got ${r.offset}`);if(!Number.isInteger(r.length)||r.length<0)throw new RangeError(`length must be a non-negative integer, got ${r.length}`)}function z(r){return r.padStart(4,"0")}var X=/^(-|[dalTLDpSugct?]+)([-r][-w][-x]){3}$/;function N(r){if(!X.test(r))throw new RangeError(`not a Go file mode string: ${r}`);let e=r.slice(0,-9),t=r.slice(-9),n=e.includes("d")?"dir":e.includes("L")?"symlink":/[DpSc?]/.test(e)?"other":"file",s=(e.includes("u")?2048:0)|(e.includes("g")?1024:0)|(e.includes("t")?512:0);for(let o=0;o<9;o++)t[o]!=="-"&&(s|=1<<8-o);return {type:n,mode:z(s.toString(8))}}function v(r){let e=r instanceof Date?r:typeof r=="number"?new Date(r*1e3):new Date(r);if(Number.isNaN(e.getTime()))throw new RangeError(`not a timestamp: ${String(r)}`);return e.toISOString()}function D(r,e){return r.endsWith("/")?`${r}${e}`:`${r}/${e}`}async function $(r,e,t){if(E(e),e.length===0)return new Uint8Array(0);let n=e.offset+e.length-1,s=await fetch(r,{headers:{Range:`bytes=${e.offset}-${n}`},signal:AbortSignal.timeout(t.timeoutMs)});if(s.status===206){let o=new Uint8Array(await s.arrayBuffer());return o.length>e.length?o.subarray(0,e.length):o}if(s.status===200)return Y(s,e);if(s.status===416)return await s.body?.cancel().catch(()=>{}),new Uint8Array(0);throw await s.body?.cancel().catch(()=>{}),s.status===404?new m(t.path,t.provider):new Error(`${t.provider}: range read of ${t.path} failed (HTTP ${s.status})`)}async function Y(r,e){if(!r.body)return new Uint8Array(0);let t=r.body.getReader(),n=[],s=0,o=0,a=e.offset+e.length;try{for(;;){let{done:c,value:p}=await t.read();if(c)break;let h=s;if(s+=p.length,s>e.offset){let d=Math.max(0,e.offset-h),u=Math.min(p.length,a-h);u>d&&(n.push(p.subarray(d,u)),o+=u-d);}if(s>=a)break}}finally{await t.cancel().catch(()=>{});}let i=new Uint8Array(o),l=0;for(let c of n)i.set(c,l),l+=c.length;return i}var b=3e5,_="0.2.5",ee=new Date(0);function I(r){if(!r||typeof r!="object")return false;if(r.name==="TimeoutError")return true;let e=r.message;return typeof e=="string"&&/timed?\s*out/i.test(e)}var L=100,K=100;function w(r){return r instanceof Date?r.toISOString():String(r)}function q(r){if(typeof r=="string"||r instanceof ArrayBuffer)return r;if(r instanceof Buffer)return new Uint8Array(r).buffer;if(r instanceof Uint8Array)return new Uint8Array(r).buffer;throw new Error(`Unsupported data type for file upload: ${typeof r}. Expected string, Buffer, ArrayBuffer, or Uint8Array.`)}var S=class extends Error{constructor(e){super(e),this.name="E2BResourcesError";}},te="2.25.0",A=class extends Error{constructor(e){super(e),this.name="E2BNetworkUpdateUnsupportedError";}};function R(r){if(r?.outbound==="open"&&r.allowedDestinations?.length)throw new Error("network.allowedDestinations is only valid when outbound is blocked");let e=r?.allowedDestinations??[],t=r?.outbound==="blocked"&&e.length>0;return {allowInternetAccess:r?.outbound!=="blocked"||t,network:t?{denyOut:["0.0.0.0/0"],allowOut:e}:void 0}}var T=class extends Error{constructor(){super("E2B takes no create-time boot command: the sandbox boots its template's own init, and a start command is a template-BUILD field (Template startCmd) this provider never sets. The boot is already inert \u2014 run the process by exec after create, or bake it into the template the `image` names."),this.name="E2BBootCommandError";}},B=class extends Error{constructor(){super("E2B has no idle timeout: its sandbox timeout is an ABSOLUTE lifetime that in-sandbox activity never extends. Use `timeoutMs` for the lifetime, and call setTimeout() to extend a sandbox you know is still working."),this.name="E2BIdleTimeoutError";}},C=class{constructor(e,t){this.sandbox=e;this.defaultUser=t;}async run(e,t){try{let n=await this.sandbox.commands.run(e,{timeoutMs:t?.timeoutMs,envs:t?.envs,cwd:t?.cwd,user:this.defaultUser,onStdout:t?.onStdout,onStderr:t?.onStderr});return {exitCode:n.exitCode,stdout:n.stdout,stderr:n.stderr}}catch(n){if(n&&typeof n=="object"&&"exitCode"in n){let s=n;return {exitCode:s.exitCode,stdout:s.stdout??"",stderr:s.stderr??""}}if(I(n))return {exitCode:124,stdout:"",stderr:n instanceof Error?n.message:"command timed out"};throw n}}async spawn(e,t){let n=await this.sandbox.commands.run(e,{background:true,stdin:t?.stdin??true,timeoutMs:t?.timeoutMs,envs:t?.envs,cwd:t?.cwd,user:this.defaultUser,onStdout:t?.onStdout,onStderr:t?.onStderr});return {processId:String(n.pid),wait:async()=>{try{let s=await n.wait();return {exitCode:s.exitCode,stdout:s.stdout,stderr:s.stderr}}catch(s){if(s&&typeof s=="object"&&"exitCode"in s){let o=s;return {exitCode:o.exitCode,stdout:o.stdout??"",stderr:o.stderr??""}}if(I(s))return {exitCode:124,stdout:"",stderr:s instanceof Error?s.message:"command timed out"};throw s}},kill:()=>this.sandbox.commands.kill(n.pid)}}async list(){return (await this.sandbox.commands.list()).map(t=>({...t,processId:String(t.pid)}))}async connect(e,t){let n=await this.sandbox.commands.connect(Number(e),{onStdout:t?.onStdout,onStderr:t?.onStderr,timeoutMs:t?.timeoutMs});return {processId:String(n.pid),wait:async()=>{try{let s=await n.wait();return {exitCode:s.exitCode,stdout:s.stdout,stderr:s.stderr}}catch(s){if(s&&typeof s=="object"&&"exitCode"in s){let o=s;return {exitCode:o.exitCode,stdout:o.stdout??"",stderr:o.stderr??""}}if(I(s))return {exitCode:124,stdout:"",stderr:s instanceof Error?s.message:"command timed out"};throw s}},kill:()=>this.sandbox.commands.kill(n.pid)}}async sendStdin(e,t){await this.sandbox.commands.sendStdin(Number(e),t);}async kill(e){return this.sandbox.commands.kill(Number(e))}},M=class{constructor(e,t,n){this.sandbox=e;this.defaultUser=t;this.envdVersion=n;}async assertEntryInfo(e){if(this.envdVersion??=(await this.sandbox.getInfo()).envdVersion,compareVersions(this.envdVersion,_)<0)throw new x(e,"e2b",`the sandbox runs envd ${this.envdVersion}; entry permissions, owner, group and mtime need envd ${_} or later (rebuild the template)`)}async read(e){let t=await this.sandbox.files.read(e,{format:"bytes",requestTimeoutMs:b,user:this.defaultUser});if(!t.includes(0))try{return new TextDecoder("utf-8",{fatal:!0,ignoreBOM:!0}).decode(t)}catch{}return t}async write(e,t){await this.sandbox.files.write(e,q(t),{requestTimeoutMs:b,user:this.defaultUser});}async writeBatch(e){let t=e.map(n=>({path:n.path,data:q(n.data)}));await this.sandbox.files.write(t,{requestTimeoutMs:b,user:this.defaultUser});}async makeDir(e){await this.sandbox.files.makeDir(e,{user:this.defaultUser});}async uploadUrl(e,t){return this.sandbox.uploadUrl(e,{user:this.defaultUser,...t?{useSignatureExpiration:t}:{}})}async downloadUrl(e,t){return this.sandbox.downloadUrl(e,{user:this.defaultUser,...t?{useSignatureExpiration:t}:{}})}async exists(e){return this.sandbox.files.exists(e,{user:this.defaultUser})}async list(e){await this.assertEntryInfo("files.list");try{return (await this.sandbox.files.list(e,{user:this.defaultUser})).map(n=>G(n))}catch(t){throw U(t)?new m(e,"e2b"):t}}async stat(e){await this.assertEntryInfo("files.stat");try{return G(await this.sandbox.files.getInfo(e,{user:this.defaultUser}))}catch(t){throw U(t)?new m(e,"e2b"):t}}async readRange(e,t){if(E(t),t.length===0)return new Uint8Array(0);let n=await this.sandbox.downloadUrl(e,{user:this.defaultUser,useSignatureExpiration:Math.ceil(b/1e3)});return $(n,t,{provider:"e2b",path:e,timeoutMs:b})}async remove(e){await this.sandbox.files.remove(e,{user:this.defaultUser});}async rename(e,t){await this.sandbox.files.rename(e,t,{user:this.defaultUser});}async readStream(e){return this.sandbox.files.read(e,{format:"stream",user:this.defaultUser})}async writeStream(e,t){await this.sandbox.files.write(e,t,{user:this.defaultUser});}async writeFromPath(e,t){let{createReadStream:n,statSync:s}=await import('fs'),{Readable:o}=await import('stream'),{randomBytes:a}=await import('crypto'),i=s(t).size,l=`----evolve${a(16).toString("hex")}`,c=Buffer.from(`--${l}\r
|
|
2
2
|
Content-Disposition: form-data; name="file"; filename="blob"\r
|
|
3
3
|
Content-Type: application/octet-stream\r
|
|
4
4
|
\r
|
|
5
5
|
`),p=Buffer.from(`\r
|
|
6
6
|
--${l}--\r
|
|
7
|
-
`);async function*h(){yield c;for await(let d of n(t))yield d;yield p;}try{let d=await this.uploadUrl(e),u=await fetch(d,{method:"POST",body:o.toWeb(o.from(h())),headers:{"Content-Type":`multipart/form-data; boundary=${l}`,"Content-Length":String(c.length+i+p.length)},duplex:"half"});if(!u.ok)throw new Error(`streamed upload to ${e} failed (HTTP ${u.status})`)}catch(d){console.warn(`[e2b] streamed upload of ${t} failed, falling back to a buffered write:`,d instanceof Error?d.message:d);let u=o.toWeb(n(t));await this.writeStream(e,u);}}async watchDir(e,t,n){let s;try{s=await this.sandbox.files.watchDir(e,o=>{let a=o.type==="chmod"?"write":o.type;return t({path:D(e,o.name),type:a})},{recursive:n?.recursive??!1,timeoutMs:0,user:this.defaultUser});}catch(o){throw U(o)?new m(e,"e2b"):o}return {stop:()=>s.stop()}}};function U(r){let e=r&&typeof r=="object"?r.name:void 0;return e==="FileNotFoundError"||e==="NotFoundError"}function
|
|
8
|
-
export{
|
|
7
|
+
`);async function*h(){yield c;for await(let d of n(t))yield d;yield p;}try{let d=await this.uploadUrl(e),u=await fetch(d,{method:"POST",body:o.toWeb(o.from(h())),headers:{"Content-Type":`multipart/form-data; boundary=${l}`,"Content-Length":String(c.length+i+p.length)},duplex:"half"});if(!u.ok)throw new Error(`streamed upload to ${e} failed (HTTP ${u.status})`)}catch(d){console.warn(`[e2b] streamed upload of ${t} failed, falling back to a buffered write:`,d instanceof Error?d.message:d);let u=o.toWeb(n(t));await this.writeStream(e,u);}}async watchDir(e,t,n){let s;try{s=await this.sandbox.files.watchDir(e,o=>{let a=o.type==="chmod"?"write":o.type;return t({path:D(e,o.name),type:a})},{recursive:n?.recursive??!1,timeoutMs:0,user:this.defaultUser});}catch(o){throw U(o)?new m(e,"e2b"):o}return {stop:()=>s.stop()}}};function U(r){let e=r&&typeof r=="object"?r.name:void 0;return e==="FileNotFoundError"||e==="NotFoundError"}function G(r){let{type:e,mode:t}=N(r.permissions),n={name:r.name,path:r.path,type:e,size:r.size,mtime:v(r.modifiedTime??ee),mode:t,owner:r.owner,group:r.group};return e==="symlink"&&r.symlinkTarget!==void 0&&r.symlinkTarget!==r.path&&(n.target=r.symlinkTarget),n}var f=class{constructor(e,t,n,s,o){this.sandbox=e;this.apiKey=t;this.apiUrl=n;this.commands=new C(e,s),this.files=new M(e,s,o);}commands;files;lastMetricsAt;get sandboxId(){return this.sandbox.sandboxId}async metrics(){let e=await this.sandbox.getMetrics(this.lastMetricsAt?{start:this.lastMetricsAt}:{}),t;for(let n of e)(!t||n.timestamp.getTime()>t.timestamp.getTime())&&(t=n);return t?(this.lastMetricsAt=t.timestamp,{cpuPct:t.cpuUsedPct,memUsedMb:t.memUsed/k,memTotalMb:t.memTotal/k,diskUsedMb:t.diskUsed/k,sampledAt:v(t.timestamp),source:"e2b:getMetrics"}):null}getHost(e){return Promise.resolve(this.sandbox.getHost(e))}async isRunning(){return this.sandbox.isRunning()}async getInfo(){let e=await this.sandbox.getInfo();return {sandboxId:e.sandboxId,image:e.templateId,name:e.name,metadata:e.metadata??{},startedAt:w(e.startedAt),endAt:e.endAt?w(e.endAt):void 0}}async updateNetwork(e){let t=R(e),n=this.sandbox;if(typeof n.updateNetwork!="function")throw new A(`The installed e2b client cannot change a running sandbox's network policy: Sandbox.updateNetwork requires e2b >= ${te}. Upgrade the e2b dependency (it is pulled in by @e2b/code-interpreter), or create the sandbox with the policy it needs for its whole lifetime.`);await n.updateNetwork({allowInternetAccess:t.allowInternetAccess,...t.network??{}});}async kill(){try{await this.sandbox.kill();}catch{await new Promise(e=>setTimeout(e,500)),await this.sandbox.kill();}}async pause(){await this.sandbox.betaPause({apiKey:this.apiKey,apiUrl:this.apiUrl});}},O=class{providerType="e2b";name="E2B";apiKey;apiUrl;defaultTimeoutMs;templateId;retryCreateRequest;sandboxUsers=new Map;constructor(e){this.apiKey=e.apiKey,this.apiUrl=e.apiUrl,this.defaultTimeoutMs=e.defaultTimeoutMs??36e5,this.templateId=e.templateId,this.retryCreateRequest=e.retryCreateRequest;}async create(e){if(e.bootCommand!==void 0)throw new T;if(e.idleTimeoutMs!==void 0)throw new B;if(e.resources?.gpu!==void 0||e.resources?.gpuTypes!==void 0)throw new S("E2B offers no GPU allocation at any tier \u2014 a `resources.gpu` request cannot be enforced. Run GPU workloads on a provider that reserves GPUs (modal).");if(e.resources&&(e.resources.cpu!==void 0||e.resources.memory!==void 0||e.resources.disk!==void 0))throw new S("E2B cannot size a sandbox at create time: sizing is fixed by the template (Template.build cpuCount/memoryMB; disk is plan-fixed). Build a template with the desired resources and pass it as `image` instead of `resources`.");let t=e.timeoutMs??this.defaultTimeoutMs,n=e.image??this.templateId??"evolve-all";for(let i of e.phaseNetworkPolicies??[])R(i);let s=R(e.network),o=()=>Sandbox.create(n,{apiKey:this.apiKey,apiUrl:this.apiUrl,envs:e.envs,metadata:e.metadata,timeoutMs:t,...s}),a=await(this.retryCreateRequest?this.retryCreateRequest(o):o());return e.workingDirectory&&await a.files.makeDir(e.workingDirectory,{user:e.user}),e.user&&this.sandboxUsers.set(a.sandboxId,e.user),new f(a,this.apiKey,this.apiUrl,e.user)}async connect(e,t){let n=await Sandbox.connect(e,{apiKey:this.apiKey,apiUrl:this.apiUrl,timeoutMs:t??this.defaultTimeoutMs});return new f(n,this.apiKey,this.apiUrl,this.sandboxUsers.get(e))}async inspect(e,t){let n=await this.fetchSandboxDetail(e);if(n.state!=="running")throw new g(e,"e2b",n.state);let s=F.attach({sandboxId:n.sandboxID,sandboxDomain:n.domain??void 0,envdVersion:n.envdVersion,envdAccessToken:n.envdAccessToken,trafficAccessToken:n.trafficAccessToken??void 0,apiKey:this.apiKey,apiUrl:this.apiUrl});return new f(s,this.apiKey,this.apiUrl,t?.user??this.sandboxUsers.get(e),n.envdVersion)}async fetchSandboxDetail(e){let t=new ConnectionConfig({apiKey:this.apiKey,apiUrl:this.apiUrl}),n=await new ApiClient(t).api.GET("/sandboxes/{sandboxID}",{params:{path:{sandboxID:e}}});if(n.error?.code===404||!n.data&&!n.error)throw new g(e,"e2b","not found");if(n.error)throw new Error(`E2B refused the sandbox record for ${e}: ${n.error.message??n.error.code}`);return n.data}async list(e){let t=await this.paginate(e);if(t.error&&!t.stoppedAtLimit)throw new Error(t.error);return t.sandboxes}async listAll(e){let{stoppedAtLimit:t,...n}=await this.paginate(e);return n}async paginate(e){let t=e?.limit;return H(Sandbox.list({apiKey:this.apiKey,apiUrl:this.apiUrl,query:{state:e?.state,metadata:e?.metadata},limit:t===void 0?L:Math.min(t,L)}),t)}};async function H(r,e){let t=[],n=0,s=new Set;for(;r.hasNext;){if(n>=K)return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:false,error:`sandbox list exceeded ${K} pages`};let o=r.nextToken;if(o!==void 0){if(s.has(o))return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:false,error:"pagination token repeated"};s.add(o);}let a;try{a=await r.nextItems();}catch(i){return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:false,error:`sandbox list failed: ${i instanceof Error?i.message:String(i)}`}}n+=1;for(let i of a){if(e!==void 0&&t.length>=e)return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:true,error:`stopped at the requested limit of ${e} with more sandboxes available`};t.push({sandboxId:i.sandboxId,image:i.templateId,name:i.name,metadata:i.metadata??{},startedAt:w(i.startedAt),endAt:i.endAt?w(i.endAt):void 0});}if(e!==void 0&&t.length>=e&&r.hasNext)return {sandboxes:t,complete:false,pagesFetched:n,stoppedAtLimit:true,error:`stopped at the requested limit of ${e} with more sandboxes available`};if(e!==void 0&&t.length>=e)break}return {sandboxes:t,complete:true,pagesFetched:n,stoppedAtLimit:false}}var ce=H,k=1024*1024,F=class r extends Sandbox{static attach(e){return new r(e)}};function le(r={}){let e=r.apiKey??process.env.E2B_API_KEY;if(!e)throw new Error("E2B API key required. Set E2B_API_KEY environment variable or pass apiKey in config. Get your key at https://e2b.dev/sign-in");return new O({...r,apiKey:e})}var pe=f;
|
|
8
|
+
export{T as E2BBootCommandError,C as E2BCommands,M as E2BFiles,B as E2BIdleTimeoutError,A as E2BNetworkUpdateUnsupportedError,O as E2BProvider,S as E2BResourcesError,K as E2B_MAX_LIST_PAGES,L as E2B_MAX_PAGE_SIZE,te as E2B_MIN_UPDATE_NETWORK_VERSION,x as SandboxFeatureUnsupportedError,g as SandboxNotRunningError,m as SandboxPathNotFoundError,ce as _testCollectSandboxPages,pe as _testE2BSandboxImplCtor,le as createE2BProvider,V as isSandboxFeatureUnsupportedError,j as isSandboxNotRunningError,W as isSandboxPathNotFoundError};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@evolvingmachines/e2b",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.68",
|
|
4
4
|
"keywords": [
|
|
5
5
|
"ai",
|
|
6
6
|
"agents",
|
|
@@ -33,7 +33,7 @@
|
|
|
33
33
|
"build": "tsup --minify",
|
|
34
34
|
"dev": "tsup --watch",
|
|
35
35
|
"type-check": "tsc --noEmit",
|
|
36
|
-
"test:unit": "tsx tests/unit/e2b-list-pagination.test.ts && tsx tests/unit/e2b-files-read.test.ts && tsx tests/unit/e2b-gpu-rejection.test.ts && tsx tests/unit/e2b-boot-command-rejection.test.ts && tsx tests/unit/e2b-template-refresh.test.ts && tsx tests/unit/e2b-files-observe.test.ts"
|
|
36
|
+
"test:unit": "tsx tests/unit/e2b-list-pagination.test.ts && tsx tests/unit/e2b-files-read.test.ts && tsx tests/unit/e2b-gpu-rejection.test.ts && tsx tests/unit/e2b-boot-command-rejection.test.ts && tsx tests/unit/e2b-template-refresh.test.ts && tsx tests/unit/e2b-files-observe.test.ts && tsx tests/unit/e2b-create-request-retry.test.ts"
|
|
37
37
|
},
|
|
38
38
|
"dependencies": {
|
|
39
39
|
"@e2b/code-interpreter": "^2.7.1",
|