Repository navigation
[Python] Add HTTPX2 client library support #24966
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
wing328
merged 7 commits into
OpenAPITools:master
from
Bernardoow:add-support-to-httpx2-python
Sep 23, 2026
Merged
Changes from all commits
Commits
Show all changes
7 commits
Select commit
Hold shift + click to select a range
e557ccd
feat(python): add httpx2 client library support
Bernardoow 2a2cb1b
fix(python): modernize HTTPX2 package metadata and builds
Bernardoow 4139861
refactor(python): unify pyproject generation for httpx2
Bernardoow 963da07
removed duplicated #httpx2
Bernardoow c57ebbf
fix(python): support legacy Poetry packaging with httpx2
Bernardoow ad8ae24
docs(python): remove outdated httpx2 poetry1 limitation
Bernardoow 7ad5928
chore(samples): update generated Python READMEs
Bernardoow File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,17 @@ | ||
| generatorName: python | ||
| outputDir: samples/openapi3/client/petstore/python-httpx2-sync | ||
| inputSpec: modules/openapi-generator/src/test/resources/3_0/python/petstore-with-fake-endpoints-models-for-testing.yaml | ||
| templateDir: modules/openapi-generator/src/main/resources/python | ||
| library: httpx2 | ||
| additionalProperties: | ||
| buildSystem: hatchling | ||
| packageName: petstore_api | ||
| mapNumberTo: float | ||
| poetry1: false | ||
| supportHttpxSync: true | ||
| nameMappings: | ||
| _type: underscore_type | ||
| type_: type_with_underscore | ||
| modelNameMappings: | ||
| # The OpenAPI spec ApiResponse conflicts with the internal ApiResponse | ||
| ApiResponse: ModelApiResponse |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,16 @@ | ||
| generatorName: python | ||
| outputDir: samples/openapi3/client/petstore/python-httpx2 | ||
| inputSpec: modules/openapi-generator/src/test/resources/3_0/python/petstore-with-fake-endpoints-models-for-testing.yaml | ||
| templateDir: modules/openapi-generator/src/main/resources/python | ||
| library: httpx2 | ||
| additionalProperties: | ||
| buildSystem: hatchling | ||
| packageName: petstore_api | ||
| mapNumberTo: float | ||
| poetry1: false | ||
| nameMappings: | ||
| _type: underscore_type | ||
| type_: type_with_underscore | ||
| modelNameMappings: | ||
| # The OpenAPI spec ApiResponse conflicts with the internal ApiResponse | ||
| ApiResponse: ModelApiResponse |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -227,7 +227,7 @@ public PythonClientCodegen() { | |
| cliOptions.add(new CliOption(POETRY1_FALLBACK, "Fallback to formatting pyproject.toml to Poetry 1.x format.")); | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. P2: When an HTTPX2 user supplies metadata containing quotes or control characters, this line selects a template that inserts Prompt for AI agents |
||
| cliOptions.add(new CliOption(LAZY_IMPORTS, "Enable lazy imports.").defaultValue(Boolean.FALSE.toString())); | ||
| cliOptions.add(new CliOption(BUILD_SYSTEM, "Build system to use in pyproject.toml (setuptools, hatchling).").defaultValue("setuptools")); | ||
| cliOptions.add(CliOption.newBoolean(SUPPORT_HTTPX_SYNC, "Generate synchronous '_sync' variants of each API method (httpx library only). " + | ||
| cliOptions.add(CliOption.newBoolean(SUPPORT_HTTPX_SYNC, "Generate synchronous '_sync' variants of each API method (httpx and httpx2 libraries only). " + | ||
| "Each '_sync' method simply calls the corresponding async method and waits for its completion, " + | ||
| "so both synchronous and asynchronous methods are available from the same API class.").defaultValue(Boolean.FALSE.toString())); | ||
| cliOptions.add(CliOption.newBoolean(USE_INDEPENDENT_IMPLICIT_CLIENTS, | ||
|
|
@@ -247,7 +247,8 @@ public PythonClientCodegen() { | |
| supportedLibraries.put("urllib3", "urllib3-based client"); | ||
| supportedLibraries.put("asyncio", "asyncio-based client"); | ||
| supportedLibraries.put("httpx", "httpx-based client"); | ||
| CliOption libraryOption = new CliOption(CodegenConstants.LIBRARY, "library template (sub-template) to use: asyncio, urllib3, httpx"); | ||
| supportedLibraries.put("httpx2", "httpx2-based client"); | ||
| CliOption libraryOption = new CliOption(CodegenConstants.LIBRARY, "library template (sub-template) to use: asyncio, urllib3, httpx, httpx2"); | ||
| libraryOption.setDefault(DEFAULT_LIBRARY); | ||
| cliOptions.add(libraryOption); | ||
| setLibrary(DEFAULT_LIBRARY); | ||
|
|
@@ -271,6 +272,9 @@ public void processOpts() { | |
| this.setLegacyDiscriminatorBehavior(false); | ||
|
|
||
| super.processOpts(); | ||
| if (additionalProperties.containsKey(POETRY1_FALLBACK)) { | ||
| convertPropertyToBooleanAndWriteBack(POETRY1_FALLBACK); | ||
|
Bernardoow marked this conversation as resolved.
|
||
| } | ||
|
|
||
| // map to Dot instead of Period | ||
| specialCharReplacements.put(".", "Dot"); | ||
|
|
@@ -450,10 +454,12 @@ public void processOpts() { | |
| supportingFiles.add(new SupportingFile("asyncio/rest.mustache", packagePath(), "rest.py")); | ||
| additionalProperties.put("async", "true"); | ||
| additionalProperties.put("asyncio", "true"); | ||
| } else if ("httpx".equals(getLibrary())) { | ||
| } else if (isHttpxLibrary()) { | ||
| supportingFiles.add(new SupportingFile("httpx/rest.mustache", packagePath(), "rest.py")); | ||
| additionalProperties.put("async", "true"); | ||
| additionalProperties.put("httpx", "true"); | ||
| additionalProperties.put(getLibrary(), "true"); | ||
| additionalProperties.put("httpxLibrary", true); | ||
| additionalProperties.put("httpxModule", getLibrary()); | ||
| if (Boolean.parseBoolean(String.valueOf(additionalProperties.get(SUPPORT_HTTPX_SYNC)))) { | ||
| // generate synchronous '_sync' method variants alongside the async ones | ||
| additionalProperties.put(SUPPORT_HTTPX_SYNC, true); | ||
|
|
@@ -465,10 +471,10 @@ public void processOpts() { | |
| supportingFiles.add(new SupportingFile("rest.mustache", packagePath(), "rest.py")); | ||
| } | ||
|
|
||
| // 'supportHttpxSync' only makes sense for the (async) httpx library | ||
| if (!"httpx".equals(getLibrary())) { | ||
| // 'supportHttpxSync' only makes sense for the (async) httpx and httpx2 libraries | ||
| if (!isHttpxLibrary()) { | ||
| if (Boolean.parseBoolean(String.valueOf(additionalProperties.get(SUPPORT_HTTPX_SYNC)))) { | ||
| LOGGER.warn("'{}' is only supported with the 'httpx' library and will be ignored.", SUPPORT_HTTPX_SYNC); | ||
| LOGGER.warn("'{}' is only supported with the 'httpx' and 'httpx2' libraries and will be ignored.", SUPPORT_HTTPX_SYNC); | ||
| } | ||
| additionalProperties.remove(SUPPORT_HTTPX_SYNC); | ||
| } | ||
|
|
@@ -635,7 +641,7 @@ private void renameIndependentClientOperationMembers( | |
|
|
||
| private Set<String> independentClientApiMembers() { | ||
| Set<String> members = new HashSet<>(INDEPENDENT_API_MEMBER_NAMES); | ||
| boolean async = "asyncio".equals(getLibrary()) || "httpx".equals(getLibrary()); | ||
| boolean async = "asyncio".equals(getLibrary()) || isHttpxLibrary(); | ||
| members.addAll(async | ||
| ? ASYNC_API_LIFECYCLE_METHODS | ||
| : SYNC_API_LIFECYCLE_METHODS); | ||
|
|
@@ -665,8 +671,12 @@ private boolean usesLegacyApiCompatibility() { | |
| return compatibleWithPythonLegacy && DEFAULT_LIBRARY.equals(getLibrary()); | ||
| } | ||
|
|
||
| private boolean isHttpxLibrary() { | ||
| return "httpx".equals(getLibrary()) || "httpx2".equals(getLibrary()); | ||
| } | ||
|
|
||
| private boolean supportsHttpxSync() { | ||
| return "httpx".equals(getLibrary()) | ||
| return isHttpxLibrary() | ||
| && Boolean.parseBoolean(String.valueOf( | ||
| additionalProperties.get(SUPPORT_HTTPX_SYNC))); | ||
| } | ||
|
|
||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
P2: When an OAS 3.1 license provides an SPDX identifier, this selection makes HTTPX2 emit the shared template's
license = { text = ... }instead of PEP 639 license-expression metadata. Preserve HTTPX2's license-expression rendering in the shared template or keep the HTTPX2-specific template.Prompt for AI agents