forked from loafle/openapi-generator-original
Merge remote-tracking branch 'origin/master' into 5.4.x
This commit is contained in:
commit
2b7910c875
@ -26,17 +26,17 @@ jobs:
|
||||
- name: Set up JDK ${{ matrix.java }}
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
distribution: 'adopt'
|
||||
distribution: 'temurin'
|
||||
java-version: ${{ matrix.java }}
|
||||
|
||||
- uses: actions/cache@v2.1.6
|
||||
- uses: actions/cache@v2.1.7
|
||||
with:
|
||||
path: ~/.m2/repository
|
||||
key: ${{ runner.os }}-maven-${{ hashFiles('pom.xml', 'modules/**/pom.xml') }}
|
||||
restore-keys: |
|
||||
${{ runner.os }}-maven-
|
||||
|
||||
- uses: actions/cache@v2.1.6
|
||||
- uses: actions/cache@v2.1.7
|
||||
with:
|
||||
path: |
|
||||
~/.gradle/caches
|
||||
|
6
.github/workflows/gradle-test.yaml
vendored
6
.github/workflows/gradle-test.yaml
vendored
@ -36,18 +36,18 @@ jobs:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-java@v2
|
||||
with:
|
||||
distribution: 'adopt'
|
||||
distribution: 'temurin'
|
||||
java-version: 11
|
||||
# Cache Gradle Dependencies
|
||||
- name: Setup Gradle Dependencies Cache
|
||||
uses: actions/cache@v2
|
||||
uses: actions/cache@v2.1.7
|
||||
with:
|
||||
path: ~/.gradle/caches
|
||||
key: ${{ runner.os }}-gradle-caches-${{ hashFiles('**/*.gradle', '**/*.gradle.kts') }}
|
||||
|
||||
# Cache Gradle Wrapper
|
||||
- name: Setup Gradle Wrapper Cache
|
||||
uses: actions/cache@v2
|
||||
uses: actions/cache@v2.1.7
|
||||
with:
|
||||
path: ~/.gradle/wrapper
|
||||
key: ${{ runner.os }}-gradle-wrapper-${{ hashFiles('**/gradle/wrapper/gradle-wrapper.properties') }}
|
||||
|
26
.github/workflows/openapi-generator.yaml
vendored
26
.github/workflows/openapi-generator.yaml
vendored
@ -17,11 +17,12 @@ jobs:
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up JDK 8
|
||||
uses: actions/setup-java@v1
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
java-version: 8
|
||||
distribution: 'temurin'
|
||||
- name: Cache maven dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: cache-maven-repository
|
||||
with:
|
||||
@ -52,11 +53,12 @@ jobs:
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up JDK 8
|
||||
uses: actions/setup-java@v1
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
java-version: 8
|
||||
distribution: 'temurin'
|
||||
- name: Cache maven dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: cache-maven-repository
|
||||
with:
|
||||
@ -86,9 +88,10 @@ jobs:
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up JDK 8
|
||||
uses: actions/setup-java@v1
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
java-version: 8
|
||||
distribution: 'temurin'
|
||||
- name: Download openapi-generator-cli.jar artifact
|
||||
uses: actions/download-artifact@v2.0.10
|
||||
with:
|
||||
@ -124,9 +127,10 @@ jobs:
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up JDK 8
|
||||
uses: actions/setup-java@v1
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
java-version: 8
|
||||
distribution: 'temurin'
|
||||
- name: Download openapi-generator-cli.jar artifact
|
||||
uses: actions/download-artifact@v2.0.10
|
||||
with:
|
||||
@ -158,11 +162,12 @@ jobs:
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up JDK 11
|
||||
uses: actions/setup-java@v1
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
java-version: 11
|
||||
distribution: 'temurin'
|
||||
- name: Cache maven dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: cache-maven-repository
|
||||
with:
|
||||
@ -190,11 +195,12 @@ jobs:
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up JDK 11
|
||||
uses: actions/setup-java@v1
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
java-version: 11
|
||||
distribution: 'temurin'
|
||||
- name: Cache maven dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: cache-maven-repository
|
||||
with:
|
||||
|
12
.github/workflows/samples-dart.yaml
vendored
12
.github/workflows/samples-dart.yaml
vendored
@ -20,10 +20,10 @@ jobs:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-java@v2
|
||||
with:
|
||||
distribution: 'adopt'
|
||||
distribution: 'temurin'
|
||||
java-version: 8
|
||||
- name: Cache maven dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: maven-repository
|
||||
with:
|
||||
@ -32,7 +32,7 @@ jobs:
|
||||
~/.gradle
|
||||
key: ${{ runner.os }}-${{ github.job }}-${{ env.cache-name }}-${{ hashFiles('**/pom.xml') }}
|
||||
- name: Cache test dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: pub-cache
|
||||
with:
|
||||
@ -53,10 +53,10 @@ jobs:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-java@v2
|
||||
with:
|
||||
distribution: 'adopt'
|
||||
distribution: 'temurin'
|
||||
java-version: 8
|
||||
- name: Cache maven dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: maven-repository
|
||||
with:
|
||||
@ -65,7 +65,7 @@ jobs:
|
||||
~/.gradle
|
||||
key: ${{ runner.os }}-${{ github.job }}-${{ env.cache-name }}-${{ hashFiles('**/pom.xml') }}
|
||||
- name: Cache test dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: pub-cache
|
||||
with:
|
||||
|
7
.github/workflows/samples-kotlin.yaml
vendored
7
.github/workflows/samples-kotlin.yaml
vendored
@ -30,8 +30,7 @@ jobs:
|
||||
#- samples/client/petstore/kotlin-json-request-string
|
||||
- samples/client/petstore/kotlin-jvm-okhttp4-coroutines
|
||||
- samples/client/petstore/kotlin-moshi-codegen
|
||||
# need some special setup
|
||||
#- samples/client/petstore/kotlin-multiplatform
|
||||
- samples/client/petstore/kotlin-multiplatform
|
||||
- samples/client/petstore/kotlin-nonpublic
|
||||
- samples/client/petstore/kotlin-nullable
|
||||
- samples/client/petstore/kotlin-okhttp3
|
||||
@ -45,10 +44,10 @@ jobs:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-java@v2
|
||||
with:
|
||||
distribution: 'adopt'
|
||||
distribution: 'temurin'
|
||||
java-version: 8
|
||||
- name: Cache maven dependencies
|
||||
uses: actions/cache@v2.1.6
|
||||
uses: actions/cache@v2.1.7
|
||||
env:
|
||||
cache-name: maven-repository
|
||||
with:
|
||||
|
2
.github/workflows/sonar.yml
vendored
2
.github/workflows/sonar.yml
vendored
@ -16,7 +16,7 @@ jobs:
|
||||
- name: Set up JDK 11
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
distribution: 'adopt'
|
||||
distribution: 'temurin'
|
||||
java-version: 11
|
||||
- name: Compile with Maven
|
||||
run: mvn -B -q clean install jacoco:report
|
||||
|
28
README.md
28
README.md
@ -76,7 +76,7 @@ OpenAPI Generator allows generation of API client libraries (SDK generation), se
|
||||
| | Languages/Frameworks |
|
||||
| -------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
||||
| **API clients** | **ActionScript**, **Ada**, **Apex**, **Bash**, **C**, **C#** (.net 2.0, 3.5 or later, .NET Standard 1.3 - 2.0, .NET Core 2.0, .NET 5.0. Libraries: RestSharp, HttpClient), **C++** (Arduino, cpp-restsdk, Qt5, Tizen, Unreal Engine 4), **Clojure**, **Crystal**, **Dart**, **Elixir**, **Elm**, **Eiffel**, **Erlang**, **Go**, **Groovy**, **Haskell** (http-client, Servant), **Java** (Apache HttpClient, Jersey1.x, Jersey2.x, OkHttp, Retrofit1.x, Retrofit2.x, Feign, RestTemplate, RESTEasy, Vertx, Google API Client Library for Java, Rest-assured, Spring 5 Web Client, MicroProfile Rest Client), **k6**, **Kotlin**, **Lua**, **Nim**, **Node.js/JavaScript** (ES5, ES6, AngularJS with Google Closure Compiler annotations, Flow types, Apollo GraphQL DataStore), **Objective-C**, **OCaml**, **Perl**, **PHP**, **PowerShell**, **Python**, **R**, **Ruby**, **Rust** (hyper, reqwest, rust-server), **Scala** (akka, http4s, scalaz, sttp, swagger-async-httpclient), **Swift** (2.x, 3.x, 4.x, 5.x), **Typescript** (AngularJS, Angular (2.x - 11.x), Aurelia, Axios, Fetch, Inversify, jQuery, Nestjs, Node, redux-query, Rxjs) |
|
||||
| **Server stubs** | **Ada**, **C#** (ASP.NET Core, NancyFx), **C++** (Pistache, Restbed, Qt5 QHTTPEngine), **Erlang**, **F#** (Giraffe), **Go** (net/http, Gin, Echo), **Haskell** (Servant, Yesod), **Java** (MSF4J, Spring, Undertow, JAX-RS: CDI, CXF, Inflector, Jersey, RestEasy, Play Framework, [PKMST](https://github.com/ProKarma-Inc/pkmst-getting-started-examples), [Vert.x](https://vertx.io/)), **Kotlin** (Spring Boot, Ktor, Vertx), **PHP** (Laravel, Lumen, [Mezzio (fka Zend Expressive)](https://github.com/mezzio/mezzio), Slim, Silex, [Symfony](https://symfony.com/)), **Python** (FastAPI, Flask), **NodeJS**, **Ruby** (Sinatra, Rails5), **Rust** (rust-server), **Scala** (Akka, [Finch](https://github.com/finagle/finch), [Lagom](https://github.com/lagom/lagom), [Play](https://www.playframework.com/), Scalatra) |
|
||||
| **Server stubs** | **Ada**, **C#** (ASP.NET Core, NancyFx, Azure Functions), **C++** (Pistache, Restbed, Qt5 QHTTPEngine), **Erlang**, **F#** (Giraffe), **Go** (net/http, Gin, Echo), **Haskell** (Servant, Yesod), **Java** (MSF4J, Spring, Undertow, JAX-RS: CDI, CXF, Inflector, Jersey, RestEasy, Play Framework, [PKMST](https://github.com/ProKarma-Inc/pkmst-getting-started-examples), [Vert.x](https://vertx.io/)), **Kotlin** (Spring Boot, Ktor, Vertx), **PHP** (Laravel, Lumen, [Mezzio (fka Zend Expressive)](https://github.com/mezzio/mezzio), Slim, Silex, [Symfony](https://symfony.com/)), **Python** (FastAPI, Flask), **NodeJS**, **Ruby** (Sinatra, Rails5), **Rust** (rust-server), **Scala** (Akka, [Finch](https://github.com/finagle/finch), [Lagom](https://github.com/lagom/lagom), [Play](https://www.playframework.com/), Scalatra) |
|
||||
| **API documentation generators** | **HTML**, **Confluence Wiki**, **Asciidoc**, **Markdown**, **PlantUML** |
|
||||
| **Configuration files** | [**Apache2**](https://httpd.apache.org/) |
|
||||
| **Others** | **GraphQL**, **JMeter**, **Ktorm**, **MySQL Schema**, **Protocol Buffer**, **WSDL** |
|
||||
@ -223,21 +223,21 @@ Examples:
|
||||
# Execute latest released openapi-generator-cli
|
||||
openapi-generator-cli version
|
||||
|
||||
# Execute version 3.1.0 for the current invocation, regardless of the latest released version
|
||||
OPENAPI_GENERATOR_VERSION=3.1.0 openapi-generator-cli version
|
||||
# Execute version 4.1.0 for the current invocation, regardless of the latest released version
|
||||
OPENAPI_GENERATOR_VERSION=4.1.0 openapi-generator-cli version
|
||||
|
||||
# Execute version 3.1.0-SNAPSHOT for the current invocation
|
||||
OPENAPI_GENERATOR_VERSION=3.1.0-SNAPSHOT openapi-generator-cli version
|
||||
# Execute version 4.1.0-SNAPSHOT for the current invocation
|
||||
OPENAPI_GENERATOR_VERSION=4.1.0-SNAPSHOT openapi-generator-cli version
|
||||
|
||||
# Execute version 3.0.2 for every invocation in the current shell session
|
||||
export OPENAPI_GENERATOR_VERSION=3.0.2
|
||||
openapi-generator-cli version # is 3.0.2
|
||||
openapi-generator-cli version # is also 3.0.2
|
||||
# Execute version 4.0.2 for every invocation in the current shell session
|
||||
export OPENAPI_GENERATOR_VERSION=4.0.2
|
||||
openapi-generator-cli version # is 4.0.2
|
||||
openapi-generator-cli version # is also 4.0.2
|
||||
|
||||
# To "install" a specific version, set the variable in .bashrc/.bash_profile
|
||||
echo "export OPENAPI_GENERATOR_VERSION=3.0.2" >> ~/.bashrc
|
||||
echo "export OPENAPI_GENERATOR_VERSION=4.0.2" >> ~/.bashrc
|
||||
source ~/.bashrc
|
||||
openapi-generator-cli version # is always 3.0.2, unless any of the above overrides are done ad hoc
|
||||
openapi-generator-cli version # is always 4.0.2, unless any of the above overrides are done ad hoc
|
||||
```
|
||||
|
||||
### [1.4 - Build Projects](#table-of-contents)
|
||||
@ -577,6 +577,7 @@ Here are some companies/projects (alphabetical order) using OpenAPI Generator in
|
||||
- [Adaptant Solutions AG](https://www.adaptant.io/)
|
||||
- [adesso SE](https://www.adesso.de/)
|
||||
- [Agoda](https://www.agoda.com/)
|
||||
- [Airthings](https://www.airthings.com/)
|
||||
- [Allianz](https://www.allianz.com)
|
||||
- [Angular.Schule](https://angular.schule/)
|
||||
- [Aqovia](https://aqovia.com/)
|
||||
@ -843,6 +844,8 @@ Here are some companies/projects (alphabetical order) using OpenAPI Generator in
|
||||
- 2021-10-02 - [How to Write Fewer Lines of Code with the OpenAPI Generator](https://hackernoon.com/how-to-write-fewer-lines-of-code-with-the-openapi-generator) by [Mikhail Alfa](https://hackernoon.com/u/alphamikle)
|
||||
- 2021-10-12 - [OpenAPI Generator : 4000 étoiles sur GitHub et des spaghettis](https://www.youtube.com/watch?v=9hEsNBSqTFk) by [Jérémie Bresson](https://github.com/jmini) at [Devoxx FR 2021](https://cfp.devoxx.fr/2021/speaker/jeremie_bresson)
|
||||
- 2021-10-17 - [Generate a TypeScript HTTP Client From An OpenAPI Spec In DotNET 5](https://richardwillis.info/blog/generate-a-type-script-http-client-from-an-open-api-spec-in-dot-net-5) by [Richard Willis](https://github.com/badsyntax)
|
||||
- 2021-11-06 - [スタートアップの開発で意識したこと](https://zenn.dev/woo_noo/articles/5cb09f8e2899ae782ad1) by [woo-noo](https://zenn.dev/woo_noo)
|
||||
- 2021-11-09 - [Effective Software Development using OpenAPI Generator](https://apexlabs.ai/post/effective-software-development-using-openapi-generator) by Ajil Oomme
|
||||
|
||||
## [6 - About Us](#table-of-contents)
|
||||
|
||||
@ -951,6 +954,7 @@ Here is a list of template creators:
|
||||
* C# ASP.NET 5: @jimschubert [:heart:](https://www.patreon.com/jimschubert)
|
||||
* C# ASP.NET Core 3.0: @A-Joshi
|
||||
* C# APS.NET Core 3.1: @phatcher
|
||||
* C# Azure functions: @Abrhm7786
|
||||
* C# NancyFX: @mstefaniuk
|
||||
* C++ (Qt5 QHttpEngine): @etherealjoy
|
||||
* C++ Pistache: @sebymiano
|
||||
@ -1059,7 +1063,7 @@ If you want to join the committee, please kindly apply by sending an email to te
|
||||
| GraphQL | @renepardon (2018/12) |
|
||||
| Groovy | |
|
||||
| Haskell | |
|
||||
| Java | @bbdouglas (2017/07) @sreeshas (2017/08) @jfiala (2017/08) @lukoyanov (2017/09) @cbornet (2017/09) @jeff9finger (2018/01) @karismann (2019/03) @Zomzog (2019/04) @lwlee2608 (2019/10) @nmuesch (2021/01) |
|
||||
| Java | @bbdouglas (2017/07) @sreeshas (2017/08) @jfiala (2017/08) @lukoyanov (2017/09) @cbornet (2017/09) @jeff9finger (2018/01) @karismann (2019/03) @Zomzog (2019/04) @lwlee2608 (2019/10) |
|
||||
| JMeter | @kannkyo (2021/01) |
|
||||
| Kotlin | @jimschubert (2017/09) [:heart:](https://www.patreon.com/jimschubert), @dr4ke616 (2018/08) @karismann (2019/03) @Zomzog (2019/04) @andrewemery (2019/10) @4brunu (2019/11) @yutaka0m (2020/03) |
|
||||
| Lua | @daurnimator (2017/08) |
|
||||
|
9
bin/configs/java-okhttp-gson-nextgen.yaml
Normal file
9
bin/configs/java-okhttp-gson-nextgen.yaml
Normal file
@ -0,0 +1,9 @@
|
||||
generatorName: java
|
||||
outputDir: samples/client/petstore/java/okhttp-gson-nextgen
|
||||
library: okhttp-gson-nextgen
|
||||
#inputSpec: modules/openapi-generator/src/test/resources/2_0/petstore-with-fake-endpoints-models-for-testing.yaml
|
||||
inputSpec: modules/openapi-generator/src/test/resources/3_0/java/petstore-with-fake-endpoints-models-for-testing-with-http-signature-okhttp-gson.yaml
|
||||
templateDir: modules/openapi-generator/src/main/resources/Java
|
||||
additionalProperties:
|
||||
artifactId: petstore-okhttp-gson-nextgen
|
||||
hideGenerationTimestamp: "true"
|
6
bin/configs/other/csharp-netcore-functions.yaml
Normal file
6
bin/configs/other/csharp-netcore-functions.yaml
Normal file
@ -0,0 +1,6 @@
|
||||
generatorName: csharp-netcore-functions
|
||||
outputDir: samples/client/petstore/csharp-netcore-functions
|
||||
inputSpec: modules/openapi-generator/src/test/resources/3_0/petstore.yaml
|
||||
templateDir: modules/openapi-generator/src/main/resources/csharp-netcore-functions
|
||||
#additionalProperties:
|
||||
# packageGuid: '{321C8C3F-0156-40C1-AE42-D59761FB9B6C}'
|
12
bin/configs/swift5-frozenEnums.yaml
Normal file
12
bin/configs/swift5-frozenEnums.yaml
Normal file
@ -0,0 +1,12 @@
|
||||
generatorName: swift5
|
||||
outputDir: samples/client/petstore/swift5/frozenEnums
|
||||
inputSpec: modules/openapi-generator/src/test/resources/2_0/swift/petstore-with-fake-endpoints-models-for-testing.yaml
|
||||
templateDir: modules/openapi-generator/src/main/resources/swift5
|
||||
generateAliasAsModel: true
|
||||
additionalProperties:
|
||||
podAuthors: ""
|
||||
podSummary: PetstoreClient
|
||||
sortParamsByRequiredFlag: false
|
||||
generateFrozenEnums: false
|
||||
projectName: PetstoreClient
|
||||
podHomepage: https://github.com/openapitools/openapi-generator
|
@ -0,0 +1,11 @@
|
||||
generatorName: typescript-angular
|
||||
outputDir: samples/client/petstore/typescript-angular-v13-provided-in-root/builds/with-npm
|
||||
inputSpec: modules/openapi-generator/src/test/resources/2_0/petstore.yaml
|
||||
templateDir: modules/openapi-generator/src/main/resources/typescript-angular
|
||||
additionalProperties:
|
||||
ngVersion: 13.0.1
|
||||
npmVersion: 1.0.0
|
||||
npmName: '@openapitools/typescript-angular-petstore'
|
||||
npmRepository: https://skimdb.npmjs.com/registry
|
||||
snapshot: false
|
||||
supportsES6: true
|
7
bin/configs/typescript-angular-v13-provided-in-root.yaml
Normal file
7
bin/configs/typescript-angular-v13-provided-in-root.yaml
Normal file
@ -0,0 +1,7 @@
|
||||
generatorName: typescript-angular
|
||||
outputDir: samples/client/petstore/typescript-angular-v13-provided-in-root/builds/default
|
||||
inputSpec: modules/openapi-generator/src/test/resources/2_0/petstore.yaml
|
||||
templateDir: modules/openapi-generator/src/main/resources/typescript-angular
|
||||
additionalProperties:
|
||||
ngVersion: 13.0.1
|
||||
supportsES6: true
|
@ -86,6 +86,7 @@ The following generators are available:
|
||||
* [cpp-qt-qhttpengine-server](generators/cpp-qt-qhttpengine-server.md)
|
||||
* [cpp-restbed-server](generators/cpp-restbed-server.md)
|
||||
* [csharp-nancyfx](generators/csharp-nancyfx.md)
|
||||
* [csharp-netcore-functions (beta)](generators/csharp-netcore-functions.md)
|
||||
* [erlang-server](generators/erlang-server.md)
|
||||
* [fsharp-functions (beta)](generators/fsharp-functions.md)
|
||||
* [fsharp-giraffe-server (beta)](generators/fsharp-giraffe-server.md)
|
||||
|
@ -58,6 +58,7 @@ These options may be applied as additional-properties (cli) or configOptions (pl
|
||||
<ul class="column-ul">
|
||||
<li>abstract</li>
|
||||
<li>alias</li>
|
||||
<li>annotation</li>
|
||||
<li>as</li>
|
||||
<li>as?</li>
|
||||
<li>asm</li>
|
||||
|
300
docs/generators/csharp-netcore-functions.md
Normal file
300
docs/generators/csharp-netcore-functions.md
Normal file
@ -0,0 +1,300 @@
|
||||
---
|
||||
title: Config Options for csharp-netcore-functions
|
||||
sidebar_label: csharp-netcore-functions
|
||||
---
|
||||
|
||||
These options may be applied as additional-properties (cli) or configOptions (plugins). Refer to [configuration docs](https://openapi-generator.tech/docs/configuration) for more details.
|
||||
|
||||
| Option | Description | Values | Default |
|
||||
| ------ | ----------- | ------ | ------- |
|
||||
|allowUnicodeIdentifiers|boolean, toggles whether unicode identifiers are allowed in names or not, default is false| |false|
|
||||
|caseInsensitiveResponseHeaders|Make API response's headers case-insensitive| |false|
|
||||
|conditionalSerialization|Serialize only those properties which are initialized by user, accepted values are true or false, default value is false.| |false|
|
||||
|disallowAdditionalPropertiesIfNotPresent|If false, the 'additionalProperties' implementation (set to true by default) is compliant with the OAS and JSON schema specifications. If true (default), keep the old (incorrect) behaviour that 'additionalProperties' is set to false by default.|<dl><dt>**false**</dt><dd>The 'additionalProperties' implementation is compliant with the OAS and JSON schema specifications.</dd><dt>**true**</dt><dd>Keep the old (incorrect) behaviour that 'additionalProperties' is set to false by default.</dd></dl>|true|
|
||||
|hideGenerationTimestamp|Hides the generation timestamp when files are generated.| |true|
|
||||
|interfacePrefix|Prefix interfaces with a community standard or widely accepted prefix.| |I|
|
||||
|library|HTTP library template (sub-template) to use|<dl><dt>**httpclient**</dt><dd>HttpClient (https://docs.microsoft.com/en-us/dotnet/api/system.net.http.httpclient) (Experimental. May subject to breaking changes without further notice.)</dd><dt>**restsharp**</dt><dd>RestSharp (https://github.com/restsharp/RestSharp)</dd></dl>|restsharp|
|
||||
|licenseId|The identifier of the license| |null|
|
||||
|modelPropertyNaming|Naming convention for the property: 'camelCase', 'PascalCase', 'snake_case' and 'original', which keeps the original name| |PascalCase|
|
||||
|netCoreProjectFile|Use the new format (.NET Core) for .NET project files (.csproj).| |false|
|
||||
|nonPublicApi|Generates code with reduced access modifiers; allows embedding elsewhere without exposing non-public API calls to consumers.| |false|
|
||||
|nullableReferenceTypes|Use nullable annotations in the project. Only supported on C# 8 / ASP.NET Core 3.0 or newer.| |false|
|
||||
|optionalAssemblyInfo|Generate AssemblyInfo.cs.| |true|
|
||||
|optionalEmitDefaultValues|Set DataMember's EmitDefaultValue.| |false|
|
||||
|optionalMethodArgument|C# Optional method argument, e.g. void square(int x=10) (.net 4.0+ only).| |true|
|
||||
|optionalProjectFile|Generate {PackageName}.csproj.| |true|
|
||||
|packageGuid|The GUID that will be associated with the C# project| |null|
|
||||
|packageName|C# package name (convention: Title.Case).| |Org.OpenAPITools|
|
||||
|packageTags|Tags to identify the package| |null|
|
||||
|packageVersion|C# package version.| |1.0.0|
|
||||
|releaseNote|Release note, default to 'Minor update'.| |Minor update|
|
||||
|returnICollection|Return ICollection<T> instead of the concrete type.| |false|
|
||||
|sortParamsByRequiredFlag|Sort method arguments to place required parameters before optional parameters.| |true|
|
||||
|sourceFolder|source folder for generated code| |src|
|
||||
|targetFramework|The target .NET framework version. To target multiple frameworks, use `;` as the separator, e.g. `netstandard2.1;netcoreapp3.0`|<dl><dt>**netstandard1.3**</dt><dd>.NET Standard 1.3 compatible</dd><dt>**netstandard1.4**</dt><dd>.NET Standard 1.4 compatible</dd><dt>**netstandard1.5**</dt><dd>.NET Standard 1.5 compatible</dd><dt>**netstandard1.6**</dt><dd>.NET Standard 1.6 compatible</dd><dt>**netstandard2.0**</dt><dd>.NET Standard 2.0 compatible</dd><dt>**netstandard2.1**</dt><dd>.NET Standard 2.1 compatible</dd><dt>**netcoreapp2.0**</dt><dd>.NET Core 2.0 compatible</dd><dt>**netcoreapp2.1**</dt><dd>.NET Core 2.1 compatible</dd><dt>**netcoreapp3.0**</dt><dd>.NET Core 3.0 compatible</dd><dt>**netcoreapp3.1**</dt><dd>.NET Core 3.1 compatible</dd><dt>**net47**</dt><dd>.NET Framework 4.7 compatible</dd><dt>**net5.0**</dt><dd>.NET 5.0 compatible</dd></dl>|netstandard2.0|
|
||||
|useCollection|Deserialize array types to Collection<T> instead of List<T>.| |false|
|
||||
|useDateTimeOffset|Use DateTimeOffset to model date-time properties| |false|
|
||||
|useOneOfDiscriminatorLookup|Use the discriminator's mapping in oneOf to speed up the model lookup. IMPORTANT: Validation (e.g. one and only one match in oneOf's schemas) will be skipped.| |false|
|
||||
|validatable|Generates self-validatable models.| |true|
|
||||
|
||||
## IMPORT MAPPING
|
||||
|
||||
| Type/Alias | Imports |
|
||||
| ---------- | ------- |
|
||||
|
||||
|
||||
## INSTANTIATION TYPES
|
||||
|
||||
| Type/Alias | Instantiated By |
|
||||
| ---------- | --------------- |
|
||||
|array|List|
|
||||
|list|List|
|
||||
|map|Dictionary|
|
||||
|
||||
|
||||
## LANGUAGE PRIMITIVES
|
||||
|
||||
<ul class="column-ul">
|
||||
<li>Boolean</li>
|
||||
<li>Collection</li>
|
||||
<li>DateTime</li>
|
||||
<li>DateTime?</li>
|
||||
<li>DateTimeOffset</li>
|
||||
<li>DateTimeOffset?</li>
|
||||
<li>Decimal</li>
|
||||
<li>Dictionary</li>
|
||||
<li>Double</li>
|
||||
<li>Float</li>
|
||||
<li>Guid</li>
|
||||
<li>Guid?</li>
|
||||
<li>ICollection</li>
|
||||
<li>Int32</li>
|
||||
<li>Int64</li>
|
||||
<li>List</li>
|
||||
<li>Object</li>
|
||||
<li>String</li>
|
||||
<li>System.IO.Stream</li>
|
||||
<li>bool</li>
|
||||
<li>bool?</li>
|
||||
<li>byte[]</li>
|
||||
<li>decimal</li>
|
||||
<li>decimal?</li>
|
||||
<li>double</li>
|
||||
<li>double?</li>
|
||||
<li>float</li>
|
||||
<li>float?</li>
|
||||
<li>int</li>
|
||||
<li>int?</li>
|
||||
<li>long</li>
|
||||
<li>long?</li>
|
||||
<li>string</li>
|
||||
</ul>
|
||||
|
||||
## RESERVED WORDS
|
||||
|
||||
<ul class="column-ul">
|
||||
<li>Client</li>
|
||||
<li>Configuration</li>
|
||||
<li>Version</li>
|
||||
<li>abstract</li>
|
||||
<li>as</li>
|
||||
<li>base</li>
|
||||
<li>bool</li>
|
||||
<li>break</li>
|
||||
<li>byte</li>
|
||||
<li>case</li>
|
||||
<li>catch</li>
|
||||
<li>char</li>
|
||||
<li>checked</li>
|
||||
<li>class</li>
|
||||
<li>client</li>
|
||||
<li>const</li>
|
||||
<li>continue</li>
|
||||
<li>decimal</li>
|
||||
<li>default</li>
|
||||
<li>delegate</li>
|
||||
<li>do</li>
|
||||
<li>double</li>
|
||||
<li>else</li>
|
||||
<li>enum</li>
|
||||
<li>event</li>
|
||||
<li>explicit</li>
|
||||
<li>extern</li>
|
||||
<li>false</li>
|
||||
<li>finally</li>
|
||||
<li>fixed</li>
|
||||
<li>float</li>
|
||||
<li>for</li>
|
||||
<li>foreach</li>
|
||||
<li>goto</li>
|
||||
<li>if</li>
|
||||
<li>implicit</li>
|
||||
<li>in</li>
|
||||
<li>int</li>
|
||||
<li>interface</li>
|
||||
<li>internal</li>
|
||||
<li>is</li>
|
||||
<li>localVarFileParams</li>
|
||||
<li>localVarFormParams</li>
|
||||
<li>localVarHeaderParams</li>
|
||||
<li>localVarHttpContentType</li>
|
||||
<li>localVarHttpContentTypes</li>
|
||||
<li>localVarHttpHeaderAccept</li>
|
||||
<li>localVarHttpHeaderAccepts</li>
|
||||
<li>localVarPath</li>
|
||||
<li>localVarPathParams</li>
|
||||
<li>localVarPostBody</li>
|
||||
<li>localVarQueryParams</li>
|
||||
<li>localVarResponse</li>
|
||||
<li>localVarStatusCode</li>
|
||||
<li>lock</li>
|
||||
<li>long</li>
|
||||
<li>namespace</li>
|
||||
<li>new</li>
|
||||
<li>null</li>
|
||||
<li>object</li>
|
||||
<li>operator</li>
|
||||
<li>out</li>
|
||||
<li>override</li>
|
||||
<li>parameter</li>
|
||||
<li>params</li>
|
||||
<li>private</li>
|
||||
<li>protected</li>
|
||||
<li>public</li>
|
||||
<li>readonly</li>
|
||||
<li>ref</li>
|
||||
<li>return</li>
|
||||
<li>sbyte</li>
|
||||
<li>sealed</li>
|
||||
<li>short</li>
|
||||
<li>sizeof</li>
|
||||
<li>stackalloc</li>
|
||||
<li>static</li>
|
||||
<li>string</li>
|
||||
<li>struct</li>
|
||||
<li>switch</li>
|
||||
<li>this</li>
|
||||
<li>throw</li>
|
||||
<li>true</li>
|
||||
<li>try</li>
|
||||
<li>typeof</li>
|
||||
<li>uint</li>
|
||||
<li>ulong</li>
|
||||
<li>unchecked</li>
|
||||
<li>unsafe</li>
|
||||
<li>ushort</li>
|
||||
<li>using</li>
|
||||
<li>virtual</li>
|
||||
<li>void</li>
|
||||
<li>volatile</li>
|
||||
<li>while</li>
|
||||
</ul>
|
||||
|
||||
## FEATURE SET
|
||||
|
||||
|
||||
### Client Modification Feature
|
||||
| Name | Supported | Defined By |
|
||||
| ---- | --------- | ---------- |
|
||||
|BasePath|✓|ToolingExtension
|
||||
|Authorizations|✗|ToolingExtension
|
||||
|UserAgent|✓|ToolingExtension
|
||||
|MockServer|✗|ToolingExtension
|
||||
|
||||
### Data Type Feature
|
||||
| Name | Supported | Defined By |
|
||||
| ---- | --------- | ---------- |
|
||||
|Custom|✗|OAS2,OAS3
|
||||
|Int32|✓|OAS2,OAS3
|
||||
|Int64|✓|OAS2,OAS3
|
||||
|Float|✓|OAS2,OAS3
|
||||
|Double|✓|OAS2,OAS3
|
||||
|Decimal|✓|ToolingExtension
|
||||
|String|✓|OAS2,OAS3
|
||||
|Byte|✓|OAS2,OAS3
|
||||
|Binary|✓|OAS2,OAS3
|
||||
|Boolean|✓|OAS2,OAS3
|
||||
|Date|✓|OAS2,OAS3
|
||||
|DateTime|✓|OAS2,OAS3
|
||||
|Password|✓|OAS2,OAS3
|
||||
|File|✓|OAS2
|
||||
|Array|✓|OAS2,OAS3
|
||||
|Maps|✓|ToolingExtension
|
||||
|CollectionFormat|✓|OAS2
|
||||
|CollectionFormatMulti|✓|OAS2
|
||||
|Enum|✓|OAS2,OAS3
|
||||
|ArrayOfEnum|✓|ToolingExtension
|
||||
|ArrayOfModel|✓|ToolingExtension
|
||||
|ArrayOfCollectionOfPrimitives|✓|ToolingExtension
|
||||
|ArrayOfCollectionOfModel|✓|ToolingExtension
|
||||
|ArrayOfCollectionOfEnum|✓|ToolingExtension
|
||||
|MapOfEnum|✓|ToolingExtension
|
||||
|MapOfModel|✓|ToolingExtension
|
||||
|MapOfCollectionOfPrimitives|✓|ToolingExtension
|
||||
|MapOfCollectionOfModel|✓|ToolingExtension
|
||||
|MapOfCollectionOfEnum|✓|ToolingExtension
|
||||
|
||||
### Documentation Feature
|
||||
| Name | Supported | Defined By |
|
||||
| ---- | --------- | ---------- |
|
||||
|Readme|✓|ToolingExtension
|
||||
|Model|✓|ToolingExtension
|
||||
|Api|✓|ToolingExtension
|
||||
|
||||
### Global Feature
|
||||
| Name | Supported | Defined By |
|
||||
| ---- | --------- | ---------- |
|
||||
|Host|✓|OAS2,OAS3
|
||||
|BasePath|✓|OAS2,OAS3
|
||||
|Info|✓|OAS2,OAS3
|
||||
|Schemes|✗|OAS2,OAS3
|
||||
|PartialSchemes|✓|OAS2,OAS3
|
||||
|Consumes|✓|OAS2
|
||||
|Produces|✓|OAS2
|
||||
|ExternalDocumentation|✓|OAS2,OAS3
|
||||
|Examples|✓|OAS2,OAS3
|
||||
|XMLStructureDefinitions|✗|OAS2,OAS3
|
||||
|MultiServer|✗|OAS3
|
||||
|ParameterizedServer|✗|OAS3
|
||||
|ParameterStyling|✗|OAS3
|
||||
|Callbacks|✗|OAS3
|
||||
|LinkObjects|✗|OAS3
|
||||
|
||||
### Parameter Feature
|
||||
| Name | Supported | Defined By |
|
||||
| ---- | --------- | ---------- |
|
||||
|Path|✓|OAS2,OAS3
|
||||
|Query|✓|OAS2,OAS3
|
||||
|Header|✓|OAS2,OAS3
|
||||
|Body|✓|OAS2
|
||||
|FormUnencoded|✓|OAS2
|
||||
|FormMultipart|✓|OAS2
|
||||
|Cookie|✓|OAS3
|
||||
|
||||
### Schema Support Feature
|
||||
| Name | Supported | Defined By |
|
||||
| ---- | --------- | ---------- |
|
||||
|Simple|✓|OAS2,OAS3
|
||||
|Composite|✓|OAS2,OAS3
|
||||
|Polymorphism|✓|OAS2,OAS3
|
||||
|Union|✗|OAS3
|
||||
|
||||
### Security Feature
|
||||
| Name | Supported | Defined By |
|
||||
| ---- | --------- | ---------- |
|
||||
|BasicAuth|✓|OAS2,OAS3
|
||||
|ApiKey|✓|OAS2,OAS3
|
||||
|OpenIDConnect|✗|OAS3
|
||||
|BearerToken|✗|OAS3
|
||||
|OAuth2_Implicit|✓|OAS2,OAS3
|
||||
|OAuth2_Password|✗|OAS2,OAS3
|
||||
|OAuth2_ClientCredentials|✗|OAS2,OAS3
|
||||
|OAuth2_AuthorizationCode|✗|OAS2,OAS3
|
||||
|
||||
### Wire Format Feature
|
||||
| Name | Supported | Defined By |
|
||||
| ---- | --------- | ---------- |
|
||||
|JSON|✓|OAS2,OAS3
|
||||
|XML|✓|OAS2,OAS3
|
||||
|PROTOBUF|✗|ToolingExtension
|
||||
|Custom|✗|OAS2,OAS3
|
@ -31,7 +31,7 @@ These options may be applied as additional-properties (cli) or configOptions (pl
|
||||
|returnICollection|Return ICollection<T> instead of the concrete type.| |false|
|
||||
|sortParamsByRequiredFlag|Sort method arguments to place required parameters before optional parameters.| |true|
|
||||
|sourceFolder|source folder for generated code| |src|
|
||||
|targetFramework|The target .NET framework version. To target multiple frameworks, use `;` as the separator, e.g. `netstandard2.1;netcoreapp3.0`|<dl><dt>**netstandard1.3**</dt><dd>.NET Standard 1.3 compatible</dd><dt>**netstandard1.4**</dt><dd>.NET Standard 1.4 compatible</dd><dt>**netstandard1.5**</dt><dd>.NET Standard 1.5 compatible</dd><dt>**netstandard1.6**</dt><dd>.NET Standard 1.6 compatible</dd><dt>**netstandard2.0**</dt><dd>.NET Standard 2.0 compatible</dd><dt>**netstandard2.1**</dt><dd>.NET Standard 2.1 compatible</dd><dt>**netcoreapp2.0**</dt><dd>.NET Core 2.0 compatible</dd><dt>**netcoreapp2.1**</dt><dd>.NET Core 2.1 compatible</dd><dt>**netcoreapp3.0**</dt><dd>.NET Core 3.0 compatible</dd><dt>**netcoreapp3.1**</dt><dd>.NET Core 3.1 compatible</dd><dt>**net47**</dt><dd>.NET Framework 4.7 compatible</dd><dt>**net5.0**</dt><dd>.NET 5.0 compatible</dd></dl>|netstandard2.0|
|
||||
|targetFramework|The target .NET framework version. To target multiple frameworks, use `;` as the separator, e.g. `netstandard2.1;netcoreapp3.0`|<dl><dt>**netstandard1.3**</dt><dd>.NET Standard 1.3 compatible</dd><dt>**netstandard1.4**</dt><dd>.NET Standard 1.4 compatible</dd><dt>**netstandard1.5**</dt><dd>.NET Standard 1.5 compatible</dd><dt>**netstandard1.6**</dt><dd>.NET Standard 1.6 compatible</dd><dt>**netstandard2.0**</dt><dd>.NET Standard 2.0 compatible</dd><dt>**netstandard2.1**</dt><dd>.NET Standard 2.1 compatible</dd><dt>**netcoreapp2.0**</dt><dd>.NET Core 2.0 compatible</dd><dt>**netcoreapp2.1**</dt><dd>.NET Core 2.1 compatible</dd><dt>**netcoreapp3.0**</dt><dd>.NET Core 3.0 compatible</dd><dt>**netcoreapp3.1**</dt><dd>.NET Core 3.1 compatible</dd><dt>**net47**</dt><dd>.NET Framework 4.7 compatible</dd><dt>**net5.0**</dt><dd>.NET 5.0 compatible</dd><dt>**net6.0**</dt><dd>.NET 6.0 compatible</dd></dl>|netstandard2.0|
|
||||
|useCollection|Deserialize array types to Collection<T> instead of List<T>.| |false|
|
||||
|useDateTimeOffset|Use DateTimeOffset to model date-time properties| |false|
|
||||
|useOneOfDiscriminatorLookup|Use the discriminator's mapping in oneOf to speed up the model lookup. IMPORTANT: Validation (e.g. one and only one match in oneOf's schemas) will be skipped.| |false|
|
||||
|
@ -38,7 +38,7 @@ These options may be applied as additional-properties (cli) or configOptions (pl
|
||||
|invokerPackage|root package for generated code| |org.openapitools.client|
|
||||
|java8|Use Java8 classes instead of third party equivalents. Starting in 5.x, JDK8 is the default and the support for JDK7, JDK6 has been dropped|<dl><dt>**true**</dt><dd>Use Java 8 classes such as Base64</dd><dt>**false**</dt><dd>Various third party libraries as needed</dd></dl>|true|
|
||||
|legacyDiscriminatorBehavior|Set to false for generators with better support for discriminators. (Python, Java, Go, PowerShell, C#have this enabled by default).|<dl><dt>**true**</dt><dd>The mapping in the discriminator includes descendent schemas that allOf inherit from self and the discriminator mapping schemas in the OAS document.</dd><dt>**false**</dt><dd>The mapping in the discriminator includes any descendent schemas that allOf inherit from self, any oneOf schemas, any anyOf schemas, any x-discriminator-values, and the discriminator mapping schemas in the OAS document AND Codegen validates that oneOf and anyOf schemas contain the required discriminator and throws an error if the discriminator is missing.</dd></dl>|true|
|
||||
|library|library template (sub-template) to use|<dl><dt>**jersey1**</dt><dd>HTTP client: Jersey client 1.19.x. JSON processing: Jackson 2.9.x. Enable gzip request encoding using '-DuseGzipFeature=true'. IMPORTANT NOTE: jersey 1.x is no longer actively maintained so please upgrade to 'jersey2' or other HTTP libraries instead.</dd><dt>**jersey2**</dt><dd>HTTP client: Jersey client 2.25.1. JSON processing: Jackson 2.9.x</dd><dt>**feign**</dt><dd>HTTP client: OpenFeign 10.x. JSON processing: Jackson 2.9.x.</dd><dt>**okhttp-gson**</dt><dd>[DEFAULT] HTTP client: OkHttp 3.x. JSON processing: Gson 2.8.x. Enable Parcelable models on Android using '-DparcelableModel=true'. Enable gzip request encoding using '-DuseGzipFeature=true'.</dd><dt>**retrofit2**</dt><dd>HTTP client: OkHttp 3.x. JSON processing: Gson 2.x (Retrofit 2.3.0). Enable the RxJava adapter using '-DuseRxJava[2/3]=true'. (RxJava 1.x or 2.x or 3.x)</dd><dt>**resttemplate**</dt><dd>HTTP client: Spring RestTemplate 4.x. JSON processing: Jackson 2.9.x</dd><dt>**webclient**</dt><dd>HTTP client: Spring WebClient 5.x. JSON processing: Jackson 2.9.x</dd><dt>**resteasy**</dt><dd>HTTP client: Resteasy client 3.x. JSON processing: Jackson 2.9.x</dd><dt>**vertx**</dt><dd>HTTP client: VertX client 3.x. JSON processing: Jackson 2.9.x</dd><dt>**google-api-client**</dt><dd>HTTP client: Google API client 1.x. JSON processing: Jackson 2.9.x</dd><dt>**rest-assured**</dt><dd>HTTP client: rest-assured : 4.x. JSON processing: Gson 2.x or Jackson 2.10.x. Only for Java 8</dd><dt>**native**</dt><dd>HTTP client: Java native HttpClient. JSON processing: Jackson 2.9.x. Only for Java11+</dd><dt>**microprofile**</dt><dd>HTTP client: Microprofile client 1.x. JSON processing: JSON-B</dd><dt>**apache-httpclient**</dt><dd>HTTP client: Apache httpclient 4.x</dd></dl>|okhttp-gson|
|
||||
|library|library template (sub-template) to use|<dl><dt>**jersey1**</dt><dd>HTTP client: Jersey client 1.19.x. JSON processing: Jackson 2.9.x. Enable gzip request encoding using '-DuseGzipFeature=true'. IMPORTANT NOTE: jersey 1.x is no longer actively maintained so please upgrade to 'jersey2' or other HTTP libraries instead.</dd><dt>**jersey2**</dt><dd>HTTP client: Jersey client 2.25.1. JSON processing: Jackson 2.9.x</dd><dt>**feign**</dt><dd>HTTP client: OpenFeign 10.x. JSON processing: Jackson 2.9.x.</dd><dt>**okhttp-gson**</dt><dd>[DEFAULT] HTTP client: OkHttp 3.x. JSON processing: Gson 2.8.x. Enable Parcelable models on Android using '-DparcelableModel=true'. Enable gzip request encoding using '-DuseGzipFeature=true'.</dd><dt>**okhttp-gson-nextgen**</dt><dd>HTTP client: OkHttp 3.x. JSON processing: Gson 2.8.x.'. Better support for oneOf/anyOf with breaking changes. Will replace `okhttp-gson` in the 6.0.0 release.</dd><dt>**retrofit2**</dt><dd>HTTP client: OkHttp 3.x. JSON processing: Gson 2.x (Retrofit 2.3.0). Enable the RxJava adapter using '-DuseRxJava[2/3]=true'. (RxJava 1.x or 2.x or 3.x)</dd><dt>**resttemplate**</dt><dd>HTTP client: Spring RestTemplate 4.x. JSON processing: Jackson 2.9.x</dd><dt>**webclient**</dt><dd>HTTP client: Spring WebClient 5.x. JSON processing: Jackson 2.9.x</dd><dt>**resteasy**</dt><dd>HTTP client: Resteasy client 3.x. JSON processing: Jackson 2.9.x</dd><dt>**vertx**</dt><dd>HTTP client: VertX client 3.x. JSON processing: Jackson 2.9.x</dd><dt>**google-api-client**</dt><dd>HTTP client: Google API client 1.x. JSON processing: Jackson 2.9.x</dd><dt>**rest-assured**</dt><dd>HTTP client: rest-assured : 4.x. JSON processing: Gson 2.x or Jackson 2.10.x. Only for Java 8</dd><dt>**native**</dt><dd>HTTP client: Java native HttpClient. JSON processing: Jackson 2.9.x. Only for Java11+</dd><dt>**microprofile**</dt><dd>HTTP client: Microprofile client 1.x. JSON processing: JSON-B</dd><dt>**apache-httpclient**</dt><dd>HTTP client: Apache httpclient 4.x</dd></dl>|okhttp-gson|
|
||||
|licenseName|The name of the license| |Unlicense|
|
||||
|licenseUrl|The URL of the license| |http://unlicense.org|
|
||||
|microprofileFramework|Framework for microprofile. Possible values "kumuluzee"| |null|
|
||||
|
@ -17,6 +17,7 @@ These options may be applied as additional-properties (cli) or configOptions (pl
|
||||
|library|Library template (sub-template) to use|<dl><dt>**jvm-okhttp4**</dt><dd>[DEFAULT] Platform: Java Virtual Machine. HTTP client: OkHttp 4.2.0 (Android 5.0+ and Java 8+). JSON processing: Moshi 1.8.0.</dd><dt>**jvm-okhttp3**</dt><dd>Platform: Java Virtual Machine. HTTP client: OkHttp 3.12.4 (Android 2.3+ and Java 7+). JSON processing: Moshi 1.8.0.</dd><dt>**jvm-retrofit2**</dt><dd>Platform: Java Virtual Machine. HTTP client: Retrofit 2.6.2.</dd><dt>**multiplatform**</dt><dd>Platform: Kotlin multiplatform. HTTP client: Ktor 1.6.0. JSON processing: Kotlinx Serialization: 1.2.1.</dd></dl>|jvm-okhttp4|
|
||||
|modelMutable|Create mutable models| |false|
|
||||
|moshiCodeGen|Whether to enable codegen with the Moshi library. Refer to the [official Moshi doc](https://github.com/square/moshi#codegen) for more info.| |false|
|
||||
|omitGradlePluginVersions|Whether to declare Gradle plugin versions in build files.| |false|
|
||||
|packageName|Generated artifact package name.| |org.openapitools.client|
|
||||
|parcelizeModels|toggle "@Parcelize" for generated models| |null|
|
||||
|requestDateConverter|JVM-Option. Defines in how to handle date-time objects that are used for a request (as query or parameter)|<dl><dt>**toJson**</dt><dd>[DEFAULT] Date formatter option using a json converter.</dd><dt>**toString**</dt><dd>Use the 'toString'-method of the date-time object to retrieve the related string representation.</dd></dl>|toJson|
|
||||
|
@ -7,6 +7,8 @@ These options may be applied as additional-properties (cli) or configOptions (pl
|
||||
|
||||
| Option | Description | Values | Default |
|
||||
| ------ | ----------- | ------ | ------- |
|
||||
|numberedFieldNumberList|Field numbers in order.| |false|
|
||||
|startEnumsWithUnknown|Introduces "UNKNOWN" as the first element of enumerations.| |false|
|
||||
|
||||
## IMPORT MAPPING
|
||||
|
||||
|
@ -10,13 +10,13 @@ These options may be applied as additional-properties (cli) or configOptions (pl
|
||||
|allowUnicodeIdentifiers|boolean, toggles whether unicode identifiers are allowed in names or not, default is false| |false|
|
||||
|disallowAdditionalPropertiesIfNotPresent|If false, the 'additionalProperties' implementation (set to true by default) is compliant with the OAS and JSON schema specifications. If true (default), keep the old (incorrect) behaviour that 'additionalProperties' is set to false by default.|<dl><dt>**false**</dt><dd>The 'additionalProperties' implementation is compliant with the OAS and JSON schema specifications.</dd><dt>**true**</dt><dd>Keep the old (incorrect) behaviour that 'additionalProperties' is set to false by default.</dd></dl>|true|
|
||||
|ensureUniqueParams|Whether to ensure parameter names are unique in an operation (rename parameters that are not).| |true|
|
||||
|gemAuthor|gem author (only one is supported).| |null|
|
||||
|gemAuthor|gem author (only one is supported).| |OpenAPI-Generator|
|
||||
|gemAuthorEmail|gem author email (only one is supported).| |null|
|
||||
|gemDescription|gem description. | |This gem maps to a REST API|
|
||||
|gemHomepage|gem homepage. | |http://org.openapitools|
|
||||
|gemHomepage|gem homepage. | |https://openapi-generator.tech|
|
||||
|gemLicense|gem license. | |unlicense|
|
||||
|gemName|gem name (convention: underscore_case).| |openapi_client|
|
||||
|gemRequiredRubyVersion|gem required Ruby version. | |>= 1.9|
|
||||
|gemRequiredRubyVersion|gem required Ruby version. | |>= 2.4|
|
||||
|gemSummary|gem summary. | |A ruby wrapper for the REST APIs|
|
||||
|gemVersion|gem version.| |1.0.0|
|
||||
|hideGenerationTimestamp|Hides the generation timestamp when files are generated.| |true|
|
||||
|
@ -11,6 +11,7 @@ These options may be applied as additional-properties (cli) or configOptions (pl
|
||||
|apiNamePrefix|Prefix that will be appended to all API names ('tags'). Default: empty string. e.g. Pet => Pet.| |null|
|
||||
|disallowAdditionalPropertiesIfNotPresent|If false, the 'additionalProperties' implementation (set to true by default) is compliant with the OAS and JSON schema specifications. If true (default), keep the old (incorrect) behaviour that 'additionalProperties' is set to false by default.|<dl><dt>**false**</dt><dd>The 'additionalProperties' implementation is compliant with the OAS and JSON schema specifications.</dd><dt>**true**</dt><dd>Keep the old (incorrect) behaviour that 'additionalProperties' is set to false by default.</dd></dl>|true|
|
||||
|ensureUniqueParams|Whether to ensure parameter names are unique in an operation (rename parameters that are not).| |true|
|
||||
|generateFrozenEnums|Generate frozen enums (default: true)| |true|
|
||||
|generateModelAdditionalProperties|Generate model additional properties (default: true)| |true|
|
||||
|hashableModels|Make hashable models (default: true)| |true|
|
||||
|hideGenerationTimestamp|Hides the generation timestamp when files are generated.| |true|
|
||||
|
@ -19,7 +19,7 @@ These options may be applied as additional-properties (cli) or configOptions (pl
|
||||
|modelFileSuffix|The suffix of the file of the generated model (model<suffix>.ts).| |null|
|
||||
|modelPropertyNaming|Naming convention for the property: 'camelCase', 'PascalCase', 'snake_case' and 'original', which keeps the original name. Only change it if you provide your own run-time code for (de-)serialization of models| |original|
|
||||
|modelSuffix|The suffix of the generated model.| |null|
|
||||
|ngVersion|The version of Angular. (At least 6.0.0)| |12.2.12|
|
||||
|ngVersion|The version of Angular. (At least 6.0.0)| |13.0.1|
|
||||
|npmName|The name under which you want to publish generated npm package. Required to generate a full package| |null|
|
||||
|npmRepository|Use this property to set an url your private npmRepo in the package.json| |null|
|
||||
|npmVersion|The version of your npm package. If not provided, using the version from the OpenAPI specification file.| |1.0.0|
|
||||
|
@ -0,0 +1,67 @@
|
||||
package org.openapitools.codegen;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
||||
public class CodegenEncoding {
|
||||
private String contentType;
|
||||
private List<CodegenParameter> headers;
|
||||
private String style;
|
||||
private boolean explode;
|
||||
private boolean allowReserved;
|
||||
|
||||
public CodegenEncoding(String contentType, List<CodegenParameter> headers, String style, boolean explode, boolean allowReserved) {
|
||||
this.contentType = contentType;
|
||||
this.headers = headers;
|
||||
this.style = style;
|
||||
this.explode = explode;
|
||||
this.allowReserved = allowReserved;
|
||||
}
|
||||
|
||||
public String getContentType() {
|
||||
return contentType;
|
||||
}
|
||||
|
||||
public List<CodegenParameter> getHeaders() {
|
||||
return headers;
|
||||
}
|
||||
|
||||
public String getStyle() {
|
||||
return style;
|
||||
}
|
||||
|
||||
public boolean getExplode() {
|
||||
return explode;
|
||||
}
|
||||
|
||||
public boolean getAllowReserved() {
|
||||
return allowReserved;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
final StringBuilder sb = new StringBuilder("CodegenEncoding{");
|
||||
sb.append("contentType=").append(contentType);
|
||||
sb.append(", headers=").append(headers);
|
||||
sb.append(", style=").append(style);
|
||||
sb.append(", explode=").append(explode);
|
||||
sb.append(", allowReserved=").append(allowReserved);
|
||||
sb.append('}');
|
||||
return sb.toString();
|
||||
}
|
||||
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (o == null || getClass() != o.getClass()) return false;
|
||||
CodegenEncoding that = (CodegenEncoding) o;
|
||||
return contentType == that.getContentType() &&
|
||||
Objects.equals(headers, that.getHeaders()) &&
|
||||
style == that.getStyle() &&
|
||||
explode == that.getExplode() &&
|
||||
allowReserved == that.getAllowReserved();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(contentType, headers, style, explode, allowReserved);
|
||||
}
|
||||
}
|
@ -0,0 +1,45 @@
|
||||
package org.openapitools.codegen;
|
||||
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.Objects;
|
||||
|
||||
public class CodegenMediaType {
|
||||
private CodegenProperty schema;
|
||||
private LinkedHashMap<String, CodegenEncoding> encoding;
|
||||
|
||||
public CodegenMediaType(CodegenProperty schema, LinkedHashMap<String, CodegenEncoding> encoding) {
|
||||
this.schema = schema;
|
||||
this.encoding = encoding;
|
||||
}
|
||||
|
||||
public CodegenProperty getSchema() {
|
||||
return schema;
|
||||
}
|
||||
|
||||
public LinkedHashMap<String, CodegenEncoding> getEncoding() {
|
||||
return encoding;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
final StringBuilder sb = new StringBuilder("CodegenMediaType{");
|
||||
sb.append("schema=").append(schema);
|
||||
sb.append(", encoding=").append(encoding);
|
||||
sb.append('}');
|
||||
return sb.toString();
|
||||
}
|
||||
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (o == null || getClass() != o.getClass()) return false;
|
||||
CodegenMediaType that = (CodegenMediaType) o;
|
||||
return Objects.equals(schema,that.getSchema()) &&
|
||||
Objects.equals(encoding, that.getEncoding());
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(schema, encoding);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -29,7 +29,8 @@ public class CodegenOperation {
|
||||
isArray, isMultipart,
|
||||
isResponseBinary = false, isResponseFile = false, hasReference = false,
|
||||
isRestfulIndex, isRestfulShow, isRestfulCreate, isRestfulUpdate, isRestfulDestroy,
|
||||
isRestful, isDeprecated, isCallbackRequest, uniqueItems, hasDefaultResponse = false;
|
||||
isRestful, isDeprecated, isCallbackRequest, uniqueItems, hasDefaultResponse = false,
|
||||
hasErrorResponseObject; // if 4xx, 5xx repsonses have at least one error object defined
|
||||
public String path, operationId, returnType, returnFormat, httpMethod, returnBaseType,
|
||||
returnContainer, summary, unescapedNotes, notes, baseName, defaultResponse;
|
||||
public CodegenDiscriminator discriminator;
|
||||
@ -297,6 +298,7 @@ public class CodegenOperation {
|
||||
sb.append(", isResponseFile=").append(isResponseFile);
|
||||
sb.append(", hasReference=").append(hasReference);
|
||||
sb.append(", hasDefaultResponse=").append(hasDefaultResponse);
|
||||
sb.append(", hasErrorResponseObject=").append(hasErrorResponseObject);
|
||||
sb.append(", isRestfulIndex=").append(isRestfulIndex);
|
||||
sb.append(", isRestfulShow=").append(isRestfulShow);
|
||||
sb.append(", isRestfulCreate=").append(isRestfulCreate);
|
||||
@ -371,6 +373,7 @@ public class CodegenOperation {
|
||||
isResponseFile == that.isResponseFile &&
|
||||
hasReference == that.hasReference &&
|
||||
hasDefaultResponse == that.hasDefaultResponse &&
|
||||
hasErrorResponseObject == that.hasErrorResponseObject &&
|
||||
isRestfulIndex == that.isRestfulIndex &&
|
||||
isRestfulShow == that.isRestfulShow &&
|
||||
isRestfulCreate == that.isRestfulCreate &&
|
||||
@ -435,6 +438,7 @@ public class CodegenOperation {
|
||||
produces, prioritizedContentTypes, servers, bodyParam, allParams, bodyParams, pathParams, queryParams,
|
||||
headerParams, formParams, cookieParams, requiredParams, optionalParams, authMethods, tags,
|
||||
responses, callbacks, imports, examples, requestBodyExamples, externalDocs, vendorExtensions,
|
||||
nickname, operationIdOriginal, operationIdLowerCase, operationIdCamelCase, operationIdSnakeCase);
|
||||
nickname, operationIdOriginal, operationIdLowerCase, operationIdCamelCase, operationIdSnakeCase,
|
||||
hasErrorResponseObject);
|
||||
}
|
||||
}
|
||||
|
@ -52,6 +52,7 @@ public class CodegenParameter implements IJsonSchemaValidationProperties {
|
||||
public boolean hasValidation;
|
||||
public boolean isNullable;
|
||||
public boolean isDeprecated;
|
||||
private CodegenProperty schema;
|
||||
/**
|
||||
* Determines whether this parameter is mandatory. If the parameter is in "path",
|
||||
* this property is required and its value MUST be true. Otherwise, the property
|
||||
@ -109,6 +110,7 @@ public class CodegenParameter implements IJsonSchemaValidationProperties {
|
||||
private boolean hasDiscriminatorWithNonEmptyMapping;
|
||||
private CodegenComposedSchemas composedSchemas;
|
||||
private boolean hasMultipleTypes = false;
|
||||
private LinkedHashMap<String, CodegenMediaType> content;
|
||||
|
||||
public CodegenParameter copy() {
|
||||
CodegenParameter output = new CodegenParameter();
|
||||
@ -162,6 +164,12 @@ public class CodegenParameter implements IJsonSchemaValidationProperties {
|
||||
output.setHasDiscriminatorWithNonEmptyMapping(this.hasDiscriminatorWithNonEmptyMapping);
|
||||
output.setHasMultipleTypes(this.hasMultipleTypes);
|
||||
|
||||
if (this.content != null) {
|
||||
output.setContent(this.content);
|
||||
}
|
||||
if (this.schema != null) {
|
||||
output.setSchema(this.schema);
|
||||
}
|
||||
if (this.composedSchemas != null) {
|
||||
output.setComposedSchemas(this.getComposedSchemas());
|
||||
}
|
||||
@ -222,7 +230,7 @@ public class CodegenParameter implements IJsonSchemaValidationProperties {
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(isFormParam, isQueryParam, isPathParam, isHeaderParam, isCookieParam, isBodyParam, isContainer, isCollectionFormatMulti, isPrimitiveType, isModel, isExplode, baseName, paramName, dataType, datatypeWithEnum, dataFormat, collectionFormat, description, unescapedDescription, baseType, defaultValue, enumName, style, isDeepObject, isAllowEmptyValue, example, jsonSchema, isString, isNumeric, isInteger, isLong, isNumber, isFloat, isDouble, isDecimal, isByteArray, isBinary, isBoolean, isDate, isDateTime, isUuid, isUri, isEmail, isFreeFormObject, isAnyType, isArray, isMap, isFile, isEnum, _enum, allowableValues, items, mostInnerItems, additionalProperties, vars, requiredVars, vendorExtensions, hasValidation, getMaxProperties(), getMinProperties(), isNullable, isDeprecated, required, getMaximum(), getExclusiveMaximum(), getMinimum(), getExclusiveMinimum(), getMaxLength(), getMinLength(), getPattern(), getMaxItems(), getMinItems(), getUniqueItems(), contentType, multipleOf, isNull, additionalPropertiesIsAnyType, hasVars, hasRequired, isShort, isUnboundedInteger, hasDiscriminatorWithNonEmptyMapping, composedSchemas, hasMultipleTypes);
|
||||
return Objects.hash(isFormParam, isQueryParam, isPathParam, isHeaderParam, isCookieParam, isBodyParam, isContainer, isCollectionFormatMulti, isPrimitiveType, isModel, isExplode, baseName, paramName, dataType, datatypeWithEnum, dataFormat, collectionFormat, description, unescapedDescription, baseType, defaultValue, enumName, style, isDeepObject, isAllowEmptyValue, example, jsonSchema, isString, isNumeric, isInteger, isLong, isNumber, isFloat, isDouble, isDecimal, isByteArray, isBinary, isBoolean, isDate, isDateTime, isUuid, isUri, isEmail, isFreeFormObject, isAnyType, isArray, isMap, isFile, isEnum, _enum, allowableValues, items, mostInnerItems, additionalProperties, vars, requiredVars, vendorExtensions, hasValidation, getMaxProperties(), getMinProperties(), isNullable, isDeprecated, required, getMaximum(), getExclusiveMaximum(), getMinimum(), getExclusiveMinimum(), getMaxLength(), getMinLength(), getPattern(), getMaxItems(), getMinItems(), getUniqueItems(), contentType, multipleOf, isNull, additionalPropertiesIsAnyType, hasVars, hasRequired, isShort, isUnboundedInteger, hasDiscriminatorWithNonEmptyMapping, composedSchemas, hasMultipleTypes, schema, content);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -278,6 +286,8 @@ public class CodegenParameter implements IJsonSchemaValidationProperties {
|
||||
getExclusiveMaximum() == that.getExclusiveMaximum() &&
|
||||
getExclusiveMinimum() == that.getExclusiveMinimum() &&
|
||||
getUniqueItems() == that.getUniqueItems() &&
|
||||
Objects.equals(content, that.getContent()) &&
|
||||
Objects.equals(schema, that.getSchema()) &&
|
||||
Objects.equals(composedSchemas, that.getComposedSchemas()) &&
|
||||
Objects.equals(baseName, that.baseName) &&
|
||||
Objects.equals(paramName, that.paramName) &&
|
||||
@ -403,6 +413,8 @@ public class CodegenParameter implements IJsonSchemaValidationProperties {
|
||||
sb.append(", getHasDiscriminatorWithNonEmptyMapping=").append(hasDiscriminatorWithNonEmptyMapping);
|
||||
sb.append(", composedSchemas=").append(composedSchemas);
|
||||
sb.append(", hasMultipleTypes=").append(hasMultipleTypes);
|
||||
sb.append(", schema=").append(schema);
|
||||
sb.append(", content=").append(content);
|
||||
sb.append('}');
|
||||
return sb.toString();
|
||||
}
|
||||
@ -732,5 +744,17 @@ public class CodegenParameter implements IJsonSchemaValidationProperties {
|
||||
|
||||
@Override
|
||||
public void setHasMultipleTypes(boolean hasMultipleTypes) { this.hasMultipleTypes = hasMultipleTypes; }
|
||||
|
||||
public CodegenProperty getSchema() {return schema; }
|
||||
|
||||
public void setSchema(CodegenProperty schema) { this.schema = schema; }
|
||||
|
||||
public LinkedHashMap<String, CodegenMediaType> getContent() {
|
||||
return content;
|
||||
}
|
||||
|
||||
public void setContent(LinkedHashMap<String, CodegenMediaType> content) {
|
||||
this.content = content;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -570,14 +570,7 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
List<Map<String, Object>> models = (List<Map<String, Object>>) inner.get("models");
|
||||
for (Map<String, Object> mo : models) {
|
||||
CodegenModel cm = (CodegenModel) mo.get("model");
|
||||
for (CodegenProperty cp : cm.allVars) {
|
||||
// detect self import
|
||||
if (cp.dataType.equalsIgnoreCase(cm.classname) ||
|
||||
(cp.isContainer && cp.items != null && cp.items.dataType.equalsIgnoreCase(cm.classname))) {
|
||||
cm.imports.remove(cm.classname); // remove self import
|
||||
cp.isSelfReference = true;
|
||||
}
|
||||
}
|
||||
removeSelfReferenceImports(cm);
|
||||
}
|
||||
}
|
||||
setCircularReferences(allModels);
|
||||
@ -585,6 +578,23 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
return objs;
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes imports from the model that points to itself
|
||||
* Marks a self referencing property, if detected
|
||||
*
|
||||
* @param model Self imports will be removed from this model.imports collection
|
||||
*/
|
||||
protected void removeSelfReferenceImports(CodegenModel model) {
|
||||
for (CodegenProperty cp : model.allVars) {
|
||||
// detect self import
|
||||
if (cp.dataType.equalsIgnoreCase(model.classname) ||
|
||||
(cp.isContainer && cp.items != null && cp.items.dataType.equalsIgnoreCase(model.classname))) {
|
||||
model.imports.remove(model.classname); // remove self import
|
||||
cp.isSelfReference = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setCircularReferences(Map<String, CodegenModel> models) {
|
||||
final Map<String, List<CodegenProperty>> dependencyMap = models.entrySet().stream()
|
||||
.collect(Collectors.toMap(Entry::getKey, entry -> getModelDependencies(entry.getValue())));
|
||||
@ -3966,6 +3976,12 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
if (Boolean.TRUE.equals(r.isFile) && Boolean.TRUE.equals(r.is2xx) && Boolean.FALSE.equals(op.isResponseFile)) {
|
||||
op.isResponseFile = Boolean.TRUE;
|
||||
}
|
||||
|
||||
// check if any 4xx or 5xx reponse has an error response object defined
|
||||
if ((Boolean.TRUE.equals(r.is4xx) || Boolean.TRUE.equals(r.is5xx)) &&
|
||||
Boolean.FALSE.equals(r.primitiveType) && Boolean.FALSE.equals(r.simpleType)) {
|
||||
op.hasErrorResponseObject = Boolean.TRUE;
|
||||
}
|
||||
}
|
||||
op.responses.sort((a, b) -> {
|
||||
int aScore = a.isWildcard() ? 2 : a.isRange() ? 1 : 0;
|
||||
@ -4259,6 +4275,7 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
r.setComposedSchemas(getComposedSchemas(responseSchema));
|
||||
if (ModelUtils.isArraySchema(responseSchema)) {
|
||||
r.simpleType = false;
|
||||
r.isArray = true;
|
||||
r.containerType = cp.containerType;
|
||||
ArraySchema as = (ArraySchema) responseSchema;
|
||||
CodegenProperty items = fromProperty("response", getSchemaItems(as));
|
||||
@ -4314,6 +4331,8 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
} else if (ModelUtils.isTypeObjectSchema(responseSchema)) {
|
||||
if (ModelUtils.isFreeFormObject(openAPI, responseSchema)) {
|
||||
r.isFreeFormObject = true;
|
||||
} else {
|
||||
r.isModel = true;
|
||||
}
|
||||
r.simpleType = false;
|
||||
r.containerType = cp.containerType;
|
||||
@ -4325,9 +4344,6 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
LOGGER.debug("Property type is not primitive: {}", cp.dataType);
|
||||
}
|
||||
|
||||
if (!r.isMap && !r.isArray) {
|
||||
r.simpleType = true;
|
||||
}
|
||||
r.primitiveType = (r.baseType == null || languageSpecificPrimitives().contains(r.baseType));
|
||||
|
||||
if (r.baseType == null) {
|
||||
@ -4486,6 +4502,7 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
codegenParameter.isDeprecated = parameter.getDeprecated();
|
||||
}
|
||||
codegenParameter.jsonSchema = Json.pretty(parameter);
|
||||
codegenParameter.setContent(getContent(parameter.getContent(), imports));
|
||||
|
||||
if (GlobalSettings.getProperty("debugParser") != null) {
|
||||
LOGGER.info("working on Parameter {}", parameter.getName());
|
||||
@ -4499,6 +4516,8 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
Schema parameterSchema;
|
||||
if (parameter.getSchema() != null) {
|
||||
parameterSchema = parameter.getSchema();
|
||||
CodegenProperty prop = fromProperty(parameter.getName(), parameterSchema);
|
||||
codegenParameter.setSchema(prop);
|
||||
} else if (parameter.getContent() != null) {
|
||||
Content content = parameter.getContent();
|
||||
if (content.size() > 1) {
|
||||
@ -4771,12 +4790,12 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
final CodegenSecurity cs = defaultCodegenSecurity(key, securityScheme);
|
||||
cs.isKeyInHeader = cs.isKeyInQuery = cs.isKeyInCookie = cs.isApiKey = cs.isOAuth = false;
|
||||
cs.isBasic = true;
|
||||
if ("basic".equals(securityScheme.getScheme())) {
|
||||
if ("basic".equalsIgnoreCase(securityScheme.getScheme())) {
|
||||
cs.isBasicBasic = true;
|
||||
} else if ("bearer".equals(securityScheme.getScheme())) {
|
||||
} else if ("bearer".equalsIgnoreCase(securityScheme.getScheme())) {
|
||||
cs.isBasicBearer = true;
|
||||
cs.bearerFormat = securityScheme.getBearerFormat();
|
||||
} else if ("signature".equals(securityScheme.getScheme())) {
|
||||
} else if ("signature".equalsIgnoreCase(securityScheme.getScheme())) {
|
||||
// HTTP signature as defined in https://datatracker.ietf.org/doc/draft-cavage-http-signatures/
|
||||
// The registry of security schemes is maintained by IANA.
|
||||
// https://www.iana.org/assignments/http-authschemes/http-authschemes.xhtml
|
||||
@ -5165,17 +5184,7 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
cm.hasOnlyReadOnly = false;
|
||||
}
|
||||
|
||||
// TODO revise the logic to include map
|
||||
if (cp.isContainer) {
|
||||
addImport(cm, typeMapping.get("array"));
|
||||
}
|
||||
|
||||
addImport(cm, cp.baseType);
|
||||
CodegenProperty innerCp = cp;
|
||||
while (innerCp != null) {
|
||||
addImport(cm, innerCp.complexType);
|
||||
innerCp = innerCp.items;
|
||||
}
|
||||
addImportsForPropertyType(cm, cp);
|
||||
|
||||
// if required, add to the list "requiredVars"
|
||||
if (Boolean.TRUE.equals(cp.required)) {
|
||||
@ -5196,6 +5205,28 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
* For a given property, adds all needed imports to the model
|
||||
* This includes a flat property type (e.g. property type: ReferencedModel)
|
||||
* as well as container type (property type: array of ReferencedModel's)
|
||||
*
|
||||
* @param model The codegen representation of the OAS schema.
|
||||
* @param property The codegen representation of the OAS schema's property.
|
||||
*/
|
||||
protected void addImportsForPropertyType(CodegenModel model, CodegenProperty property) {
|
||||
// TODO revise the logic to include map
|
||||
if (property.isContainer) {
|
||||
addImport(model, typeMapping.get("array"));
|
||||
}
|
||||
|
||||
addImport(model, property.baseType);
|
||||
CodegenProperty innerCp = property;
|
||||
while (innerCp != null) {
|
||||
addImport(model, innerCp.complexType);
|
||||
innerCp = innerCp.items;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine all of the types in the model definitions (schemas) that are aliases of
|
||||
* simple types.
|
||||
@ -6555,6 +6586,65 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
codegenParameter.pattern = toRegularExpression(schema.getPattern());
|
||||
}
|
||||
|
||||
protected String toMediaTypeSchemaName(String contentType) {
|
||||
return toModelName(contentType + "Schema");
|
||||
}
|
||||
|
||||
protected LinkedHashMap<String, CodegenMediaType> getContent(Content content, Set<String> imports) {
|
||||
if (content == null) {
|
||||
return null;
|
||||
}
|
||||
LinkedHashMap<String, CodegenMediaType> cmtContent = new LinkedHashMap<>();
|
||||
for (Entry<String, MediaType> contentEntry: content.entrySet()) {
|
||||
MediaType mt = contentEntry.getValue();
|
||||
LinkedHashMap<String, CodegenEncoding> ceMap = null;
|
||||
if (mt.getEncoding() != null ) {
|
||||
ceMap = new LinkedHashMap<>();
|
||||
Map<String, Encoding> encMap = mt.getEncoding();
|
||||
for (Entry<String, Encoding> encodingEntry: encMap.entrySet()) {
|
||||
Encoding enc = encodingEntry.getValue();
|
||||
List<CodegenParameter> headers = new ArrayList<>();
|
||||
if (enc.getHeaders() != null) {
|
||||
Map<String, Header> encHeaders = enc.getHeaders();
|
||||
for (Entry<String, Header> headerEntry: encHeaders.entrySet()) {
|
||||
String headerName = headerEntry.getKey();
|
||||
Header header = ModelUtils.getReferencedHeader(this.openAPI, headerEntry.getValue());
|
||||
Parameter headerParam = new Parameter();
|
||||
headerParam.setName(headerName);
|
||||
headerParam.setIn("header");
|
||||
headerParam.setDescription(header.getDescription());
|
||||
headerParam.setRequired(header.getRequired());
|
||||
headerParam.setDeprecated(header.getDeprecated());
|
||||
headerParam.setStyle(Parameter.StyleEnum.valueOf(header.getStyle().name()));
|
||||
headerParam.setExplode(header.getExplode());
|
||||
headerParam.setSchema(header.getSchema());
|
||||
headerParam.setExamples(header.getExamples());
|
||||
headerParam.setExample(header.getExample());
|
||||
headerParam.setContent(header.getContent());
|
||||
headerParam.setExtensions(header.getExtensions());
|
||||
CodegenParameter param = fromParameter(headerParam, imports);
|
||||
headers.add(param);
|
||||
}
|
||||
}
|
||||
CodegenEncoding ce = new CodegenEncoding(
|
||||
enc.getContentType(),
|
||||
headers,
|
||||
enc.getStyle().toString(),
|
||||
enc.getExplode().booleanValue(),
|
||||
enc.getAllowReserved().booleanValue()
|
||||
);
|
||||
String propName = encodingEntry.getKey();
|
||||
ceMap.put(propName, ce);
|
||||
}
|
||||
}
|
||||
String contentType = contentEntry.getKey();
|
||||
CodegenProperty schemaProp = fromProperty(toMediaTypeSchemaName(contentType), mt.getSchema());
|
||||
CodegenMediaType codegenMt = new CodegenMediaType(schemaProp, ceMap);
|
||||
cmtContent.put(contentType, codegenMt);
|
||||
}
|
||||
return cmtContent;
|
||||
}
|
||||
|
||||
public CodegenParameter fromRequestBody(RequestBody body, Set<String> imports, String bodyParameterName) {
|
||||
if (body == null) {
|
||||
LOGGER.error("body in fromRequestBody cannot be null!");
|
||||
@ -6576,6 +6666,7 @@ public class DefaultCodegen implements CodegenConfig {
|
||||
if (schema == null) {
|
||||
throw new RuntimeException("Request body cannot be null. Possible cause: missing schema in body parameter (OAS v2): " + body);
|
||||
}
|
||||
codegenParameter.setContent(getContent(body.getContent(), imports));
|
||||
|
||||
if (StringUtils.isNotBlank(schema.get$ref())) {
|
||||
name = ModelUtils.getSimpleRef(schema.get$ref());
|
||||
|
@ -505,7 +505,7 @@ public abstract class AbstractDartCodegen extends DefaultCodegen {
|
||||
super.postProcessModelProperty(model, property);
|
||||
if (!model.isEnum && property.isEnum) {
|
||||
// These are inner enums, enums which do not exist as models, just as properties.
|
||||
// They are handled via the enum_inline template and and are generated in the
|
||||
// They are handled via the enum_inline template and are generated in the
|
||||
// same file as the containing class. To prevent name clashes the inline enum classes
|
||||
// are prefix with the classname of the containing class in the template.
|
||||
// Here the datatypeWithEnum template variable gets updated to match that scheme.
|
||||
@ -529,9 +529,9 @@ public abstract class AbstractDartCodegen extends DefaultCodegen {
|
||||
public CodegenOperation fromOperation(String path, String httpMethod, Operation operation, List<Server> servers) {
|
||||
final CodegenOperation op = super.fromOperation(path, httpMethod, operation, servers);
|
||||
for (CodegenResponse r : op.responses) {
|
||||
// By default only set types are automatically added to operation imports, not sure why.
|
||||
// By default, only set types are automatically added to operation imports, not sure why.
|
||||
// Add all container type imports here, by default 'dart:core' imports are skipped
|
||||
// but other sub classes may required specific container type imports.
|
||||
// but other sub-classes may require specific container type imports.
|
||||
if (r.containerType != null && typeMapping().containsKey(r.containerType)) {
|
||||
final String value = typeMapping().get(r.containerType);
|
||||
if (needToImport(value)) {
|
||||
|
@ -323,6 +323,7 @@ public class CLibcurlClientCodegen extends DefaultCodegen implements CodegenConf
|
||||
|
||||
// root folder
|
||||
supportingFiles.add(new SupportingFile("CMakeLists.txt.mustache", "", "CMakeLists.txt"));
|
||||
supportingFiles.add(new SupportingFile("Packing.cmake.mustache", "", "Packing.cmake"));
|
||||
supportingFiles.add(new SupportingFile("libcurl.licence.mustache", "", "libcurl.licence"));
|
||||
supportingFiles.add(new SupportingFile("uncrustify-rules.cfg.mustache", "", "uncrustify-rules.cfg"));
|
||||
supportingFiles.add(new SupportingFile("README.md.mustache", "", "README.md"));
|
||||
|
@ -70,7 +70,8 @@ public class CSharpNetCoreClientCodegen extends AbstractCSharpCodegen {
|
||||
FrameworkStrategy.NETCOREAPP_3_0,
|
||||
FrameworkStrategy.NETCOREAPP_3_1,
|
||||
FrameworkStrategy.NETFRAMEWORK_4_7,
|
||||
FrameworkStrategy.NET_5_0
|
||||
FrameworkStrategy.NET_5_0,
|
||||
FrameworkStrategy.NET_6_0
|
||||
);
|
||||
private static FrameworkStrategy defaultFramework = FrameworkStrategy.NETSTANDARD_2_0;
|
||||
protected final Map<String, String> frameworks;
|
||||
@ -1001,6 +1002,8 @@ public class CSharpNetCoreClientCodegen extends AbstractCSharpCodegen {
|
||||
};
|
||||
static FrameworkStrategy NET_5_0 = new FrameworkStrategy("net5.0", ".NET 5.0 compatible", "net5.0", Boolean.FALSE) {
|
||||
};
|
||||
static FrameworkStrategy NET_6_0 = new FrameworkStrategy("net6.0", ".NET 6.0 compatible", "net6.0", Boolean.FALSE) {
|
||||
};
|
||||
protected String name;
|
||||
protected String description;
|
||||
protected String testTargetFramework;
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -132,7 +132,7 @@ public class CrystalClientCodegen extends DefaultCodegen {
|
||||
// reserved word. Ref: https://github.com/crystal-lang/crystal/wiki/Crystal-for-Rubyists#available-keywords
|
||||
reservedWords = new HashSet<>(
|
||||
Arrays.asList(
|
||||
"abstract", "do", "if", "nil?", "select", "union",
|
||||
"abstract", "annotation", "do", "if", "nil?", "select", "union",
|
||||
"alias", "else", "in", "of", "self", "unless",
|
||||
"as", "elsif", "include", "out", "sizeof", "until",
|
||||
"as?", "end", "instance", "sizeof", "pointerof", "struct", "verbatim",
|
||||
|
@ -0,0 +1,105 @@
|
||||
/*
|
||||
* Copyright 2018 OpenAPI-Generator Contributors (https://openapi-generator.tech)
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.openapitools.codegen.languages;
|
||||
|
||||
import org.openapitools.codegen.*;
|
||||
import io.swagger.models.properties.ArrayProperty;
|
||||
import io.swagger.models.properties.MapProperty;
|
||||
import io.swagger.models.properties.Property;
|
||||
import io.swagger.models.parameters.Parameter;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.*;
|
||||
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
|
||||
import org.openapitools.codegen.meta.GeneratorMetadata;
|
||||
import org.openapitools.codegen.meta.Stability;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class CsharpNetcoreFunctionsServerCodegen extends CSharpNetCoreReducedClientCodegen {
|
||||
public static final String PROJECT_NAME = "projectName";
|
||||
|
||||
final Logger LOGGER = LoggerFactory.getLogger(CsharpNetcoreFunctionsServerCodegen.class);
|
||||
|
||||
public CodegenType getTag() {
|
||||
return CodegenType.SERVER;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return "csharp-netcore-functions";
|
||||
}
|
||||
|
||||
public String getHelp() {
|
||||
return "Generates a csharp server.";
|
||||
}
|
||||
|
||||
public CsharpNetcoreFunctionsServerCodegen() {
|
||||
super();
|
||||
|
||||
generatorMetadata = GeneratorMetadata.newBuilder(generatorMetadata)
|
||||
.stability(Stability.BETA)
|
||||
.build();
|
||||
|
||||
outputFolder = "generated-code" + File.separator + "csharp";
|
||||
modelTemplateFiles.put("model.mustache", ".cs");
|
||||
apiTemplateFiles.put("functions.mustache", ".cs");
|
||||
embeddedTemplateDir = templateDir = "csharp-netcore-functions";
|
||||
apiPackage = "Apis";
|
||||
modelPackage = "Models";
|
||||
String clientPackageDir = "generatedSrc/Client";
|
||||
supportingFiles.add(new SupportingFile("README.mustache", "generatedSrc", "README.md"));
|
||||
supportingFiles.add(new SupportingFile("project.mustache", "generatedSrc", "project.json"));
|
||||
|
||||
supportingFiles.add(new SupportingFile("IApiAccessor.mustache",
|
||||
clientPackageDir, "IApiAccessor.cs"));
|
||||
supportingFiles.add(new SupportingFile("Configuration.mustache",
|
||||
clientPackageDir, "Configuration.cs"));
|
||||
supportingFiles.add(new SupportingFile("ApiClient.mustache",
|
||||
clientPackageDir, "ApiClient.cs"));
|
||||
supportingFiles.add(new SupportingFile("ApiException.mustache",
|
||||
clientPackageDir, "ApiException.cs"));
|
||||
supportingFiles.add(new SupportingFile("ApiResponse.mustache",
|
||||
clientPackageDir, "ApiResponse.cs"));
|
||||
supportingFiles.add(new SupportingFile("ExceptionFactory.mustache",
|
||||
clientPackageDir, "ExceptionFactory.cs"));
|
||||
supportingFiles.add(new SupportingFile("OpenAPIDateConverter.mustache",
|
||||
clientPackageDir, "OpenAPIDateConverter.cs"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String apiFileFolder() {
|
||||
return outputFolder + File.separator + "generatedSrc" + File.separator + "Functions";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String modelFileFolder() {
|
||||
return outputFolder + File.separator + "generatedSrc" + File.separator + "Models";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String apiDocFileFolder() {
|
||||
return (outputFolder + "/Docs").replace('/', File.separatorChar);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String apiTestFileFolder() {
|
||||
return outputFolder + File.separator + "Tests" + File.separator + "Tests" + File.separator + apiPackage();
|
||||
}
|
||||
|
||||
}
|
@ -323,6 +323,21 @@ public class DartDioNextClientCodegen extends AbstractDartCodegen {
|
||||
// enums are generated with built_value and make use of BuiltSet
|
||||
model.imports.add("BuiltSet");
|
||||
}
|
||||
|
||||
if (property.isContainer) {
|
||||
// Figure out if there are any container type additionalProperties
|
||||
// that need a custom serializer builder factory added.
|
||||
final CodegenProperty items = property.items;
|
||||
if (items.getAdditionalProperties() != null) {
|
||||
addBuiltValueSerializer(new BuiltValueSerializer(
|
||||
items.isArray,
|
||||
items.getUniqueItems(),
|
||||
items.isMap,
|
||||
items.items.isNullable,
|
||||
items.getAdditionalProperties().dataType
|
||||
));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -332,7 +347,6 @@ public class DartDioNextClientCodegen extends AbstractDartCodegen {
|
||||
Map<String, Object> operations = (Map<String, Object>) objs.get("operations");
|
||||
List<CodegenOperation> operationList = (List<CodegenOperation>) operations.get("operation");
|
||||
|
||||
Set<Map<String, Object>> serializers = new HashSet<>();
|
||||
Set<String> resultImports = new HashSet<>();
|
||||
|
||||
for (CodegenOperation op : operationList) {
|
||||
@ -370,12 +384,13 @@ public class DartDioNextClientCodegen extends AbstractDartCodegen {
|
||||
// Generate serializer factories for all container type parameters.
|
||||
// But skip binary and file parameters, JSON serializers don't make sense there.
|
||||
if (param.isContainer && !(param.isBinary || param.isFile )) {
|
||||
final Map<String, Object> serializer = new HashMap<>();
|
||||
serializer.put("isArray", param.isArray);
|
||||
serializer.put("uniqueItems", param.uniqueItems);
|
||||
serializer.put("isMap", param.isMap);
|
||||
serializer.put("baseType", param.baseType);
|
||||
serializers.add(serializer);
|
||||
addBuiltValueSerializer(new BuiltValueSerializer(
|
||||
param.isArray,
|
||||
param.uniqueItems,
|
||||
param.isMap,
|
||||
param.items.isNullable,
|
||||
param.baseType
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
@ -387,17 +402,17 @@ public class DartDioNextClientCodegen extends AbstractDartCodegen {
|
||||
// Generate serializer factories for response types.
|
||||
// But skip binary and file response, JSON serializers don't make sense there.
|
||||
if (op.returnContainer != null && !(op.isResponseBinary || op.isResponseFile)) {
|
||||
final Map<String, Object> serializer = new HashMap<>();
|
||||
serializer.put("isArray", Objects.equals("array", op.returnContainer) || Objects.equals("set", op.returnContainer));
|
||||
serializer.put("uniqueItems", op.uniqueItems);
|
||||
serializer.put("isMap", Objects.equals("map", op.returnContainer));
|
||||
serializer.put("baseType", op.returnBaseType);
|
||||
serializers.add(serializer);
|
||||
addBuiltValueSerializer(new BuiltValueSerializer(
|
||||
Objects.equals("array", op.returnContainer) || Objects.equals("set", op.returnContainer),
|
||||
op.uniqueItems,
|
||||
Objects.equals("map", op.returnContainer),
|
||||
false,
|
||||
op.returnBaseType
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
objs.put("imports", resultImports.stream().sorted().collect(Collectors.toList()));
|
||||
objs.put("serializers", serializers);
|
||||
|
||||
return objs;
|
||||
}
|
||||
@ -410,6 +425,19 @@ public class DartDioNextClientCodegen extends AbstractDartCodegen {
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds the serializer to the global list of custom built_value serializers.
|
||||
* @param serializer
|
||||
*/
|
||||
private void addBuiltValueSerializer(BuiltValueSerializer serializer) {
|
||||
System.out.println("######## Add serializer!");
|
||||
additionalProperties.compute("builtValueSerializers", (k, v) -> {
|
||||
Set<BuiltValueSerializer> serializers = v == null ? Sets.newHashSet() : ((Set<BuiltValueSerializer>) v);
|
||||
serializers.add(serializer);
|
||||
return serializers;
|
||||
});
|
||||
}
|
||||
|
||||
private Set<String> rewriteImports(Set<String> originalImports, boolean isModel) {
|
||||
Set<String> resultImports = Sets.newHashSet();
|
||||
for (String modelImport : originalImports) {
|
||||
@ -428,4 +456,58 @@ public class DartDioNextClientCodegen extends AbstractDartCodegen {
|
||||
}
|
||||
return resultImports;
|
||||
}
|
||||
|
||||
static class BuiltValueSerializer {
|
||||
|
||||
final boolean isArray;
|
||||
|
||||
final boolean uniqueItems;
|
||||
|
||||
final boolean isMap;
|
||||
|
||||
final boolean isNullable;
|
||||
|
||||
final String dataType;
|
||||
|
||||
private BuiltValueSerializer(boolean isArray, boolean uniqueItems, boolean isMap, boolean isNullable, String dataType) {
|
||||
this.isArray = isArray;
|
||||
this.uniqueItems = uniqueItems;
|
||||
this.isMap = isMap;
|
||||
this.isNullable = isNullable;
|
||||
this.dataType = dataType;
|
||||
}
|
||||
|
||||
public boolean isArray() {
|
||||
return isArray;
|
||||
}
|
||||
|
||||
public boolean isUniqueItems() {
|
||||
return uniqueItems;
|
||||
}
|
||||
|
||||
public boolean isMap() {
|
||||
return isMap;
|
||||
}
|
||||
|
||||
public boolean isNullable() {
|
||||
return isNullable;
|
||||
}
|
||||
|
||||
public String getDataType() {
|
||||
return dataType;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (o == null || getClass() != o.getClass()) return false;
|
||||
BuiltValueSerializer that = (BuiltValueSerializer) o;
|
||||
return isArray == that.isArray && uniqueItems == that.uniqueItems && isMap == that.isMap && isNullable == that.isNullable && dataType.equals(that.dataType);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(isArray, uniqueItems, isMap, isNullable, dataType);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -613,7 +613,7 @@ public class ElixirClientCodegen extends DefaultCodegen implements CodegenConfig
|
||||
return "%{}";
|
||||
}
|
||||
// Primitive return type, don't even try to decode
|
||||
if (baseType == null || (simpleType && primitiveType)) {
|
||||
if (baseType == null || (containerType == null && primitiveType)) {
|
||||
return "false";
|
||||
} else if (isArray && languageSpecificPrimitives().contains(baseType)) {
|
||||
return "[]";
|
||||
@ -733,16 +733,13 @@ public class ElixirClientCodegen extends DefaultCodegen implements CodegenConfig
|
||||
StringBuilder returnEntry = new StringBuilder();
|
||||
if (exResponse.baseType == null) {
|
||||
returnEntry.append("nil");
|
||||
} else if (exResponse.simpleType) {
|
||||
} else if (exResponse.containerType == null) { // not container (array, map, set)
|
||||
if (!exResponse.primitiveType) {
|
||||
returnEntry.append(moduleName);
|
||||
returnEntry.append(".Model.");
|
||||
}
|
||||
returnEntry.append(exResponse.baseType);
|
||||
returnEntry.append(".t");
|
||||
} else if (exResponse.containerType == null) {
|
||||
returnEntry.append(returnBaseType);
|
||||
returnEntry.append(".t");
|
||||
} else {
|
||||
if (exResponse.containerType.equals("array") ||
|
||||
exResponse.containerType.equals("set")) {
|
||||
|
@ -80,6 +80,7 @@ public class JavaClientCodegen extends AbstractJavaCodegen
|
||||
public static final String JERSEY2 = "jersey2";
|
||||
public static final String NATIVE = "native";
|
||||
public static final String OKHTTP_GSON = "okhttp-gson";
|
||||
public static final String OKHTTP_GSON_NEXTGEN = "okhttp-gson-nextgen";
|
||||
public static final String RESTEASY = "resteasy";
|
||||
public static final String RESTTEMPLATE = "resttemplate";
|
||||
public static final String WEBCLIENT = "webclient";
|
||||
@ -168,6 +169,7 @@ public class JavaClientCodegen extends AbstractJavaCodegen
|
||||
supportedLibraries.put(JERSEY2, "HTTP client: Jersey client 2.25.1. JSON processing: Jackson 2.9.x");
|
||||
supportedLibraries.put(FEIGN, "HTTP client: OpenFeign 10.x. JSON processing: Jackson 2.9.x.");
|
||||
supportedLibraries.put(OKHTTP_GSON, "[DEFAULT] HTTP client: OkHttp 3.x. JSON processing: Gson 2.8.x. Enable Parcelable models on Android using '-DparcelableModel=true'. Enable gzip request encoding using '-DuseGzipFeature=true'.");
|
||||
supportedLibraries.put(OKHTTP_GSON_NEXTGEN, "HTTP client: OkHttp 3.x. JSON processing: Gson 2.8.x.'. Better support for oneOf/anyOf with breaking changes. Will replace `okhttp-gson` in the 6.0.0 release.");
|
||||
supportedLibraries.put(RETROFIT_2, "HTTP client: OkHttp 3.x. JSON processing: Gson 2.x (Retrofit 2.3.0). Enable the RxJava adapter using '-DuseRxJava[2/3]=true'. (RxJava 1.x or 2.x or 3.x)");
|
||||
supportedLibraries.put(RESTTEMPLATE, "HTTP client: Spring RestTemplate 4.x. JSON processing: Jackson 2.9.x");
|
||||
supportedLibraries.put(WEBCLIENT, "HTTP client: Spring WebClient 5.x. JSON processing: Jackson 2.9.x");
|
||||
@ -423,7 +425,7 @@ public class JavaClientCodegen extends AbstractJavaCodegen
|
||||
supportingFiles.add(new SupportingFile("ParamExpander.mustache", invokerFolder, "ParamExpander.java"));
|
||||
supportingFiles.add(new SupportingFile("EncodingUtils.mustache", invokerFolder, "EncodingUtils.java"));
|
||||
supportingFiles.add(new SupportingFile("auth/DefaultApi20Impl.mustache", authFolder, "DefaultApi20Impl.java"));
|
||||
} else if (OKHTTP_GSON.equals(getLibrary()) || StringUtils.isEmpty(getLibrary())) {
|
||||
} else if (OKHTTP_GSON.equals(getLibrary()) || StringUtils.isEmpty(getLibrary()) || OKHTTP_GSON_NEXTGEN.equals(getLibrary())) {
|
||||
// the "okhttp-gson" library template requires "ApiCallback.mustache" for async call
|
||||
supportingFiles.add(new SupportingFile("ApiCallback.mustache", invokerFolder, "ApiCallback.java"));
|
||||
supportingFiles.add(new SupportingFile("ApiResponse.mustache", invokerFolder, "ApiResponse.java"));
|
||||
@ -431,6 +433,9 @@ public class JavaClientCodegen extends AbstractJavaCodegen
|
||||
supportingFiles.add(new SupportingFile("ProgressRequestBody.mustache", invokerFolder, "ProgressRequestBody.java"));
|
||||
supportingFiles.add(new SupportingFile("ProgressResponseBody.mustache", invokerFolder, "ProgressResponseBody.java"));
|
||||
supportingFiles.add(new SupportingFile("GzipRequestInterceptor.mustache", invokerFolder, "GzipRequestInterceptor.java"));
|
||||
if (OKHTTP_GSON_NEXTGEN.equals(getLibrary())) {
|
||||
supportingFiles.add(new SupportingFile("AbstractOpenApiSchema.mustache", modelsFolder, "AbstractOpenApiSchema.java"));
|
||||
}
|
||||
|
||||
// NOTE: below moved to postProcessOperationsWithModels
|
||||
//supportingFiles.add(new SupportingFile("auth/OAuthOkHttpClient.mustache", authFolder, "OAuthOkHttpClient.java"));
|
||||
@ -615,7 +620,7 @@ public class JavaClientCodegen extends AbstractJavaCodegen
|
||||
// has OAuth defined
|
||||
if (ProcessUtils.hasOAuthMethods(openAPI)) {
|
||||
// for okhttp-gson (default), check to see if OAuth is defined and included OAuth-related files accordingly
|
||||
if ((OKHTTP_GSON.equals(getLibrary()) || StringUtils.isEmpty(getLibrary()))) {
|
||||
if ((OKHTTP_GSON.equals(getLibrary()) || StringUtils.isEmpty(getLibrary())) || OKHTTP_GSON_NEXTGEN.equals(getLibrary())) {
|
||||
supportingFiles.add(new SupportingFile("auth/OAuthOkHttpClient.mustache", authFolder, "OAuthOkHttpClient.java"));
|
||||
supportingFiles.add(new SupportingFile("auth/RetryingOAuth.mustache", authFolder, "RetryingOAuth.java"));
|
||||
}
|
||||
@ -916,7 +921,7 @@ public class JavaClientCodegen extends AbstractJavaCodegen
|
||||
CodegenModel cm = (CodegenModel) mo.get("model");
|
||||
|
||||
cm.getVendorExtensions().putIfAbsent("x-implements", new ArrayList<String>());
|
||||
if (JERSEY2.equals(getLibrary()) || NATIVE.equals(getLibrary())) {
|
||||
if (JERSEY2.equals(getLibrary()) || NATIVE.equals(getLibrary()) || OKHTTP_GSON_NEXTGEN.equals(getLibrary())) {
|
||||
cm.getVendorExtensions().put("x-implements", new ArrayList<String>());
|
||||
|
||||
if (cm.oneOf != null && !cm.oneOf.isEmpty() && cm.oneOf.contains("ModelNull")) {
|
||||
|
@ -49,6 +49,7 @@ public class KotlinClientCodegen extends AbstractKotlinCodegen {
|
||||
public static final String USE_RX_JAVA3 = "useRxJava3";
|
||||
public static final String USE_COROUTINES = "useCoroutines";
|
||||
public static final String DO_NOT_USE_RX_AND_COROUTINES = "doNotUseRxAndCoroutines";
|
||||
public static final String OMIT_GRADLE_PLUGIN_VERSIONS = "omitGradlePluginVersions";
|
||||
|
||||
public static final String DATE_LIBRARY = "dateLibrary";
|
||||
public static final String REQUEST_DATE_CONVERTER = "requestDateConverter";
|
||||
@ -201,6 +202,7 @@ public class KotlinClientCodegen extends AbstractKotlinCodegen {
|
||||
cliOptions.add(CliOption.newBoolean(USE_RX_JAVA2, "Whether to use the RxJava2 adapter with the retrofit2 library. IMPORTANT: this option has been deprecated. Please use `useRxJava3` instead."));
|
||||
cliOptions.add(CliOption.newBoolean(USE_RX_JAVA3, "Whether to use the RxJava3 adapter with the retrofit2 library."));
|
||||
cliOptions.add(CliOption.newBoolean(USE_COROUTINES, "Whether to use the Coroutines adapter with the retrofit2 library."));
|
||||
cliOptions.add(CliOption.newBoolean(OMIT_GRADLE_PLUGIN_VERSIONS, "Whether to declare Gradle plugin versions in build files."));
|
||||
|
||||
cliOptions.add(CliOption.newBoolean(MOSHI_CODE_GEN, "Whether to enable codegen with the Moshi library. Refer to the [official Moshi doc](https://github.com/square/moshi#codegen) for more info."));
|
||||
|
||||
|
@ -47,10 +47,18 @@ public class ProtobufSchemaCodegen extends DefaultCodegen implements CodegenConf
|
||||
|
||||
private static final String IMPORTS = "imports";
|
||||
|
||||
public static final String NUMBERED_FIELD_NUMBER_LIST = "numberedFieldNumberList";
|
||||
|
||||
public static final String START_ENUMS_WITH_UNKNOWN = "startEnumsWithUnknown";
|
||||
|
||||
private final Logger LOGGER = LoggerFactory.getLogger(ProtobufSchemaCodegen.class);
|
||||
|
||||
protected String packageName = "openapitools";
|
||||
|
||||
private boolean numberedFieldNumberList = false;
|
||||
|
||||
private boolean startEnumsWithUnknown = false;
|
||||
|
||||
@Override
|
||||
public CodegenType getTag() {
|
||||
return CodegenType.SCHEMA;
|
||||
@ -145,6 +153,8 @@ public class ProtobufSchemaCodegen extends DefaultCodegen implements CodegenConf
|
||||
|
||||
cliOptions.clear();
|
||||
|
||||
addSwitch(NUMBERED_FIELD_NUMBER_LIST, "Field numbers in order.", numberedFieldNumberList);
|
||||
addSwitch(START_ENUMS_WITH_UNKNOWN, "Introduces \"UNKNOWN\" as the first element of enumerations.", startEnumsWithUnknown);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -164,6 +174,14 @@ public class ProtobufSchemaCodegen extends DefaultCodegen implements CodegenConf
|
||||
setPackageName((String) additionalProperties.get(CodegenConstants.PACKAGE_NAME));
|
||||
}
|
||||
|
||||
if (additionalProperties.containsKey(this.NUMBERED_FIELD_NUMBER_LIST)) {
|
||||
this.numberedFieldNumberList = convertPropertyToBooleanAndWriteBack(NUMBERED_FIELD_NUMBER_LIST);
|
||||
}
|
||||
|
||||
if (additionalProperties.containsKey(this.START_ENUMS_WITH_UNKNOWN)) {
|
||||
this.startEnumsWithUnknown = convertPropertyToBooleanAndWriteBack(START_ENUMS_WITH_UNKNOWN);
|
||||
}
|
||||
|
||||
supportingFiles.add(new SupportingFile("README.mustache", "", "README.md"));
|
||||
}
|
||||
|
||||
@ -183,6 +201,34 @@ public class ProtobufSchemaCodegen extends DefaultCodegen implements CodegenConf
|
||||
return camelize(sanitizeName(operationId));
|
||||
}
|
||||
|
||||
public void addUnknownToAllowableValues(Map<String, Object> allowableValues, String name) {
|
||||
if(startEnumsWithUnknown) {
|
||||
if(allowableValues.containsKey("enumVars")) {
|
||||
List<Map<String, Object>> enumVars = (List<Map<String, Object>>)allowableValues.get("enumVars");
|
||||
|
||||
HashMap<String, Object> unknown = new HashMap<String, Object>();
|
||||
unknown.put("name", name + "_UNKNOWN");
|
||||
unknown.put("isString", "false");
|
||||
unknown.put("value", "\"" + name + "_UNKNOWN\"");
|
||||
|
||||
enumVars.add(0, unknown);
|
||||
}
|
||||
|
||||
if(allowableValues.containsKey("values")) {
|
||||
List<String> values = (List<String>)allowableValues.get("values");
|
||||
values.add(0, name + "_UNKNOWN");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void addEnumIndexes(List<Map<String, Object>> enumVars) {
|
||||
int enumIndex = 0;
|
||||
for (Map<String, Object> enumVar : enumVars) {
|
||||
enumVar.put("protobuf-enum-index", enumIndex);
|
||||
enumIndex++;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, Object> postProcessModels(Map<String, Object> objs) {
|
||||
objs = postProcessModelsEnum(objs);
|
||||
@ -192,6 +238,17 @@ public class ProtobufSchemaCodegen extends DefaultCodegen implements CodegenConf
|
||||
Map<String, Object> mo = (Map<String, Object>) _mo;
|
||||
CodegenModel cm = (CodegenModel) mo.get("model");
|
||||
|
||||
if(cm.isEnum) {
|
||||
Map<String, Object> allowableValues = cm.getAllowableValues();
|
||||
addUnknownToAllowableValues(allowableValues, cm.getClassname());
|
||||
|
||||
if (allowableValues.containsKey("enumVars")) {
|
||||
List<Map<String, Object>> enumVars = (List<Map<String, Object>>)allowableValues.get("enumVars");
|
||||
addEnumIndexes(enumVars);
|
||||
}
|
||||
}
|
||||
|
||||
int index = 1;
|
||||
for (CodegenProperty var : cm.vars) {
|
||||
// add x-protobuf-type: repeated if it's an array
|
||||
if (Boolean.TRUE.equals(var.isArray)) {
|
||||
@ -208,21 +265,27 @@ public class ProtobufSchemaCodegen extends DefaultCodegen implements CodegenConf
|
||||
}
|
||||
}
|
||||
|
||||
if (var.isEnum && var.allowableValues.containsKey("enumVars")) {
|
||||
List<Map<String, Object>> enumVars = (List<Map<String, Object>>) var.allowableValues.get("enumVars");
|
||||
int enumIndex = 0;
|
||||
for (Map<String, Object> enumVar : enumVars) {
|
||||
enumVar.put("protobuf-enum-index", enumIndex);
|
||||
enumIndex++;
|
||||
if (var.isEnum) {
|
||||
addUnknownToAllowableValues(var.allowableValues, var.getEnumName());
|
||||
|
||||
if(var.allowableValues.containsKey("enumVars")) {
|
||||
List<Map<String, Object>> enumVars = (List<Map<String, Object>>) var.allowableValues.get("enumVars");
|
||||
addEnumIndexes(enumVars);
|
||||
}
|
||||
}
|
||||
|
||||
// Add x-protobuf-index, unless already specified
|
||||
try {
|
||||
var.vendorExtensions.putIfAbsent("x-protobuf-index", generateFieldNumberFromString(var.getName()));
|
||||
} catch (ProtoBufIndexComputationException e) {
|
||||
LOGGER.error("Exception when assigning a index to a protobuf field", e);
|
||||
var.vendorExtensions.putIfAbsent("x-protobuf-index", "Generated field number is in reserved range (19000, 19999)");
|
||||
if(this.numberedFieldNumberList) {
|
||||
var.vendorExtensions.putIfAbsent("x-protobuf-index", index);
|
||||
index++;
|
||||
}
|
||||
else {
|
||||
try {
|
||||
var.vendorExtensions.putIfAbsent("x-protobuf-index", generateFieldNumberFromString(var.getName()));
|
||||
} catch (ProtoBufIndexComputationException e) {
|
||||
LOGGER.error("Exception when assigning a index to a protobuf field", e);
|
||||
var.vendorExtensions.putIfAbsent("x-protobuf-index", "Generated field number is in reserved range (19000, 19999)");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -215,6 +215,9 @@ public class PythonLegacyClientCodegen extends AbstractPythonCodegen implements
|
||||
}
|
||||
}
|
||||
|
||||
String modelPath = packagePath() + File.separatorChar + modelPackage.replace('.', File.separatorChar);
|
||||
String apiPath = packagePath() + File.separatorChar + apiPackage.replace('.', File.separatorChar);
|
||||
|
||||
String readmePath = "README.md";
|
||||
String readmeTemplate = "README.mustache";
|
||||
if (generateSourceCodeOnly) {
|
||||
@ -237,8 +240,8 @@ public class PythonLegacyClientCodegen extends AbstractPythonCodegen implements
|
||||
}
|
||||
supportingFiles.add(new SupportingFile("configuration.mustache", packagePath(), "configuration.py"));
|
||||
supportingFiles.add(new SupportingFile("__init__package.mustache", packagePath(), "__init__.py"));
|
||||
supportingFiles.add(new SupportingFile("__init__model.mustache", packagePath() + File.separatorChar + modelPackage, "__init__.py"));
|
||||
supportingFiles.add(new SupportingFile("__init__api.mustache", packagePath() + File.separatorChar + apiPackage, "__init__.py"));
|
||||
supportingFiles.add(new SupportingFile("__init__model.mustache", modelPath, "__init__.py"));
|
||||
supportingFiles.add(new SupportingFile("__init__api.mustache", apiPath, "__init__.py"));
|
||||
|
||||
// If the package name consists of dots(openapi.client), then we need to create the directory structure like openapi/client with __init__ files.
|
||||
String[] packageNameSplits = packageName.split("\\.");
|
||||
|
@ -141,10 +141,10 @@ public class RubyClientCodegen extends AbstractRubyCodegen {
|
||||
defaultValue("unlicense"));
|
||||
|
||||
cliOptions.add(new CliOption(GEM_REQUIRED_RUBY_VERSION, "gem required Ruby version. ").
|
||||
defaultValue(">= 1.9"));
|
||||
defaultValue(">= 2.4"));
|
||||
|
||||
cliOptions.add(new CliOption(GEM_HOMEPAGE, "gem homepage. ").
|
||||
defaultValue("http://org.openapitools"));
|
||||
defaultValue("https://openapi-generator.tech"));
|
||||
|
||||
cliOptions.add(new CliOption(GEM_SUMMARY, "gem summary. ").
|
||||
defaultValue("A ruby wrapper for the REST APIs"));
|
||||
@ -152,7 +152,7 @@ public class RubyClientCodegen extends AbstractRubyCodegen {
|
||||
cliOptions.add(new CliOption(GEM_DESCRIPTION, "gem description. ").
|
||||
defaultValue("This gem maps to a REST API"));
|
||||
|
||||
cliOptions.add(new CliOption(GEM_AUTHOR, "gem author (only one is supported)."));
|
||||
cliOptions.add(new CliOption(GEM_AUTHOR, "gem author (only one is supported).").defaultValue("OpenAPI-Generator"));
|
||||
|
||||
cliOptions.add(new CliOption(GEM_AUTHOR_EMAIL, "gem author email (only one is supported)."));
|
||||
|
||||
|
@ -66,6 +66,7 @@ public class Swift5ClientCodegen extends DefaultCodegen implements CodegenConfig
|
||||
public static final String SWIFT_PACKAGE_PATH = "swiftPackagePath";
|
||||
public static final String USE_CLASSES = "useClasses";
|
||||
public static final String USE_BACKTICK_ESCAPES = "useBacktickEscapes";
|
||||
public static final String GENERATE_FROZEN_ENUMS = "generateFrozenEnums";
|
||||
public static final String GENERATE_MODEL_ADDITIONAL_PROPERTIES = "generateModelAdditionalProperties";
|
||||
public static final String HASHABLE_MODELS = "hashableModels";
|
||||
public static final String MAP_FILE_BINARY_TO_DATA = "mapFileBinaryToData";
|
||||
@ -90,6 +91,7 @@ public class Swift5ClientCodegen extends DefaultCodegen implements CodegenConfig
|
||||
protected boolean useClasses = false;
|
||||
protected boolean useBacktickEscapes = false;
|
||||
protected boolean generateModelAdditionalProperties = true;
|
||||
protected boolean generateFrozenEnums = true;
|
||||
protected boolean hashableModels = true;
|
||||
protected boolean mapFileBinaryToData = false;
|
||||
protected String[] responseAs = new String[0];
|
||||
@ -281,6 +283,9 @@ public class Swift5ClientCodegen extends DefaultCodegen implements CodegenConfig
|
||||
cliOptions.add(new CliOption(USE_BACKTICK_ESCAPES,
|
||||
"Escape reserved words using backticks (default: false)")
|
||||
.defaultValue(Boolean.FALSE.toString()));
|
||||
cliOptions.add(new CliOption(GENERATE_FROZEN_ENUMS,
|
||||
"Generate frozen enums (default: true)")
|
||||
.defaultValue(Boolean.TRUE.toString()));
|
||||
cliOptions.add(new CliOption(GENERATE_MODEL_ADDITIONAL_PROPERTIES,
|
||||
"Generate model additional properties (default: true)")
|
||||
.defaultValue(Boolean.TRUE.toString()));
|
||||
@ -485,6 +490,13 @@ public class Swift5ClientCodegen extends DefaultCodegen implements CodegenConfig
|
||||
setUseBacktickEscapes(convertPropertyToBooleanAndWriteBack(USE_BACKTICK_ESCAPES));
|
||||
}
|
||||
|
||||
// Setup generateFrozenEnums option. If true, enums will strictly include
|
||||
// cases matching the spec. If false, enums will also include an extra catch-all case.
|
||||
if (additionalProperties.containsKey(GENERATE_FROZEN_ENUMS)) {
|
||||
setGenerateFrozenEnums(convertPropertyToBooleanAndWriteBack(GENERATE_FROZEN_ENUMS));
|
||||
}
|
||||
additionalProperties.put(GENERATE_FROZEN_ENUMS, generateFrozenEnums);
|
||||
|
||||
if (additionalProperties.containsKey(GENERATE_MODEL_ADDITIONAL_PROPERTIES)) {
|
||||
setGenerateModelAdditionalProperties(convertPropertyToBooleanAndWriteBack(GENERATE_MODEL_ADDITIONAL_PROPERTIES));
|
||||
}
|
||||
@ -943,6 +955,10 @@ public class Swift5ClientCodegen extends DefaultCodegen implements CodegenConfig
|
||||
this.useBacktickEscapes = useBacktickEscapes;
|
||||
}
|
||||
|
||||
public void setGenerateFrozenEnums(boolean generateFrozenEnums) {
|
||||
this.generateFrozenEnums = generateFrozenEnums;
|
||||
}
|
||||
|
||||
public void setGenerateModelAdditionalProperties(boolean generateModelAdditionalProperties) {
|
||||
this.generateModelAdditionalProperties = generateModelAdditionalProperties;
|
||||
}
|
||||
|
@ -67,7 +67,7 @@ public class TypeScriptAngularClientCodegen extends AbstractTypeScriptClientCode
|
||||
public static final String STRING_ENUMS_DESC = "Generate string enums instead of objects for enum values.";
|
||||
public static final String QUERY_PARAM_OBJECT_FORMAT = "queryParamObjectFormat";
|
||||
|
||||
protected String ngVersion = "12.2.12";
|
||||
protected String ngVersion = "13.0.1";
|
||||
protected String npmRepository = null;
|
||||
private boolean useSingleRequestParameter = false;
|
||||
protected String serviceSuffix = "Service";
|
||||
@ -146,7 +146,7 @@ public class TypeScriptAngularClientCodegen extends AbstractTypeScriptClientCode
|
||||
|
||||
@Override
|
||||
public String getHelp() {
|
||||
return "Generates a TypeScript Angular (6.x - 12.x) client library.";
|
||||
return "Generates a TypeScript Angular (6.x - 13.x) client library.";
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -243,7 +243,7 @@ public class TypeScriptAngularClientCodegen extends AbstractTypeScriptClientCode
|
||||
} else {
|
||||
additionalProperties.put(DELETE_ACCEPTS_BODY, false);
|
||||
}
|
||||
|
||||
|
||||
additionalProperties.put(NG_VERSION, ngVersion);
|
||||
|
||||
if (additionalProperties.containsKey(API_MODULE_PREFIX)) {
|
||||
@ -300,7 +300,9 @@ public class TypeScriptAngularClientCodegen extends AbstractTypeScriptClientCode
|
||||
}
|
||||
|
||||
// Set the typescript version compatible to the Angular version
|
||||
if (ngVersion.atLeast("12.0.0")) {
|
||||
if (ngVersion.atLeast("13.0.0")) {
|
||||
additionalProperties.put("tsVersion", ">=4.4.2 <4.5.0");
|
||||
} else if (ngVersion.atLeast("12.0.0")) {
|
||||
additionalProperties.put("tsVersion", ">=4.3.0 <4.4.0");
|
||||
} else if (ngVersion.atLeast("11.0.0")) {
|
||||
additionalProperties.put("tsVersion", ">=4.0.0 <4.1.0");
|
||||
@ -318,7 +320,9 @@ public class TypeScriptAngularClientCodegen extends AbstractTypeScriptClientCode
|
||||
}
|
||||
|
||||
// Set the rxJS version compatible to the Angular version
|
||||
if (ngVersion.atLeast("10.0.0")) {
|
||||
if (ngVersion.atLeast("13.0.0")) {
|
||||
additionalProperties.put("rxjsVersion", "7.4.0");
|
||||
} else if (ngVersion.atLeast("10.0.0")) {
|
||||
additionalProperties.put("rxjsVersion", "6.6.0");
|
||||
} else if (ngVersion.atLeast("9.0.0")) {
|
||||
additionalProperties.put("rxjsVersion", "6.5.3");
|
||||
@ -334,7 +338,10 @@ public class TypeScriptAngularClientCodegen extends AbstractTypeScriptClientCode
|
||||
supportingFiles.add(new SupportingFile("ng-package.mustache", getIndexDirectory(), "ng-package.json"));
|
||||
|
||||
// Specific ng-packagr configuration
|
||||
if (ngVersion.atLeast("12.0.0")) {
|
||||
if (ngVersion.atLeast("13.0.0")) {
|
||||
additionalProperties.put("ngPackagrVersion", "13.0.3");
|
||||
additionalProperties.put("tsickleVersion", "0.43.0");
|
||||
} else if (ngVersion.atLeast("12.0.0")) {
|
||||
additionalProperties.put("ngPackagrVersion", "12.2.1");
|
||||
additionalProperties.put("tsickleVersion", "0.43.0");
|
||||
} else if (ngVersion.atLeast("11.0.0")) {
|
||||
@ -542,8 +549,19 @@ public class TypeScriptAngularClientCodegen extends AbstractTypeScriptClientCode
|
||||
setChildDiscriminatorValue(cm, child);
|
||||
}
|
||||
}
|
||||
|
||||
// with tagged union, a child model doesn't extend the parent (all properties are just copied over)
|
||||
// it means we don't need to import that parent any more
|
||||
if (cm.parent != null) {
|
||||
cm.imports.remove(cm.parent);
|
||||
|
||||
// however, it's possible that the child model contains a recursive reference to the parent
|
||||
// in order to support this case, we update the list of imports from properties once again
|
||||
for (CodegenProperty cp: cm.allVars) {
|
||||
addImportsForPropertyType(cm, cp);
|
||||
}
|
||||
removeSelfReferenceImports(cm);
|
||||
|
||||
}
|
||||
}
|
||||
// Add additional filename information for imports
|
||||
|
@ -28,7 +28,11 @@ else()
|
||||
endif()
|
||||
|
||||
set(pkgName "{{projectName}}")
|
||||
set(VERSION 0.0.1) # this default version can be overridden in PreTarget.cmake
|
||||
|
||||
# this default version can be overridden in PreTarget.cmake
|
||||
set(PROJECT_VERSION_MAJOR 0)
|
||||
set(PROJECT_VERSION_MINOR 0)
|
||||
set(PROJECT_VERSION_PATCH 1)
|
||||
|
||||
find_package(CURL 7.58.0 REQUIRED)
|
||||
if(CURL_FOUND)
|
||||
@ -84,6 +88,8 @@ set(HDRS
|
||||
|
||||
include(PreTarget.cmake OPTIONAL)
|
||||
|
||||
set(PROJECT_VERSION_STRING "${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}.${PROJECT_VERSION_PATCH}")
|
||||
|
||||
# Add library with project file with project name as library name
|
||||
add_library(${pkgName} ${SRCS} ${HDRS})
|
||||
# Link dependent libraries
|
||||
@ -100,22 +106,22 @@ include(PostTarget.cmake OPTIONAL)
|
||||
|
||||
# installation of libraries, headers, and config files
|
||||
if (NOT EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/Config.cmake.in)
|
||||
install(TARGETS ${pkgName} DESTINATION ${CMAKE_INSTALL_PREFIX})
|
||||
install(TARGETS ${pkgName} DESTINATION lib)
|
||||
else()
|
||||
include(GNUInstallDirs)
|
||||
install(TARGETS ${pkgName} DESTINATION ${CMAKE_INSTALL_PREFIX} EXPORT ${pkgName}Targets)
|
||||
install(TARGETS ${pkgName} DESTINATION lib EXPORT ${pkgName}Targets)
|
||||
|
||||
foreach(HDR_FILE ${HDRS})
|
||||
get_filename_component(HDR_DIRECTORY ${HDR_FILE} DIRECTORY)
|
||||
get_filename_component(ABSOLUTE_HDR_DIRECTORY ${HDR_DIRECTORY} ABSOLUTE)
|
||||
file(RELATIVE_PATH RELATIVE_HDR_PATH ${CMAKE_CURRENT_SOURCE_DIR} ${ABSOLUTE_HDR_DIRECTORY})
|
||||
install(FILES ${HDR_FILE} DESTINATION include/${RELATIVE_HDR_PATH})
|
||||
install(FILES ${HDR_FILE} DESTINATION include/${pkgName}/${RELATIVE_HDR_PATH})
|
||||
endforeach()
|
||||
|
||||
include(CMakePackageConfigHelpers)
|
||||
write_basic_package_version_file(
|
||||
"${CMAKE_CURRENT_BINARY_DIR}/${pkgName}/${pkgName}ConfigVersion.cmake"
|
||||
VERSION "${VERSION}"
|
||||
VERSION "${PROJECT_VERSION_STRING}"
|
||||
COMPATIBILITY AnyNewerVersion
|
||||
)
|
||||
|
||||
@ -147,6 +153,9 @@ else()
|
||||
)
|
||||
endif()
|
||||
|
||||
# make installation packages
|
||||
include(Packing.cmake OPTIONAL)
|
||||
|
||||
# Setting file variables to null
|
||||
set(SRCS "")
|
||||
set(HDRS "")
|
||||
|
24
modules/openapi-generator/src/main/resources/C-libcurl/Packing.cmake.mustache
vendored
Normal file
24
modules/openapi-generator/src/main/resources/C-libcurl/Packing.cmake.mustache
vendored
Normal file
@ -0,0 +1,24 @@
|
||||
set(CPACK_PACKAGE_NAME lib${pkgName})
|
||||
|
||||
set(CPACK_PACKAGE_VERSION_MAJOR ${PROJECT_VERSION_MAJOR})
|
||||
set(CPACK_PACKAGE_VERSION_MINOR ${PROJECT_VERSION_MINOR})
|
||||
set(CPACK_PACKAGE_VERSION_PATCH ${PROJECT_VERSION_PATCH})
|
||||
|
||||
set(CPACK_PACKAGE_DESCRIPTION_SUMMARY ${PROJECT_PACKAGE_DESCRIPTION_SUMMARY})
|
||||
set(CPACK_PACKAGE_VENDOR ${PROJECT_PACKAGE_VENDOR})
|
||||
set(CPACK_PACKAGE_CONTACT ${PROJECT_PACKAGE_CONTACT})
|
||||
set(CPACK_DEBIAN_PACKAGE_MAINTAINER ${PROJECT_PACKAGE_MAINTAINER})
|
||||
|
||||
set(CPACK_VERBATIM_VARIABLES YES)
|
||||
|
||||
set(CPACK_PACKAGE_INSTALL_DIRECTORY ${CPACK_PACKAGE_NAME})
|
||||
|
||||
set(CPACK_PACKAGING_INSTALL_PREFIX ${CMAKE_INSTALL_PREFIX})
|
||||
|
||||
set(CPACK_DEBIAN_FILE_NAME DEB-DEFAULT)
|
||||
|
||||
set(CPACK_DEB_COMPONENT_INSTALL YES)
|
||||
|
||||
set(CPACK_DEBIAN_PACKAGE_SHLIBDEPS TRUE)
|
||||
|
||||
include(CPack)
|
@ -222,14 +222,25 @@ public class {{classname}} {
|
||||
if (memberVarResponseInterceptor != null) {
|
||||
memberVarResponseInterceptor.accept(localVarResponse);
|
||||
}
|
||||
if (localVarResponse.statusCode()/ 100 != 2) {
|
||||
throw getApiException("{{operationId}}", localVarResponse);
|
||||
}
|
||||
return new ApiResponse<{{{returnType}}}{{^returnType}}Void{{/returnType}}>(
|
||||
try {
|
||||
if (localVarResponse.statusCode()/ 100 != 2) {
|
||||
throw getApiException("{{operationId}}", localVarResponse);
|
||||
}
|
||||
return new ApiResponse<{{{returnType}}}{{^returnType}}Void{{/returnType}}>(
|
||||
localVarResponse.statusCode(),
|
||||
localVarResponse.headers().map(),
|
||||
{{#returnType}}memberVarObjectMapper.readValue(localVarResponse.body(), new TypeReference<{{{returnType}}}>() {}){{/returnType}}{{^returnType}}null{{/returnType}}
|
||||
{{#returnType}}memberVarObjectMapper.readValue(localVarResponse.body(), new TypeReference<{{{returnType}}}>() {}) // closes the InputStream{{/returnType}}
|
||||
{{^returnType}}null{{/returnType}}
|
||||
);
|
||||
} finally {
|
||||
{{^returnType}}
|
||||
// Drain the InputStream
|
||||
while (localVarResponse.body().read() != -1) {
|
||||
// Ignore
|
||||
}
|
||||
localVarResponse.body().close();
|
||||
{{/returnType}}
|
||||
}
|
||||
} catch (IOException e) {
|
||||
throw new ApiException(e);
|
||||
}
|
||||
|
@ -0,0 +1,138 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{modelPackage}};
|
||||
|
||||
import {{invokerPackage}}.ApiException;
|
||||
import java.util.Objects;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.Map;
|
||||
import javax.ws.rs.core.GenericType;
|
||||
|
||||
//import com.fasterxml.jackson.annotation.JsonValue;
|
||||
|
||||
/**
|
||||
* Abstract class for oneOf,anyOf schemas defined in OpenAPI spec
|
||||
*/
|
||||
{{>additionalModelTypeAnnotations}}{{>generatedAnnotation}}
|
||||
public abstract class AbstractOpenApiSchema {
|
||||
|
||||
// store the actual instance of the schema/object
|
||||
private Object instance;
|
||||
|
||||
// is nullable
|
||||
private Boolean isNullable;
|
||||
|
||||
// schema type (e.g. oneOf, anyOf)
|
||||
private final String schemaType;
|
||||
|
||||
public AbstractOpenApiSchema(String schemaType, Boolean isNullable) {
|
||||
this.schemaType = schemaType;
|
||||
this.isNullable = isNullable;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the list of oneOf/anyOf composed schemas allowed to be stored in this object
|
||||
*
|
||||
* @return an instance of the actual schema/object
|
||||
*/
|
||||
public abstract Map<String, GenericType> getSchemas();
|
||||
|
||||
/**
|
||||
* Get the actual instance
|
||||
*
|
||||
* @return an instance of the actual schema/object
|
||||
*/
|
||||
//@JsonValue
|
||||
public Object getActualInstance() {return instance;}
|
||||
|
||||
/**
|
||||
* Set the actual instance
|
||||
*
|
||||
* @param instance the actual instance of the schema/object
|
||||
*/
|
||||
public void setActualInstance(Object instance) {this.instance = instance;}
|
||||
|
||||
/**
|
||||
* Get the instant recursively when the schemas defined in oneOf/anyof happen to be oneOf/anyOf schema as well
|
||||
*
|
||||
* @return an instance of the actual schema/object
|
||||
*/
|
||||
public Object getActualInstanceRecursively() {
|
||||
return getActualInstanceRecursively(this);
|
||||
}
|
||||
|
||||
private Object getActualInstanceRecursively(AbstractOpenApiSchema object) {
|
||||
if (object.getActualInstance() == null) {
|
||||
return null;
|
||||
} else if (object.getActualInstance() instanceof AbstractOpenApiSchema) {
|
||||
return getActualInstanceRecursively((AbstractOpenApiSchema)object.getActualInstance());
|
||||
} else {
|
||||
return object.getActualInstance();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the schema type (e.g. anyOf, oneOf)
|
||||
*
|
||||
* @return the schema type
|
||||
*/
|
||||
public String getSchemaType() {
|
||||
return schemaType;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
StringBuilder sb = new StringBuilder();
|
||||
sb.append("class ").append(getClass()).append(" {\n");
|
||||
sb.append(" instance: ").append(toIndentedString(instance)).append("\n");
|
||||
sb.append(" isNullable: ").append(toIndentedString(isNullable)).append("\n");
|
||||
sb.append(" schemaType: ").append(toIndentedString(schemaType)).append("\n");
|
||||
sb.append("}");
|
||||
return sb.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert the given object to string with each line indented by 4 spaces
|
||||
* (except the first line).
|
||||
*/
|
||||
private String toIndentedString(Object o) {
|
||||
if (o == null) {
|
||||
return "null";
|
||||
}
|
||||
return o.toString().replace("\n", "\n ");
|
||||
}
|
||||
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) {
|
||||
return true;
|
||||
}
|
||||
if (o == null || getClass() != o.getClass()) {
|
||||
return false;
|
||||
}
|
||||
AbstractOpenApiSchema a = (AbstractOpenApiSchema) o;
|
||||
return Objects.equals(this.instance, a.instance) &&
|
||||
Objects.equals(this.isNullable, a.isNullable) &&
|
||||
Objects.equals(this.schemaType, a.schemaType);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(instance, isNullable, schemaType);
|
||||
}
|
||||
|
||||
/**
|
||||
* Is nullable
|
||||
*
|
||||
* @return true if it's nullable
|
||||
*/
|
||||
public Boolean isNullable() {
|
||||
if (Boolean.TRUE.equals(isNullable)) {
|
||||
return Boolean.TRUE;
|
||||
} else {
|
||||
return Boolean.FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
{{>libraries/jersey2/additional_properties}}
|
||||
|
||||
}
|
@ -0,0 +1,51 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}};
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Callback for asynchronous API call.
|
||||
*
|
||||
* @param <T> The return type
|
||||
*/
|
||||
public interface ApiCallback<T> {
|
||||
/**
|
||||
* This is called when the API call fails.
|
||||
*
|
||||
* @param e The exception causing the failure
|
||||
* @param statusCode Status code of the response if available, otherwise it would be 0
|
||||
* @param responseHeaders Headers of the response if available, otherwise it would be null
|
||||
*/
|
||||
void onFailure(ApiException e, int statusCode, Map<String, List<String>> responseHeaders);
|
||||
|
||||
/**
|
||||
* This is called when the API call succeeded.
|
||||
*
|
||||
* @param result The result deserialized from response
|
||||
* @param statusCode Status code of the response
|
||||
* @param responseHeaders Headers of the response
|
||||
*/
|
||||
void onSuccess(T result, int statusCode, Map<String, List<String>> responseHeaders);
|
||||
|
||||
/**
|
||||
* This is called when the API upload processing.
|
||||
*
|
||||
* @param bytesWritten bytes Written
|
||||
* @param contentLength content length of request body
|
||||
* @param done write end
|
||||
*/
|
||||
void onUploadProgress(long bytesWritten, long contentLength, boolean done);
|
||||
|
||||
/**
|
||||
* This is called when the API download processing.
|
||||
*
|
||||
* @param bytesRead bytes Read
|
||||
* @param contentLength content length of the response
|
||||
* @param done Read end
|
||||
*/
|
||||
void onDownloadProgress(long bytesRead, long contentLength, boolean done);
|
||||
}
|
1737
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/ApiClient.mustache
vendored
Normal file
1737
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/ApiClient.mustache
vendored
Normal file
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,75 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}};
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
{{#caseInsensitiveResponseHeaders}}
|
||||
import java.util.Map.Entry;
|
||||
import java.util.TreeMap;
|
||||
{{/caseInsensitiveResponseHeaders}}
|
||||
|
||||
/**
|
||||
* API response returned by API call.
|
||||
*/
|
||||
public class ApiResponse<T> {
|
||||
final private int statusCode;
|
||||
final private Map<String, List<String>> headers;
|
||||
final private T data;
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiResponse.</p>
|
||||
*
|
||||
* @param statusCode The status code of HTTP response
|
||||
* @param headers The headers of HTTP response
|
||||
*/
|
||||
public ApiResponse(int statusCode, Map<String, List<String>> headers) {
|
||||
this(statusCode, headers, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiResponse.</p>
|
||||
*
|
||||
* @param statusCode The status code of HTTP response
|
||||
* @param headers The headers of HTTP response
|
||||
* @param data The object deserialized from response bod
|
||||
*/
|
||||
public ApiResponse(int statusCode, Map<String, List<String>> headers, T data) {
|
||||
this.statusCode = statusCode;
|
||||
{{#caseInsensitiveResponseHeaders}}
|
||||
Map<String, List<String>> responseHeaders = new TreeMap<String, List<String>>(String.CASE_INSENSITIVE_ORDER);
|
||||
for(Entry<String, List<String>> entry : headers.entrySet()){
|
||||
responseHeaders.put(entry.getKey().toLowerCase(), entry.getValue());
|
||||
}
|
||||
{{/caseInsensitiveResponseHeaders}}
|
||||
this.headers = {{#caseInsensitiveResponseHeaders}}responseHeaders{{/caseInsensitiveResponseHeaders}}{{^caseInsensitiveResponseHeaders}}headers{{/caseInsensitiveResponseHeaders}};
|
||||
this.data = data;
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Get the <code>status code</code>.</p>
|
||||
*
|
||||
* @return the status code
|
||||
*/
|
||||
public int getStatusCode() {
|
||||
return statusCode;
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Get the <code>headers</code>.</p>
|
||||
*
|
||||
* @return a {@link java.util.Map} of headers
|
||||
*/
|
||||
public Map<String, List<String>> getHeaders() {
|
||||
return headers;
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Get the <code>data</code>.</p>
|
||||
*
|
||||
* @return the data
|
||||
*/
|
||||
public T getData() {
|
||||
return data;
|
||||
}
|
||||
}
|
@ -0,0 +1,74 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}};
|
||||
|
||||
import okhttp3.*;
|
||||
import okio.Buffer;
|
||||
import okio.BufferedSink;
|
||||
import okio.GzipSink;
|
||||
import okio.Okio;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
/**
|
||||
* Encodes request bodies using gzip.
|
||||
*
|
||||
* Taken from https://github.com/square/okhttp/issues/350
|
||||
*/
|
||||
class GzipRequestInterceptor implements Interceptor {
|
||||
@Override
|
||||
public Response intercept(Chain chain) throws IOException {
|
||||
Request originalRequest = chain.request();
|
||||
if (originalRequest.body() == null || originalRequest.header("Content-Encoding") != null) {
|
||||
return chain.proceed(originalRequest);
|
||||
}
|
||||
|
||||
Request compressedRequest = originalRequest.newBuilder()
|
||||
.header("Content-Encoding", "gzip")
|
||||
.method(originalRequest.method(), forceContentLength(gzip(originalRequest.body())))
|
||||
.build();
|
||||
return chain.proceed(compressedRequest);
|
||||
}
|
||||
|
||||
private RequestBody forceContentLength(final RequestBody requestBody) throws IOException {
|
||||
final Buffer buffer = new Buffer();
|
||||
requestBody.writeTo(buffer);
|
||||
return new RequestBody() {
|
||||
@Override
|
||||
public MediaType contentType() {
|
||||
return requestBody.contentType();
|
||||
}
|
||||
|
||||
@Override
|
||||
public long contentLength() {
|
||||
return buffer.size();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(BufferedSink sink) throws IOException {
|
||||
sink.write(buffer.snapshot());
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private RequestBody gzip(final RequestBody body) {
|
||||
return new RequestBody() {
|
||||
@Override
|
||||
public MediaType contentType() {
|
||||
return body.contentType();
|
||||
}
|
||||
|
||||
@Override
|
||||
public long contentLength() {
|
||||
return -1; // We don't know the compressed length in advance!
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(BufferedSink sink) throws IOException {
|
||||
BufferedSink gzipSink = Okio.buffer(new GzipSink(sink));
|
||||
body.writeTo(gzipSink);
|
||||
gzipSink.close();
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
541
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/JSON.mustache
vendored
Normal file
541
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/JSON.mustache
vendored
Normal file
@ -0,0 +1,541 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}};
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.GsonBuilder;
|
||||
import com.google.gson.JsonParseException;
|
||||
import com.google.gson.TypeAdapter;
|
||||
import com.google.gson.internal.bind.util.ISO8601Utils;
|
||||
import com.google.gson.stream.JsonReader;
|
||||
import com.google.gson.stream.JsonWriter;
|
||||
import com.google.gson.JsonElement;
|
||||
import io.gsonfire.GsonFireBuilder;
|
||||
import io.gsonfire.TypeSelector;
|
||||
{{#joda}}
|
||||
import org.joda.time.DateTime;
|
||||
import org.joda.time.LocalDate;
|
||||
import org.joda.time.format.DateTimeFormatter;
|
||||
import org.joda.time.format.DateTimeFormatterBuilder;
|
||||
import org.joda.time.format.ISODateTimeFormat;
|
||||
{{/joda}}
|
||||
{{#threetenbp}}
|
||||
import org.threeten.bp.LocalDate;
|
||||
import org.threeten.bp.OffsetDateTime;
|
||||
import org.threeten.bp.format.DateTimeFormatter;
|
||||
{{/threetenbp}}
|
||||
|
||||
import okio.ByteString;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.StringReader;
|
||||
import java.lang.reflect.Type;
|
||||
import java.text.DateFormat;
|
||||
import java.text.ParseException;
|
||||
import java.text.ParsePosition;
|
||||
{{#java8}}
|
||||
import java.time.LocalDate;
|
||||
import java.time.OffsetDateTime;
|
||||
import java.time.format.DateTimeFormatter;
|
||||
{{/java8}}
|
||||
import java.util.Date;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.HashMap;
|
||||
|
||||
/*
|
||||
* A JSON utility class
|
||||
*
|
||||
* NOTE: in the future, this class may be converted to static, which may break
|
||||
* backward-compatibility
|
||||
*/
|
||||
public class JSON {
|
||||
private Gson gson;
|
||||
private boolean isLenientOnJson = false;
|
||||
private DateTypeAdapter dateTypeAdapter = new DateTypeAdapter();
|
||||
private SqlDateTypeAdapter sqlDateTypeAdapter = new SqlDateTypeAdapter();
|
||||
{{#joda}}
|
||||
private DateTimeTypeAdapter dateTimeTypeAdapter = new DateTimeTypeAdapter();
|
||||
private LocalDateTypeAdapter localDateTypeAdapter = new LocalDateTypeAdapter();
|
||||
{{/joda}}
|
||||
{{#jsr310}}
|
||||
private OffsetDateTimeTypeAdapter offsetDateTimeTypeAdapter = new OffsetDateTimeTypeAdapter();
|
||||
private LocalDateTypeAdapter localDateTypeAdapter = new LocalDateTypeAdapter();
|
||||
{{/jsr310}}
|
||||
private ByteArrayAdapter byteArrayAdapter = new ByteArrayAdapter();
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public static GsonBuilder createGson() {
|
||||
GsonFireBuilder fireBuilder = new GsonFireBuilder()
|
||||
{{#models}}
|
||||
{{#model}}
|
||||
{{#discriminator}}
|
||||
.registerTypeSelector({{modelPackage}}.{{classname}}.class, new TypeSelector<{{modelPackage}}.{{classname}}>() {
|
||||
@Override
|
||||
public Class<? extends {{modelPackage}}.{{classname}}> getClassForElement(JsonElement readElement) {
|
||||
Map<String, Class> classByDiscriminatorValue = new HashMap<String, Class>();
|
||||
{{#mappedModels}}
|
||||
classByDiscriminatorValue.put("{{mappingName}}"{{^discriminatorCaseSensitive}}.toUpperCase(Locale.ROOT){{/discriminatorCaseSensitive}}, {{modelPackage}}.{{modelName}}.class);
|
||||
{{/mappedModels}}
|
||||
classByDiscriminatorValue.put("{{name}}"{{^discriminatorCaseSensitive}}.toUpperCase(Locale.ROOT){{/discriminatorCaseSensitive}}, {{modelPackage}}.{{classname}}.class);
|
||||
return getClassByDiscriminator(classByDiscriminatorValue,
|
||||
getDiscriminatorValue(readElement, "{{{propertyBaseName}}}"));
|
||||
}
|
||||
})
|
||||
{{/discriminator}}
|
||||
{{/model}}
|
||||
{{/models}}
|
||||
;
|
||||
GsonBuilder builder = fireBuilder.createGsonBuilder();
|
||||
{{#disableHtmlEscaping}}
|
||||
builder.disableHtmlEscaping();
|
||||
{{/disableHtmlEscaping}}
|
||||
return builder;
|
||||
}
|
||||
|
||||
private static String getDiscriminatorValue(JsonElement readElement, String discriminatorField) {
|
||||
JsonElement element = readElement.getAsJsonObject().get(discriminatorField);
|
||||
if (null == element) {
|
||||
throw new IllegalArgumentException("missing discriminator field: <" + discriminatorField + ">");
|
||||
}
|
||||
return element.getAsString();
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the Java class that implements the OpenAPI schema for the specified discriminator value.
|
||||
*
|
||||
* @param classByDiscriminatorValue The map of discriminator values to Java classes.
|
||||
* @param discriminatorValue The value of the OpenAPI discriminator in the input data.
|
||||
* @return The Java class that implements the OpenAPI schema
|
||||
*/
|
||||
private static Class getClassByDiscriminator(Map classByDiscriminatorValue, String discriminatorValue) {
|
||||
Class clazz = (Class) classByDiscriminatorValue.get(discriminatorValue{{^discriminatorCaseSensitive}}.toUpperCase(Locale.ROOT){{/discriminatorCaseSensitive}});
|
||||
if (null == clazz) {
|
||||
throw new IllegalArgumentException("cannot determine model class of name: <" + discriminatorValue + ">");
|
||||
}
|
||||
return clazz;
|
||||
}
|
||||
|
||||
public JSON() {
|
||||
gson = createGson()
|
||||
.registerTypeAdapter(Date.class, dateTypeAdapter)
|
||||
.registerTypeAdapter(java.sql.Date.class, sqlDateTypeAdapter)
|
||||
{{#joda}}
|
||||
.registerTypeAdapter(DateTime.class, dateTimeTypeAdapter)
|
||||
.registerTypeAdapter(LocalDate.class, localDateTypeAdapter)
|
||||
{{/joda}}
|
||||
{{#jsr310}}
|
||||
.registerTypeAdapter(OffsetDateTime.class, offsetDateTimeTypeAdapter)
|
||||
.registerTypeAdapter(LocalDate.class, localDateTypeAdapter)
|
||||
{{/jsr310}}
|
||||
.registerTypeAdapter(byte[].class, byteArrayAdapter)
|
||||
{{#models}}
|
||||
{{#model}}
|
||||
{{^isEnum}}
|
||||
{{^hasChildren}}
|
||||
.registerTypeAdapterFactory(new {{modelPackage}}.{{{classname}}}.CustomTypeAdapterFactory())
|
||||
{{/hasChildren}}
|
||||
{{/isEnum}}
|
||||
{{/model}}
|
||||
{{/models}}
|
||||
.create();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get Gson.
|
||||
*
|
||||
* @return Gson
|
||||
*/
|
||||
public Gson getGson() {
|
||||
return gson;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set Gson.
|
||||
*
|
||||
* @param gson Gson
|
||||
*/
|
||||
public void setGson(Gson gson) {
|
||||
this.gson = gson;
|
||||
}
|
||||
|
||||
public void setLenientOnJson(boolean lenientOnJson) {
|
||||
isLenientOnJson = lenientOnJson;
|
||||
}
|
||||
|
||||
/**
|
||||
* Serialize the given Java object into JSON string.
|
||||
*
|
||||
* @param obj Object
|
||||
* @return String representation of the JSON
|
||||
*/
|
||||
public String serialize(Object obj) {
|
||||
return gson.toJson(obj);
|
||||
}
|
||||
|
||||
/**
|
||||
* Deserialize the given JSON string to Java object.
|
||||
*
|
||||
* @param <T> Type
|
||||
* @param body The JSON string
|
||||
* @param returnType The type to deserialize into
|
||||
* @return The deserialized Java object
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public <T> T deserialize(String body, Type returnType) {
|
||||
try {
|
||||
if (isLenientOnJson) {
|
||||
JsonReader jsonReader = new JsonReader(new StringReader(body));
|
||||
// see https://google-gson.googlecode.com/svn/trunk/gson/docs/javadocs/com/google/gson/stream/JsonReader.html#setLenient(boolean)
|
||||
jsonReader.setLenient(true);
|
||||
return gson.fromJson(jsonReader, returnType);
|
||||
} else {
|
||||
return gson.fromJson(body, returnType);
|
||||
}
|
||||
} catch (JsonParseException e) {
|
||||
// Fallback processing when failed to parse JSON form response body:
|
||||
// return the response body string directly for the String return type;
|
||||
if (returnType.equals(String.class)) {
|
||||
return (T) body;
|
||||
} else {
|
||||
throw (e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gson TypeAdapter for Byte Array type
|
||||
*/
|
||||
public class ByteArrayAdapter extends TypeAdapter<byte[]> {
|
||||
|
||||
@Override
|
||||
public void write(JsonWriter out, byte[] value) throws IOException {
|
||||
if (value == null) {
|
||||
out.nullValue();
|
||||
} else {
|
||||
out.value(ByteString.of(value).base64());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public byte[] read(JsonReader in) throws IOException {
|
||||
switch (in.peek()) {
|
||||
case NULL:
|
||||
in.nextNull();
|
||||
return null;
|
||||
default:
|
||||
String bytesAsBase64 = in.nextString();
|
||||
ByteString byteString = ByteString.decodeBase64(bytesAsBase64);
|
||||
return byteString.toByteArray();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
{{#joda}}
|
||||
/**
|
||||
* Gson TypeAdapter for Joda DateTime type
|
||||
*/
|
||||
public class DateTimeTypeAdapter extends TypeAdapter<DateTime> {
|
||||
|
||||
private DateTimeFormatter formatter;
|
||||
|
||||
public DateTimeTypeAdapter() {
|
||||
this(new DateTimeFormatterBuilder()
|
||||
.append(ISODateTimeFormat.dateTime().getPrinter(), ISODateTimeFormat.dateOptionalTimeParser().getParser())
|
||||
.toFormatter());
|
||||
}
|
||||
|
||||
public DateTimeTypeAdapter(DateTimeFormatter formatter) {
|
||||
this.formatter = formatter;
|
||||
}
|
||||
|
||||
public void setFormat(DateTimeFormatter dateFormat) {
|
||||
this.formatter = dateFormat;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(JsonWriter out, DateTime date) throws IOException {
|
||||
if (date == null) {
|
||||
out.nullValue();
|
||||
} else {
|
||||
out.value(formatter.print(date));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public DateTime read(JsonReader in) throws IOException {
|
||||
switch (in.peek()) {
|
||||
case NULL:
|
||||
in.nextNull();
|
||||
return null;
|
||||
default:
|
||||
String date = in.nextString();
|
||||
return formatter.parseDateTime(date);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gson TypeAdapter for Joda LocalDate type
|
||||
*/
|
||||
public class LocalDateTypeAdapter extends TypeAdapter<LocalDate> {
|
||||
|
||||
private DateTimeFormatter formatter;
|
||||
|
||||
public LocalDateTypeAdapter() {
|
||||
this(ISODateTimeFormat.date());
|
||||
}
|
||||
|
||||
public LocalDateTypeAdapter(DateTimeFormatter formatter) {
|
||||
this.formatter = formatter;
|
||||
}
|
||||
|
||||
public void setFormat(DateTimeFormatter dateFormat) {
|
||||
this.formatter = dateFormat;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(JsonWriter out, LocalDate date) throws IOException {
|
||||
if (date == null) {
|
||||
out.nullValue();
|
||||
} else {
|
||||
out.value(formatter.print(date));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public LocalDate read(JsonReader in) throws IOException {
|
||||
switch (in.peek()) {
|
||||
case NULL:
|
||||
in.nextNull();
|
||||
return null;
|
||||
default:
|
||||
String date = in.nextString();
|
||||
return formatter.parseLocalDate(date);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setDateTimeFormat(DateTimeFormatter dateFormat) {
|
||||
dateTimeTypeAdapter.setFormat(dateFormat);
|
||||
}
|
||||
|
||||
public void setLocalDateFormat(DateTimeFormatter dateFormat) {
|
||||
localDateTypeAdapter.setFormat(dateFormat);
|
||||
}
|
||||
|
||||
{{/joda}}
|
||||
{{#jsr310}}
|
||||
/**
|
||||
* Gson TypeAdapter for JSR310 OffsetDateTime type
|
||||
*/
|
||||
public class OffsetDateTimeTypeAdapter extends TypeAdapter<OffsetDateTime> {
|
||||
|
||||
private DateTimeFormatter formatter;
|
||||
|
||||
public OffsetDateTimeTypeAdapter() {
|
||||
this(DateTimeFormatter.ISO_OFFSET_DATE_TIME);
|
||||
}
|
||||
|
||||
public OffsetDateTimeTypeAdapter(DateTimeFormatter formatter) {
|
||||
this.formatter = formatter;
|
||||
}
|
||||
|
||||
public void setFormat(DateTimeFormatter dateFormat) {
|
||||
this.formatter = dateFormat;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(JsonWriter out, OffsetDateTime date) throws IOException {
|
||||
if (date == null) {
|
||||
out.nullValue();
|
||||
} else {
|
||||
out.value(formatter.format(date));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public OffsetDateTime read(JsonReader in) throws IOException {
|
||||
switch (in.peek()) {
|
||||
case NULL:
|
||||
in.nextNull();
|
||||
return null;
|
||||
default:
|
||||
String date = in.nextString();
|
||||
if (date.endsWith("+0000")) {
|
||||
date = date.substring(0, date.length()-5) + "Z";
|
||||
}
|
||||
return OffsetDateTime.parse(date, formatter);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gson TypeAdapter for JSR310 LocalDate type
|
||||
*/
|
||||
public class LocalDateTypeAdapter extends TypeAdapter<LocalDate> {
|
||||
|
||||
private DateTimeFormatter formatter;
|
||||
|
||||
public LocalDateTypeAdapter() {
|
||||
this(DateTimeFormatter.ISO_LOCAL_DATE);
|
||||
}
|
||||
|
||||
public LocalDateTypeAdapter(DateTimeFormatter formatter) {
|
||||
this.formatter = formatter;
|
||||
}
|
||||
|
||||
public void setFormat(DateTimeFormatter dateFormat) {
|
||||
this.formatter = dateFormat;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(JsonWriter out, LocalDate date) throws IOException {
|
||||
if (date == null) {
|
||||
out.nullValue();
|
||||
} else {
|
||||
out.value(formatter.format(date));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public LocalDate read(JsonReader in) throws IOException {
|
||||
switch (in.peek()) {
|
||||
case NULL:
|
||||
in.nextNull();
|
||||
return null;
|
||||
default:
|
||||
String date = in.nextString();
|
||||
return LocalDate.parse(date, formatter);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setOffsetDateTimeFormat(DateTimeFormatter dateFormat) {
|
||||
offsetDateTimeTypeAdapter.setFormat(dateFormat);
|
||||
}
|
||||
|
||||
public void setLocalDateFormat(DateTimeFormatter dateFormat) {
|
||||
localDateTypeAdapter.setFormat(dateFormat);
|
||||
}
|
||||
|
||||
{{/jsr310}}
|
||||
/**
|
||||
* Gson TypeAdapter for java.sql.Date type
|
||||
* If the dateFormat is null, a simple "yyyy-MM-dd" format will be used
|
||||
* (more efficient than SimpleDateFormat).
|
||||
*/
|
||||
public class SqlDateTypeAdapter extends TypeAdapter<java.sql.Date> {
|
||||
|
||||
private DateFormat dateFormat;
|
||||
|
||||
public SqlDateTypeAdapter() {}
|
||||
|
||||
public SqlDateTypeAdapter(DateFormat dateFormat) {
|
||||
this.dateFormat = dateFormat;
|
||||
}
|
||||
|
||||
public void setFormat(DateFormat dateFormat) {
|
||||
this.dateFormat = dateFormat;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(JsonWriter out, java.sql.Date date) throws IOException {
|
||||
if (date == null) {
|
||||
out.nullValue();
|
||||
} else {
|
||||
String value;
|
||||
if (dateFormat != null) {
|
||||
value = dateFormat.format(date);
|
||||
} else {
|
||||
value = date.toString();
|
||||
}
|
||||
out.value(value);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public java.sql.Date read(JsonReader in) throws IOException {
|
||||
switch (in.peek()) {
|
||||
case NULL:
|
||||
in.nextNull();
|
||||
return null;
|
||||
default:
|
||||
String date = in.nextString();
|
||||
try {
|
||||
if (dateFormat != null) {
|
||||
return new java.sql.Date(dateFormat.parse(date).getTime());
|
||||
}
|
||||
return new java.sql.Date(ISO8601Utils.parse(date, new ParsePosition(0)).getTime());
|
||||
} catch (ParseException e) {
|
||||
throw new JsonParseException(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gson TypeAdapter for java.util.Date type
|
||||
* If the dateFormat is null, ISO8601Utils will be used.
|
||||
*/
|
||||
public class DateTypeAdapter extends TypeAdapter<Date> {
|
||||
|
||||
private DateFormat dateFormat;
|
||||
|
||||
public DateTypeAdapter() {}
|
||||
|
||||
public DateTypeAdapter(DateFormat dateFormat) {
|
||||
this.dateFormat = dateFormat;
|
||||
}
|
||||
|
||||
public void setFormat(DateFormat dateFormat) {
|
||||
this.dateFormat = dateFormat;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(JsonWriter out, Date date) throws IOException {
|
||||
if (date == null) {
|
||||
out.nullValue();
|
||||
} else {
|
||||
String value;
|
||||
if (dateFormat != null) {
|
||||
value = dateFormat.format(date);
|
||||
} else {
|
||||
value = ISO8601Utils.format(date, true);
|
||||
}
|
||||
out.value(value);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Date read(JsonReader in) throws IOException {
|
||||
try {
|
||||
switch (in.peek()) {
|
||||
case NULL:
|
||||
in.nextNull();
|
||||
return null;
|
||||
default:
|
||||
String date = in.nextString();
|
||||
try {
|
||||
if (dateFormat != null) {
|
||||
return dateFormat.parse(date);
|
||||
}
|
||||
return ISO8601Utils.parse(date, new ParsePosition(0));
|
||||
} catch (ParseException e) {
|
||||
throw new JsonParseException(e);
|
||||
}
|
||||
}
|
||||
} catch (IllegalArgumentException e) {
|
||||
throw new JsonParseException(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setDateFormat(DateFormat dateFormat) {
|
||||
dateTypeAdapter.setFormat(dateFormat);
|
||||
}
|
||||
|
||||
public void setSqlDateFormat(DateFormat dateFormat) {
|
||||
sqlDateTypeAdapter.setFormat(dateFormat);
|
||||
}
|
||||
}
|
@ -0,0 +1,62 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}};
|
||||
|
||||
import okhttp3.MediaType;
|
||||
import okhttp3.RequestBody;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
import okio.Buffer;
|
||||
import okio.BufferedSink;
|
||||
import okio.ForwardingSink;
|
||||
import okio.Okio;
|
||||
import okio.Sink;
|
||||
|
||||
public class ProgressRequestBody extends RequestBody {
|
||||
|
||||
private final RequestBody requestBody;
|
||||
|
||||
private final ApiCallback callback;
|
||||
|
||||
public ProgressRequestBody(RequestBody requestBody, ApiCallback callback) {
|
||||
this.requestBody = requestBody;
|
||||
this.callback = callback;
|
||||
}
|
||||
|
||||
@Override
|
||||
public MediaType contentType() {
|
||||
return requestBody.contentType();
|
||||
}
|
||||
|
||||
@Override
|
||||
public long contentLength() throws IOException {
|
||||
return requestBody.contentLength();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(BufferedSink sink) throws IOException {
|
||||
BufferedSink bufferedSink = Okio.buffer(sink(sink));
|
||||
requestBody.writeTo(bufferedSink);
|
||||
bufferedSink.flush();
|
||||
}
|
||||
|
||||
private Sink sink(Sink sink) {
|
||||
return new ForwardingSink(sink) {
|
||||
|
||||
long bytesWritten = 0L;
|
||||
long contentLength = 0L;
|
||||
|
||||
@Override
|
||||
public void write(Buffer source, long byteCount) throws IOException {
|
||||
super.write(source, byteCount);
|
||||
if (contentLength == 0) {
|
||||
contentLength = contentLength();
|
||||
}
|
||||
|
||||
bytesWritten += byteCount;
|
||||
callback.onUploadProgress(bytesWritten, contentLength, bytesWritten == contentLength);
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
@ -0,0 +1,59 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}};
|
||||
|
||||
import okhttp3.MediaType;
|
||||
import okhttp3.ResponseBody;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
import okio.Buffer;
|
||||
import okio.BufferedSource;
|
||||
import okio.ForwardingSource;
|
||||
import okio.Okio;
|
||||
import okio.Source;
|
||||
|
||||
public class ProgressResponseBody extends ResponseBody {
|
||||
|
||||
private final ResponseBody responseBody;
|
||||
private final ApiCallback callback;
|
||||
private BufferedSource bufferedSource;
|
||||
|
||||
public ProgressResponseBody(ResponseBody responseBody, ApiCallback callback) {
|
||||
this.responseBody = responseBody;
|
||||
this.callback = callback;
|
||||
}
|
||||
|
||||
@Override
|
||||
public MediaType contentType() {
|
||||
return responseBody.contentType();
|
||||
}
|
||||
|
||||
@Override
|
||||
public long contentLength() {
|
||||
return responseBody.contentLength();
|
||||
}
|
||||
|
||||
@Override
|
||||
public BufferedSource source() {
|
||||
if (bufferedSource == null) {
|
||||
bufferedSource = Okio.buffer(source(responseBody.source()));
|
||||
}
|
||||
return bufferedSource;
|
||||
}
|
||||
|
||||
private Source source(Source source) {
|
||||
return new ForwardingSource(source) {
|
||||
long totalBytesRead = 0L;
|
||||
|
||||
@Override
|
||||
public long read(Buffer sink, long byteCount) throws IOException {
|
||||
long bytesRead = super.read(sink, byteCount);
|
||||
// read() returns the number of bytes read, or -1 if this source is exhausted.
|
||||
totalBytesRead += bytesRead != -1 ? bytesRead : 0;
|
||||
callback.onDownloadProgress(totalBytesRead, responseBody.contentLength(), bytesRead == -1);
|
||||
return bytesRead;
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
183
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/README.mustache
vendored
Normal file
183
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/README.mustache
vendored
Normal file
@ -0,0 +1,183 @@
|
||||
# {{artifactId}}
|
||||
|
||||
{{appName}}
|
||||
- API version: {{appVersion}}
|
||||
{{^hideGenerationTimestamp}}
|
||||
- Build date: {{generatedDate}}
|
||||
{{/hideGenerationTimestamp}}
|
||||
|
||||
{{{appDescriptionWithNewLines}}}
|
||||
|
||||
{{#infoUrl}}
|
||||
For more information, please visit [{{{infoUrl}}}]({{{infoUrl}}})
|
||||
{{/infoUrl}}
|
||||
|
||||
*Automatically generated by the [OpenAPI Generator](https://openapi-generator.tech)*
|
||||
|
||||
|
||||
## Requirements
|
||||
|
||||
Building the API client library requires:
|
||||
1. Java {{#java8}}1.8{{/java8}}{{^java8}}1.7{{/java8}}+
|
||||
2. Maven (3.8.3+)/Gradle (7.2+)
|
||||
|
||||
## Installation
|
||||
|
||||
To install the API client library to your local Maven repository, simply execute:
|
||||
|
||||
```shell
|
||||
mvn clean install
|
||||
```
|
||||
|
||||
To deploy it to a remote Maven repository instead, configure the settings of the repository and execute:
|
||||
|
||||
```shell
|
||||
mvn clean deploy
|
||||
```
|
||||
|
||||
Refer to the [OSSRH Guide](http://central.sonatype.org/pages/ossrh-guide.html) for more information.
|
||||
|
||||
### Maven users
|
||||
|
||||
Add this dependency to your project's POM:
|
||||
|
||||
```xml
|
||||
<dependency>
|
||||
<groupId>{{{groupId}}}</groupId>
|
||||
<artifactId>{{{artifactId}}}</artifactId>
|
||||
<version>{{{artifactVersion}}}</version>
|
||||
<scope>compile</scope>
|
||||
</dependency>
|
||||
```
|
||||
|
||||
### Gradle users
|
||||
|
||||
Add this dependency to your project's build file:
|
||||
|
||||
```groovy
|
||||
repositories {
|
||||
mavenCentral() // Needed if the '{{{artifactId}}}' jar has been published to maven central.
|
||||
mavenLocal() // Needed if the '{{{artifactId}}}' jar has been published to the local maven repo.
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation "{{{groupId}}}:{{{artifactId}}}:{{{artifactVersion}}}"
|
||||
}
|
||||
```
|
||||
|
||||
### Others
|
||||
|
||||
At first generate the JAR by executing:
|
||||
|
||||
```shell
|
||||
mvn clean package
|
||||
```
|
||||
|
||||
Then manually install the following JARs:
|
||||
|
||||
* `target/{{{artifactId}}}-{{{artifactVersion}}}.jar`
|
||||
* `target/lib/*.jar`
|
||||
|
||||
## Getting Started
|
||||
|
||||
Please follow the [installation](#installation) instruction and execute the following Java code:
|
||||
|
||||
```java
|
||||
{{#apiInfo}}{{#apis}}{{#-first}}{{#operations}}{{#operation}}{{#-first}}
|
||||
// Import classes:
|
||||
import {{{invokerPackage}}}.ApiClient;
|
||||
import {{{invokerPackage}}}.ApiException;
|
||||
import {{{invokerPackage}}}.Configuration;{{#hasAuthMethods}}
|
||||
import {{{invokerPackage}}}.auth.*;{{/hasAuthMethods}}
|
||||
import {{{invokerPackage}}}.models.*;
|
||||
import {{{package}}}.{{{classname}}};
|
||||
|
||||
public class Example {
|
||||
public static void main(String[] args) {
|
||||
ApiClient defaultClient = Configuration.getDefaultApiClient();
|
||||
defaultClient.setBasePath("{{{basePath}}}");
|
||||
{{#hasAuthMethods}}
|
||||
{{#authMethods}}{{#isBasic}}{{#isBasicBasic}}
|
||||
// Configure HTTP basic authorization: {{{name}}}
|
||||
HttpBasicAuth {{{name}}} = (HttpBasicAuth) defaultClient.getAuthentication("{{{name}}}");
|
||||
{{{name}}}.setUsername("YOUR USERNAME");
|
||||
{{{name}}}.setPassword("YOUR PASSWORD");{{/isBasicBasic}}{{#isBasicBearer}}
|
||||
// Configure HTTP bearer authorization: {{{name}}}
|
||||
HttpBearerAuth {{{name}}} = (HttpBearerAuth) defaultClient.getAuthentication("{{{name}}}");
|
||||
{{{name}}}.setBearerToken("BEARER TOKEN");{{/isBasicBearer}}{{/isBasic}}{{#isApiKey}}
|
||||
// Configure API key authorization: {{{name}}}
|
||||
ApiKeyAuth {{{name}}} = (ApiKeyAuth) defaultClient.getAuthentication("{{{name}}}");
|
||||
{{{name}}}.setApiKey("YOUR API KEY");
|
||||
// Uncomment the following line to set a prefix for the API key, e.g. "Token" (defaults to null)
|
||||
//{{{name}}}.setApiKeyPrefix("Token");{{/isApiKey}}{{#isOAuth}}
|
||||
// Configure OAuth2 access token for authorization: {{{name}}}
|
||||
OAuth {{{name}}} = (OAuth) defaultClient.getAuthentication("{{{name}}}");
|
||||
{{{name}}}.setAccessToken("YOUR ACCESS TOKEN");{{/isOAuth}}
|
||||
{{/authMethods}}
|
||||
{{/hasAuthMethods}}
|
||||
|
||||
{{{classname}}} apiInstance = new {{{classname}}}(defaultClient);
|
||||
{{#allParams}}
|
||||
{{{dataType}}} {{{paramName}}} = {{{example}}}; // {{{dataType}}} | {{{description}}}
|
||||
{{/allParams}}
|
||||
try {
|
||||
{{#returnType}}{{{.}}} result = {{/returnType}}apiInstance.{{{operationId}}}{{^vendorExtensions.x-group-parameters}}({{#allParams}}{{{paramName}}}{{^-last}}, {{/-last}}{{/allParams}});{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}({{#requiredParams}}{{{paramName}}}{{^-last}}, {{/-last}}{{/requiredParams}}){{#optionalParams}}
|
||||
.{{{paramName}}}({{{paramName}}}){{/optionalParams}}
|
||||
.execute();{{/vendorExtensions.x-group-parameters}}{{#returnType}}
|
||||
System.out.println(result);{{/returnType}}
|
||||
} catch (ApiException e) {
|
||||
System.err.println("Exception when calling {{{classname}}}#{{{operationId}}}");
|
||||
System.err.println("Status code: " + e.getCode());
|
||||
System.err.println("Reason: " + e.getResponseBody());
|
||||
System.err.println("Response headers: " + e.getResponseHeaders());
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
{{/-first}}{{/operation}}{{/operations}}{{/-first}}{{/apis}}{{/apiInfo}}
|
||||
```
|
||||
|
||||
## Documentation for API Endpoints
|
||||
|
||||
All URIs are relative to *{{basePath}}*
|
||||
|
||||
Class | Method | HTTP request | Description
|
||||
------------ | ------------- | ------------- | -------------
|
||||
{{#apiInfo}}{{#apis}}{{#operations}}{{#operation}}*{{classname}}* | [**{{operationId}}**]({{apiDocPath}}{{classname}}.md#{{operationId}}) | **{{httpMethod}}** {{path}} | {{summary}}
|
||||
{{/operation}}{{/operations}}{{/apis}}{{/apiInfo}}
|
||||
|
||||
## Documentation for Models
|
||||
|
||||
{{#models}}{{#model}} - [{{classname}}]({{modelDocPath}}{{classname}}.md)
|
||||
{{/model}}{{/models}}
|
||||
|
||||
## Documentation for Authorization
|
||||
|
||||
{{^authMethods}}All endpoints do not require authorization.
|
||||
{{/authMethods}}Authentication schemes defined for the API:
|
||||
{{#authMethods}}### {{name}}
|
||||
|
||||
{{#isApiKey}}- **Type**: API key
|
||||
- **API key parameter name**: {{keyParamName}}
|
||||
- **Location**: {{#isKeyInQuery}}URL query string{{/isKeyInQuery}}{{#isKeyInHeader}}HTTP header{{/isKeyInHeader}}
|
||||
{{/isApiKey}}
|
||||
{{#isBasic}}- **Type**: HTTP basic authentication
|
||||
{{/isBasic}}
|
||||
{{#isOAuth}}- **Type**: OAuth
|
||||
- **Flow**: {{flow}}
|
||||
- **Authorization URL**: {{authorizationUrl}}
|
||||
- **Scopes**: {{^scopes}}N/A{{/scopes}}
|
||||
{{#scopes}} - {{scope}}: {{description}}
|
||||
{{/scopes}}
|
||||
{{/isOAuth}}
|
||||
|
||||
{{/authMethods}}
|
||||
|
||||
## Recommendation
|
||||
|
||||
It's recommended to create an instance of `ApiClient` per thread in a multithreaded environment to avoid any potential issues.
|
||||
|
||||
## Author
|
||||
|
||||
{{#apiInfo}}{{#apis}}{{#-last}}{{infoEmail}}
|
||||
{{/-last}}{{/apis}}{{/apiInfo}}
|
183
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/anyof_model.mustache
vendored
Normal file
183
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/anyof_model.mustache
vendored
Normal file
@ -0,0 +1,183 @@
|
||||
import javax.ws.rs.core.GenericType;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.HashSet;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.GsonBuilder;
|
||||
import com.google.gson.JsonParseException;
|
||||
import com.google.gson.TypeAdapter;
|
||||
import com.google.gson.TypeAdapterFactory;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
import com.google.gson.JsonPrimitive;
|
||||
import com.google.gson.annotations.JsonAdapter;
|
||||
import com.google.gson.annotations.SerializedName;
|
||||
import com.google.gson.stream.JsonReader;
|
||||
import com.google.gson.stream.JsonWriter;
|
||||
import com.google.gson.JsonDeserializationContext;
|
||||
import com.google.gson.JsonDeserializer;
|
||||
import com.google.gson.JsonSerializationContext;
|
||||
import com.google.gson.JsonSerializer;
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import com.google.gson.JsonParseException;
|
||||
|
||||
import {{invokerPackage}}.JSON;
|
||||
|
||||
{{>additionalModelTypeAnnotations}}{{>generatedAnnotation}}{{>xmlAnnotation}}
|
||||
public class {{classname}} extends AbstractOpenApiSchema{{#vendorExtensions.x-implements}}, {{{.}}}{{/vendorExtensions.x-implements}} {
|
||||
private static final Logger log = Logger.getLogger({{classname}}.class.getName());
|
||||
|
||||
public static class CustomTypeAdapterFactory implements TypeAdapterFactory {
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> type) {
|
||||
if (!{{classname}}.class.isAssignableFrom(type.getRawType())) {
|
||||
return null; // this class only serializes '{{classname}}' and its subtypes
|
||||
}
|
||||
final TypeAdapter<JsonElement> elementAdapter = gson.getAdapter(JsonElement.class);
|
||||
{{#anyOf}}
|
||||
final TypeAdapter<{{.}}> adapter{{.}} = gson.getDelegateAdapter(this, TypeToken.get({{.}}.class));
|
||||
{{/anyOf}}
|
||||
|
||||
return (TypeAdapter<T>) new TypeAdapter<{{classname}}>() {
|
||||
@Override
|
||||
public void write(JsonWriter out, {{classname}} value) throws IOException {
|
||||
{{#anyOf}}
|
||||
// check if the actual instance is of the type `{{.}}`
|
||||
if (value.getActualInstance() instanceof {{.}}) {
|
||||
JsonObject obj = adapter{{.}}.toJsonTree(({{.}})value.getActualInstance()).getAsJsonObject();
|
||||
elementAdapter.write(out, obj);
|
||||
}
|
||||
|
||||
{{/anyOf}}
|
||||
throw new IOException("Failed to deserialize as the type doesn't match anyOf schemas: {{#anyOf}}{{{.}}}{{^-last}}, {{/-last}}{{/anyOf}}");
|
||||
}
|
||||
|
||||
@Override
|
||||
public {{classname}} read(JsonReader in) throws IOException {
|
||||
Object deserialized = null;
|
||||
{{#useOneOfDiscriminatorLookup}}
|
||||
{{#discriminator}}
|
||||
// use discriminator value for faster anyOf lookup
|
||||
{{classname}} new{{classname}} = new {{classname}}();
|
||||
String discriminatorValue = elementAdapter.read(in).getAsJsonObject().get("{{{propertyBaseName}}}").getAsString();
|
||||
switch (discriminatorValue) {
|
||||
{{#mappedModels}}
|
||||
case "{{{mappingName}}}":
|
||||
deserialized = gson.fromJson(in, {{{modelName}}}.class);
|
||||
new{{classname}}.setActualInstance(deserialized);
|
||||
return new{{classname}};
|
||||
{{/mappedModels}}
|
||||
default:
|
||||
log.log(Level.WARNING, String.format("Failed to lookup discriminator value `%s` for {{classname}}. Possible values:{{#mappedModels}} {{{mappingName}}}{{/mappedModels}}", discriminatorValue));
|
||||
}
|
||||
|
||||
{{/discriminator}}
|
||||
{{/useOneOfDiscriminatorLookup}}
|
||||
|
||||
{{#anyOf}}
|
||||
// deserialize {{{.}}}
|
||||
try {
|
||||
deserialized = gson.fromJson(in, {{.}}.class);
|
||||
log.log(Level.FINER, "Input data matches schema '{{{.}}}'");
|
||||
{{classname}} ret = new {{classname}}();
|
||||
ret.setActualInstance(deserialized);
|
||||
return ret;
|
||||
} catch (Exception e) {
|
||||
// deserialization failed, continue
|
||||
log.log(Level.FINER, "Input data does not match schema '{{{.}}}'", e);
|
||||
}
|
||||
|
||||
{{/anyOf}}
|
||||
throw new IOException("Failed deserialization for {{classname}}: no match found.");
|
||||
}
|
||||
}.nullSafe();
|
||||
}
|
||||
}
|
||||
|
||||
// store a list of schema names defined in anyOf
|
||||
public static final Map<String, GenericType> schemas = new HashMap<String, GenericType>();
|
||||
|
||||
public {{classname}}() {
|
||||
super("anyOf", {{#isNullable}}Boolean.TRUE{{/isNullable}}{{^isNullable}}Boolean.FALSE{{/isNullable}});
|
||||
}
|
||||
|
||||
{{#anyOf}}
|
||||
public {{classname}}({{{.}}} o) {
|
||||
super("anyOf", {{#isNullable}}Boolean.TRUE{{/isNullable}}{{^isNullable}}Boolean.FALSE{{/isNullable}});
|
||||
setActualInstance(o);
|
||||
}
|
||||
|
||||
{{/anyOf}}
|
||||
static {
|
||||
{{#anyOf}}
|
||||
schemas.put("{{{.}}}", new GenericType<{{{.}}}>() {
|
||||
});
|
||||
{{/anyOf}}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, GenericType> getSchemas() {
|
||||
return {{classname}}.schemas;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the instance that matches the anyOf child schema, check
|
||||
* the instance parameter is valid against the anyOf child schemas:
|
||||
* {{#anyOf}}{{{.}}}{{^-last}}, {{/-last}}{{/anyOf}}
|
||||
*
|
||||
* It could be an instance of the 'anyOf' schemas.
|
||||
* The anyOf child schemas may themselves be a composed schema (allOf, anyOf, anyOf).
|
||||
*/
|
||||
@Override
|
||||
public void setActualInstance(Object instance) {
|
||||
{{#isNullable}}
|
||||
if (instance == null) {
|
||||
super.setActualInstance(instance);
|
||||
return;
|
||||
}
|
||||
|
||||
{{/isNullable}}
|
||||
{{#anyOf}}
|
||||
if (instance instanceof {{{.}}}) {
|
||||
super.setActualInstance(instance);
|
||||
return;
|
||||
}
|
||||
|
||||
{{/anyOf}}
|
||||
throw new RuntimeException("Invalid instance type. Must be {{#anyOf}}{{{.}}}{{^-last}}, {{/-last}}{{/anyOf}}");
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the actual instance, which can be the following:
|
||||
* {{#anyOf}}{{{.}}}{{^-last}}, {{/-last}}{{/anyOf}}
|
||||
*
|
||||
* @return The actual instance ({{#anyOf}}{{{.}}}{{^-last}}, {{/-last}}{{/anyOf}})
|
||||
*/
|
||||
@Override
|
||||
public Object getActualInstance() {
|
||||
return super.getActualInstance();
|
||||
}
|
||||
|
||||
{{#anyOf}}
|
||||
/**
|
||||
* Get the actual instance of `{{{.}}}`. If the actual instance is not `{{{.}}}`,
|
||||
* the ClassCastException will be thrown.
|
||||
*
|
||||
* @return The actual instance of `{{{.}}}`
|
||||
* @throws ClassCastException if the instance is not `{{{.}}}`
|
||||
*/
|
||||
public {{{.}}} get{{{.}}}() throws ClassCastException {
|
||||
return ({{{.}}})super.getActualInstance();
|
||||
}
|
||||
|
||||
{{/anyOf}}
|
||||
}
|
500
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/api.mustache
vendored
Normal file
500
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/api.mustache
vendored
Normal file
@ -0,0 +1,500 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{package}};
|
||||
|
||||
import {{invokerPackage}}.ApiCallback;
|
||||
import {{invokerPackage}}.ApiClient;
|
||||
import {{invokerPackage}}.ApiException;
|
||||
{{#dynamicOperations}}
|
||||
import {{invokerPackage}}.ApiOperation;
|
||||
{{/dynamicOperations}}
|
||||
import {{invokerPackage}}.ApiResponse;
|
||||
import {{invokerPackage}}.Configuration;
|
||||
import {{invokerPackage}}.Pair;
|
||||
import {{invokerPackage}}.ProgressRequestBody;
|
||||
import {{invokerPackage}}.ProgressResponseBody;
|
||||
{{#performBeanValidation}}
|
||||
import {{invokerPackage}}.BeanValidationException;
|
||||
{{/performBeanValidation}}
|
||||
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
{{#dynamicOperations}}
|
||||
import io.swagger.v3.oas.models.Operation;
|
||||
import io.swagger.v3.oas.models.parameters.Parameter;
|
||||
{{/dynamicOperations}}
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
{{#useBeanValidation}}
|
||||
import javax.validation.constraints.*;
|
||||
{{/useBeanValidation}}
|
||||
{{#performBeanValidation}}
|
||||
import javax.validation.ConstraintViolation;
|
||||
import javax.validation.Validation;
|
||||
import javax.validation.ValidatorFactory;
|
||||
import javax.validation.executable.ExecutableValidator;
|
||||
import java.util.Set;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Type;
|
||||
{{/performBeanValidation}}
|
||||
|
||||
{{#imports}}import {{import}};
|
||||
{{/imports}}
|
||||
|
||||
import java.lang.reflect.Type;
|
||||
{{^fullJavaUtil}}
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
{{#supportStreaming}}
|
||||
import java.io.InputStream;
|
||||
{{/supportStreaming}}
|
||||
{{/fullJavaUtil}}
|
||||
|
||||
{{#operations}}
|
||||
public class {{classname}} {
|
||||
private ApiClient localVarApiClient;
|
||||
|
||||
public {{classname}}() {
|
||||
this(Configuration.getDefaultApiClient());
|
||||
}
|
||||
|
||||
public {{classname}}(ApiClient apiClient) {
|
||||
this.localVarApiClient = apiClient;
|
||||
}
|
||||
|
||||
public ApiClient getApiClient() {
|
||||
return localVarApiClient;
|
||||
}
|
||||
|
||||
public void setApiClient(ApiClient apiClient) {
|
||||
this.localVarApiClient = apiClient;
|
||||
}
|
||||
|
||||
{{#operation}}
|
||||
{{^vendorExtensions.x-group-parameters}}/**
|
||||
* Build call for {{operationId}}{{#allParams}}
|
||||
* @param {{paramName}} {{description}}{{#required}} (required){{/required}}{{^required}} (optional{{^isContainer}}{{#defaultValue}}, default to {{.}}{{/defaultValue}}{{/isContainer}}){{/required}}{{/allParams}}
|
||||
* @param _callback Callback for upload/download progress
|
||||
* @return Call to execute
|
||||
* @throws ApiException If fail to serialize the request body object
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
{{#externalDocs}}
|
||||
* {{description}}
|
||||
* @see <a href="{{url}}">{{summary}} Documentation</a>
|
||||
{{/externalDocs}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}private{{/vendorExtensions.x-group-parameters}} okhttp3.Call {{operationId}}Call({{#allParams}}{{{dataType}}} {{paramName}}, {{/allParams}}final ApiCallback _callback) throws ApiException {
|
||||
Object localVarPostBody = {{#bodyParam}}{{paramName}}{{/bodyParam}}{{^bodyParam}}null{{/bodyParam}};
|
||||
|
||||
// create path and map variables
|
||||
{{^dynamicOperations}}
|
||||
String localVarPath = "{{{path}}}"{{#pathParams}}
|
||||
.replaceAll("\\{" + "{{baseName}}" + "\\}", localVarApiClient.escapeString({{#collectionFormat}}localVarApiClient.collectionPathParameterToString("{{{collectionFormat}}}", {{{paramName}}}){{/collectionFormat}}{{^collectionFormat}}{{{paramName}}}.toString(){{/collectionFormat}})){{/pathParams}};
|
||||
{{/dynamicOperations}}
|
||||
{{#dynamicOperations}}
|
||||
ApiOperation apiOperation = localVarApiClient.getOperationLookupMap().get("{{{operationId}}}");
|
||||
if (apiOperation == null) {
|
||||
throw new ApiException("Operation not found in OAS");
|
||||
}
|
||||
Operation operation = apiOperation.getOperation();
|
||||
String localVarPath = apiOperation.getPath();
|
||||
Map<String, Object> paramMap = new HashMap<>();
|
||||
{{#allParams}}
|
||||
{{^isFormParam}}
|
||||
{{^isBodyParam}}
|
||||
paramMap.put("{{baseName}}", {{paramName}});
|
||||
{{/isBodyParam}}
|
||||
{{/isFormParam}}
|
||||
{{/allParams}}
|
||||
{{/dynamicOperations}}
|
||||
|
||||
{{javaUtilPrefix}}List<Pair> localVarQueryParams = new {{javaUtilPrefix}}ArrayList<Pair>();
|
||||
{{javaUtilPrefix}}List<Pair> localVarCollectionQueryParams = new {{javaUtilPrefix}}ArrayList<Pair>();
|
||||
{{javaUtilPrefix}}Map<String, String> localVarHeaderParams = new {{javaUtilPrefix}}HashMap<String, String>();
|
||||
{{javaUtilPrefix}}Map<String, String> localVarCookieParams = new {{javaUtilPrefix}}HashMap<String, String>();
|
||||
{{javaUtilPrefix}}Map<String, Object> localVarFormParams = new {{javaUtilPrefix}}HashMap<String, Object>();
|
||||
|
||||
{{#formParams}}
|
||||
if ({{paramName}} != null) {
|
||||
localVarFormParams.put("{{baseName}}", {{paramName}});
|
||||
}
|
||||
|
||||
{{/formParams}}
|
||||
{{^dynamicOperations}}
|
||||
{{#queryParams}}
|
||||
if ({{paramName}} != null) {
|
||||
{{#collectionFormat}}localVarCollectionQueryParams.addAll(localVarApiClient.parameterToPairs("{{{.}}}", {{/collectionFormat}}{{^collectionFormat}}localVarQueryParams.addAll(localVarApiClient.parameterToPair({{/collectionFormat}}"{{baseName}}", {{paramName}}));
|
||||
}
|
||||
|
||||
{{/queryParams}}
|
||||
{{#headerParams}}
|
||||
if ({{paramName}} != null) {
|
||||
localVarHeaderParams.put("{{baseName}}", localVarApiClient.parameterToString({{paramName}}));
|
||||
}
|
||||
|
||||
{{/headerParams}}
|
||||
{{#cookieParams}}
|
||||
if ({{paramName}} != null) {
|
||||
localVarCookieParams.put("{{baseName}}", localVarApiClient.parameterToString({{paramName}}));
|
||||
}
|
||||
|
||||
{{/cookieParams}}
|
||||
{{/dynamicOperations}}
|
||||
{{#dynamicOperations}}
|
||||
localVarPath = localVarApiClient.fillParametersFromOperation(operation, paramMap, localVarPath, localVarQueryParams, localVarCollectionQueryParams, localVarHeaderParams, localVarCookieParams);
|
||||
|
||||
{{/dynamicOperations}}
|
||||
final String[] localVarAccepts = {
|
||||
{{#produces}}"{{{mediaType}}}"{{^-last}}, {{/-last}}{{/produces}}
|
||||
};
|
||||
final String localVarAccept = localVarApiClient.selectHeaderAccept(localVarAccepts);
|
||||
if (localVarAccept != null) {
|
||||
localVarHeaderParams.put("Accept", localVarAccept);
|
||||
}
|
||||
|
||||
final String[] localVarContentTypes = {
|
||||
{{#consumes}}"{{{mediaType}}}"{{^-last}}, {{/-last}}{{/consumes}}
|
||||
};
|
||||
final String localVarContentType = localVarApiClient.selectHeaderContentType(localVarContentTypes);
|
||||
if (localVarHeaderParams != null) {
|
||||
localVarHeaderParams.put("Content-Type", localVarContentType);
|
||||
}
|
||||
|
||||
String[] localVarAuthNames = new String[] { {{#authMethods}}"{{name}}"{{^-last}}, {{/-last}}{{/authMethods}} };
|
||||
return localVarApiClient.buildCall(localVarPath, {{^dynamicOperations}}"{{httpMethod}}"{{/dynamicOperations}}{{#dynamicOperations}}apiOperation.getMethod(){{/dynamicOperations}}, localVarQueryParams, localVarCollectionQueryParams, localVarPostBody, localVarHeaderParams, localVarCookieParams, localVarFormParams, localVarAuthNames, _callback);
|
||||
}
|
||||
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
@SuppressWarnings("rawtypes")
|
||||
private okhttp3.Call {{operationId}}ValidateBeforeCall({{#allParams}}{{{dataType}}} {{paramName}}, {{/allParams}}final ApiCallback _callback) throws ApiException {
|
||||
{{^performBeanValidation}}
|
||||
{{#allParams}}{{#required}}
|
||||
// verify the required parameter '{{paramName}}' is set
|
||||
if ({{paramName}} == null) {
|
||||
throw new ApiException("Missing the required parameter '{{paramName}}' when calling {{operationId}}(Async)");
|
||||
}
|
||||
{{/required}}{{/allParams}}
|
||||
|
||||
okhttp3.Call localVarCall = {{operationId}}Call({{#allParams}}{{paramName}}, {{/allParams}}_callback);
|
||||
return localVarCall;
|
||||
|
||||
{{/performBeanValidation}}
|
||||
{{#performBeanValidation}}
|
||||
try {
|
||||
ValidatorFactory factory = Validation.buildDefaultValidatorFactory();
|
||||
ExecutableValidator executableValidator = factory.getValidator().forExecutables();
|
||||
|
||||
Object[] parameterValues = { {{#allParams}}{{paramName}}{{^-last}}, {{/-last}}{{/allParams}} };
|
||||
Method method = this.getClass().getMethod("{{operationId}}WithHttpInfo"{{#allParams}}, {{#isArray}}java.util.List{{/isArray}}{{#isMap}}java.util.Map{{/isMap}}{{^isArray}}{{^isMap}}{{{dataType}}}{{/isMap}}{{/isArray}}.class{{/allParams}});
|
||||
Set<ConstraintViolation<{{classname}}>> violations = executableValidator.validateParameters(this, method,
|
||||
parameterValues);
|
||||
|
||||
if (violations.size() == 0) {
|
||||
okhttp3.Call localVarCall = {{operationId}}Call({{#allParams}}{{paramName}}, {{/allParams}}_callback);
|
||||
return localVarCall;
|
||||
|
||||
} else {
|
||||
throw new BeanValidationException((Set) violations);
|
||||
}
|
||||
} catch (NoSuchMethodException e) {
|
||||
e.printStackTrace();
|
||||
throw new ApiException(e.getMessage());
|
||||
} catch (SecurityException e) {
|
||||
e.printStackTrace();
|
||||
throw new ApiException(e.getMessage());
|
||||
}
|
||||
|
||||
{{/performBeanValidation}}
|
||||
}
|
||||
|
||||
{{^vendorExtensions.x-group-parameters}}
|
||||
/**
|
||||
* {{summary}}
|
||||
* {{notes}}{{#allParams}}
|
||||
* @param {{paramName}} {{description}}{{#required}} (required){{/required}}{{^required}} (optional{{^isContainer}}{{#defaultValue}}, default to {{.}}{{/defaultValue}}{{/isContainer}}){{/required}}{{/allParams}}{{#returnType}}
|
||||
* @return {{.}}{{/returnType}}
|
||||
* @throws ApiException If fail to call the API, e.g. server error or cannot deserialize the response body
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
{{#externalDocs}}
|
||||
* {{description}}
|
||||
* @see <a href="{{url}}">{{summary}} Documentation</a>
|
||||
{{/externalDocs}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
{{#vendorExtensions.x-streaming}}
|
||||
public {{#returnType}}InputStream {{/returnType}}{{^returnType}}void {{/returnType}}{{operationId}}({{#allParams}}{{{dataType}}} {{paramName}}{{^-last}}, {{/-last}}{{/allParams}}) throws ApiException {
|
||||
{{#returnType}}InputStream localVarResp = {{/returnType}}{{operationId}}WithHttpInfo({{#allParams}}{{paramName}}{{^-last}}, {{/-last}}{{/allParams}});{{#returnType}}
|
||||
return localVarResp;{{/returnType}}
|
||||
}
|
||||
{{/vendorExtensions.x-streaming}}
|
||||
{{^vendorExtensions.x-streaming}}
|
||||
public {{#returnType}}{{{.}}} {{/returnType}}{{^returnType}}void {{/returnType}}{{operationId}}({{#allParams}}{{{dataType}}} {{paramName}}{{^-last}}, {{/-last}}{{/allParams}}) throws ApiException {
|
||||
{{#returnType}}ApiResponse<{{{.}}}> localVarResp = {{/returnType}}{{operationId}}WithHttpInfo({{#allParams}}{{paramName}}{{^-last}}, {{/-last}}{{/allParams}});{{#returnType}}
|
||||
return localVarResp.getData();{{/returnType}}
|
||||
}
|
||||
{{/vendorExtensions.x-streaming}}
|
||||
{{/vendorExtensions.x-group-parameters}}
|
||||
|
||||
{{^vendorExtensions.x-group-parameters}}/**
|
||||
* {{summary}}
|
||||
* {{notes}}{{#allParams}}
|
||||
* @param {{paramName}} {{description}}{{#required}} (required){{/required}}{{^required}} (optional{{^isContainer}}{{#defaultValue}}, default to {{.}}{{/defaultValue}}{{/isContainer}}){{/required}}{{/allParams}}
|
||||
* @return ApiResponse<{{returnType}}{{^returnType}}Void{{/returnType}}>
|
||||
* @throws ApiException If fail to call the API, e.g. server error or cannot deserialize the response body
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
{{#externalDocs}}
|
||||
* {{description}}
|
||||
* @see <a href="{{url}}">{{summary}} Documentation</a>
|
||||
{{/externalDocs}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}private{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-streaming}} InputStream {{operationId}}WithHttpInfo({{#allParams}}{{#useBeanValidation}}{{>beanValidationQueryParams}}{{/useBeanValidation}}{{{dataType}}} {{paramName}}{{^-last}}, {{/-last}}{{/allParams}}) throws ApiException {
|
||||
okhttp3.Call localVarCall = {{operationId}}ValidateBeforeCall({{#allParams}}{{paramName}}, {{/allParams}}null);
|
||||
{{#returnType}}Type localVarReturnType = new TypeToken<{{{returnType}}}>(){}.getType();
|
||||
return localVarApiClient.executeStream(localVarCall, localVarReturnType);{{/returnType}}
|
||||
}
|
||||
{{/vendorExtensions.x-streaming}}{{^vendorExtensions.x-streaming}} ApiResponse<{{#returnType}}{{{returnType}}}{{/returnType}}{{^returnType}}Void{{/returnType}}> {{operationId}}WithHttpInfo({{#allParams}}{{#useBeanValidation}}{{>beanValidationQueryParams}}{{/useBeanValidation}}{{{dataType}}} {{paramName}}{{^-last}}, {{/-last}}{{/allParams}}) throws ApiException {
|
||||
okhttp3.Call localVarCall = {{operationId}}ValidateBeforeCall({{#allParams}}{{paramName}}, {{/allParams}}null);
|
||||
{{#returnType}}Type localVarReturnType = new TypeToken<{{{returnType}}}>(){}.getType();
|
||||
return localVarApiClient.execute(localVarCall, localVarReturnType);{{/returnType}}{{^returnType}}return localVarApiClient.execute(localVarCall);{{/returnType}}
|
||||
}
|
||||
{{/vendorExtensions.x-streaming}}
|
||||
|
||||
{{^vendorExtensions.x-group-parameters}}/**
|
||||
* {{summary}} (asynchronously)
|
||||
* {{notes}}{{#allParams}}
|
||||
* @param {{paramName}} {{description}}{{#required}} (required){{/required}}{{^required}} (optional{{^isContainer}}{{#defaultValue}}, default to {{.}}{{/defaultValue}}{{/isContainer}}){{/required}}{{/allParams}}
|
||||
* @param _callback The callback to be executed when the API call finishes
|
||||
* @return The request call
|
||||
* @throws ApiException If fail to process the API call, e.g. serializing the request body object
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
{{#externalDocs}}
|
||||
* {{description}}
|
||||
* @see <a href="{{url}}">{{summary}} Documentation</a>
|
||||
{{/externalDocs}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}private{{/vendorExtensions.x-group-parameters}} okhttp3.Call {{operationId}}Async({{#allParams}}{{{dataType}}} {{paramName}}, {{/allParams}}final ApiCallback<{{{returnType}}}{{^returnType}}Void{{/returnType}}> _callback) throws ApiException {
|
||||
|
||||
okhttp3.Call localVarCall = {{operationId}}ValidateBeforeCall({{#allParams}}{{paramName}}, {{/allParams}}_callback);
|
||||
{{#returnType}}Type localVarReturnType = new TypeToken<{{{returnType}}}>(){}.getType();
|
||||
localVarApiClient.executeAsync(localVarCall, localVarReturnType, _callback);{{/returnType}}{{^returnType}}localVarApiClient.executeAsync(localVarCall, _callback);{{/returnType}}
|
||||
return localVarCall;
|
||||
}
|
||||
{{#vendorExtensions.x-group-parameters}}
|
||||
|
||||
public class API{{operationId}}Request {
|
||||
{{#requiredParams}}
|
||||
private final {{{dataType}}} {{paramName}};
|
||||
{{/requiredParams}}
|
||||
{{#optionalParams}}
|
||||
private {{{dataType}}} {{paramName}};
|
||||
{{/optionalParams}}
|
||||
|
||||
private API{{operationId}}Request({{#requiredParams}}{{{dataType}}} {{paramName}}{{^-last}}, {{/-last}}{{/requiredParams}}) {
|
||||
{{#requiredParams}}
|
||||
this.{{paramName}} = {{paramName}};
|
||||
{{/requiredParams}}
|
||||
}
|
||||
|
||||
{{#optionalParams}}
|
||||
/**
|
||||
* Set {{paramName}}
|
||||
* @param {{paramName}} {{description}} (optional{{^isContainer}}{{#defaultValue}}, default to {{.}}{{/defaultValue}}{{/isContainer}})
|
||||
* @return API{{operationId}}Request
|
||||
*/
|
||||
public API{{operationId}}Request {{paramName}}({{{dataType}}} {{paramName}}) {
|
||||
this.{{paramName}} = {{paramName}};
|
||||
return this;
|
||||
}
|
||||
|
||||
{{/optionalParams}}
|
||||
/**
|
||||
* Build call for {{operationId}}
|
||||
* @param _callback ApiCallback API callback
|
||||
* @return Call to execute
|
||||
* @throws ApiException If fail to serialize the request body object
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public okhttp3.Call buildCall(final ApiCallback _callback) throws ApiException {
|
||||
return {{operationId}}Call({{#allParams}}{{paramName}}, {{/allParams}}_callback);
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute {{operationId}} request{{#returnType}}
|
||||
* @return {{.}}{{/returnType}}
|
||||
* @throws ApiException If fail to call the API, e.g. server error or cannot deserialize the response body
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public {{{returnType}}}{{^returnType}}void{{/returnType}} execute() throws ApiException {
|
||||
{{#returnType}}ApiResponse<{{{.}}}> localVarResp = {{/returnType}}{{operationId}}WithHttpInfo({{#allParams}}{{paramName}}{{^-last}}, {{/-last}}{{/allParams}});{{#returnType}}
|
||||
return localVarResp.getData();{{/returnType}}
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute {{operationId}} request with HTTP info returned
|
||||
* @return ApiResponse<{{returnType}}{{^returnType}}Void{{/returnType}}>
|
||||
* @throws ApiException If fail to call the API, e.g. server error or cannot deserialize the response body
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public ApiResponse<{{{returnType}}}{{^returnType}}Void{{/returnType}}> executeWithHttpInfo() throws ApiException {
|
||||
return {{operationId}}WithHttpInfo({{#allParams}}{{paramName}}{{^-last}}, {{/-last}}{{/allParams}});
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute {{operationId}} request (asynchronously)
|
||||
* @param _callback The callback to be executed when the API call finishes
|
||||
* @return The request call
|
||||
* @throws ApiException If fail to process the API call, e.g. serializing the request body object
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public okhttp3.Call executeAsync(final ApiCallback<{{{returnType}}}{{^returnType}}Void{{/returnType}}> _callback) throws ApiException {
|
||||
return {{operationId}}Async({{#allParams}}{{paramName}}, {{/allParams}}_callback);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* {{summary}}
|
||||
* {{notes}}{{#requiredParams}}
|
||||
* @param {{paramName}} {{description}} (required){{/requiredParams}}
|
||||
* @return API{{operationId}}Request
|
||||
{{#responses.0}}
|
||||
* @http.response.details
|
||||
<table summary="Response Details" border="1">
|
||||
<tr><td> Status Code </td><td> Description </td><td> Response Headers </td></tr>
|
||||
{{#responses}}
|
||||
<tr><td> {{code}} </td><td> {{message}} </td><td> {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} </td></tr>
|
||||
{{/responses}}
|
||||
</table>
|
||||
{{/responses.0}}
|
||||
{{#isDeprecated}}
|
||||
* @deprecated
|
||||
{{/isDeprecated}}
|
||||
{{#externalDocs}}
|
||||
* {{description}}
|
||||
* @see <a href="{{url}}">{{summary}} Documentation</a>
|
||||
{{/externalDocs}}
|
||||
*/
|
||||
{{#isDeprecated}}
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public API{{operationId}}Request {{operationId}}({{#requiredParams}}{{{dataType}}} {{paramName}}{{^-last}}, {{/-last}}{{/requiredParams}}) {
|
||||
return new API{{operationId}}Request({{#requiredParams}}{{paramName}}{{^-last}}, {{/-last}}{{/requiredParams}});
|
||||
}
|
||||
{{/vendorExtensions.x-group-parameters}}
|
||||
{{/operation}}
|
||||
}
|
||||
{{/operations}}
|
@ -0,0 +1,159 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}};
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
{{#caseInsensitiveResponseHeaders}}
|
||||
import java.util.Map.Entry;
|
||||
import java.util.TreeMap;
|
||||
{{/caseInsensitiveResponseHeaders}}
|
||||
|
||||
/**
|
||||
* <p>ApiException class.</p>
|
||||
*/
|
||||
@SuppressWarnings("serial")
|
||||
{{>generatedAnnotation}}
|
||||
public class ApiException extends{{#useRuntimeException}} RuntimeException {{/useRuntimeException}}{{^useRuntimeException}} Exception {{/useRuntimeException}}{
|
||||
private int code = 0;
|
||||
private Map<String, List<String>> responseHeaders = null;
|
||||
private String responseBody = null;
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*/
|
||||
public ApiException() {}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*
|
||||
* @param throwable a {@link java.lang.Throwable} object
|
||||
*/
|
||||
public ApiException(Throwable throwable) {
|
||||
super(throwable);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*
|
||||
* @param message the error message
|
||||
*/
|
||||
public ApiException(String message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*
|
||||
* @param message the error message
|
||||
* @param throwable a {@link java.lang.Throwable} object
|
||||
* @param code HTTP status code
|
||||
* @param responseHeaders a {@link java.util.Map} of HTTP response headers
|
||||
* @param responseBody the response body
|
||||
*/
|
||||
public ApiException(String message, Throwable throwable, int code, Map<String, List<String>> responseHeaders, String responseBody) {
|
||||
super(message, throwable);
|
||||
this.code = code;
|
||||
{{#caseInsensitiveResponseHeaders}}
|
||||
Map<String, List<String>> headers = new TreeMap<String, List<String>>(String.CASE_INSENSITIVE_ORDER);
|
||||
for(Entry<String, List<String>> entry : responseHeaders.entrySet()){
|
||||
headers.put(entry.getKey().toLowerCase(), entry.getValue());
|
||||
}
|
||||
{{/caseInsensitiveResponseHeaders}}
|
||||
this.responseHeaders = {{#caseInsensitiveResponseHeaders}}headers{{/caseInsensitiveResponseHeaders}}{{^caseInsensitiveResponseHeaders}}responseHeaders{{/caseInsensitiveResponseHeaders}};
|
||||
this.responseBody = responseBody;
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*
|
||||
* @param message the error message
|
||||
* @param code HTTP status code
|
||||
* @param responseHeaders a {@link java.util.Map} of HTTP response headers
|
||||
* @param responseBody the response body
|
||||
*/
|
||||
public ApiException(String message, int code, Map<String, List<String>> responseHeaders, String responseBody) {
|
||||
this(message, (Throwable) null, code, responseHeaders, responseBody);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*
|
||||
* @param message the error message
|
||||
* @param throwable a {@link java.lang.Throwable} object
|
||||
* @param code HTTP status code
|
||||
* @param responseHeaders a {@link java.util.Map} of HTTP response headers
|
||||
*/
|
||||
public ApiException(String message, Throwable throwable, int code, Map<String, List<String>> responseHeaders) {
|
||||
this(message, throwable, code, responseHeaders, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*
|
||||
* @param code HTTP status code
|
||||
* @param responseHeaders a {@link java.util.Map} of HTTP response headers
|
||||
* @param responseBody the response body
|
||||
*/
|
||||
public ApiException(int code, Map<String, List<String>> responseHeaders, String responseBody) {
|
||||
this((String) null, (Throwable) null, code, responseHeaders, responseBody);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*
|
||||
* @param code HTTP status code
|
||||
* @param message a {@link java.lang.String} object
|
||||
*/
|
||||
public ApiException(int code, String message) {
|
||||
super(message);
|
||||
this.code = code;
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Constructor for ApiException.</p>
|
||||
*
|
||||
* @param code HTTP status code
|
||||
* @param message the error message
|
||||
* @param responseHeaders a {@link java.util.Map} of HTTP response headers
|
||||
* @param responseBody the response body
|
||||
*/
|
||||
public ApiException(int code, String message, Map<String, List<String>> responseHeaders, String responseBody) {
|
||||
this(code, message);
|
||||
{{#caseInsensitiveResponseHeaders}}
|
||||
Map<String, List<String>> headers = new TreeMap<String, List<String>>(String.CASE_INSENSITIVE_ORDER);
|
||||
for(Entry<String, List<String>> entry : responseHeaders.entrySet()){
|
||||
headers.put(entry.getKey().toLowerCase(), entry.getValue());
|
||||
}
|
||||
{{/caseInsensitiveResponseHeaders}}
|
||||
this.responseHeaders = {{#caseInsensitiveResponseHeaders}}headers{{/caseInsensitiveResponseHeaders}}{{^caseInsensitiveResponseHeaders}}responseHeaders{{/caseInsensitiveResponseHeaders}};
|
||||
this.responseBody = responseBody;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the HTTP status code.
|
||||
*
|
||||
* @return HTTP status code
|
||||
*/
|
||||
public int getCode() {
|
||||
return code;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the HTTP response headers.
|
||||
*
|
||||
* @return A map of list of string
|
||||
*/
|
||||
public Map<String, List<String>> getResponseHeaders() {
|
||||
return responseHeaders;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the HTTP response body.
|
||||
*
|
||||
* @return Response body in the form of string
|
||||
*/
|
||||
public String getResponseBody() {
|
||||
return responseBody;
|
||||
}
|
||||
}
|
106
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/api_doc.mustache
vendored
Normal file
106
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/api_doc.mustache
vendored
Normal file
@ -0,0 +1,106 @@
|
||||
# {{classname}}{{#description}}
|
||||
{{.}}{{/description}}
|
||||
|
||||
All URIs are relative to *{{basePath}}*
|
||||
|
||||
Method | HTTP request | Description
|
||||
------------- | ------------- | -------------
|
||||
{{#operations}}{{#operation}}[**{{operationId}}**]({{classname}}.md#{{operationId}}) | **{{httpMethod}}** {{path}} | {{summary}}
|
||||
{{/operation}}{{/operations}}
|
||||
|
||||
{{#operations}}
|
||||
{{#operation}}
|
||||
<a name="{{operationId}}"></a>
|
||||
# **{{operationId}}**{{^vendorExtensions.x-group-parameters}}
|
||||
> {{#returnType}}{{.}} {{/returnType}}{{operationId}}({{#allParams}}{{{paramName}}}{{^-last}}, {{/-last}}{{/allParams}}){{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}
|
||||
> {{#returnType}}{{.}} {{/returnType}}{{operationId}}({{#requiredParams}}{{paramName}}{{^-last}}, {{/-last}}{{/requiredParams}}){{#optionalParams}}.{{paramName}}({{paramName}}){{/optionalParams}}.execute();{{/vendorExtensions.x-group-parameters}}
|
||||
|
||||
{{summary}}{{#notes}}
|
||||
|
||||
{{.}}{{/notes}}
|
||||
|
||||
### Example
|
||||
```java
|
||||
// Import classes:
|
||||
import {{{invokerPackage}}}.ApiClient;
|
||||
import {{{invokerPackage}}}.ApiException;
|
||||
import {{{invokerPackage}}}.Configuration;{{#hasAuthMethods}}
|
||||
import {{{invokerPackage}}}.auth.*;{{/hasAuthMethods}}
|
||||
import {{{invokerPackage}}}.models.*;
|
||||
import {{{package}}}.{{{classname}}};
|
||||
|
||||
public class Example {
|
||||
public static void main(String[] args) {
|
||||
ApiClient defaultClient = Configuration.getDefaultApiClient();
|
||||
defaultClient.setBasePath("{{{basePath}}}");
|
||||
{{#hasAuthMethods}}
|
||||
{{#authMethods}}{{#isBasic}}{{#isBasicBasic}}
|
||||
// Configure HTTP basic authorization: {{{name}}}
|
||||
HttpBasicAuth {{{name}}} = (HttpBasicAuth) defaultClient.getAuthentication("{{{name}}}");
|
||||
{{{name}}}.setUsername("YOUR USERNAME");
|
||||
{{{name}}}.setPassword("YOUR PASSWORD");{{/isBasicBasic}}{{#isBasicBearer}}
|
||||
// Configure HTTP bearer authorization: {{{name}}}
|
||||
HttpBearerAuth {{{name}}} = (HttpBearerAuth) defaultClient.getAuthentication("{{{name}}}");
|
||||
{{{name}}}.setBearerToken("BEARER TOKEN");{{/isBasicBearer}}{{/isBasic}}{{#isApiKey}}
|
||||
// Configure API key authorization: {{{name}}}
|
||||
ApiKeyAuth {{{name}}} = (ApiKeyAuth) defaultClient.getAuthentication("{{{name}}}");
|
||||
{{{name}}}.setApiKey("YOUR API KEY");
|
||||
// Uncomment the following line to set a prefix for the API key, e.g. "Token" (defaults to null)
|
||||
//{{{name}}}.setApiKeyPrefix("Token");{{/isApiKey}}{{#isOAuth}}
|
||||
// Configure OAuth2 access token for authorization: {{{name}}}
|
||||
OAuth {{{name}}} = (OAuth) defaultClient.getAuthentication("{{{name}}}");
|
||||
{{{name}}}.setAccessToken("YOUR ACCESS TOKEN");{{/isOAuth}}
|
||||
{{/authMethods}}
|
||||
{{/hasAuthMethods}}
|
||||
|
||||
{{{classname}}} apiInstance = new {{{classname}}}(defaultClient);
|
||||
{{#allParams}}
|
||||
{{{dataType}}} {{{paramName}}} = {{{example}}}; // {{{dataType}}} | {{{description}}}
|
||||
{{/allParams}}
|
||||
try {
|
||||
{{#returnType}}{{{.}}} result = {{/returnType}}apiInstance.{{{operationId}}}{{^vendorExtensions.x-group-parameters}}({{#allParams}}{{{paramName}}}{{^-last}}, {{/-last}}{{/allParams}});{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}({{#requiredParams}}{{{paramName}}}{{^-last}}, {{/-last}}{{/requiredParams}}){{#optionalParams}}
|
||||
.{{{paramName}}}({{{paramName}}}){{/optionalParams}}
|
||||
.execute();{{/vendorExtensions.x-group-parameters}}{{#returnType}}
|
||||
System.out.println(result);{{/returnType}}
|
||||
} catch (ApiException e) {
|
||||
System.err.println("Exception when calling {{{classname}}}#{{{operationId}}}");
|
||||
System.err.println("Status code: " + e.getCode());
|
||||
System.err.println("Reason: " + e.getResponseBody());
|
||||
System.err.println("Response headers: " + e.getResponseHeaders());
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Parameters
|
||||
{{^allParams}}This endpoint does not need any parameter.{{/allParams}}{{#allParams}}{{#-last}}
|
||||
Name | Type | Description | Notes
|
||||
------------- | ------------- | ------------- | -------------{{/-last}}{{/allParams}}
|
||||
{{#allParams}} **{{paramName}}** | {{#isPrimitiveType}}**{{dataType}}**{{/isPrimitiveType}}{{^isPrimitiveType}}{{#isFile}}**{{dataType}}**{{/isFile}}{{^isFile}}[**{{dataType}}**]({{baseType}}.md){{/isFile}}{{/isPrimitiveType}}| {{description}} |{{^required}} [optional]{{/required}}{{^isContainer}}{{#defaultValue}} [default to {{.}}]{{/defaultValue}}{{/isContainer}}{{#allowableValues}} [enum: {{#values}}{{{.}}}{{^-last}}, {{/-last}}{{/values}}]{{/allowableValues}}
|
||||
{{/allParams}}
|
||||
|
||||
### Return type
|
||||
|
||||
{{#returnType}}{{#returnTypeIsPrimitive}}**{{returnType}}**{{/returnTypeIsPrimitive}}{{^returnTypeIsPrimitive}}[**{{returnType}}**]({{returnBaseType}}.md){{/returnTypeIsPrimitive}}{{/returnType}}{{^returnType}}null (empty response body){{/returnType}}
|
||||
|
||||
### Authorization
|
||||
|
||||
{{^authMethods}}No authorization required{{/authMethods}}{{#authMethods}}[{{name}}](../README.md#{{name}}){{^-last}}, {{/-last}}{{/authMethods}}
|
||||
|
||||
### HTTP request headers
|
||||
|
||||
- **Content-Type**: {{#consumes}}{{{mediaType}}}{{^-last}}, {{/-last}}{{/consumes}}{{^consumes}}Not defined{{/consumes}}
|
||||
- **Accept**: {{#produces}}{{{mediaType}}}{{^-last}}, {{/-last}}{{/produces}}{{^produces}}Not defined{{/produces}}
|
||||
|
||||
{{#responses.0}}
|
||||
### HTTP response details
|
||||
| Status code | Description | Response headers |
|
||||
|-------------|-------------|------------------|
|
||||
{{#responses}}
|
||||
**{{code}}** | {{message}} | {{#headers}} * {{baseName}} - {{description}} <br> {{/headers}}{{^headers.0}} - {{/headers.0}} |
|
||||
{{/responses}}
|
||||
{{/responses.0}}
|
||||
|
||||
{{/operation}}
|
||||
{{/operations}}
|
@ -0,0 +1,56 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{package}};
|
||||
|
||||
import {{invokerPackage}}.ApiException;
|
||||
{{#imports}}import {{import}};
|
||||
{{/imports}}
|
||||
import org.junit.Test;
|
||||
import org.junit.Ignore;
|
||||
|
||||
{{^fullJavaUtil}}
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
{{#supportStreaming}}
|
||||
import java.io.InputStream;
|
||||
{{/supportStreaming}}
|
||||
{{/fullJavaUtil}}
|
||||
|
||||
/**
|
||||
* API tests for {{classname}}
|
||||
*/
|
||||
@Ignore
|
||||
public class {{classname}}Test {
|
||||
|
||||
private final {{classname}} api = new {{classname}}();
|
||||
|
||||
{{#operations}}{{#operation}}
|
||||
/**
|
||||
* {{summary}}
|
||||
*
|
||||
* {{notes}}
|
||||
*
|
||||
* @throws ApiException
|
||||
* if the Api call fails
|
||||
*/
|
||||
@Test
|
||||
public void {{operationId}}Test() throws ApiException {
|
||||
{{#allParams}}
|
||||
{{{dataType}}} {{paramName}} = null;
|
||||
{{/allParams}}
|
||||
{{#vendorExtensions.x-streaming}}
|
||||
InputStream response = api.{{operationId}}{{^vendorExtensions.x-group-parameters}}({{#allParams}}{{paramName}}{{^-last}}, {{/-last}}{{/allParams}});{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}({{#requiredParams}}{{paramName}}{{^-last}}, {{/-last}}{{/requiredParams}}){{#optionalParams}}
|
||||
.{{paramName}}({{paramName}}){{/optionalParams}}
|
||||
.execute();{{/vendorExtensions.x-group-parameters}}
|
||||
{{/vendorExtensions.x-streaming}}
|
||||
{{^vendorExtensions.x-streaming}}
|
||||
{{#returnType}}{{{returnType}}} response = {{/returnType}}api.{{operationId}}{{^vendorExtensions.x-group-parameters}}({{#allParams}}{{paramName}}{{^-last}}, {{/-last}}{{/allParams}});{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}({{#requiredParams}}{{paramName}}{{^-last}}, {{/-last}}{{/requiredParams}}){{#optionalParams}}
|
||||
.{{paramName}}({{paramName}}){{/optionalParams}}
|
||||
.execute();{{/vendorExtensions.x-group-parameters}}
|
||||
{{/vendorExtensions.x-streaming}}
|
||||
// TODO: test validations
|
||||
}
|
||||
{{/operation}}{{/operations}}
|
||||
}
|
@ -0,0 +1,69 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}}.auth;
|
||||
|
||||
import {{invokerPackage}}.ApiException;
|
||||
import {{invokerPackage}}.Pair;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
|
||||
{{>generatedAnnotation}}
|
||||
public class ApiKeyAuth implements Authentication {
|
||||
private final String location;
|
||||
private final String paramName;
|
||||
|
||||
private String apiKey;
|
||||
private String apiKeyPrefix;
|
||||
|
||||
public ApiKeyAuth(String location, String paramName) {
|
||||
this.location = location;
|
||||
this.paramName = paramName;
|
||||
}
|
||||
|
||||
public String getLocation() {
|
||||
return location;
|
||||
}
|
||||
|
||||
public String getParamName() {
|
||||
return paramName;
|
||||
}
|
||||
|
||||
public String getApiKey() {
|
||||
return apiKey;
|
||||
}
|
||||
|
||||
public void setApiKey(String apiKey) {
|
||||
this.apiKey = apiKey;
|
||||
}
|
||||
|
||||
public String getApiKeyPrefix() {
|
||||
return apiKeyPrefix;
|
||||
}
|
||||
|
||||
public void setApiKeyPrefix(String apiKeyPrefix) {
|
||||
this.apiKeyPrefix = apiKeyPrefix;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void applyToParams(List<Pair> queryParams, Map<String, String> headerParams, Map<String, String> cookieParams,
|
||||
String payload, String method, URI uri) throws ApiException {
|
||||
if (apiKey == null) {
|
||||
return;
|
||||
}
|
||||
String value;
|
||||
if (apiKeyPrefix != null) {
|
||||
value = apiKeyPrefix + " " + apiKey;
|
||||
} else {
|
||||
value = apiKey;
|
||||
}
|
||||
if ("query".equals(location)) {
|
||||
queryParams.add(new Pair(paramName, value));
|
||||
} else if ("header".equals(location)) {
|
||||
headerParams.put(paramName, value);
|
||||
} else if ("cookie".equals(location)) {
|
||||
cookieParams.put(paramName, value);
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,25 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}}.auth;
|
||||
|
||||
import {{invokerPackage}}.Pair;
|
||||
import {{invokerPackage}}.ApiException;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
|
||||
public interface Authentication {
|
||||
/**
|
||||
* Apply authentication settings to header and query params.
|
||||
*
|
||||
* @param queryParams List of query parameters
|
||||
* @param headerParams Map of header parameters
|
||||
* @param cookieParams Map of cookie parameters
|
||||
* @param payload HTTP request body
|
||||
* @param method HTTP method
|
||||
* @param uri URI
|
||||
* @throws ApiException if failed to update the parameters
|
||||
*/
|
||||
void applyToParams(List<Pair> queryParams, Map<String, String> headerParams, Map<String, String> cookieParams, String payload, String method, URI uri) throws ApiException;
|
||||
}
|
@ -0,0 +1,46 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}}.auth;
|
||||
|
||||
import {{invokerPackage}}.Pair;
|
||||
import {{invokerPackage}}.ApiException;
|
||||
|
||||
import okhttp3.Credentials;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
|
||||
import java.io.UnsupportedEncodingException;
|
||||
|
||||
public class HttpBasicAuth implements Authentication {
|
||||
private String username;
|
||||
private String password;
|
||||
|
||||
public String getUsername() {
|
||||
return username;
|
||||
}
|
||||
|
||||
public void setUsername(String username) {
|
||||
this.username = username;
|
||||
}
|
||||
|
||||
public String getPassword() {
|
||||
return password;
|
||||
}
|
||||
|
||||
public void setPassword(String password) {
|
||||
this.password = password;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void applyToParams(List<Pair> queryParams, Map<String, String> headerParams, Map<String, String> cookieParams,
|
||||
String payload, String method, URI uri) throws ApiException {
|
||||
if (username == null && password == null) {
|
||||
return;
|
||||
}
|
||||
headerParams.put("Authorization", Credentials.basic(
|
||||
username == null ? "" : username,
|
||||
password == null ? "" : password));
|
||||
}
|
||||
}
|
@ -0,0 +1,52 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}}.auth;
|
||||
|
||||
import {{invokerPackage}}.ApiException;
|
||||
import {{invokerPackage}}.Pair;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
|
||||
{{>generatedAnnotation}}
|
||||
public class HttpBearerAuth implements Authentication {
|
||||
private final String scheme;
|
||||
private String bearerToken;
|
||||
|
||||
public HttpBearerAuth(String scheme) {
|
||||
this.scheme = scheme;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the token, which together with the scheme, will be sent as the value of the Authorization header.
|
||||
*
|
||||
* @return The bearer token
|
||||
*/
|
||||
public String getBearerToken() {
|
||||
return bearerToken;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the token, which together with the scheme, will be sent as the value of the Authorization header.
|
||||
*
|
||||
* @param bearerToken The bearer token to send in the Authorization header
|
||||
*/
|
||||
public void setBearerToken(String bearerToken) {
|
||||
this.bearerToken = bearerToken;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void applyToParams(List<Pair> queryParams, Map<String, String> headerParams, Map<String, String> cookieParams,
|
||||
String payload, String method, URI uri) throws ApiException {
|
||||
if (bearerToken == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
headerParams.put("Authorization", (scheme != null ? upperCaseBearer(scheme) + " " : "") + bearerToken);
|
||||
}
|
||||
|
||||
private static String upperCaseBearer(String scheme) {
|
||||
return ("bearer".equalsIgnoreCase(scheme)) ? "Bearer" : scheme;
|
||||
}
|
||||
}
|
@ -0,0 +1,31 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{invokerPackage}}.auth;
|
||||
|
||||
import {{invokerPackage}}.Pair;
|
||||
import {{invokerPackage}}.ApiException;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
|
||||
{{>generatedAnnotation}}
|
||||
public class OAuth implements Authentication {
|
||||
private String accessToken;
|
||||
|
||||
public String getAccessToken() {
|
||||
return accessToken;
|
||||
}
|
||||
|
||||
public void setAccessToken(String accessToken) {
|
||||
this.accessToken = accessToken;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void applyToParams(List<Pair> queryParams, Map<String, String> headerParams, Map<String, String> cookieParams,
|
||||
String payload, String method, URI uri) throws ApiException {
|
||||
if (accessToken != null) {
|
||||
headerParams.put("Authorization", "Bearer " + accessToken);
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,70 @@
|
||||
{{#hasOAuthMethods}}
|
||||
package {{invokerPackage}}.auth;
|
||||
|
||||
import okhttp3.OkHttpClient;
|
||||
import okhttp3.MediaType;
|
||||
import okhttp3.Request;
|
||||
import okhttp3.RequestBody;
|
||||
import okhttp3.Response;
|
||||
|
||||
import org.apache.oltu.oauth2.client.HttpClient;
|
||||
import org.apache.oltu.oauth2.client.request.OAuthClientRequest;
|
||||
import org.apache.oltu.oauth2.client.response.OAuthClientResponse;
|
||||
import org.apache.oltu.oauth2.client.response.OAuthClientResponseFactory;
|
||||
import org.apache.oltu.oauth2.common.exception.OAuthProblemException;
|
||||
import org.apache.oltu.oauth2.common.exception.OAuthSystemException;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
|
||||
public class OAuthOkHttpClient implements HttpClient {
|
||||
private OkHttpClient client;
|
||||
|
||||
public OAuthOkHttpClient() {
|
||||
this.client = new OkHttpClient();
|
||||
}
|
||||
|
||||
public OAuthOkHttpClient(OkHttpClient client) {
|
||||
this.client = client;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T extends OAuthClientResponse> T execute(OAuthClientRequest request, Map<String, String> headers,
|
||||
String requestMethod, Class<T> responseClass)
|
||||
throws OAuthSystemException, OAuthProblemException {
|
||||
|
||||
MediaType mediaType = MediaType.parse("application/json");
|
||||
Request.Builder requestBuilder = new Request.Builder().url(request.getLocationUri());
|
||||
|
||||
if(headers != null) {
|
||||
for (Entry<String, String> entry : headers.entrySet()) {
|
||||
if (entry.getKey().equalsIgnoreCase("Content-Type")) {
|
||||
mediaType = MediaType.parse(entry.getValue());
|
||||
} else {
|
||||
requestBuilder.addHeader(entry.getKey(), entry.getValue());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RequestBody body = request.getBody() != null ? RequestBody.create(request.getBody(), mediaType) : null;
|
||||
requestBuilder.method(requestMethod, body);
|
||||
|
||||
try {
|
||||
Response response = client.newCall(requestBuilder.build()).execute();
|
||||
return OAuthClientResponseFactory.createCustomResponse(
|
||||
response.body().string(),
|
||||
response.body().contentType().toString(),
|
||||
response.code(),
|
||||
responseClass);
|
||||
} catch (IOException e) {
|
||||
throw new OAuthSystemException(e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void shutdown() {
|
||||
// Nothing to do here
|
||||
}
|
||||
}
|
||||
{{/hasOAuthMethods}}
|
@ -0,0 +1,184 @@
|
||||
{{#hasOAuthMethods}}
|
||||
package {{invokerPackage}}.auth;
|
||||
|
||||
import {{invokerPackage}}.ApiException;
|
||||
import {{invokerPackage}}.Pair;
|
||||
|
||||
import okhttp3.Interceptor;
|
||||
import okhttp3.OkHttpClient;
|
||||
import okhttp3.Request;
|
||||
import okhttp3.Response;
|
||||
|
||||
import org.apache.oltu.oauth2.client.OAuthClient;
|
||||
import org.apache.oltu.oauth2.client.request.OAuthBearerClientRequest;
|
||||
import org.apache.oltu.oauth2.client.request.OAuthClientRequest;
|
||||
import org.apache.oltu.oauth2.client.request.OAuthClientRequest.TokenRequestBuilder;
|
||||
import org.apache.oltu.oauth2.client.response.OAuthJSONAccessTokenResponse;
|
||||
import org.apache.oltu.oauth2.common.exception.OAuthProblemException;
|
||||
import org.apache.oltu.oauth2.common.exception.OAuthSystemException;
|
||||
import org.apache.oltu.oauth2.common.message.types.GrantType;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.net.HttpURLConnection;
|
||||
import java.net.URI;
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
|
||||
public class RetryingOAuth extends OAuth implements Interceptor {
|
||||
private OAuthClient oAuthClient;
|
||||
|
||||
private TokenRequestBuilder tokenRequestBuilder;
|
||||
|
||||
public RetryingOAuth(OkHttpClient client, TokenRequestBuilder tokenRequestBuilder) {
|
||||
this.oAuthClient = new OAuthClient(new OAuthOkHttpClient(client));
|
||||
this.tokenRequestBuilder = tokenRequestBuilder;
|
||||
}
|
||||
|
||||
public RetryingOAuth(TokenRequestBuilder tokenRequestBuilder) {
|
||||
this(new OkHttpClient(), tokenRequestBuilder);
|
||||
}
|
||||
|
||||
/**
|
||||
@param tokenUrl The token URL to be used for this OAuth2 flow.
|
||||
Applicable to the following OAuth2 flows: "password", "clientCredentials" and "authorizationCode".
|
||||
The value must be an absolute URL.
|
||||
@param clientId The OAuth2 client ID for the "clientCredentials" flow.
|
||||
@param clientSecret The OAuth2 client secret for the "clientCredentials" flow.
|
||||
*/
|
||||
public RetryingOAuth(
|
||||
String tokenUrl,
|
||||
String clientId,
|
||||
OAuthFlow flow,
|
||||
String clientSecret,
|
||||
Map<String, String> parameters
|
||||
) {
|
||||
this(OAuthClientRequest.tokenLocation(tokenUrl)
|
||||
.setClientId(clientId)
|
||||
.setClientSecret(clientSecret));
|
||||
setFlow(flow);
|
||||
if (parameters != null) {
|
||||
for (String paramName : parameters.keySet()) {
|
||||
tokenRequestBuilder.setParameter(paramName, parameters.get(paramName));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setFlow(OAuthFlow flow) {
|
||||
switch(flow) {
|
||||
case accessCode:
|
||||
tokenRequestBuilder.setGrantType(GrantType.AUTHORIZATION_CODE);
|
||||
break;
|
||||
case implicit:
|
||||
tokenRequestBuilder.setGrantType(GrantType.IMPLICIT);
|
||||
break;
|
||||
case password:
|
||||
tokenRequestBuilder.setGrantType(GrantType.PASSWORD);
|
||||
break;
|
||||
case application:
|
||||
tokenRequestBuilder.setGrantType(GrantType.CLIENT_CREDENTIALS);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Response intercept(Chain chain) throws IOException {
|
||||
return retryingIntercept(chain, true);
|
||||
}
|
||||
|
||||
private Response retryingIntercept(Chain chain, boolean updateTokenAndRetryOnAuthorizationFailure) throws IOException {
|
||||
Request request = chain.request();
|
||||
|
||||
// If the request already has an authorization (e.g. Basic auth), proceed with the request as is
|
||||
if (request.header("Authorization") != null) {
|
||||
return chain.proceed(request);
|
||||
}
|
||||
|
||||
// Get the token if it has not yet been acquired
|
||||
if (getAccessToken() == null) {
|
||||
updateAccessToken(null);
|
||||
}
|
||||
|
||||
OAuthClientRequest oAuthRequest;
|
||||
if (getAccessToken() != null) {
|
||||
// Build the request
|
||||
Request.Builder requestBuilder = request.newBuilder();
|
||||
|
||||
String requestAccessToken = getAccessToken();
|
||||
try {
|
||||
oAuthRequest =
|
||||
new OAuthBearerClientRequest(request.url().toString()).
|
||||
setAccessToken(requestAccessToken).
|
||||
buildHeaderMessage();
|
||||
} catch (OAuthSystemException e) {
|
||||
throw new IOException(e);
|
||||
}
|
||||
|
||||
Map<String, String> headers = oAuthRequest.getHeaders();
|
||||
for (String headerName : headers.keySet()) {
|
||||
requestBuilder.addHeader(headerName, headers.get(headerName));
|
||||
}
|
||||
requestBuilder.url(oAuthRequest.getLocationUri());
|
||||
|
||||
// Execute the request
|
||||
Response response = chain.proceed(requestBuilder.build());
|
||||
|
||||
// 401/403 response codes most likely indicate an expired access token, unless it happens two times in a row
|
||||
if (
|
||||
response != null &&
|
||||
( response.code() == HttpURLConnection.HTTP_UNAUTHORIZED ||
|
||||
response.code() == HttpURLConnection.HTTP_FORBIDDEN ) &&
|
||||
updateTokenAndRetryOnAuthorizationFailure
|
||||
) {
|
||||
try {
|
||||
if (updateAccessToken(requestAccessToken)) {
|
||||
response.body().close();
|
||||
return retryingIntercept(chain, false);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
response.body().close();
|
||||
throw e;
|
||||
}
|
||||
}
|
||||
return response;
|
||||
}
|
||||
else {
|
||||
return chain.proceed(chain.request());
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Returns true if the access token has been updated
|
||||
*/
|
||||
public synchronized boolean updateAccessToken(String requestAccessToken) throws IOException {
|
||||
if (getAccessToken() == null || getAccessToken().equals(requestAccessToken)) {
|
||||
try {
|
||||
OAuthJSONAccessTokenResponse accessTokenResponse =
|
||||
oAuthClient.accessToken(tokenRequestBuilder.buildBodyMessage());
|
||||
if (accessTokenResponse != null && accessTokenResponse.getAccessToken() != null) {
|
||||
setAccessToken(accessTokenResponse.getAccessToken());
|
||||
}
|
||||
} catch (OAuthSystemException | OAuthProblemException e) {
|
||||
throw new IOException(e);
|
||||
}
|
||||
}
|
||||
return getAccessToken() == null || !getAccessToken().equals(requestAccessToken);
|
||||
}
|
||||
|
||||
public TokenRequestBuilder getTokenRequestBuilder() {
|
||||
return tokenRequestBuilder;
|
||||
}
|
||||
|
||||
public void setTokenRequestBuilder(TokenRequestBuilder tokenRequestBuilder) {
|
||||
this.tokenRequestBuilder = tokenRequestBuilder;
|
||||
}
|
||||
|
||||
// Applying authorization to parameters is performed in the retryingIntercept method
|
||||
@Override
|
||||
public void applyToParams(List<Pair> queryParams, Map<String, String> headerParams, Map<String, String> cookieParams,
|
||||
String payload, String method, URI uri) throws ApiException {
|
||||
// No implementation necessary
|
||||
}
|
||||
}
|
||||
{{/hasOAuthMethods}}
|
@ -0,0 +1,169 @@
|
||||
apply plugin: 'idea'
|
||||
apply plugin: 'eclipse'
|
||||
{{#sourceFolder}}
|
||||
apply plugin: 'java'
|
||||
{{/sourceFolder}}
|
||||
apply plugin: 'com.diffplug.spotless'
|
||||
|
||||
group = '{{groupId}}'
|
||||
version = '{{artifactVersion}}'
|
||||
|
||||
buildscript {
|
||||
repositories {
|
||||
mavenCentral()
|
||||
}
|
||||
dependencies {
|
||||
classpath 'com.android.tools.build:gradle:2.3.+'
|
||||
classpath 'com.github.dcendents:android-maven-gradle-plugin:1.5'
|
||||
classpath 'com.diffplug.spotless:spotless-plugin-gradle:5.17.1'
|
||||
}
|
||||
}
|
||||
|
||||
repositories {
|
||||
mavenCentral()
|
||||
}
|
||||
{{#sourceFolder}}
|
||||
sourceSets {
|
||||
main.java.srcDirs = ['{{sourceFolder}}']
|
||||
}
|
||||
|
||||
{{/sourceFolder}}
|
||||
if(hasProperty('target') && target == 'android') {
|
||||
|
||||
apply plugin: 'com.android.library'
|
||||
apply plugin: 'com.github.dcendents.android-maven'
|
||||
|
||||
android {
|
||||
compileSdkVersion 25
|
||||
buildToolsVersion '25.0.2'
|
||||
defaultConfig {
|
||||
minSdkVersion 14
|
||||
targetSdkVersion 25
|
||||
}
|
||||
compileOptions {
|
||||
sourceCompatibility JavaVersion.VERSION_1_8
|
||||
targetCompatibility JavaVersion.VERSION_1_8
|
||||
}
|
||||
|
||||
// Rename the aar correctly
|
||||
libraryVariants.all { variant ->
|
||||
variant.outputs.each { output ->
|
||||
def outputFile = output.outputFile
|
||||
if (outputFile != null && outputFile.name.endsWith('.aar')) {
|
||||
def fileName = "${project.name}-${variant.baseName}-${version}.aar"
|
||||
output.outputFile = new File(outputFile.parent, fileName)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
dependencies {
|
||||
provided "jakarta.annotation:jakarta.annotation-api:$jakarta_annotation_version"
|
||||
}
|
||||
}
|
||||
|
||||
afterEvaluate {
|
||||
android.libraryVariants.all { variant ->
|
||||
def task = project.tasks.create "jar${variant.name.capitalize()}", Jar
|
||||
task.description = "Create jar artifact for ${variant.name}"
|
||||
task.dependsOn variant.javaCompile
|
||||
task.from variant.javaCompile.destinationDir
|
||||
task.destinationDir = project.file("${project.buildDir}/outputs/jar")
|
||||
task.archiveName = "${project.name}-${variant.baseName}-${version}.jar"
|
||||
artifacts.add('archives', task);
|
||||
}
|
||||
}
|
||||
|
||||
task sourcesJar(type: Jar) {
|
||||
from android.sourceSets.main.java.srcDirs
|
||||
classifier = 'sources'
|
||||
}
|
||||
|
||||
artifacts {
|
||||
archives sourcesJar
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
apply plugin: 'java'
|
||||
apply plugin: 'maven-publish'
|
||||
|
||||
sourceCompatibility = JavaVersion.VERSION_1_8
|
||||
targetCompatibility = JavaVersion.VERSION_1_8
|
||||
|
||||
publishing {
|
||||
publications {
|
||||
maven(MavenPublication) {
|
||||
artifactId = '{{artifactId}}'
|
||||
from components.java
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
task execute(type:JavaExec) {
|
||||
main = System.getProperty('mainClass')
|
||||
classpath = sourceSets.main.runtimeClasspath
|
||||
}
|
||||
}
|
||||
|
||||
ext {
|
||||
jakarta_annotation_version = "1.3.5"
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation 'io.swagger:swagger-annotations:1.5.24'
|
||||
implementation "com.google.code.findbugs:jsr305:3.0.2"
|
||||
implementation 'com.squareup.okhttp3:okhttp:4.9.1'
|
||||
implementation 'com.squareup.okhttp3:logging-interceptor:4.9.1'
|
||||
implementation 'com.google.code.gson:gson:2.8.6'
|
||||
implementation 'io.gsonfire:gson-fire:1.8.4'
|
||||
{{#openApiNullable}}
|
||||
implementation 'org.openapitools:jackson-databind-nullable:0.2.1'
|
||||
{{/openApiNullable}}
|
||||
{{#hasOAuthMethods}}
|
||||
implementation group: 'org.apache.oltu.oauth2', name: 'org.apache.oltu.oauth2.client', version: '1.0.1'
|
||||
{{/hasOAuthMethods}}
|
||||
implementation group: 'org.apache.commons', name: 'commons-lang3', version: '3.10'
|
||||
{{#joda}}
|
||||
implementation 'joda-time:joda-time:2.9.9'
|
||||
{{/joda}}
|
||||
{{#threetenbp}}
|
||||
implementation 'org.threeten:threetenbp:1.4.3'
|
||||
{{/threetenbp}}
|
||||
{{#dynamicOperations}}
|
||||
implementation 'io.swagger.parser.v3:swagger-parser-v3:2.0.23'
|
||||
{{/dynamicOperations}}
|
||||
implementation "jakarta.annotation:jakarta.annotation-api:$jakarta_annotation_version"
|
||||
testImplementation 'junit:junit:4.13.1'
|
||||
testImplementation 'org.mockito:mockito-core:3.11.2'
|
||||
}
|
||||
|
||||
javadoc {
|
||||
options.tags = [ "http.response.details:a:Http Response Details" ]
|
||||
}
|
||||
|
||||
// Use spotless plugin to automatically format code, remove unused import, etc
|
||||
// To apply changes directly to the file, run `gradlew spotlessApply`
|
||||
// Ref: https://github.com/diffplug/spotless/tree/main/plugin-gradle
|
||||
spotless {
|
||||
// comment out below to run spotless as part of the `check` task
|
||||
enforceCheck false
|
||||
|
||||
format 'misc', {
|
||||
// define the files (e.g. '*.gradle', '*.md') to apply `misc` to
|
||||
target '.gitignore'
|
||||
|
||||
// define the steps to apply to those files
|
||||
trimTrailingWhitespace()
|
||||
indentWithSpaces() // Takes an integer argument if you don't like 4
|
||||
endWithNewline()
|
||||
}
|
||||
java {
|
||||
// don't need to set target, it is inferred from java
|
||||
|
||||
// apply a specific flavor of google-java-format
|
||||
googleJavaFormat('1.8').aosp().reflowLongStrings()
|
||||
|
||||
removeUnusedImports()
|
||||
importOrder()
|
||||
}
|
||||
}
|
@ -0,0 +1,39 @@
|
||||
lazy val root = (project in file(".")).
|
||||
settings(
|
||||
organization := "{{groupId}}",
|
||||
name := "{{artifactId}}",
|
||||
version := "{{artifactVersion}}",
|
||||
scalaVersion := "2.11.4",
|
||||
scalacOptions ++= Seq("-feature"),
|
||||
javacOptions in compile ++= Seq("-Xlint:deprecation"),
|
||||
publishArtifact in (Compile, packageDoc) := false,
|
||||
resolvers += Resolver.mavenLocal,
|
||||
libraryDependencies ++= Seq(
|
||||
"io.swagger" % "swagger-annotations" % "1.5.24",
|
||||
"com.squareup.okhttp3" % "okhttp" % "4.9.1",
|
||||
"com.squareup.okhttp3" % "logging-interceptor" % "4.9.1",
|
||||
"com.google.code.gson" % "gson" % "2.8.6",
|
||||
"org.apache.commons" % "commons-lang3" % "3.10",
|
||||
{{#openApiNullable}}
|
||||
"org.openapitools" % "jackson-databind-nullable" % "0.2.1",
|
||||
{{/openApiNullable}}
|
||||
{{#hasOAuthMethods}}
|
||||
"org.apache.oltu.oauth2" % "org.apache.oltu.oauth2.client" % "1.0.1",
|
||||
{{/hasOAuthMethods}}
|
||||
{{#joda}}
|
||||
"joda-time" % "joda-time" % "2.9.9" % "compile",
|
||||
{{/joda}}
|
||||
{{#threetenbp}}
|
||||
"org.threeten" % "threetenbp" % "1.4.3" % "compile",
|
||||
{{/threetenbp}}
|
||||
{{#dynamicOperations}}
|
||||
"io.swagger.parser.v3" % "swagger-parser-v3" "2.0.23" % "compile"
|
||||
{{/dynamicOperations}}
|
||||
"io.gsonfire" % "gson-fire" % "1.8.3" % "compile",
|
||||
"jakarta.annotation" % "jakarta.annotation-api" % "1.3.5" % "compile",
|
||||
"com.google.code.findbugs" % "jsr305" % "3.0.2" % "compile",
|
||||
"jakarta.annotation" % "jakarta.annotation-api" % "1.3.5" % "compile",
|
||||
"junit" % "junit" % "4.13.1" % "test",
|
||||
"com.novocode" % "junit-interface" % "0.10" % "test"
|
||||
)
|
||||
)
|
61
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/model.mustache
vendored
Normal file
61
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/model.mustache
vendored
Normal file
@ -0,0 +1,61 @@
|
||||
{{>licenseInfo}}
|
||||
|
||||
package {{package}};
|
||||
|
||||
{{#useReflectionEqualsHashCode}}
|
||||
import org.apache.commons.lang3.builder.EqualsBuilder;
|
||||
import org.apache.commons.lang3.builder.HashCodeBuilder;
|
||||
{{/useReflectionEqualsHashCode}}
|
||||
import java.util.Objects;
|
||||
import java.util.Arrays;
|
||||
{{#imports}}
|
||||
import {{import}};
|
||||
{{/imports}}
|
||||
{{#serializableModel}}
|
||||
import java.io.Serializable;
|
||||
{{/serializableModel}}
|
||||
{{#jackson}}
|
||||
import com.fasterxml.jackson.annotation.JsonPropertyOrder;
|
||||
import com.fasterxml.jackson.annotation.JsonTypeName;
|
||||
{{#withXml}}
|
||||
import com.fasterxml.jackson.dataformat.xml.annotation.*;
|
||||
{{/withXml}}
|
||||
{{#vendorExtensions.x-has-readonly-properties}}
|
||||
import com.fasterxml.jackson.annotation.JsonCreator;
|
||||
{{/vendorExtensions.x-has-readonly-properties}}
|
||||
{{/jackson}}
|
||||
{{#withXml}}
|
||||
import javax.xml.bind.annotation.*;
|
||||
{{/withXml}}
|
||||
{{#jsonb}}
|
||||
import java.lang.reflect.Type;
|
||||
import javax.json.bind.annotation.JsonbTypeDeserializer;
|
||||
import javax.json.bind.annotation.JsonbTypeSerializer;
|
||||
import javax.json.bind.serializer.DeserializationContext;
|
||||
import javax.json.bind.serializer.JsonbDeserializer;
|
||||
import javax.json.bind.serializer.JsonbSerializer;
|
||||
import javax.json.bind.serializer.SerializationContext;
|
||||
import javax.json.stream.JsonGenerator;
|
||||
import javax.json.stream.JsonParser;
|
||||
import javax.json.bind.annotation.JsonbProperty;
|
||||
{{#vendorExtensions.x-has-readonly-properties}}
|
||||
import javax.json.bind.annotation.JsonbCreator;
|
||||
{{/vendorExtensions.x-has-readonly-properties}}
|
||||
{{/jsonb}}
|
||||
{{#parcelableModel}}
|
||||
import android.os.Parcelable;
|
||||
import android.os.Parcel;
|
||||
{{/parcelableModel}}
|
||||
{{#useBeanValidation}}
|
||||
import javax.validation.constraints.*;
|
||||
import javax.validation.Valid;
|
||||
{{/useBeanValidation}}
|
||||
{{#performBeanValidation}}
|
||||
import org.hibernate.validator.constraints.*;
|
||||
{{/performBeanValidation}}
|
||||
|
||||
{{#models}}
|
||||
{{#model}}
|
||||
{{#isEnum}}{{>modelEnum}}{{/isEnum}}{{^isEnum}}{{#oneOf}}{{#-first}}{{>oneof_model}}{{/-first}}{{/oneOf}}{{^oneOf}}{{#anyOf}}{{#-first}}{{>anyof_model}}{{/-first}}{{/anyOf}}{{^anyOf}}{{>pojo}}{{/anyOf}}{{/oneOf}}{{/isEnum}}
|
||||
{{/model}}
|
||||
{{/models}}
|
190
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/oneof_model.mustache
vendored
Normal file
190
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/oneof_model.mustache
vendored
Normal file
@ -0,0 +1,190 @@
|
||||
import javax.ws.rs.core.GenericType;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.HashSet;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.GsonBuilder;
|
||||
import com.google.gson.JsonParseException;
|
||||
import com.google.gson.TypeAdapter;
|
||||
import com.google.gson.TypeAdapterFactory;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
import com.google.gson.JsonPrimitive;
|
||||
import com.google.gson.annotations.JsonAdapter;
|
||||
import com.google.gson.annotations.SerializedName;
|
||||
import com.google.gson.stream.JsonReader;
|
||||
import com.google.gson.stream.JsonWriter;
|
||||
import com.google.gson.JsonDeserializationContext;
|
||||
import com.google.gson.JsonDeserializer;
|
||||
import com.google.gson.JsonSerializationContext;
|
||||
import com.google.gson.JsonSerializer;
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import com.google.gson.JsonParseException;
|
||||
|
||||
import {{invokerPackage}}.JSON;
|
||||
|
||||
{{>additionalModelTypeAnnotations}}{{>generatedAnnotation}}{{>xmlAnnotation}}
|
||||
public class {{classname}} extends AbstractOpenApiSchema{{#vendorExtensions.x-implements}}, {{{.}}}{{/vendorExtensions.x-implements}} {
|
||||
private static final Logger log = Logger.getLogger({{classname}}.class.getName());
|
||||
|
||||
public static class CustomTypeAdapterFactory implements TypeAdapterFactory {
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> type) {
|
||||
if (!{{classname}}.class.isAssignableFrom(type.getRawType())) {
|
||||
return null; // this class only serializes '{{classname}}' and its subtypes
|
||||
}
|
||||
final TypeAdapter<JsonElement> elementAdapter = gson.getAdapter(JsonElement.class);
|
||||
{{#oneOf}}
|
||||
final TypeAdapter<{{.}}> adapter{{.}} = gson.getDelegateAdapter(this, TypeToken.get({{.}}.class));
|
||||
{{/oneOf}}
|
||||
|
||||
return (TypeAdapter<T>) new TypeAdapter<{{classname}}>() {
|
||||
@Override
|
||||
public void write(JsonWriter out, {{classname}} value) throws IOException {
|
||||
{{#oneOf}}
|
||||
// check if the actual instance is of the type `{{.}}`
|
||||
if (value.getActualInstance() instanceof {{.}}) {
|
||||
JsonObject obj = adapter{{.}}.toJsonTree(({{.}})value.getActualInstance()).getAsJsonObject();
|
||||
elementAdapter.write(out, obj);
|
||||
}
|
||||
|
||||
{{/oneOf}}
|
||||
throw new IOException("Failed to deserialize as the type doesn't match oneOf schemas: {{#oneOf}}{{{.}}}{{^-last}}, {{/-last}}{{/oneOf}}");
|
||||
}
|
||||
|
||||
@Override
|
||||
public {{classname}} read(JsonReader in) throws IOException {
|
||||
Object deserialized = null;
|
||||
JsonObject jsonObject = elementAdapter.read(in).getAsJsonObject();
|
||||
|
||||
{{#useOneOfDiscriminatorLookup}}
|
||||
{{#discriminator}}
|
||||
// use discriminator value for faster oneOf lookup
|
||||
{{classname}} new{{classname}} = new {{classname}}();
|
||||
String discriminatorValue = elementAdapter.read(in).getAsJsonObject().get("{{{propertyBaseName}}}").getAsString();
|
||||
switch (discriminatorValue) {
|
||||
{{#mappedModels}}
|
||||
case "{{{mappingName}}}":
|
||||
deserialized = adapter{{.}}.fromJsonTree(jsonObject);
|
||||
new{{classname}}.setActualInstance(deserialized);
|
||||
return new{{classname}};
|
||||
{{/mappedModels}}
|
||||
default:
|
||||
log.log(Level.WARNING, String.format("Failed to lookup discriminator value `%s` for {{classname}}. Possible values:{{#mappedModels}} {{{mappingName}}}{{/mappedModels}}", discriminatorValue));
|
||||
}
|
||||
|
||||
{{/discriminator}}
|
||||
{{/useOneOfDiscriminatorLookup}}
|
||||
int match = 0;
|
||||
|
||||
{{#oneOf}}
|
||||
// deserialize {{{.}}}
|
||||
try {
|
||||
deserialized = adapter{{.}}.fromJsonTree(jsonObject);
|
||||
match++;
|
||||
log.log(Level.FINER, "Input data matches schema '{{{.}}}'");
|
||||
} catch (Exception e) {
|
||||
// deserialization failed, continue
|
||||
log.log(Level.FINER, "Input data does not match schema '{{{.}}}'", e);
|
||||
}
|
||||
|
||||
{{/oneOf}}
|
||||
if (match == 1) {
|
||||
{{classname}} ret = new {{classname}}();
|
||||
ret.setActualInstance(deserialized);
|
||||
return ret;
|
||||
}
|
||||
|
||||
throw new IOException(String.format("Failed deserialization for {{classname}}: %d classes match result, expected 1", match));
|
||||
}
|
||||
}.nullSafe();
|
||||
}
|
||||
}
|
||||
|
||||
// store a list of schema names defined in oneOf
|
||||
public static final Map<String, GenericType> schemas = new HashMap<String, GenericType>();
|
||||
|
||||
public {{classname}}() {
|
||||
super("oneOf", {{#isNullable}}Boolean.TRUE{{/isNullable}}{{^isNullable}}Boolean.FALSE{{/isNullable}});
|
||||
}
|
||||
|
||||
{{#oneOf}}
|
||||
public {{classname}}({{{.}}} o) {
|
||||
super("oneOf", {{#isNullable}}Boolean.TRUE{{/isNullable}}{{^isNullable}}Boolean.FALSE{{/isNullable}});
|
||||
setActualInstance(o);
|
||||
}
|
||||
|
||||
{{/oneOf}}
|
||||
static {
|
||||
{{#oneOf}}
|
||||
schemas.put("{{{.}}}", new GenericType<{{{.}}}>() {
|
||||
});
|
||||
{{/oneOf}}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, GenericType> getSchemas() {
|
||||
return {{classname}}.schemas;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the instance that matches the oneOf child schema, check
|
||||
* the instance parameter is valid against the oneOf child schemas:
|
||||
* {{#oneOf}}{{{.}}}{{^-last}}, {{/-last}}{{/oneOf}}
|
||||
*
|
||||
* It could be an instance of the 'oneOf' schemas.
|
||||
* The oneOf child schemas may themselves be a composed schema (allOf, anyOf, oneOf).
|
||||
*/
|
||||
@Override
|
||||
public void setActualInstance(Object instance) {
|
||||
{{#isNullable}}
|
||||
if (instance == null) {
|
||||
super.setActualInstance(instance);
|
||||
return;
|
||||
}
|
||||
|
||||
{{/isNullable}}
|
||||
{{#oneOf}}
|
||||
if (instance instanceof {{{.}}}) {
|
||||
super.setActualInstance(instance);
|
||||
return;
|
||||
}
|
||||
|
||||
{{/oneOf}}
|
||||
throw new RuntimeException("Invalid instance type. Must be {{#oneOf}}{{{.}}}{{^-last}}, {{/-last}}{{/oneOf}}");
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the actual instance, which can be the following:
|
||||
* {{#oneOf}}{{{.}}}{{^-last}}, {{/-last}}{{/oneOf}}
|
||||
*
|
||||
* @return The actual instance ({{#oneOf}}{{{.}}}{{^-last}}, {{/-last}}{{/oneOf}})
|
||||
*/
|
||||
@Override
|
||||
public Object getActualInstance() {
|
||||
return super.getActualInstance();
|
||||
}
|
||||
|
||||
{{#oneOf}}
|
||||
/**
|
||||
* Get the actual instance of `{{{.}}}`. If the actual instance is not `{{{.}}}`,
|
||||
* the ClassCastException will be thrown.
|
||||
*
|
||||
* @return The actual instance of `{{{.}}}`
|
||||
* @throws ClassCastException if the instance is not `{{{.}}}`
|
||||
*/
|
||||
public {{{.}}} get{{{.}}}() throws ClassCastException {
|
||||
return ({{{.}}})super.getActualInstance();
|
||||
}
|
||||
|
||||
{{/oneOf}}
|
||||
}
|
447
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/pojo.mustache
vendored
Normal file
447
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/pojo.mustache
vendored
Normal file
@ -0,0 +1,447 @@
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.GsonBuilder;
|
||||
import com.google.gson.JsonDeserializationContext;
|
||||
import com.google.gson.JsonDeserializer;
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import com.google.gson.JsonParseException;
|
||||
import com.google.gson.TypeAdapterFactory;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.HashSet;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* {{description}}{{^description}}{{classname}}{{/description}}{{#isDeprecated}}
|
||||
* @deprecated{{/isDeprecated}}
|
||||
*/{{#isDeprecated}}
|
||||
@Deprecated{{/isDeprecated}}{{#description}}
|
||||
@ApiModel(description = "{{{.}}}"){{/description}}
|
||||
{{#jackson}}
|
||||
@JsonPropertyOrder({
|
||||
{{#vars}}
|
||||
{{classname}}.JSON_PROPERTY_{{nameInSnakeCase}}{{^-last}},{{/-last}}
|
||||
{{/vars}}
|
||||
})
|
||||
@JsonTypeName("{{name}}")
|
||||
{{/jackson}}
|
||||
{{>additionalModelTypeAnnotations}}{{>generatedAnnotation}}{{#discriminator}}{{>typeInfoAnnotation}}{{/discriminator}}{{>xmlAnnotation}}
|
||||
public class {{classname}} {{#parent}}extends {{{.}}} {{/parent}}{{#vendorExtensions.x-implements}}{{#-first}}implements {{{.}}}{{/-first}}{{^-first}}, {{{.}}}{{/-first}}{{#-last}} {{/-last}}{{/vendorExtensions.x-implements}}{
|
||||
{{#serializableModel}}
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
{{/serializableModel}}
|
||||
{{#vars}}
|
||||
{{#isEnum}}
|
||||
{{^isContainer}}
|
||||
{{>modelInnerEnum}}
|
||||
{{/isContainer}}
|
||||
{{#isContainer}}
|
||||
{{#mostInnerItems}}
|
||||
{{>modelInnerEnum}}
|
||||
{{/mostInnerItems}}
|
||||
{{/isContainer}}
|
||||
{{/isEnum}}
|
||||
{{#gson}}
|
||||
public static final String SERIALIZED_NAME_{{nameInSnakeCase}} = "{{baseName}}";
|
||||
{{/gson}}
|
||||
{{#jackson}}
|
||||
public static final String JSON_PROPERTY_{{nameInSnakeCase}} = "{{baseName}}";
|
||||
{{/jackson}}
|
||||
{{#withXml}}
|
||||
{{#isXmlAttribute}}
|
||||
@XmlAttribute(name = "{{xmlName}}{{^xmlName}}{{baseName}}{{/xmlName}}")
|
||||
{{/isXmlAttribute}}
|
||||
{{^isXmlAttribute}}
|
||||
{{^isContainer}}
|
||||
@XmlElement({{#xmlNamespace}}namespace="{{.}}", {{/xmlNamespace}}name = "{{xmlName}}{{^xmlName}}{{baseName}}{{/xmlName}}")
|
||||
{{/isContainer}}
|
||||
{{#isContainer}}
|
||||
// Is a container wrapped={{isXmlWrapped}}
|
||||
{{#items}}
|
||||
// items.name={{name}} items.baseName={{baseName}} items.xmlName={{xmlName}} items.xmlNamespace={{xmlNamespace}}
|
||||
// items.example={{example}} items.type={{dataType}}
|
||||
@XmlElement({{#xmlNamespace}}namespace="{{.}}", {{/xmlNamespace}}name = "{{xmlName}}{{^xmlName}}{{baseName}}{{/xmlName}}")
|
||||
{{/items}}
|
||||
{{#isXmlWrapped}}
|
||||
@XmlElementWrapper({{#xmlNamespace}}namespace="{{.}}", {{/xmlNamespace}}name = "{{xmlName}}{{^xmlName}}{{baseName}}{{/xmlName}}")
|
||||
{{/isXmlWrapped}}
|
||||
{{/isContainer}}
|
||||
{{/isXmlAttribute}}
|
||||
{{/withXml}}
|
||||
{{#gson}}
|
||||
@SerializedName(SERIALIZED_NAME_{{nameInSnakeCase}})
|
||||
{{/gson}}
|
||||
{{#vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{#isContainer}}
|
||||
private JsonNullable<{{{datatypeWithEnum}}}> {{name}} = JsonNullable.<{{{datatypeWithEnum}}}>undefined();
|
||||
{{/isContainer}}
|
||||
{{^isContainer}}
|
||||
private JsonNullable<{{{datatypeWithEnum}}}> {{name}} = JsonNullable.<{{{datatypeWithEnum}}}>{{#defaultValue}}of({{{.}}}){{/defaultValue}}{{^defaultValue}}undefined(){{/defaultValue}};
|
||||
{{/isContainer}}
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{#isContainer}}
|
||||
private {{{datatypeWithEnum}}} {{name}}{{#required}}{{#defaultValue}} = {{{.}}}{{/defaultValue}}{{/required}}{{^required}} = null{{/required}};
|
||||
{{/isContainer}}
|
||||
{{^isContainer}}
|
||||
{{#isDiscriminator}}protected{{/isDiscriminator}}{{^isDiscriminator}}private{{/isDiscriminator}} {{{datatypeWithEnum}}} {{name}}{{#defaultValue}} = {{{.}}}{{/defaultValue}};
|
||||
{{/isContainer}}
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
|
||||
{{/vars}}
|
||||
public {{classname}}() { {{#parent}}{{#parcelableModel}}
|
||||
super();{{/parcelableModel}}{{/parent}}{{#gson}}{{#discriminator}}
|
||||
this.{{{discriminatorName}}} = this.getClass().getSimpleName();{{/discriminator}}{{/gson}}
|
||||
}{{#vendorExtensions.x-has-readonly-properties}}{{^withXml}}
|
||||
|
||||
{{#jsonb}}@JsonbCreator{{/jsonb}}{{#jackson}}@JsonCreator{{/jackson}}
|
||||
public {{classname}}(
|
||||
{{#readOnlyVars}}
|
||||
{{#jsonb}}@JsonbProperty("{{baseName}}"){{/jsonb}}{{#jackson}}@JsonProperty(JSON_PROPERTY_{{nameInSnakeCase}}){{/jackson}} {{{datatypeWithEnum}}} {{name}}{{^-last}}, {{/-last}}
|
||||
{{/readOnlyVars}}
|
||||
) {
|
||||
this();
|
||||
{{#readOnlyVars}}
|
||||
this.{{name}} = {{name}};
|
||||
{{/readOnlyVars}}
|
||||
}{{/withXml}}{{/vendorExtensions.x-has-readonly-properties}}
|
||||
{{#vars}}
|
||||
|
||||
{{^isReadOnly}}
|
||||
public {{classname}} {{name}}({{{datatypeWithEnum}}} {{name}}) {
|
||||
{{#vendorExtensions.x-is-jackson-optional-nullable}}this.{{name}} = JsonNullable.<{{{datatypeWithEnum}}}>of({{name}});{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^vendorExtensions.x-is-jackson-optional-nullable}}this.{{name}} = {{name}};{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
return this;
|
||||
}
|
||||
{{#isArray}}
|
||||
|
||||
public {{classname}} add{{nameInCamelCase}}Item({{{items.datatypeWithEnum}}} {{name}}Item) {
|
||||
{{#vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
if (this.{{name}} == null || !this.{{name}}.isPresent()) {
|
||||
this.{{name}} = JsonNullable.<{{{datatypeWithEnum}}}>of({{{defaultValue}}});
|
||||
}
|
||||
try {
|
||||
this.{{name}}.get().add({{name}}Item);
|
||||
} catch (java.util.NoSuchElementException e) {
|
||||
// this can never happen, as we make sure above that the value is present
|
||||
}
|
||||
return this;
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^required}}
|
||||
if (this.{{name}} == null) {
|
||||
this.{{name}} = {{{defaultValue}}};
|
||||
}
|
||||
{{/required}}
|
||||
this.{{name}}.add({{name}}Item);
|
||||
return this;
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
}
|
||||
{{/isArray}}
|
||||
{{#isMap}}
|
||||
|
||||
public {{classname}} put{{nameInCamelCase}}Item(String key, {{{items.datatypeWithEnum}}} {{name}}Item) {
|
||||
{{#vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
if (this.{{name}} == null || !this.{{name}}.isPresent()) {
|
||||
this.{{name}} = JsonNullable.<{{{datatypeWithEnum}}}>of({{{defaultValue}}});
|
||||
}
|
||||
try {
|
||||
this.{{name}}.get().put(key, {{name}}Item);
|
||||
} catch (java.util.NoSuchElementException e) {
|
||||
// this can never happen, as we make sure above that the value is present
|
||||
}
|
||||
return this;
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^required}}
|
||||
if (this.{{name}} == null) {
|
||||
this.{{name}} = {{{defaultValue}}};
|
||||
}
|
||||
{{/required}}
|
||||
this.{{name}}.put(key, {{name}}Item);
|
||||
return this;
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
}
|
||||
{{/isMap}}
|
||||
|
||||
{{/isReadOnly}}
|
||||
/**
|
||||
{{#description}}
|
||||
* {{.}}
|
||||
{{/description}}
|
||||
{{^description}}
|
||||
* Get {{name}}
|
||||
{{/description}}
|
||||
{{#minimum}}
|
||||
* minimum: {{.}}
|
||||
{{/minimum}}
|
||||
{{#maximum}}
|
||||
* maximum: {{.}}
|
||||
{{/maximum}}
|
||||
* @return {{name}}
|
||||
{{#deprecated}}
|
||||
* @deprecated
|
||||
{{/deprecated}}
|
||||
**/
|
||||
{{#deprecated}}
|
||||
@Deprecated
|
||||
{{/deprecated}}
|
||||
{{#required}}
|
||||
{{#isNullable}}
|
||||
@javax.annotation.Nullable
|
||||
{{/isNullable}}
|
||||
{{^isNullable}}
|
||||
@javax.annotation.Nonnull
|
||||
{{/isNullable}}
|
||||
{{/required}}
|
||||
{{^required}}
|
||||
@javax.annotation.Nullable
|
||||
{{/required}}
|
||||
{{#jsonb}}
|
||||
@JsonbProperty("{{baseName}}")
|
||||
{{/jsonb}}
|
||||
{{#useBeanValidation}}{{>beanValidation}}{{/useBeanValidation}} @ApiModelProperty({{#example}}example = "{{{.}}}", {{/example}}{{#required}}required = {{required}}, {{/required}}value = "{{{description}}}")
|
||||
{{#vendorExtensions.x-extra-annotation}}
|
||||
{{{vendorExtensions.x-extra-annotation}}}
|
||||
{{/vendorExtensions.x-extra-annotation}}
|
||||
{{#vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{!unannotated, Jackson would pick this up automatically and add it *in addition* to the _JsonNullable getter field}}
|
||||
@JsonIgnore
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^vendorExtensions.x-is-jackson-optional-nullable}}{{#jackson}}{{> jackson_annotations}}{{/jackson}}{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
public {{{datatypeWithEnum}}} {{getter}}() {
|
||||
{{#vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{#isReadOnly}}{{! A readonly attribute doesn't have setter => jackson will set null directly if explicitly returned by API, so make sure we have an empty JsonNullable}}
|
||||
if ({{name}} == null) {
|
||||
{{name}} = JsonNullable.<{{{datatypeWithEnum}}}>{{#defaultValue}}of({{{.}}}){{/defaultValue}}{{^defaultValue}}undefined(){{/defaultValue}};
|
||||
}
|
||||
{{/isReadOnly}}
|
||||
return {{name}}.orElse(null);
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
return {{name}};
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
}
|
||||
|
||||
{{#vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{> jackson_annotations}}
|
||||
public JsonNullable<{{{datatypeWithEnum}}}> {{getter}}_JsonNullable() {
|
||||
return {{name}};
|
||||
}
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}{{#vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
@JsonProperty(JSON_PROPERTY_{{nameInSnakeCase}})
|
||||
{{#isReadOnly}}private{{/isReadOnly}}{{^isReadOnly}}public{{/isReadOnly}} void {{setter}}_JsonNullable(JsonNullable<{{{datatypeWithEnum}}}> {{name}}) {
|
||||
{{! For getters/setters that have name differing from attribute name, we must include setter (albeit private) for jackson to be able to set the attribute}}
|
||||
this.{{name}} = {{name}};
|
||||
}
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
|
||||
{{^isReadOnly}}
|
||||
{{#vendorExtensions.x-setter-extra-annotation}} {{{vendorExtensions.x-setter-extra-annotation}}}
|
||||
{{/vendorExtensions.x-setter-extra-annotation}}{{#jackson}}{{^vendorExtensions.x-is-jackson-optional-nullable}}{{> jackson_annotations}}{{/vendorExtensions.x-is-jackson-optional-nullable}}{{/jackson}} public void {{setter}}({{{datatypeWithEnum}}} {{name}}) {
|
||||
{{#vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
this.{{name}} = JsonNullable.<{{{datatypeWithEnum}}}>of({{name}});
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
{{^vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
this.{{name}} = {{name}};
|
||||
{{/vendorExtensions.x-is-jackson-optional-nullable}}
|
||||
}
|
||||
{{/isReadOnly}}
|
||||
|
||||
{{/vars}}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
{{#useReflectionEqualsHashCode}}
|
||||
return EqualsBuilder.reflectionEquals(this, o, false, null, true);
|
||||
{{/useReflectionEqualsHashCode}}
|
||||
{{^useReflectionEqualsHashCode}}
|
||||
if (this == o) {
|
||||
return true;
|
||||
}
|
||||
if (o == null || getClass() != o.getClass()) {
|
||||
return false;
|
||||
}{{#hasVars}}
|
||||
{{classname}} {{classVarName}} = ({{classname}}) o;
|
||||
return {{#vars}}{{#vendorExtensions.x-is-jackson-optional-nullable}}equalsNullable(this.{{name}}, {{classVarName}}.{{name}}){{/vendorExtensions.x-is-jackson-optional-nullable}}{{^vendorExtensions.x-is-jackson-optional-nullable}}{{#isByteArray}}Arrays{{/isByteArray}}{{^isByteArray}}Objects{{/isByteArray}}.equals(this.{{name}}, {{classVarName}}.{{name}}){{/vendorExtensions.x-is-jackson-optional-nullable}}{{^-last}} &&
|
||||
{{/-last}}{{/vars}}{{#parent}} &&
|
||||
super.equals(o){{/parent}};{{/hasVars}}{{^hasVars}}
|
||||
return {{#parent}}super.equals(o){{/parent}}{{^parent}}true{{/parent}};{{/hasVars}}
|
||||
{{/useReflectionEqualsHashCode}}
|
||||
}{{#vendorExtensions.x-jackson-optional-nullable-helpers}}
|
||||
|
||||
private static <T> boolean equalsNullable(JsonNullable<T> a, JsonNullable<T> b) {
|
||||
return a == b || (a != null && b != null && a.isPresent() && b.isPresent() && Objects.deepEquals(a.get(), b.get()));
|
||||
}{{/vendorExtensions.x-jackson-optional-nullable-helpers}}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
{{#useReflectionEqualsHashCode}}
|
||||
return HashCodeBuilder.reflectionHashCode(this);
|
||||
{{/useReflectionEqualsHashCode}}
|
||||
{{^useReflectionEqualsHashCode}}
|
||||
return Objects.hash({{#vars}}{{#vendorExtensions.x-is-jackson-optional-nullable}}hashCodeNullable({{name}}){{/vendorExtensions.x-is-jackson-optional-nullable}}{{^vendorExtensions.x-is-jackson-optional-nullable}}{{^isByteArray}}{{name}}{{/isByteArray}}{{#isByteArray}}Arrays.hashCode({{name}}){{/isByteArray}}{{/vendorExtensions.x-is-jackson-optional-nullable}}{{^-last}}, {{/-last}}{{/vars}}{{#parent}}{{#hasVars}}, {{/hasVars}}super.hashCode(){{/parent}});
|
||||
{{/useReflectionEqualsHashCode}}
|
||||
}{{#vendorExtensions.x-jackson-optional-nullable-helpers}}
|
||||
|
||||
private static <T> int hashCodeNullable(JsonNullable<T> a) {
|
||||
if (a == null) {
|
||||
return 1;
|
||||
}
|
||||
return a.isPresent() ? Arrays.deepHashCode(new Object[]{a.get()}) : 31;
|
||||
}{{/vendorExtensions.x-jackson-optional-nullable-helpers}}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
StringBuilder sb = new StringBuilder();
|
||||
sb.append("class {{classname}} {\n");
|
||||
{{#parent}}
|
||||
sb.append(" ").append(toIndentedString(super.toString())).append("\n");
|
||||
{{/parent}}
|
||||
{{#vars}}
|
||||
sb.append(" {{name}}: ").append(toIndentedString({{name}})).append("\n");
|
||||
{{/vars}}
|
||||
sb.append("}");
|
||||
return sb.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert the given object to string with each line indented by 4 spaces
|
||||
* (except the first line).
|
||||
*/
|
||||
private{{#jsonb}} static{{/jsonb}} String toIndentedString(Object o) {
|
||||
if (o == null) {
|
||||
return "null";
|
||||
}
|
||||
return o.toString().replace("\n", "\n ");
|
||||
}
|
||||
|
||||
{{#parcelableModel}}
|
||||
|
||||
public void writeToParcel(Parcel out, int flags) {
|
||||
{{#model}}
|
||||
{{#isArray}}
|
||||
out.writeList(this);
|
||||
{{/isArray}}
|
||||
{{^isArray}}
|
||||
{{#parent}}
|
||||
super.writeToParcel(out, flags);
|
||||
{{/parent}}
|
||||
{{#vars}}
|
||||
out.writeValue({{name}});
|
||||
{{/vars}}
|
||||
{{/isArray}}
|
||||
{{/model}}
|
||||
}
|
||||
|
||||
{{classname}}(Parcel in) {
|
||||
{{#isArray}}
|
||||
in.readTypedList(this, {{arrayModelType}}.CREATOR);
|
||||
{{/isArray}}
|
||||
{{^isArray}}
|
||||
{{#parent}}
|
||||
super(in);
|
||||
{{/parent}}
|
||||
{{#vars}}
|
||||
{{#isPrimitiveType}}
|
||||
{{name}} = ({{{datatypeWithEnum}}})in.readValue(null);
|
||||
{{/isPrimitiveType}}
|
||||
{{^isPrimitiveType}}
|
||||
{{name}} = ({{{datatypeWithEnum}}})in.readValue({{complexType}}.class.getClassLoader());
|
||||
{{/isPrimitiveType}}
|
||||
{{/vars}}
|
||||
{{/isArray}}
|
||||
}
|
||||
|
||||
public int describeContents() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static final Parcelable.Creator<{{classname}}> CREATOR = new Parcelable.Creator<{{classname}}>() {
|
||||
public {{classname}} createFromParcel(Parcel in) {
|
||||
{{#model}}
|
||||
{{#isArray}}
|
||||
{{classname}} result = new {{classname}}();
|
||||
result.addAll(in.readArrayList({{arrayModelType}}.class.getClassLoader()));
|
||||
return result;
|
||||
{{/isArray}}
|
||||
{{^isArray}}
|
||||
return new {{classname}}(in);
|
||||
{{/isArray}}
|
||||
{{/model}}
|
||||
}
|
||||
public {{classname}}[] newArray(int size) {
|
||||
return new {{classname}}[size];
|
||||
}
|
||||
};
|
||||
{{/parcelableModel}}
|
||||
{{^hasChildren}}
|
||||
public static HashSet<String> openapiFields;
|
||||
public static HashSet<String> openapiRequiredFields;
|
||||
|
||||
static {
|
||||
// a set of all properties/fields (JSON key names)
|
||||
openapiFields = new HashSet<String>();
|
||||
{{#allVars}}
|
||||
openapiFields.add("{{baseName}}");
|
||||
{{/allVars}}
|
||||
|
||||
// a set of required properties/fields (JSON key names)
|
||||
openapiRequiredFields = new HashSet<String>();
|
||||
{{#requiredVars}}
|
||||
openapiRequiredFields.add("{{baseName}}");
|
||||
{{/requiredVars}}
|
||||
}
|
||||
|
||||
public static class CustomTypeAdapterFactory implements TypeAdapterFactory {
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> type) {
|
||||
if (!{{classname}}.class.isAssignableFrom(type.getRawType())) {
|
||||
return null; // this class only serializes '{{classname}}' and its subtypes
|
||||
}
|
||||
final TypeAdapter<JsonElement> elementAdapter = gson.getAdapter(JsonElement.class);
|
||||
final TypeAdapter<{{classname}}> thisAdapter
|
||||
= gson.getDelegateAdapter(this, TypeToken.get({{classname}}.class));
|
||||
|
||||
return (TypeAdapter<T>) new TypeAdapter<{{classname}}>() {
|
||||
@Override
|
||||
public void write(JsonWriter out, {{classname}} value) throws IOException {
|
||||
JsonObject obj = thisAdapter.toJsonTree(value).getAsJsonObject();
|
||||
elementAdapter.write(out, obj);
|
||||
}
|
||||
|
||||
@Override
|
||||
public {{classname}} read(JsonReader in) throws IOException {
|
||||
JsonObject obj = elementAdapter.read(in).getAsJsonObject();
|
||||
Set<Entry<String, JsonElement>> entries = obj.entrySet();//will return members of your object
|
||||
// check to see if the JSON string contains additional fields
|
||||
for (Entry<String, JsonElement> entry: entries) {
|
||||
if (!{{classname}}.openapiFields.contains(entry.getKey())) {
|
||||
throw new IllegalArgumentException("The field `" + entry.getKey() + "` in the JSON string is not defined in the `{{classname}}` properties");
|
||||
}
|
||||
}
|
||||
|
||||
{{#requiredVars}}
|
||||
{{#-first}}
|
||||
// check to make sure all required properties/fields are present in the JSON string
|
||||
for (String requiredField : {{classname}}.openapiRequiredFields) {
|
||||
if (obj.get(requiredField) == null) {
|
||||
throw new IllegalArgumentException("The required field `" + requiredField + "` is not found in the JSON string");
|
||||
}
|
||||
}
|
||||
|
||||
{{/-first}}
|
||||
{{/requiredVars}}
|
||||
return thisAdapter.fromJsonTree(obj);
|
||||
}
|
||||
|
||||
}.nullSafe();
|
||||
}
|
||||
}
|
||||
{{/hasChildren}}
|
||||
}
|
420
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/pom.mustache
vendored
Normal file
420
modules/openapi-generator/src/main/resources/Java/libraries/okhttp-gson-nextgen/pom.mustache
vendored
Normal file
@ -0,0 +1,420 @@
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
<groupId>{{groupId}}</groupId>
|
||||
<artifactId>{{artifactId}}</artifactId>
|
||||
<packaging>jar</packaging>
|
||||
<name>{{artifactId}}</name>
|
||||
<version>{{artifactVersion}}</version>
|
||||
<url>{{artifactUrl}}</url>
|
||||
<description>{{artifactDescription}}</description>
|
||||
<scm>
|
||||
<connection>{{scmConnection}}</connection>
|
||||
<developerConnection>{{scmDeveloperConnection}}</developerConnection>
|
||||
<url>{{scmUrl}}</url>
|
||||
</scm>
|
||||
{{#parentOverridden}}
|
||||
<parent>
|
||||
<groupId>{{{parentGroupId}}}</groupId>
|
||||
<artifactId>{{{parentArtifactId}}}</artifactId>
|
||||
<version>{{{parentVersion}}}</version>
|
||||
</parent>
|
||||
{{/parentOverridden}}
|
||||
|
||||
<licenses>
|
||||
<license>
|
||||
<name>{{licenseName}}</name>
|
||||
<url>{{licenseUrl}}</url>
|
||||
<distribution>repo</distribution>
|
||||
</license>
|
||||
</licenses>
|
||||
|
||||
<developers>
|
||||
<developer>
|
||||
<name>{{developerName}}</name>
|
||||
<email>{{developerEmail}}</email>
|
||||
<organization>{{developerOrganization}}</organization>
|
||||
<organizationUrl>{{developerOrganizationUrl}}</organizationUrl>
|
||||
</developer>
|
||||
</developers>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.8.1</version>
|
||||
<configuration>
|
||||
<fork>true</fork>
|
||||
<meminitial>128m</meminitial>
|
||||
<maxmem>512m</maxmem>
|
||||
<compilerArgs>
|
||||
<arg>-Xlint:all</arg>
|
||||
<arg>-J-Xss4m</arg><!-- Compiling the generated JSON.java file may require larger stack size. -->
|
||||
</compilerArgs>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-enforcer-plugin</artifactId>
|
||||
<version>3.0.0</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>enforce-maven</id>
|
||||
<goals>
|
||||
<goal>enforce</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<rules>
|
||||
<requireMavenVersion>
|
||||
<version>2.2.0</version>
|
||||
</requireMavenVersion>
|
||||
</rules>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-surefire-plugin</artifactId>
|
||||
<version>3.0.0-M5</version>
|
||||
<configuration>
|
||||
<systemProperties>
|
||||
<property>
|
||||
<name>loggerPath</name>
|
||||
<value>conf/log4j.properties</value>
|
||||
</property>
|
||||
</systemProperties>
|
||||
<argLine>-Xms512m -Xmx1500m</argLine>
|
||||
<parallel>methods</parallel>
|
||||
<threadCount>10</threadCount>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<artifactId>maven-dependency-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<phase>package</phase>
|
||||
<goals>
|
||||
<goal>copy-dependencies</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<outputDirectory>${project.build.directory}/lib</outputDirectory>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<!-- attach test jar -->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-jar-plugin</artifactId>
|
||||
<version>3.2.0</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<goals>
|
||||
<goal>test-jar</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
<configuration>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.codehaus.mojo</groupId>
|
||||
<artifactId>build-helper-maven-plugin</artifactId>
|
||||
<version>3.2.0</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>add_sources</id>
|
||||
<phase>generate-sources</phase>
|
||||
<goals>
|
||||
<goal>add-source</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<sources>
|
||||
<source>{{{sourceFolder}}}</source>
|
||||
</sources>
|
||||
</configuration>
|
||||
</execution>
|
||||
<execution>
|
||||
<id>add_test_sources</id>
|
||||
<phase>generate-test-sources</phase>
|
||||
<goals>
|
||||
<goal>add-test-source</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<sources>
|
||||
<source>src/test/java</source>
|
||||
</sources>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-javadoc-plugin</artifactId>
|
||||
<version>3.3.1</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>attach-javadocs</id>
|
||||
<goals>
|
||||
<goal>jar</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
<configuration>
|
||||
<doclint>none</doclint>
|
||||
<tags>
|
||||
<tag>
|
||||
<name>http.response.details</name>
|
||||
<placement>a</placement>
|
||||
<head>Http Response Details:</head>
|
||||
</tag>
|
||||
</tags>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-source-plugin</artifactId>
|
||||
<version>3.2.0</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>attach-sources</id>
|
||||
<goals>
|
||||
<goal>jar-no-fork</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<!-- Use spotless plugin to automatically format code, remove unused import, etc
|
||||
To apply changes directly to the file, run `mvn spotless:apply`
|
||||
Ref: https://github.com/diffplug/spotless/tree/main/plugin-maven
|
||||
-->
|
||||
<plugin>
|
||||
<groupId>com.diffplug.spotless</groupId>
|
||||
<artifactId>spotless-maven-plugin</artifactId>
|
||||
<version>${spotless.version}</version>
|
||||
<configuration>
|
||||
<formats>
|
||||
<!-- you can define as many formats as you want, each is independent -->
|
||||
<format>
|
||||
<!-- define the files to apply to -->
|
||||
<includes>
|
||||
<include>.gitignore</include>
|
||||
</includes>
|
||||
<!-- define the steps to apply to those files -->
|
||||
<trimTrailingWhitespace/>
|
||||
<endWithNewline/>
|
||||
<indent>
|
||||
<spaces>true</spaces> <!-- or <tabs>true</tabs> -->
|
||||
<spacesPerTab>4</spacesPerTab> <!-- optional, default is 4 -->
|
||||
</indent>
|
||||
</format>
|
||||
</formats>
|
||||
<!-- define a language-specific format -->
|
||||
<java>
|
||||
<!-- no need to specify files, inferred automatically, but you can if you want -->
|
||||
|
||||
<!-- apply a specific flavor of google-java-format and reflow long strings -->
|
||||
<googleJavaFormat>
|
||||
<version>1.8</version>
|
||||
<style>AOSP</style>
|
||||
<reflowLongStrings>true</reflowLongStrings>
|
||||
</googleJavaFormat>
|
||||
|
||||
<removeUnusedImports/>
|
||||
<importOrder/>
|
||||
|
||||
</java>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>sign-artifacts</id>
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-gpg-plugin</artifactId>
|
||||
<version>3.0.1</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>sign-artifacts</id>
|
||||
<phase>verify</phase>
|
||||
<goals>
|
||||
<goal>sign</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</profile>
|
||||
</profiles>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>io.swagger</groupId>
|
||||
<artifactId>swagger-annotations</artifactId>
|
||||
<version>${swagger-core-version}</version>
|
||||
</dependency>
|
||||
<!-- @Nullable annotation -->
|
||||
<dependency>
|
||||
<groupId>com.google.code.findbugs</groupId>
|
||||
<artifactId>jsr305</artifactId>
|
||||
<version>3.0.2</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.squareup.okhttp3</groupId>
|
||||
<artifactId>okhttp</artifactId>
|
||||
<version>${okhttp-version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.squareup.okhttp3</groupId>
|
||||
<artifactId>logging-interceptor</artifactId>
|
||||
<version>${okhttp-version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.google.code.gson</groupId>
|
||||
<artifactId>gson</artifactId>
|
||||
<version>${gson-version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>io.gsonfire</groupId>
|
||||
<artifactId>gson-fire</artifactId>
|
||||
<version>${gson-fire-version}</version>
|
||||
</dependency>
|
||||
{{#hasOAuthMethods}}
|
||||
<dependency>
|
||||
<groupId>org.apache.oltu.oauth2</groupId>
|
||||
<artifactId>org.apache.oltu.oauth2.client</artifactId>
|
||||
<version>1.0.1</version>
|
||||
</dependency>
|
||||
{{/hasOAuthMethods}}
|
||||
<dependency>
|
||||
<groupId>org.apache.commons</groupId>
|
||||
<artifactId>commons-lang3</artifactId>
|
||||
<version>${commons-lang3-version}</version>
|
||||
</dependency>
|
||||
{{#joda}}
|
||||
<dependency>
|
||||
<groupId>joda-time</groupId>
|
||||
<artifactId>joda-time</artifactId>
|
||||
<version>${jodatime-version}</version>
|
||||
</dependency>
|
||||
{{/joda}}
|
||||
{{#threetenbp}}
|
||||
<dependency>
|
||||
<groupId>org.threeten</groupId>
|
||||
<artifactId>threetenbp</artifactId>
|
||||
<version>${threetenbp-version}</version>
|
||||
</dependency>
|
||||
{{/threetenbp}}
|
||||
{{#dynamicOperations}}
|
||||
<dependency>
|
||||
<groupId>io.swagger.parser.v3</groupId>
|
||||
<artifactId>swagger-parser-v3</artifactId>
|
||||
<version>2.0.28</version>
|
||||
</dependency>
|
||||
{{/dynamicOperations}}
|
||||
{{#useBeanValidation}}
|
||||
<!-- Bean Validation API support -->
|
||||
<dependency>
|
||||
<groupId>jakarta.validation</groupId>
|
||||
<artifactId>jakarta.validation-api</artifactId>
|
||||
<version>${beanvalidation-version}</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
{{/useBeanValidation}}
|
||||
{{#performBeanValidation}}
|
||||
<!-- Bean Validation Impl. used to perform BeanValidation -->
|
||||
<dependency>
|
||||
<groupId>org.hibernate</groupId>
|
||||
<artifactId>hibernate-validator</artifactId>
|
||||
<version>5.4.3.Final</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>jakarta.el</groupId>
|
||||
<artifactId>jakarta.el-api</artifactId>
|
||||
<version>${jakarta.el-version}</version>
|
||||
</dependency>
|
||||
{{/performBeanValidation}}
|
||||
{{#parcelableModel}}
|
||||
<!-- Needed for Parcelable support-->
|
||||
<dependency>
|
||||
<groupId>com.google.android</groupId>
|
||||
<artifactId>android</artifactId>
|
||||
<version>4.1.1.4</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
{{/parcelableModel}}
|
||||
<dependency>
|
||||
<groupId>jakarta.annotation</groupId>
|
||||
<artifactId>jakarta.annotation-api</artifactId>
|
||||
<version>${jakarta-annotation-version}</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
{{#openApiNullable}}
|
||||
<dependency>
|
||||
<groupId>org.openapitools</groupId>
|
||||
<artifactId>jackson-databind-nullable</artifactId>
|
||||
<version>${jackson-databind-nullable-version}</version>
|
||||
</dependency>
|
||||
{{/openApiNullable}}
|
||||
<dependency>
|
||||
<groupId>javax.ws.rs</groupId>
|
||||
<artifactId>jsr311-api</artifactId>
|
||||
<version>1.1.1</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>javax.ws.rs</groupId>
|
||||
<artifactId>javax.ws.rs-api</artifactId>
|
||||
<version>2.0</version>
|
||||
</dependency>
|
||||
<!-- test dependencies -->
|
||||
<dependency>
|
||||
<groupId>junit</groupId>
|
||||
<artifactId>junit</artifactId>
|
||||
<version>${junit-version}</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.mockito</groupId>
|
||||
<artifactId>mockito-core</artifactId>
|
||||
<version>3.12.4</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
<properties>
|
||||
<java.version>1.8</java.version>
|
||||
<maven.compiler.source>${java.version}</maven.compiler.source>
|
||||
<maven.compiler.target>${java.version}</maven.compiler.target>
|
||||
<gson-fire-version>1.8.5</gson-fire-version>
|
||||
<swagger-core-version>1.6.3</swagger-core-version>
|
||||
<okhttp-version>4.9.2</okhttp-version>
|
||||
<gson-version>2.8.8</gson-version>
|
||||
<commons-lang3-version>3.12.0</commons-lang3-version>
|
||||
{{#openApiNullable}}
|
||||
<jackson-databind-nullable-version>0.2.1</jackson-databind-nullable-version>
|
||||
{{/openApiNullable}}
|
||||
{{#joda}}
|
||||
<jodatime-version>2.10.9</jodatime-version>
|
||||
{{/joda}}
|
||||
{{#threetenbp}}
|
||||
<threetenbp-version>1.5.0</threetenbp-version>
|
||||
{{/threetenbp}}
|
||||
<jakarta-annotation-version>1.3.5</jakarta-annotation-version>
|
||||
{{#performBeanValidation}}
|
||||
<jakarta.el-version>3.0.3</jakarta.el-version>
|
||||
{{/performBeanValidation}}
|
||||
{{#useBeanValidation}}
|
||||
<beanvalidation-version>2.0.2</beanvalidation-version>
|
||||
{{/useBeanValidation}}
|
||||
<junit-version>4.13.2</junit-version>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
<spotless.version>2.17.3</spotless.version>
|
||||
</properties>
|
||||
</project>
|
@ -1081,6 +1081,8 @@ public class ApiClient {
|
||||
} else if (obj instanceof File) {
|
||||
// File body parameter support.
|
||||
return RequestBody.create((File) obj, MediaType.parse(contentType));
|
||||
} else if ("text/plain".equals(contentType) && obj instanceof String) {
|
||||
return RequestBody.create((String) obj, MediaType.parse(contentType));
|
||||
} else if (isJsonMime(contentType)) {
|
||||
String content;
|
||||
if (obj != null) {
|
||||
@ -1314,8 +1316,8 @@ public class ApiClient {
|
||||
* @return The HTTP call
|
||||
* @throws org.openapitools.client.ApiException If fail to serialize the request body object
|
||||
*/
|
||||
public Call buildCall(String path, String method, List<Pair> queryParams, List<Pair> collectionQueryParams, Object body, Map<String, String> headerParams, Map<String, String> cookieParams, Map<String, Object> formParams, String[] authNames, ApiCallback callback) throws ApiException {
|
||||
Request request = buildRequest(path, method, queryParams, collectionQueryParams, body, headerParams, cookieParams, formParams, authNames, callback);
|
||||
public Call buildCall(String baseUrl, String path, String method, List<Pair> queryParams, List<Pair> collectionQueryParams, Object body, Map<String, String> headerParams, Map<String, String> cookieParams, Map<String, Object> formParams, String[] authNames, ApiCallback callback) throws ApiException {
|
||||
Request request = buildRequest(baseUrl, path, method, queryParams, collectionQueryParams, body, headerParams, cookieParams, formParams, authNames, callback);
|
||||
|
||||
return httpClient.newCall(request);
|
||||
}
|
||||
@ -1336,12 +1338,12 @@ public class ApiClient {
|
||||
* @return The HTTP request
|
||||
* @throws org.openapitools.client.ApiException If fail to serialize the request body object
|
||||
*/
|
||||
public Request buildRequest(String path, String method, List<Pair> queryParams, List<Pair> collectionQueryParams, Object body, Map<String, String> headerParams, Map<String, String> cookieParams, Map<String, Object> formParams, String[] authNames, ApiCallback callback) throws ApiException {
|
||||
public Request buildRequest(String baseUrl, String path, String method, List<Pair> queryParams, List<Pair> collectionQueryParams, Object body, Map<String, String> headerParams, Map<String, String> cookieParams, Map<String, Object> formParams, String[] authNames, ApiCallback callback) throws ApiException {
|
||||
// aggregate queryParams (non-collection) and collectionQueryParams into allQueryParams
|
||||
List<Pair> allQueryParams = new ArrayList<Pair>(queryParams);
|
||||
allQueryParams.addAll(collectionQueryParams);
|
||||
|
||||
final String url = buildUrl(path, queryParams, collectionQueryParams);
|
||||
final String url = buildUrl(baseUrl, path, queryParams, collectionQueryParams);
|
||||
|
||||
// prepare HTTP request body
|
||||
RequestBody reqBody;
|
||||
@ -1396,9 +1398,13 @@ public class ApiClient {
|
||||
* @param collectionQueryParams The collection query parameters
|
||||
* @return The full URL
|
||||
*/
|
||||
public String buildUrl(String path, List<Pair> queryParams, List<Pair> collectionQueryParams) {
|
||||
public String buildUrl(String baseUrl, String path, List<Pair> queryParams, List<Pair> collectionQueryParams) {
|
||||
final StringBuilder url = new StringBuilder();
|
||||
url.append(basePath).append(path);
|
||||
if (baseUrl != null) {
|
||||
url.append(baseUrl).append(path);
|
||||
} else {
|
||||
url.append(basePath).append(path);
|
||||
}
|
||||
|
||||
if (queryParams != null && !queryParams.isEmpty()) {
|
||||
// support (constant) query string in `path`, e.g. "/posts?draft=1"
|
||||
|
@ -55,6 +55,8 @@ import java.io.InputStream;
|
||||
{{#operations}}
|
||||
public class {{classname}} {
|
||||
private ApiClient localVarApiClient;
|
||||
private int localHostIndex;
|
||||
private String localCustomBaseUrl;
|
||||
|
||||
public {{classname}}() {
|
||||
this(Configuration.getDefaultApiClient());
|
||||
@ -72,6 +74,22 @@ public class {{classname}} {
|
||||
this.localVarApiClient = apiClient;
|
||||
}
|
||||
|
||||
public int getHostIndex() {
|
||||
return localHostIndex;
|
||||
}
|
||||
|
||||
public void setHostIndex(int hostIndex) {
|
||||
this.localHostIndex = hostIndex;
|
||||
}
|
||||
|
||||
public String getCustomBaseUrl() {
|
||||
return localCustomBaseUrl;
|
||||
}
|
||||
|
||||
public void setCustomBaseUrl(String customBaseUrl) {
|
||||
this.localCustomBaseUrl = customBaseUrl;
|
||||
}
|
||||
|
||||
{{#operation}}
|
||||
{{^vendorExtensions.x-group-parameters}}/**
|
||||
* Build call for {{operationId}}{{#allParams}}
|
||||
@ -100,6 +118,20 @@ public class {{classname}} {
|
||||
@Deprecated
|
||||
{{/isDeprecated}}
|
||||
public{{/vendorExtensions.x-group-parameters}}{{#vendorExtensions.x-group-parameters}}private{{/vendorExtensions.x-group-parameters}} okhttp3.Call {{operationId}}Call({{#allParams}}{{{dataType}}} {{paramName}}, {{/allParams}}final ApiCallback _callback) throws ApiException {
|
||||
String basePath = null;
|
||||
|
||||
// Operation Servers
|
||||
String[] localBasePaths = new String[] { {{#servers}}"{{{url}}}"{{^-last}}, {{/-last}}{{/servers}} };
|
||||
|
||||
// Determine Base Path to Use
|
||||
if (localCustomBaseUrl != null){
|
||||
basePath = localCustomBaseUrl;
|
||||
} else if ( localBasePaths.length > 0 ) {
|
||||
basePath = localBasePaths[localHostIndex];
|
||||
} else {
|
||||
basePath = null;
|
||||
}
|
||||
|
||||
Object localVarPostBody = {{#bodyParam}}{{paramName}}{{/bodyParam}}{{^bodyParam}}null{{/bodyParam}};
|
||||
|
||||
// create path and map variables
|
||||
@ -177,7 +209,7 @@ public class {{classname}} {
|
||||
}
|
||||
|
||||
String[] localVarAuthNames = new String[] { {{#authMethods}}"{{name}}"{{^-last}}, {{/-last}}{{/authMethods}} };
|
||||
return localVarApiClient.buildCall(localVarPath, {{^dynamicOperations}}"{{httpMethod}}"{{/dynamicOperations}}{{#dynamicOperations}}apiOperation.getMethod(){{/dynamicOperations}}, localVarQueryParams, localVarCollectionQueryParams, localVarPostBody, localVarHeaderParams, localVarCookieParams, localVarFormParams, localVarAuthNames, _callback);
|
||||
return localVarApiClient.buildCall(basePath, localVarPath, {{^dynamicOperations}}"{{httpMethod}}"{{/dynamicOperations}}{{#dynamicOperations}}apiOperation.getMethod(){{/dynamicOperations}}, localVarQueryParams, localVarCollectionQueryParams, localVarPostBody, localVarHeaderParams, localVarCookieParams, localVarFormParams, localVarAuthNames, _callback);
|
||||
}
|
||||
|
||||
{{#isDeprecated}}
|
||||
|
@ -34,6 +34,7 @@ import org.springframework.util.StringUtils;
|
||||
import org.springframework.web.client.RestClientException;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
import org.springframework.web.util.UriComponentsBuilder;
|
||||
import org.springframework.web.util.DefaultUriBuilderFactory;
|
||||
{{#threetenbp}}
|
||||
import org.threeten.bp.*;
|
||||
import com.fasterxml.jackson.datatype.threetenbp.ThreeTenModule;
|
||||
@ -622,6 +623,12 @@ public class ApiClient{{#jsr310}} extends JavaTimeFormatter{{/jsr310}} {
|
||||
* @return path with placeholders replaced by variables
|
||||
*/
|
||||
public String expandPath(String pathTemplate, Map<String, Object> variables) {
|
||||
// disable default URL encoding
|
||||
DefaultUriBuilderFactory uriBuilderFactory = new DefaultUriBuilderFactory();
|
||||
uriBuilderFactory.setEncodingMode(DefaultUriBuilderFactory.EncodingMode.NONE);
|
||||
final RestTemplate restTemplate = new RestTemplate();
|
||||
restTemplate.setUriTemplateHandler(uriBuilderFactory);
|
||||
|
||||
return restTemplate.getUriTemplateHandler().expand(pathTemplate, variables).toString();
|
||||
}
|
||||
|
||||
@ -632,27 +639,33 @@ public class ApiClient{{#jsr310}} extends JavaTimeFormatter{{/jsr310}} {
|
||||
* @param uriParams The path parameters
|
||||
* return templatized query string
|
||||
*/
|
||||
private String generateQueryUri(MultiValueMap<String, String> queryParams, Map<String, Object> uriParams) {
|
||||
public String generateQueryUri(MultiValueMap<String, String> queryParams, Map<String, Object> uriParams) {
|
||||
StringBuilder queryBuilder = new StringBuilder();
|
||||
queryParams.forEach((name, values) -> {
|
||||
if (CollectionUtils.isEmpty(values)) {
|
||||
if (queryBuilder.length() != 0) {
|
||||
queryBuilder.append('&');
|
||||
}
|
||||
queryBuilder.append(name);
|
||||
} else {
|
||||
int valueItemCounter = 0;
|
||||
for (Object value : values) {
|
||||
try {
|
||||
final String encodedName = URLEncoder.encode(name.toString(), "UTF-8");
|
||||
if (CollectionUtils.isEmpty(values)) {
|
||||
if (queryBuilder.length() != 0) {
|
||||
queryBuilder.append('&');
|
||||
}
|
||||
queryBuilder.append(name);
|
||||
if (value != null) {
|
||||
String templatizedKey = name + valueItemCounter++;
|
||||
uriParams.put(templatizedKey, value.toString());
|
||||
queryBuilder.append('=').append("{").append(templatizedKey).append("}");
|
||||
queryBuilder.append(encodedName);
|
||||
} else {
|
||||
int valueItemCounter = 0;
|
||||
for (Object value : values) {
|
||||
if (queryBuilder.length() != 0) {
|
||||
queryBuilder.append('&');
|
||||
}
|
||||
queryBuilder.append(encodedName);
|
||||
if (value != null) {
|
||||
String templatizedKey = encodedName + valueItemCounter++;
|
||||
final String encodedValue = URLEncoder.encode(value.toString(), "UTF-8");
|
||||
uriParams.put(templatizedKey, encodedValue);
|
||||
queryBuilder.append('=').append("{").append(templatizedKey).append("}");
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (UnsupportedEncodingException e) {
|
||||
|
||||
}
|
||||
});
|
||||
return queryBuilder.toString();
|
||||
|
@ -23,6 +23,7 @@ org.openapitools.codegen.languages.CSharpClientCodegen
|
||||
org.openapitools.codegen.languages.CSharpNetCoreClientCodegen
|
||||
org.openapitools.codegen.languages.CSharpDotNet2ClientCodegen
|
||||
org.openapitools.codegen.languages.CSharpNancyFXServerCodegen
|
||||
org.openapitools.codegen.languages.CsharpNetcoreFunctionsServerCodegen
|
||||
org.openapitools.codegen.languages.DartClientCodegen
|
||||
org.openapitools.codegen.languages.DartDioClientCodegen
|
||||
org.openapitools.codegen.languages.DartDioNextClientCodegen
|
||||
|
@ -104,7 +104,7 @@ Operation Id:: {{nickname}}
|
||||
|
||||
| {{code}}
|
||||
| {{message}}
|
||||
| {{^simpleType}}{{dataType}}[<<{{baseType}}>>]{{/simpleType}} {{#simpleType}}<<{{dataType}}>>{{/simpleType}}
|
||||
| {{#containerType}}{{dataType}}[<<{{baseType}}>>]{{/containerType}} {{^containerType}}<<{{dataType}}>>{{/containerType}}
|
||||
|
||||
{{/responses}}
|
||||
|===
|
||||
|
@ -0,0 +1,68 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace {{packageName}}.{{modelPackage}}
|
||||
{
|
||||
/// <summary>
|
||||
/// Abstract base class for oneOf, anyOf schemas in the OpenAPI specification
|
||||
/// </summary>
|
||||
{{>visibility}} abstract partial class AbstractOpenAPISchema
|
||||
{
|
||||
/// <summary>
|
||||
/// Custom JSON serializer
|
||||
/// </summary>
|
||||
static public readonly JsonSerializerSettings SerializerSettings = new JsonSerializerSettings
|
||||
{
|
||||
// OpenAPI generated types generally hide default constructors.
|
||||
ConstructorHandling = ConstructorHandling.AllowNonPublicDefaultConstructor,
|
||||
MissingMemberHandling = MissingMemberHandling.Error,
|
||||
ContractResolver = new DefaultContractResolver
|
||||
{
|
||||
NamingStrategy = new CamelCaseNamingStrategy
|
||||
{
|
||||
OverrideSpecifiedNames = false
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/// <summary>
|
||||
/// Custom JSON serializer for objects with additional properties
|
||||
/// </summary>
|
||||
static public readonly JsonSerializerSettings AdditionalPropertiesSerializerSettings = new JsonSerializerSettings
|
||||
{
|
||||
// OpenAPI generated types generally hide default constructors.
|
||||
ConstructorHandling = ConstructorHandling.AllowNonPublicDefaultConstructor,
|
||||
MissingMemberHandling = MissingMemberHandling.Ignore,
|
||||
ContractResolver = new DefaultContractResolver
|
||||
{
|
||||
NamingStrategy = new CamelCaseNamingStrategy
|
||||
{
|
||||
OverrideSpecifiedNames = false
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/// <summary>
|
||||
/// Gets or Sets the actual instance
|
||||
/// </summary>
|
||||
public abstract Object ActualInstance { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or Sets IsNullable to indicate whether the instance is nullable
|
||||
/// </summary>
|
||||
public bool IsNullable { get; protected set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or Sets the schema type, which can be either `oneOf` or `anyOf`
|
||||
/// </summary>
|
||||
public string SchemaType { get; protected set; }
|
||||
|
||||
/// <summary>
|
||||
/// Converts the instance into JSON string.
|
||||
/// </summary>
|
||||
public abstract string ToJson();
|
||||
}
|
||||
}
|
867
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ApiClient.mustache
vendored
Normal file
867
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ApiClient.mustache
vendored
Normal file
@ -0,0 +1,867 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Net;
|
||||
using System.Reflection;
|
||||
using System.Runtime.Serialization;
|
||||
using System.Runtime.Serialization.Formatters;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
using System.Text.RegularExpressions;
|
||||
using System.Threading.Tasks;
|
||||
{{^netStandard}}
|
||||
using System.Web;
|
||||
{{/netStandard}}
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
using ErrorEventArgs = Newtonsoft.Json.Serialization.ErrorEventArgs;
|
||||
using RestSharp;
|
||||
using RestSharp.Deserializers;
|
||||
using RestSharpMethod = RestSharp.Method;
|
||||
{{#useWebRequest}}
|
||||
using System.Net.Http;
|
||||
{{/useWebRequest}}
|
||||
{{#supportsRetry}}
|
||||
using Polly;
|
||||
{{/supportsRetry}}
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Allows RestSharp to Serialize/Deserialize JSON using our custom logic, but only when ContentType is JSON.
|
||||
/// </summary>
|
||||
internal class CustomJsonCodec : RestSharp.Serializers.ISerializer, RestSharp.Deserializers.IDeserializer
|
||||
{
|
||||
private readonly IReadableConfiguration _configuration;
|
||||
private static readonly string _contentType = "application/json";
|
||||
private readonly JsonSerializerSettings _serializerSettings = new JsonSerializerSettings
|
||||
{
|
||||
// OpenAPI generated types generally hide default constructors.
|
||||
ConstructorHandling = ConstructorHandling.AllowNonPublicDefaultConstructor,
|
||||
ContractResolver = new DefaultContractResolver
|
||||
{
|
||||
NamingStrategy = new CamelCaseNamingStrategy
|
||||
{
|
||||
OverrideSpecifiedNames = false
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
public CustomJsonCodec(IReadableConfiguration configuration)
|
||||
{
|
||||
_configuration = configuration;
|
||||
}
|
||||
|
||||
public CustomJsonCodec(JsonSerializerSettings serializerSettings, IReadableConfiguration configuration)
|
||||
{
|
||||
_serializerSettings = serializerSettings;
|
||||
_configuration = configuration;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Serialize the object into a JSON string.
|
||||
/// </summary>
|
||||
/// <param name="obj">Object to be serialized.</param>
|
||||
/// <returns>A JSON string.</returns>
|
||||
public string Serialize(object obj)
|
||||
{
|
||||
if (obj != null && obj is {{{packageName}}}.{{modelPackage}}.AbstractOpenAPISchema)
|
||||
{
|
||||
// the object to be serialized is an oneOf/anyOf schema
|
||||
return (({{{packageName}}}.{{modelPackage}}.AbstractOpenAPISchema)obj).ToJson();
|
||||
}
|
||||
else
|
||||
{
|
||||
return JsonConvert.SerializeObject(obj, _serializerSettings);
|
||||
}
|
||||
}
|
||||
|
||||
public T Deserialize<T>(IRestResponse response)
|
||||
{
|
||||
var result = (T)Deserialize(response, typeof(T));
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Deserialize the JSON string into a proper object.
|
||||
/// </summary>
|
||||
/// <param name="response">The HTTP response.</param>
|
||||
/// <param name="type">Object type.</param>
|
||||
/// <returns>Object representation of the JSON string.</returns>
|
||||
internal object Deserialize(IRestResponse response, Type type)
|
||||
{
|
||||
if (type == typeof(byte[])) // return byte array
|
||||
{
|
||||
return response.RawBytes;
|
||||
}
|
||||
|
||||
// TODO: ? if (type.IsAssignableFrom(typeof(Stream)))
|
||||
if (type == typeof(Stream))
|
||||
{
|
||||
var bytes = response.RawBytes;
|
||||
if (response.Headers != null)
|
||||
{
|
||||
var filePath = string.IsNullOrEmpty(_configuration.TempFolderPath)
|
||||
? Path.GetTempPath()
|
||||
: _configuration.TempFolderPath;
|
||||
var regex = new Regex(@"Content-Disposition=.*filename=['""]?([^'""\s]+)['""]?$");
|
||||
foreach (var header in response.Headers)
|
||||
{
|
||||
var match = regex.Match(header.ToString());
|
||||
if (match.Success)
|
||||
{
|
||||
string fileName = filePath + ClientUtils.SanitizeFilename(match.Groups[1].Value.Replace("\"", "").Replace("'", ""));
|
||||
File.WriteAllBytes(fileName, bytes);
|
||||
return new FileStream(fileName, FileMode.Open);
|
||||
}
|
||||
}
|
||||
}
|
||||
var stream = new MemoryStream(bytes);
|
||||
return stream;
|
||||
}
|
||||
|
||||
if (type.Name.StartsWith("System.Nullable`1[[System.DateTime")) // return a datetime object
|
||||
{
|
||||
return DateTime.Parse(response.Content, null, System.Globalization.DateTimeStyles.RoundtripKind);
|
||||
}
|
||||
|
||||
if (type == typeof(string) || type.Name.StartsWith("System.Nullable")) // return primitive type
|
||||
{
|
||||
return Convert.ChangeType(response.Content, type);
|
||||
}
|
||||
|
||||
// at this point, it must be a model (json)
|
||||
try
|
||||
{
|
||||
return JsonConvert.DeserializeObject(response.Content, type, _serializerSettings);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new ApiException(500, e.Message);
|
||||
}
|
||||
}
|
||||
|
||||
public string RootElement { get; set; }
|
||||
public string Namespace { get; set; }
|
||||
public string DateFormat { get; set; }
|
||||
|
||||
public string ContentType
|
||||
{
|
||||
get { return _contentType; }
|
||||
set { throw new InvalidOperationException("Not allowed to set content type."); }
|
||||
}
|
||||
}
|
||||
{{! NOTE: Any changes related to RestSharp should be done in this class. All other client classes are for extensibility by consumers.}}
|
||||
/// <summary>
|
||||
/// Provides a default implementation of an Api client (both synchronous and asynchronous implementatios),
|
||||
/// encapsulating general REST accessor use cases.
|
||||
/// </summary>
|
||||
{{>visibility}} partial class ApiClient : ISynchronousClient{{#supportsAsync}}, IAsynchronousClient{{/supportsAsync}}
|
||||
{
|
||||
private readonly string _baseUrl;
|
||||
|
||||
/// <summary>
|
||||
/// Specifies the settings on a <see cref="JsonSerializer" /> object.
|
||||
/// These settings can be adjusted to accomodate custom serialization rules.
|
||||
/// </summary>
|
||||
public JsonSerializerSettings SerializerSettings { get; set; } = new JsonSerializerSettings
|
||||
{
|
||||
// OpenAPI generated types generally hide default constructors.
|
||||
ConstructorHandling = ConstructorHandling.AllowNonPublicDefaultConstructor,
|
||||
ContractResolver = new DefaultContractResolver
|
||||
{
|
||||
NamingStrategy = new CamelCaseNamingStrategy
|
||||
{
|
||||
OverrideSpecifiedNames = false
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/// <summary>
|
||||
/// Allows for extending request processing for <see cref="ApiClient"/> generated code.
|
||||
/// </summary>
|
||||
/// <param name="request">The RestSharp request object</param>
|
||||
partial void InterceptRequest(IRestRequest request);
|
||||
|
||||
/// <summary>
|
||||
/// Allows for extending response processing for <see cref="ApiClient"/> generated code.
|
||||
/// </summary>
|
||||
/// <param name="request">The RestSharp request object</param>
|
||||
/// <param name="response">The RestSharp response object</param>
|
||||
partial void InterceptResponse(IRestRequest request, IRestResponse response);
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiClient" />, defaulting to the global configurations' base url.
|
||||
/// </summary>
|
||||
public ApiClient()
|
||||
{
|
||||
_baseUrl = {{packageName}}.Client.GlobalConfiguration.Instance.BasePath;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiClient" />
|
||||
/// </summary>
|
||||
/// <param name="basePath">The target service's base path in URL format.</param>
|
||||
/// <exception cref="ArgumentException"></exception>
|
||||
public ApiClient(string basePath)
|
||||
{
|
||||
if (string.IsNullOrEmpty(basePath))
|
||||
throw new ArgumentException("basePath cannot be empty");
|
||||
|
||||
_baseUrl = basePath;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Constructs the RestSharp version of an http method
|
||||
/// </summary>
|
||||
/// <param name="method">Swagger Client Custom HttpMethod</param>
|
||||
/// <returns>RestSharp's HttpMethod instance.</returns>
|
||||
/// <exception cref="ArgumentOutOfRangeException"></exception>
|
||||
private RestSharpMethod Method(HttpMethod method)
|
||||
{
|
||||
RestSharpMethod other;
|
||||
switch (method)
|
||||
{
|
||||
case HttpMethod.Get:
|
||||
other = RestSharpMethod.GET;
|
||||
break;
|
||||
case HttpMethod.Post:
|
||||
other = RestSharpMethod.POST;
|
||||
break;
|
||||
case HttpMethod.Put:
|
||||
other = RestSharpMethod.PUT;
|
||||
break;
|
||||
case HttpMethod.Delete:
|
||||
other = RestSharpMethod.DELETE;
|
||||
break;
|
||||
case HttpMethod.Head:
|
||||
other = RestSharpMethod.HEAD;
|
||||
break;
|
||||
case HttpMethod.Options:
|
||||
other = RestSharpMethod.OPTIONS;
|
||||
break;
|
||||
case HttpMethod.Patch:
|
||||
other = RestSharpMethod.PATCH;
|
||||
break;
|
||||
default:
|
||||
throw new ArgumentOutOfRangeException("method", method, null);
|
||||
}
|
||||
|
||||
return other;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Provides all logic for constructing a new RestSharp <see cref="RestRequest"/>.
|
||||
/// At this point, all information for querying the service is known. Here, it is simply
|
||||
/// mapped into the RestSharp request.
|
||||
/// </summary>
|
||||
/// <param name="method">The http verb.</param>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <returns>[private] A new RestRequest instance.</returns>
|
||||
/// <exception cref="ArgumentNullException"></exception>
|
||||
private RestRequest NewRequest(
|
||||
HttpMethod method,
|
||||
string path,
|
||||
RequestOptions options,
|
||||
IReadableConfiguration configuration)
|
||||
{
|
||||
if (path == null) throw new ArgumentNullException("path");
|
||||
if (options == null) throw new ArgumentNullException("options");
|
||||
if (configuration == null) throw new ArgumentNullException("configuration");
|
||||
|
||||
RestRequest request = new RestRequest(Method(method))
|
||||
{
|
||||
Resource = path,
|
||||
JsonSerializer = new CustomJsonCodec(SerializerSettings, configuration)
|
||||
};
|
||||
|
||||
if (options.PathParameters != null)
|
||||
{
|
||||
foreach (var pathParam in options.PathParameters)
|
||||
{
|
||||
request.AddParameter(pathParam.Key, pathParam.Value, ParameterType.UrlSegment);
|
||||
}
|
||||
}
|
||||
|
||||
if (options.QueryParameters != null)
|
||||
{
|
||||
foreach (var queryParam in options.QueryParameters)
|
||||
{
|
||||
foreach (var value in queryParam.Value)
|
||||
{
|
||||
request.AddQueryParameter(queryParam.Key, value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (configuration.DefaultHeaders != null)
|
||||
{
|
||||
foreach (var headerParam in configuration.DefaultHeaders)
|
||||
{
|
||||
request.AddHeader(headerParam.Key, headerParam.Value);
|
||||
}
|
||||
}
|
||||
|
||||
if (options.HeaderParameters != null)
|
||||
{
|
||||
foreach (var headerParam in options.HeaderParameters)
|
||||
{
|
||||
foreach (var value in headerParam.Value)
|
||||
{
|
||||
request.AddHeader(headerParam.Key, value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (options.FormParameters != null)
|
||||
{
|
||||
foreach (var formParam in options.FormParameters)
|
||||
{
|
||||
request.AddParameter(formParam.Key, formParam.Value);
|
||||
}
|
||||
}
|
||||
|
||||
if (options.Data != null)
|
||||
{
|
||||
if (options.Data is Stream stream)
|
||||
{
|
||||
var contentType = "application/octet-stream";
|
||||
if (options.HeaderParameters != null)
|
||||
{
|
||||
var contentTypes = options.HeaderParameters["Content-Type"];
|
||||
contentType = contentTypes[0];
|
||||
}
|
||||
|
||||
var bytes = ClientUtils.ReadAsBytes(stream);
|
||||
request.AddParameter(contentType, bytes, ParameterType.RequestBody);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (options.HeaderParameters != null)
|
||||
{
|
||||
var contentTypes = options.HeaderParameters["Content-Type"];
|
||||
if (contentTypes == null || contentTypes.Any(header => header.Contains("application/json")))
|
||||
{
|
||||
request.RequestFormat = DataFormat.Json;
|
||||
}
|
||||
else
|
||||
{
|
||||
// TODO: Generated client user should add additional handlers. RestSharp only supports XML and JSON, with XML as default.
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Here, we'll assume JSON APIs are more common. XML can be forced by adding produces/consumes to openapi spec explicitly.
|
||||
request.RequestFormat = DataFormat.Json;
|
||||
}
|
||||
|
||||
request.AddJsonBody(options.Data);
|
||||
}
|
||||
}
|
||||
|
||||
if (options.FileParameters != null)
|
||||
{
|
||||
foreach (var fileParam in options.FileParameters)
|
||||
{
|
||||
var bytes = ClientUtils.ReadAsBytes(fileParam.Value);
|
||||
var fileStream = fileParam.Value as FileStream;
|
||||
if (fileStream != null)
|
||||
request.Files.Add(FileParameter.Create(fileParam.Key, bytes, System.IO.Path.GetFileName(fileStream.Name)));
|
||||
else
|
||||
request.Files.Add(FileParameter.Create(fileParam.Key, bytes, "no_file_name_provided"));
|
||||
}
|
||||
}
|
||||
|
||||
if (options.Cookies != null && options.Cookies.Count > 0)
|
||||
{
|
||||
foreach (var cookie in options.Cookies)
|
||||
{
|
||||
request.AddCookie(cookie.Name, cookie.Value);
|
||||
}
|
||||
}
|
||||
|
||||
return request;
|
||||
}
|
||||
|
||||
private ApiResponse<T> ToApiResponse<T>(IRestResponse<T> response)
|
||||
{
|
||||
T result = response.Data;
|
||||
string rawContent = response.Content;
|
||||
|
||||
var transformed = new ApiResponse<T>(response.StatusCode, new Multimap<string, string>({{#caseInsensitiveResponseHeaders}}StringComparer.OrdinalIgnoreCase{{/caseInsensitiveResponseHeaders}}), result, rawContent)
|
||||
{
|
||||
ErrorText = response.ErrorMessage,
|
||||
Cookies = new List<Cookie>()
|
||||
};
|
||||
|
||||
if (response.Headers != null)
|
||||
{
|
||||
foreach (var responseHeader in response.Headers)
|
||||
{
|
||||
transformed.Headers.Add(responseHeader.Name, ClientUtils.ParameterToString(responseHeader.Value));
|
||||
}
|
||||
}
|
||||
|
||||
if (response.Cookies != null)
|
||||
{
|
||||
foreach (var responseCookies in response.Cookies)
|
||||
{
|
||||
transformed.Cookies.Add(
|
||||
new Cookie(
|
||||
responseCookies.Name,
|
||||
responseCookies.Value,
|
||||
responseCookies.Path,
|
||||
responseCookies.Domain)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
return transformed;
|
||||
}
|
||||
|
||||
private ApiResponse<T> Exec<T>(RestRequest req, IReadableConfiguration configuration)
|
||||
{
|
||||
RestClient client = new RestClient(_baseUrl);
|
||||
|
||||
client.ClearHandlers();
|
||||
var existingDeserializer = req.JsonSerializer as IDeserializer;
|
||||
if (existingDeserializer != null)
|
||||
{
|
||||
client.AddHandler("application/json", () => existingDeserializer);
|
||||
client.AddHandler("text/json", () => existingDeserializer);
|
||||
client.AddHandler("text/x-json", () => existingDeserializer);
|
||||
client.AddHandler("text/javascript", () => existingDeserializer);
|
||||
client.AddHandler("*+json", () => existingDeserializer);
|
||||
}
|
||||
else
|
||||
{
|
||||
var customDeserializer = new CustomJsonCodec(SerializerSettings, configuration);
|
||||
client.AddHandler("application/json", () => customDeserializer);
|
||||
client.AddHandler("text/json", () => customDeserializer);
|
||||
client.AddHandler("text/x-json", () => customDeserializer);
|
||||
client.AddHandler("text/javascript", () => customDeserializer);
|
||||
client.AddHandler("*+json", () => customDeserializer);
|
||||
}
|
||||
|
||||
var xmlDeserializer = new XmlDeserializer();
|
||||
client.AddHandler("application/xml", () => xmlDeserializer);
|
||||
client.AddHandler("text/xml", () => xmlDeserializer);
|
||||
client.AddHandler("*+xml", () => xmlDeserializer);
|
||||
client.AddHandler("*", () => xmlDeserializer);
|
||||
|
||||
client.Timeout = configuration.Timeout;
|
||||
|
||||
if (configuration.Proxy != null)
|
||||
{
|
||||
client.Proxy = configuration.Proxy;
|
||||
}
|
||||
|
||||
if (configuration.UserAgent != null)
|
||||
{
|
||||
client.UserAgent = configuration.UserAgent;
|
||||
}
|
||||
|
||||
if (configuration.ClientCertificates != null)
|
||||
{
|
||||
client.ClientCertificates = configuration.ClientCertificates;
|
||||
}
|
||||
|
||||
InterceptRequest(req);
|
||||
|
||||
IRestResponse<T> response;
|
||||
if (RetryConfiguration.RetryPolicy != null)
|
||||
{
|
||||
var policy = RetryConfiguration.RetryPolicy;
|
||||
var policyResult = policy.ExecuteAndCapture(() => client.Execute(req));
|
||||
response = (policyResult.Outcome == OutcomeType.Successful) ? client.Deserialize<T>(policyResult.Result) : new RestResponse<T>
|
||||
{
|
||||
Request = req,
|
||||
ErrorException = policyResult.FinalException
|
||||
};
|
||||
}
|
||||
else
|
||||
{
|
||||
response = client.Execute<T>(req);
|
||||
}
|
||||
|
||||
// if the response type is oneOf/anyOf, call FromJSON to deserialize the data
|
||||
if (typeof({{{packageName}}}.{{modelPackage}}.AbstractOpenAPISchema).IsAssignableFrom(typeof(T)))
|
||||
{
|
||||
response.Data = (T) typeof(T).GetMethod("FromJson").Invoke(null, new object[] { response.Content });
|
||||
}
|
||||
else if (typeof(T).Name == "Stream") // for binary response
|
||||
{
|
||||
response.Data = (T)(object)new MemoryStream(response.RawBytes);
|
||||
}
|
||||
|
||||
InterceptResponse(req, response);
|
||||
|
||||
var result = ToApiResponse(response);
|
||||
if (response.ErrorMessage != null)
|
||||
{
|
||||
result.ErrorText = response.ErrorMessage;
|
||||
}
|
||||
|
||||
if (response.Cookies != null && response.Cookies.Count > 0)
|
||||
{
|
||||
if (result.Cookies == null) result.Cookies = new List<Cookie>();
|
||||
foreach (var restResponseCookie in response.Cookies)
|
||||
{
|
||||
var cookie = new Cookie(
|
||||
restResponseCookie.Name,
|
||||
restResponseCookie.Value,
|
||||
restResponseCookie.Path,
|
||||
restResponseCookie.Domain
|
||||
)
|
||||
{
|
||||
Comment = restResponseCookie.Comment,
|
||||
CommentUri = restResponseCookie.CommentUri,
|
||||
Discard = restResponseCookie.Discard,
|
||||
Expired = restResponseCookie.Expired,
|
||||
Expires = restResponseCookie.Expires,
|
||||
HttpOnly = restResponseCookie.HttpOnly,
|
||||
Port = restResponseCookie.Port,
|
||||
Secure = restResponseCookie.Secure,
|
||||
Version = restResponseCookie.Version
|
||||
};
|
||||
|
||||
result.Cookies.Add(cookie);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
{{#supportsAsync}}
|
||||
private async Task<ApiResponse<T>> ExecAsync<T>(RestRequest req, IReadableConfiguration configuration, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken))
|
||||
{
|
||||
RestClient client = new RestClient(_baseUrl);
|
||||
|
||||
client.ClearHandlers();
|
||||
var existingDeserializer = req.JsonSerializer as IDeserializer;
|
||||
if (existingDeserializer != null)
|
||||
{
|
||||
client.AddHandler("application/json", () => existingDeserializer);
|
||||
client.AddHandler("text/json", () => existingDeserializer);
|
||||
client.AddHandler("text/x-json", () => existingDeserializer);
|
||||
client.AddHandler("text/javascript", () => existingDeserializer);
|
||||
client.AddHandler("*+json", () => existingDeserializer);
|
||||
}
|
||||
else
|
||||
{
|
||||
var customDeserializer = new CustomJsonCodec(SerializerSettings, configuration);
|
||||
client.AddHandler("application/json", () => customDeserializer);
|
||||
client.AddHandler("text/json", () => customDeserializer);
|
||||
client.AddHandler("text/x-json", () => customDeserializer);
|
||||
client.AddHandler("text/javascript", () => customDeserializer);
|
||||
client.AddHandler("*+json", () => customDeserializer);
|
||||
}
|
||||
|
||||
var xmlDeserializer = new XmlDeserializer();
|
||||
client.AddHandler("application/xml", () => xmlDeserializer);
|
||||
client.AddHandler("text/xml", () => xmlDeserializer);
|
||||
client.AddHandler("*+xml", () => xmlDeserializer);
|
||||
client.AddHandler("*", () => xmlDeserializer);
|
||||
|
||||
client.Timeout = configuration.Timeout;
|
||||
|
||||
if (configuration.Proxy != null)
|
||||
{
|
||||
client.Proxy = configuration.Proxy;
|
||||
}
|
||||
|
||||
if (configuration.UserAgent != null)
|
||||
{
|
||||
client.UserAgent = configuration.UserAgent;
|
||||
}
|
||||
|
||||
if (configuration.ClientCertificates != null)
|
||||
{
|
||||
client.ClientCertificates = configuration.ClientCertificates;
|
||||
}
|
||||
|
||||
InterceptRequest(req);
|
||||
|
||||
IRestResponse<T> response;
|
||||
{{#supportsRetry}}
|
||||
if (RetryConfiguration.AsyncRetryPolicy != null)
|
||||
{
|
||||
var policy = RetryConfiguration.AsyncRetryPolicy;
|
||||
var policyResult = await policy.ExecuteAndCaptureAsync((ct) => client.ExecuteAsync(req, ct), cancellationToken).ConfigureAwait(false);
|
||||
response = (policyResult.Outcome == OutcomeType.Successful) ? client.Deserialize<T>(policyResult.Result) : new RestResponse<T>
|
||||
{
|
||||
Request = req,
|
||||
ErrorException = policyResult.FinalException
|
||||
};
|
||||
}
|
||||
else
|
||||
{
|
||||
{{/supportsRetry}}
|
||||
response = await client.ExecuteAsync<T>(req, cancellationToken).ConfigureAwait(false);
|
||||
{{#supportsRetry}}
|
||||
}
|
||||
{{/supportsRetry}}
|
||||
|
||||
// if the response type is oneOf/anyOf, call FromJSON to deserialize the data
|
||||
if (typeof({{{packageName}}}.{{modelPackage}}.AbstractOpenAPISchema).IsAssignableFrom(typeof(T)))
|
||||
{
|
||||
response.Data = (T) typeof(T).GetMethod("FromJson").Invoke(null, new object[] { response.Content });
|
||||
}
|
||||
else if (typeof(T).Name == "Stream") // for binary response
|
||||
{
|
||||
response.Data = (T)(object)new MemoryStream(response.RawBytes);
|
||||
}
|
||||
|
||||
InterceptResponse(req, response);
|
||||
|
||||
var result = ToApiResponse(response);
|
||||
if (response.ErrorMessage != null)
|
||||
{
|
||||
result.ErrorText = response.ErrorMessage;
|
||||
}
|
||||
|
||||
if (response.Cookies != null && response.Cookies.Count > 0)
|
||||
{
|
||||
if (result.Cookies == null) result.Cookies = new List<Cookie>();
|
||||
foreach (var restResponseCookie in response.Cookies)
|
||||
{
|
||||
var cookie = new Cookie(
|
||||
restResponseCookie.Name,
|
||||
restResponseCookie.Value,
|
||||
restResponseCookie.Path,
|
||||
restResponseCookie.Domain
|
||||
)
|
||||
{
|
||||
Comment = restResponseCookie.Comment,
|
||||
CommentUri = restResponseCookie.CommentUri,
|
||||
Discard = restResponseCookie.Discard,
|
||||
Expired = restResponseCookie.Expired,
|
||||
Expires = restResponseCookie.Expires,
|
||||
HttpOnly = restResponseCookie.HttpOnly,
|
||||
Port = restResponseCookie.Port,
|
||||
Secure = restResponseCookie.Secure,
|
||||
Version = restResponseCookie.Version
|
||||
};
|
||||
|
||||
result.Cookies.Add(cookie);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
#region IAsynchronousClient
|
||||
/// <summary>
|
||||
/// Make a HTTP GET request (async).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <param name="cancellationToken">Token that enables callers to cancel the request.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public Task<ApiResponse<T>> GetAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken))
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return ExecAsync<T>(NewRequest(HttpMethod.Get, path, options, config), config, cancellationToken);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP POST request (async).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <param name="cancellationToken">Token that enables callers to cancel the request.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public Task<ApiResponse<T>> PostAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken))
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return ExecAsync<T>(NewRequest(HttpMethod.Post, path, options, config), config, cancellationToken);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP PUT request (async).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <param name="cancellationToken">Token that enables callers to cancel the request.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public Task<ApiResponse<T>> PutAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken))
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return ExecAsync<T>(NewRequest(HttpMethod.Put, path, options, config), config, cancellationToken);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP DELETE request (async).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <param name="cancellationToken">Token that enables callers to cancel the request.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public Task<ApiResponse<T>> DeleteAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken))
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return ExecAsync<T>(NewRequest(HttpMethod.Delete, path, options, config), config, cancellationToken);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP HEAD request (async).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <param name="cancellationToken">Token that enables callers to cancel the request.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public Task<ApiResponse<T>> HeadAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken))
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return ExecAsync<T>(NewRequest(HttpMethod.Head, path, options, config), config, cancellationToken);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP OPTION request (async).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <param name="cancellationToken">Token that enables callers to cancel the request.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public Task<ApiResponse<T>> OptionsAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken))
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return ExecAsync<T>(NewRequest(HttpMethod.Options, path, options, config), config, cancellationToken);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP PATCH request (async).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <param name="cancellationToken">Token that enables callers to cancel the request.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public Task<ApiResponse<T>> PatchAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken))
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return ExecAsync<T>(NewRequest(HttpMethod.Patch, path, options, config), config, cancellationToken);
|
||||
}
|
||||
#endregion IAsynchronousClient
|
||||
{{/supportsAsync}}
|
||||
|
||||
#region ISynchronousClient
|
||||
/// <summary>
|
||||
/// Make a HTTP GET request (synchronous).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public ApiResponse<T> Get<T>(string path, RequestOptions options, IReadableConfiguration configuration = null)
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return Exec<T>(NewRequest(HttpMethod.Get, path, options, config), config);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP POST request (synchronous).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public ApiResponse<T> Post<T>(string path, RequestOptions options, IReadableConfiguration configuration = null)
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return Exec<T>(NewRequest(HttpMethod.Post, path, options, config), config);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP PUT request (synchronous).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public ApiResponse<T> Put<T>(string path, RequestOptions options, IReadableConfiguration configuration = null)
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return Exec<T>(NewRequest(HttpMethod.Put, path, options, config), config);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP DELETE request (synchronous).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public ApiResponse<T> Delete<T>(string path, RequestOptions options, IReadableConfiguration configuration = null)
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return Exec<T>(NewRequest(HttpMethod.Delete, path, options, config), config);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP HEAD request (synchronous).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public ApiResponse<T> Head<T>(string path, RequestOptions options, IReadableConfiguration configuration = null)
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return Exec<T>(NewRequest(HttpMethod.Head, path, options, config), config);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP OPTION request (synchronous).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public ApiResponse<T> Options<T>(string path, RequestOptions options, IReadableConfiguration configuration = null)
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return Exec<T>(NewRequest(HttpMethod.Options, path, options, config), config);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Make a HTTP PATCH request (synchronous).
|
||||
/// </summary>
|
||||
/// <param name="path">The target path (or resource).</param>
|
||||
/// <param name="options">The additional request options.</param>
|
||||
/// <param name="configuration">A per-request configuration object. It is assumed that any merge with
|
||||
/// GlobalConfiguration has been done before calling this method.</param>
|
||||
/// <returns>A Task containing ApiResponse</returns>
|
||||
public ApiResponse<T> Patch<T>(string path, RequestOptions options, IReadableConfiguration configuration = null)
|
||||
{
|
||||
var config = configuration ?? GlobalConfiguration.Instance;
|
||||
return Exec<T>(NewRequest(HttpMethod.Patch, path, options, config), config);
|
||||
}
|
||||
#endregion ISynchronousClient
|
||||
}
|
||||
}
|
60
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ApiException.mustache
vendored
Normal file
60
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ApiException.mustache
vendored
Normal file
@ -0,0 +1,60 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// API Exception
|
||||
/// </summary>
|
||||
{{>visibility}} class ApiException : Exception
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the error code (HTTP status code)
|
||||
/// </summary>
|
||||
/// <value>The error code (HTTP status code).</value>
|
||||
public int ErrorCode { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the error content (body json object)
|
||||
/// </summary>
|
||||
/// <value>The error content (Http response body).</value>
|
||||
public object ErrorContent { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the HTTP headers
|
||||
/// </summary>
|
||||
/// <value>HTTP headers</value>
|
||||
public Multimap<string, string> Headers { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiException"/> class.
|
||||
/// </summary>
|
||||
public ApiException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiException"/> class.
|
||||
/// </summary>
|
||||
/// <param name="errorCode">HTTP status code.</param>
|
||||
/// <param name="message">Error message.</param>
|
||||
public ApiException(int errorCode, string message) : base(message)
|
||||
{
|
||||
this.ErrorCode = errorCode;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiException"/> class.
|
||||
/// </summary>
|
||||
/// <param name="errorCode">HTTP status code.</param>
|
||||
/// <param name="message">Error message.</param>
|
||||
/// <param name="errorContent">Error content.</param>
|
||||
/// <param name="headers">HTTP Headers.</param>
|
||||
public ApiException(int errorCode, string message, object errorContent = null, Multimap<string, string> headers = null) : base(message)
|
||||
{
|
||||
this.ErrorCode = errorCode;
|
||||
this.ErrorContent = errorContent;
|
||||
this.Headers = headers;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
158
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ApiResponse.mustache
vendored
Normal file
158
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ApiResponse.mustache
vendored
Normal file
@ -0,0 +1,158 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Net;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides a non-generic contract for the ApiResponse wrapper.
|
||||
/// </summary>
|
||||
public interface IApiResponse
|
||||
{
|
||||
/// <summary>
|
||||
/// The data type of <see cref="Content"/>
|
||||
/// </summary>
|
||||
Type ResponseType { get; }
|
||||
|
||||
/// <summary>
|
||||
/// The content of this response
|
||||
/// </summary>
|
||||
Object Content { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the status code (HTTP status code)
|
||||
/// </summary>
|
||||
/// <value>The status code.</value>
|
||||
HttpStatusCode StatusCode { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the HTTP headers
|
||||
/// </summary>
|
||||
/// <value>HTTP headers</value>
|
||||
Multimap<string, string> Headers { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets any error text defined by the calling client.
|
||||
/// </summary>
|
||||
string ErrorText { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets any cookies passed along on the response.
|
||||
/// </summary>
|
||||
List<Cookie> Cookies { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The raw content of this response
|
||||
/// </summary>
|
||||
string RawContent { get; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// API Response
|
||||
/// </summary>
|
||||
public class ApiResponse<T> : IApiResponse
|
||||
{
|
||||
#region Properties
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the status code (HTTP status code)
|
||||
/// </summary>
|
||||
/// <value>The status code.</value>
|
||||
public HttpStatusCode StatusCode { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the HTTP headers
|
||||
/// </summary>
|
||||
/// <value>HTTP headers</value>
|
||||
public Multimap<string, string> Headers { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the data (parsed HTTP body)
|
||||
/// </summary>
|
||||
/// <value>The data.</value>
|
||||
public T Data { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets any error text defined by the calling client.
|
||||
/// </summary>
|
||||
public string ErrorText { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets any cookies passed along on the response.
|
||||
/// </summary>
|
||||
public List<Cookie> Cookies { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The content of this response
|
||||
/// </summary>
|
||||
public Type ResponseType
|
||||
{
|
||||
get { return typeof(T); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The data type of <see cref="Content"/>
|
||||
/// </summary>
|
||||
public object Content
|
||||
{
|
||||
get { return Data; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The raw content
|
||||
/// </summary>
|
||||
public string RawContent { get; }
|
||||
|
||||
#endregion Properties
|
||||
|
||||
#region Constructors
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiResponse{T}" /> class.
|
||||
/// </summary>
|
||||
/// <param name="statusCode">HTTP status code.</param>
|
||||
/// <param name="headers">HTTP headers.</param>
|
||||
/// <param name="data">Data (parsed HTTP body)</param>
|
||||
/// <param name="rawContent">Raw content.</param>
|
||||
public ApiResponse(HttpStatusCode statusCode, Multimap<string, string> headers, T data, string rawContent)
|
||||
{
|
||||
StatusCode = statusCode;
|
||||
Headers = headers;
|
||||
Data = data;
|
||||
RawContent = rawContent;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiResponse{T}" /> class.
|
||||
/// </summary>
|
||||
/// <param name="statusCode">HTTP status code.</param>
|
||||
/// <param name="headers">HTTP headers.</param>
|
||||
/// <param name="data">Data (parsed HTTP body)</param>
|
||||
public ApiResponse(HttpStatusCode statusCode, Multimap<string, string> headers, T data) : this(statusCode, headers, data, null)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiResponse{T}" /> class.
|
||||
/// </summary>
|
||||
/// <param name="statusCode">HTTP status code.</param>
|
||||
/// <param name="data">Data (parsed HTTP body)</param>
|
||||
/// <param name="rawContent">Raw content.</param>
|
||||
public ApiResponse(HttpStatusCode statusCode, T data, string rawContent) : this(statusCode, null, data, rawContent)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApiResponse{T}" /> class.
|
||||
/// </summary>
|
||||
/// <param name="statusCode">HTTP status code.</param>
|
||||
/// <param name="data">Data (parsed HTTP body)</param>
|
||||
public ApiResponse(HttpStatusCode statusCode, T data) : this(statusCode, data, null)
|
||||
{
|
||||
}
|
||||
|
||||
#endregion Constructors
|
||||
}
|
||||
}
|
40
modules/openapi-generator/src/main/resources/csharp-netcore-functions/AssemblyInfo.mustache
vendored
Normal file
40
modules/openapi-generator/src/main/resources/csharp-netcore-functions/AssemblyInfo.mustache
vendored
Normal file
@ -0,0 +1,40 @@
|
||||
using System.Reflection;
|
||||
using System.Runtime.CompilerServices;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
// General Information about an assembly is controlled through the following
|
||||
// set of attributes. Change these attribute values to modify the information
|
||||
// associated with an assembly.
|
||||
[assembly: AssemblyTitle("{{packageTitle}}")]
|
||||
[assembly: AssemblyDescription("{{packageDescription}}")]
|
||||
[assembly: AssemblyConfiguration("")]
|
||||
[assembly: AssemblyCompany("{{packageCompany}}")]
|
||||
[assembly: AssemblyProduct("{{packageProductName}}")]
|
||||
[assembly: AssemblyCopyright("{{packageCopyright}}")]
|
||||
[assembly: AssemblyTrademark("")]
|
||||
[assembly: AssemblyCulture("")]
|
||||
|
||||
// Setting ComVisible to false makes the types in this assembly not visible
|
||||
// to COM components. If you need to access a type in this assembly from
|
||||
// COM, set the ComVisible attribute to true on that type.
|
||||
[assembly: ComVisible(false)]
|
||||
|
||||
// Version information for an assembly consists of the following four values:
|
||||
//
|
||||
// Major Version
|
||||
// Minor Version
|
||||
// Build Number
|
||||
// Revision
|
||||
//
|
||||
// You can specify all the values or you can default the Build and Revision Numbers
|
||||
// by using the '*' as shown below:
|
||||
// [assembly: AssemblyVersion("1.0.*")]
|
||||
[assembly: AssemblyVersion("{{packageVersion}}")]
|
||||
[assembly: AssemblyFileVersion("{{packageVersion}}")]
|
||||
{{^supportsAsync}}
|
||||
// Settings which don't support asynchronous operations rely on non-public constructors
|
||||
// This is due to how RestSharp requires the type constraint `where T : new()` in places it probably shouldn't.
|
||||
[assembly: InternalsVisibleTo("RestSharp")]
|
||||
[assembly: InternalsVisibleTo("NewtonSoft.Json")]
|
||||
[assembly: InternalsVisibleTo("JsonSubTypes")]
|
||||
{{/supportsAsync}}
|
239
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ClientUtils.mustache
vendored
Normal file
239
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ClientUtils.mustache
vendored
Normal file
@ -0,0 +1,239 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Globalization;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Text.RegularExpressions;
|
||||
{{#useCompareNetObjects}}
|
||||
using KellermanSoftware.CompareNetObjects;
|
||||
{{/useCompareNetObjects}}
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Utility functions providing some benefit to API client consumers.
|
||||
/// </summary>
|
||||
public static class ClientUtils
|
||||
{
|
||||
{{#useCompareNetObjects}}
|
||||
/// <summary>
|
||||
/// An instance of CompareLogic.
|
||||
/// </summary>
|
||||
public static CompareLogic compareLogic;
|
||||
|
||||
/// <summary>
|
||||
/// Static contstructor to initialise compareLogic.
|
||||
/// </summary>
|
||||
static ClientUtils()
|
||||
{
|
||||
compareLogic = new CompareLogic();
|
||||
}
|
||||
|
||||
{{/useCompareNetObjects}}
|
||||
/// <summary>
|
||||
/// Sanitize filename by removing the path
|
||||
/// </summary>
|
||||
/// <param name="filename">Filename</param>
|
||||
/// <returns>Filename</returns>
|
||||
public static string SanitizeFilename(string filename)
|
||||
{
|
||||
Match match = Regex.Match(filename, @".*[/\\](.*)$");
|
||||
return match.Success ? match.Groups[1].Value : filename;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Convert params to key/value pairs.
|
||||
/// Use collectionFormat to properly format lists and collections.
|
||||
/// </summary>
|
||||
/// <param name="collectionFormat">The swagger-supported collection format, one of: csv, tsv, ssv, pipes, multi</param>
|
||||
/// <param name="name">Key name.</param>
|
||||
/// <param name="value">Value object.</param>
|
||||
/// <returns>A multimap of keys with 1..n associated values.</returns>
|
||||
public static Multimap<string, string> ParameterToMultiMap(string collectionFormat, string name, object value)
|
||||
{
|
||||
var parameters = new Multimap<string, string>();
|
||||
|
||||
if (value is ICollection collection && collectionFormat == "multi")
|
||||
{
|
||||
foreach (var item in collection)
|
||||
{
|
||||
parameters.Add(name, ParameterToString(item));
|
||||
}
|
||||
}
|
||||
else if (value is IDictionary dictionary)
|
||||
{
|
||||
if(collectionFormat == "deepObject") {
|
||||
foreach (DictionaryEntry entry in dictionary)
|
||||
{
|
||||
parameters.Add(name + "[" + entry.Key + "]", ParameterToString(entry.Value));
|
||||
}
|
||||
}
|
||||
else {
|
||||
foreach (DictionaryEntry entry in dictionary)
|
||||
{
|
||||
parameters.Add(entry.Key.ToString(), ParameterToString(entry.Value));
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
parameters.Add(name, ParameterToString(value));
|
||||
}
|
||||
|
||||
return parameters;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// If parameter is DateTime, output in a formatted string (default ISO 8601), customizable with Configuration.DateTime.
|
||||
/// If parameter is a list, join the list with ",".
|
||||
/// Otherwise just return the string.
|
||||
/// </summary>
|
||||
/// <param name="obj">The parameter (header, path, query, form).</param>
|
||||
/// <param name="configuration">An optional configuration instance, providing formatting options used in processing.</param>
|
||||
/// <returns>Formatted string.</returns>
|
||||
public static string ParameterToString(object obj, IReadableConfiguration configuration = null)
|
||||
{
|
||||
if (obj is DateTime dateTime)
|
||||
// Return a formatted date string - Can be customized with Configuration.DateTimeFormat
|
||||
// Defaults to an ISO 8601, using the known as a Round-trip date/time pattern ("o")
|
||||
// https://msdn.microsoft.com/en-us/library/az4se3k1(v=vs.110).aspx#Anchor_8
|
||||
// For example: 2009-06-15T13:45:30.0000000
|
||||
return dateTime.ToString((configuration ?? GlobalConfiguration.Instance).DateTimeFormat);
|
||||
if (obj is DateTimeOffset dateTimeOffset)
|
||||
// Return a formatted date string - Can be customized with Configuration.DateTimeFormat
|
||||
// Defaults to an ISO 8601, using the known as a Round-trip date/time pattern ("o")
|
||||
// https://msdn.microsoft.com/en-us/library/az4se3k1(v=vs.110).aspx#Anchor_8
|
||||
// For example: 2009-06-15T13:45:30.0000000
|
||||
return dateTimeOffset.ToString((configuration ?? GlobalConfiguration.Instance).DateTimeFormat);
|
||||
if (obj is bool boolean)
|
||||
return boolean ? "true" : "false";
|
||||
if (obj is ICollection collection)
|
||||
return string.Join(",", collection.Cast<object>());
|
||||
|
||||
return Convert.ToString(obj, CultureInfo.InvariantCulture);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// URL encode a string
|
||||
/// Credit/Ref: https://github.com/restsharp/RestSharp/blob/master/RestSharp/Extensions/StringExtensions.cs#L50
|
||||
/// </summary>
|
||||
/// <param name="input">string to be URL encoded</param>
|
||||
/// <returns>Byte array</returns>
|
||||
public static string UrlEncode(string input)
|
||||
{
|
||||
const int maxLength = 32766;
|
||||
|
||||
if (input == null)
|
||||
{
|
||||
throw new ArgumentNullException("input");
|
||||
}
|
||||
|
||||
if (input.Length <= maxLength)
|
||||
{
|
||||
return Uri.EscapeDataString(input);
|
||||
}
|
||||
|
||||
StringBuilder sb = new StringBuilder(input.Length * 2);
|
||||
int index = 0;
|
||||
|
||||
while (index < input.Length)
|
||||
{
|
||||
int length = Math.Min(input.Length - index, maxLength);
|
||||
string subString = input.Substring(index, length);
|
||||
|
||||
sb.Append(Uri.EscapeDataString(subString));
|
||||
index += subString.Length;
|
||||
}
|
||||
|
||||
return sb.ToString();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Encode string in base64 format.
|
||||
/// </summary>
|
||||
/// <param name="text">string to be encoded.</param>
|
||||
/// <returns>Encoded string.</returns>
|
||||
public static string Base64Encode(string text)
|
||||
{
|
||||
return Convert.ToBase64String(System.Text.Encoding.UTF8.GetBytes(text));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Convert stream to byte array
|
||||
/// </summary>
|
||||
/// <param name="inputStream">Input stream to be converted</param>
|
||||
/// <returns>Byte array</returns>
|
||||
public static byte[] ReadAsBytes(Stream inputStream)
|
||||
{
|
||||
using (var ms = new MemoryStream())
|
||||
{
|
||||
inputStream.CopyTo(ms);
|
||||
return ms.ToArray();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Select the Content-Type header's value from the given content-type array:
|
||||
/// if JSON type exists in the given array, use it;
|
||||
/// otherwise use the first one defined in 'consumes'
|
||||
/// </summary>
|
||||
/// <param name="contentTypes">The Content-Type array to select from.</param>
|
||||
/// <returns>The Content-Type header to use.</returns>
|
||||
public static string SelectHeaderContentType(string[] contentTypes)
|
||||
{
|
||||
if (contentTypes.Length == 0)
|
||||
return null;
|
||||
|
||||
foreach (var contentType in contentTypes)
|
||||
{
|
||||
if (IsJsonMime(contentType))
|
||||
return contentType;
|
||||
}
|
||||
|
||||
return contentTypes[0]; // use the first content type specified in 'consumes'
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Select the Accept header's value from the given accepts array:
|
||||
/// if JSON exists in the given array, use it;
|
||||
/// otherwise use all of them (joining into a string)
|
||||
/// </summary>
|
||||
/// <param name="accepts">The accepts array to select from.</param>
|
||||
/// <returns>The Accept header to use.</returns>
|
||||
public static string SelectHeaderAccept(string[] accepts)
|
||||
{
|
||||
if (accepts.Length == 0)
|
||||
return null;
|
||||
|
||||
if (accepts.Contains("application/json", StringComparer.OrdinalIgnoreCase))
|
||||
return "application/json";
|
||||
|
||||
return string.Join(",", accepts);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Provides a case-insensitive check that a provided content type is a known JSON-like content type.
|
||||
/// </summary>
|
||||
public static readonly Regex JsonRegex = new Regex("(?i)^(application/json|[^;/ \t]+/[^;/ \t]+[+]json)[ \t]*(;.*)?$");
|
||||
|
||||
/// <summary>
|
||||
/// Check if the given MIME is a JSON MIME.
|
||||
/// JSON MIME examples:
|
||||
/// application/json
|
||||
/// application/json; charset=UTF8
|
||||
/// APPLICATION/JSON
|
||||
/// application/vnd.company+json
|
||||
/// </summary>
|
||||
/// <param name="mime">MIME</param>
|
||||
/// <returns>Returns True if MIME type is json.</returns>
|
||||
public static bool IsJsonMime(string mime)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(mime)) return false;
|
||||
|
||||
return JsonRegex.IsMatch(mime) || mime.Equals("application/json-patch+json");
|
||||
}
|
||||
}
|
||||
}
|
574
modules/openapi-generator/src/main/resources/csharp-netcore-functions/Configuration.mustache
vendored
Normal file
574
modules/openapi-generator/src/main/resources/csharp-netcore-functions/Configuration.mustache
vendored
Normal file
@ -0,0 +1,574 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
{{^net35}}
|
||||
using System.Collections.Concurrent;
|
||||
{{/net35}}
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Net;
|
||||
using System.Reflection;
|
||||
using System.Security.Cryptography.X509Certificates;
|
||||
using System.Text;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents a set of configuration settings
|
||||
/// </summary>
|
||||
{{>visibility}} class Configuration : IReadableConfiguration
|
||||
{
|
||||
#region Constants
|
||||
|
||||
/// <summary>
|
||||
/// Version of the package.
|
||||
/// </summary>
|
||||
/// <value>Version of the package.</value>
|
||||
public const string Version = "{{packageVersion}}";
|
||||
|
||||
/// <summary>
|
||||
/// Identifier for ISO 8601 DateTime Format
|
||||
/// </summary>
|
||||
/// <remarks>See https://msdn.microsoft.com/en-us/library/az4se3k1(v=vs.110).aspx#Anchor_8 for more information.</remarks>
|
||||
// ReSharper disable once InconsistentNaming
|
||||
public const string ISO8601_DATETIME_FORMAT = "o";
|
||||
|
||||
#endregion Constants
|
||||
|
||||
#region Static Members
|
||||
|
||||
/// <summary>
|
||||
/// Default creation of exceptions for a given method name and response object
|
||||
/// </summary>
|
||||
public static readonly ExceptionFactory DefaultExceptionFactory = (methodName, response) =>
|
||||
{
|
||||
var status = (int)response.StatusCode;
|
||||
if (status >= 400)
|
||||
{
|
||||
return new ApiException(status,
|
||||
string.Format("Error calling {0}: {1}", methodName, response.RawContent),
|
||||
response.RawContent, response.Headers);
|
||||
}
|
||||
{{^netStandard}}
|
||||
if (status == 0)
|
||||
{
|
||||
return new ApiException(status,
|
||||
string.Format("Error calling {0}: {1}", methodName, response.ErrorText), response.ErrorText);
|
||||
}
|
||||
{{/netStandard}}
|
||||
return null;
|
||||
};
|
||||
|
||||
#endregion Static Members
|
||||
|
||||
#region Private Members
|
||||
|
||||
/// <summary>
|
||||
/// Defines the base path of the target API server.
|
||||
/// Example: http://localhost:3000/v1/
|
||||
/// </summary>
|
||||
private string _basePath;
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the API key based on the authentication name.
|
||||
/// This is the key and value comprising the "secret" for acessing an API.
|
||||
/// </summary>
|
||||
/// <value>The API key.</value>
|
||||
private IDictionary<string, string> _apiKey;
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the prefix (e.g. Token) of the API key based on the authentication name.
|
||||
/// </summary>
|
||||
/// <value>The prefix of the API key.</value>
|
||||
private IDictionary<string, string> _apiKeyPrefix;
|
||||
|
||||
private string _dateTimeFormat = ISO8601_DATETIME_FORMAT;
|
||||
private string _tempFolderPath = Path.GetTempPath();
|
||||
{{#servers.0}}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the servers defined in the OpenAPI spec.
|
||||
/// </summary>
|
||||
/// <value>The servers</value>
|
||||
private IList<IReadOnlyDictionary<string, object>> _servers;
|
||||
{{/servers.0}}
|
||||
{{#hasHttpSignatureMethods}}
|
||||
|
||||
/// <summary>
|
||||
/// HttpSigning configuration
|
||||
/// </summary>
|
||||
private HttpSigningConfiguration _HttpSigningConfiguration = null;
|
||||
{{/hasHttpSignatureMethods}}
|
||||
#endregion Private Members
|
||||
|
||||
#region Constructors
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="Configuration" /> class
|
||||
/// </summary>
|
||||
[System.Diagnostics.CodeAnalysis.SuppressMessage("ReSharper", "VirtualMemberCallInConstructor")]
|
||||
public Configuration()
|
||||
{
|
||||
Proxy = null;
|
||||
UserAgent = "{{#httpUserAgent}}{{.}}{{/httpUserAgent}}{{^httpUserAgent}}OpenAPI-Generator/{{packageVersion}}/csharp{{/httpUserAgent}}";
|
||||
BasePath = "{{{basePath}}}";
|
||||
DefaultHeaders = new {{^net35}}Concurrent{{/net35}}Dictionary<string, string>();
|
||||
ApiKey = new {{^net35}}Concurrent{{/net35}}Dictionary<string, string>();
|
||||
ApiKeyPrefix = new {{^net35}}Concurrent{{/net35}}Dictionary<string, string>();
|
||||
{{#servers}}
|
||||
{{#-first}}
|
||||
Servers = new List<IReadOnlyDictionary<string, object>>()
|
||||
{
|
||||
{{/-first}}
|
||||
{
|
||||
new Dictionary<string, object> {
|
||||
{"url", "{{{url}}}"},
|
||||
{"description", "{{{description}}}{{^description}}No description provided{{/description}}"},
|
||||
{{#variables}}
|
||||
{{#-first}}
|
||||
{
|
||||
"variables", new Dictionary<string, object> {
|
||||
{{/-first}}
|
||||
{
|
||||
"{{{name}}}", new Dictionary<string, object> {
|
||||
{"description", "{{{description}}}{{^description}}No description provided{{/description}}"},
|
||||
{"default_value", "{{{defaultValue}}}"},
|
||||
{{#enumValues}}
|
||||
{{#-first}}
|
||||
{
|
||||
"enum_values", new List<string>() {
|
||||
{{/-first}}
|
||||
"{{{.}}}"{{^-last}},{{/-last}}
|
||||
{{#-last}}
|
||||
}
|
||||
}
|
||||
{{/-last}}
|
||||
{{/enumValues}}
|
||||
}
|
||||
}{{^-last}},{{/-last}}
|
||||
{{#-last}}
|
||||
}
|
||||
}
|
||||
{{/-last}}
|
||||
{{/variables}}
|
||||
}
|
||||
}{{^-last}},{{/-last}}
|
||||
{{#-last}}
|
||||
};
|
||||
{{/-last}}
|
||||
{{/servers}}
|
||||
|
||||
// Setting Timeout has side effects (forces ApiClient creation).
|
||||
Timeout = 100000;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="Configuration" /> class
|
||||
/// </summary>
|
||||
[System.Diagnostics.CodeAnalysis.SuppressMessage("ReSharper", "VirtualMemberCallInConstructor")]
|
||||
public Configuration(
|
||||
IDictionary<string, string> defaultHeaders,
|
||||
IDictionary<string, string> apiKey,
|
||||
IDictionary<string, string> apiKeyPrefix,
|
||||
string basePath = "{{{basePath}}}") : this()
|
||||
{
|
||||
if (string.{{^net35}}IsNullOrWhiteSpace{{/net35}}{{#net35}}IsNullOrEmpty{{/net35}}(basePath))
|
||||
throw new ArgumentException("The provided basePath is invalid.", "basePath");
|
||||
if (defaultHeaders == null)
|
||||
throw new ArgumentNullException("defaultHeaders");
|
||||
if (apiKey == null)
|
||||
throw new ArgumentNullException("apiKey");
|
||||
if (apiKeyPrefix == null)
|
||||
throw new ArgumentNullException("apiKeyPrefix");
|
||||
|
||||
BasePath = basePath;
|
||||
|
||||
foreach (var keyValuePair in defaultHeaders)
|
||||
{
|
||||
DefaultHeaders.Add(keyValuePair);
|
||||
}
|
||||
|
||||
foreach (var keyValuePair in apiKey)
|
||||
{
|
||||
ApiKey.Add(keyValuePair);
|
||||
}
|
||||
|
||||
foreach (var keyValuePair in apiKeyPrefix)
|
||||
{
|
||||
ApiKeyPrefix.Add(keyValuePair);
|
||||
}
|
||||
}
|
||||
|
||||
#endregion Constructors
|
||||
|
||||
#region Properties
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the base path for API access.
|
||||
/// </summary>
|
||||
public virtual string BasePath {
|
||||
get { return _basePath; }
|
||||
set { _basePath = value; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the default header.
|
||||
/// </summary>
|
||||
[Obsolete("Use DefaultHeaders instead.")]
|
||||
public virtual IDictionary<string, string> DefaultHeader
|
||||
{
|
||||
get
|
||||
{
|
||||
return DefaultHeaders;
|
||||
}
|
||||
set
|
||||
{
|
||||
DefaultHeaders = value;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the default headers.
|
||||
/// </summary>
|
||||
public virtual IDictionary<string, string> DefaultHeaders { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the HTTP timeout (milliseconds) of ApiClient. Default to 100000 milliseconds.
|
||||
/// </summary>
|
||||
public virtual int Timeout { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the proxy
|
||||
/// </summary>
|
||||
/// <value>Proxy.</value>
|
||||
public virtual WebProxy Proxy { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the HTTP user agent.
|
||||
/// </summary>
|
||||
/// <value>Http user agent.</value>
|
||||
public virtual string UserAgent { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the username (HTTP basic authentication).
|
||||
/// </summary>
|
||||
/// <value>The username.</value>
|
||||
public virtual string Username { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the password (HTTP basic authentication).
|
||||
/// </summary>
|
||||
/// <value>The password.</value>
|
||||
public virtual string Password { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the API key with prefix.
|
||||
/// </summary>
|
||||
/// <param name="apiKeyIdentifier">API key identifier (authentication scheme).</param>
|
||||
/// <returns>API key with prefix.</returns>
|
||||
public string GetApiKeyWithPrefix(string apiKeyIdentifier)
|
||||
{
|
||||
string apiKeyValue;
|
||||
ApiKey.TryGetValue(apiKeyIdentifier, out apiKeyValue);
|
||||
string apiKeyPrefix;
|
||||
if (ApiKeyPrefix.TryGetValue(apiKeyIdentifier, out apiKeyPrefix))
|
||||
{
|
||||
return apiKeyPrefix + " " + apiKeyValue;
|
||||
}
|
||||
|
||||
return apiKeyValue;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets certificate collection to be sent with requests.
|
||||
/// </summary>
|
||||
/// <value>X509 Certificate collection.</value>
|
||||
public X509CertificateCollection ClientCertificates { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the access token for OAuth2 authentication.
|
||||
///
|
||||
/// This helper property simplifies code generation.
|
||||
/// </summary>
|
||||
/// <value>The access token.</value>
|
||||
public virtual string AccessToken { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the temporary folder path to store the files downloaded from the server.
|
||||
/// </summary>
|
||||
/// <value>Folder path.</value>
|
||||
public virtual string TempFolderPath
|
||||
{
|
||||
get { return _tempFolderPath; }
|
||||
|
||||
set
|
||||
{
|
||||
if (string.IsNullOrEmpty(value))
|
||||
{
|
||||
_tempFolderPath = Path.GetTempPath();
|
||||
return;
|
||||
}
|
||||
|
||||
// create the directory if it does not exist
|
||||
if (!Directory.Exists(value))
|
||||
{
|
||||
Directory.CreateDirectory(value);
|
||||
}
|
||||
|
||||
// check if the path contains directory separator at the end
|
||||
if (value[value.Length - 1] == Path.DirectorySeparatorChar)
|
||||
{
|
||||
_tempFolderPath = value;
|
||||
}
|
||||
else
|
||||
{
|
||||
_tempFolderPath = value + Path.DirectorySeparatorChar;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the date time format used when serializing in the ApiClient
|
||||
/// By default, it's set to ISO 8601 - "o", for others see:
|
||||
/// https://msdn.microsoft.com/en-us/library/az4se3k1(v=vs.110).aspx
|
||||
/// and https://msdn.microsoft.com/en-us/library/8kb3ddd4(v=vs.110).aspx
|
||||
/// No validation is done to ensure that the string you're providing is valid
|
||||
/// </summary>
|
||||
/// <value>The DateTimeFormat string</value>
|
||||
public virtual string DateTimeFormat
|
||||
{
|
||||
get { return _dateTimeFormat; }
|
||||
set
|
||||
{
|
||||
if (string.IsNullOrEmpty(value))
|
||||
{
|
||||
// Never allow a blank or null string, go back to the default
|
||||
_dateTimeFormat = ISO8601_DATETIME_FORMAT;
|
||||
return;
|
||||
}
|
||||
|
||||
// Caution, no validation when you choose date time format other than ISO 8601
|
||||
// Take a look at the above links
|
||||
_dateTimeFormat = value;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the prefix (e.g. Token) of the API key based on the authentication name.
|
||||
///
|
||||
/// Whatever you set here will be prepended to the value defined in AddApiKey.
|
||||
///
|
||||
/// An example invocation here might be:
|
||||
/// <example>
|
||||
/// ApiKeyPrefix["Authorization"] = "Bearer";
|
||||
/// </example>
|
||||
/// … where ApiKey["Authorization"] would then be used to set the value of your bearer token.
|
||||
///
|
||||
/// <remarks>
|
||||
/// OAuth2 workflows should set tokens via AccessToken.
|
||||
/// </remarks>
|
||||
/// </summary>
|
||||
/// <value>The prefix of the API key.</value>
|
||||
public virtual IDictionary<string, string> ApiKeyPrefix
|
||||
{
|
||||
get { return _apiKeyPrefix; }
|
||||
set
|
||||
{
|
||||
if (value == null)
|
||||
{
|
||||
throw new InvalidOperationException("ApiKeyPrefix collection may not be null.");
|
||||
}
|
||||
_apiKeyPrefix = value;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the API key based on the authentication name.
|
||||
/// </summary>
|
||||
/// <value>The API key.</value>
|
||||
public virtual IDictionary<string, string> ApiKey
|
||||
{
|
||||
get { return _apiKey; }
|
||||
set
|
||||
{
|
||||
if (value == null)
|
||||
{
|
||||
throw new InvalidOperationException("ApiKey collection may not be null.");
|
||||
}
|
||||
_apiKey = value;
|
||||
}
|
||||
}
|
||||
{{#servers.0}}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the servers.
|
||||
/// </summary>
|
||||
/// <value>The servers.</value>
|
||||
public virtual IList<IReadOnlyDictionary<string, object>> Servers
|
||||
{
|
||||
get { return _servers; }
|
||||
set
|
||||
{
|
||||
if (value == null)
|
||||
{
|
||||
throw new InvalidOperationException("Servers may not be null.");
|
||||
}
|
||||
_servers = value;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns URL based on server settings without providing values
|
||||
/// for the variables
|
||||
/// </summary>
|
||||
/// <param name="index">Array index of the server settings.</param>
|
||||
/// <return>The server URL.</return>
|
||||
public string GetServerUrl(int index)
|
||||
{
|
||||
return GetServerUrl(index, null);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns URL based on server settings.
|
||||
/// </summary>
|
||||
/// <param name="index">Array index of the server settings.</param>
|
||||
/// <param name="inputVariables">Dictionary of the variables and the corresponding values.</param>
|
||||
/// <return>The server URL.</return>
|
||||
public string GetServerUrl(int index, Dictionary<string, string> inputVariables)
|
||||
{
|
||||
if (index < 0 || index >= Servers.Count)
|
||||
{
|
||||
throw new InvalidOperationException($"Invalid index {index} when selecting the server. Must be less than {Servers.Count}.");
|
||||
}
|
||||
|
||||
if (inputVariables == null)
|
||||
{
|
||||
inputVariables = new Dictionary<string, string>();
|
||||
}
|
||||
|
||||
IReadOnlyDictionary<string, object> server = Servers[index];
|
||||
string url = (string)server["url"];
|
||||
|
||||
// go through variable and assign a value
|
||||
foreach (KeyValuePair<string, object> variable in (IReadOnlyDictionary<string, object>)server["variables"])
|
||||
{
|
||||
|
||||
IReadOnlyDictionary<string, object> serverVariables = (IReadOnlyDictionary<string, object>)(variable.Value);
|
||||
|
||||
if (inputVariables.ContainsKey(variable.Key))
|
||||
{
|
||||
if (((List<string>)serverVariables["enum_values"]).Contains(inputVariables[variable.Key]))
|
||||
{
|
||||
url = url.Replace("{" + variable.Key + "}", inputVariables[variable.Key]);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new InvalidOperationException($"The variable `{variable.Key}` in the server URL has invalid value #{inputVariables[variable.Key]}. Must be {(List<string>)serverVariables["enum_values"]}");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// use defualt value
|
||||
url = url.Replace("{" + variable.Key + "}", (string)serverVariables["default_value"]);
|
||||
}
|
||||
}
|
||||
|
||||
return url;
|
||||
}
|
||||
{{/servers.0}}
|
||||
{{#hasHttpSignatureMethods}}
|
||||
|
||||
/// <summary>
|
||||
/// Gets and Sets the HttpSigningConfiuration
|
||||
/// </summary>
|
||||
public HttpSigningConfiguration HttpSigningConfiguration
|
||||
{
|
||||
get { return _HttpSigningConfiguration; }
|
||||
set { _HttpSigningConfiguration = value; }
|
||||
}
|
||||
{{/hasHttpSignatureMethods}}
|
||||
|
||||
#endregion Properties
|
||||
|
||||
#region Methods
|
||||
|
||||
/// <summary>
|
||||
/// Returns a string with essential information for debugging.
|
||||
/// </summary>
|
||||
public static string ToDebugReport()
|
||||
{
|
||||
string report = "C# SDK ({{{packageName}}}) Debug Report:\n";
|
||||
report += " OS: " + System.Environment.OSVersion + "\n";
|
||||
report += " .NET Framework Version: " + System.Environment.Version + "\n";
|
||||
report += " Version of the API: {{{version}}}\n";
|
||||
report += " SDK Package Version: {{{packageVersion}}}\n";
|
||||
|
||||
return report;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add Api Key Header.
|
||||
/// </summary>
|
||||
/// <param name="key">Api Key name.</param>
|
||||
/// <param name="value">Api Key value.</param>
|
||||
/// <returns></returns>
|
||||
public void AddApiKey(string key, string value)
|
||||
{
|
||||
ApiKey[key] = value;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets the API key prefix.
|
||||
/// </summary>
|
||||
/// <param name="key">Api Key name.</param>
|
||||
/// <param name="value">Api Key value.</param>
|
||||
public void AddApiKeyPrefix(string key, string value)
|
||||
{
|
||||
ApiKeyPrefix[key] = value;
|
||||
}
|
||||
|
||||
#endregion Methods
|
||||
|
||||
#region Static Members
|
||||
/// <summary>
|
||||
/// Merge configurations.
|
||||
/// </summary>
|
||||
/// <param name="first">First configuration.</param>
|
||||
/// <param name="second">Second configuration.</param>
|
||||
/// <return>Merged configuration.</return>
|
||||
public static IReadableConfiguration MergeConfigurations(IReadableConfiguration first, IReadableConfiguration second)
|
||||
{
|
||||
if (second == null) return first ?? GlobalConfiguration.Instance;
|
||||
|
||||
Dictionary<string, string> apiKey = first.ApiKey.ToDictionary(kvp => kvp.Key, kvp => kvp.Value);
|
||||
Dictionary<string, string> apiKeyPrefix = first.ApiKeyPrefix.ToDictionary(kvp => kvp.Key, kvp => kvp.Value);
|
||||
Dictionary<string, string> defaultHeaders = first.DefaultHeaders.ToDictionary(kvp => kvp.Key, kvp => kvp.Value);
|
||||
|
||||
foreach (var kvp in second.ApiKey) apiKey[kvp.Key] = kvp.Value;
|
||||
foreach (var kvp in second.ApiKeyPrefix) apiKeyPrefix[kvp.Key] = kvp.Value;
|
||||
foreach (var kvp in second.DefaultHeaders) defaultHeaders[kvp.Key] = kvp.Value;
|
||||
|
||||
var config = new Configuration
|
||||
{
|
||||
ApiKey = apiKey,
|
||||
ApiKeyPrefix = apiKeyPrefix,
|
||||
DefaultHeaders = defaultHeaders,
|
||||
BasePath = second.BasePath ?? first.BasePath,
|
||||
Timeout = second.Timeout,
|
||||
Proxy = second.Proxy ?? first.Proxy,
|
||||
UserAgent = second.UserAgent ?? first.UserAgent,
|
||||
Username = second.Username ?? first.Username,
|
||||
Password = second.Password ?? first.Password,
|
||||
AccessToken = second.AccessToken ?? first.AccessToken,
|
||||
{{#hasHttpSignatureMethods}}
|
||||
HttpSigningConfiguration = second.HttpSigningConfiguration ?? first.HttpSigningConfiguration,
|
||||
{{/hasHttpSignatureMethods}}
|
||||
TempFolderPath = second.TempFolderPath ?? first.TempFolderPath,
|
||||
DateTimeFormat = second.DateTimeFormat ?? first.DateTimeFormat
|
||||
};
|
||||
return config;
|
||||
}
|
||||
#endregion Static Members
|
||||
}
|
||||
}
|
14
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ExceptionFactory.mustache
vendored
Normal file
14
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ExceptionFactory.mustache
vendored
Normal file
@ -0,0 +1,14 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// A delegate to ExceptionFactory method
|
||||
/// </summary>
|
||||
/// <param name="methodName">Method name</param>
|
||||
/// <param name="response">Response</param>
|
||||
/// <returns>Exceptions</returns>
|
||||
{{>visibility}} delegate Exception ExceptionFactory(string methodName, IApiResponse response);
|
||||
}
|
@ -0,0 +1,59 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// <see cref="GlobalConfiguration"/> provides a compile-time extension point for globally configuring
|
||||
/// API Clients.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// A customized implementation via partial class may reside in another file and may
|
||||
/// be excluded from automatic generation via a .openapi-generator-ignore file.
|
||||
/// </remarks>
|
||||
public partial class GlobalConfiguration : Configuration
|
||||
{
|
||||
#region Private Members
|
||||
|
||||
private static readonly object GlobalConfigSync = new { };
|
||||
private static IReadableConfiguration _globalConfiguration;
|
||||
|
||||
#endregion Private Members
|
||||
|
||||
#region Constructors
|
||||
|
||||
/// <inheritdoc />
|
||||
private GlobalConfiguration()
|
||||
{
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public GlobalConfiguration(IDictionary<string, string> defaultHeader, IDictionary<string, string> apiKey, IDictionary<string, string> apiKeyPrefix, string basePath = "http://localhost:3000/api") : base(defaultHeader, apiKey, apiKeyPrefix, basePath)
|
||||
{
|
||||
}
|
||||
|
||||
static GlobalConfiguration()
|
||||
{
|
||||
Instance = new GlobalConfiguration();
|
||||
}
|
||||
|
||||
#endregion Constructors
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the default Configuration.
|
||||
/// </summary>
|
||||
/// <value>Configuration.</value>
|
||||
public static IReadableConfiguration Instance
|
||||
{
|
||||
get { return _globalConfiguration; }
|
||||
set
|
||||
{
|
||||
lock (GlobalConfigSync)
|
||||
{
|
||||
_globalConfiguration = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
25
modules/openapi-generator/src/main/resources/csharp-netcore-functions/HttpMethod.mustache
vendored
Normal file
25
modules/openapi-generator/src/main/resources/csharp-netcore-functions/HttpMethod.mustache
vendored
Normal file
@ -0,0 +1,25 @@
|
||||
{{>partial_header}}
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Http methods supported by swagger
|
||||
/// </summary>
|
||||
public enum HttpMethod
|
||||
{
|
||||
/// <summary>HTTP GET request.</summary>
|
||||
Get,
|
||||
/// <summary>HTTP POST request.</summary>
|
||||
Post,
|
||||
/// <summary>HTTP PUT request.</summary>
|
||||
Put,
|
||||
/// <summary>HTTP DELETE request.</summary>
|
||||
Delete,
|
||||
/// <summary>HTTP HEAD request.</summary>
|
||||
Head,
|
||||
/// <summary>HTTP OPTIONS request.</summary>
|
||||
Options,
|
||||
/// <summary>HTTP PATCH request.</summary>
|
||||
Patch
|
||||
}
|
||||
}
|
@ -0,0 +1,757 @@
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Security;
|
||||
using System.Security.Cryptography;
|
||||
using System.Text;
|
||||
using System.Web;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Class for HttpSigning auth related parameter and methods
|
||||
/// </summary>
|
||||
public class HttpSigningConfiguration
|
||||
{
|
||||
#region
|
||||
/// <summary>
|
||||
/// Initailize the HashAlgorithm and SigningAlgorithm to default value
|
||||
/// </summary>
|
||||
public HttpSigningConfiguration()
|
||||
{
|
||||
HashAlgorithm = HashAlgorithmName.SHA256;
|
||||
SigningAlgorithm = "PKCS1-v15";
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region Properties
|
||||
/// <summary>
|
||||
///Gets the Api keyId
|
||||
/// </summary>
|
||||
public string KeyId { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the Key file path
|
||||
/// </summary>
|
||||
public string KeyFilePath { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the key pass phrase for password protected key
|
||||
/// </summary>
|
||||
public SecureString KeyPassPhrase { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the HTTP signing header
|
||||
/// </summary>
|
||||
public List<string> HttpSigningHeader { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the hash algorithm sha256 or sha512
|
||||
/// </summary>
|
||||
public HashAlgorithmName HashAlgorithm { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the signing algorithm
|
||||
/// </summary>
|
||||
public string SigningAlgorithm { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the Signature validaty period in seconds
|
||||
/// </summary>
|
||||
public int SignatureValidityPeriod { get; set; }
|
||||
|
||||
#endregion
|
||||
|
||||
#region enum
|
||||
private enum PrivateKeyType
|
||||
{
|
||||
None = 0,
|
||||
RSA = 1,
|
||||
ECDSA = 2,
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region Methods
|
||||
/// <summary>
|
||||
/// Gets the Headers for HttpSigning
|
||||
/// </summary>
|
||||
/// <param name="basePath">Base path</param>
|
||||
/// <param name="method">HTTP method</param>
|
||||
/// <param name="path">Path</param>
|
||||
/// <param name="requestOptions">Request options</param>
|
||||
/// <returns></returns>
|
||||
internal Dictionary<string, string> GetHttpSignedHeader(string basePath,string method, string path, RequestOptions requestOptions)
|
||||
{
|
||||
const string HEADER_REQUEST_TARGET = "(request-target)";
|
||||
//The time when the HTTP signature expires. The API server should reject HTTP requests
|
||||
//that have expired.
|
||||
const string HEADER_EXPIRES = "(expires)";
|
||||
//The 'Date' header.
|
||||
const string HEADER_DATE = "Date";
|
||||
//The 'Host' header.
|
||||
const string HEADER_HOST = "Host";
|
||||
//The time when the HTTP signature was generated.
|
||||
const string HEADER_CREATED = "(created)";
|
||||
//When the 'Digest' header is included in the HTTP signature, the client automatically
|
||||
//computes the digest of the HTTP request body, per RFC 3230.
|
||||
const string HEADER_DIGEST = "Digest";
|
||||
//The 'Authorization' header is automatically generated by the client. It includes
|
||||
//the list of signed headers and a base64-encoded signature.
|
||||
const string HEADER_AUTHORIZATION = "Authorization";
|
||||
|
||||
//Hash table to store singed headers
|
||||
var HttpSignedRequestHeader = new Dictionary<string, string>();
|
||||
var HttpSignatureHeader = new Dictionary<string, string>();
|
||||
|
||||
if (HttpSigningHeader.Count == 0)
|
||||
{
|
||||
HttpSigningHeader.Add("(created)");
|
||||
}
|
||||
|
||||
if (requestOptions.PathParameters != null)
|
||||
{
|
||||
foreach (var pathParam in requestOptions.PathParameters)
|
||||
{
|
||||
var tempPath = path.Replace(pathParam.Key, "0");
|
||||
path = string.Format(tempPath, pathParam.Value);
|
||||
}
|
||||
}
|
||||
|
||||
var httpValues = HttpUtility.ParseQueryString(string.Empty);
|
||||
foreach (var parameter in requestOptions.QueryParameters)
|
||||
{
|
||||
#if (NETCOREAPP)
|
||||
if (parameter.Value.Count > 1)
|
||||
{ // array
|
||||
foreach (var value in parameter.Value)
|
||||
{
|
||||
httpValues.Add(HttpUtility.UrlEncode(parameter.Key) + "[]", value);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
httpValues.Add(HttpUtility.UrlEncode(parameter.Key), parameter.Value[0]);
|
||||
}
|
||||
#else
|
||||
if (parameter.Value.Count > 1)
|
||||
{ // array
|
||||
foreach (var value in parameter.Value)
|
||||
{
|
||||
httpValues.Add(parameter.Key + "[]", value);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
httpValues.Add(parameter.Key, parameter.Value[0]);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
var uriBuilder = new UriBuilder(string.Concat(basePath, path));
|
||||
uriBuilder.Query = httpValues.ToString().Replace("+", "%20");
|
||||
|
||||
var dateTime = DateTime.Now;
|
||||
string Digest = string.Empty;
|
||||
|
||||
//get the body
|
||||
string requestBody = string.Empty;
|
||||
if (requestOptions.Data != null)
|
||||
{
|
||||
var serializerSettings = new JsonSerializerSettings();
|
||||
requestBody = JsonConvert.SerializeObject(requestOptions.Data, serializerSettings);
|
||||
}
|
||||
|
||||
if (HashAlgorithm == HashAlgorithmName.SHA256)
|
||||
{
|
||||
var bodyDigest = GetStringHash(HashAlgorithm.ToString(), requestBody);
|
||||
Digest = string.Format("SHA-256={0}", Convert.ToBase64String(bodyDigest));
|
||||
}
|
||||
else if (HashAlgorithm == HashAlgorithmName.SHA512)
|
||||
{
|
||||
var bodyDigest = GetStringHash(HashAlgorithm.ToString(), requestBody);
|
||||
Digest = string.Format("SHA-512={0}", Convert.ToBase64String(bodyDigest));
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception(string.Format("{0} not supported", HashAlgorithm));
|
||||
}
|
||||
|
||||
|
||||
foreach (var header in HttpSigningHeader)
|
||||
{
|
||||
if (header.Equals(HEADER_REQUEST_TARGET))
|
||||
{
|
||||
var targetUrl = string.Format("{0} {1}{2}", method.ToLower(), uriBuilder.Path, uriBuilder.Query);
|
||||
HttpSignatureHeader.Add(header.ToLower(), targetUrl);
|
||||
}
|
||||
else if (header.Equals(HEADER_EXPIRES))
|
||||
{
|
||||
var expireDateTime = dateTime.AddSeconds(SignatureValidityPeriod);
|
||||
HttpSignatureHeader.Add(header.ToLower(), GetUnixTime(expireDateTime).ToString());
|
||||
}
|
||||
else if (header.Equals(HEADER_DATE))
|
||||
{
|
||||
var utcDateTime = dateTime.ToString("r").ToString();
|
||||
HttpSignatureHeader.Add(header.ToLower(), utcDateTime);
|
||||
HttpSignedRequestHeader.Add(HEADER_DATE, utcDateTime);
|
||||
}
|
||||
else if (header.Equals(HEADER_HOST))
|
||||
{
|
||||
HttpSignatureHeader.Add(header.ToLower(), uriBuilder.Host);
|
||||
HttpSignedRequestHeader.Add(HEADER_HOST, uriBuilder.Host);
|
||||
}
|
||||
else if (header.Equals(HEADER_CREATED))
|
||||
{
|
||||
HttpSignatureHeader.Add(header.ToLower(), GetUnixTime(dateTime).ToString());
|
||||
}
|
||||
else if (header.Equals(HEADER_DIGEST))
|
||||
{
|
||||
HttpSignedRequestHeader.Add(HEADER_DIGEST, Digest);
|
||||
HttpSignatureHeader.Add(header.ToLower(), Digest);
|
||||
}
|
||||
else
|
||||
{
|
||||
bool isHeaderFound = false;
|
||||
foreach (var item in requestOptions.HeaderParameters)
|
||||
{
|
||||
if (string.Equals(item.Key, header, StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
HttpSignatureHeader.Add(header.ToLower(), item.Value.ToString());
|
||||
isHeaderFound = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!isHeaderFound)
|
||||
{
|
||||
throw new Exception(string.Format("Cannot sign HTTP request.Request does not contain the {0} header.",header));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
var headersKeysString = string.Join(" ", HttpSignatureHeader.Keys);
|
||||
var headerValuesList = new List<string>();
|
||||
|
||||
foreach (var keyVal in HttpSignatureHeader)
|
||||
{
|
||||
headerValuesList.Add(string.Format("{0}: {1}", keyVal.Key, keyVal.Value));
|
||||
|
||||
}
|
||||
//Concatinate headers value separated by new line
|
||||
var headerValuesString = string.Join("\n", headerValuesList);
|
||||
var signatureStringHash = GetStringHash(HashAlgorithm.ToString(), headerValuesString);
|
||||
string headerSignatureStr = null;
|
||||
var keyType = GetKeyType(KeyFilePath);
|
||||
|
||||
if (keyType == PrivateKeyType.RSA)
|
||||
{
|
||||
headerSignatureStr = GetRSASignature(signatureStringHash);
|
||||
}
|
||||
else if (keyType == PrivateKeyType.ECDSA)
|
||||
{
|
||||
headerSignatureStr = GetECDSASignature(signatureStringHash);
|
||||
}
|
||||
var cryptographicScheme = "hs2019";
|
||||
var authorizationHeaderValue = string.Format("Signature keyId=\"{0}\",algorithm=\"{1}\"",
|
||||
KeyId, cryptographicScheme);
|
||||
|
||||
if (HttpSignatureHeader.ContainsKey(HEADER_CREATED))
|
||||
{
|
||||
authorizationHeaderValue += string.Format(",created={0}", HttpSignatureHeader[HEADER_CREATED]);
|
||||
}
|
||||
|
||||
if (HttpSignatureHeader.ContainsKey(HEADER_EXPIRES))
|
||||
{
|
||||
authorizationHeaderValue += string.Format(",expires={0}", HttpSignatureHeader[HEADER_EXPIRES]);
|
||||
}
|
||||
|
||||
authorizationHeaderValue += string.Format(",headers=\"{0}\",signature=\"{1}\"",
|
||||
headersKeysString, headerSignatureStr);
|
||||
|
||||
HttpSignedRequestHeader.Add(HEADER_AUTHORIZATION, authorizationHeaderValue);
|
||||
|
||||
return HttpSignedRequestHeader;
|
||||
}
|
||||
|
||||
private byte[] GetStringHash(string hashName, string stringToBeHashed)
|
||||
{
|
||||
var hashAlgorithm = System.Security.Cryptography.HashAlgorithm.Create(hashName);
|
||||
var bytes = Encoding.UTF8.GetBytes(stringToBeHashed);
|
||||
var stringHash = hashAlgorithm.ComputeHash(bytes);
|
||||
return stringHash;
|
||||
}
|
||||
|
||||
private int GetUnixTime(DateTime date2)
|
||||
{
|
||||
DateTime date1 = new DateTime(1970, 01, 01);
|
||||
TimeSpan timeSpan = date2 - date1;
|
||||
return (int)timeSpan.TotalSeconds;
|
||||
}
|
||||
|
||||
private string GetRSASignature(byte[] stringToSign)
|
||||
{
|
||||
RSA rsa = GetRSAProviderFromPemFile(KeyFilePath, KeyPassPhrase);
|
||||
if (SigningAlgorithm == "RSASSA-PSS")
|
||||
{
|
||||
var signedbytes = rsa.SignHash(stringToSign, HashAlgorithm, RSASignaturePadding.Pss);
|
||||
return Convert.ToBase64String(signedbytes);
|
||||
}
|
||||
else if (SigningAlgorithm == "PKCS1-v15")
|
||||
{
|
||||
var signedbytes = rsa.SignHash(stringToSign, HashAlgorithm, RSASignaturePadding.Pkcs1);
|
||||
return Convert.ToBase64String(signedbytes);
|
||||
}
|
||||
return string.Empty;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the ECDSA signature
|
||||
/// </summary>
|
||||
/// <param name="dataToSign"></param>
|
||||
/// <returns></returns>
|
||||
private string GetECDSASignature(byte[] dataToSign)
|
||||
{
|
||||
if (!File.Exists(KeyFilePath))
|
||||
{
|
||||
throw new Exception("key file path does not exist.");
|
||||
}
|
||||
|
||||
var ecKeyHeader = "-----BEGIN EC PRIVATE KEY-----";
|
||||
var ecKeyFooter = "-----END EC PRIVATE KEY-----";
|
||||
var keyStr = File.ReadAllText(KeyFilePath);
|
||||
var ecKeyBase64String = keyStr.Replace(ecKeyHeader, "").Replace(ecKeyFooter, "").Trim();
|
||||
var keyBytes = System.Convert.FromBase64String(ecKeyBase64String);
|
||||
var ecdsa = ECDsa.Create();
|
||||
|
||||
#if (NETCOREAPP3_0 || NETCOREAPP3_1 || NET5_0)
|
||||
var byteCount = 0;
|
||||
if (KeyPassPhrase != null)
|
||||
{
|
||||
IntPtr unmanagedString = IntPtr.Zero;
|
||||
try
|
||||
{
|
||||
// convert secure string to byte array
|
||||
unmanagedString = Marshal.SecureStringToGlobalAllocUnicode(KeyPassPhrase);
|
||||
ecdsa.ImportEncryptedPkcs8PrivateKey(Encoding.UTF8.GetBytes(Marshal.PtrToStringUni(unmanagedString)), keyBytes, out byteCount);
|
||||
}
|
||||
finally
|
||||
{
|
||||
if (unmanagedString != IntPtr.Zero)
|
||||
{
|
||||
Marshal.ZeroFreeBSTR(unmanagedString);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
ecdsa.ImportPkcs8PrivateKey(keyBytes, out byteCount);
|
||||
}
|
||||
var signedBytes = ecdsa.SignHash(dataToSign);
|
||||
var derBytes = ConvertToECDSAANS1Format(signedBytes);
|
||||
var signedString = System.Convert.ToBase64String(derBytes);
|
||||
|
||||
return signedString;
|
||||
#else
|
||||
throw new Exception("ECDSA signing is supported only on NETCOREAPP3_0 and above");
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
private byte[] ConvertToECDSAANS1Format(byte[] signedBytes)
|
||||
{
|
||||
var derBytes = new List<byte>();
|
||||
byte derLength = 68; //default lenght for ECDSA code signinged bit 0x44
|
||||
byte rbytesLength = 32; //R length 0x20
|
||||
byte sbytesLength = 32; //S length 0x20
|
||||
var rBytes = new List<byte>();
|
||||
var sBytes = new List<byte>();
|
||||
for (int i = 0; i < 32; i++)
|
||||
{
|
||||
rBytes.Add(signedBytes[i]);
|
||||
}
|
||||
for (int i = 32; i < 64; i++)
|
||||
{
|
||||
sBytes.Add(signedBytes[i]);
|
||||
}
|
||||
|
||||
if (rBytes[0] > 0x7F)
|
||||
{
|
||||
derLength++;
|
||||
rbytesLength++;
|
||||
var tempBytes = new List<byte>();
|
||||
tempBytes.AddRange(rBytes);
|
||||
rBytes.Clear();
|
||||
rBytes.Add(0x00);
|
||||
rBytes.AddRange(tempBytes);
|
||||
}
|
||||
|
||||
if (sBytes[0] > 0x7F)
|
||||
{
|
||||
derLength++;
|
||||
sbytesLength++;
|
||||
var tempBytes = new List<byte>();
|
||||
tempBytes.AddRange(sBytes);
|
||||
sBytes.Clear();
|
||||
sBytes.Add(0x00);
|
||||
sBytes.AddRange(tempBytes);
|
||||
|
||||
}
|
||||
|
||||
derBytes.Add(48); //start of the sequence 0x30
|
||||
derBytes.Add(derLength); //total length r lenth, type and r bytes
|
||||
|
||||
derBytes.Add(2); //tag for integer
|
||||
derBytes.Add(rbytesLength); //length of r
|
||||
derBytes.AddRange(rBytes);
|
||||
|
||||
derBytes.Add(2); //tag for integer
|
||||
derBytes.Add(sbytesLength); //length of s
|
||||
derBytes.AddRange(sBytes);
|
||||
return derBytes.ToArray();
|
||||
}
|
||||
|
||||
private RSACryptoServiceProvider GetRSAProviderFromPemFile(string pemfile, SecureString keyPassPharse = null)
|
||||
{
|
||||
const string pempubheader = "-----BEGIN PUBLIC KEY-----";
|
||||
const string pempubfooter = "-----END PUBLIC KEY-----";
|
||||
bool isPrivateKeyFile = true;
|
||||
byte[] pemkey = null;
|
||||
|
||||
if (!File.Exists(pemfile))
|
||||
{
|
||||
throw new Exception("private key file does not exist.");
|
||||
}
|
||||
string pemstr = File.ReadAllText(pemfile).Trim();
|
||||
|
||||
if (pemstr.StartsWith(pempubheader) && pemstr.EndsWith(pempubfooter))
|
||||
{
|
||||
isPrivateKeyFile = false;
|
||||
}
|
||||
|
||||
if (isPrivateKeyFile)
|
||||
{
|
||||
pemkey = ConvertPrivateKeyToBytes(pemstr, keyPassPharse);
|
||||
if (pemkey == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
return DecodeRSAPrivateKey(pemkey);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private byte[] ConvertPrivateKeyToBytes(string instr, SecureString keyPassPharse = null)
|
||||
{
|
||||
const string pemprivheader = "-----BEGIN RSA PRIVATE KEY-----";
|
||||
const string pemprivfooter = "-----END RSA PRIVATE KEY-----";
|
||||
string pemstr = instr.Trim();
|
||||
byte[] binkey;
|
||||
|
||||
if (!pemstr.StartsWith(pemprivheader) || !pemstr.EndsWith(pemprivfooter))
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
StringBuilder sb = new StringBuilder(pemstr);
|
||||
sb.Replace(pemprivheader, "");
|
||||
sb.Replace(pemprivfooter, "");
|
||||
string pvkstr = sb.ToString().Trim();
|
||||
|
||||
try
|
||||
{ // if there are no PEM encryption info lines, this is an UNencrypted PEM private key
|
||||
binkey = Convert.FromBase64String(pvkstr);
|
||||
return binkey;
|
||||
}
|
||||
catch (System.FormatException)
|
||||
{
|
||||
StringReader str = new StringReader(pvkstr);
|
||||
|
||||
//-------- read PEM encryption info. lines and extract salt -----
|
||||
if (!str.ReadLine().StartsWith("Proc-Type: 4,ENCRYPTED"))
|
||||
{
|
||||
return null;
|
||||
}
|
||||
string saltline = str.ReadLine();
|
||||
if (!saltline.StartsWith("DEK-Info: DES-EDE3-CBC,"))
|
||||
{
|
||||
return null;
|
||||
}
|
||||
string saltstr = saltline.Substring(saltline.IndexOf(",") + 1).Trim();
|
||||
byte[] salt = new byte[saltstr.Length / 2];
|
||||
for (int i = 0; i < salt.Length; i++)
|
||||
salt[i] = Convert.ToByte(saltstr.Substring(i * 2, 2), 16);
|
||||
if (!(str.ReadLine() == ""))
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
//------ remaining b64 data is encrypted RSA key ----
|
||||
string encryptedstr = str.ReadToEnd();
|
||||
|
||||
try
|
||||
{ //should have b64 encrypted RSA key now
|
||||
binkey = Convert.FromBase64String(encryptedstr);
|
||||
}
|
||||
catch (System.FormatException)
|
||||
{ //data is not in base64 fromat
|
||||
return null;
|
||||
}
|
||||
|
||||
byte[] deskey = GetEncryptedKey(salt, keyPassPharse, 1, 2); // count=1 (for OpenSSL implementation); 2 iterations to get at least 24 bytes
|
||||
if (deskey == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
//------ Decrypt the encrypted 3des-encrypted RSA private key ------
|
||||
byte[] rsakey = DecryptKey(binkey, deskey, salt); //OpenSSL uses salt value in PEM header also as 3DES IV
|
||||
return rsakey;
|
||||
}
|
||||
}
|
||||
|
||||
private RSACryptoServiceProvider DecodeRSAPrivateKey(byte[] privkey)
|
||||
{
|
||||
byte[] MODULUS, E, D, P, Q, DP, DQ, IQ;
|
||||
|
||||
// --------- Set up stream to decode the asn.1 encoded RSA private key ------
|
||||
MemoryStream mem = new MemoryStream(privkey);
|
||||
BinaryReader binr = new BinaryReader(mem); //wrap Memory Stream with BinaryReader for easy reading
|
||||
byte bt = 0;
|
||||
ushort twobytes = 0;
|
||||
int elems = 0;
|
||||
try
|
||||
{
|
||||
twobytes = binr.ReadUInt16();
|
||||
if (twobytes == 0x8130) //data read as little endian order (actual data order for Sequence is 30 81)
|
||||
{
|
||||
binr.ReadByte(); //advance 1 byte
|
||||
}
|
||||
else if (twobytes == 0x8230)
|
||||
{
|
||||
binr.ReadInt16(); //advance 2 bytes
|
||||
}
|
||||
else
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
twobytes = binr.ReadUInt16();
|
||||
if (twobytes != 0x0102) //version number
|
||||
{
|
||||
return null;
|
||||
}
|
||||
bt = binr.ReadByte();
|
||||
if (bt != 0x00)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
//------ all private key components are Integer sequences ----
|
||||
elems = GetIntegerSize(binr);
|
||||
MODULUS = binr.ReadBytes(elems);
|
||||
|
||||
elems = GetIntegerSize(binr);
|
||||
E = binr.ReadBytes(elems);
|
||||
|
||||
elems = GetIntegerSize(binr);
|
||||
D = binr.ReadBytes(elems);
|
||||
|
||||
elems = GetIntegerSize(binr);
|
||||
P = binr.ReadBytes(elems);
|
||||
|
||||
elems = GetIntegerSize(binr);
|
||||
Q = binr.ReadBytes(elems);
|
||||
|
||||
elems = GetIntegerSize(binr);
|
||||
DP = binr.ReadBytes(elems);
|
||||
|
||||
elems = GetIntegerSize(binr);
|
||||
DQ = binr.ReadBytes(elems);
|
||||
|
||||
elems = GetIntegerSize(binr);
|
||||
IQ = binr.ReadBytes(elems);
|
||||
|
||||
// ------- create RSACryptoServiceProvider instance and initialize with public key -----
|
||||
RSACryptoServiceProvider RSA = new RSACryptoServiceProvider();
|
||||
RSAParameters RSAparams = new RSAParameters();
|
||||
RSAparams.Modulus = MODULUS;
|
||||
RSAparams.Exponent = E;
|
||||
RSAparams.D = D;
|
||||
RSAparams.P = P;
|
||||
RSAparams.Q = Q;
|
||||
RSAparams.DP = DP;
|
||||
RSAparams.DQ = DQ;
|
||||
RSAparams.InverseQ = IQ;
|
||||
RSA.ImportParameters(RSAparams);
|
||||
return RSA;
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
finally
|
||||
{
|
||||
binr.Close();
|
||||
}
|
||||
}
|
||||
|
||||
private int GetIntegerSize(BinaryReader binr)
|
||||
{
|
||||
byte bt = 0;
|
||||
byte lowbyte = 0x00;
|
||||
byte highbyte = 0x00;
|
||||
int count = 0;
|
||||
bt = binr.ReadByte();
|
||||
if (bt != 0x02) //expect integer
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
bt = binr.ReadByte();
|
||||
|
||||
if (bt == 0x81)
|
||||
{
|
||||
count = binr.ReadByte(); // data size in next byte
|
||||
}
|
||||
else if (bt == 0x82)
|
||||
{
|
||||
highbyte = binr.ReadByte(); // data size in next 2 bytes
|
||||
lowbyte = binr.ReadByte();
|
||||
byte[] modint = { lowbyte, highbyte, 0x00, 0x00 };
|
||||
count = BitConverter.ToInt32(modint, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
count = bt; // we already have the data size
|
||||
}
|
||||
while (binr.ReadByte() == 0x00)
|
||||
{
|
||||
//remove high order zeros in data
|
||||
count -= 1;
|
||||
}
|
||||
binr.BaseStream.Seek(-1, SeekOrigin.Current);
|
||||
//last ReadByte wasn't a removed zero, so back up a byte
|
||||
return count;
|
||||
}
|
||||
|
||||
private byte[] GetEncryptedKey(byte[] salt, SecureString secpswd, int count, int miter)
|
||||
{
|
||||
IntPtr unmanagedPswd = IntPtr.Zero;
|
||||
int HASHLENGTH = 16; //MD5 bytes
|
||||
byte[] keymaterial = new byte[HASHLENGTH * miter]; //to store contatenated Mi hashed results
|
||||
|
||||
byte[] psbytes = new byte[secpswd.Length];
|
||||
unmanagedPswd = Marshal.SecureStringToGlobalAllocAnsi(secpswd);
|
||||
Marshal.Copy(unmanagedPswd, psbytes, 0, psbytes.Length);
|
||||
Marshal.ZeroFreeGlobalAllocAnsi(unmanagedPswd);
|
||||
|
||||
// --- contatenate salt and pswd bytes into fixed data array ---
|
||||
byte[] data00 = new byte[psbytes.Length + salt.Length];
|
||||
Array.Copy(psbytes, data00, psbytes.Length); //copy the pswd bytes
|
||||
Array.Copy(salt, 0, data00, psbytes.Length, salt.Length); //concatenate the salt bytes
|
||||
|
||||
// ---- do multi-hashing and contatenate results D1, D2 ... into keymaterial bytes ----
|
||||
MD5 md5 = new MD5CryptoServiceProvider();
|
||||
byte[] result = null;
|
||||
byte[] hashtarget = new byte[HASHLENGTH + data00.Length]; //fixed length initial hashtarget
|
||||
|
||||
for (int j = 0; j < miter; j++)
|
||||
{
|
||||
// ---- Now hash consecutively for count times ------
|
||||
if (j == 0)
|
||||
{
|
||||
result = data00; //initialize
|
||||
}
|
||||
else
|
||||
{
|
||||
Array.Copy(result, hashtarget, result.Length);
|
||||
Array.Copy(data00, 0, hashtarget, result.Length, data00.Length);
|
||||
result = hashtarget;
|
||||
}
|
||||
|
||||
for (int i = 0; i < count; i++)
|
||||
result = md5.ComputeHash(result);
|
||||
Array.Copy(result, 0, keymaterial, j * HASHLENGTH, result.Length); //contatenate to keymaterial
|
||||
}
|
||||
byte[] deskey = new byte[24];
|
||||
Array.Copy(keymaterial, deskey, deskey.Length);
|
||||
|
||||
Array.Clear(psbytes, 0, psbytes.Length);
|
||||
Array.Clear(data00, 0, data00.Length);
|
||||
Array.Clear(result, 0, result.Length);
|
||||
Array.Clear(hashtarget, 0, hashtarget.Length);
|
||||
Array.Clear(keymaterial, 0, keymaterial.Length);
|
||||
return deskey;
|
||||
}
|
||||
|
||||
private byte[] DecryptKey(byte[] cipherData, byte[] desKey, byte[] IV)
|
||||
{
|
||||
MemoryStream memst = new MemoryStream();
|
||||
TripleDES alg = TripleDES.Create();
|
||||
alg.Key = desKey;
|
||||
alg.IV = IV;
|
||||
try
|
||||
{
|
||||
CryptoStream cs = new CryptoStream(memst, alg.CreateDecryptor(), CryptoStreamMode.Write);
|
||||
cs.Write(cipherData, 0, cipherData.Length);
|
||||
cs.Close();
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
byte[] decryptedData = memst.ToArray();
|
||||
return decryptedData;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Detect the key type from the pem file.
|
||||
/// </summary>
|
||||
/// <param name="keyFilePath">key file path in pem format</param>
|
||||
/// <returns></returns>
|
||||
private PrivateKeyType GetKeyType(string keyFilePath)
|
||||
{
|
||||
if (!File.Exists(keyFilePath))
|
||||
{
|
||||
throw new Exception("Key file path does not exist.");
|
||||
}
|
||||
|
||||
var ecPrivateKeyHeader = "BEGIN EC PRIVATE KEY";
|
||||
var ecPrivateKeyFooter = "END EC PRIVATE KEY";
|
||||
var rsaPrivateKeyHeader = "BEGIN RSA PRIVATE KEY";
|
||||
var rsaPrivateFooter = "END RSA PRIVATE KEY";
|
||||
//var pkcs8Header = "BEGIN PRIVATE KEY";
|
||||
//var pkcs8Footer = "END PRIVATE KEY";
|
||||
var keyType = PrivateKeyType.None;
|
||||
var key = File.ReadAllLines(keyFilePath);
|
||||
|
||||
if (key[0].ToString().Contains(rsaPrivateKeyHeader) &&
|
||||
key[key.Length - 1].ToString().Contains(rsaPrivateFooter))
|
||||
{
|
||||
keyType = PrivateKeyType.RSA;
|
||||
}
|
||||
else if (key[0].ToString().Contains(ecPrivateKeyHeader) &&
|
||||
key[key.Length - 1].ToString().Contains(ecPrivateKeyFooter))
|
||||
{
|
||||
keyType = PrivateKeyType.ECDSA;
|
||||
}
|
||||
else if (key[0].ToString().Contains(ecPrivateKeyHeader) &&
|
||||
key[key.Length - 1].ToString().Contains(ecPrivateKeyFooter))
|
||||
{
|
||||
|
||||
/* this type of key can hold many type different types of private key, but here due lack of pem header
|
||||
Considering this as EC key
|
||||
*/
|
||||
//TODO :- update the key based on oid
|
||||
keyType = PrivateKeyType.ECDSA;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception("Either the key is invalid or key is not supported");
|
||||
|
||||
}
|
||||
return keyType;
|
||||
}
|
||||
#endregion
|
||||
}
|
||||
}
|
29
modules/openapi-generator/src/main/resources/csharp-netcore-functions/IApiAccessor.mustache
vendored
Normal file
29
modules/openapi-generator/src/main/resources/csharp-netcore-functions/IApiAccessor.mustache
vendored
Normal file
@ -0,0 +1,29 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents configuration aspects required to interact with the API endpoints.
|
||||
/// </summary>
|
||||
{{>visibility}} interface IApiAccessor
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the configuration object
|
||||
/// </summary>
|
||||
/// <value>An instance of the Configuration</value>
|
||||
IReadableConfiguration Configuration { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the base path of the API client.
|
||||
/// </summary>
|
||||
/// <value>The base path</value>
|
||||
string GetBasePath();
|
||||
|
||||
/// <summary>
|
||||
/// Provides a factory method hook for the creation of exceptions.
|
||||
/// </summary>
|
||||
ExceptionFactory ExceptionFactory { get; set; }
|
||||
}
|
||||
}
|
@ -0,0 +1,92 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Contract for Asynchronous RESTful API interactions.
|
||||
///
|
||||
/// This interface allows consumers to provide a custom API accessor client.
|
||||
/// </summary>
|
||||
public interface IAsynchronousClient
|
||||
{
|
||||
/// <summary>
|
||||
/// Executes a non-blocking call to some <paramref name="path"/> using the GET http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <param name="cancellationToken">Cancellation Token to cancel the request.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>A task eventually representing the response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
Task<ApiResponse<T>> GetAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken));
|
||||
|
||||
/// <summary>
|
||||
/// Executes a non-blocking call to some <paramref name="path"/> using the POST http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <param name="cancellationToken">Cancellation Token to cancel the request.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>A task eventually representing the response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
Task<ApiResponse<T>> PostAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken));
|
||||
|
||||
/// <summary>
|
||||
/// Executes a non-blocking call to some <paramref name="path"/> using the PUT http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <param name="cancellationToken">Cancellation Token to cancel the request.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>A task eventually representing the response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
Task<ApiResponse<T>> PutAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken));
|
||||
|
||||
/// <summary>
|
||||
/// Executes a non-blocking call to some <paramref name="path"/> using the DELETE http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <param name="cancellationToken">Cancellation Token to cancel the request.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>A task eventually representing the response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
Task<ApiResponse<T>> DeleteAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken));
|
||||
|
||||
/// <summary>
|
||||
/// Executes a non-blocking call to some <paramref name="path"/> using the HEAD http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <param name="cancellationToken">Cancellation Token to cancel the request.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>A task eventually representing the response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
Task<ApiResponse<T>> HeadAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken));
|
||||
|
||||
/// <summary>
|
||||
/// Executes a non-blocking call to some <paramref name="path"/> using the OPTIONS http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <param name="cancellationToken">Cancellation Token to cancel the request.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>A task eventually representing the response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
Task<ApiResponse<T>> OptionsAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken));
|
||||
|
||||
/// <summary>
|
||||
/// Executes a non-blocking call to some <paramref name="path"/> using the PATCH http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <param name="cancellationToken">Cancellation Token to cancel the request.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>A task eventually representing the response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
Task<ApiResponse<T>> PatchAsync<T>(string path, RequestOptions options, IReadableConfiguration configuration = null, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken));
|
||||
}
|
||||
}
|
@ -0,0 +1,114 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Net;
|
||||
using System.Security.Cryptography.X509Certificates;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Represents a readable-only configuration contract.
|
||||
/// </summary>
|
||||
public interface IReadableConfiguration
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the access token.
|
||||
/// </summary>
|
||||
/// <value>Access token.</value>
|
||||
string AccessToken { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the API key.
|
||||
/// </summary>
|
||||
/// <value>API key.</value>
|
||||
IDictionary<string, string> ApiKey { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the API key prefix.
|
||||
/// </summary>
|
||||
/// <value>API key prefix.</value>
|
||||
IDictionary<string, string> ApiKeyPrefix { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the base path.
|
||||
/// </summary>
|
||||
/// <value>Base path.</value>
|
||||
string BasePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the date time format.
|
||||
/// </summary>
|
||||
/// <value>Date time foramt.</value>
|
||||
string DateTimeFormat { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the default header.
|
||||
/// </summary>
|
||||
/// <value>Default header.</value>
|
||||
[Obsolete("Use DefaultHeaders instead.")]
|
||||
IDictionary<string, string> DefaultHeader { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the default headers.
|
||||
/// </summary>
|
||||
/// <value>Default headers.</value>
|
||||
IDictionary<string, string> DefaultHeaders { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the temp folder path.
|
||||
/// </summary>
|
||||
/// <value>Temp folder path.</value>
|
||||
string TempFolderPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the HTTP connection timeout (in milliseconds)
|
||||
/// </summary>
|
||||
/// <value>HTTP connection timeout.</value>
|
||||
int Timeout { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the proxy.
|
||||
/// </summary>
|
||||
/// <value>Proxy.</value>
|
||||
WebProxy Proxy { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the user agent.
|
||||
/// </summary>
|
||||
/// <value>User agent.</value>
|
||||
string UserAgent { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the username.
|
||||
/// </summary>
|
||||
/// <value>Username.</value>
|
||||
string Username { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the password.
|
||||
/// </summary>
|
||||
/// <value>Password.</value>
|
||||
string Password { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the API key with prefix.
|
||||
/// </summary>
|
||||
/// <param name="apiKeyIdentifier">API key identifier (authentication scheme).</param>
|
||||
/// <returns>API key with prefix.</returns>
|
||||
string GetApiKeyWithPrefix(string apiKeyIdentifier);
|
||||
|
||||
/// <summary>
|
||||
/// Gets certificate collection to be sent with requests.
|
||||
/// </summary>
|
||||
/// <value>X509 Certificate collection.</value>
|
||||
X509CertificateCollection ClientCertificates { get; }
|
||||
{{#hasHttpSignatureMethods}}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the HttpSigning configuration
|
||||
/// </summary>
|
||||
HttpSigningConfiguration HttpSigningConfiguration { get; }
|
||||
{{/hasHttpSignatureMethods}}
|
||||
}
|
||||
}
|
@ -0,0 +1,85 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Contract for Synchronous RESTful API interactions.
|
||||
///
|
||||
/// This interface allows consumers to provide a custom API accessor client.
|
||||
/// </summary>
|
||||
public interface ISynchronousClient
|
||||
{
|
||||
/// <summary>
|
||||
/// Executes a blocking call to some <paramref name="path"/> using the GET http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>The response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
ApiResponse<T> Get<T>(string path, RequestOptions options, IReadableConfiguration configuration = null);
|
||||
|
||||
/// <summary>
|
||||
/// Executes a blocking call to some <paramref name="path"/> using the POST http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>The response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
ApiResponse<T> Post<T>(string path, RequestOptions options, IReadableConfiguration configuration = null);
|
||||
|
||||
/// <summary>
|
||||
/// Executes a blocking call to some <paramref name="path"/> using the PUT http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>The response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
ApiResponse<T> Put<T>(string path, RequestOptions options, IReadableConfiguration configuration = null);
|
||||
|
||||
/// <summary>
|
||||
/// Executes a blocking call to some <paramref name="path"/> using the DELETE http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>The response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
ApiResponse<T> Delete<T>(string path, RequestOptions options, IReadableConfiguration configuration = null);
|
||||
|
||||
/// <summary>
|
||||
/// Executes a blocking call to some <paramref name="path"/> using the HEAD http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>The response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
ApiResponse<T> Head<T>(string path, RequestOptions options, IReadableConfiguration configuration = null);
|
||||
|
||||
/// <summary>
|
||||
/// Executes a blocking call to some <paramref name="path"/> using the OPTIONS http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>The response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
ApiResponse<T> Options<T>(string path, RequestOptions options, IReadableConfiguration configuration = null);
|
||||
|
||||
/// <summary>
|
||||
/// Executes a blocking call to some <paramref name="path"/> using the PATCH http verb.
|
||||
/// </summary>
|
||||
/// <param name="path">The relative path to invoke.</param>
|
||||
/// <param name="options">The request parameters to pass along to the client.</param>
|
||||
/// <param name="configuration">Per-request configurable settings.</param>
|
||||
/// <typeparam name="T">The return type.</typeparam>
|
||||
/// <returns>The response data, decorated with <see cref="ApiResponse{T}"/></returns>
|
||||
ApiResponse<T> Patch<T>(string path, RequestOptions options, IReadableConfiguration configuration = null);
|
||||
}
|
||||
}
|
125
modules/openapi-generator/src/main/resources/csharp-netcore-functions/JsonSubTypesTests.mustache
vendored
Normal file
125
modules/openapi-generator/src/main/resources/csharp-netcore-functions/JsonSubTypesTests.mustache
vendored
Normal file
@ -0,0 +1,125 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using JsonSubTypes;
|
||||
using Newtonsoft.Json;
|
||||
using NUnit.Framework;
|
||||
|
||||
using {{packageName}}.{{apiPackage}};
|
||||
using {{packageName}}.{{modelPackage}};
|
||||
using {{packageName}}.Client;
|
||||
|
||||
namespace {{packageName}}.Test.Client
|
||||
{
|
||||
public class JsonSubTypesTests
|
||||
{
|
||||
[Test]
|
||||
public void TestSimpleJsonSubTypesExample()
|
||||
{
|
||||
var annimal =
|
||||
JsonConvert.DeserializeObject<IAnimal>("{\"Kind\":\"Dog\",\"Breed\":\"Jack Russell Terrier\"}");
|
||||
Assert.AreEqual("Jack Russell Terrier", (annimal as Dog)?.Breed);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void DeserializeObjectWithCustomMapping()
|
||||
{
|
||||
var annimal =
|
||||
JsonConvert.DeserializeObject<Animal2>("{\"Sound\":\"Bark\",\"Breed\":\"Jack Russell Terrier\"}");
|
||||
Assert.AreEqual("Jack Russell Terrier", (annimal as Dog2)?.Breed);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void DeserializeObjectMappingByPropertyPresence()
|
||||
{
|
||||
string json =
|
||||
"[{\"Department\":\"Department1\",\"JobTitle\":\"JobTitle1\",\"FirstName\":\"FirstName1\",\"LastName\":\"LastName1\"}," +
|
||||
"{\"Department\":\"Department1\",\"JobTitle\":\"JobTitle1\",\"FirstName\":\"FirstName1\",\"LastName\":\"LastName1\"}," +
|
||||
"{\"Skill\":\"Painter\",\"FirstName\":\"FirstName1\",\"LastName\":\"LastName1\"}]";
|
||||
|
||||
|
||||
var persons = JsonConvert.DeserializeObject<ICollection<Person>>(json);
|
||||
Assert.AreEqual("Painter", (persons.Last() as Artist)?.Skill);
|
||||
}
|
||||
}
|
||||
|
||||
[JsonConverter(typeof(JsonSubtypes), "Kind")]
|
||||
public interface IAnimal
|
||||
{
|
||||
string Kind { get; }
|
||||
}
|
||||
|
||||
public class Dog : IAnimal
|
||||
{
|
||||
public Dog()
|
||||
{
|
||||
Kind = "Dog";
|
||||
}
|
||||
|
||||
public string Kind { get; }
|
||||
public string Breed { get; set; }
|
||||
}
|
||||
|
||||
class Cat : IAnimal
|
||||
{
|
||||
public Cat()
|
||||
{
|
||||
Kind = "Cat";
|
||||
}
|
||||
|
||||
public string Kind { get; }
|
||||
bool Declawed { get; set; }
|
||||
}
|
||||
|
||||
[JsonConverter(typeof(JsonSubtypes), "Sound")]
|
||||
[JsonSubtypes.KnownSubType(typeof(Dog2), "Bark")]
|
||||
[JsonSubtypes.KnownSubType(typeof(Cat2), "Meow")]
|
||||
public class Animal2
|
||||
{
|
||||
public virtual string Sound { get; }
|
||||
public string Color { get; set; }
|
||||
}
|
||||
|
||||
public class Dog2 : Animal2
|
||||
{
|
||||
public Dog2()
|
||||
{
|
||||
Sound = "Bark";
|
||||
}
|
||||
|
||||
public override string Sound { get; }
|
||||
public string Breed { get; set; }
|
||||
}
|
||||
|
||||
public class Cat2 : Animal2
|
||||
{
|
||||
public Cat2()
|
||||
{
|
||||
Sound = "Meow";
|
||||
}
|
||||
|
||||
public override string Sound { get; }
|
||||
public bool Declawed { get; set; }
|
||||
}
|
||||
|
||||
[JsonConverter(typeof(JsonSubtypes))]
|
||||
[JsonSubtypes.KnownSubTypeWithProperty(typeof(Employee), "JobTitle")]
|
||||
[JsonSubtypes.KnownSubTypeWithProperty(typeof(Artist), "Skill")]
|
||||
public class Person
|
||||
{
|
||||
public string FirstName { get; set; }
|
||||
public string LastName { get; set; }
|
||||
}
|
||||
|
||||
public class Employee : Person
|
||||
{
|
||||
public string Department { get; set; }
|
||||
public string JobTitle { get; set; }
|
||||
}
|
||||
|
||||
public class Artist : Person
|
||||
{
|
||||
public string Skill { get; set; }
|
||||
}
|
||||
}
|
287
modules/openapi-generator/src/main/resources/csharp-netcore-functions/Multimap.mustache
vendored
Normal file
287
modules/openapi-generator/src/main/resources/csharp-netcore-functions/Multimap.mustache
vendored
Normal file
@ -0,0 +1,287 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// A dictionary in which one key has many associated values.
|
||||
/// </summary>
|
||||
/// <typeparam name="TKey">The type of the key</typeparam>
|
||||
/// <typeparam name="TValue">The type of the value associated with the key.</typeparam>
|
||||
public class Multimap<TKey, TValue> : IDictionary<TKey, IList<TValue>>
|
||||
{
|
||||
#region Private Fields
|
||||
|
||||
private readonly Dictionary<TKey, IList<TValue>> _dictionary;
|
||||
|
||||
#endregion Private Fields
|
||||
|
||||
#region Constructors
|
||||
|
||||
/// <summary>
|
||||
/// Empty Constructor.
|
||||
/// </summary>
|
||||
public Multimap()
|
||||
{
|
||||
_dictionary = new Dictionary<TKey, IList<TValue>>();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Constructor with comparer.
|
||||
/// </summary>
|
||||
/// <param name="comparer"></param>
|
||||
public Multimap(IEqualityComparer<TKey> comparer)
|
||||
{
|
||||
_dictionary = new Dictionary<TKey, IList<TValue>>(comparer);
|
||||
}
|
||||
|
||||
#endregion Constructors
|
||||
|
||||
#region Enumerators
|
||||
|
||||
/// <summary>
|
||||
/// To get the enumerator.
|
||||
/// </summary>
|
||||
/// <returns>Enumerator</returns>
|
||||
public IEnumerator<KeyValuePair<TKey, IList<TValue>>> GetEnumerator()
|
||||
{
|
||||
return _dictionary.GetEnumerator();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// To get the enumerator.
|
||||
/// </summary>
|
||||
/// <returns>Enumerator</returns>
|
||||
IEnumerator IEnumerable.GetEnumerator()
|
||||
{
|
||||
return _dictionary.GetEnumerator();
|
||||
}
|
||||
|
||||
#endregion Enumerators
|
||||
|
||||
#region Public Members
|
||||
/// <summary>
|
||||
/// Add values to Multimap
|
||||
/// </summary>
|
||||
/// <param name="item">Key value pair</param>
|
||||
public void Add(KeyValuePair<TKey, IList<TValue>> item)
|
||||
{
|
||||
if (!TryAdd(item.Key, item.Value))
|
||||
throw new InvalidOperationException("Could not add values to Multimap.");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add Multimap to Multimap
|
||||
/// </summary>
|
||||
/// <param name="multimap">Multimap</param>
|
||||
public void Add(Multimap<TKey, TValue> multimap)
|
||||
{
|
||||
foreach (var item in multimap)
|
||||
{
|
||||
if (!TryAdd(item.Key, item.Value))
|
||||
throw new InvalidOperationException("Could not add values to Multimap.");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Clear Multimap
|
||||
/// </summary>
|
||||
public void Clear()
|
||||
{
|
||||
_dictionary.Clear();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determines whether Multimap contains the specified item.
|
||||
/// </summary>
|
||||
/// <param name="item">Key value pair</param>
|
||||
/// <exception cref="NotImplementedException">Method needs to be implemented</exception>
|
||||
/// <returns>true if the Multimap contains the item; otherwise, false.</returns>
|
||||
public bool Contains(KeyValuePair<TKey, IList<TValue>> item)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copy items of the Multimap to an array,
|
||||
/// starting at a particular array index.
|
||||
/// </summary>
|
||||
/// <param name="array">The array that is the destination of the items copied
|
||||
/// from Multimap. The array must have zero-based indexing.</param>
|
||||
/// <param name="arrayIndex">The zero-based index in array at which copying begins.</param>
|
||||
/// <exception cref="NotImplementedException">Method needs to be implemented</exception>
|
||||
public void CopyTo(KeyValuePair<TKey, IList<TValue>>[] array, int arrayIndex)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Removes the specified item from the Multimap.
|
||||
/// </summary>
|
||||
/// <param name="item">Key value pair</param>
|
||||
/// <returns>true if the item is successfully removed; otherwise, false.</returns>
|
||||
/// <exception cref="NotImplementedException">Method needs to be implemented</exception>
|
||||
public bool Remove(KeyValuePair<TKey, IList<TValue>> item)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the number of items contained in the Multimap.
|
||||
/// </summary>
|
||||
public int Count => _dictionary.Count;
|
||||
|
||||
/// <summary>
|
||||
/// Gets a value indicating whether the Multimap is read-only.
|
||||
/// </summary>
|
||||
public bool IsReadOnly => false;
|
||||
|
||||
/// <summary>
|
||||
/// Adds an item with the provided key and value to the Multimap.
|
||||
/// </summary>
|
||||
/// <param name="key">The object to use as the key of the item to add.</param>
|
||||
/// <param name="value">The object to use as the value of the item to add.</param>
|
||||
/// <exception cref="InvalidOperationException">Thrown when couldn't add the value to Multimap.</exception>
|
||||
public void Add(TKey key, IList<TValue> value)
|
||||
{
|
||||
if (value != null && value.Count > 0)
|
||||
{
|
||||
if (_dictionary.TryGetValue(key, out var list))
|
||||
{
|
||||
foreach (var k in value) list.Add(k);
|
||||
}
|
||||
else
|
||||
{
|
||||
list = new List<TValue>(value);
|
||||
if (!TryAdd(key, list))
|
||||
throw new InvalidOperationException("Could not add values to Multimap.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determines whether the Multimap contains an item with the specified key.
|
||||
/// </summary>
|
||||
/// <param name="key">The key to locate in the Multimap.</param>
|
||||
/// <returns>true if the Multimap contains an item with
|
||||
/// the key; otherwise, false.</returns>
|
||||
public bool ContainsKey(TKey key)
|
||||
{
|
||||
return _dictionary.ContainsKey(key);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Removes item with the specified key from the Multimap.
|
||||
/// </summary>
|
||||
/// <param name="key">The key to locate in the Multimap.</param>
|
||||
/// <returns>true if the item is successfully removed; otherwise, false.</returns>
|
||||
public bool Remove(TKey key)
|
||||
{
|
||||
return TryRemove(key, out var _);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the value associated with the specified key.
|
||||
/// </summary>
|
||||
/// <param name="key">The key whose value to get.</param>
|
||||
/// <param name="value">When this method returns, the value associated with the specified key, if the
|
||||
/// key is found; otherwise, the default value for the type of the value parameter.
|
||||
/// This parameter is passed uninitialized.</param>
|
||||
/// <returns> true if the object that implements Multimap contains
|
||||
/// an item with the specified key; otherwise, false.</returns>
|
||||
public bool TryGetValue(TKey key, out IList<TValue> value)
|
||||
{
|
||||
return _dictionary.TryGetValue(key, out value);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the item with the specified key.
|
||||
/// </summary>
|
||||
/// <param name="key">The key of the item to get or set.</param>
|
||||
/// <returns>The value of the specified key.</returns>
|
||||
public IList<TValue> this[TKey key]
|
||||
{
|
||||
get => _dictionary[key];
|
||||
set => _dictionary[key] = value;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a System.Collections.Generic.ICollection containing the keys of the Multimap.
|
||||
/// </summary>
|
||||
public ICollection<TKey> Keys => _dictionary.Keys;
|
||||
|
||||
/// <summary>
|
||||
/// Gets a System.Collections.Generic.ICollection containing the values of the Multimap.
|
||||
/// </summary>
|
||||
public ICollection<IList<TValue>> Values => _dictionary.Values;
|
||||
|
||||
/// <summary>
|
||||
/// Copy the items of the Multimap to an System.Array,
|
||||
/// starting at a particular System.Array index.
|
||||
/// </summary>
|
||||
/// <param name="array">The one-dimensional System.Array that is the destination of the items copied
|
||||
/// from Multimap. The System.Array must have zero-based indexing.</param>
|
||||
/// <param name="index">The zero-based index in array at which copying begins.</param>
|
||||
public void CopyTo(Array array, int index)
|
||||
{
|
||||
((ICollection)_dictionary).CopyTo(array, index);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Adds an item with the provided key and value to the Multimap.
|
||||
/// </summary>
|
||||
/// <param name="key">The object to use as the key of the item to add.</param>
|
||||
/// <param name="value">The object to use as the value of the item to add.</param>
|
||||
/// <exception cref="InvalidOperationException">Thrown when couldn't add value to Multimap.</exception>
|
||||
public void Add(TKey key, TValue value)
|
||||
{
|
||||
if (value != null)
|
||||
{
|
||||
if (_dictionary.TryGetValue(key, out var list))
|
||||
{
|
||||
list.Add(value);
|
||||
}
|
||||
else
|
||||
{
|
||||
list = new List<TValue> { value };
|
||||
if (!TryAdd(key, list))
|
||||
throw new InvalidOperationException("Could not add value to Multimap.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endregion Public Members
|
||||
|
||||
#region Private Members
|
||||
|
||||
/**
|
||||
* Helper method to encapsulate generator differences between dictionary types.
|
||||
*/
|
||||
private bool TryRemove(TKey key, out IList<TValue> value)
|
||||
{
|
||||
_dictionary.TryGetValue(key, out value);
|
||||
return _dictionary.Remove(key);
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper method to encapsulate generator differences between dictionary types.
|
||||
*/
|
||||
private bool TryAdd(TKey key, IList<TValue> value)
|
||||
{
|
||||
try
|
||||
{
|
||||
_dictionary.Add(key, value);
|
||||
}
|
||||
catch (ArgumentException)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
#endregion Private Members
|
||||
}
|
||||
}
|
@ -0,0 +1,21 @@
|
||||
{{>partial_header}}
|
||||
using Newtonsoft.Json.Converters;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Formatter for 'date' openapi formats ss defined by full-date - RFC3339
|
||||
/// see https://github.com/OAI/OpenAPI-Specification/blob/master/versions/3.0.0.md#data-types
|
||||
/// </summary>
|
||||
public class OpenAPIDateConverter : IsoDateTimeConverter
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="OpenAPIDateConverter" /> class.
|
||||
/// </summary>
|
||||
public OpenAPIDateConverter()
|
||||
{
|
||||
// full-date = date-fullyear "-" date-month "-" date-mday
|
||||
DateTimeFormat = "yyyy-MM-dd";
|
||||
}
|
||||
}
|
||||
}
|
270
modules/openapi-generator/src/main/resources/csharp-netcore-functions/README.mustache
vendored
Normal file
270
modules/openapi-generator/src/main/resources/csharp-netcore-functions/README.mustache
vendored
Normal file
@ -0,0 +1,270 @@
|
||||
# {{packageName}} - the C# library for the {{appName}}
|
||||
|
||||
{{#appDescriptionWithNewLines}}
|
||||
{{{appDescriptionWithNewLines}}}
|
||||
{{/appDescriptionWithNewLines}}
|
||||
|
||||
This C# SDK is automatically generated by the [OpenAPI Generator](https://openapi-generator.tech) project:
|
||||
|
||||
- API version: {{appVersion}}
|
||||
- SDK version: {{packageVersion}}
|
||||
{{^hideGenerationTimestamp}}
|
||||
- Build date: {{generatedDate}}
|
||||
{{/hideGenerationTimestamp}}
|
||||
- Build package: {{generatorClass}}
|
||||
{{#infoUrl}}
|
||||
For more information, please visit [{{{infoUrl}}}]({{{infoUrl}}})
|
||||
{{/infoUrl}}
|
||||
|
||||
<a name="frameworks-supported"></a>
|
||||
## Frameworks supported
|
||||
{{#netStandard}}
|
||||
- .NET Core >=1.0
|
||||
- .NET Framework >=4.6
|
||||
- Mono/Xamarin >=vNext
|
||||
{{/netStandard}}
|
||||
|
||||
<a name="dependencies"></a>
|
||||
## Dependencies
|
||||
|
||||
{{#useRestSharp}}
|
||||
- [RestSharp](https://www.nuget.org/packages/RestSharp) - 106.11.7 or later
|
||||
{{/useRestSharp}}
|
||||
- [Json.NET](https://www.nuget.org/packages/Newtonsoft.Json/) - 12.0.3 or later
|
||||
- [JsonSubTypes](https://www.nuget.org/packages/JsonSubTypes/) - 1.8.0 or later
|
||||
{{#useCompareNetObjects}}
|
||||
- [CompareNETObjects](https://www.nuget.org/packages/CompareNETObjects) - 4.61.0 or later
|
||||
{{/useCompareNetObjects}}
|
||||
{{#validatable}}
|
||||
- [System.ComponentModel.Annotations](https://www.nuget.org/packages/System.ComponentModel.Annotations) - 5.0.0 or later
|
||||
{{/validatable}}
|
||||
|
||||
The DLLs included in the package may not be the latest version. We recommend using [NuGet](https://docs.nuget.org/consume/installing-nuget) to obtain the latest version of the packages:
|
||||
```
|
||||
{{#useRestSharp}}
|
||||
Install-Package RestSharp
|
||||
{{/useRestSharp}}
|
||||
Install-Package Newtonsoft.Json
|
||||
Install-Package JsonSubTypes
|
||||
{{#validatable}}
|
||||
Install-Package System.ComponentModel.Annotations
|
||||
{{/validatable}}
|
||||
{{#useCompareNetObjects}}
|
||||
Install-Package CompareNETObjects
|
||||
{{/useCompareNetObjects}}
|
||||
```
|
||||
{{#useRestSharp}}
|
||||
|
||||
NOTE: RestSharp versions greater than 105.1.0 have a bug which causes file uploads to fail. See [RestSharp#742](https://github.com/restsharp/RestSharp/issues/742).
|
||||
NOTE: RestSharp for .Net Core creates a new socket for each api call, which can lead to a socket exhaustion problem. See [RestSharp#1406](https://github.com/restsharp/RestSharp/issues/1406).
|
||||
|
||||
{{/useRestSharp}}
|
||||
<a name="installation"></a>
|
||||
## Installation
|
||||
{{#netStandard}}
|
||||
Generate the DLL using your preferred tool (e.g. `dotnet build`)
|
||||
{{/netStandard}}
|
||||
{{^netStandard}}
|
||||
Run the following command to generate the DLL
|
||||
- [Mac/Linux] `/bin/sh build.sh`
|
||||
- [Windows] `build.bat`
|
||||
{{/netStandard}}
|
||||
|
||||
Then include the DLL (under the `bin` folder) in the C# project, and use the namespaces:
|
||||
```csharp
|
||||
using {{packageName}}.{{apiPackage}};
|
||||
using {{packageName}}.Client;
|
||||
using {{packageName}}.{{modelPackage}};
|
||||
```
|
||||
{{^netStandard}}
|
||||
<a name="packaging"></a>
|
||||
## Packaging
|
||||
|
||||
A `.nuspec` is included with the project. You can follow the Nuget quickstart to [create](https://docs.microsoft.com/en-us/nuget/quickstart/create-and-publish-a-package#create-the-package) and [publish](https://docs.microsoft.com/en-us/nuget/quickstart/create-and-publish-a-package#publish-the-package) packages.
|
||||
|
||||
This `.nuspec` uses placeholders from the `.csproj`, so build the `.csproj` directly:
|
||||
|
||||
```
|
||||
nuget pack -Build -OutputDirectory out {{packageName}}.csproj
|
||||
```
|
||||
|
||||
Then, publish to a [local feed](https://docs.microsoft.com/en-us/nuget/hosting-packages/local-feeds) or [other host](https://docs.microsoft.com/en-us/nuget/hosting-packages/overview) and consume the new package via Nuget as usual.
|
||||
|
||||
{{/netStandard}}
|
||||
<a name="usage"></a>
|
||||
## Usage
|
||||
|
||||
To use the API client with a HTTP proxy, setup a `System.Net.WebProxy`
|
||||
```csharp
|
||||
Configuration c = new Configuration();
|
||||
System.Net.WebProxy webProxy = new System.Net.WebProxy("http://myProxyUrl:80/");
|
||||
webProxy.Credentials = System.Net.CredentialCache.DefaultCredentials;
|
||||
c.Proxy = webProxy;
|
||||
```
|
||||
{{#useHttpClient}}
|
||||
|
||||
### Connections
|
||||
Each ApiClass (properly the ApiClient inside it) will create an istance of HttpClient. It will use that for the entire lifecycle and dispose it when called the Dispose method.
|
||||
|
||||
To better manager the connections it's a common practice to reuse the HttpClient and HttpClientHander (see [here](https://docs.microsoft.com/en-us/dotnet/architecture/microservices/implement-resilient-applications/use-httpclientfactory-to-implement-resilient-http-requests#issues-with-the-original-httpclient-class-available-in-net) for details). To use your own HttpClient instance just pass it to the ApiClass constructor.
|
||||
|
||||
```csharp
|
||||
HttpClientHandler yourHandler = new HttpClientHandler();
|
||||
HttpClient yourHttpClient = new HttpClient(yourHandler);
|
||||
var api = new YourApiClass(yourHttpClient, yourHandler);
|
||||
```
|
||||
|
||||
If you want to use an HttpClient and don't have access to the handler, for example in a DI context in Asp.net Core when using IHttpClientFactory.
|
||||
|
||||
```csharp
|
||||
HttpClient yourHttpClient = new HttpClient();
|
||||
var api = new YourApiClass(yourHttpClient);
|
||||
```
|
||||
You'll loose some configuration settings, the features affected are: Setting and Retrieving Cookies, Client Certificates, Proxy settings. You need to either manually handle those in your setup of the HttpClient or they won't be available.
|
||||
|
||||
Here an example of DI setup in a sample web project:
|
||||
|
||||
```csharp
|
||||
services.AddHttpClient<YourApiClass>(httpClient =>
|
||||
new PetApi(httpClient));
|
||||
```
|
||||
|
||||
{{/useHttpClient}}
|
||||
|
||||
<a name="getting-started"></a>
|
||||
## Getting Started
|
||||
|
||||
```csharp
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
{{#useHttpClient}}
|
||||
using System.Net.Http;
|
||||
{{/useHttpClient}}
|
||||
using {{packageName}}.{{apiPackage}};
|
||||
using {{packageName}}.Client;
|
||||
using {{packageName}}.{{modelPackage}};
|
||||
|
||||
namespace Example
|
||||
{
|
||||
public class {{operationId}}Example
|
||||
{
|
||||
public static void Main()
|
||||
{
|
||||
{{#apiInfo}}{{#apis}}{{#-first}}{{#operations}}{{#operation}}{{#-first}}
|
||||
Configuration config = new Configuration();
|
||||
config.BasePath = "{{{basePath}}}";
|
||||
{{#hasAuthMethods}}
|
||||
{{#authMethods}}
|
||||
{{#isBasicBasic}}
|
||||
// Configure HTTP basic authorization: {{{name}}}
|
||||
config.Username = "YOUR_USERNAME";
|
||||
config.Password = "YOUR_PASSWORD";
|
||||
{{/isBasicBasic}}
|
||||
{{#isBasicBearer}}
|
||||
// Configure Bearer token for authorization: {{{name}}}
|
||||
config.AccessToken = "YOUR_BEARER_TOKEN";
|
||||
{{/isBasicBearer}}
|
||||
{{#isApiKey}}
|
||||
// Configure API key authorization: {{{name}}}
|
||||
config.ApiKey.Add("{{{keyParamName}}}", "YOUR_API_KEY");
|
||||
// Uncomment below to setup prefix (e.g. Bearer) for API key, if needed
|
||||
// config.ApiKeyPrefix.Add("{{{keyParamName}}}", "Bearer");
|
||||
{{/isApiKey}}
|
||||
{{#isOAuth}}
|
||||
// Configure OAuth2 access token for authorization: {{{name}}}
|
||||
config.AccessToken = "YOUR_ACCESS_TOKEN";
|
||||
{{/isOAuth}}
|
||||
{{/authMethods}}
|
||||
|
||||
{{/hasAuthMethods}}
|
||||
{{#useHttpClient}}
|
||||
// create instances of HttpClient, HttpClientHandler to be reused later with different Api classes
|
||||
HttpClient httpClient = new HttpClient();
|
||||
HttpClientHandler httpClientHandler = new HttpClientHandler();
|
||||
var apiInstance = new {{classname}}(httpClient, config, httpClientHandler);
|
||||
{{/useHttpClient}}
|
||||
{{^useHttpClient}}
|
||||
var apiInstance = new {{classname}}(config);
|
||||
{{/useHttpClient}}
|
||||
{{#allParams}}
|
||||
{{#isPrimitiveType}}
|
||||
var {{paramName}} = {{{example}}}; // {{{dataType}}} | {{{description}}}{{^required}} (optional) {{/required}}{{#defaultValue}} (default to {{{.}}}){{/defaultValue}}
|
||||
{{/isPrimitiveType}}
|
||||
{{^isPrimitiveType}}
|
||||
var {{paramName}} = new {{{dataType}}}(); // {{{dataType}}} | {{{description}}}{{^required}} (optional) {{/required}}{{#defaultValue}} (default to {{{.}}}){{/defaultValue}}
|
||||
{{/isPrimitiveType}}
|
||||
{{/allParams}}
|
||||
|
||||
try
|
||||
{
|
||||
{{#summary}}
|
||||
// {{{.}}}
|
||||
{{/summary}}
|
||||
{{#returnType}}{{{returnType}}} result = {{/returnType}}apiInstance.{{{operationId}}}({{#allParams}}{{paramName}}{{^-last}}, {{/-last}}{{/allParams}});{{#returnType}}
|
||||
Debug.WriteLine(result);{{/returnType}}
|
||||
}
|
||||
catch (ApiException e)
|
||||
{
|
||||
Debug.Print("Exception when calling {{classname}}.{{operationId}}: " + e.Message );
|
||||
Debug.Print("Status Code: "+ e.ErrorCode);
|
||||
Debug.Print(e.StackTrace);
|
||||
}
|
||||
{{/-first}}{{/operation}}{{/operations}}{{/-first}}{{/apis}}{{/apiInfo}}
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
<a name="documentation-for-api-endpoints"></a>
|
||||
## Documentation for API Endpoints
|
||||
|
||||
All URIs are relative to *{{{basePath}}}*
|
||||
|
||||
Class | Method | HTTP request | Description
|
||||
------------ | ------------- | ------------- | -------------
|
||||
{{#apiInfo}}{{#apis}}{{#operations}}{{#operation}}*{{classname}}* | [**{{operationId}}**]({{apiDocPath}}{{classname}}.md#{{operationIdLowerCase}}) | **{{httpMethod}}** {{path}} | {{#summary}}{{{summary}}}{{/summary}}
|
||||
{{/operation}}{{/operations}}{{/apis}}{{/apiInfo}}
|
||||
|
||||
<a name="documentation-for-models"></a>
|
||||
## Documentation for Models
|
||||
|
||||
{{#modelPackage}}
|
||||
{{#models}}{{#model}} - [{{{modelPackage}}}.{{{classname}}}]({{modelDocPath}}{{{classname}}}.md)
|
||||
{{/model}}{{/models}}
|
||||
{{/modelPackage}}
|
||||
{{^modelPackage}}
|
||||
No model defined in this package
|
||||
{{/modelPackage}}
|
||||
|
||||
<a name="documentation-for-authorization"></a>
|
||||
## Documentation for Authorization
|
||||
|
||||
{{^authMethods}}
|
||||
All endpoints do not require authorization.
|
||||
{{/authMethods}}
|
||||
{{#authMethods}}
|
||||
{{#last}}
|
||||
Authentication schemes defined for the API:
|
||||
{{/last}}
|
||||
{{/authMethods}}
|
||||
{{#authMethods}}
|
||||
<a name="{{name}}"></a>
|
||||
### {{name}}
|
||||
|
||||
{{#isApiKey}}- **Type**: API key
|
||||
- **API key parameter name**: {{keyParamName}}
|
||||
- **Location**: {{#isKeyInQuery}}URL query string{{/isKeyInQuery}}{{#isKeyInHeader}}HTTP header{{/isKeyInHeader}}
|
||||
{{/isApiKey}}
|
||||
{{#isBasicBasic}}- **Type**: HTTP basic authentication
|
||||
{{/isBasicBasic}}
|
||||
{{#isBasicBearer}}- **Type**: Bearer Authentication
|
||||
{{/isBasicBearer}}
|
||||
{{#isOAuth}}- **Type**: OAuth
|
||||
- **Flow**: {{flow}}
|
||||
- **Authorization URL**: {{authorizationUrl}}
|
||||
- **Scopes**: {{^scopes}}N/A{{/scopes}}
|
||||
{{#scopes}} - {{scope}}: {{description}}
|
||||
{{/scopes}}
|
||||
{{/isOAuth}}
|
||||
|
||||
{{/authMethods}}
|
137
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ReadOnlyDictionary.mustache
vendored
Normal file
137
modules/openapi-generator/src/main/resources/csharp-netcore-functions/ReadOnlyDictionary.mustache
vendored
Normal file
@ -0,0 +1,137 @@
|
||||
{{>partial_header}}
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
public class ReadOnlyDictionary<T, K> : IDictionary<T, K>
|
||||
{
|
||||
private IDictionary<T, K> _dictionaryImplementation;
|
||||
public IEnumerator<KeyValuePair<T, K>> GetEnumerator()
|
||||
{
|
||||
return _dictionaryImplementation.GetEnumerator();
|
||||
}
|
||||
|
||||
public ReadOnlyDictionary()
|
||||
{
|
||||
_dictionaryImplementation = new Dictionary<T, K>();
|
||||
}
|
||||
|
||||
public ReadOnlyDictionary(IDictionary<T, K> dictionaryImplementation)
|
||||
{
|
||||
if (dictionaryImplementation == null) throw new ArgumentNullException("dictionaryImplementation");
|
||||
_dictionaryImplementation = dictionaryImplementation;
|
||||
}
|
||||
|
||||
IEnumerator IEnumerable.GetEnumerator()
|
||||
{
|
||||
return ((IEnumerable) _dictionaryImplementation).GetEnumerator();
|
||||
}
|
||||
|
||||
public void Add(KeyValuePair<T, K> item)
|
||||
{
|
||||
throw new ReadonlyOperationException("This instance is readonly.");
|
||||
}
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
throw new ReadonlyOperationException("This instance is readonly.");
|
||||
}
|
||||
|
||||
public bool Contains(KeyValuePair<T, K> item)
|
||||
{
|
||||
return _dictionaryImplementation.Contains(item);
|
||||
}
|
||||
|
||||
public void CopyTo(KeyValuePair<T, K>[] array, int arrayIndex)
|
||||
{
|
||||
_dictionaryImplementation.CopyTo(array, arrayIndex);
|
||||
}
|
||||
|
||||
public bool Remove(KeyValuePair<T, K> item)
|
||||
{
|
||||
throw new ReadonlyOperationException("This instance is readonly.");
|
||||
}
|
||||
|
||||
public int Count
|
||||
{
|
||||
get { return _dictionaryImplementation.Count; }
|
||||
}
|
||||
|
||||
public bool IsReadOnly
|
||||
{
|
||||
get { return true; }
|
||||
}
|
||||
|
||||
public void Add(T key, K value)
|
||||
{
|
||||
throw new ReadonlyOperationException("This instance is readonly.");
|
||||
}
|
||||
|
||||
public bool ContainsKey(T key)
|
||||
{
|
||||
return _dictionaryImplementation.ContainsKey(key);
|
||||
}
|
||||
|
||||
public bool Remove(T key)
|
||||
{
|
||||
throw new ReadonlyOperationException("This instance is readonly.");
|
||||
}
|
||||
|
||||
public bool TryGetValue(T key, out K value)
|
||||
{
|
||||
return _dictionaryImplementation.TryGetValue(key, out value);
|
||||
}
|
||||
|
||||
public K this[T key]
|
||||
{
|
||||
get { return _dictionaryImplementation[key]; }
|
||||
set
|
||||
{
|
||||
throw new ReadonlyOperationException("This instance is readonly.");
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
public ICollection<T> Keys
|
||||
{
|
||||
get { return _dictionaryImplementation.Keys; }
|
||||
}
|
||||
|
||||
public ICollection<K> Values
|
||||
{
|
||||
get { return _dictionaryImplementation.Values; }
|
||||
}
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
public class ReadonlyOperationException : Exception
|
||||
{
|
||||
//
|
||||
// For guidelines regarding the creation of new exception types, see
|
||||
// http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpgenref/html/cpconerrorraisinghandlingguidelines.asp
|
||||
// and
|
||||
// http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dncscol/html/csharp07192001.asp
|
||||
//
|
||||
|
||||
public ReadonlyOperationException()
|
||||
{
|
||||
}
|
||||
|
||||
public ReadonlyOperationException(string message) : base(message)
|
||||
{
|
||||
}
|
||||
|
||||
public ReadonlyOperationException(string message, Exception inner) : base(message, inner)
|
||||
{
|
||||
}
|
||||
|
||||
protected ReadonlyOperationException(
|
||||
SerializationInfo info,
|
||||
StreamingContext context) : base(info, context)
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
66
modules/openapi-generator/src/main/resources/csharp-netcore-functions/RequestOptions.mustache
vendored
Normal file
66
modules/openapi-generator/src/main/resources/csharp-netcore-functions/RequestOptions.mustache
vendored
Normal file
@ -0,0 +1,66 @@
|
||||
{{>partial_header}}
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Net;
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// A container for generalized request inputs. This type allows consumers to extend the request functionality
|
||||
/// by abstracting away from the default (built-in) request framework (e.g. RestSharp).
|
||||
/// </summary>
|
||||
public class RequestOptions
|
||||
{
|
||||
/// <summary>
|
||||
/// Parameters to be bound to path parts of the Request's URL
|
||||
/// </summary>
|
||||
public Dictionary<string, string> PathParameters { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Query parameters to be applied to the request.
|
||||
/// Keys may have 1 or more values associated.
|
||||
/// </summary>
|
||||
public Multimap<string, string> QueryParameters { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Header parameters to be applied to to the request.
|
||||
/// Keys may have 1 or more values associated.
|
||||
/// </summary>
|
||||
public Multimap<string, string> HeaderParameters { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Form parameters to be sent along with the request.
|
||||
/// </summary>
|
||||
public Dictionary<string, string> FormParameters { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// File parameters to be sent along with the request.
|
||||
/// </summary>
|
||||
public Dictionary<string, Stream> FileParameters { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Cookies to be sent along with the request.
|
||||
/// </summary>
|
||||
public List<Cookie> Cookies { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Any data associated with a request body.
|
||||
/// </summary>
|
||||
public Object Data { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Constructs a new instance of <see cref="RequestOptions"/>
|
||||
/// </summary>
|
||||
public RequestOptions()
|
||||
{
|
||||
PathParameters = new Dictionary<string, string>();
|
||||
QueryParameters = new Multimap<string, string>();
|
||||
HeaderParameters = new Multimap<string, string>();
|
||||
FormParameters = new Dictionary<string, string>();
|
||||
FileParameters = new Dictionary<string, Stream>();
|
||||
Cookies = new List<Cookie>();
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,39 @@
|
||||
using Polly;
|
||||
{{#useRestSharp}}
|
||||
using RestSharp;
|
||||
{{/useRestSharp}}
|
||||
{{#useHttpClient}}
|
||||
using System.Net.Http;
|
||||
{{/useHttpClient}}
|
||||
|
||||
namespace {{packageName}}.Client
|
||||
{
|
||||
/// <summary>
|
||||
/// Configuration class to set the polly retry policies to be applied to the requests.
|
||||
/// </summary>
|
||||
public class RetryConfiguration
|
||||
{
|
||||
{{#useRestSharp}}
|
||||
/// <summary>
|
||||
/// Retry policy
|
||||
/// </summary>
|
||||
public static Policy<IRestResponse> RetryPolicy { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Async retry policy
|
||||
/// </summary>
|
||||
public static AsyncPolicy<IRestResponse> AsyncRetryPolicy { get; set; }
|
||||
{{/useRestSharp}}
|
||||
{{#useHttpClient}}
|
||||
/// <summary>
|
||||
/// Retry policy
|
||||
/// </summary>
|
||||
public static Policy<HttpResponseMessage> RetryPolicy { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Async retry policy
|
||||
/// </summary>
|
||||
public static AsyncPolicy<HttpResponseMessage> AsyncRetryPolicy { get; set; }
|
||||
{{/useHttpClient}}
|
||||
}
|
||||
}
|
27
modules/openapi-generator/src/main/resources/csharp-netcore-functions/Solution.mustache
vendored
Normal file
27
modules/openapi-generator/src/main/resources/csharp-netcore-functions/Solution.mustache
vendored
Normal file
@ -0,0 +1,27 @@
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio {{^netStandard}}2012{{/netStandard}}{{#netStandard}}14{{/netStandard}}
|
||||
VisualStudioVersion = {{^netStandard}}12.0.0.0{{/netStandard}}{{#netStandard}}14.0.25420.1{{/netStandard}}
|
||||
MinimumVisualStudioVersion = {{^netStandard}}10.0.0.1{{/netStandard}}{{#netStandard}}10.0.40219.1{{/netStandard}}
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "{{packageName}}", "src\{{packageName}}\{{packageName}}.csproj", "{{packageGuid}}"
|
||||
EndProject
|
||||
{{^excludeTests}}Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "{{testPackageName}}", "src\{{testPackageName}}\{{testPackageName}}.csproj", "{19F1DEBC-DE5E-4517-8062-F000CD499087}"
|
||||
EndProject
|
||||
{{/excludeTests}}Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
Release|Any CPU = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{{packageGuid}}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{{packageGuid}}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{{packageGuid}}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{{packageGuid}}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
EndGlobal
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user