From fa699d9dd3ae62262be8c519fe8d3d5e9da0897c Mon Sep 17 00:00:00 2001 From: Mish Ushakov <10400064+mishushakov@users.noreply.github.com> Date: Wed, 3 Jun 2026 13:50:33 +0200 Subject: [PATCH 1/4] Update e2b SDK: js to 2.27.1, python to 2.25.1 Bumps the e2b dependency for both SDKs and adapts to the breaking change in e2b 2.24.0, which removed Sandbox.betaCreate / SandboxBetaCreateOpts (JS) and Sandbox.beta_create (Python). The lifecycle config those methods gated now ships on Sandbox.create, so the desktop overrides are dropped: - js-sdk: removed the betaCreate override and SandboxBetaCreateOpts interface (tsc failed against the new types) - python-sdk: removed the beta_create override (super().beta_create no longer exists, leaving it broken at runtime) Co-Authored-By: Claude Opus 4.8 --- packages/js-sdk/package.json | 2 +- packages/js-sdk/src/sandbox.ts | 91 ------------------------- packages/python-sdk/e2b_desktop/main.py | 74 -------------------- packages/python-sdk/poetry.lock | 55 +++++++++++++-- packages/python-sdk/pyproject.toml | 2 +- pnpm-lock.yaml | 19 ++++-- 6 files changed, 63 insertions(+), 180 deletions(-) diff --git a/packages/js-sdk/package.json b/packages/js-sdk/package.json index 3d4fee4..aab9e7b 100644 --- a/packages/js-sdk/package.json +++ b/packages/js-sdk/package.json @@ -61,6 +61,6 @@ "vitest": "^4.0.0" }, "dependencies": { - "e2b": "^2.19.4" + "e2b": "^2.27.1" } } diff --git a/packages/js-sdk/src/sandbox.ts b/packages/js-sdk/src/sandbox.ts index 8ed85e9..71ef691 100644 --- a/packages/js-sdk/src/sandbox.ts +++ b/packages/js-sdk/src/sandbox.ts @@ -1,7 +1,6 @@ import { Sandbox as SandboxBase, SandboxOpts as SandboxOptsBase, - SandboxBetaCreateOpts as SandboxBetaCreateOptsBase, CommandHandle, CommandResult, CommandExitError, @@ -116,31 +115,6 @@ export interface SandboxOpts extends SandboxOptsBase { display?: string } -/** - * Configuration options for the Sandbox environment. - * @interface SandboxOpts - * @extends {SandboxOptsBase} - */ -export interface SandboxBetaCreateOpts extends SandboxBetaCreateOptsBase { - /** - * The screen resolution in pixels, specified as [width, height]. - * @type {[number, number]} - */ - resolution?: [number, number] - - /** - * Dots per inch (DPI) setting for the display. - * @type {number} - */ - dpi?: number - - /** - * Display identifier. - * @type {string} - */ - display?: string -} - export class Sandbox extends SandboxBase { protected static override readonly defaultTemplate: string = 'desktop' public display: string = ':0' @@ -229,71 +203,6 @@ export class Sandbox extends SandboxBase { return sbx } - /** - * Create a new sandbox from the default `desktop` sandbox template. - * - * @param opts connection options. - * - * @returns sandbox instance for the new sandbox. - * - * @example - * ```ts - * const sandbox = await Sandbox.create() - * ``` - * @constructs Sandbox - */ - static async betaCreate( - this: S, - opts?: SandboxBetaCreateOpts - ): Promise> - /** - * Create a new sandbox from the specified sandbox template. - * - * @param template sandbox template name or ID. - * @param opts connection options. - * - * @returns sandbox instance for the new sandbox. - * - * @example - * ```ts - * const sandbox = await Sandbox.create('') - * ``` - * @constructs Sandbox - */ - static async betaCreate( - this: S, - template: string, - opts?: SandboxBetaCreateOpts - ): Promise> - static async betaCreate( - this: S, - templateOrOpts?: SandboxBetaCreateOpts | string, - opts?: SandboxOpts - ): Promise> { - const { template, sandboxOpts } = - typeof templateOrOpts === 'string' - ? { template: templateOrOpts, sandboxOpts: opts } - : { template: this.defaultTemplate, sandboxOpts: templateOrOpts } - - // Add DISPLAY environment variable if not already set - const display = opts?.display || ':0' - const sandboxOptsWithDisplay = { - ...sandboxOpts, - envs: { - ...sandboxOpts?.envs, - DISPLAY: display, - }, - } - - const sbx = (await super.betaCreate( - template, - sandboxOptsWithDisplay - )) as InstanceType - await sbx._start(display, sandboxOptsWithDisplay) - - return sbx - } - /** * Wait for a command to return a specific result. * @param cmd - The command to run. diff --git a/packages/python-sdk/e2b_desktop/main.py b/packages/python-sdk/e2b_desktop/main.py index c3cabf4..2077721 100644 --- a/packages/python-sdk/e2b_desktop/main.py +++ b/packages/python-sdk/e2b_desktop/main.py @@ -277,80 +277,6 @@ def create( return sbx - @classmethod - def beta_create( - cls, - template: Optional[str] = None, - resolution: Optional[Tuple[int, int]] = None, - dpi: Optional[int] = None, - display: Optional[str] = None, - timeout: Optional[int] = None, - auto_pause: Optional[bool] = False, - metadata: Optional[Dict[str, str]] = None, - envs: Optional[Dict[str, str]] = None, - secure: bool = True, - allow_internet_access: bool = True, - **opts: Unpack[ApiParams], - ) -> Self: - """ - [BETA] This feature is in beta and may change in the future. - - Create a new sandbox. - - By default, the sandbox is created from the default `desktop` sandbox template. - - - :param template: Sandbox template name or ID - :param resolution: Startup the desktop with custom screen resolution. Defaults to (1024, 768) - :param dpi: Startup the desktop with custom DPI. Defaults to 96 - :param display: Startup the desktop with custom display. Defaults to ":0" - :param timeout: Timeout for the sandbox in **seconds**, default to 300 seconds. The maximum time a sandbox can be kept alive is 24 hours (86_400 seconds) for Pro users and 1 hour (3_600 seconds) for Hobby users. - :param auto_pause: Automatically pause the sandbox after the timeout expires. Defaults to `False`. - :param metadata: Custom metadata for the sandbox - :param envs: Custom environment variables for the sandbox - :param secure: Envd is secured with access token and cannot be used without it - :param allow_internet_access: Allow sandbox to access the internet, defaults to `True`. - - :return: A Sandbox instance for the new sandbox - - Use this method instead of using the constructor to create a new sandbox. - """ - - # Initialize environment variables with DISPLAY - display = display or ":0" - if envs is None: - envs = {} - envs["DISPLAY"] = display - - sbx = super().beta_create( - template=template, - timeout=timeout, - metadata=metadata, - envs=envs, - secure=secure, - allow_internet_access=allow_internet_access, - **opts, - ) - - sbx._display = display - width, height = resolution or (1024, 768) - sbx.commands.run( - f"Xvfb {display} -ac -screen 0 {width}x{height}x24" - f" -retro -dpi {dpi or 96} -nolisten tcp -nolisten unix", - background=True, - timeout=0, - ) - - if not sbx._wait_and_verify( - f"xdpyinfo -display {display}", lambda r: r.exit_code == 0 - ): - raise TimeoutException("Could not start Xvfb") - - sbx.__vnc_server = _VNCServer(sbx) - sbx._start_xfce4() - - return sbx - def _wait_and_verify( self, cmd: str, diff --git a/packages/python-sdk/poetry.lock b/packages/python-sdk/poetry.lock index b116efb..b162eeb 100644 --- a/packages/python-sdk/poetry.lock +++ b/packages/python-sdk/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 2.2.1 and should not be changed by hand. +# This file is automatically @generated by Poetry 2.1.1 and should not be changed by hand. [[package]] name = "anyio" @@ -209,19 +209,20 @@ files = [ [[package]] name = "e2b" -version = "2.20.3" +version = "2.25.1" description = "E2B SDK that give agents cloud environments" optional = false python-versions = "<4.0,>=3.10" groups = ["main"] files = [ - {file = "e2b-2.20.3-py3-none-any.whl", hash = "sha256:46c6b5ffc45c9ca6dc270dd4d29427cef6a2600c55a895565657ff2bedc06303"}, - {file = "e2b-2.20.3.tar.gz", hash = "sha256:c6e91f71946755e1579b4ca1e175819d9f174b932b92e115cf36c2fd04674f3c"}, + {file = "e2b-2.25.1-py3-none-any.whl", hash = "sha256:5ea5d1766082c1db504f86ebe17abe8b6a07f33d8addfb1a7778fae4a9549891"}, + {file = "e2b-2.25.1.tar.gz", hash = "sha256:b87f8da3bbcce613e1bef9a90c46ef042a053f3f311b5ab45fcff5bdf1b1b425"}, ] [package.dependencies] attrs = ">=23.2.0" dockerfile-parse = ">=2.0.1,<3.0.0" +h2 = ">=4,<5" httpcore = ">=1.0.5,<2.0.0" httpx = ">=0.27.0,<1.0.0" packaging = ">=24.1" @@ -238,7 +239,7 @@ description = "Backport of PEP 654 (exception groups)" optional = false python-versions = ">=3.7" groups = ["main", "dev"] -markers = "python_version == \"3.10\"" +markers = "python_version < \"3.11\"" files = [ {file = "exceptiongroup-1.2.2-py3-none-any.whl", hash = "sha256:3111b9d131c238bec2f8f516e123e14ba243563fb135d3fe885990585aa7795b"}, {file = "exceptiongroup-1.2.2.tar.gz", hash = "sha256:47c2edf7c6738fafb49fd34290706d1a1a2f4d1c6df275526b62cbb4aa5393cc"}, @@ -274,6 +275,34 @@ files = [ {file = "h11-0.16.0.tar.gz", hash = "sha256:4e35b956cf45792e4caa5885e69fba00bdbc6ffafbfa020300e549b208ee5ff1"}, ] +[[package]] +name = "h2" +version = "4.3.0" +description = "Pure-Python HTTP/2 protocol implementation" +optional = false +python-versions = ">=3.9" +groups = ["main"] +files = [ + {file = "h2-4.3.0-py3-none-any.whl", hash = "sha256:c438f029a25f7945c69e0ccf0fb951dc3f73a5f6412981daee861431b70e2bdd"}, + {file = "h2-4.3.0.tar.gz", hash = "sha256:6c59efe4323fa18b47a632221a1888bd7fde6249819beda254aeca909f221bf1"}, +] + +[package.dependencies] +hpack = ">=4.1,<5" +hyperframe = ">=6.1,<7" + +[[package]] +name = "hpack" +version = "4.1.0" +description = "Pure-Python HPACK header encoding" +optional = false +python-versions = ">=3.9" +groups = ["main"] +files = [ + {file = "hpack-4.1.0-py3-none-any.whl", hash = "sha256:157ac792668d995c657d93111f46b4535ed114f0c9c8d672271bbec7eae1b496"}, + {file = "hpack-4.1.0.tar.gz", hash = "sha256:ec5eca154f7056aa06f196a557655c5b009b382873ac8d1e66e79e87535f1dca"}, +] + [[package]] name = "httpcore" version = "1.0.9" @@ -322,6 +351,18 @@ http2 = ["h2 (>=3,<5)"] socks = ["socksio (==1.*)"] zstd = ["zstandard (>=0.18.0)"] +[[package]] +name = "hyperframe" +version = "6.1.0" +description = "Pure-Python HTTP/2 framing" +optional = false +python-versions = ">=3.9" +groups = ["main"] +files = [ + {file = "hyperframe-6.1.0-py3-none-any.whl", hash = "sha256:b03380493a519fce58ea5af42e4a42317bf9bd425596f7a0835ffce80f1a42e5"}, + {file = "hyperframe-6.1.0.tar.gz", hash = "sha256:f630908a00854a7adeabd6382b43923a4c4cd4b821fcb527e6ab9e15382a3b08"}, +] + [[package]] name = "idna" version = "3.15" @@ -750,7 +791,7 @@ description = "A lil' TOML parser" optional = false python-versions = ">=3.8" groups = ["dev"] -markers = "python_version == \"3.10\"" +markers = "python_version < \"3.11\"" files = [ {file = "tomli-2.1.0-py3-none-any.whl", hash = "sha256:a5c57c3d1c56f5ccdf89f6523458f60ef716e210fc47c4cfb188c5ba473e0391"}, {file = "tomli-2.1.0.tar.gz", hash = "sha256:3f646cae2aec94e17d04973e4249548320197cfabdf130015d023de4b74d8ab8"}, @@ -804,4 +845,4 @@ bracex = ">=2.1.1" [metadata] lock-version = "2.1" python-versions = "^3.10" -content-hash = "3d660548cc270f9e4c0383804f3b014869fc37008ff978a14fd8836485d90896" +content-hash = "baec4f9ed950af94df86d95be9664b72216f307fa51a3c2780057bfa4f1a3972" diff --git a/packages/python-sdk/pyproject.toml b/packages/python-sdk/pyproject.toml index a879613..a88285b 100644 --- a/packages/python-sdk/pyproject.toml +++ b/packages/python-sdk/pyproject.toml @@ -12,7 +12,7 @@ packages = [{ include = "e2b_desktop" }] [tool.poetry.dependencies] python = "^3.10" -e2b = "^2.20.3" +e2b = "^2.25.1" requests = "^2.32.3" pillow = "^12.0.0" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 53a614b..da30975 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -45,8 +45,8 @@ importers: packages/js-sdk: dependencies: e2b: - specifier: ^2.19.4 - version: 2.19.4 + specifier: ^2.27.1 + version: 2.27.1 devDependencies: '@types/node': specifier: ^22.13.9 @@ -758,9 +758,9 @@ packages: resolution: {integrity: sha512-uBq4egWHTcTt33a72vpSG0z3HnPuIl6NqYcTrKEg2azoEyl2hpW0zqlxysq2pK9HlDIHyHyakeYaYnSAwd8bow==} engines: {node: '>=12'} - e2b@2.19.4: - resolution: {integrity: sha512-9RefLykkjzVu+kUQfX5RxBonmZb08jcXIrRCRmZ8zutbG2bKV6PPyhV9O7mcyB1ZVHHO9UD2G8Z0VtY0lC+AAQ==} - engines: {node: '>=20'} + e2b@2.27.1: + resolution: {integrity: sha512-xZ1vXSl4dpWxbvan5vihE2embXzHdlpK1N0CmFUIcj5kdGLpiQXGoQYsz1Dhy8wr9VO724DyRC7Y3iblMElLPQ==} + engines: {node: '>=20.18.1'} es-module-lexer@2.1.0: resolution: {integrity: sha512-n27zTYMjYu1aj4MjCWzSP7G9r75utsaoc8m61weK+W8JMBGGQybd43GstCXZ3WNmSFtGT9wi59qQTW6mhTR5LQ==} @@ -1441,6 +1441,10 @@ packages: undici-types@6.21.0: resolution: {integrity: sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==} + undici@7.27.0: + resolution: {integrity: sha512-+t2Z/GwkZQDtu00813aP66ygViGtPHKhhoFZpQKpKrE+9jIgES+Zw+mFNaDWOVRKiuJjuqKHzD3B1sfGg8+ZOQ==} + engines: {node: '>=20.18.1'} + universalify@0.1.2: resolution: {integrity: sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg==} engines: {node: '>= 4.0.0'} @@ -2154,7 +2158,7 @@ snapshots: dotenv@16.6.1: {} - e2b@2.19.4: + e2b@2.27.1: dependencies: '@bufbuild/protobuf': 2.12.0 '@connectrpc/connect': 2.0.0-rc.3(@bufbuild/protobuf@2.12.0) @@ -2166,6 +2170,7 @@ snapshots: openapi-fetch: 0.14.1 platform: 1.3.6 tar: 7.5.13 + undici: 7.27.0 es-module-lexer@2.1.0: {} @@ -2854,6 +2859,8 @@ snapshots: undici-types@6.21.0: {} + undici@7.27.0: {} + universalify@0.1.2: {} uri-js@4.4.1: From da7e4ecc8d0b9998e2588e79f26e70bc2df59759 Mon Sep 17 00:00:00 2001 From: Mish Ushakov <10400064+mishushakov@users.noreply.github.com> Date: Wed, 3 Jun 2026 13:53:29 +0200 Subject: [PATCH 2/4] Tighten js-sdk engines.node to >=20.18.1 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit e2b 2.27.1 declares engines.node >=20.18.1. Bump @e2b/desktop's range to match so consumers on Node 20.0–20.17 get a clear engine mismatch at install time rather than runtime failures from the upgraded SDK. Co-Authored-By: Claude Opus 4.8 --- packages/js-sdk/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/js-sdk/package.json b/packages/js-sdk/package.json index aab9e7b..fbe5793 100644 --- a/packages/js-sdk/package.json +++ b/packages/js-sdk/package.json @@ -34,7 +34,7 @@ "package.json" ], "engines": { - "node": ">=20" + "node": ">=20.18.1" }, "browserslist": [ "defaults" From 7baa97e0887d35b339e7a4dac5df8097bf464f36 Mon Sep 17 00:00:00 2001 From: Mish Ushakov <10400064+mishushakov@users.noreply.github.com> Date: Wed, 3 Jun 2026 13:54:45 +0200 Subject: [PATCH 3/4] Add changeset for e2b update and betaCreate removal Co-Authored-By: Claude Opus 4.8 --- .changeset/spicy-suns-bow.md | 14 ++++++++++++++ 1 file changed, 14 insertions(+) create mode 100644 .changeset/spicy-suns-bow.md diff --git a/.changeset/spicy-suns-bow.md b/.changeset/spicy-suns-bow.md new file mode 100644 index 0000000..6374ea5 --- /dev/null +++ b/.changeset/spicy-suns-bow.md @@ -0,0 +1,14 @@ +--- +"@e2b/desktop": minor +--- + +Update `e2b` to `2.27.1` and require Node `>=20.18.1` (matching the SDK's engine range). + +The base SDK removed the beta create API in e2b 2.24.0, so `Sandbox.betaCreate` and `SandboxBetaCreateOpts` have been removed. Use `Sandbox.create` with the `lifecycle` option instead: + +```ts +// before +await Sandbox.betaCreate({ autoPause: true }) +// after +await Sandbox.create({ lifecycle: { onTimeout: 'pause' } }) +``` From fbbadc827017f2aaf227a99286e52554b05724c9 Mon Sep 17 00:00:00 2001 From: Mish Ushakov <10400064+mishushakov@users.noreply.github.com> Date: Wed, 3 Jun 2026 13:55:41 +0200 Subject: [PATCH 4/4] Include python sdk in changeset Co-Authored-By: Claude Opus 4.8 --- .changeset/spicy-suns-bow.md | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/.changeset/spicy-suns-bow.md b/.changeset/spicy-suns-bow.md index 6374ea5..cae5761 100644 --- a/.changeset/spicy-suns-bow.md +++ b/.changeset/spicy-suns-bow.md @@ -1,10 +1,11 @@ --- "@e2b/desktop": minor +"@e2b/desktop-python": minor --- -Update `e2b` to `2.27.1` and require Node `>=20.18.1` (matching the SDK's engine range). +Update `e2b` (js → `2.27.1`, python → `2.25.1`). The js SDK now requires Node `>=20.18.1`, matching the upstream engine range. -The base SDK removed the beta create API in e2b 2.24.0, so `Sandbox.betaCreate` and `SandboxBetaCreateOpts` have been removed. Use `Sandbox.create` with the `lifecycle` option instead: +The base SDK removed the beta create API in e2b 2.24.0, so the desktop overrides have been removed: `Sandbox.betaCreate` / `SandboxBetaCreateOpts` (js) and `Sandbox.beta_create` (python). Use `Sandbox.create` with the `lifecycle` option instead: ```ts // before @@ -12,3 +13,10 @@ await Sandbox.betaCreate({ autoPause: true }) // after await Sandbox.create({ lifecycle: { onTimeout: 'pause' } }) ``` + +```python +# before +Sandbox.beta_create(auto_pause=True) +# after +Sandbox.create(lifecycle={"on_timeout": "pause"}) +```