Skip to content

release: 4.1.0 - #88

Closed
stainless-app[bot] wants to merge 140 commits into
mainfrom
release-please--branches--main--changes--next
Closed

release: 4.1.0#88
stainless-app[bot] wants to merge 140 commits into
mainfrom
release-please--branches--main--changes--next

Conversation

@stainless-app

@stainless-app stainless-app Bot commented Jul 28, 2026

Copy link
Copy Markdown
Contributor

Automated Release PR

4.1.0 (2026-07-28)

Full Changelog: v4.0.0...v4.1.0

Features

  • api: update via SDK Studio (#61) (9c0c551)
  • clean up environment call outs (696f18b)
  • client: add custom JSON encoder for extended type support (87eaded)
  • client: add follow_redirects request option (6eb41c9)
  • client: add support for aiohttp (6f6ddd9)
  • client: add support for binary request streaming (41c399b)
  • client: allow passing NotGiven for body (#67) (3ad7f25)
  • client: send X-Stainless-Read-Timeout header (#63) (a594c75)
  • client: support file upload requests (fde965a)
  • improve future compat with pydantic v3 (bccbddf)
  • internal/types: support eagerly validating pydantic iterators (8e8ca68)
  • internal: implement indices array format for query and form serialization (c601950)
  • stlc: configurable CI runner and private-production-repo support in workflow templates (2da8c4d)
  • support setting headers via env (20336c3)
  • types: replace List[str] with SequenceNotStr in params (0578887)

Bug Fixes

  • asyncify on non-asyncio runtimes (#66) (ca310cd)
  • avoid newer type syntax (db10820)
  • ci: correct conditional (66eb0ef)
  • ci: ensure pip is always available (#78) (d3d295a)
  • ci: release-doctor — report correct token name (65cdccf)
  • ci: remove publishing patch (#79) (493f504)
  • client: add missing f-string prefix in file type error message (8026d49)
  • client: close streams without requiring full consumption (e783145)
  • client: correctly parse binary response | stream (3924997)
  • client: don't send Content-Type header on GET requests (6bcbc4e)
  • client: mark some request bodies as optional (3ad7f25)
  • client: preserve hardcoded query params when merging with user params (12d00c8)
  • compat with Python 3.14 (f7d6103)
  • compat: update signatures of model_dump and model_dump_json for Pydantic v1 (898ca7b)
  • deps: bump minimum typing-extensions version (323a703)
  • ensure file data are only sent as 1 parameter (2a24f49)
  • ensure streams are always closed (f89af68)
  • package: support direct resource imports (ad2d130)
  • parsing: correctly handle nested discriminated unions (cd511d2)
  • parsing: ignore empty metadata (bdd8ead)
  • parsing: parse extra field types (470d8a8)
  • perf: optimize some hot paths (7cc4937)
  • perf: skip traversing types for NotGiven values (38509ba)
  • pydantic v1: more robust ModelField.annotation check (3dc3480)
  • pydantic: do not pass by_alias unless set (887a8ec)
  • sanitize endpoint path params (40f9b7b)
  • tests: fix: tests which call HTTP endpoints directly with the example parameters (539215f)
  • types: allow pyright to infer TypedDict types within SequenceNotStr (84b4806)
  • types: handle more discriminated union shapes (#77) (8b6dcf0)
  • use async_to_httpx_files in patch method (6bfd0c0)
  • use correct field name format for multipart file arrays (0f7a6a4)

Performance Improvements

  • client: optimize file structure copying in multipart requests (639db35)

Chores

  • add Python 3.14 classifier and testing (c172e9c)
  • broadly detect json family of content-type headers (febefbc)
  • bump httpx-aiohttp version to 0.1.9 (7aeb4c8)
  • ci: add timeout thresholds for CI jobs (d5cbcd0)
  • ci: change upload type (d7e4405)
  • ci: enable for pull requests (1ea6fbc)
  • ci: fix installation instructions (6291f4a)
  • ci: only run for pushes and fork pull requests (5d00f3e)
  • ci: only use depot for staging repos (19ee773)
  • ci: skip lint on metadata-only changes (287d210)
  • ci: skip uploading artifacts on stainless-internal branches (d12f89a)
  • ci: upgrade actions/github-script (bdad5ed)
  • ci: upload sdks to package manager (598ec7e)
  • client: minor internal fixes (1e29d3b)
  • deps: mypy 1.18.1 has a regression, pin to 1.17 (fd940b6)
  • do not install brew dependencies in ./scripts/bootstrap by default (67c48f0)
  • docs: grammar improvements (540e711)
  • docs: remove reference to rye shell (ec32daa)
  • docs: update client docstring (#71) (b41543a)
  • docs: use environment variables for authentication in code snippets (ff7f0ef)
  • fix typos (#80) (c1576cc)
  • format all api.md files (034e708)
  • internal/tests: avoid race condition with implicit client cleanup (d3a5435)
  • internal: add --fix argument to lint script (0b1e68e)
  • internal: add missing files argument to base client (5547d1b)
  • internal: add request options to SSE classes (931a27e)
  • internal: add Sequence related utils (5f815ef)
  • internal: avoid errors for isinstance checks on proxies (5dc0949)
  • internal: base client updates (0ac179a)
  • internal: bump dependencies (5c298f6)
  • internal: bump pinned h11 dep (6cafe07)
  • internal: bump pyright version (81c2baf)
  • internal: bump rye to 0.44.0 (#76) (21a20b3)
  • internal: change ci workflow machines (656643d)
  • internal: codegen related update (0b4efb7)
  • internal: codegen related update (2f8fbc4)
  • internal: codegen related update (d6d5a1d)
  • internal: codegen related update (a145cee)
  • internal: codegen related update (#75) (db19786)
  • internal: detect missing future annotations with ruff (23b94ed)
  • internal: expand CI branch coverage (7fd1145)
  • internal: fix devcontainers setup (#68) (97b7254)
  • internal: fix lint error on Python 3.14 (1d9c80a)
  • internal: fix list file params (1b5e333)
  • internal: fix ruff target version (1437b86)
  • internal: fix type traversing dictionary params (#64) (1322c80)
  • internal: grammar fix (it's -> its) (8b1cdb7)
  • internal: import reformatting (8a3f6f0)
  • internal: make test_proxy_environment_variables more resilient (f79d30c)
  • internal: make test_proxy_environment_variables more resilient to env (08e33e4)
  • internal: minor type handling changes (#65) (7e69125)
  • internal: more robust bootstrap script (449a9c3)
  • internal: move mypy configurations to pyproject.toml file (f87b268)
  • internal: properly set pydantic_private (#69) (bc25b84)
  • internal: reduce CI branch coverage (2492996)
  • internal: refactor retries to not use recursion (055e329)
  • internal: reformat pyproject.toml (5b57987)
  • internal: remove extra empty newlines (#74) (3d90dff)
  • internal: remove mock server code (cb06a16)
  • internal: remove trailing character (#81) (4cfa80b)
  • internal: remove unused http client options forwarding (#72) (69a44e3)
  • internal: slight transform perf improvement (#82) (5498eaf)
  • internal: tweak CI branches (2372dd8)
  • internal: update actions/checkout version (54d6bd9)
  • internal: update comment in script (103820e)
  • internal: update conftest.py (83531b4)
  • internal: update gitignore (15b9637)
  • internal: update models test (421a2b5)
  • internal: update pydantic dependency (5dd09a4)
  • internal: update pyright exclude list (f306088)
  • internal: update pyright settings (2d267e1)
  • package: drop Python 3.8 support (95ca18d)
  • package: mark python 3.13 as supported (06ad64f)
  • project: add settings file for vscode (6754b39)
  • readme: fix version rendering on pypi (b1e9e51)
  • readme: update badges (f3f214f)
  • speedup initial import (3b3f4e6)
  • tests: add tests for httpx client instantiation & proxies (5e172cd)
  • tests: run tests in parallel (497b381)
  • tests: simplify get_platform test (ef07d85)
  • tests: skip some failing tests on the latest python versions (39d037c)
  • types: change optional parameter type from NotGiven to Omit (14cb9a9)
  • update @stainless-api/prism-cli to v5.15.0 (d766a01)
  • update github action (d0f9d9e)
  • update lockfile (77726a0)
  • update mock server docs (1241c00)

Documentation

  • client: fix httpx.Timeout documentation reference (3341b85)
  • update URLs from stainlessapi.com to stainless.com (#70) (08062c4)

This pull request is managed by Stainless's GitHub App.

The semver version number is based on included commit messages. Alternatively, you can manually set the version number in the title of this pull request.

For a better experience, it is recommended to use either rebase-merge or squash-merge when merging this pull request.

🔗 Stainless website
📚 Read the docs
🙋 Reach out for help or questions

Greptile Summary

This is the automated 4.1.0 release PR generated by Stainless, consolidating a large batch of upstream SDK improvements into the Brainbase Python client. The changes span client infrastructure, type system, resource loading, and API layer.

  • Client infrastructure: The retry loop is refactored from recursion to iteration (fixing idempotency key drift across retries), resources are now lazy-loaded via cached_property, raw f-string path interpolation is replaced by the new path_template utility which percent-encodes segments and rejects dot-traversal, and a custom JSON serializer (openapi_dumps) adds support for datetime and Pydantic model serialization.
  • Type system: not_given/omit singleton instances are introduced alongside the existing NOT_GIVEN sentinel for ergonomics; SequenceNotStr, BinaryTypes, and AsyncBinaryTypes are added; follow_redirects is wired through RequestOptions to httpx.
  • Voice deployment types: VoiceCreateResponse, VoiceUpdateResponse, and VoiceRetrieveResponse (all structurally identical) are consolidated into a single VoiceDeployment model — this simplifies the API surface but removes previously-published type names.

Confidence Score: 4/5

Safe to merge for new users; existing users who imported VoiceCreateResponse, VoiceUpdateResponse, or VoiceRetrieveResponse directly will encounter ImportError after upgrading.

The infrastructure changes (retry-loop refactor, lazy resource loading, path sanitization, custom JSON encoder) are well-constructed and test-backed. The one concrete concern is the removal of three publicly-documented type names in a minor version: users who pinned from brainbase.types.workers.deployments import VoiceCreateResponse will break on upgrade. All other changes are additive or fix-forward.

Files Needing Attention: src/brainbase/types/workers/deployments/init.py — the removal of the three response type aliases without backward-compat shims is the only file warranting a second look before merging.

Important Files Changed

Filename Overview
src/brainbase/_client.py Resources switched from eager init assignment to cached_property for lazy loading; adds BRAINBASE_CUSTOM_HEADERS env var support; minor docstring redundancy in AsyncBrainbase.init.
src/brainbase/types/workers/deployments/init.py Removes three publicly-documented types (VoiceCreateResponse, VoiceUpdateResponse, VoiceRetrieveResponse) and replaces them with the unified VoiceDeployment; this is a breaking change shipped in a minor version.
src/brainbase/resources/workers/deployments/voice.py Path parameters now sanitised via path_template instead of raw f-strings; optional fields switched from NotGiven/NOT_GIVEN to Omit/omit; return types consolidated to VoiceDeployment.
src/brainbase/_utils/_path.py New path_template utility that percent-encodes URI path/query/fragment segments per RFC 3986 and rejects dot-segment traversal; well-structured security improvement over raw f-string interpolation.
src/brainbase/_base_client.py Retry loop refactored from recursion to iteration; idempotency key now generated once before the loop (fixing per-attempt key drift); X-Stainless-Read-Timeout header added; follow_redirects request option plumbed through; PageInfo gains json body support for pagination.
src/brainbase/_types.py Adds not_given/omit singleton instances, SequenceNotStr protocol, BinaryTypes/AsyncBinaryTypes, follow_redirects in RequestOptions, and ArrayFormat/NestedFormat literal types.
src/brainbase/_utils/_json.py New openapi_dumps serializer with custom encoder handling datetime (ISO 8601) and pydantic.BaseModel objects; used to replace httpx's built-in JSON serialization for finer control.
src/brainbase/types/workers/deployments/voice_deployment.py New unified VoiceDeployment model consolidating the previously separate Create/Retrieve/Update response types, which all had identical fields.

Class Diagram

%%{init: {'theme': 'neutral'}}%%
classDiagram
    class VoiceDeployment {
        +str id
        +Optional[str] delegate_aux_deployments_id
        +Optional[str] phone_number
        +Optional[str] voice_id
        +Optional[str] voice_provider
    }
    class VoiceCreateResponse {
        <<removed>>
    }
    class VoiceRetrieveResponse {
        <<removed>>
    }
    class VoiceUpdateResponse {
        <<removed>>
    }
    VoiceCreateResponse --|> VoiceDeployment : consolidated into
    VoiceRetrieveResponse --|> VoiceDeployment : consolidated into
    VoiceUpdateResponse --|> VoiceDeployment : consolidated into
    class VoiceResource {
        +create(worker_id) VoiceDeployment
        +retrieve(worker_id, deployment_id) VoiceDeployment
        +update(deployment_id, worker_id) VoiceDeployment
        +list(worker_id) VoiceListResponse
        +delete(deployment_id, worker_id) None
    }
    VoiceResource --> VoiceDeployment : returns
Loading

Comments Outside Diff (1)

  1. src/brainbase/types/workers/deployments/__init__.py, line 1-8 (link)

    P1 Breaking type removal in a minor release

    VoiceCreateResponse, VoiceUpdateResponse, and VoiceRetrieveResponse were publicly documented types in api.md and exported from brainbase.types.workers.deployments. Removing them in a 4.0.0 → 4.1.0 minor bump violates semver — any user who imported them directly (e.g. from brainbase.types.workers.deployments import VoiceCreateResponse) will get an ImportError at import time. The consolidation into VoiceDeployment makes semantic sense (all three had identical fields), but it should be accompanied by backward-compat re-exports until a major version, or released as 5.0.0.

    Prompt To Fix With AI
    This is a comment left during a code review.
    Path: src/brainbase/types/workers/deployments/__init__.py
    Line: 1-8
    
    Comment:
    **Breaking type removal in a minor release**
    
    `VoiceCreateResponse`, `VoiceUpdateResponse`, and `VoiceRetrieveResponse` were publicly documented types in `api.md` and exported from `brainbase.types.workers.deployments`. Removing them in a 4.0.0 → 4.1.0 minor bump violates semver — any user who imported them directly (e.g. `from brainbase.types.workers.deployments import VoiceCreateResponse`) will get an `ImportError` at import time. The consolidation into `VoiceDeployment` makes semantic sense (all three had identical fields), but it should be accompanied by backward-compat re-exports until a major version, or released as 5.0.0.
    
    ---
    
    For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.
Prompt To Fix All With AI
### Issue 1
src/brainbase/types/workers/deployments/__init__.py:1-8
**Breaking type removal in a minor release**

`VoiceCreateResponse`, `VoiceUpdateResponse`, and `VoiceRetrieveResponse` were publicly documented types in `api.md` and exported from `brainbase.types.workers.deployments`. Removing them in a 4.0.0 → 4.1.0 minor bump violates semver — any user who imported them directly (e.g. `from brainbase.types.workers.deployments import VoiceCreateResponse`) will get an `ImportError` at import time. The consolidation into `VoiceDeployment` makes semantic sense (all three had identical fields), but it should be accompanied by backward-compat re-exports until a major version, or released as 5.0.0.

### Issue 2
src/brainbase/_client.py:263
Redundant "async" prefix — "async AsyncBrainbase" reads as the word "async" twice. The Sync docstring uses "synchronous Brainbase client instance" as the pattern; the async counterpart should mirror that form.

```suggestion
        """Construct a new asynchronous Brainbase client instance.
```

---

For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.

Reviews (1): Last reviewed commit: "release: 4.1.0" | Re-trigger Greptile

Greptile also left 1 inline comment on this PR.

fix(client): mark some request bodies as optional
Note that we still want to run tests, as these depend on the metadata.
Pin all GitHub Actions referenced in generated workflows (both
first-party `actions/*` and third-party) to immutable commit SHAs.
Updating pinned actions is now a deliberate codegen-side bump rather
than implicit on every workflow run.
Comment thread src/brainbase/_client.py
_strict_response_validation: bool = False,
) -> None:
"""Construct a new async brainbase client instance.
"""Construct a new async AsyncBrainbase client instance.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Redundant "async" prefix — "async AsyncBrainbase" reads as the word "async" twice. The Sync docstring uses "synchronous Brainbase client instance" as the pattern; the async counterpart should mirror that form.

Suggested change
"""Construct a new async AsyncBrainbase client instance.
"""Construct a new asynchronous Brainbase client instance.
Prompt To Fix With AI
This is a comment left during a code review.
Path: src/brainbase/_client.py
Line: 263

Comment:
Redundant "async" prefix — "async AsyncBrainbase" reads as the word "async" twice. The Sync docstring uses "synchronous Brainbase client instance" as the pattern; the async counterpart should mirror that form.

```suggestion
        """Construct a new asynchronous Brainbase client instance.
```

---

For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.

Note: If this suggestion doesn't match your team's coding style, reply to this and let me know. I'll remember it for next time!

@Nauxie Nauxie closed this Aug 4, 2026
@Nauxie

Nauxie commented Aug 4, 2026

Copy link
Copy Markdown
Member

Auto-closed by PR Janitor after 8 days of inactivity. Reopen anytime if this is still relevant.

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.

1 participant