Skip to content

Add Python SDK option to opt out of HTTP/2#1406

Closed
sarmientoF wants to merge 1 commit into
e2b-dev:mainfrom
sarmientoF:fix/python-sdk-http1-transport-default
Closed

Add Python SDK option to opt out of HTTP/2#1406
sarmientoF wants to merge 1 commit into
e2b-dev:mainfrom
sarmientoF:fix/python-sdk-http1-transport-default

Conversation

@sarmientoF

@sarmientoF sarmientoF commented Jun 9, 2026

Copy link
Copy Markdown

Summary

  • Keep HTTP/2 as the Python SDK default.
  • Add a public http2 connection option so callers can opt out with http2=False for API and envd transports.
  • Thread the option through sync/async API clients and sandbox envd transport creation.
  • Add tests for the default HTTP/2 behavior and the explicit HTTP/1.1 opt-out.

Why

For normal use, HTTP/2 remains the right default. The opt-out is for server-side high fan-out workloads where httpx uses one HTTP/2 connection per origin and therefore one server MAX_CONCURRENT_STREAMS budget. Once a workload has more long-lived concurrent envd RPCs than the peer stream cap, HTTP/2 requests queue behind that single connection instead of spreading across the existing connection pool.

http2=False gives those workloads a documented alternative: HTTP/1.1 uses the SDK/httpx connection pool and avoids coupling all concurrent envd RPCs to one HTTP/2 stream budget. This is useful for bash/filesystem/commands/pty/control-plane fan-out and does not change behavior for default users.

Reproduction / metrics

Using this branch and AsyncSandbox.commands.run, I ran 180 concurrent commands against one sandbox:

python /tmp/e2b_cloud_http2_repro.py \
  --env-file /Users/fernando-sarmiento/Desktop/jai/E2B/.env \
  --concurrency 180 \
  --sleep-seconds 4 \
  --request-timeout 45

Workload: sleep 4; echo ok, 180 concurrent server-streaming envd RPCs.

mode ok/errors elapsed throughput p50 p95 p99 max
HTTP/2 default 180/0 9.03s 19.94/s 4.82s 9.01s 9.01s 9.01s
HTTP/1.1 opt-out 180/0 5.20s 34.63/s 5.01s 5.16s 5.17s 5.18s

The HTTP/2 run completes in two waves because concurrency above the stream budget cannot use a second HTTP/2 connection. The HTTP/1.1 opt-out completes in one wave because requests are distributed through the connection pool.

Tests

  • ./.venv/bin/pytest tests/test_api_client_transport.py tests/sync/sandbox_sync/test_config_propagation.py tests/async/sandbox_async/test_config_propagation.py
  • ./.venv/bin/ruff check .
  • ./.venv/bin/ruff format --check .
  • ./.venv/bin/ty check

@cla-bot

cla-bot Bot commented Jun 9, 2026

Copy link
Copy Markdown

We require contributors to sign our Contributor License Agreement, and we don't have @sarmientoF on file. You can sign our CLA at https://e2b.dev/docs/cla . Once you've signed, post a comment here that says '@cla-bot check'

@changeset-bot

changeset-bot Bot commented Jun 9, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: ca635b4

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 1 package
Name Type
@e2b/python-sdk Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@sarmientoF sarmientoF force-pushed the fix/python-sdk-http1-transport-default branch from 54abb22 to f847e58 Compare June 9, 2026 06:48
@cla-bot

cla-bot Bot commented Jun 9, 2026

Copy link
Copy Markdown

We require contributors to sign our Contributor License Agreement, and we don't have @sarmientoF on file. You can sign our CLA at https://e2b.dev/docs/cla . Once you've signed, post a comment here that says '@cla-bot check'

@sarmientoF

sarmientoF commented Jun 9, 2026

Copy link
Copy Markdown
Author

@cla-bot check

@cla-bot cla-bot Bot added the cla-signed label Jun 9, 2026
@cla-bot

cla-bot Bot commented Jun 9, 2026

Copy link
Copy Markdown

The cla-bot has been summoned, and re-checked this pull request!

@sarmientoF sarmientoF force-pushed the fix/python-sdk-http1-transport-default branch from f847e58 to ca635b4 Compare June 9, 2026 06:55
@matthewlouisbrockman

Copy link
Copy Markdown
Contributor

switching to http1 leads to more problems than it solves

@matthewlouisbrockman

Copy link
Copy Markdown
Contributor

To reopen, please submit a reproduction of the issue along with metrics for performance

@sarmientoF sarmientoF changed the title Default Python SDK transports to HTTP/1.1 Add Python SDK option to opt out of HTTP/2 Jun 9, 2026
@sarmientoF

Copy link
Copy Markdown
Author

I revised the branch based on the feedback:

  • HTTP/2 remains the default.
  • The PR now only adds a public http2=False opt-out and threads it to API/envd transports.
  • I added the requested reproduction/metrics to the PR body.

Key result from a real E2B sandbox workload: 180 concurrent AsyncSandbox.commands.run("sleep 4; echo ok") calls completed with HTTP/2 default p95 ~= 9.01s versus HTTP/1.1 opt-out p95 ~= 5.16s. This demonstrates the concrete case for HTTP/1.1: high fan-out, long-lived envd RPCs above the HTTP/2 stream budget serialize on one httpx HTTP/2 connection, while HTTP/1.1 spreads across the connection pool.

This keeps default users on HTTP/2 and gives high fan-out users a documented escape hatch instead of requiring monkeypatching.

@sarmientoF

Copy link
Copy Markdown
Author

Opened a fresh PR with the revised scope and current head SHA because this closed PR would not reopen or refresh its head ref: #1407

The new PR keeps HTTP/2 as default and includes the reproduction/metrics requested here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants