From f40670ee9fed508cfe21612ec0329a2d0758eefc Mon Sep 17 00:00:00 2001 From: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com> Date: Thu, 9 Apr 2026 18:54:50 +0000 Subject: [PATCH 1/3] Add aiohttp support documentation for Python SDK Co-Authored-By: bot_apk --- .../sdks/overview/python/aiohttp-support.mdx | 78 +++++++++++++++++++ fern/products/sdks/sdks.yml | 3 + 2 files changed, 81 insertions(+) create mode 100644 fern/products/sdks/overview/python/aiohttp-support.mdx diff --git a/fern/products/sdks/overview/python/aiohttp-support.mdx b/fern/products/sdks/overview/python/aiohttp-support.mdx new file mode 100644 index 000000000..eb96d6fbe --- /dev/null +++ b/fern/products/sdks/overview/python/aiohttp-support.mdx @@ -0,0 +1,78 @@ +--- +title: aiohttp support +headline: aiohttp support (Python) +description: Fern-generated Python SDKs auto-detect aiohttp for async HTTP operations, resolving DNS concurrency issues without requiring code changes. +--- + + +Fern-generated Python SDKs include built-in support for [aiohttp](https://docs.aiohttp.org/) as an async HTTP transport. When the `httpx_aiohttp` package is installed, the generated async client uses it automatically instead of the default `httpx.AsyncClient`, resolving DNS concurrency issues that can occur in high-throughput async contexts. + +No code changes are required. Install the optional extra and the SDK handles the rest. + +## Why use aiohttp + +Python's `httpx.AsyncClient` uses `asyncio.getaddrinfo` for DNS resolution, which can serialize lookups under heavy concurrency. The `aiohttp` transport layer uses its own resolver, avoiding this bottleneck. If your application makes many concurrent async API calls, enabling aiohttp support can improve throughput and reduce latency. + +## Installation + +Install the SDK with the `aiohttp` optional extra: + +```bash +pip install your-package[aiohttp] +``` + +Or with Poetry: + +```bash +poetry add "your-package[aiohttp]" +``` + +This installs two additional dependencies: + +- `aiohttp` — the async HTTP framework +- `httpx-aiohttp` — a bridge that lets `httpx` use `aiohttp` as its transport + +## How auto-detection works + +The generated async client checks at runtime whether `httpx_aiohttp` is importable: + +- **With `[aiohttp]` installed:** async operations use the aiohttp transport automatically. +- **Without `[aiohttp]` installed:** async operations use the default httpx transport, with no change in behavior. + +If a custom `httpx_client` is passed to the async client constructor, that client is used as-is and auto-detection is skipped. + +## Generated dependencies + +The generated `pyproject.toml` includes an `[aiohttp]` optional dependency group: + +```toml title="pyproject.toml" +[tool.poetry.extras] +aiohttp = ["aiohttp", "httpx-aiohttp"] +``` + +The generator also produces a `_default_clients.py` module and a test file (`tests/test_aiohttp_autodetect.py`) that verifies auto-detection for both the with and without `httpx_aiohttp` scenarios. + +## CI testing + +The generated GitHub Actions workflow includes a two-pass test strategy: + +1. **Standard tests** — runs the full test suite without the aiohttp extra. +2. **aiohttp tests** — installs the extra and runs tests marked with `@pytest.mark.aiohttp`. + +To run aiohttp-specific tests locally: + +```bash +poetry install --extras aiohttp +poetry run pytest -m aiohttp +``` + +To run all tests including aiohttp: + +```bash +poetry install --extras aiohttp +poetry run pytest +``` + + +If you use the `extras` configuration option in `generators.yml` to define your own extras, the built-in `aiohttp` extra is merged with your custom configuration automatically. + diff --git a/fern/products/sdks/sdks.yml b/fern/products/sdks/sdks.yml index 17c73071b..7318eafe4 100644 --- a/fern/products/sdks/sdks.yml +++ b/fern/products/sdks/sdks.yml @@ -71,6 +71,9 @@ navigation: - page: Dynamic authentication path: ./overview/python/dynamic-authentication.mdx slug: dynamic-authentication + - page: aiohttp support + path: ./overview/python/aiohttp-support.mdx + slug: aiohttp-support - changelog: ./overview/python/changelog slug: changelog - link: Customer showcase From fdb8da60cb7a97df5111a5b55862747d86315442 Mon Sep 17 00:00:00 2001 From: Devin Logan Date: Wed, 15 Apr 2026 14:30:00 -0400 Subject: [PATCH 2/3] add cross references, condense explanation --- fern/products/sdks/guides/generated-sdk.mdx | 1 + .../sdks/overview/python/aiohttp-support.mdx | 45 +++++-------------- .../sdks/overview/python/configuration.mdx | 2 + 3 files changed, 13 insertions(+), 35 deletions(-) diff --git a/fern/products/sdks/guides/generated-sdk.mdx b/fern/products/sdks/guides/generated-sdk.mdx index c1378ed1c..7288fec5c 100644 --- a/fern/products/sdks/guides/generated-sdk.mdx +++ b/fern/products/sdks/guides/generated-sdk.mdx @@ -56,6 +56,7 @@ Your SDK users can configure individual requests using language-specific options | Timeouts | Configure request timeouts (default: 30 seconds for C# and PHP, 60 seconds for all other languages) | All languages | | [Retries](/sdks/deep-dives/retries-with-backoff) | Configure maximum retries (default: 2 with exponential backoff for 408, 429, and 5xx responses) | All languages except Ruby and Swift | | Custom HTTP client | Override the default HTTP client for unsupported environments or custom requirements | TypeScript, Python, Java, PHP, and Swift | +| [aiohttp transport](/learn/sdks/generators/python/aiohttp-support) | Opt into `aiohttp` as the async HTTP transport to resolve DNS concurrency bottlenecks | Python only | | Custom headers | Send additional headers with any request | TypeScript, Java, and Swift | | Raw response data | Access response headers alongside parsed data | TypeScript, Python, and Go | | Query parameters | Add extra query string parameters | TypeScript and Swift | diff --git a/fern/products/sdks/overview/python/aiohttp-support.mdx b/fern/products/sdks/overview/python/aiohttp-support.mdx index eb96d6fbe..5ee59e696 100644 --- a/fern/products/sdks/overview/python/aiohttp-support.mdx +++ b/fern/products/sdks/overview/python/aiohttp-support.mdx @@ -5,17 +5,15 @@ description: Fern-generated Python SDKs auto-detect aiohttp for async HTTP opera --- -Fern-generated Python SDKs include built-in support for [aiohttp](https://docs.aiohttp.org/) as an async HTTP transport. When the `httpx_aiohttp` package is installed, the generated async client uses it automatically instead of the default `httpx.AsyncClient`, resolving DNS concurrency issues that can occur in high-throughput async contexts. +Every Fern-generated Python SDK ships with opt-in support for [aiohttp](https://docs.aiohttp.org/) as an async HTTP transport. When the `aiohttp` optional extra is installed, the generated async client uses it automatically instead of the default `httpx.AsyncClient`. -No code changes are required. Install the optional extra and the SDK handles the rest. +This matters for SDKs that make many concurrent async API calls: `httpx.AsyncClient` serializes DNS lookups via `asyncio.getaddrinfo` under heavy concurrency, while `aiohttp` uses its own resolver to avoid that bottleneck. -## Why use aiohttp - -Python's `httpx.AsyncClient` uses `asyncio.getaddrinfo` for DNS resolution, which can serialize lookups under heavy concurrency. The `aiohttp` transport layer uses its own resolver, avoiding this bottleneck. If your application makes many concurrent async API calls, enabling aiohttp support can improve throughput and reduce latency. +No generator configuration is required. The `[aiohttp]` extra, runtime auto-detection, and CI coverage are generated for every Python SDK. ## Installation -Install the SDK with the `aiohttp` optional extra: +SDK users opt in by installing the `aiohttp` extra alongside your package: ```bash pip install your-package[aiohttp] @@ -27,19 +25,7 @@ Or with Poetry: poetry add "your-package[aiohttp]" ``` -This installs two additional dependencies: - -- `aiohttp` — the async HTTP framework -- `httpx-aiohttp` — a bridge that lets `httpx` use `aiohttp` as its transport - -## How auto-detection works - -The generated async client checks at runtime whether `httpx_aiohttp` is importable: - -- **With `[aiohttp]` installed:** async operations use the aiohttp transport automatically. -- **Without `[aiohttp]` installed:** async operations use the default httpx transport, with no change in behavior. - -If a custom `httpx_client` is passed to the async client constructor, that client is used as-is and auto-detection is skipped. +If a user passes a custom `httpx_client` to the async client constructor, auto-detection is skipped and the provided client is used as-is. ## Generated dependencies @@ -50,29 +36,18 @@ The generated `pyproject.toml` includes an `[aiohttp]` optional dependency group aiohttp = ["aiohttp", "httpx-aiohttp"] ``` -The generator also produces a `_default_clients.py` module and a test file (`tests/test_aiohttp_autodetect.py`) that verifies auto-detection for both the with and without `httpx_aiohttp` scenarios. +If you define your own extras via the [`extras`](/sdks/overview/python/configuration#extras) configuration option in `generators.yml`, the built-in `aiohttp` extra is preserved and merged with your custom configuration. ## CI testing -The generated GitHub Actions workflow includes a two-pass test strategy: +The generated GitHub Actions workflow runs tests in two passes so both transport paths are covered: -1. **Standard tests** — runs the full test suite without the aiohttp extra. -2. **aiohttp tests** — installs the extra and runs tests marked with `@pytest.mark.aiohttp`. +1. Standard tests without the aiohttp extra. +2. Tests marked `@pytest.mark.aiohttp` with the extra installed. -To run aiohttp-specific tests locally: +To verify the aiohttp path locally: ```bash poetry install --extras aiohttp poetry run pytest -m aiohttp ``` - -To run all tests including aiohttp: - -```bash -poetry install --extras aiohttp -poetry run pytest -``` - - -If you use the `extras` configuration option in `generators.yml` to define your own extras, the built-in `aiohttp` extra is merged with your custom configuration automatically. - diff --git a/fern/products/sdks/overview/python/configuration.mdx b/fern/products/sdks/overview/python/configuration.mdx index f678ec427..20366b669 100644 --- a/fern/products/sdks/overview/python/configuration.mdx +++ b/fern/products/sdks/overview/python/configuration.mdx @@ -94,6 +94,8 @@ Specify additional development dependencies to include in the generated SDK's se Define optional dependency groups that users can install with your package using pip extras (e.g., `pip install your-package[extra-name]`). + +Custom extras are merged with the built-in [`aiohttp` extra](/learn/sdks/generators/python/aiohttp-support) at generation time, so declaring your own extras won't clobber it. From 26f3bd36a16e2e19a82ced255661b417b8a5a098 Mon Sep 17 00:00:00 2001 From: Devin Logan Date: Wed, 15 Apr 2026 14:39:55 -0400 Subject: [PATCH 3/3] correct file loc --- .../sdks/{overview => generators}/python/aiohttp-support.mdx | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename fern/products/sdks/{overview => generators}/python/aiohttp-support.mdx (100%) diff --git a/fern/products/sdks/overview/python/aiohttp-support.mdx b/fern/products/sdks/generators/python/aiohttp-support.mdx similarity index 100% rename from fern/products/sdks/overview/python/aiohttp-support.mdx rename to fern/products/sdks/generators/python/aiohttp-support.mdx