Compare commits

..

18 Commits

Author SHA1 Message Date
Jim Schubert
9563e8e3b6 [docs] Creating a new generator 2019-01-09 12:09:14 -05:00
Jim Schubert
cddb722b30 Copy current contributing/code of conduct to website 2019-01-06 23:11:53 -05:00
Jim Schubert
3ed68a0515 [docs] Migrate FAQ, release summary from wiki
FAQ has been split into multiple smaller documents to better categorize
and allow users to find what they're looking for (in docs folder or in
new website).

Release summary information (versioning strategy and cadence) has been
migrated from the Wiki and clarified a bit.

Also adds copy button for all code snippets in website.
2019-01-06 22:45:32 -05:00
Jim Schubert
009e2f3ea7 travis configuration, and baseUrl mods to image URLs 2019-01-03 23:39:39 -05:00
Jim Schubert
148041812e Move users to yaml file for easy edit. 2019-01-03 22:17:58 -05:00
Jim Schubert
d173d778cb Cleanup templating page(s). 2019-01-03 21:51:02 -05:00
Jim Schubert
e335cfcf11 Add vendor extension docs 2019-01-03 12:13:46 -05:00
Jim Schubert
1978db5ab7 Merge branch 'master' into docusaurus
* master: (26 commits)
  Delete unused method (#1744)
  Use JsonNullable wrapper on nullable/x-nullable fields (#1762)
  Add an option to use reflection in equals, hashCode (Java client) (#1767)
  [Slim] Encode path to support non-latin characters (#1687)
  [elm] Add support for sending headers (#1704)
  Add test case for InlineModelResolver: inline array response (#1778)
  fix group parameter logic (#1779)
  Add test case for InlineModelResolver: inline array request body (#1777)
  Add test case for InlineModelResolver: inline array schema (#1772)
  Fix type inference error (#1773)
  skip default value for contaier in spring (#1725)
  [Slim] Add PHP CodeSniffer config template (#1764)
  Use CompareNetObject for object comparison in C# client (refactor) (#1765)
  Add test case for InlineModelResolver (#1771)
  Add online gen tests (#1759)
  Resolve inline models before preprocess (#1761)
  better handling of allOf (composition) (#1757)
  Fix UUID support (#1746)
  Use appInfo.version for podspec (#1760)
  [Swift 4] Add `createURLRequest` method (#1727)
  ...
2018-12-30 21:33:14 -05:00
Jim Schubert
e57f8f02fd Updating templating and customization docs 2018-12-30 21:14:07 -05:00
Jim Schubert
78faa74bd7 Include new custom template documentation 2018-12-30 16:22:42 -05:00
Jim Schubert
185313e08e Improve "Getting Started" type docs 2018-12-30 00:38:05 -05:00
Jim Schubert
193b09693c Include NPM try it out section 2018-12-29 10:03:47 -05:00
Jim Schubert
c4de50f845 Remove feature callout until it is completed 2018-12-29 09:41:19 -05:00
Jim Schubert
c69af94397 Add Font Awesome attribution footer 2018-12-29 09:40:38 -05:00
Jim Schubert
37ce585e27 Include generator indexes in ensure-up-to-date (docusaurus site and /generators/README) 2018-12-29 09:01:39 -05:00
Jim Schubert
fb49fa7c8e Change pinned users to represent global presence rather than alphabetical order pinning 2018-12-29 08:58:02 -05:00
Jim Schubert
c81c9b4ad2 Remove error about default local being used by String.format 2018-12-28 17:11:28 -05:00
Jim Schubert
6aeb534242 Iniital docusaurus based site 2018-12-28 16:53:24 -05:00
2785 changed files with 21248 additions and 166783 deletions

View File

@@ -7,15 +7,6 @@ assignees: ''
---
#### Bug Report Checklist
- [ ] Have you provided a full/minimal spec to reproduce the issue?
- [ ] Have you validated the input using an OpenAPI validator ([example](https://apidevtools.org/swagger-parser/online/))?
- [ ] What's the version of OpenAPI Generator used?
- [ ] Have you search for related issues/PRs?
- [ ] What's the actual output vs expected output?
- [ ] [Optional] Bounty to sponsor the fix ([example](https://www.bountysource.com/issues/66123212-javascript-client-produces-a-wrong-object-for-a-string-enum-type-that-is-used-with-ref))
<!--
Please follow the issue template below for bug reports.
Also please indicate in the issue title which language/library is concerned. Eg: [BUG][JAVA] Bug generating foo with bar

2
.gitignore vendored
View File

@@ -27,7 +27,6 @@ packages/
.packages
.vagrant/
.vscode/
**/.vs
.settings
@@ -129,6 +128,7 @@ samples/client/petstore/swift3/**/SwaggerClientTests/Podfile.lock
# C#
*.csproj.user
samples/client/petstore/csharp/SwaggerClient/IO.Swagger.userprefs
samples/client/petstore/csharp/SwaggerClientTest/.vs
samples/client/petstore/csharp/SwaggerClientTest/obj
samples/client/petstore/csharp/SwaggerClientTest/bin
samples/client/petstore/csharp/SwaggerClientTest/packages

View File

@@ -15,7 +15,7 @@ elif [ "$NODE_INDEX" = "2" ]; then
java -version
#export GO_POST_PROCESS_FILE="/usr/local/bin/gofmt -w"
# not formatting the code as different go versions may format the code a bit different
# ./bin/utils/ensure-up-to-date
./bin/utils/ensure-up-to-date
else
echo "Running node $NODE_INDEX to test 'samples.circleci.jdk7' defined in pom.xml ..."
sudo update-java-alternatives -s java-1.7.0-openjdk-amd64

View File

@@ -157,11 +157,11 @@ public class ApiClientTest {
public void testGetAndSetConnectTimeout() {
// connect timeout defaults to 10 seconds
assertEquals(10000, apiClient.getConnectTimeout());
assertEquals(10000, apiClient.getHttpClient().connectTimeoutMillis());
assertEquals(10000, apiClient.getHttpClient().getConnectTimeout());
apiClient.setConnectTimeout(0);
assertEquals(0, apiClient.getConnectTimeout());
assertEquals(0, apiClient.getHttpClient().connectTimeoutMillis());
assertEquals(0, apiClient.getHttpClient().getConnectTimeout());
apiClient.setConnectTimeout(10000);
}
@@ -170,11 +170,11 @@ public class ApiClientTest {
public void testGetAndSetReadTimeout() {
// read timeout defaults to 10 seconds
assertEquals(10000, apiClient.getReadTimeout());
assertEquals(10000, apiClient.getHttpClient().readTimeoutMillis());
assertEquals(10000, apiClient.getHttpClient().getReadTimeout());
apiClient.setReadTimeout(0);
assertEquals(0, apiClient.getReadTimeout());
assertEquals(0, apiClient.getHttpClient().readTimeoutMillis());
assertEquals(0, apiClient.getHttpClient().getReadTimeout());
apiClient.setReadTimeout(10000);
}
@@ -183,11 +183,11 @@ public class ApiClientTest {
public void testGetAndSetWriteTimeout() {
// write timeout defaults to 10 seconds
assertEquals(10000, apiClient.getWriteTimeout());
assertEquals(10000, apiClient.getHttpClient().writeTimeoutMillis());
assertEquals(10000, apiClient.getHttpClient().getWriteTimeout());
apiClient.setWriteTimeout(0);
assertEquals(0, apiClient.getWriteTimeout());
assertEquals(0, apiClient.getHttpClient().writeTimeoutMillis());
assertEquals(0, apiClient.getHttpClient().getWriteTimeout());
apiClient.setWriteTimeout(10000);
}

View File

@@ -1,358 +0,0 @@
/*
* OpenAPI Petstore
* This spec is mainly for testing Petstore server and contains fake endpoints, models. Please do not use this for any other purpose. Special characters: \" \\
*
* OpenAPI spec version: 1.0.0
*
*
* NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
* https://openapi-generator.tech
* Do not edit the class manually.
*/
package org.openapitools.client.api;
import org.openapitools.client.ApiException;
import org.openapitools.client.model.Pet;
import org.openapitools.client.auth.*;
import org.openapitools.client.model.*;
import org.openapitools.client.*;
import java.lang.reflect.Type;
import java.util.Arrays;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import org.junit.*;
import static org.junit.Assert.*;
/**
* API tests for PetApi
*/
public class PetApiTest {
private PetApi api = new PetApi();
@Before
public void setup() {
// setup authentication
ApiKeyAuth apiKeyAuth = (ApiKeyAuth) api.getApiClient().getAuthentication("api_key");
apiKeyAuth.setApiKey("special-key");
}
@Test
public void testApiClient() {
// the default api client is used
assertEquals(Configuration.getDefaultApiClient(), api.getApiClient());
assertNotNull(api.getApiClient());
assertEquals("http://petstore.swagger.io:80/v2", api.getApiClient().getBasePath());
assertFalse(api.getApiClient().isDebugging());
ApiClient oldClient = api.getApiClient();
ApiClient newClient = new ApiClient();
newClient.setBasePath("http://example.com");
newClient.setDebugging(true);
// set api client via constructor
api = new PetApi(newClient);
assertNotNull(api.getApiClient());
assertEquals("http://example.com", api.getApiClient().getBasePath());
assertTrue(api.getApiClient().isDebugging());
// set api client via setter method
api.setApiClient(oldClient);
assertNotNull(api.getApiClient());
assertEquals("http://petstore.swagger.io:80/v2", api.getApiClient().getBasePath());
assertFalse(api.getApiClient().isDebugging());
}
@Test
public void testCreateAndGetPet() throws Exception {
Pet pet = createPet();
api.addPet(pet);
Pet fetched = api.getPetById(pet.getId());
assertNotNull(fetched);
assertEquals(pet.getId(), fetched.getId());
assertNotNull(fetched.getCategory());
assertEquals(fetched.getCategory().getName(), pet.getCategory().getName());
}
@Test
public void testCreateAndGetPetWithHttpInfo() throws Exception {
Pet pet = createPet();
api.addPetWithHttpInfo(pet);
ApiResponse<Pet> resp = api.getPetByIdWithHttpInfo(pet.getId());
assertEquals(200, resp.getStatusCode());
assertEquals("application/json", resp.getHeaders().get("Content-Type").get(0));
Pet fetched = resp.getData();
assertNotNull(fetched);
assertEquals(pet.getId(), fetched.getId());
assertNotNull(fetched.getCategory());
assertEquals(fetched.getCategory().getName(), pet.getCategory().getName());
}
@Test
public void testCreateAndGetPetAsync() throws Exception {
Pet pet = createPet();
api.addPet(pet);
// to store returned Pet or error message/exception
final Map<String, Object> result = new HashMap<String, Object>();
api.getPetByIdAsync(pet.getId(), new ApiCallback<Pet>() {
@Override
public void onFailure(ApiException e, int statusCode, Map<String, List<String>> responseHeaders) {
result.put("error", e.getMessage());
}
@Override
public void onSuccess(Pet pet, int statusCode, Map<String, List<String>> responseHeaders) {
result.put("pet", pet);
}
@Override
public void onUploadProgress(long bytesWritten, long contentLength, boolean done) {
//empty
}
@Override
public void onDownloadProgress(long bytesRead, long contentLength, boolean done) {
//empty
}
});
// the API call should be executed asynchronously, so result should be empty at the moment
assertTrue(result.isEmpty());
// wait for the asynchronous call to finish (at most 10 seconds)
final int maxTry = 10;
int tryCount = 1;
Pet fetched = null;
do {
if (tryCount > maxTry) fail("have not got result of getPetByIdAsync after 10 seconds");
Thread.sleep(1000);
tryCount += 1;
if (result.get("error") != null) fail((String) result.get("error"));
if (result.get("pet") != null) {
fetched = (Pet) result.get("pet");
break;
}
} while (result.isEmpty());
assertNotNull(fetched);
assertEquals(pet.getId(), fetched.getId());
assertNotNull(fetched.getCategory());
assertEquals(fetched.getCategory().getName(), pet.getCategory().getName());
// test getting a nonexistent pet
result.clear();
api.getPetByIdAsync(-10000L, new ApiCallback<Pet>() {
@Override
public void onFailure(ApiException e, int statusCode, Map<String, List<String>> responseHeaders) {
result.put("exception", e);
}
@Override
public void onSuccess(Pet pet, int statusCode, Map<String, List<String>> responseHeaders) {
result.put("pet", pet);
}
@Override
public void onUploadProgress(long bytesWritten, long contentLength, boolean done) {
//empty
}
@Override
public void onDownloadProgress(long bytesRead, long contentLength, boolean done) {
//empty
}
});
// wait for the asynchronous call to finish (at most 10 seconds)
tryCount = 1;
ApiException exception = null;
do {
if (tryCount > maxTry) fail("have not got result of getPetByIdAsync after 10 seconds");
Thread.sleep(1000);
tryCount += 1;
if (result.get("pet") != null) fail("expected an error");
if (result.get("exception") != null) {
exception = (ApiException) result.get("exception");
break;
}
} while (result.isEmpty());
assertNotNull(exception);
assertEquals(404, exception.getCode());
assertEquals("Not Found", exception.getMessage());
assertEquals("application/json", exception.getResponseHeaders().get("Content-Type").get(0));
}
@Test
public void testUpdatePet() throws Exception {
Pet pet = createPet();
pet.setName("programmer");
api.updatePet(pet);
Pet fetched = api.getPetById(pet.getId());
assertNotNull(fetched);
assertEquals(pet.getId(), fetched.getId());
assertNotNull(fetched.getCategory());
assertEquals(fetched.getCategory().getName(), pet.getCategory().getName());
}
@Test
public void testFindPetsByStatus() throws Exception {
Pet pet = createPet();
pet.setName("programmer");
pet.setStatus(Pet.StatusEnum.PENDING);
api.updatePet(pet);
List<Pet> pets = api.findPetsByStatus(Arrays.asList("pending"));
assertNotNull(pets);
boolean found = false;
for (Pet fetched : pets) {
if (fetched.getId().equals(pet.getId())) {
found = true;
break;
}
}
assertTrue(found);
api.deletePet(pet.getId(), null);
}
@Test
public void testFindPetsByTags() throws Exception {
Pet pet = createPet();
pet.setName("monster");
pet.setStatus(Pet.StatusEnum.AVAILABLE);
List<Tag> tags = new ArrayList<Tag>();
Tag tag1 = new Tag();
tag1.setName("friendly");
tags.add(tag1);
pet.setTags(tags);
api.updatePet(pet);
List<Pet> pets = api.findPetsByTags(Arrays.asList("friendly"));
assertNotNull(pets);
boolean found = false;
for (Pet fetched : pets) {
if (fetched.getId().equals(pet.getId())) {
found = true;
break;
}
}
assertTrue(found);
api.deletePet(pet.getId(), null);
}
@Test
public void testUpdatePetWithForm() throws Exception {
Pet pet = createPet();
pet.setName("frank");
api.addPet(pet);
Pet fetched = api.getPetById(pet.getId());
api.updatePetWithForm(fetched.getId(), "furt", null);
Pet updated = api.getPetById(fetched.getId());
assertEquals(updated.getName(), "furt");
}
@Test
public void testDeletePet() throws Exception {
Pet pet = createPet();
api.addPet(pet);
Pet fetched = api.getPetById(pet.getId());
api.deletePet(fetched.getId(), null);
try {
fetched = api.getPetById(fetched.getId());
fail("expected an error");
} catch (ApiException e) {
assertEquals(404, e.getCode());
}
}
@Test
public void testUploadFile() throws Exception {
Pet pet = createPet();
api.addPet(pet);
File file = new File("hello.txt");
BufferedWriter writer = new BufferedWriter(new FileWriter(file));
writer.write("Hello world!");
writer.close();
api.uploadFile(pet.getId(), "a test file", new File(file.getAbsolutePath()));
}
@Test
public void testEqualsAndHashCode() {
Pet pet1 = new Pet();
Pet pet2 = new Pet();
assertTrue(pet1.equals(pet2));
assertTrue(pet2.equals(pet1));
assertTrue(pet1.hashCode() == pet2.hashCode());
assertTrue(pet1.equals(pet1));
assertTrue(pet1.hashCode() == pet1.hashCode());
pet2.setName("really-happy");
pet2.setPhotoUrls(Arrays.asList("http://foo.bar.com/1", "http://foo.bar.com/2"));
assertFalse(pet1.equals(pet2));
assertFalse(pet2.equals(pet1));
assertFalse(pet1.hashCode() == (pet2.hashCode()));
assertTrue(pet2.equals(pet2));
assertTrue(pet2.hashCode() == pet2.hashCode());
pet1.setName("really-happy");
pet1.setPhotoUrls(Arrays.asList("http://foo.bar.com/1", "http://foo.bar.com/2"));
assertTrue(pet1.equals(pet2));
assertTrue(pet2.equals(pet1));
assertTrue(pet1.hashCode() == pet2.hashCode());
assertTrue(pet1.equals(pet1));
assertTrue(pet1.hashCode() == pet1.hashCode());
}
private Pet createPet() {
Pet pet = new Pet();
pet.setId(1234567L);
pet.setName("gorilla");
Category category = new Category();
category.setName("really-happy");
pet.setCategory(category);
pet.setStatus(Pet.StatusEnum.AVAILABLE);
List<String> photos = Arrays.asList("http://foo.bar.com/1", "http://foo.bar.com/2");
pet.setPhotoUrls(photos);
return pet;
}
private String serializeJson(Object o, ApiClient apiClient) {
return apiClient.getJSON().serialize(o);
}
private <T> T deserializeJson(String json, Type type, ApiClient apiClient) {
return (T) apiClient.getJSON().deserialize(json, type);
}
}

View File

@@ -38,7 +38,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), **C++** (cpprest, Qt5, Tizen), **Clojure**, **Dart (1.x, 2.x)**, **Elixir**, **Elm**, **Eiffel**, **Erlang**, **Go**, **Groovy**, **Haskell** (http-client, Servant), **Java** (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), **Kotlin**, **Lua**, **Node.js** (ES5, ES6, AngularJS with Google Closure Compiler annotations, Flow types) **Objective-C**, **Perl**, **PHP**, **PowerShell**, **Python**, **R**, **Ruby**, **Rust** (rust, rust-server), **Scala** (akka, http4s, scalaz, swagger-async-httpclient), **Swift** (2.x, 3.x, 4.x), **Typescript** (AngularJS, Angular (2.x - 7.x), Aurelia, Axios, Fetch, Inversify, jQuery, Node, Rxjs)
**API clients** | **ActionScript**, **Ada**, **Apex**, **Bash**, **C**, **C#** (.net 2.0, 3.5 or later), **C++** (cpprest, Qt5, Tizen), **Clojure**, **Dart (1.x, 2.x)**, **Elixir**, **Elm**, **Eiffel**, **Erlang**, **Go**, **Groovy**, **Haskell** (http-client, Servant), **Java** (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), **Kotlin**, **Lua**, **Node.js** (ES5, ES6, AngularJS with Google Closure Compiler annotations, Flow types) **Objective-C**, **Perl**, **PHP**, **PowerShell**, **Python**, **R**, **Ruby**, **Rust** (rust, rust-server), **Scala** (akka, http4s, scalaz, swagger-async-httpclient), **Swift** (2.x, 3.x, 4.x), **Typescript** (AngularJS, Angular (2.x - 7.x), Aurelia, Axios, Fetch, Inversify, jQuery, Node)
**Server stubs** | **Ada**, **C#** (ASP.NET Core, NancyFx), **C++** (Pistache, Restbed), **Erlang**, **Go** (net/http, Gin), **Haskell** (Servant), **Java** (MSF4J, Spring, Undertow, JAX-RS: CDI, CXF, Inflector, RestEasy, Play Framework, [PKMST](https://github.com/ProKarma-Inc/pkmst-getting-started-examples)), **Kotlin** (Spring Boot), **PHP** (Laravel, Lumen, Slim, Silex, [Symfony](https://symfony.com/), [Zend Expressive](https://github.com/zendframework/zend-expressive)), **Python** (Flask), **NodeJS**, **Ruby** (Sinatra, Rails5), **Rust** (rust-server), **Scala** ([Finch](https://github.com/finagle/finch), [Lagom](https://github.com/lagom/lagom), Scalatra)
**API documentation generators** | **HTML**, **Confluence Wiki**
**Configuration files** | [**Apache2**](https://httpd.apache.org/)
@@ -374,7 +374,7 @@ java -jar modules/openapi-generator-cli/target/openapi-generator-cli.jar generat
```
(if you're on Windows, replace the last command with `java -jar modules\openapi-generator-cli\target\openapi-generator-cli.jar generate -i https://raw.githubusercontent.com/openapitools/openapi-generator/master/modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g php -o c:\temp\php_api_client`)
You can also download the JAR (latest release) directly from [maven.org](http://central.maven.org/maven2/org/openapitools/openapi-generator-cli/3.3.4/openapi-generator-cli-3.3.4.jar)
You can also download the JAR (latest release) directly from [maven.org](http://central.maven.org/maven2/org/openapitools/openapi-generator-cli/3.0.0/openapi-generator-cli-3.0.0.jar)
To get a list of **general** options available, please run `java -jar modules/openapi-generator-cli/target/openapi-generator-cli.jar help generate`
@@ -485,7 +485,7 @@ The server is sponsored by [Linode](https://www.linode.com/) [![Linode Logo](htt
(These services are beta and do not have any guarantee on service level)
Please refer to [online.md](docs/online.md) on how to run and use the `openapi-generator-online` - a web service for `openapi-generator`.
Please refer to [online-openapi-generator.md](docs/online-openapi-generator.md) on how to run and use the `openapi-generator-online` - a web service for `openapi-generator`.
### [3.4 - License information on Generated Code](#table-of-contents)
@@ -499,23 +499,16 @@ When code is generated from this project, it shall be considered **AS IS** and o
## [4 - Companies/Projects using OpenAPI Generator](#table-of-contents)
Here are some companies/projects (alphabetical order) using OpenAPI Generator in production. To add your company/project to the list, please visit [README.md](README.md) and click on the icon to edit the page.
- [Adaptant Solutions AG](https://www.adaptant.io/)
- [Angular.Schule](https://angular.schule/)
- [ASKUL](https://www.askul.co.jp)
- [b<>com](https://b-com.com/en)
- [BIMData.io](https://bimdata.io)
- [Bithost GmbH](https://www.bithost.ch)
- [Boxever](https://www.boxever.com/)
- [codecentric AG](https://www.codecentric.de/)
- [Cupix](https://www.cupix.com/)
- [FormAPI](https://formapi.io/)
- [GenFlow](https://github.com/RepreZen/GenFlow)
- [GMO Pepabo](https://pepabo.com/en/)
- [JustStar](https://www.juststarinfo.com)
- [Klarna](https://www.klarna.com/)
- [Metaswitch](https://www.metaswitch.com/)
- [Myworkout](https://myworkout.com)
- [Prometheus/Alertmanager](https://github.com/prometheus/alertmanager)
- [Raiffeisen Schweiz Genossenschaft](https://www.raiffeisen.ch)
- [RepreZen API Studio](https://www.reprezen.com/swagger-openapi-code-generation-api-first-microservices-enterprise-development)
- [REST United](https://restunited.com)
@@ -524,7 +517,6 @@ Here are some companies/projects (alphabetical order) using OpenAPI Generator in
- [Telstra](https://dev.telstra.com)
- [TUI InfoTec GmbH](http://www.tui-infotec.com/)
- [unblu inc.](https://www.unblu.com/)
- [Xero](https://www.xero.com/)
- [Zalando](https://www.zalando.com)
## [5 - Presentations/Videos/Tutorials/Books](#table-of-contents)
@@ -537,13 +529,9 @@ Here are some companies/projects (alphabetical order) using OpenAPI Generator in
- 2018/06/27 - [Lessons Learned from Leading an Open-Source Project Supporting 30+ Programming Languages](https://speakerdeck.com/wing328/lessons-learned-from-leading-an-open-source-project-supporting-30-plus-programming-languages) - [William Cheng](https://github.com/wing328) at [LinuxCon + ContainerCon + CloudOpen China 2018](http://bit.ly/2waDKKX)
- 2018/07/19 - [OpenAPI Generator Contribution Quickstart - RingCentral Go SDK](https://medium.com/ringcentral-developers/openapi-generator-for-go-contribution-quickstart-8cc72bf37b53) by [John Wang](https://github.com/grokify)
- 2018/08/22 - [OpenAPI Generatorのプロジェクト構成などのメモ](https://yinm.info/20180822/) by [Yusuke Iinuma](https://github.com/yinm)
- 2018/09/12 - [RepreZen and OpenAPI 3.0: Now is the Time](https://www.reprezen.com/blog/reprezen-openapi-3.0-upgrade-now-is-the-time) by [Miles Daffin](https://www.reprezen.com/blog/author/miles-daffin)
- 2018/10/31 - [A node package wrapper for openapi-generator](https://github.com/HarmoWatch/openapi-generator-cli)
- 2018/11/03 - [OpenAPI Generator + golang + Flutter でアプリ開発](http://ryuichi111std.hatenablog.com/entry/2018/11/03/214005) by [Ryuichi Daigo](https://github.com/ryuichi111)
- 2018/11/19 - [OpenAPIs are everywhere](https://youtu.be/-lDot4Yn7Dg) by [Jeremie Bresson (Unblu)](https://github.com/jmini) at [EclipseCon Europe 2018](https://www.eclipsecon.org/europe2018)
- 2018/12/09 - [openapi-generator をカスタマイズする方法](https://qiita.com/watiko/items/0961287c02eac9211572) by [@watiko](https://qiita.com/watiko)
- 2019/01/03 - [Calling a Swagger service from Apex using openapi-generator](https://lekkimworld.com/2019/01/03/calling-a-swagger-service-from-apex-using-openapi-generator/) by [Mikkel Flindt Heisterberg](https://lekkimworld.com)
- 2019/01/13 - [OpenAPI GeneratorでRESTful APIの定義書から色々自動生成する](https://ky-yk-d.hatenablog.com/entry/2019/01/13/234108) by [@ky_yk_d](https://twitter.com/ky_yk_d)
## [6 - About Us](#table-of-contents)
@@ -552,15 +540,14 @@ Here are some companies/projects (alphabetical order) using OpenAPI Generator in
OpenAPI Generator core team members are contributors who have been making significant contributions (review issues, fix bugs, make enhancements, etc) to the project on a regular basis.
#### Core Team Members
* [@wing328](https://github.com/wing328) (2015/07) [:heart:](https://www.patreon.com/wing328)
* [@jimschubert](https://github.com/jimschubert) (2016/05) [:heart:](https://www.patreon.com/jimschubert)
* [@wing328](https://github.com/wing328) (2015/07)
* [@jimschubert](https://github.com/jimschubert) (2016/05)
* [@cbornet](https://github.com/cbornet) (2016/05)
* [@ackintosh](https://github.com/ackintosh) (2018/02) [:heart:](https://www.patreon.com/ackintosh/overview)
* [@jaz-ah](https://github.com/jaz-ah) (2016/05)
* [@ackintosh](https://github.com/ackintosh) (2018/02)
* [@JFCote](https://github.com/JFCote) (2018/03)
* [@jmini](https://github.com/jmini) (2018/04)
:heart: = Link to support the contributor directly
#### Template Creator
Here is a list of template creators:
* API Clients:
@@ -568,23 +555,23 @@ Here is a list of template creators:
* Akka-Scala: @cchafer
* Apex: @asnelling
* Bash: @bkryza
* C: @PowerOfCreation @zhemant [:heart:](https://www.patreon.com/zhemant)
* C: @PowerOfCreation @zhemant
* C++ REST: @Danielku15
* C# (.NET 2.0): @who
* C# (.NET Standard 1.3 ): @Gronsak
* C# (.NET 4.5 refactored): @jimschubert [:heart:](https://www.patreon.com/jimschubert)
* C# (.NET 4.5 refactored): @jimschubert
* Clojure: @xhh
* Dart: @yissachar
* Dart (refactor): @joernahrens
* Dart 2: @swipesight
* Dart (Jaguar): @jaumard
* Elixir: @niku
* Elm: @eriktim
* Elm: @trenneman
* Eiffel: @jvelilla
* Erlang: @tsloughter
* Erlang (PropEr): @jfacorro @robertoaloi
* Groovy: @victorgit
* Go: @wing328 [:heart:](https://www.patreon.com/wing328)
* Go: @wing328
* Go (rewritten in 2.3.0): @antihax
* Haskell (http-client): @jonschoning
* Java (Feign): @davidkiss
@@ -602,9 +589,9 @@ Here is a list of template creators:
* Javascript (Closure-annotated Angular) @achew22
* Javascript (Flow types) @jaypea
* JMeter: @davidkiss
* Kotlin: @jimschubert [:heart:](https://www.patreon.com/jimschubert)
* Kotlin: @jimschubert
* Lua: @daurnimator
* Perl: @wing328 [:heart:](https://www.patreon.com/wing328)
* Perl: @wing328
* PHP (Guzzle): @baartosz
* PowerShell: @beatcracker
* R: @ramnov
@@ -622,10 +609,9 @@ Here is a list of template creators:
* TypeScript (Fetch): @leonyu
* TypeScript (jQuery): @bherila
* TypeScript (Node): @mhardorf
* TypeScript (Rxjs): @denyo
* Server Stubs
* Ada: @stcarrez
* C# ASP.NET5: @jimschubert [:heart:](https://www.patreon.com/jimschubert)
* C# ASP.NET5: @jimschubert
* C# NancyFX: @mstefaniuk
* C++ (Qt5 QHttpEngine): @etherealjoy
* C++ Pistache: @sebymiano
@@ -644,17 +630,16 @@ Here is a list of template creators:
* JAX-RS CXF: @hiveship
* JAX-RS CXF (CDI): @nickcmaynard
* JAX-RS RestEasy (JBoss EAP): @jfiala
* Kotlin: @jimschubert [:heart:](https://www.patreon.com/jimschubert)
* Kotlin: @jimschubert
* Kotlin (Spring Boot): @dr4ke616
* PHP Laravel: @renepardon
* PHP Lumen: @abcsun
* PHP Slim: @jfastnacht
* PHP Symfony: @ksm2
* PHP Zend Expressive (with Path Handler): @Articus
* Python AIOHTTP: @Jyhess
* Ruby on Rails 5: @zlx
* Rust (rust-server): @metaswitch
* Scala Finch: @jimschubert [:heart:](https://www.patreon.com/jimschubert)
* Scala Finch: @jimschubert
* Scala Lagom: @gmkumar2005
* Documentation
* HTML Doc 2: @jhitchcock
@@ -662,11 +647,9 @@ Here is a list of template creators:
* Configuration
* Apache2: @stkrwork
* Schema
* GraphQL: @wing328 [:heart:](https://www.patreon.com/wing328)
* GraphQL: @wing328
* MySQL: @ybelenko
:heart: = Link to support the contributor directly
#### How to join the core team
Here are the requirements to become a core team member:
@@ -705,35 +688,33 @@ If you want to join the committee, please kindly apply by sending an email to te
| Bash | @frol (2017/07) @bkryza (2017/08) @kenjones-cisco (2017/09) |
| C | @zhemant (2018/11) |
| C++ | @ravinikam (2017/07) @stkrwork (2017/07) @fvarose (2017/11) @etherealjoy (2018/02) @martindelille (2018/03) |
| C# | @mandrean (2017/08), @jimschubert (2017/09) [:heart:](https://www.patreon.com/jimschubert) |
| C# | @mandrean (2017/08) @jimschubert (2017/09) |
| Clojure | |
| Dart | @ircecho (2017/07) @swipesight (2018/09) @jaumard (2018/09) |
| Eiffel | @jvelilla (2017/09) |
| Elixir | @mrmstn (2018/12) |
| Elm | @eriktim (2018/09) |
| Elixir | |
| Elm | @trenneman (2018/09) |
| Erlang | @tsloughter (2017/11) @jfacorro (2018/10) @robertoaloi (2018/10) |
| Go | @antihax (2017/11) @bvwells (2017/12) @grokify (2018/07) @kemokemo (2018/09 |
| GraphQL | @renepardon (2018/12) |
| Groovy | |
| Haskell | |
| Java | @bbdouglas (2017/07) @JFCote (2017/08) @sreeshas (2017/08) @jfiala (2017/08) @lukoyanov (2017/09) @cbornet (2017/09) @jeff9finger (2018/01) |
| Kotlin | @jimschubert (2017/09) [:heart:](https://www.patreon.com/jimschubert), @dr4ke616 (2018/08) |
| Kotlin | @jimschubert (2017/09) @dr4ke616 (2018/08) |
| Lua | @daurnimator (2017/08) |
| NodeJS/Javascript | @CodeNinjai (2017/07) @frol (2017/07) @cliffano (2017/07) |
| ObjC | |
| Perl | @wing328 (2017/07) [:heart:](https://www.patreon.com/wing328) |
| PHP | @jebentier (2017/07), @dkarlovi (2017/07), @mandrean (2017/08), @jfastnacht (2017/09), @ackintosh (2017/09) [:heart:](https://www.patreon.com/ackintosh/overview), @ybelenko (2018/07), @renepardon (2018/12) |
| Perl | @wing328 (2017/07) |
| PHP | @jebentier (2017/07) @dkarlovi (2017/07) @mandrean (2017/08) @jfastnacht (2017/09) @ackintosh (2017/09) @ybelenko (2018/07) @renepardon (2018/12) |
| PowerShell | |
| Python | @taxpon (2017/07) @frol (2017/07) @mbohlool (2017/07) @cbornet (2017/09) @kenjones-cisco (2017/11) @tomplus (2018/10) @Jyhess (2019/01) |
| Python | @taxpon (2017/07) @frol (2017/07) @mbohlool (2017/07) @cbornet (2017/09) @kenjones-cisco (2017/11) @tomplus (2018/10) |
| R | |
| Ruby | @cliffano (2017/07) @zlx (2017/09) |
| Rust | @frol (2017/07) @farcaller (2017/08) @bjgill (2017/12) |
| Scala | @clasnake (2017/07), @jimschubert (2017/09) [:heart:](https://www.patreon.com/jimschubert), @shijinkui (2018/01), @ramzimaalej (2018/03) |
| Scala | @clasnake (2017/07) @jimschubert (2017/09) @shijinkui (2018/01) @ramzimaalej (2018/03) |
| Swift | @jgavris (2017/07) @ehyche (2017/08) @Edubits (2017/09) @jaz-ah (2017/09) @d-date (2018/03) |
| TypeScript | @TiFu (2017/07) @taxpon (2017/07) @sebastianhaas (2017/07) @kenisteward (2017/07) @Vrolijkx (2017/09) @macjohnny (2018/01) @nicokoenig (2018/09) @topce (2018/10) |
:heart: = Link to support the contributor directly
### [6.3 - History of OpenAPI Generator](#table-of-contents)
OpenAPI Generator is a fork of [Swagger Codegen](https://github.com/swagger-api/swagger-codegen). In view of the issues with the Swagger Codegen 3.0.0 (beta) release and the disagreement on the project's direction, more than 40 top contributors and template creators of Swagger Codegen decided to fork Swagger Codegen and maintain a community-driven version called "OpenAPI Generator". Please refer to the [Q&A](docs/qna.md) for more information.
@@ -751,7 +732,7 @@ OpenAPI Generator is a fork of [Swagger Codegen](https://github.com/swagger-api/
- [Daiki Matsudate](https://github.com/d-date)
- [Daniel](https://github.com/Danielku15)
- [Emiliano Bonassi](https://github.com/emilianobonassi)
- [Erik Timmers](https://github.com/eriktim)
- [Erik Timmers](https://github.com/trenneman)
- [Esteban Marin](https://github.com/macjohnny)
- [Gustavo Paz](https://github.com/gustavoapaz)
- [Javier Velilla](https://github.com/jvelilla)
@@ -781,7 +762,7 @@ OpenAPI Generator is a fork of [Swagger Codegen](https://github.com/swagger-api/
- [Vlad Frolov](https://github.com/frol)
- [Vladimir Pouzanov](https://github.com/farcaller)
- [William Cheng](https://github.com/wing328)
- [Xin Meng](https://github.com/xmeng1) [:heart:](https://www.patreon.com/user/overview?u=16435385)
- [Xin Meng](https://github.com/xmeng1)
- [Xu Hui Hui](https://github.com/xhh)
- [antihax](https://github.com/antihax)
- [beatcracker](https://github.com/beatcracker)
@@ -790,7 +771,6 @@ OpenAPI Generator is a fork of [Swagger Codegen](https://github.com/swagger-api/
- [jfiala](https://github.com/jfiala)
- [lukoyanov](https://github.com/lukoyanov)
:heart: = Link to support the contributor directly
## [7 - License](#table-of-contents)
-------

View File

@@ -27,6 +27,6 @@ fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -Xmx1024M -DloggerPath=conf/log4j.properties $@"
ags="generate -t modules/openapi-generator/src/main/resources/graphql-nodejs-express-server -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g graphql-nodejs-express-server -o samples/server/petstore/graphql-nodejs-express-server -DpackageName=petstore $@"
ags="generate -t modules/openapi-generator/src/main/resources/graphql-server -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g graphql-server -o samples/server/petstore/graphql-server -DpackageName=petstore $@"
java $JAVA_OPTS -jar $executable $ags

View File

@@ -34,9 +34,9 @@ find samples/client/petstore/java/okhttp-gson -maxdepth 1 -type f ! -name "READM
java $JAVA_OPTS -jar $executable $ags
# copy additional manually written unit-tests
mkdir -p samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client
mkdir -p samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/auth
mkdir -p samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/model
mkdir samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client
mkdir samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/auth
mkdir samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/model
cp CI/samples.ci/client/petstore/java/test-manual/common/StringUtilTest.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/StringUtilTest.java
cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/ApiClientTest.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/ApiClientTest.java
@@ -45,6 +45,5 @@ cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/auth/ApiKeyAuthTes
cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/auth/HttpBasicAuthTest.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/auth/HttpBasicAuthTest.java
cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/model/EnumValueTest.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/model/EnumValueTest.java
cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/model/PetTest.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/model/PetTest.java
cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/model/ArrayOfArrayOfNumberOnlyTest.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/model/ArrayOfArrayOfNumberOnlyTest.java
cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/model/ArrayOfArrayOfNumberOnly.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/model/ArrayOfArrayOfNumberOnlyTest.java
cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/JSONTest.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/JSONTest.java
cp CI/samples.ci/client/petstore/java/test-manual/okhttp-gson/api/PetApiTest.java samples/client/petstore/java/okhttp-gson/src/test/java/org/openapitools/client/api/PetApiTest.java

View File

@@ -29,6 +29,7 @@ fi
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t modules/openapi-generator/src/main/resources/Javascript/es6 \
-i modules/openapi-generator/src/test/resources/2_0/petstore-with-fake-endpoints-models-for-testing.yaml -g javascript \
-o samples/client/petstore/javascript-es6 $@"
-o samples/client/petstore/javascript-es6 \
--additional-properties useES6=true $@"
java -DappName=PetstoreClient $JAVA_OPTS -jar $executable $ags

View File

@@ -1,32 +0,0 @@
#!/bin/sh
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -Xmx1024M -DloggerPath=conf/log4j.properties $@"
ags="generate -t modules/openapi-generator/src/main/resources/graphql-nodejs-express-server -i modules/openapi-generator/src/test/resources/3_0/petstore.yaml -g graphql-nodejs-express-server -o samples/server/petstore/graphql-nodejs-express-server -DpackageName=petstore $@"
java $JAVA_OPTS -jar $executable $ags

View File

@@ -0,0 +1,42 @@
#!/bin/bash
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
# Make sure that the working directory is the root dir
SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
cd "${SCRIPT_DIR}/../"
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
# Make sure that we are regenerating the sample by removing any existing target directory
TARGET_DIR="$SCRIPT_DIR/../../samples/server/petstore/graphql-server"
if [ -d "$TARGET_DIR" ]; then
rm -rf $TARGET_DIR
fi
executable="$SCRIPT_DIR/../../modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn clean package
fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t $SCRIPT_DIR/../../modules/openapi-generator/src/main/resources/graphql-server -i $SCRIPT_DIR/../../modules/openapi-generator/src/test/resources/3_0/petstore.yaml -g graphql-server -o $TARGET_DIR $@"
java $JAVA_OPTS -jar $executable $ags

View File

@@ -1,34 +0,0 @@
#!/bin/sh
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t modules/openapi-generator/src/main/resources/Javascript/es6 \
-i modules/openapi-generator/src/test/resources/3_0/petstore-with-fake-endpoints-models-for-testing.yaml -g javascript \
-o samples/openapi3/client/petstore/javascript-es6 $@"
java -DappName=PetstoreClient $JAVA_OPTS -jar $executable $ags

View File

@@ -26,25 +26,9 @@ then
fi
# if you've executed sbt assembly previously it will use that instead.
input=modules/openapi-generator/src/test/resources/3_0/petstore.yaml
out_folder=samples/server/openapi3/petstore/python-flask-python2
resources=modules/openapi-generator/src/main/resources/python-flask
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t $resources -i $input -g python-flask -o $out_folder -c bin/supportPython2.json -D service $@"
rm -rf $out_folder/.openapi*
rm -rf $out_folder/openapi_server
rm $out_folder/.dockerignore
rm $out_folder/.gitignore
rm $out_folder/.travis.yml
rm $out_folder/Dockerfile
rm $out_folder/git_push.sh
rm $out_folder/README.md
rm $out_folder/requirements.txt
rm $out_folder/setup.py
rm $out_folder/test-requirements.txt
rm $out_folder/tox.ini
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
#ags="generate -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g python-flask -o samples/server/petstore/flaskConnexion-python2 -DsupportPython2=true $@"
ags="generate -t modules/openapi-generator/src/main/resources/flaskConnexion -i modules/openapi-generator/src/test/resources/3_0/petstore.yaml -g python-flask -o samples/server/petstore/flaskConnexion-python2 -c bin/supportPython2.json -D service $@"
rm -rf samples/server/petstore/flaskConnexion-python2/*
java $JAVA_OPTS -jar $executable $ags

View File

@@ -26,25 +26,8 @@ then
fi
# if you've executed sbt assembly previously it will use that instead.
input=modules/openapi-generator/src/test/resources/3_0/petstore.yaml
out_folder=samples/server/openapi3/petstore/python-flask
resources=modules/openapi-generator/src/main/resources/python-flask
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t $resources -i $input -g python-flask -o $out_folder -Dservice $@"
rm -rf $out_folder/.openapi*
rm -rf $out_folder/openapi_server
rm $out_folder/.dockerignore
rm $out_folder/.gitignore
rm $out_folder/.travis.yml
rm $out_folder/Dockerfile
rm $out_folder/git_push.sh
rm $out_folder/README.md
rm $out_folder/requirements.txt
rm $out_folder/setup.py
rm $out_folder/test-requirements.txt
rm $out_folder/tox.ini
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t modules/openapi-generator/src/main/resources/flaskConnexion -i modules/openapi-generator/src/test/resources/3_0/petstore.yaml -g python-flask -o samples/server/petstore/flaskConnexion -Dservice $@"
rm -rf samples/server/petstore/flaskConnexion/*
java $JAVA_OPTS -jar $executable $ags

View File

@@ -22,11 +22,11 @@ executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
mvn clean package
fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g typescript-rxjs -o samples/client/petstore/typescript-rxjs/builds/with-interfaces -D withInterfaces=true $@"
ags="generate -t modules/openapi-generator/src/main/resources/ze-ph -i modules/openapi-generator/src/test/resources/3_0/petstore-with-fake-endpoints-models-for-testing.yaml -g php-ze-ph -o samples/server/petstore/ze-ph $@"
java $JAVA_OPTS -jar $executable $ags

View File

@@ -25,12 +25,8 @@ then
mvn -B clean package
fi
input=modules/openapi-generator/src/test/resources/2_0/petstore-with-fake-endpoints-models-for-testing.yaml
out_folder=samples/server/petstore/php-ze-ph
resources=modules/openapi-generator/src/main/resources/ze-ph
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t $resources -i $input -g php-ze-ph -o $out_folder $@"
ags="generate -t modules/openapi-generator/src/main/resources/ze-ph -i modules/openapi-generator/src/test/resources/2_0/petstore-with-fake-endpoints-models-for-testing.yaml -g php-ze-ph -o samples/server/petstore/php-ze-ph $@"
java $JAVA_OPTS -jar $executable $ags

4
bin/python-flask-all.sh Executable file
View File

@@ -0,0 +1,4 @@
#!/bin/sh
./bin/python-flask-petstore.sh
./bin/python-flask-petstore-python2.sh

View File

@@ -22,11 +22,13 @@ executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn clean package
mvn -B clean package
fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t modules/openapi-generator/src/main/resources/python -i modules/openapi-generator/src/test/resources/3_0/petstore-with-fake-endpoints-models-for-testing.yaml -g python -o samples/openapi3/client/petstore/python/ -DpackageName=petstore_api $@"
#ags="generate -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g python-flask -o samples/server/petstore/flaskConnexion-python2 -DsupportPython2=true $@"
ags="generate -t modules/openapi-generator/src/main/resources/flaskConnexion -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g python-flask -o samples/server/petstore/flaskConnexion-python2 -c bin/supportPython2.json -D service $@"
rm -rf samples/server/petstore/flaskConnexion-python2/*
java $JAVA_OPTS -jar $executable $ags

View File

@@ -25,12 +25,9 @@ then
mvn -B clean package
fi
input=modules/openapi-generator/src/test/resources/3_0/petstore-with-fake-endpoints-models-for-testing.yaml
out_folder=samples/server/openapi3/petstore/php-ze-ph
resources=modules/openapi-generator/src/main/resources/ze-ph
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t $resources -i $input -g php-ze-ph -o $out_folder $@"
ags="generate -t modules/openapi-generator/src/main/resources/flaskConnexion -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g python-flask -o samples/server/petstore/flaskConnexion -Dservice $@"
rm -rf samples/server/petstore/flaskConnexion/*
java $JAVA_OPTS -jar $executable $ags

View File

@@ -1,44 +0,0 @@
#!/bin/sh
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
fi
generator=python-aiohttp
input=modules/openapi-generator/src/test/resources/2_0/petstore.yaml
out_folder=samples/server/petstore/$generator
resources=modules/openapi-generator/src/main/resources/$generator
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t $resources -i $input -g $generator -o $out_folder -Dservice $@"
rm -rf $out_folder/.openapi*
rm -rf $out_folder/openapi_server
rm -rf $out_folder/tests*
rm $out_folder/README.md
rm $out_folder/requirements.txt
rm $out_folder/test-requirements.txt
java $JAVA_OPTS -jar $executable $ags

View File

@@ -1,5 +0,0 @@
#!/bin/sh
./bin/python-server-aiohttp-petstore.sh
./bin/python-server-flask-petstore.sh
./bin/python-server-flask-petstore-python2.sh

View File

@@ -1,50 +0,0 @@
#!/bin/sh
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
fi
generator=python-flask
input=modules/openapi-generator/src/test/resources/2_0/petstore.yaml
out_folder=samples/server/petstore/$generator-python2
resources=modules/openapi-generator/src/main/resources/$generator
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t $resources -i $input -g $generator -o $out_folder -c bin/supportPython2.json -D service $@"
rm -rf $out_folder/.openapi*
rm -rf $out_folder/openapi_server
rm $out_folder/.dockerignore
rm $out_folder/.gitignore
rm $out_folder/.travis.yml
rm $out_folder/Dockerfile
rm $out_folder/git_push.sh
rm $out_folder/README.md
rm $out_folder/requirements.txt
rm $out_folder/setup.py
rm $out_folder/test-requirements.txt
rm $out_folder/tox.ini
java $JAVA_OPTS -jar $executable $ags

View File

@@ -1,50 +0,0 @@
#!/bin/sh
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
fi
generator=python-flask
input=modules/openapi-generator/src/test/resources/2_0/petstore.yaml
out_folder=samples/server/petstore/$generator
resources=modules/openapi-generator/src/main/resources/$generator
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -t $resources -i $input -g $generator -o $out_folder -Dservice $@"
rm -rf $out_folder/.openapi*
rm -rf $out_folder/openapi_server
rm $out_folder/.dockerignore
rm $out_folder/.gitignore
rm $out_folder/.travis.yml
rm $out_folder/Dockerfile
rm $out_folder/git_push.sh
rm $out_folder/README.md
rm $out_folder/requirements.txt
rm $out_folder/setup.py
rm $out_folder/test-requirements.txt
rm $out_folder/tox.ini
java $JAVA_OPTS -jar $executable $ags

View File

@@ -1,6 +0,0 @@
{
"npmName": "@swagger/node-typescript-petstore",
"npmVersion": "0.0.1",
"npmRepository": "https://skimdb.npmjs.com/registry",
"snapshot": false
}

View File

@@ -27,6 +27,6 @@ fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g typescript-node -c bin/typescript-node-petstore-npm.json -o samples/client/petstore/typescript-node/npm $@"
ags="generate -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g typescript-node -c bin/typescript-petstore-npm.json -o samples/client/petstore/typescript-node/npm $@"
java $JAVA_OPTS -jar $executable $ags

View File

@@ -1,6 +0,0 @@
#!/bin/sh
./bin/typescript-rxjs-petstore-target-es6.sh
./bin/typescript-rxjs-petstore-with-npm-version.sh
./bin/typescript-rxjs-petstore-interfaces.sh
./bin/typescript-rxjs-petstore.sh

View File

@@ -1,7 +0,0 @@
{
"npmName": "@swagger/typescript-rxjs-petstore",
"npmVersion": "1.0.0",
"npmRepository" : "https://skimdb.npmjs.com/registry",
"snapshot" : false,
"supportsES6": true
}

View File

@@ -1,32 +0,0 @@
#!/bin/sh
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g typescript-rxjs -c bin/typescript-rxjs-petstore-target-es6.json -o samples/client/petstore/typescript-rxjs/builds/es6-target $@"
java $JAVA_OPTS -jar $executable $ags

View File

@@ -1,6 +0,0 @@
{
"npmName": "@swagger/typescript-rxjs-petstore",
"npmVersion": "1.0.0",
"npmRepository" : "https://skimdb.npmjs.com/registry",
"snapshot" : false
}

View File

@@ -1,32 +0,0 @@
#!/bin/sh
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g typescript-rxjs -c bin/typescript-rxjs-petstore-with-npm-version.json -o samples/client/petstore/typescript-rxjs/builds/with-npm-version $@"
java $JAVA_OPTS -jar $executable $ags

View File

@@ -1,32 +0,0 @@
#!/bin/sh
SCRIPT="$0"
echo "# START SCRIPT: $SCRIPT"
while [ -h "$SCRIPT" ] ; do
ls=`ls -ld "$SCRIPT"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
SCRIPT="$link"
else
SCRIPT=`dirname "$SCRIPT"`/"$link"
fi
done
if [ ! -d "${APP_DIR}" ]; then
APP_DIR=`dirname "$SCRIPT"`/..
APP_DIR=`cd "${APP_DIR}"; pwd`
fi
executable="./modules/openapi-generator-cli/target/openapi-generator-cli.jar"
if [ ! -f "$executable" ]
then
mvn -B clean package
fi
# if you've executed sbt assembly previously it will use that instead.
export JAVA_OPTS="${JAVA_OPTS} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties"
ags="generate -i modules/openapi-generator/src/test/resources/2_0/petstore.yaml -g typescript-rxjs -o samples/client/petstore/typescript-rxjs/builds/default $@"
java $JAVA_OPTS -jar $executable $ags

View File

@@ -21,8 +21,6 @@ declare -a scripts=("./bin/openapi3/ruby-client-petstore.sh"
"./bin/kotlin-client-threetenbp.sh"
"./bin/kotlin-server-petstore.sh"
"./bin/mysql-schema-petstore.sh"
"./bin/python-petstore.sh"
"./bin/openapi3/python-petstore.sh"
"./bin/php-petstore.sh"
"./bin/php-silex-petstore-server.sh"
"./bin/php-symfony-petstore.sh"
@@ -34,7 +32,6 @@ declare -a scripts=("./bin/openapi3/ruby-client-petstore.sh"
"./bin/typescript-fetch-petstore-all.sh"
"./bin/typescript-node-petstore-all.sh"
"./bin/typescript-inversify-petstore.sh"
"./bin/typescript-rxjs-petstore.sh"
"./bin/rust-server-petstore.sh"
"./bin/haskell-http-client-petstore.sh"
"./bin/csharp-petstore.sh"

View File

@@ -5,6 +5,6 @@ If Not Exist %executable% (
)
REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -t modules\openapi-generator\src\main\resources\graphql-nodejs-express-server -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g graphql-nodejs-express-server -o samples\server\petstore\graphql-nodejs-express-server
set ags=generate -t modules\openapi-generator\src\main\resources\graphql-server -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g graphql-server -o samples\server\petstore\graphql-server
java %JAVA_OPTS% -jar %executable% %ags%

View File

@@ -5,6 +5,6 @@ If Not Exist %executable% (
)
REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g python-flask -o samples\server\petstore\python-flask-python2 -c bin\supportPython2.json -D service
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g python-flask -o samples\server\petstore\flaskConnexion-python2 -c bin\supportPython2.json -D service
java %JAVA_OPTS% -jar %executable% %ags%

View File

@@ -5,6 +5,6 @@ If Not Exist %executable% (
)
REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g python-flask -o samples\server\petstore\python-flask -D service
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g python-flask -o samples\server\petstore\flaskConnexion -D service
java %JAVA_OPTS% -jar %executable% %ags%

View File

@@ -5,6 +5,6 @@ If Not Exist %executable% (
)
REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -c bin\typescript-node-petstore-npm.json -g typescript-node -o samples\client\petstore\typescript-node\npm
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -c bin\typescript-petstore-npm.json -g typescript-node -o samples\client\petstore\typescript-node\npm
java %JAVA_OPTS% -jar %executable% %ags%

View File

@@ -1,6 +0,0 @@
@ECHO OFF
call bin\windows\typescript-rxjs-petstore.bat
call bin\windows\typescript-rxjs-petstore-target-es6.bat
call bin\windows\typescript-rxjs-petstore-with-npm-version.bat
call bin\windows\typescript-rxjs-petstore-interfaces.bat

View File

@@ -1,12 +0,0 @@
@ECHO OFF
set executable=.\modules\openapi-generator-cli\target\openapi-generator-cli.jar
If Not Exist %executable% (
mvn clean package
)
REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g typescript-rxjs -o samples\client\petstore\typescript-rxjs\builds\with-interfaces -D withInterfaces=true
java %JAVA_OPTS% -jar %executable% %ags%

View File

@@ -1,12 +0,0 @@
@ECHO OFF
set executable=.\modules\openapi-generator-cli\target\openapi-generator-cli.jar
If Not Exist %executable% (
mvn clean package
)
REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g typescript-rxjs -c bin\typescript-rxjs-petstore-target-es6.json -o samples\client\petstore\typescript-rxjs\builds\es6-target
java %JAVA_OPTS% -jar %executable% %ags%

View File

@@ -1,12 +0,0 @@
@ECHO OFF
set executable=.\modules\openapi-generator-cli\target\openapi-generator-cli.jar
If Not Exist %executable% (
mvn clean package
)
REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g typescript-rxjs -c bin\typescript-rxjs-petstore-with-npm-version.json -o samples\client\petstore\typescript-rxjs\builds\with-npm-version
java %JAVA_OPTS% -jar %executable% %ags%

View File

@@ -1,14 +0,0 @@
@ECHO OFF
set executable=.\modules\openapi-generator-cli\target\openapi-generator-cli.jar
If Not Exist %executable% (
mvn clean package
)
REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
echo
set ags=generate -i modules\openapi-generator\src\test\resources\2_0\petstore.yaml -g typescript-rxjs -o samples\client\petstore\typescript-rxjs\builds\default
java %JAVA_OPTS% -jar %executable% %ags%

View File

@@ -12,7 +12,7 @@ codegen="${cli}/target/openapi-generator-cli.jar"
# We code in a list of commands here as source processing is potentially buggy (requires undocumented conventional use of annotations).
# A list of known commands helps us determine if we should compile CLI. There's an edge-case where a new command not added to this
# list won't be considered a "real" command. We can get around that a bit by checking CLI completions beforehand if it exists.
commands="list,generate,meta,help,config-help,validate,version"
commands="list,generate,meta,langs,help,config-help,validate,version"
# if CLI jar exists, check $1 against completions available in the CLI
if [[ -f "${codegen}" && -n "$(java ${JAVA_OPTS} -jar "${codegen}" completion | grep "^$1\$" )" ]]; then

View File

@@ -60,7 +60,6 @@ The following generators are available:
- [typescript-inversify](generators/typescript-inversify.md)
- [typescript-jquery](generators/typescript-jquery.md)
- [typescript-node](generators/typescript-node.md)
- [typescript-rxjs](generators/typescript-rxjs.md)
* SERVER generators:
@@ -73,7 +72,7 @@ The following generators are available:
- [erlang-server](generators/erlang-server.md)
- [go-gin-server](generators/go-gin-server.md)
- [go-server](generators/go-server.md)
- [graphql-nodejs-express-server](generators/graphql-nodejs-express-server.md)
- [graphql-server](generators/graphql-server.md)
- [haskell](generators/haskell.md)
- [java-inflector](generators/java-inflector.md)
- [java-msf4j](generators/java-msf4j.md)
@@ -96,7 +95,6 @@ The following generators are available:
- [php-slim](generators/php-slim.md)
- [php-symfony](generators/php-symfony.md)
- [php-ze-ph](generators/php-ze-ph.md)
- [python-aiohttp](generators/python-aiohttp.md)
- [python-flask](generators/python-flask.md)
- [ruby-on-rails](generators/ruby-on-rails.md)
- [ruby-sinatra](generators/ruby-sinatra.md)

View File

@@ -55,7 +55,6 @@ The following generators are available:
- [typescript-inversify](typescript-inversify.md)
- [typescript-jquery](typescript-jquery.md)
- [typescript-node](typescript-node.md)
- [typescript-rxjs](typescript-rxjs.md)
* SERVER generators:

View File

@@ -1,12 +0,0 @@
---
id: generator-opts-server-graphql-nodejs-express-server
title: Config Options for graphql-nodejs-express-server
sidebar_label: graphql-nodejs-express-server
---
| Option | Description | Values | Default |
| ------ | ----------- | ------ | ------- |
|packageName|GraphQL Node.js Express server package name (convention: lowercase).| |openapi3graphql-server|
|packageVersion|GraphQL Node.js Express server package version.| |1.0.0|
|hideGenerationTimestamp|Hides the generation timestamp when files are generated.| |true|

View File

@@ -26,5 +26,5 @@ sidebar_label: javascript
|emitJSDoc|generate JSDoc comments| |true|
|useInheritance|use JavaScript prototype chains &amp; delegation for inheritance| |true|
|hideGenerationTimestamp|Hides the generation timestamp when files are generated.| |true|
|useES6|use JavaScript ES6 (ECMAScript 6) (beta). Default is ES6.| |true|
|useES6|use JavaScript ES6 (ECMAScript 6) (beta). Default is ES5.| |false|
|modelPropertyNaming|Naming convention for the property: 'camelCase', 'PascalCase', 'snake_case' and 'original', which keeps the original name| |camelCase|

View File

@@ -1,19 +0,0 @@
---
id: generator-opts-server-python-aiohttp
title: Config Options for python-aiohttp
sidebar_label: python-aiohttp
---
| Option | Description | Values | Default |
| ------ | ----------- | ------ | ------- |
|sortParamsByRequiredFlag|Sort method arguments to place required parameters before optional parameters.| |true|
|ensureUniqueParams|Whether to ensure parameter names are unique in an operation (rename parameters that are not).| |true|
|allowUnicodeIdentifiers|boolean, toggles whether unicode identifiers are allowed in names or not, default is false| |false|
|prependFormOrBodyParameters|Add form or body parameters to the beginning of the parameter list.| |false|
|packageName|python package name (convention: snake_case).| |openapi_server|
|packageVersion|python package version.| |1.0.0|
|controllerPackage|controller package| |controllers|
|defaultController|default controller| |default_controller|
|supportPython2|support python2| |false|
|serverPort|TCP port to listen to in app.run| |8080|

View File

@@ -1,20 +0,0 @@
---
id: generator-opts-client-typescript-rxjs
title: Config Options for typescript-rxjs
sidebar_label: typescript-rxjs
---
| Option | Description | Values | Default |
| ------ | ----------- | ------ | ------- |
|sortParamsByRequiredFlag|Sort method arguments to place required parameters before optional parameters.| |true|
|ensureUniqueParams|Whether to ensure parameter names are unique in an operation (rename parameters that are not).| |true|
|allowUnicodeIdentifiers|boolean, toggles whether unicode identifiers are allowed in names or not, default is false| |false|
|prependFormOrBodyParameters|Add form or body parameters to the beginning of the parameter list.| |false|
|modelPropertyNaming|Naming convention for the property: 'camelCase', 'PascalCase', 'snake_case' and 'original', which keeps the original name| |camelCase|
|supportsES6|Generate code that conforms to ES6.| |false|
|npmName|The name under which you want to publish generated npm package| |null|
|npmVersion|The version of your npm package| |null|
|npmRepository|Use this property to set an url your private npmRepo in the package.json| |null|
|snapshot|When setting this property to true the version will be suffixed with -SNAPSHOT.yyyyMMddHHmm| |false|
|withInterfaces|Setting this property to true will generate interfaces next to the default class implementations.| |false|

View File

@@ -21,7 +21,7 @@ This guide explains the major differences in order to help you with the migratio
- [New default values for the generated code](#new-default-values-for-the-generated-code)
- [New fully qualified name for the classes](#new-fully-qualified-name-for-the-classes)
- [Body parameter name](#body-parameter-name)
- [Default basePath](#default-basepath)
- [Generators not yet fully migrated](#generators-not-yet-fully-migrated)
## New docker images
@@ -159,7 +159,7 @@ Corresponding java code: `CodegenProperty.datatype` is renamed to `CodegenProper
`.swagger-codegen-ignore` is replaced by `.openapi-generator-ignore`.
The syntax inside the file stays the same.
You don't need to rename the file manually, OpenAPI Generator will do it when your run it against an existing output directory.
You don't need to rename the file manually, OpenAPI Generator will do it when your run it against an existing an existing output directory.
(When there is no `.openapi-generator-ignore` in a folder, if a `.swagger-codegen-ignore` file is present it will be considered and renamed to `.openapi-generator-ignore`).
@@ -187,9 +187,7 @@ Example: `org.openapitools.codegen.DefaultGenerator`
## Body parameter name
:bangbang: Since 4.0.0-beta, the body parameter name in OAS v2 is automatically preserved in the vendor extension `x-codegen-request-body-name`
In OpenAPI spec v3, there's no body parameter, which is replaced by [Request Body Object](https://github.com/OAI/OpenAPI-Specification/blob/master/versions/3.0.1.md#request-body-object). The parameter name for Request Body is named automatically based on the model name (e.g. User). To control how the "Request Body" parameter is named, please add the vendor extension `x-codegen-request-body-name` to the operation:
In OpenAPI spec v3, there's no body parameter, which is replaced by [Request Body Object](https://github.com/OAI/OpenAPI-Specification/blob/master/versions/3.0.1.md#request-body-object). The parameter name for Request Body is named automatically based on the model name (e.g. User). To control how the "Request Body" parmaeter is named, please add the vendor extension `x-codegen-request-body-name` to the operation:
OpenAPI Spec v3:
```yaml
@@ -246,7 +244,3 @@ paths:
- 'read:pets'
```
If your API client is using named parameters in the function call (e.g. Perl required & optional parameters, Ruby optional parameters), you will need to add `x-codegen-request-body-name` to the spec to restore the original body parameter name.
## Default basePath
The default `basePath` has been changed from `https://localhost` to `http://locallhost` (http without s)

View File

@@ -20,25 +20,7 @@ Version `4.0.0` is a major release, which contains some breaking changes without
The option is replaced with `-g` (`--generator-name`).
* `-g` allows the same values as `-l`
* See `list` command for the list of generator name
==== Access OpenAPI instance as member and not as parameter
If you are creating or extending a generator (programmatically), you might have use one of the following parameters: `OpenAPI openAPI` or `Map<String, Schema> allDefinitions` or `Map<String, Schema> allSchemas`. Example methods:
* `CodegenConfig#fromOperation(String, String, Operation, Map<String, Schema>, OpenAPI)`
* `CodegenConfig#fromModel(String, Schema, Map<String, Schema>)`
* `DefaultCodegen#fromResponse(OpenAPI, String, ApiResponse)`
* `DefaultCodegen#DefaultCodegen.fromRequestBody(RequestBody, Map<String, Schema>, Set<String>, String)`
* `DefaultCodegen#createDiscriminator(String, Schema, Map<String, Schema>)`
* ...
The parameters (`openAPI`, `allDefinitions`, `allSchemas` ...) are now removed from the methods.
To access the current OpenAPI instance, if you are extending `DefaultCodegen` you can use the protected `openAPI` member.
If you are creating your own generator by implementing `CodegenConfig`, then the setter `CodegenConfig.setOpenAPI(OpenAPI)` will be called.
You can keep a reference on the `OpenAPI` instance.
* See `langs` command for the list of generator name
=== From 3.1.x to 3.2.0

View File

@@ -615,41 +615,6 @@ For example, suppose you use your specification document for code generation wit
The following are vendor extensions supported by OpenAPI Generator. The list may not be up-to-date, the best way is to look for "x-" in the built-in mustache templates.
### All generators (core)
#### Enum
`x-enum-varnames` can be used to have an other enum name for the corresponding value.
This is used to define names of the enum items.
`x-enum-descriptions` can be used to provide an individual description for each value.
This is used for comments in the code (like javadoc if the target language is java).
`x-enum-descriptions` and `x-enum-varnames` are each expected to be list of items containing the same number of items as `enum`.
The order of the items in the list matters: their position is used to group them together.
Example:
```yaml
WeatherType:
type: integer
format: int32
enum:
- 42
- 18
- 56
x-enum-descriptions:
- 'Blue sky'
- 'Slightly overcast'
- 'Take an umbrella with you'
x-enum-varnames:
- Sunny
- Cloudy
- Rainy
```
In the example for the integer value `42`, the description will be `Blue sky` and the name of the enum item will be `Sunny` (some generators changes it to `SUNNY` to respect some coding convention).
### ObjC
#### x-objc-operationId

View File

@@ -3,7 +3,7 @@
<parent>
<groupId>org.openapitools</groupId>
<artifactId>openapi-generator-project</artifactId>
<version>4.0.0-beta2</version>
<version>4.0.0-SNAPSHOT</version>
<relativePath>../..</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>

View File

@@ -30,7 +30,6 @@ import org.slf4j.LoggerFactory;
import java.io.*;
import java.nio.charset.StandardCharsets;
import java.util.Map;
import java.nio.file.Paths;
import static org.apache.commons.lang3.StringEscapeUtils.escapeHtml4;
import static org.apache.commons.lang3.StringUtils.isEmpty;
@@ -82,7 +81,7 @@ public class ConfigHelp implements Runnable {
}
if (!isEmpty(outputFile)) {
File out = Paths.get(outputFile).toFile();
File out = new File(outputFile);
//noinspection ResultOfMethodCallIgnored
out.getParentFile().mkdirs();

View File

@@ -50,7 +50,7 @@ public class Generate implements Runnable {
private Boolean verbose;
@Option(name = {"-g", "--generator-name"}, title = "generator name",
description = "generator to use (see list command for list)")
description = "generator to use (see langs command for list)")
private String generatorName;
@Option(name = {"-o", "--output"}, title = "output directory",
@@ -208,9 +208,6 @@ public class Generate implements Runnable {
@Option(name = {"--enable-post-process-file"}, title = "enable post-process file", description = CodegenConstants.ENABLE_POST_PROCESS_FILE)
private Boolean enablePostProcessFile;
@Option(name = {"--generate-alias-as-model"}, title = "generate alias (array, map) as model", description = CodegenConstants.GENERATE_ALIAS_AS_MODEL_DESC)
private Boolean generateAliasAsModel;
@Override
public void run() {
if (logToStderr != null) {
@@ -337,10 +334,6 @@ public class Generate implements Runnable {
configurator.setEnablePostProcessFile(enablePostProcessFile);
}
if (generateAliasAsModel != null) {
configurator.setGenerateAliasAsModel(generateAliasAsModel);
}
applySystemPropertiesKvpList(systemProperties, configurator);
applyInstantiationTypesKvpList(instantiationTypes, configurator);
applyImportMappingsKvpList(importMappings, configurator);

View File

@@ -268,26 +268,6 @@ The gradle plugin is not currently published to https://plugins.gradle.org/m2/.
|None
|A map of options specific to a generator.
|logToStderr
|Boolean
|false
|To write all log messages (not just errors) to STDOUT
|enablePostProcessFile
|Boolean
|false
|To enable the file post-processing hook. This enables executing an external post-processor (usually a linter program). This only enables the post-processor. To define the post-processing command, define an environment variable such as LANG_POST_PROCESS_FILE (e.g. GO_POST_PROCESS_FILE, SCALA_POST_PROCESS_FILE). Please open an issue if your target generator does not support this functionality.
|skipValidateSpec
|Boolean
|false
|To skip spec validation. When true, we will skip the default behavior of validating a spec before generation.
|generateAliasAsModel
|Boolean
|false
|To generate alias (array, list, map) as model. When false, top-level objects defined as array, list, or map will result in those definitions generated as top-level Array-of-items, List-of-items, Map-of-items definitions. When true, A model representation either containing or extending the array,list,map (depending on specific generator implementation) will be generated.
|===
[NOTE]
@@ -577,35 +557,3 @@ you need a task reference or instance. One way to do this is to access it as `ta
You can run `gradle tasks --debug` to see this registration.
====
== Troubleshooting
=== Android Studio
Android Studio may experience a Windows-specific Guava dependency conflict with openapig-enerator-gradle-plugin versions greater than 3.0.0.
As a workaround, you may force exclude conflicting Guava dependencies.
```gradle
buildscript {
repositories {
google()
jcenter()
}
dependencies {
classpath 'com.android.tools.build:gradle:3.2.1'
classpath('org.openapitools:openapi-generator-gradle-plugin:3.3.4') {
exclude group: 'com.google.guava'
}
}
}
// …
configurations {
compile.exclude module: 'guava-jdk5'
}
// …
apply plugin: 'org.openapi.generator'
```
See https://github.com/OpenAPITools/openapi-generator/issues/1818[OpenAPITools/openapi-generator#1818] for more details.

View File

@@ -0,0 +1,131 @@
/*
* 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
*
* http://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.generator.gradle.plugin
import org.gradle.api.Plugin
import org.gradle.api.Project
import org.gradle.kotlin.dsl.invoke
import org.openapitools.generator.gradle.plugin.extensions.OpenApiGeneratorGenerateExtension
import org.openapitools.generator.gradle.plugin.extensions.OpenApiGeneratorMetaExtension
import org.openapitools.generator.gradle.plugin.extensions.OpenApiGeneratorValidateExtension
import org.openapitools.generator.gradle.plugin.tasks.GenerateTask
import org.openapitools.generator.gradle.plugin.tasks.GeneratorsTask
import org.openapitools.generator.gradle.plugin.tasks.MetaTask
import org.openapitools.generator.gradle.plugin.tasks.ValidateTask
/**
* A plugin providing common Open API Generator use cases.
*
* @author Jim Schubert
*/
@Suppress("unused")
class OpenApiGeneratorPlugin : Plugin<Project> {
override fun apply(project: Project) {
project.run {
val meta = extensions.create(
"openApiMeta",
OpenApiGeneratorMetaExtension::class.java,
project
)
val validate = extensions.create(
"openApiValidate",
OpenApiGeneratorValidateExtension::class.java,
project
)
val generate = extensions.create(
"openApiGenerate",
OpenApiGeneratorGenerateExtension::class.java,
project
)
generate.outputDir.set("$buildDir/generate-resources/main")
tasks {
"openApiGenerators"(GeneratorsTask::class) {
group = pluginGroup
description = "Lists generators available via Open API Generators."
}
"openApiMeta"(MetaTask::class) {
group = pluginGroup
description = "Generates a new generator to be consumed via Open API Generator."
generatorName.set(meta.generatorName)
packageName.set(meta.packageName)
outputFolder.set(meta.outputFolder)
}
"openApiValidate"(ValidateTask::class) {
group = pluginGroup
description = "Validates an Open API 2.0 or 3.x specification document."
inputSpec.set(validate.inputSpec)
}
"openApiGenerate"(GenerateTask::class) {
group = pluginGroup
description = "Generate code via Open API Tools Generator for Open API 2.0 or 3.x specification documents."
verbose.set(generate.verbose)
validateSpec.set(generate.validateSpec)
generatorName.set(generate.generatorName)
outputDir.set(generate.outputDir)
inputSpec.set(generate.inputSpec)
templateDir.set(generate.templateDir)
auth.set(generate.auth)
systemProperties.set(generate.systemProperties)
configFile.set(generate.configFile)
skipOverwrite.set(generate.skipOverwrite)
apiPackage.set(generate.apiPackage)
modelPackage.set(generate.modelPackage)
modelNamePrefix.set(generate.modelNamePrefix)
modelNameSuffix.set(generate.modelNameSuffix)
instantiationTypes.set(generate.instantiationTypes)
typeMappings.set(generate.typeMappings)
additionalProperties.set(generate.additionalProperties)
languageSpecificPrimitives.set(generate.languageSpecificPrimitives)
importMappings.set(generate.importMappings)
invokerPackage.set(generate.invokerPackage)
groupId.set(generate.groupId)
id.set(generate.id)
version.set(generate.version)
library.set(generate.library)
gitUserId.set(generate.gitUserId)
gitRepoId.set(generate.gitRepoId)
releaseNote.set(generate.releaseNote)
httpUserAgent.set(generate.httpUserAgent)
reservedWordsMappings.set(generate.reservedWordsMappings)
ignoreFileOverride.set(generate.ignoreFileOverride)
removeOperationIdPrefix.set(generate.removeOperationIdPrefix)
apiFilesConstrainedTo.set(generate.apiFilesConstrainedTo)
modelFilesConstrainedTo.set(generate.modelFilesConstrainedTo)
supportingFilesConstrainedTo.set(generate.supportingFilesConstrainedTo)
generateModelTests.set(generate.generateModelTests)
generateModelDocumentation.set(generate.generateModelDocumentation)
generateApiTests.set(generate.generateApiTests)
generateApiDocumentation.set(generate.generateApiDocumentation)
withXml.set(generate.withXml)
configOptions.set(generate.configOptions)
}
}
}
}
companion object {
const val pluginGroup = "OpenAPI Tools"
}
}

View File

@@ -0,0 +1,286 @@
/*
* 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
*
* http://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.generator.gradle.plugin.extensions
import org.gradle.api.Project
import org.gradle.kotlin.dsl.listProperty
import org.gradle.kotlin.dsl.property
/**
* Gradle project level extension object definition for the generate task
*
* @author Jim Schubert
*/
open class OpenApiGeneratorGenerateExtension(project: Project) {
/**
* The verbosity of generation
*/
val verbose = project.objects.property<Boolean>()
/**
* Whether or not an input specification should be validated upon generation.
*/
val validateSpec = project.objects.property<Boolean>()
/**
* The name of the generator which will handle codegen. (see "openApiGenerators" task)
*/
val generatorName = project.objects.property<String>()
/**
* The output target directory into which code will be generated.
*/
val outputDir = project.objects.property<String>()
/**
* The Open API 2.0/3.x specification location.
*/
val inputSpec = project.objects.property<String>()
/**
* The template directory holding a custom template.
*/
val templateDir = project.objects.property<String?>()
/**
* Adds authorization headers when fetching the OpenAPI definitions remotely.
* Pass in a URL-encoded string of name:header with a comma separating multiple values
*/
val auth = project.objects.property<String>()
/**
* Sets specified system properties.
*/
val systemProperties = project.objects.property<Map<String, String>>()
/**
* Path to json configuration file.
* File content should be in a json format { "optionKey":"optionValue", "optionKey1":"optionValue1"...}
* Supported options can be different for each language. Run config-help -g {generator name} command for language specific config options.
*/
val configFile = project.objects.property<String>()
/**
* Specifies if the existing files should be overwritten during the generation.
*/
val skipOverwrite = project.objects.property<Boolean?>()
/**
* Package for generated api classes
*/
val apiPackage = project.objects.property<String>()
/**
* Package for generated models
*/
val modelPackage = project.objects.property<String>()
/**
* Prefix that will be prepended to all model names. Default is the empty string.
*/
val modelNamePrefix = project.objects.property<String>()
/**
* Suffix that will be appended to all model names. Default is the empty string.
*/
val modelNameSuffix = project.objects.property<String>()
/**
* Sets instantiation type mappings.
*/
val instantiationTypes = project.objects.property<Map<String, String>>()
/**
* Sets mappings between OpenAPI spec types and generated code types.
*/
val typeMappings = project.objects.property<Map<String, String>>()
/**
* Sets additional properties that can be referenced by the mustache templates.
*/
val additionalProperties = project.objects.property<Map<String, String>>()
/**
* Specifies additional language specific primitive types in the format of type1,type2,type3,type3. For example: String,boolean,Boolean,Double.
*/
val languageSpecificPrimitives = project.objects.listProperty<String>()
/**
* Specifies mappings between a given class and the import that should be used for that class.
*/
val importMappings = project.objects.property<Map<String, String>>()
/**
* Root package for generated code.
*/
val invokerPackage = project.objects.property<String>()
/**
* GroupId in generated pom.xml/build.gradle or other build script. Language-specific conversions occur in non-jvm generators.
*/
val groupId = project.objects.property<String>()
/**
* ArtifactId in generated pom.xml/build.gradle or other build script. Language-specific conversions occur in non-jvm generators.
*/
val id = project.objects.property<String>()
/**
* Artifact version in generated pom.xml/build.gradle or other build script. Language-specific conversions occur in non-jvm generators.
*/
val version = project.objects.property<String>()
/**
* Reference the library template (sub-template) of a generator.
*/
val library = project.objects.property<String?>()
/**
* Git user ID, e.g. openapitools.
*/
val gitUserId = project.objects.property<String?>()
/**
* Git repo ID, e.g. openapi-generator.
*/
val gitRepoId = project.objects.property<String?>()
/**
* Release note, default to 'Minor update'.
*/
val releaseNote = project.objects.property<String?>()
/**
* HTTP user agent, e.g. codegen_csharp_api_client, default to 'OpenAPI-Generator/{packageVersion}}/{language}'
*/
val httpUserAgent = project.objects.property<String?>()
/**
* Specifies how a reserved name should be escaped to. Otherwise, the default _<name> is used.
*/
val reservedWordsMappings = project.objects.property<Map<String, String>>()
/**
* Specifies an override location for the .openapi-generator-ignore file. Most useful on initial generation.
*/
val ignoreFileOverride = project.objects.property<String?>()
/**
* Remove prefix of operationId, e.g. config_getId => getId
*/
val removeOperationIdPrefix = project.objects.property<Boolean?>()
/**
* Defines which API-related files should be generated. This allows you to create a subset of generated files (or none at all).
*
* NOTE: Configuring any one of [apiFilesConstrainedTo], [modelFilesConstrainedTo], or [supportingFilesConstrainedTo] results
* in others being disabled. That is, OpenAPI Generator considers any one of these to define a subset of generation.
* For more control over generation of individual files, configure an ignore file and refer to it via [ignoreFileOverride].
*/
val apiFilesConstrainedTo = project.objects.listProperty<String>()
/**
* Defines which model-related files should be generated. This allows you to create a subset of generated files (or none at all).
*
* NOTE: Configuring any one of [apiFilesConstrainedTo], [modelFilesConstrainedTo], or [supportingFilesConstrainedTo] results
* in others being disabled. That is, OpenAPI Generator considers any one of these to define a subset of generation.
* For more control over generation of individual files, configure an ignore file and refer to it via [ignoreFileOverride].
*/
val modelFilesConstrainedTo = project.objects.listProperty<String>()
/**
* Defines which supporting files should be generated. This allows you to create a subset of generated files (or none at all).
*
* Supporting files are those related to projects/frameworks which may be modified
* by consumers.
*
* NOTE: Configuring any one of [apiFilesConstrainedTo], [modelFilesConstrainedTo], or [supportingFilesConstrainedTo] results
* in others being disabled. That is, OpenAPI Generator considers any one of these to define a subset of generation.
* For more control over generation of individual files, configure an ignore file and refer to it via [ignoreFileOverride].
*/
val supportingFilesConstrainedTo = project.objects.listProperty<String>()
/**
* Defines whether or not model-related _test_ files should be generated.
*
* This option enables/disables generation of ALL model-related _test_ files.
*
* For more control over generation of individual files, configure an ignore file and
* refer to it via [ignoreFileOverride].
*/
val generateModelTests = project.objects.property<Boolean>()
/**
* Defines whether or not model-related _documentation_ files should be generated.
*
* This option enables/disables generation of ALL model-related _documentation_ files.
*
* For more control over generation of individual files, configure an ignore file and
* refer to it via [ignoreFileOverride].
*/
val generateModelDocumentation = project.objects.property<Boolean>()
/**
* Defines whether or not api-related _test_ files should be generated.
*
* This option enables/disables generation of ALL api-related _test_ files.
*
* For more control over generation of individual files, configure an ignore file and
* refer to it via [ignoreFileOverride].
*/
val generateApiTests = project.objects.property<Boolean>()
/**
* Defines whether or not api-related _documentation_ files should be generated.
*
* This option enables/disables generation of ALL api-related _documentation_ files.
*
* For more control over generation of individual files, configure an ignore file and
* refer to it via [ignoreFileOverride].
*/
val generateApiDocumentation = project.objects.property<Boolean>()
/**
* A special-case setting which configures some generators with XML support. In some cases,
* this forces json OR xml, so the default here is false.
*/
val withXml = project.objects.property<Boolean>()
/**
* A map of options specific to a generator.
*/
val configOptions = project.objects.property<Map<String, String>>()
init {
applyDefaults()
}
@Suppress("MemberVisibilityCanBePrivate")
fun applyDefaults(){
releaseNote.set("Minor update")
modelNamePrefix.set("")
modelNameSuffix.set("")
generateModelTests.set(true)
generateModelDocumentation.set(true)
generateApiTests.set(true)
generateApiDocumentation.set(true)
withXml.set(false)
configOptions.set(mapOf())
validateSpec.set(true)
}
}

View File

@@ -0,0 +1,48 @@
/*
* 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
*
* http://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.generator.gradle.plugin.extensions
import org.gradle.api.Project
import org.gradle.kotlin.dsl.property
/**
* Gradle project level extension object definition for the meta-generator task
*
* @author Jim Schubert
*/
open class OpenApiGeneratorMetaExtension(project: Project) {
/**
* The human-readable generator name of the newly created template generator.
*/
val generatorName = project.objects.property<String>()
/**
* The packageName generatorName to put the main class into (defaults to org.openapitools.codegen)
*/
val packageName = project.objects.property<String>()
/**
* Where to write the generated files (current dir by default).
*/
val outputFolder = project.objects.property<String>()
init {
generatorName.set("default")
packageName.set("org.openapitools.codegen")
outputFolder.set("")
}
}

View File

@@ -0,0 +1,32 @@
/*
* 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
*
* http://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.generator.gradle.plugin.extensions
import org.gradle.api.Project
import org.gradle.kotlin.dsl.property
/**
* Gradle project level extension object definition for the generators task
*
* @author Jim Schubert
*/
open class OpenApiGeneratorValidateExtension(project: Project) {
/**
* The input specification to validate. Supports all formats supported by the Parser.
*/
val inputSpec = project.objects.property<String>()
}

View File

@@ -0,0 +1,549 @@
/*
* 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
*
* http://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.generator.gradle.plugin.tasks
import org.gradle.api.DefaultTask
import org.gradle.api.GradleException
import org.gradle.api.provider.Property
import org.gradle.api.tasks.Internal
import org.gradle.api.tasks.TaskAction
import org.gradle.internal.logging.text.StyledTextOutput
import org.gradle.internal.logging.text.StyledTextOutputFactory
import org.gradle.kotlin.dsl.listProperty
import org.gradle.kotlin.dsl.property
import org.openapitools.codegen.CodegenConstants
import org.openapitools.codegen.DefaultGenerator
import org.openapitools.codegen.config.CodegenConfigurator
import org.openapitools.codegen.config.GeneratorProperties
/**
* A task which generates the desired code.
*
* Example (CLI):
*
* ./gradlew -q openApiGenerate
*
* @author Jim Schubert
*/
open class GenerateTask : DefaultTask() {
/**
* The verbosity of generation
*/
@get:Internal
val verbose = project.objects.property<Boolean>()
/**
* Whether or not an input specification should be validated upon generation.
*/
@get:Internal
val validateSpec = project.objects.property<Boolean>()
/**
* The name of the generator which will handle codegen. (see "openApiGenerators" task)
*/
@get:Internal
val generatorName = project.objects.property<String>()
/**
* The output target directory into which code will be generated.
*/
@get:Internal
val outputDir = project.objects.property<String>()
/**
* The Open API 2.0/3.x specification location.
*/
@get:Internal
val inputSpec = project.objects.property<String>()
/**
* The template directory holding a custom template.
*/
@get:Internal
val templateDir = project.objects.property<String?>()
/**
* Adds authorization headers when fetching the OpenAPI definitions remotely.
* Pass in a URL-encoded string of name:header with a comma separating multiple values
*/
@get:Internal
val auth = project.objects.property<String>()
/**
* Sets specified system properties.
*/
@get:Internal
val systemProperties = project.objects.property<Map<String, String>>()
/**
* Path to json configuration file.
* File content should be in a json format { "optionKey":"optionValue", "optionKey1":"optionValue1"...}
* Supported options can be different for each language. Run config-help -g {generator name} command for language specific config options.
*/
@get:Internal
val configFile = project.objects.property<String>()
/**
* Specifies if the existing files should be overwritten during the generation.
*/
@get:Internal
val skipOverwrite = project.objects.property<Boolean?>()
/**
* Package for generated api classes
*/
@get:Internal
val apiPackage = project.objects.property<String>()
/**
* Package for generated models
*/
@get:Internal
val modelPackage = project.objects.property<String>()
/**
* Prefix that will be prepended to all model names. Default is the empty string.
*/
@get:Internal
val modelNamePrefix = project.objects.property<String>()
/**
* Suffix that will be appended to all model names. Default is the empty string.
*/
@get:Internal
val modelNameSuffix = project.objects.property<String>()
/**
* Sets instantiation type mappings.
*/
@get:Internal
val instantiationTypes = project.objects.property<Map<String, String>>()
/**
* Sets mappings between OpenAPI spec types and generated code types.
*/
@get:Internal
val typeMappings = project.objects.property<Map<String, String>>()
/**
* Sets additional properties that can be referenced by the mustache templates in the format of name=value,name=value.
* You can also have multiple occurrences of this option.
*/
@get:Internal
val additionalProperties = project.objects.property<Map<String, String>>()
/**
* Specifies additional language specific primitive types in the format of type1,type2,type3,type3. For example: String,boolean,Boolean,Double.
*/
@get:Internal
val languageSpecificPrimitives = project.objects.listProperty<String>()
/**
* Specifies mappings between a given class and the import that should be used for that class.
*/
@get:Internal
val importMappings = project.objects.property<Map<String, String>>()
/**
* Root package for generated code.
*/
@get:Internal
val invokerPackage = project.objects.property<String>()
/**
* GroupId in generated pom.xml/build.gradle or other build script. Language-specific conversions occur in non-jvm generators.
*/
@get:Internal
val groupId = project.objects.property<String>()
/**
* ArtifactId in generated pom.xml/build.gradle or other build script. Language-specific conversions occur in non-jvm generators.
*/
@get:Internal
val id = project.objects.property<String>()
/**
* Artifact version in generated pom.xml/build.gradle or other build script. Language-specific conversions occur in non-jvm generators.
*/
@get:Internal
val version = project.objects.property<String>()
/**
* Reference the library template (sub-template) of a generator.
*/
@get:Internal
val library = project.objects.property<String?>()
/**
* Git user ID, e.g. openapitools.
*/
@get:Internal
val gitUserId = project.objects.property<String?>()
/**
* Git repo ID, e.g. openapi-generator.
*/
@get:Internal
val gitRepoId = project.objects.property<String?>()
/**
* Release note, default to 'Minor update'.
*/
@get:Internal
val releaseNote = project.objects.property<String?>()
/**
* HTTP user agent, e.g. codegen_csharp_api_client, default to 'OpenAPI-Generator/{packageVersion}}/{language}'
*/
@get:Internal
val httpUserAgent = project.objects.property<String?>()
/**
* Specifies how a reserved name should be escaped to.
*/
@get:Internal
val reservedWordsMappings = project.objects.property<Map<String, String>>()
/**
* Specifies an override location for the .openapi-generator-ignore file. Most useful on initial generation.
*/
@get:Internal
val ignoreFileOverride = project.objects.property<String?>()
/**
* Remove prefix of operationId, e.g. config_getId => getId
*/
@get:Internal
val removeOperationIdPrefix = project.objects.property<Boolean?>()
/**
* Defines which API-related files should be generated. This allows you to create a subset of generated files (or none at all).
*
* This option enables/disables generation of ALL api-related files.
*
* NOTE: Configuring any one of [apiFilesConstrainedTo], [modelFilesConstrainedTo], or [supportingFilesConstrainedTo] results
* in others being disabled. That is, OpenAPI Generator considers any one of these to define a subset of generation.
* For more control over generation of individual files, configure an ignore file and refer to it via [ignoreFileOverride].
*/
@get:Internal
val apiFilesConstrainedTo = project.objects.listProperty<String>()
/**
* Defines which model-related files should be generated. This allows you to create a subset of generated files (or none at all).
*
* NOTE: Configuring any one of [apiFilesConstrainedTo], [modelFilesConstrainedTo], or [supportingFilesConstrainedTo] results
* in others being disabled. That is, OpenAPI Generator considers any one of these to define a subset of generation.
* For more control over generation of individual files, configure an ignore file and refer to it via [ignoreFileOverride].
*/
@get:Internal
val modelFilesConstrainedTo = project.objects.listProperty<String>()
/**
* Defines which supporting files should be generated. This allows you to create a subset of generated files (or none at all).
*
* Supporting files are those related to projects/frameworks which may be modified
* by consumers.
*
* NOTE: Configuring any one of [apiFilesConstrainedTo], [modelFilesConstrainedTo], or [supportingFilesConstrainedTo] results
* in others being disabled. That is, OpenAPI Generator considers any one of these to define a subset of generation.
* For more control over generation of individual files, configure an ignore file and refer to it via [ignoreFileOverride].
*/
@get:Internal
val supportingFilesConstrainedTo = project.objects.listProperty<String>()
/**
* Defines whether or not model-related _test_ files should be generated.
*
* This option enables/disables generation of ALL model-related _test_ files.
*
* For more control over generation of individual files, configure an ignore file and
* refer to it via [ignoreFileOverride].
*/
@get:Internal
val generateModelTests = project.objects.property<Boolean>()
/**
* Defines whether or not model-related _documentation_ files should be generated.
*
* This option enables/disables generation of ALL model-related _documentation_ files.
*
* For more control over generation of individual files, configure an ignore file and
* refer to it via [ignoreFileOverride].
*/
@get:Internal
val generateModelDocumentation = project.objects.property<Boolean>()
/**
* Defines whether or not api-related _test_ files should be generated.
*
* This option enables/disables generation of ALL api-related _test_ files.
*
* For more control over generation of individual files, configure an ignore file and
* refer to it via [ignoreFileOverride].
*/
@get:Internal
val generateApiTests = project.objects.property<Boolean>()
/**
* Defines whether or not api-related _documentation_ files should be generated.
*
* This option enables/disables generation of ALL api-related _documentation_ files.
*
* For more control over generation of individual files, configure an ignore file and
* refer to it via [ignoreFileOverride].
*/
@get:Internal
val generateApiDocumentation = project.objects.property<Boolean>()
/**
* A special-case setting which configures some generators with XML support. In some cases,
* this forces json OR xml, so the default here is false.
*/
@get:Internal
val withXml = project.objects.property<Boolean>()
/**
* A dynamic map of options specific to a generator.
*/
@get:Internal
val configOptions = project.objects.property<Map<String, String>>()
private val originalEnvironmentVariables = mutableMapOf<String, String?>()
private fun <T : Any?> Property<T>.ifNotEmpty(block: Property<T>.(T) -> Unit) {
if (isPresent) {
val item: T? = get()
if (item != null) {
when (get()) {
is String -> if ((get() as String).isNotEmpty()) {
block(get())
}
is String? -> if (true == (get() as String?)?.isNotEmpty()) {
block(get())
}
else -> block(get())
}
}
}
}
@Suppress("unused")
@TaskAction
fun doWork() {
val configurator: CodegenConfigurator = if (configFile.isPresent) {
CodegenConfigurator.fromFile(configFile.get())
} else CodegenConfigurator()
try {
if (systemProperties.isPresent) {
systemProperties.get().forEach { (key, value) ->
// GeneratorProperties.setProperty returns the original value for a key, or null.
// Cache the original value or null…we will late put the properties back in their original state.
originalEnvironmentVariables[key] = GeneratorProperties.setProperty(key, value)
configurator.addSystemProperty(key, value)
}
}
if (supportingFilesConstrainedTo.isPresent && supportingFilesConstrainedTo.get().isNotEmpty()) {
GeneratorProperties.setProperty(CodegenConstants.SUPPORTING_FILES, supportingFilesConstrainedTo.get().joinToString(","))
} else {
GeneratorProperties.clearProperty(CodegenConstants.SUPPORTING_FILES)
}
if (modelFilesConstrainedTo.isPresent && modelFilesConstrainedTo.get().isNotEmpty()) {
GeneratorProperties.setProperty(CodegenConstants.MODELS, modelFilesConstrainedTo.get().joinToString(","))
} else {
GeneratorProperties.clearProperty(CodegenConstants.MODELS)
}
if (apiFilesConstrainedTo.isPresent && apiFilesConstrainedTo.get().isNotEmpty()) {
GeneratorProperties.setProperty(CodegenConstants.APIS, apiFilesConstrainedTo.get().joinToString(","))
} else {
GeneratorProperties.clearProperty(CodegenConstants.APIS)
}
GeneratorProperties.setProperty(CodegenConstants.API_DOCS, generateApiDocumentation.get().toString())
GeneratorProperties.setProperty(CodegenConstants.MODEL_DOCS, generateModelDocumentation.get().toString())
GeneratorProperties.setProperty(CodegenConstants.MODEL_TESTS, generateModelTests.get().toString())
GeneratorProperties.setProperty(CodegenConstants.API_TESTS, generateApiTests.get().toString())
GeneratorProperties.setProperty(CodegenConstants.WITH_XML, withXml.get().toString())
// now override with any specified parameters
verbose.ifNotEmpty { value ->
configurator.isVerbose = value
}
validateSpec.ifNotEmpty { value ->
configurator.isValidateSpec = value
}
skipOverwrite.ifNotEmpty { value ->
configurator.isSkipOverwrite = value ?: false
}
inputSpec.ifNotEmpty { value ->
configurator.inputSpec = value
}
generatorName.ifNotEmpty { value ->
configurator.generatorName = value
}
outputDir.ifNotEmpty { value ->
configurator.outputDir = value
}
auth.ifNotEmpty { value ->
configurator.auth = value
}
templateDir.ifNotEmpty { value ->
configurator.templateDir = value
}
apiPackage.ifNotEmpty { value ->
configurator.apiPackage = value
}
modelPackage.ifNotEmpty { value ->
configurator.modelPackage = value
}
modelNamePrefix.ifNotEmpty { value ->
configurator.modelNamePrefix = value
}
modelNameSuffix.ifNotEmpty { value ->
configurator.modelNameSuffix = value
}
invokerPackage.ifNotEmpty { value ->
configurator.invokerPackage = value
}
groupId.ifNotEmpty { value ->
configurator.groupId = value
}
id.ifNotEmpty { value ->
configurator.artifactId = value
}
version.ifNotEmpty { value ->
configurator.artifactVersion = value
}
library.ifNotEmpty { value ->
configurator.library = value
}
gitUserId.ifNotEmpty { value ->
configurator.gitUserId = value
}
gitRepoId.ifNotEmpty { value ->
configurator.gitRepoId = value
}
releaseNote.ifNotEmpty { value ->
configurator.releaseNote = value
}
httpUserAgent.ifNotEmpty { value ->
configurator.httpUserAgent = value
}
ignoreFileOverride.ifNotEmpty { value ->
configurator.ignoreFileOverride = value
}
removeOperationIdPrefix.ifNotEmpty { value ->
configurator.removeOperationIdPrefix = value!!
}
if (systemProperties.isPresent) {
systemProperties.get().forEach { entry ->
configurator.addSystemProperty(entry.key, entry.value)
}
}
if (instantiationTypes.isPresent) {
instantiationTypes.get().forEach { entry ->
configurator.addInstantiationType(entry.key, entry.value)
}
}
if (importMappings.isPresent) {
importMappings.get().forEach { entry ->
configurator.addImportMapping(entry.key, entry.value)
}
}
if (typeMappings.isPresent) {
typeMappings.get().forEach { entry ->
configurator.addTypeMapping(entry.key, entry.value)
}
}
if (additionalProperties.isPresent) {
additionalProperties.get().forEach { entry ->
configurator.addAdditionalProperty(entry.key, entry.value)
}
}
if (languageSpecificPrimitives.isPresent) {
languageSpecificPrimitives.get().forEach {
configurator.addLanguageSpecificPrimitive(it)
}
}
if (reservedWordsMappings.isPresent) {
reservedWordsMappings.get().forEach { entry ->
configurator.addAdditionalReservedWordMapping(entry.key, entry.value)
}
}
val clientOptInput = configurator.toClientOptInput()
val codgenConfig = clientOptInput.config
if (configOptions.isPresent) {
val userSpecifiedConfigOptions = configOptions.get()
codgenConfig.cliOptions().forEach {
if (userSpecifiedConfigOptions.containsKey(it.opt)) {
clientOptInput.config.additionalProperties()[it.opt] = userSpecifiedConfigOptions[it.opt]
}
}
}
try {
val out = services.get(StyledTextOutputFactory::class.java).create("openapi")
out.withStyle(StyledTextOutput.Style.Success)
DefaultGenerator().opts(clientOptInput).generate()
out.println("Successfully generated code to ${configurator.outputDir}")
} catch (e: RuntimeException) {
throw GradleException("Code generation failed.", e)
}
} finally {
// Reset all modified system properties back to their original state
GeneratorProperties.reset()
}
}
}

View File

@@ -0,0 +1,71 @@
/*
* 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
*
* http://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.generator.gradle.plugin.tasks
import org.gradle.api.DefaultTask
import org.gradle.api.tasks.TaskAction
import org.gradle.internal.logging.text.StyledTextOutput
import org.gradle.internal.logging.text.StyledTextOutputFactory
import org.openapitools.codegen.CodegenConfigLoader
import org.openapitools.codegen.CodegenType
/**
* A task which lists out the generators available in OpenAPI Generator
*
* Example (CLI):
*
* ./gradlew -q openApiGenerators
*
* @author Jim Schubert
*/
open class GeneratorsTask : DefaultTask() {
@Suppress("unused")
@TaskAction
fun doWork() {
val generators = CodegenConfigLoader.getAll()
val out = services.get(StyledTextOutputFactory::class.java).create("openapi")
StringBuilder().apply {
val types = CodegenType.values()
append("The following generators are available:")
append(System.lineSeparator())
append(System.lineSeparator())
for (type in types) {
append(type.name).append(" generators:")
append(System.lineSeparator())
generators.filter { it.tag == type }
.sortedBy { it.name }
.forEach({ generator ->
append(" - ")
append(generator.name)
append(System.lineSeparator())
})
append(System.lineSeparator())
append(System.lineSeparator())
}
out.withStyle(StyledTextOutput.Style.Success)
out.formatln("%s%n", toString())
}
}
}

View File

@@ -0,0 +1,132 @@
/*
* 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
*
* http://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.generator.gradle.plugin.tasks
import com.samskivert.mustache.Mustache
import org.gradle.api.DefaultTask
import org.gradle.api.GradleException
import org.gradle.api.tasks.Internal
import org.gradle.api.tasks.TaskAction
import org.gradle.internal.logging.text.StyledTextOutput
import org.gradle.internal.logging.text.StyledTextOutputFactory
import org.gradle.kotlin.dsl.property
import org.openapitools.codegen.CodegenConfig
import org.openapitools.codegen.CodegenConstants
import org.openapitools.codegen.DefaultGenerator
import org.openapitools.codegen.SupportingFile
import java.io.File
import java.io.IOException
import java.nio.charset.Charset
/**
* A task which generates a new generator (meta). Useful for redistributable generator packages.
*
* @author Jim Schubert
*/
open class MetaTask : DefaultTask() {
@get:Internal
val generatorName = project.objects.property<String>()
@get:Internal
val packageName = project.objects.property<String>()
@get:Internal
val outputFolder = project.objects.property<String>()
@Suppress("unused")
@TaskAction
fun doWork() {
val packageToPath = packageName.get().replace(".", File.separator)
val dir = File(outputFolder.get())
val klass = "${generatorName.get().titleCasedTextOnly()}Generator"
val templateResourceDir = generatorName.get().hyphenatedTextOnly()
val out = services.get(StyledTextOutputFactory::class.java).create("openapi")
out.withStyle(StyledTextOutput.Style.Info)
logger.debug("package: {}", packageName.get())
logger.debug("dir: {}", dir.absolutePath)
logger.debug("generator class: {}", klass)
val supportingFiles = listOf(
SupportingFile("pom.mustache", "", "pom.xml"),
SupportingFile("generatorClass.mustache", dir("src", "main", "java", packageToPath), "$klass.java"),
SupportingFile("README.mustache", "", "README.md"),
SupportingFile("api.template", dir("src", "main", "resources", templateResourceDir), "api.mustache"),
SupportingFile("model.template", dir("src", "main", "resources", templateResourceDir), "model.mustache"),
SupportingFile("myFile.template", dir("src", "main", "resources", templateResourceDir), "myFile.mustache"),
SupportingFile("services.mustache", dir("src", "main", "resources", "META-INF", "services"), CodegenConfig::class.java.canonicalName))
val currentVersion = CodegenConstants::class.java.`package`.implementationVersion
val data = mapOf("generatorPackage" to packageToPath,
"generatorClass" to klass,
"name" to templateResourceDir,
"fullyQualifiedGeneratorClass" to "${packageName.get()}.$klass",
"openapiGeneratorVersion" to currentVersion)
val generator = DefaultGenerator()
supportingFiles.map {
try {
val destinationFolder = File(File(dir.absolutePath), it.folder)
destinationFolder.mkdirs()
val outputFile = File(destinationFolder, it.destinationFilename)
val template = generator.readTemplate(File("codegen", it.templateFile).path)
var formatted = template
if (it.templateFile.endsWith(".mustache")) {
formatted = Mustache.compiler()
.withLoader(loader(generator))
.defaultValue("")
.compile(template).execute(data)
}
outputFile.writeText(formatted, Charset.forName("UTF8"))
out.formatln("Wrote file to %s", outputFile.absolutePath)
// TODO: register outputs
// return outputFile
} catch (e: IOException) {
logger.error(e.message)
throw GradleException("Can't generate project", e)
}
}
out.withStyle(StyledTextOutput.Style.Success)
out.formatln("Created generator %s", klass)
}
private fun loader(generator: DefaultGenerator): Mustache.TemplateLoader {
return Mustache.TemplateLoader { name ->
generator.getTemplateReader("codegen${File.separator}$name.mustache")
}
}
private fun String.titleCasedTextOnly(): String =
this.split(Regex("[^a-zA-Z0-9]")).joinToString(separator = "", transform = String::capitalize)
private fun String.hyphenatedTextOnly(): String =
this.split(Regex("[^a-zA-Z0-9]")).joinToString(separator = "-", transform = String::toLowerCase)
private fun dir(vararg parts: String): String =
parts.joinToString(separator = File.separator)
}

View File

@@ -0,0 +1,82 @@
/*
* 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
*
* http://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.generator.gradle.plugin.tasks
import io.swagger.parser.OpenAPIParser
import org.gradle.api.DefaultTask
import org.gradle.api.GradleException
import org.gradle.api.tasks.Internal
import org.gradle.api.tasks.TaskAction
import org.gradle.api.tasks.options.Option
import org.gradle.internal.logging.text.StyledTextOutput
import org.gradle.internal.logging.text.StyledTextOutputFactory
import org.gradle.kotlin.dsl.property
/**
* A generator which validates an Open API spec. This task outputs a list of validation issues and errors.
*
* Example:
* cli:
*
* ./gradlew openApiValidate --input=/path/to/file
*
* build.gradle:
*
* openApiMeta {
* inputSpec = "path/to/spec.yaml"
* }
*
* @author Jim Schubert
*/
open class ValidateTask : DefaultTask() {
@get:Internal
var inputSpec = project.objects.property<String>()
@Suppress("unused")
@get:Internal
@set:Option(option = "input", description = "The input specification.")
var input: String? = null
set(value) {
inputSpec.set(value)
}
@Suppress("unused")
@TaskAction
fun doWork() {
val spec = inputSpec.get()
logger.quiet("Validating spec $spec")
val result = OpenAPIParser().readLocation(spec, null, null)
val messages = result.messages.toSet()
val out = services.get(StyledTextOutputFactory::class.java).create("openapi")
if (messages.isNotEmpty()) {
out.withStyle(StyledTextOutput.Style.Error)
out.println("\nSpec is invalid.\nIssues:\n")
messages.forEach {
out.withStyle(StyledTextOutput.Style.Error)
out.println("\t$it\n")
}
throw GradleException("Validation failed.")
} else {
out.withStyle(StyledTextOutput.Style.Success)
out.println("Spec is valid.")
}
}
}

View File

@@ -0,0 +1,71 @@
package org.openapitools.generator.gradle.plugin
import org.gradle.testkit.runner.GradleRunner
import org.gradle.testkit.runner.TaskOutcome
import org.testng.annotations.Test
import java.io.File
import kotlin.test.assertEquals
import kotlin.test.assertTrue
class GenerateTaskDslTest : TestBase() {
override var temp: File = createTempDir(javaClass.simpleName)
private val defaultBuildGradle = """
plugins {
id 'org.openapi.generator'
}
openApiGenerate {
generatorName = "kotlin"
inputSpec = file("spec.yaml").absolutePath
outputDir = file("build/kotlin").absolutePath
apiPackage = "org.openapitools.example.api"
invokerPackage = "org.openapitools.example.invoker"
modelPackage = "org.openapitools.example.model"
configOptions = [
dateLibrary: "java8"
]
}
""".trimIndent()
@Test
fun `openApiGenerate should create an expected file structure from DSL config`() {
// Arrange
val projectFiles = mapOf(
"spec.yaml" to javaClass.classLoader.getResourceAsStream("specs/petstore-v3.0.yaml")
)
withProject(defaultBuildGradle, projectFiles)
// Act
val result = GradleRunner.create()
.withProjectDir(temp)
.withArguments("openApiGenerate")
.withPluginClasspath()
.build()
// Assert
assertTrue(result.output.contains("Successfully generated code to"), "User friendly generate notice is missing.")
listOf(
"build/kotlin/.openapi-generator-ignore",
"build/kotlin/docs/PetsApi.md",
"build/kotlin/docs/Pets.md",
"build/kotlin/docs/Error.md",
"build/kotlin/docs/Pet.md",
"build/kotlin/README.md",
"build/kotlin/build.gradle",
"build/kotlin/.openapi-generator/VERSION",
"build/kotlin/settings.gradle",
"build/kotlin/src/main/kotlin/org/openapitools/example/model/Pets.kt",
"build/kotlin/src/main/kotlin/org/openapitools/example/model/Pet.kt",
"build/kotlin/src/main/kotlin/org/openapitools/example/model/Error.kt",
"build/kotlin/src/main/kotlin/org/openapitools/example/api/PetsApi.kt",
"build/kotlin/src/main/kotlin/org/openapitools/client/infrastructure/ApiClient.kt"
).map {
val f = File(temp, it)
assertTrue(f.exists() && f.isFile, "An expected file was not generated when invoking the generation.")
}
assertEquals(TaskOutcome.SUCCESS, result.task(":openApiGenerate")?.outcome,
"Expected a successful run, but found ${result.task(":openApiGenerate")?.outcome}")
}
}

View File

@@ -0,0 +1,38 @@
package org.openapitools.generator.gradle.plugin
import org.gradle.testkit.runner.GradleRunner
import org.gradle.testkit.runner.TaskOutcome
import org.testng.annotations.Test
import java.io.File
import kotlin.test.assertEquals
import kotlin.test.assertTrue
class GeneratorsTaskDslTest : TestBase() {
override var temp: File = createTempDir(javaClass.simpleName)
@Test
fun `openApiGenerators should list generators available to the user`() {
// Arrange
withProject("""
| plugins {
| id 'org.openapi.generator'
| }
""".trimMargin())
// Act
val result = GradleRunner.create()
.withProjectDir(temp)
.withArguments("openApiGenerators")
.withPluginClasspath()
.build()
// Assert
assertTrue(result.output.contains("The following generators are available:"), "User friendly generator notice is missing.")
assertTrue(result.output.contains("CLIENT generators:"), "Expected client generator header is missing.")
assertTrue(result.output.contains("android"), "Spot-checking listed client generators is missing a client generator.")
assertTrue(result.output.contains("SERVER generators:"), "Expected server generator header is missing.")
assertTrue(result.output.contains("kotlin-server"), "Spot-checking listed server generators is missing a server generator.")
assertEquals(TaskOutcome.SUCCESS, result.task(":openApiGenerators")?.outcome,
"Expected a successful run, but found ${result.task(":openApiGenerators")?.outcome}")
}
}

View File

@@ -0,0 +1,58 @@
package org.openapitools.generator.gradle.plugin
import org.gradle.testkit.runner.GradleRunner
import org.gradle.testkit.runner.TaskOutcome
import org.testng.annotations.Test
import java.io.File
import kotlin.test.assertEquals
import kotlin.test.assertTrue
class MetaTaskDslTest : TestBase() {
override var temp: File = createTempDir(javaClass.simpleName)
@Test
fun `openApiMeta should generate desired project contents`() {
// Arrange
val buildDirReplacement = "\$buildDir/meta"
withProject("""
| plugins {
| id 'org.openapi.generator'
| }
|
| openApiMeta {
| generatorName = "Sample"
| packageName = "org.openapitools.example"
| outputFolder = "$buildDirReplacement".toString()
| }
""".trimMargin())
// Act
val result = GradleRunner.create()
.withProjectDir(temp)
.withArguments("openApiMeta")
.withPluginClasspath()
.build()
// Assert
assertTrue(result.output.contains("Wrote file to"), "User friendly write notice is missing.")
// To avoid any OS-specific output causing issues with our stdout comparisons, only compare on expected filenames.
listOf(
"SampleGenerator.java",
"README.md",
"api.mustache",
"model.mustache",
"myFile.mustache",
"org.openapitools.codegen.CodegenConfig",
"pom.xml"
).map {
assertTrue(result.output.contains(it), "Expected $it to be listed in gradle stdout.")
}
assertEquals(
TaskOutcome.SUCCESS,
result.task(":openApiMeta")?.outcome,
"Expected a successful run, but found ${result.task(":openApiMeta")?.outcome}"
)
}
}

View File

@@ -0,0 +1,34 @@
package org.openapitools.generator.gradle.plugin
import org.testng.annotations.AfterMethod
import org.testng.annotations.BeforeMethod
import java.io.File
import java.io.InputStream
abstract class TestBase {
protected open lateinit var temp: File
@BeforeMethod
protected fun before() {
temp = createTempDir(javaClass.simpleName)
temp.deleteOnExit()
}
@AfterMethod
protected fun after(){
temp.deleteRecursively()
}
protected fun withProject(
buildContents: String,
projectFiles: Map<String, InputStream> = mapOf()
) {
val buildFile = File(temp,"build.gradle")
buildFile.writeText(buildContents)
projectFiles.forEach { entry ->
val target = File(temp, entry.key)
entry.value.copyTo(target.outputStream())
}
}
}

View File

@@ -0,0 +1,99 @@
package org.openapitools.generator.gradle.plugin
import org.gradle.testkit.runner.GradleRunner
import org.gradle.testkit.runner.TaskOutcome.FAILED
import org.gradle.testkit.runner.TaskOutcome.SUCCESS
import org.testng.annotations.Test
import java.io.File
import kotlin.test.assertEquals
import kotlin.test.assertTrue
class ValidateTaskDslTest : TestBase() {
override var temp: File = createTempDir(javaClass.simpleName)
@Test
fun `openApiValidate should fail on non-file spec`() {
// Arrange
withProject("""
| plugins {
| id 'org.openapi.generator'
| }
|
| openApiValidate {
| inputSpec = "some_location"
| }
""".trimMargin())
// Act
val result = GradleRunner.create()
.withProjectDir(temp)
.withArguments("openApiValidate")
.withPluginClasspath()
.buildAndFail()
// Assert
assertTrue(result.output.contains("unable to read location `some_location`"), "Unexpected/no message presented to the user for a spec pointing to an invalid URI.")
assertEquals(FAILED, result.task(":openApiValidate")?.outcome,
"Expected a failed run, but found ${result.task(":openApiValidate")?.outcome}")
}
@Test
fun `openApiValidate should succeed on valid spec`() {
// Arrange
val projectFiles = mapOf(
"spec.yaml" to javaClass.classLoader.getResourceAsStream("specs/petstore-v3.0.yaml")
)
withProject("""
| plugins {
| id 'org.openapi.generator'
| }
|
| openApiValidate {
| inputSpec = file("spec.yaml").absolutePath
| }
""".trimMargin(), projectFiles)
// Act
val result = GradleRunner.create()
.withProjectDir(temp)
.withArguments("openApiValidate")
.withPluginClasspath()
.build()
// Assert
assertTrue(result.output.contains("Spec is valid."), "Unexpected/no message presented to the user for a valid spec.")
assertEquals(SUCCESS, result.task(":openApiValidate")?.outcome,
"Expected a successful run, but found ${result.task(":openApiValidate")?.outcome}")
}
@Test
fun `openApiValidate should fail on invalid spec`() {
// Arrange
val projectFiles = mapOf(
"spec.yaml" to javaClass.classLoader.getResourceAsStream("specs/petstore-v3.0-invalid.yaml")
)
withProject("""
| plugins {
| id 'org.openapi.generator'
| }
|
| openApiValidate {
| inputSpec = file('spec.yaml').absolutePath
| }
""".trimMargin(), projectFiles)
// Act
val result = GradleRunner.create()
.withProjectDir(temp)
.withArguments("openApiValidate")
.withPluginClasspath()
.buildAndFail()
// Assert
assertTrue(result.output.contains("Spec is invalid."), "Unexpected/no message presented to the user for an invalid spec.")
assertEquals(FAILED, result.task(":openApiValidate")?.outcome,
"Expected a failed run, but found ${result.task(":openApiValidate")?.outcome}")
}
}

View File

@@ -0,0 +1,103 @@
openapi: "3.0.0"
servers:
- url: http://petstore.swagger.io/v1
paths:
/pets:
get:
summary: List all pets
operationId: listPets
tags:
- pets
parameters:
- name: limit
in: query
description: How many items to return at one time (max 100)
required: false
schema:
type: integer
format: int32
responses:
'200':
description: A paged array of pets
headers:
x-next:
description: A link to the next page of responses
schema:
type: string
content:
application/json:
schema:
$ref: "#/components/schemas/Pets"
default:
description: unexpected error
content:
application/json:
schema:
$ref: "#/components/schemas/Error"
post:
summary: Create a pet
tags:
- pets
responses:
'201':
description: Null response
default:
description: unexpected error
content:
application/json:
schema:
$ref: "#/components/schemas/Error"
/pets/{petId}:
get:
summary: Info for a specific pet
operationId: showPetById
tags:
- pets
parameters:
- name: petId
in: path
required: true
description: The id of the pet to retrieve
schema:
type: string
responses:
'200':
description: Expected response to a valid request
content:
application/json:
schema:
$ref: "#/components/schemas/Pets"
default:
description: unexpected error
content:
application/json:
schema:
$ref: "#/components/schemas/Error"
components:
schemas:
Pet:
required:
- id
- name
properties:
id:
type: integer
format: int64
name:
type: string
tag:
type: string
Pets:
type: array
items:
$ref: "#/components/schemas/Pet"
Error:
required:
- code
- message
properties:
code:
type: integer
format: int32
message:
type: string

View File

@@ -0,0 +1,109 @@
openapi: "3.0.0"
info:
version: 1.0.0
title: Swagger Petstore
license:
name: MIT
servers:
- url: http://petstore.swagger.io/v1
paths:
/pets:
get:
summary: List all pets
operationId: listPets
tags:
- pets
parameters:
- name: limit
in: query
description: How many items to return at one time (max 100)
required: false
schema:
type: integer
format: int32
responses:
'200':
description: A paged array of pets
headers:
x-next:
description: A link to the next page of responses
schema:
type: string
content:
application/json:
schema:
$ref: "#/components/schemas/Pets"
default:
description: unexpected error
content:
application/json:
schema:
$ref: "#/components/schemas/Error"
post:
summary: Create a pet
operationId: createPets
tags:
- pets
responses:
'201':
description: Null response
default:
description: unexpected error
content:
application/json:
schema:
$ref: "#/components/schemas/Error"
/pets/{petId}:
get:
summary: Info for a specific pet
operationId: showPetById
tags:
- pets
parameters:
- name: petId
in: path
required: true
description: The id of the pet to retrieve
schema:
type: string
responses:
'200':
description: Expected response to a valid request
content:
application/json:
schema:
$ref: "#/components/schemas/Pets"
default:
description: unexpected error
content:
application/json:
schema:
$ref: "#/components/schemas/Error"
components:
schemas:
Pet:
required:
- id
- name
properties:
id:
type: integer
format: int64
name:
type: string
tag:
type: string
Pets:
type: array
items:
$ref: "#/components/schemas/Pet"
Error:
required:
- code
- message
properties:
code:
type: integer
format: int32
message:
type: string

View File

@@ -181,5 +181,3 @@ compileTestKotlin {
jvmTarget = "1.8"
}
}
uploadArchives.dependsOn 'check'

View File

@@ -1,4 +1,4 @@
openApiGeneratorVersion=4.0.0-beta2
openApiGeneratorVersion=4.0.0-SNAPSHOT
# BEGIN placeholders
# these are just placeholders to allow contributors to build directly

View File

@@ -3,7 +3,7 @@
<parent>
<groupId>org.openapitools</groupId>
<artifactId>openapi-generator-project</artifactId>
<version>4.0.0-beta2</version>
<version>4.0.0-SNAPSHOT</version>
<relativePath>../..</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>

View File

@@ -44,13 +44,6 @@ openApiGenerate {
systemProperties = [
modelDocs: "false"
]
skipValidateSpec = true
logToStderr = true
generateAliasAsModel = false
// set to true and set environment variable {LANG}_POST_PROCESS_FILE
// (e.g. SCALA_POST_PROCESS_FILE) to the linter/formatter to be processed.
// This command will be passed one file at a time for most supported post processors.
enablePostProcessFile = false
}
task buildGoSdk(type: org.openapitools.generator.gradle.plugin.tasks.GenerateTask){

View File

@@ -121,10 +121,6 @@ class OpenApiGeneratorPlugin : Plugin<Project> {
generateApiDocumentation.set(generate.generateApiDocumentation)
withXml.set(generate.withXml)
configOptions.set(generate.configOptions)
logToStderr.set(generate.logToStderr)
enablePostProcessFile.set(generate.enablePostProcessFile)
skipValidateSpec.set(generate.skipValidateSpec)
generateAliasAsModel.set(generate.generateAliasAsModel)
}
}
}

View File

@@ -261,31 +261,6 @@ open class OpenApiGeneratorGenerateExtension(project: Project) {
*/
val withXml = project.objects.property<Boolean>()
/**
* To write all log messages (not just errors) to STDOUT
*/
val logToStderr = project.objects.property<Boolean>()
/**
* To enable the file post-processing hook. This enables executing an external post-processor (usually a linter program).
* This only enables the post-processor. To define the post-processing command, define an environment variable such as
* LANG_POST_PROCESS_FILE (e.g. GO_POST_PROCESS_FILE, SCALA_POST_PROCESS_FILE). Please open an issue if your target
* generator does not support this functionality.
*/
val enablePostProcessFile = project.objects.property<Boolean>()
/**
* To skip spec validation. When true, we will skip the default behavior of validating a spec before generation.
*/
val skipValidateSpec = project.objects.property<Boolean>()
/**
* To generate alias (array, list, map) as model. When false, top-level objects defined as array, list, or map will result in those
* definitions generated as top-level Array-of-items, List-of-items, Map-of-items definitions.
* When true, A model representation either containing or extending the array,list,map (depending on specific generator implementation) will be generated.
*/
val generateAliasAsModel = project.objects.property<Boolean>()
/**
* A map of options specific to a generator.
*/
@@ -307,9 +282,5 @@ open class OpenApiGeneratorGenerateExtension(project: Project) {
withXml.set(false)
configOptions.set(mapOf())
validateSpec.set(true)
logToStderr.set(false)
enablePostProcessFile.set(false)
skipValidateSpec.set(false)
generateAliasAsModel.set(false)
}
}

View File

@@ -318,36 +318,6 @@ open class GenerateTask : DefaultTask() {
@get:Internal
val withXml = project.objects.property<Boolean>()
/**
* To write all log messages (not just errors) to STDOUT
*/
@get:Internal
val logToStderr = project.objects.property<Boolean>()
/**
* To enable the file post-processing hook. This enables executing an external post-processor (usually a linter program).
* This only enables the post-processor. To define the post-processing command, define an environment variable such as
* LANG_POST_PROCESS_FILE (e.g. GO_POST_PROCESS_FILE, SCALA_POST_PROCESS_FILE). Please open an issue if your target
* generator does not support this functionality.
*/
@get:Internal
val enablePostProcessFile = project.objects.property<Boolean>()
/**
* To skip spec validation. When true, we will skip the default behavior of validating a spec before generation.
*/
@get:Internal
val skipValidateSpec = project.objects.property<Boolean>()
/**
* To generate alias (array, list, map) as model. When false, top-level objects defined as array, list, or map will result in those
* definitions generated as top-level Array-of-items, List-of-items, Map-of-items definitions.
* When true, A model representation either containing or extending the array,list,map (depending on specific generator implementation) will be generated.
*/
@get:Internal
val generateAliasAsModel = project.objects.property<Boolean>()
/**
* A dynamic map of options specific to a generator.
*/
@@ -502,22 +472,6 @@ open class GenerateTask : DefaultTask() {
configurator.removeOperationIdPrefix = value!!
}
logToStderr.ifNotEmpty { value ->
configurator.logToStderr = value
}
enablePostProcessFile.ifNotEmpty { value ->
configurator.enablePostProcessFile = value
}
skipValidateSpec.ifNotEmpty { value ->
configurator.setValidateSpec(value)
}
generateAliasAsModel.ifNotEmpty { value ->
configurator.setGenerateAliasAsModel(value)
}
if (systemProperties.isPresent) {
systemProperties.get().forEach { entry ->
configurator.addSystemProperty(entry.key, entry.value)

View File

@@ -48,12 +48,14 @@ class GenerateTaskDslTest : TestBase() {
listOf(
"build/kotlin/.openapi-generator-ignore",
"build/kotlin/docs/PetsApi.md",
"build/kotlin/docs/Pets.md",
"build/kotlin/docs/Error.md",
"build/kotlin/docs/Pet.md",
"build/kotlin/README.md",
"build/kotlin/build.gradle",
"build/kotlin/.openapi-generator/VERSION",
"build/kotlin/settings.gradle",
"build/kotlin/src/main/kotlin/org/openapitools/example/model/Pets.kt",
"build/kotlin/src/main/kotlin/org/openapitools/example/model/Pet.kt",
"build/kotlin/src/main/kotlin/org/openapitools/example/model/Error.kt",
"build/kotlin/src/main/kotlin/org/openapitools/example/api/PetsApi.kt",

View File

@@ -54,11 +54,6 @@ mvn clean compile
- `configOptions` - a map of language-specific parameters. To show a full list of generator-specified parameters (options), please use `configHelp` (explained below)
- `configHelp` - dumps the configuration help for the specified library (generates no sources)
- `ignoreFileOverride` - specifies the full path to a `.openapi-generator-ignore` used for pattern based overrides of generated outputs
- `removeOperationIdPrefix` - remove operationId prefix (e.g. user_getName => getName)
- `logToStderr` - write all log messages (not just errors) to STDOUT
- `enablePostProcessFile` - enable file post-processing hook
- `skipValidateSpec` - skip spec validation
- `generateAliasAsModel` - generate alias (array, map) as model
- `generateApis` - generate the apis (`true` by default)
- `generateApiTests` - generate the api tests (`true` by default. Only available if `generateApis` is `true`)
- `generateApiDocumentation` - generate the api documentation (`true` by default. Only available if `generateApis` is `true`)

View File

@@ -4,7 +4,7 @@
<parent>
<groupId>org.openapitools</groupId>
<artifactId>openapi-generator-project</artifactId>
<version>4.0.0-beta2</version>
<version>4.0.0-SNAPSHOT</version>
<relativePath>../..</relativePath>
</parent>
<artifactId>openapi-generator-maven-plugin</artifactId>

View File

@@ -145,6 +145,12 @@ public class CodeGenMojo extends AbstractMojo {
@Parameter(name = "skipOverwrite", required = false)
private Boolean skipOverwrite;
/**
* Specifies if the existing files should be overwritten during the generation.
*/
@Parameter(name = "removeOperationIdPrefix", required = false)
private Boolean removeOperationIdPrefix;
/**
* The package to use for generated api objects/classes
*/
@@ -205,36 +211,6 @@ public class CodeGenMojo extends AbstractMojo {
@Parameter(name = "ignoreFileOverride", required = false)
private String ignoreFileOverride;
/**
* To remove operationId prefix (e.g. user_getName => getName)
*/
@Parameter(name = "removeOperationIdPrefix", required = false)
private Boolean removeOperationIdPrefix;
/**
* To write all log messages (not just errors) to STDOUT
*/
@Parameter(name = "logToStderr", required = false)
private Boolean logToStderr;
/**
* To file post-processing hook
*/
@Parameter(name = "enablePostProcessFile", required = false)
private Boolean enablePostProcessFile;
/**
* To skip spec validation
*/
@Parameter(name = "skipValidateSpec", required = false)
private Boolean skipValidateSpec;
/**
* To generate alias (array, map) as model
*/
@Parameter(name = "generateAliasAsModel", required = false)
private Boolean generateAliasAsModel;
/**
* A map of language-specific parameters as passed with the -c option to the command line
*/
@@ -457,22 +433,6 @@ public class CodeGenMojo extends AbstractMojo {
configurator.setIgnoreFileOverride(ignoreFileOverride);
}
if (skipValidateSpec != null) {
configurator.setSkipOverwrite(skipValidateSpec);
}
if (logToStderr != null) {
configurator.setLogToStderr(logToStderr);
}
if (enablePostProcessFile != null) {
configurator.setEnablePostProcessFile(enablePostProcessFile);
}
if (generateAliasAsModel != null) {
configurator.setGenerateAliasAsModel(generateAliasAsModel);
}
// TODO: After 3.0.0 release (maybe for 3.1.0): Fully deprecate lang.
if (isNotEmpty(generatorName)) {
configurator.setGeneratorName(generatorName);

View File

@@ -3,7 +3,7 @@
<parent>
<groupId>org.openapitools</groupId>
<artifactId>openapi-generator-project</artifactId>
<version>4.0.0-beta2</version>
<version>4.0.0-SNAPSHOT</version>
<relativePath>../..</relativePath>
</parent>
<artifactId>openapi-generator-online</artifactId>

View File

@@ -3,7 +3,7 @@
<parent>
<groupId>org.openapitools</groupId>
<artifactId>openapi-generator-project</artifactId>
<version>4.0.0-beta2</version>
<version>4.0.0-SNAPSHOT</version>
<relativePath>../..</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>

View File

@@ -19,13 +19,14 @@ package config;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.util.Iterator;
import java.util.Map;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class ConfigParser {
private static final Logger LOGGER = LoggerFactory.getLogger(ConfigParser.class);

View File

@@ -17,24 +17,30 @@
package org.openapitools.codegen;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.Reader;
import java.io.Writer;
import java.util.Scanner;
import java.util.regex.Pattern;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.*;
import java.nio.file.Paths;
import java.util.Scanner;
import java.util.regex.Pattern;
public abstract class AbstractGenerator {
private static final Logger LOGGER = LoggerFactory.getLogger(AbstractGenerator.class);
@SuppressWarnings("static-method")
public File writeToFile(String filename, String contents) throws IOException {
LOGGER.info("writing file " + filename);
// Use Paths.get here to normalize path (for Windows file separator, space escaping on Linux/Mac, etc)
File output = Paths.get(filename).toFile();
File output = new File(filename);
if (output.getParent() != null && !new File(output.getParent()).exists()) {
File parent = new File(output.getParent());

View File

@@ -18,6 +18,7 @@
package org.openapitools.codegen;
import com.fasterxml.jackson.annotation.JsonIgnore;
import io.swagger.v3.parser.util.SchemaTypeUtil;
import java.util.LinkedHashMap;

View File

@@ -19,9 +19,8 @@ package org.openapitools.codegen;
import io.swagger.v3.oas.models.OpenAPI;
import io.swagger.v3.parser.core.models.AuthorizationValue;
import org.openapitools.codegen.auth.AuthParser;
import java.util.List;
import org.openapitools.codegen.auth.AuthParser;
public class ClientOptInput {
private CodegenConfig config;

View File

@@ -17,11 +17,11 @@
package org.openapitools.codegen;
import org.openapitools.codegen.auth.AuthMethod;
import java.util.HashMap;
import java.util.Map;
import org.openapitools.codegen.auth.AuthMethod;
public class ClientOpts {
protected String uri;
protected String target;

View File

@@ -18,6 +18,7 @@
package org.openapitools.codegen;
import com.samskivert.mustache.Mustache.Compiler;
import io.swagger.v3.oas.models.OpenAPI;
import io.swagger.v3.oas.models.Operation;
import io.swagger.v3.oas.models.media.Schema;
@@ -26,6 +27,7 @@ import io.swagger.v3.oas.models.servers.Server;
import io.swagger.v3.oas.models.servers.ServerVariable;
import java.io.File;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
@@ -109,9 +111,11 @@ public interface CodegenConfig {
void setOutputDir(String dir);
CodegenModel fromModel(String name, Schema schema);
CodegenModel fromModel(String name, Schema schema, Map<String, Schema> allDefinitions);
CodegenOperation fromOperation(String resourcePath, String httpMethod, Operation operation);
CodegenOperation fromOperation(String resourcePath, String httpMethod, Operation operation, Map<String, Schema> definitions, OpenAPI openAPI);
CodegenOperation fromOperation(String resourcePath, String httpMethod, Operation operation, Map<String, Schema> definitions);
List<CodegenSecurity> fromSecurity(Map<String, SecurityScheme> schemas);
@@ -175,6 +179,14 @@ public interface CodegenConfig {
Map<String, Object> postProcessModels(Map<String, Object> objs);
/**
* @deprecated use {@link #postProcessOperationsWithModels(Map, List)} instead. This method will be removed
* @param objs the objects map that will be passed to the templating engine
* @return the the objects map instance.
*/
@Deprecated
Map<String, Object> postProcessOperations(Map<String, Object> objs);
Map<String, Object> postProcessOperationsWithModels(Map<String, Object> objs, List<Object> allModels);
Map<String, Object> postProcessSupportingFileData(Map<String, Object> objs);
@@ -252,12 +264,11 @@ public interface CodegenConfig {
boolean isEnablePostProcessFile();
void setEnablePostProcessFile(boolean isEnablePostProcessFile);
public void setEnablePostProcessFile(boolean isEnablePostProcessFile);
/**
* Set the OpenAPI instance. This method needs to be called right after the instantiation of the Codegen class.
* @param openAPI specification being generated
*/
void setOpenAPI(OpenAPI openAPI);
// set OpenAPI and schemas
public void setGlobalOpenAPI(OpenAPI openAPI);
public void setGlobalSchemas(OpenAPI openAPI);
}

View File

@@ -17,12 +17,12 @@
package org.openapitools.codegen;
import static java.util.ServiceLoader.load;
import java.util.ArrayList;
import java.util.List;
import java.util.ServiceLoader;
import static java.util.ServiceLoader.load;
public class CodegenConfigLoader {
/**
* Tries to load config class with SPI first, then with class name directly from classpath

View File

@@ -284,9 +284,6 @@ public class CodegenConstants {
public static final String OPEN_API_SPEC_NAME = "openAPISpecName";
public static final String GENERATE_ALIAS_AS_MODEL = "generateAliasAsModel";
public static final String GENERATE_ALIAS_AS_MODEL_DESC = "Generate alias to map, array as models";
public static final String USE_COMPARE_NET_OBJECTS = "useCompareNetObjects";
public static final String USE_COMPARE_NET_OBJECTS_DESC = "Use KellermanSoftware.CompareNetObjects for deep recursive object comparison. WARNING: this option incurs potential performance impact.";
}

View File

@@ -2,10 +2,7 @@ package org.openapitools.codegen;
import org.apache.commons.lang3.builder.ToStringBuilder;
import java.util.LinkedHashSet;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.*;
public class CodegenDiscriminator {
private String propertyName;

View File

@@ -17,12 +17,13 @@
package org.openapitools.codegen;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import io.swagger.v3.oas.models.ExternalDocumentation;
import org.apache.commons.lang3.builder.ToStringBuilder;
import java.util.*;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import org.apache.commons.lang3.builder.ToStringBuilder;
@JsonIgnoreProperties({"parentModel", "interfaceModels"})
public class CodegenModel {
public String parent, parentSchema;

View File

@@ -20,7 +20,14 @@ package org.openapitools.codegen;
import io.swagger.v3.oas.models.ExternalDocumentation;
import io.swagger.v3.oas.models.tags.Tag;
import java.util.*;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
public class CodegenOperation {
public final List<CodegenProperty> responseHeaders = new ArrayList<CodegenProperty>();

View File

@@ -17,6 +17,8 @@
package org.openapitools.codegen;
import io.swagger.v3.oas.models.security.Scopes;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
@@ -25,11 +27,7 @@ import java.util.Map;
public class CodegenSecurity {
public String name;
public String type;
public String scheme;
public Boolean hasMore, isBasic, isOAuth, isApiKey;
// is Basic is true for all http authentication type. Those are to differentiate basic and bearer authentication
public Boolean isBasicBasic, isBasicBearer;
public String bearerFormat;
public Map<String, Object> vendorExtensions = new HashMap<String, Object>();
// ApiKey specific
public String keyParamName;
@@ -59,12 +57,6 @@ public class CodegenSecurity {
return false;
if (isBasic != null ? !isBasic.equals(that.isBasic) : that.isBasic != null)
return false;
if (isBasicBasic != null ? !isBasicBasic.equals(that.isBasicBasic) : that.isBasicBasic != null)
return false;
if (isBasicBearer != null ? !isBasicBearer.equals(that.isBasicBearer) : that.isBasicBearer != null)
return false;
if (bearerFormat != null ? !bearerFormat.equals(that.bearerFormat) : that.bearerFormat != null)
return false;
if (isOAuth != null ? !isOAuth.equals(that.isOAuth) : that.isOAuth != null)
return false;
if (isApiKey != null ? !isApiKey.equals(that.isApiKey) : that.isApiKey != null)
@@ -101,9 +93,6 @@ public class CodegenSecurity {
result = 31 * result + (type != null ? type.hashCode() : 0);
result = 31 * result + (hasMore != null ? hasMore.hashCode() : 0);
result = 31 * result + (isBasic != null ? isBasic.hashCode() : 0);
result = 31 * result + (isBasicBasic != null ? isBasicBasic.hashCode() : 0);
result = 31 * result + (isBasicBearer != null ? isBasicBearer.hashCode() : 0);
result = 31 * result + (bearerFormat != null ? bearerFormat.hashCode() : 0);
result = 31 * result + (isOAuth != null ? isOAuth.hashCode() : 0);
result = 31 * result + (isApiKey != null ? isApiKey.hashCode() : 0);
result = 31 * result + (vendorExtensions != null ? vendorExtensions.hashCode() : 0);

View File

@@ -20,14 +20,25 @@ package org.openapitools.codegen;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.google.common.base.CaseFormat;
import com.samskivert.mustache.Mustache.Compiler;
import io.swagger.v3.core.util.Json;
import io.swagger.v3.oas.models.OpenAPI;
import io.swagger.v3.oas.models.Operation;
import io.swagger.v3.oas.models.callbacks.Callback;
import io.swagger.v3.oas.models.examples.Example;
import io.swagger.v3.oas.models.headers.Header;
import io.swagger.v3.oas.models.media.*;
import io.swagger.v3.oas.models.parameters.*;
import io.swagger.v3.oas.models.media.ArraySchema;
import io.swagger.v3.oas.models.media.ComposedSchema;
import io.swagger.v3.oas.models.media.Content;
import io.swagger.v3.oas.models.media.MediaType;
import io.swagger.v3.oas.models.media.Schema;
import io.swagger.v3.oas.models.media.StringSchema;
import io.swagger.v3.oas.models.parameters.CookieParameter;
import io.swagger.v3.oas.models.parameters.HeaderParameter;
import io.swagger.v3.oas.models.parameters.Parameter;
import io.swagger.v3.oas.models.parameters.PathParameter;
import io.swagger.v3.oas.models.parameters.QueryParameter;
import io.swagger.v3.oas.models.parameters.RequestBody;
import io.swagger.v3.oas.models.responses.ApiResponse;
import io.swagger.v3.oas.models.responses.ApiResponses;
import io.swagger.v3.oas.models.security.OAuthFlow;
@@ -36,6 +47,7 @@ import io.swagger.v3.oas.models.security.SecurityScheme;
import io.swagger.v3.oas.models.servers.Server;
import io.swagger.v3.oas.models.servers.ServerVariable;
import io.swagger.v3.parser.util.SchemaTypeUtil;
import org.apache.commons.lang3.ObjectUtils;
import org.apache.commons.lang3.StringEscapeUtils;
import org.apache.commons.lang3.StringUtils;
@@ -49,14 +61,30 @@ import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.util.*;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.ListIterator;
import java.util.Locale;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;
import java.util.TreeSet;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import static org.openapitools.codegen.utils.StringUtils.*;
import static org.openapitools.codegen.utils.StringUtils.camelize;
import static org.openapitools.codegen.utils.StringUtils.underscore;
import static org.openapitools.codegen.utils.StringUtils.escape;
public class DefaultCodegen implements CodegenConfig {
private static final Logger LOGGER = LoggerFactory.getLogger(DefaultCodegen.class);
@@ -112,8 +140,9 @@ public class DefaultCodegen implements CodegenConfig {
// flag to indicate whether to use environment variable to post process file
protected boolean enablePostProcessFile = false;
// make openapi available to all methods
protected OpenAPI openAPI;
// make openapi and schemas available to all methods
protected OpenAPI globalOpenAPI;
protected Map<String, Schema> globalSchemas;
public List<CliOption> cliOptions() {
return cliOptions;
@@ -180,11 +209,6 @@ public class DefaultCodegen implements CodegenConfig {
this.setEnablePostProcessFile(Boolean.valueOf(additionalProperties
.get(CodegenConstants.ENABLE_POST_PROCESS_FILE).toString()));
}
if (additionalProperties.containsKey(CodegenConstants.GENERATE_ALIAS_AS_MODEL)) {
ModelUtils.setGenerateAliasAsModel(Boolean.valueOf(additionalProperties
.get(CodegenConstants.GENERATE_ALIAS_AS_MODEL).toString()));
}
}
// override with any special post-processing for all models
@@ -309,7 +333,7 @@ public class DefaultCodegen implements CodegenConfig {
enumVar.put("isString", isDataTypeString(cm.dataType));
enumVars.add(enumVar);
}
// if "x-enum-varnames" or "x-enum-descriptions" defined, update varnames
// if "x-enum-varnames" defined, update varnames
updateEnumVarsWithExtensions(enumVars, cm.getVendorExtensions());
cm.allowableValues.put("enumVars", enumVars);
}
@@ -417,9 +441,36 @@ public class DefaultCodegen implements CodegenConfig {
}
}
@Override
public void setOpenAPI(OpenAPI openAPI) {
this.openAPI = openAPI;
/**
* Set global OpenAPI based on OpenAPI object
*
* @param openAPI OpenAPI object
*/
public void setGlobalOpenAPI(OpenAPI openAPI) {
this.globalOpenAPI = openAPI;
}
/**
* Set global schema based on OpenAPI object
*
* @param openAPI OpenAPI object
*/
public void setGlobalSchemas(OpenAPI openAPI) {
if (openAPI != null && openAPI.getComponents() != null) {
this.globalSchemas = openAPI.getComponents().getSchemas();
}
if (this.globalSchemas == null) { // initalize with empty map if it's null
this.globalSchemas = new HashMap<String, Schema>();
}
}
// override with any special post-processing
@SuppressWarnings("static-method")
public Map<String, Object> postProcessOperations(Map<String, Object> objs) {
return objs;
}
// override with any special post-processing
@@ -1360,7 +1411,7 @@ public class DefaultCodegen implements CodegenConfig {
}
private String getSingleSchemaType(Schema schema) {
Schema unaliasSchema = ModelUtils.unaliasSchema(this.openAPI, schema);
Schema unaliasSchema = ModelUtils.unaliasSchema(globalSchemas, schema);
if (StringUtils.isNotBlank(unaliasSchema.get$ref())) { // reference to another definition/schema
// get the schema/model name from $ref
@@ -1449,15 +1500,14 @@ public class DefaultCodegen implements CodegenConfig {
}
/**
* Capitalize the string. Please use org.openapitools.codegen.utils.StringUtils.camelize instead as this method will be deprecated.
* Capitalize the string
*
* @param name string to be capitalized
* @return capitalized string
* @deprecated use {@link org.openapitools.codegen.utils.StringUtils#camelize(String)} instead
*/
@SuppressWarnings("static-method")
public String initialCaps(String name) {
return camelize(name);
return StringUtils.capitalize(name);
}
/**
@@ -1553,25 +1603,25 @@ public class DefaultCodegen implements CodegenConfig {
* @return capitalized model name
*/
public String toModelName(final String name) {
return initialCaps(modelNamePrefix + "_" + name + "_" + modelNameSuffix);
return initialCaps(modelNamePrefix + name + modelNameSuffix);
}
/**
* Convert OAS Model object to Codegen Model object
*
* @param name the name of the model
* @param schema OAS Model object
* @param name the name of the model
* @param schema OAS Model object
* @param allDefinitions a map of all OAS models from the spec
* @return Codegen Model object
*/
public CodegenModel fromModel(String name, Schema schema) {
Map<String, Schema> allDefinitions = ModelUtils.getSchemas(this.openAPI);
public CodegenModel fromModel(String name, Schema schema, Map<String, Schema> allDefinitions) {
if (typeAliases == null) {
// Only do this once during first call
typeAliases = getAllAliases(allDefinitions);
}
// unalias schema
schema = ModelUtils.unaliasSchema(this.openAPI, schema);
schema = ModelUtils.unaliasSchema(allDefinitions, schema);
if (schema == null) {
LOGGER.warn("Schema {} not found", name);
return null;
@@ -1596,7 +1646,7 @@ public class DefaultCodegen implements CodegenConfig {
m.getVendorExtensions().putAll(schema.getExtensions());
}
m.isAlias = typeAliases.containsKey(name);
m.discriminator = createDiscriminator(name, schema);
m.discriminator = createDiscriminator(name, schema, allDefinitions);
if (schema.getXml() != null) {
m.xmlPrefix = schema.getXml().getPrefix();
@@ -1629,7 +1679,7 @@ public class DefaultCodegen implements CodegenConfig {
for (Schema innerSchema : composed.getAllOf()) { // TOOD need to work with anyOf, oneOf as well
if (m.discriminator == null) {
LOGGER.debug("discriminator is set to null (not correctly set earlier): {}", name);
m.discriminator = createDiscriminator(name, schema);
m.discriminator = createDiscriminator(name, schema, allDefinitions);
}
if (innerSchema.getXml() != null) {
@@ -1668,13 +1718,13 @@ public class DefaultCodegen implements CodegenConfig {
if (allDefinitions != null && refSchema != null) {
if (allParents.contains(modelName) && supportsMultipleInheritance) {
// multiple inheritance
addProperties(allProperties, allRequired, refSchema);
addProperties(allProperties, allRequired, refSchema, allDefinitions);
} else if (parentName != null && parentName.equals(modelName) && supportsInheritance) {
// single inheritance
addProperties(allProperties, allRequired, refSchema);
addProperties(allProperties, allRequired, refSchema, allDefinitions);
} else {
// composition
addProperties(properties, required, refSchema);
addProperties(properties, required, refSchema, allDefinitions);
}
}
@@ -1711,16 +1761,16 @@ public class DefaultCodegen implements CodegenConfig {
if (component.get$ref() == null) {
if (component != null) {
// component is the child schema
addProperties(properties, required, component);
addProperties(properties, required, component, allDefinitions);
// includes child's properties (all, required) in allProperties, allRequired
addProperties(allProperties, allRequired, component);
addProperties(allProperties, allRequired, component, allDefinitions);
}
break; // at most one child only
}
}
addVars(m, unaliasPropertySchema(properties), required, unaliasPropertySchema(allProperties), allRequired);
addVars(m, unaliasPropertySchema(allDefinitions, properties), required, unaliasPropertySchema(allDefinitions, allProperties), allRequired);
// end of code block for composed schema
} else {
@@ -1745,7 +1795,7 @@ public class DefaultCodegen implements CodegenConfig {
}
// passing null to allProperties and allRequired as there's no parent
addVars(m, unaliasPropertySchema(schema.getProperties()), schema.getRequired(), null, null);
addVars(m, unaliasPropertySchema(allDefinitions, schema.getProperties()), schema.getRequired(), null, null);
}
// remove duplicated properties
@@ -1761,7 +1811,8 @@ public class DefaultCodegen implements CodegenConfig {
return m;
}
private CodegenDiscriminator createDiscriminator(String schemaName, Schema schema) {
private CodegenDiscriminator createDiscriminator(String schemaName, Schema
schema, Map<String, Schema> allDefinitions) {
if (schema.getDiscriminator() == null) {
return null;
}
@@ -1771,10 +1822,12 @@ public class DefaultCodegen implements CodegenConfig {
if (schema.getDiscriminator().getMapping() != null && !schema.getDiscriminator().getMapping().isEmpty()) {
for (Entry<String, String> e : schema.getDiscriminator().getMapping().entrySet()) {
String name = toModelName(ModelUtils.getSimpleRef(e.getValue())); // e.g e.getValue => #/components/schemas/Dog
if (allDefinitions.get(name) == null) {
LOGGER.warn("Discriminator's mapping: model {} (mapped to {}) couldn't be found", name, e.getKey());
}
discriminator.getMappedModels().add(new MappedModel(e.getKey(), name));
}
} else {
Map<String, Schema> allDefinitions = ModelUtils.getSchemas(this.openAPI);
allDefinitions.forEach((childName, child) -> {
if (child instanceof ComposedSchema && ((ComposedSchema) child).getAllOf() != null) {
Set<String> parentSchemas = ((ComposedSchema) child).getAllOf().stream()
@@ -1782,7 +1835,7 @@ public class DefaultCodegen implements CodegenConfig {
.map(s -> ModelUtils.getSimpleRef(s.get$ref()))
.collect(Collectors.toSet());
if (parentSchemas.contains(schemaName)) {
discriminator.getMappedModels().add(new MappedModel(childName, toModelName(childName)));
discriminator.getMappedModels().add(new MappedModel(childName, childName));
}
}
});
@@ -1800,29 +1853,30 @@ public class DefaultCodegen implements CodegenConfig {
* @param properties all properties
* @param required required property only
* @param schema schema in which the properties will be added to the lists
* @param allSchemas all schemas
*/
protected void addProperties(Map<String, Schema> properties, List<String> required, Schema schema) {
protected void addProperties(Map<String, Schema> properties, List<String> required, Schema
schema, Map<String, Schema> allSchemas) {
if (schema instanceof ComposedSchema) {
throw new RuntimeException("Please report the issue: Cannot process Composed Schema in addProperties: " + schema);
/*
ComposedSchema composedSchema = (ComposedSchema) schema;
if (composedSchema.getAllOf() == null) {
return;
}
for (Schema component : composedSchema.getAllOf()) {
addProperties(properties, required, component);
addProperties(properties, required, component, allSchemas);
}
if (composedSchema.getOneOf() != null) {
throw new RuntimeException("Please report the issue: Cannot process oneOf (Composed Scheme) in addProperties: " + schema);
}
if (composedSchema.getAnyOf() != null) {
throw new RuntimeException("Please report the issue: Cannot process anyOf (Composed Schema) in addProperties: " + schema);
}
return;
*/
}
Schema unaliasSchema = ModelUtils.unaliasSchema(globalSchemas, schema);
if (StringUtils.isNotBlank(schema.get$ref())) {
Schema interfaceSchema = ModelUtils.getReferencedSchema(this.openAPI, schema);
addProperties(properties, required, interfaceSchema);
Schema interfaceSchema = allSchemas.get(ModelUtils.getSimpleRef(schema.get$ref()));
addProperties(properties, required, interfaceSchema, allSchemas);
return;
}
if (schema.getProperties() != null) {
@@ -1862,7 +1916,7 @@ public class DefaultCodegen implements CodegenConfig {
LOGGER.debug("debugging fromProperty for " + name + " : " + p);
// unalias schema
p = ModelUtils.unaliasSchema(this.openAPI, p);
p = ModelUtils.unaliasSchema(globalSchemas, p);
CodegenProperty property = CodegenModelFactory.newInstance(CodegenModelType.PROPERTY);
property.name = toVarName(name);
@@ -1927,17 +1981,57 @@ public class DefaultCodegen implements CodegenConfig {
if (property.minimum != null || property.maximum != null)
property.hasValidation = true;
// legacy support
Map<String, Object> allowableValues = new HashMap<String, Object>();
if (p.getEnum() != null) {
List<Object> _enum = p.getEnum();
property._enum = new ArrayList<String>();
for (Object i : _enum) {
property._enum.add(String.valueOf(i));
}
property.isEnum = true;
allowableValues.put("values", _enum);
}
if (allowableValues.size() > 0) {
property.allowableValues = allowableValues;
}
} else if (ModelUtils.isBooleanSchema(p)) { // boolean type
property.isBoolean = true;
property.getter = toBooleanGetter(name);
} else if (ModelUtils.isDateSchema(p)) { // date format
property.isString = false; // for backward compatibility with 2.x
property.isDate = true;
if (p.getEnum() != null) {
List<String> _enum = p.getEnum();
property._enum = new ArrayList<String>();
for (String i : _enum) {
property._enum.add(i);
}
property.isEnum = true;
// legacy support
Map<String, Object> allowableValues = new HashMap<String, Object>();
allowableValues.put("values", _enum);
property.allowableValues = allowableValues;
}
} else if (ModelUtils.isDateTimeSchema(p)) { // date-time format
property.isString = false; // for backward compatibility with 2.x
property.isDateTime = true;
if (p.getEnum() != null) {
List<String> _enum = p.getEnum();
property._enum = new ArrayList<String>();
for (String i : _enum) {
property._enum.add(i);
}
property.isEnum = true;
// legacy support
Map<String, Object> allowableValues = new HashMap<String, Object>();
allowableValues.put("values", _enum);
property.allowableValues = allowableValues;
}
} else if (ModelUtils.isStringSchema(p)) {
if (ModelUtils.isByteArraySchema(p)) {
property.isByteArray = true;
@@ -1965,6 +2059,16 @@ public class DefaultCodegen implements CodegenConfig {
if (property.pattern != null || property.minLength != null || property.maxLength != null)
property.hasValidation = true;
if (p.getEnum() != null) {
List<String> _enum = p.getEnum();
property._enum = _enum;
property.isEnum = true;
// legacy support
Map<String, Object> allowableValues = new HashMap<String, Object>();
allowableValues.put("values", _enum);
property.allowableValues = allowableValues;
}
} else if (ModelUtils.isNumberSchema(p)) {
property.isNumeric = Boolean.TRUE;
if (ModelUtils.isFloatSchema(p)) { // float
@@ -1993,37 +2097,23 @@ public class DefaultCodegen implements CodegenConfig {
if (property.minimum != null || property.maximum != null)
property.hasValidation = true;
} else if (ModelUtils.isFreeFormObject(p)) {
if (p.getEnum() != null && !p.getEnum().isEmpty()) {
List<Object> _enum = p.getEnum();
property._enum = new ArrayList<String>();
for (Object i : _enum) {
property._enum.add(String.valueOf(i));
}
property.isEnum = true;
// legacy support
Map<String, Object> allowableValues = new HashMap<String, Object>();
allowableValues.put("values", _enum);
property.allowableValues = allowableValues;
}
} else if (ModelUtils.isFreeFormObject(p)){
property.isFreeFormObject = true;
}
//Inline enum case:
if (p.getEnum() != null && !p.getEnum().isEmpty()) {
List<Object> _enum = p.getEnum();
property._enum = new ArrayList<String>();
for (Object i : _enum) {
property._enum.add(String.valueOf(i));
}
property.isEnum = true;
Map<String, Object> allowableValues = new HashMap<String, Object>();
allowableValues.put("values", _enum);
if (allowableValues.size() > 0) {
property.allowableValues = allowableValues;
}
}
//Referenced enum case:
Schema r = ModelUtils.getReferencedSchema(this.openAPI, p);
if (r.getEnum() != null && !r.getEnum().isEmpty()) {
List<Object> _enum = r.getEnum();
Map<String, Object> allowableValues = new HashMap<String, Object>();
allowableValues.put("values", _enum);
if (allowableValues.size() > 0) {
property.allowableValues = allowableValues;
}
}
property.dataType = getTypeDeclaration(p);
property.dataFormat = p.getFormat();
property.baseType = getSchemaType(p);
@@ -2058,7 +2148,7 @@ public class DefaultCodegen implements CodegenConfig {
if (itemName == null) {
itemName = property.name;
}
Schema innerSchema = ModelUtils.unaliasSchema(this.openAPI, ((ArraySchema) p).getItems());
Schema innerSchema = ModelUtils.unaliasSchema(globalSchemas, ((ArraySchema) p).getItems());
CodegenProperty cp = fromProperty(itemName, innerSchema);
updatePropertyForArray(property, cp);
} else if (ModelUtils.isMapSchema(p)) {
@@ -2070,7 +2160,7 @@ public class DefaultCodegen implements CodegenConfig {
property.maxItems = p.getMaxProperties();
// handle inner property
Schema innerSchema = ModelUtils.unaliasSchema(this.openAPI, ModelUtils.getAdditionalProperties(p));
Schema innerSchema = ModelUtils.unaliasSchema(globalSchemas, ModelUtils.getAdditionalProperties(p));
CodegenProperty cp = fromProperty("inner", innerSchema);
updatePropertyForMap(property, cp);
} else if (ModelUtils.isFreeFormObject(p)) {
@@ -2272,21 +2362,38 @@ public class DefaultCodegen implements CodegenConfig {
}
/**
* Convert OAS Operation object to Codegen Operation object
* Convert OAS Operation object to Codegen Operation object (without providing a OAS object)
*
* @param path the path of the operation
* @param httpMethod HTTP method
* @param operation OAS operation object
* @param schemas a map of OAS models
* @return Codegen Operation object
*/
public CodegenOperation fromOperation(String path, String httpMethod, Operation
operation, Map<String, Schema> schemas) {
return fromOperation(path, httpMethod, operation, schemas, null);
}
/**
* Convert OAS Operation object to Codegen Operation object
*
* @param path the path of the operation
* @param httpMethod HTTP method
* @param operation OAS operation object
* @param schemas a map of OAS models
* @param openAPI a OAS object representing the spec
* @return Codegen Operation object
*/
public CodegenOperation fromOperation(String path,
String httpMethod,
Operation operation) {
Operation operation,
Map<String, Schema> schemas,
OpenAPI openAPI) {
LOGGER.debug("fromOperation => operation: " + operation);
if (operation == null)
throw new RuntimeException("operation cannot be null in fromOperation");
Map<String, Schema> schemas = ModelUtils.getSchemas(this.openAPI);
CodegenOperation op = CodegenModelFactory.newInstance(CodegenModelType.OPERATION);
Set<String> imports = new HashSet<String>();
if (operation.getExtensions() != null && !operation.getExtensions().isEmpty()) {
@@ -2324,14 +2431,14 @@ public class DefaultCodegen implements CodegenConfig {
op.isDeprecated = operation.getDeprecated();
}
addConsumesInfo(operation, op);
addConsumesInfo(openAPI, operation, op);
if (operation.getResponses() != null && !operation.getResponses().isEmpty()) {
ApiResponse methodResponse = findMethodResponse(operation.getResponses());
for (String key : operation.getResponses().keySet()) {
ApiResponse response = operation.getResponses().get(key);
addProducesInfo(response, op);
CodegenResponse r = fromResponse(key, response);
addProducesInfo(openAPI, response, op);
CodegenResponse r = fromResponse(openAPI, key, response);
r.hasMore = true;
if (r.baseType != null &&
!defaultIncludes.contains(r.baseType) &&
@@ -2350,7 +2457,7 @@ public class DefaultCodegen implements CodegenConfig {
op.responses.get(op.responses.size() - 1).hasMore = false;
if (methodResponse != null) {
Schema responseSchema = ModelUtils.unaliasSchema(this.openAPI, ModelUtils.getSchemaFromResponse(methodResponse));
Schema responseSchema = ModelUtils.unaliasSchema(globalSchemas, ModelUtils.getSchemaFromResponse(methodResponse));
if (responseSchema != null) {
CodegenProperty cm = fromProperty("response", responseSchema);
@@ -2377,16 +2484,18 @@ public class DefaultCodegen implements CodegenConfig {
exampleStatusCode = key;
}
}
op.examples = new ExampleGenerator(schemas, this.openAPI).generateFromResponseSchema(exampleStatusCode, responseSchema, getProducesInfo(this.openAPI, operation));
op.examples = new ExampleGenerator(schemas, openAPI).generateFromResponseSchema(exampleStatusCode, responseSchema, getProducesInfo(openAPI, operation));
op.defaultResponse = toDefaultValue(responseSchema);
op.returnType = cm.dataType;
op.hasReference = schemas.containsKey(op.returnBaseType);
op.hasReference = schemas != null && schemas.containsKey(op.returnBaseType);
// lookup discriminator
Schema schema = schemas.get(op.returnBaseType);
if (schema != null) {
CodegenModel cmod = fromModel(op.returnBaseType, schema);
op.discriminator = cmod.discriminator;
if (schemas != null) {
Schema schema = schemas.get(op.returnBaseType);
if (schema != null) {
CodegenModel cmod = fromModel(op.returnBaseType, schema, schemas);
op.discriminator = cmod.discriminator;
}
}
if (cm.isContainer) {
@@ -2405,13 +2514,13 @@ public class DefaultCodegen implements CodegenConfig {
op.returnTypeIsPrimitive = true;
}
}
addHeaders(methodResponse, op.responseHeaders);
addHeaders(openAPI, methodResponse, op.responseHeaders);
}
}
if (operation.getCallbacks() != null && !operation.getCallbacks().isEmpty()) {
operation.getCallbacks().forEach((name, callback) -> {
CodegenCallback c = fromCallback(name, callback);
CodegenCallback c = fromCallback(name, callback, schemas, openAPI);
c.hasMore = true;
op.callbacks.add(c);
});
@@ -2435,7 +2544,7 @@ public class DefaultCodegen implements CodegenConfig {
if ("application/x-www-form-urlencoded".equalsIgnoreCase(getContentType(requestBody)) ||
"multipart/form-data".equalsIgnoreCase(getContentType(requestBody))) {
// process form parameters
formParams = fromRequestBodyToFormParameters(requestBody, imports);
formParams = fromRequestBodyToFormParameters(requestBody, schemas, imports);
for (CodegenParameter cp : formParams) {
postProcessParameter(cp);
}
@@ -2447,13 +2556,13 @@ public class DefaultCodegen implements CodegenConfig {
}
} else {
// process body parameter
requestBody = ModelUtils.getReferencedRequestBody(this.openAPI, requestBody);
requestBody = ModelUtils.getReferencedRequestBody(openAPI, requestBody);
String bodyParameterName = "";
if (op.vendorExtensions != null && op.vendorExtensions.containsKey("x-codegen-request-body-name")) {
bodyParameterName = (String) op.vendorExtensions.get("x-codegen-request-body-name");
}
bodyParam = fromRequestBody(requestBody, imports, bodyParameterName);
bodyParam = fromRequestBody(requestBody, schemas, imports, bodyParameterName);
bodyParam.description = escapeText(requestBody.getDescription());
postProcessParameter(bodyParam);
@@ -2465,14 +2574,16 @@ public class DefaultCodegen implements CodegenConfig {
// add example
if (schemas != null) {
op.requestBodyExamples = new ExampleGenerator(schemas, this.openAPI).generate(null, new ArrayList<String>(getConsumesInfo(this.openAPI, operation)), bodyParam.baseType);
op.requestBodyExamples = new ExampleGenerator(schemas, openAPI).generate(null, new ArrayList<String>(getConsumesInfo(openAPI, operation)), bodyParam.baseType);
}
}
}
if (parameters != null) {
for (Parameter param : parameters) {
param = ModelUtils.getReferencedParameter(this.openAPI, param);
if (StringUtils.isNotBlank(param.get$ref())) {
param = getParameterFromRef(param.get$ref(), openAPI);
}
CodegenParameter p = fromParameter(param, imports);
@@ -2589,11 +2700,12 @@ public class DefaultCodegen implements CodegenConfig {
/**
* Convert OAS Response object to Codegen Response object
*
* @param openAPI a OAS object representing the spec
* @param responseCode HTTP response code
* @param response OAS Response object
* @return Codegen Response object
*/
public CodegenResponse fromResponse(String responseCode, ApiResponse response) {
public CodegenResponse fromResponse(OpenAPI openAPI, String responseCode, ApiResponse response) {
CodegenResponse r = CodegenModelFactory.newInstance(CodegenModelType.RESPONSE);
if ("default".equals(responseCode)) {
r.code = "0";
@@ -2601,8 +2713,8 @@ public class DefaultCodegen implements CodegenConfig {
r.code = responseCode;
}
Schema responseSchema;
if (this.openAPI != null && this.openAPI.getComponents() != null) {
responseSchema = ModelUtils.unaliasSchema(this.openAPI, ModelUtils.getSchemaFromResponse(response));
if (openAPI != null && openAPI.getComponents() != null) {
responseSchema = ModelUtils.unaliasSchema(openAPI.getComponents().getSchemas(), ModelUtils.getSchemaFromResponse(response));
} else { // no model/alias defined
responseSchema = ModelUtils.getSchemaFromResponse(response);
}
@@ -2615,7 +2727,7 @@ public class DefaultCodegen implements CodegenConfig {
if (response.getExtensions() != null && !response.getExtensions().isEmpty()) {
r.vendorExtensions.putAll(response.getExtensions());
}
addHeaders(response, r.headers);
addHeaders(openAPI, response, r.headers);
r.hasHeaders = !r.headers.isEmpty();
if (r.schema != null) {
@@ -2707,9 +2819,12 @@ public class DefaultCodegen implements CodegenConfig {
*
* @param name callback name
* @param callback OAS Callback object
* @param schemas a map of OAS models
* @param openAPI a OAS object representing the spec
* @return Codegen Response object
*/
public CodegenCallback fromCallback(String name, Callback callback) {
public CodegenCallback fromCallback(String name, Callback callback, Map<String, Schema> schemas, OpenAPI
openAPI) {
CodegenCallback c = new CodegenCallback();
c.name = name;
@@ -2751,7 +2866,7 @@ public class DefaultCodegen implements CodegenConfig {
// distinguish between normal operations and callback requests
op.getExtensions().put("x-callback-request", true);
CodegenOperation co = fromOperation(expression, method, op);
CodegenOperation co = fromOperation(expression, method, op, schemas, openAPI);
if (genId) {
co.operationIdOriginal = null;
// legacy (see `fromOperation()`)
@@ -2800,7 +2915,7 @@ public class DefaultCodegen implements CodegenConfig {
}
if (parameter.getSchema() != null) {
Schema parameterSchema = ModelUtils.unaliasSchema(this.openAPI, parameter.getSchema());
Schema parameterSchema = ModelUtils.unaliasSchema(globalSchemas, parameter.getSchema());
if (parameterSchema == null) {
LOGGER.warn("warning! Schema not found for parameter \"" + parameter.getName() + "\", using String");
parameterSchema = new StringSchema().description("//TODO automatically added by openapi-generator due to missing type definition.");
@@ -3107,8 +3222,6 @@ public class DefaultCodegen implements CodegenConfig {
cs.name = key;
cs.type = securityScheme.getType().toString();
cs.isCode = cs.isPassword = cs.isApplication = cs.isImplicit = false;
cs.isBasicBasic = cs.isBasicBearer = false;
cs.scheme = securityScheme.getScheme();
if (SecurityScheme.Type.APIKEY.equals(securityScheme.getType())) {
cs.isBasic = cs.isOAuth = false;
@@ -3120,12 +3233,6 @@ public class DefaultCodegen implements CodegenConfig {
} else if (SecurityScheme.Type.HTTP.equals(securityScheme.getType())) {
cs.isKeyInHeader = cs.isKeyInQuery = cs.isKeyInCookie = cs.isApiKey = cs.isOAuth = false;
cs.isBasic = true;
if ("basic".equals(securityScheme.getScheme())) {
cs.isBasicBasic = true;
} else if ("bearer".equals(securityScheme.getScheme())) {
cs.isBasicBearer = true;
cs.bearerFormat = securityScheme.getBearerFormat();
}
} else if (SecurityScheme.Type.OAUTH2.equals(securityScheme.getType())) {
cs.isKeyInHeader = cs.isKeyInQuery = cs.isKeyInCookie = cs.isApiKey = cs.isBasic = false;
cs.isOAuth = true;
@@ -3254,12 +3361,12 @@ public class DefaultCodegen implements CodegenConfig {
* @param response API response
* @param properties list of codegen property
*/
private void addHeaders(ApiResponse response, List<CodegenProperty> properties) {
private void addHeaders(OpenAPI openAPI, ApiResponse response, List<CodegenProperty> properties) {
if (response.getHeaders() != null) {
for (Map.Entry<String, Header> headers : response.getHeaders().entrySet()) {
String description = headers.getValue().getDescription();
// follow the $ref
Header header = ModelUtils.getReferencedHeader(this.openAPI, headers.getValue());
Header header = ModelUtils.getReferencedHeader(openAPI, headers.getValue());
CodegenProperty cp = fromProperty(headers.getKey(), header.getSchema());
cp.setDescription(escapeText(description));
@@ -3368,13 +3475,15 @@ public class DefaultCodegen implements CodegenConfig {
/**
* Loop through propertiies and unalias the reference if $ref (reference) is defined
*
* @param allSchemas all schemas defined in the spec
* @param properties model properties (schemas)
* @return model properties with direct reference to schemas
*/
private Map<String, Schema> unaliasPropertySchema(Map<String, Schema> properties) {
private Map<String, Schema> unaliasPropertySchema
(Map<String, Schema> allSchemas, Map<String, Schema> properties) {
if (properties != null) {
for (String key : properties.keySet()) {
properties.put(key, ModelUtils.unaliasSchema(this.openAPI, properties.get(key)));
properties.put(key, ModelUtils.unaliasSchema(allSchemas, properties.get(key)));
}
}
@@ -3917,9 +4026,6 @@ public class DefaultCodegen implements CodegenConfig {
if (Boolean.TRUE.equals(property.isFile)) {
parameter.isFile = true;
}
if (Boolean.TRUE.equals(property.isModel)) {
parameter.isModel = true;
}
}
@@ -3967,7 +4073,7 @@ public class DefaultCodegen implements CodegenConfig {
enumVar.put("isString", isDataTypeString(dataType));
enumVars.add(enumVar);
}
// if "x-enum-varnames" or "x-enum-descriptions" defined, update varnames
// if "x-enum-varnames" defined, update varnames
Map<String, Object> extensions = var.mostInnerItems != null ? var.mostInnerItems.getVendorExtensions() : var.getVendorExtensions();
updateEnumVarsWithExtensions(enumVars, extensions);
allowableValues.put("enumVars", enumVars);
@@ -3987,19 +4093,13 @@ public class DefaultCodegen implements CodegenConfig {
}
}
private void updateEnumVarsWithExtensions(List<Map<String, Object>> enumVars, Map<String, Object> vendorExtensions) {
if (vendorExtensions != null) {
updateEnumVarsWithExtensions(enumVars, vendorExtensions, "x-enum-varnames", "name");
updateEnumVarsWithExtensions(enumVars, vendorExtensions, "x-enum-descriptions", "enumDescription");
}
}
private void updateEnumVarsWithExtensions(List<Map<String, Object>> enumVars, Map<String, Object> vendorExtensions, String extensionKey, String key) {
if (vendorExtensions.containsKey(extensionKey)) {
List<String> values = (List<String>) vendorExtensions.get(extensionKey);
int size = Math.min(enumVars.size(), values.size());
private void updateEnumVarsWithExtensions
(List<Map<String, Object>> enumVars, Map<String, Object> vendorExtensions) {
if (vendorExtensions != null && vendorExtensions.containsKey("x-enum-varnames")) {
List<String> alias = (List<String>) vendorExtensions.get("x-enum-varnames");
int size = Math.min(enumVars.size(), alias.size());
for (int i = 0; i < size; i++) {
enumVars.get(i).put(key, values.get(i));
enumVars.get(i).put("name", alias.get(i));
}
}
}
@@ -4082,6 +4182,12 @@ public class DefaultCodegen implements CodegenConfig {
return new ArrayList<>(requestBody.getContent().keySet()).get(0);
}
protected Parameter getParameterFromRef(String ref, OpenAPI openAPI) {
String parameterName = ref.substring(ref.lastIndexOf('/') + 1);
Map<String, Parameter> parameterMap = openAPI.getComponents().getParameters();
return parameterMap.get(parameterName);
}
private void setOauth2Info(CodegenSecurity codegenSecurity, OAuthFlow flow) {
codegenSecurity.authorizationUrl = flow.getAuthorizationUrl();
codegenSecurity.tokenUrl = flow.getTokenUrl();
@@ -4107,8 +4213,8 @@ public class DefaultCodegen implements CodegenConfig {
}
}
private void addConsumesInfo(Operation operation, CodegenOperation codegenOperation) {
RequestBody requestBody = ModelUtils.getReferencedRequestBody(this.openAPI, operation.getRequestBody());
private void addConsumesInfo(OpenAPI openAPI, Operation operation, CodegenOperation codegenOperation) {
RequestBody requestBody = ModelUtils.getReferencedRequestBody(openAPI, operation.getRequestBody());
if (requestBody == null || requestBody.getContent() == null || requestBody.getContent().isEmpty()) {
return;
}
@@ -4176,8 +4282,8 @@ public class DefaultCodegen implements CodegenConfig {
return ModelUtils.getReferencedSchema(openAPI, schema) != null;
}
private void addProducesInfo(ApiResponse inputResponse, CodegenOperation codegenOperation) {
ApiResponse response = ModelUtils.getReferencedApiResponse(this.openAPI, inputResponse);
private void addProducesInfo(OpenAPI openAPI, ApiResponse inputResponse, CodegenOperation codegenOperation) {
ApiResponse response = ModelUtils.getReferencedApiResponse(openAPI, inputResponse);
if (response == null || response.getContent() == null || response.getContent().isEmpty()) {
return;
}
@@ -4274,11 +4380,14 @@ public class DefaultCodegen implements CodegenConfig {
return null;
}
public List<CodegenParameter> fromRequestBodyToFormParameters(RequestBody body, Set<String> imports) {
public List<CodegenParameter> fromRequestBodyToFormParameters(RequestBody
body, Map<String, Schema> schemas, Set<String> imports) {
List<CodegenParameter> parameters = new ArrayList<CodegenParameter>();
LOGGER.debug("debugging fromRequestBodyToFormParameters= " + body);
Schema schema = ModelUtils.getSchemaFromRequestBody(body);
schema = ModelUtils.getReferencedSchema(this.openAPI, schema);
if (StringUtils.isNotBlank(schema.get$ref())) {
schema = schemas.get(ModelUtils.getSimpleRef(schema.get$ref()));
}
if (schema.getProperties() != null && !schema.getProperties().isEmpty()) {
Map<String, Schema> properties = schema.getProperties();
for (Map.Entry<String, Schema> entry : properties.entrySet()) {
@@ -4428,7 +4537,8 @@ public class DefaultCodegen implements CodegenConfig {
return codegenParameter;
}
public CodegenParameter fromRequestBody(RequestBody body, Set<String> imports, String bodyParameterName) {
public CodegenParameter fromRequestBody(RequestBody
body, Map<String, Schema> schemas, Set<String> imports, String bodyParameterName) {
if (body == null) {
LOGGER.error("body in fromRequestBody cannot be null!");
}
@@ -4442,14 +4552,10 @@ public class DefaultCodegen implements CodegenConfig {
String name = null;
LOGGER.debug("Request body = " + body);
Schema schema = ModelUtils.getSchemaFromRequestBody(body);
if (schema == null) {
throw new RuntimeException("Request body cannot be null. Possible cause: missing schema in body parameter (OAS v2): " + body);
}
if (StringUtils.isNotBlank(schema.get$ref())) {
name = ModelUtils.getSimpleRef(schema.get$ref());
schema = schemas.get(name);
}
schema = ModelUtils.getReferencedSchema(this.openAPI, schema);
if (ModelUtils.isMapSchema(schema)) {
Schema inner = ModelUtils.getAdditionalProperties(schema);
@@ -4548,7 +4654,7 @@ public class DefaultCodegen implements CodegenConfig {
CodegenModel codegenModel = null;
if (StringUtils.isNotBlank(name)) {
schema.setName(name);
codegenModel = fromModel(name, schema);
codegenModel = fromModel(name, schema, schemas);
}
if (codegenModel != null) {
codegenParameter.isModel = true;

View File

@@ -19,6 +19,7 @@ package org.openapitools.codegen;
import com.samskivert.mustache.Mustache;
import com.samskivert.mustache.Template;
import io.swagger.v3.core.util.Json;
import io.swagger.v3.oas.models.OpenAPI;
import io.swagger.v3.oas.models.Operation;
@@ -32,6 +33,7 @@ import io.swagger.v3.oas.models.parameters.Parameter;
import io.swagger.v3.oas.models.security.SecurityRequirement;
import io.swagger.v3.oas.models.security.SecurityScheme;
import io.swagger.v3.oas.models.tags.Tag;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.ObjectUtils;
import org.apache.commons.lang3.StringUtils;
@@ -44,9 +46,9 @@ import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.*;
import java.net.URL;
import java.time.ZonedDateTime;
import java.util.*;
import java.net.*;
import java.time.ZonedDateTime;
public class DefaultGenerator extends AbstractGenerator implements Generator {
protected final Logger LOGGER = LoggerFactory.getLogger(DefaultGenerator.class);
@@ -180,8 +182,9 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
config.processOpts();
config.preprocessOpenAPI(openAPI);
// set OpenAPI to make these available to all methods
config.setOpenAPI(openAPI);
// set OpenAPI and schemas to make these available to all methods
config.setGlobalOpenAPI(openAPI);
config.setGlobalSchemas(openAPI);
config.additionalProperties().put("generatorVersion", ImplementationVersion.read());
config.additionalProperties().put("generatedDate", ZonedDateTime.now().toString());
@@ -431,13 +434,13 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
LOGGER.info("Model " + name + " not generated since it's a free-form object");
continue;
} else if (ModelUtils.isMapSchema(schema)) { // check to see if it's a "map" model
if (!ModelUtils.isGenerateAliasAsModel() && (schema.getProperties() == null || schema.getProperties().isEmpty())) {
if (schema.getProperties() == null || schema.getProperties().isEmpty()) {
// schema without property, i.e. alias to map
LOGGER.info("Model " + name + " not generated since it's an alias to map (without property)");
continue;
}
} else if (ModelUtils.isArraySchema(schema)) { // check to see if it's an "array" model
if (!ModelUtils.isGenerateAliasAsModel() && (schema.getProperties() == null || schema.getProperties().isEmpty())) {
if (schema.getProperties() == null || schema.getProperties().isEmpty()) {
// schema without property, i.e. alias to array
LOGGER.info("Model " + name + " not generated since it's an alias to array (without property)");
continue;
@@ -446,7 +449,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
Map<String, Schema> schemaMap = new HashMap<>();
schemaMap.put(name, schema);
Map<String, Object> models = processModels(config, schemaMap);
Map<String, Object> models = processModels(config, schemaMap, schemas);
models.put("classname", config.toModelName(name));
models.putAll(config.additionalProperties());
allProcessedModels.put(name, models);
@@ -797,7 +800,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
}
protected File writeInputStreamToFile(String filename, InputStream in, String templateFile) throws FileNotFoundException, IOException {
File outputFile = java.nio.file.Paths.get(filename).toFile();
File outputFile = new File(filename);
if (in != null) {
OutputStream out = new FileOutputStream(outputFile, false);
LOGGER.info("writing file " + outputFile);
@@ -836,15 +839,6 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
if (authMethods != null && !authMethods.isEmpty()) {
bundle.put("authMethods", authMethods);
bundle.put("hasAuthMethods", true);
if (hasOAuthMethods(authMethods)) {
bundle.put("hasOAuthMethods", true);
bundle.put("oauthMethods", getOAuthMethods(authMethods));
}
if (hasBearerMethods(authMethods)) {
bundle.put("hasBearerMethods", true);
}
}
List<CodegenServer> servers = config.fromServers(openAPI.getServers());
@@ -1017,7 +1011,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
final List<SecurityRequirement> globalSecurities = openAPI.getSecurity();
for (Tag tag : tags) {
try {
CodegenOperation codegenOperation = config.fromOperation(resourcePath, httpMethod, operation);
CodegenOperation codegenOperation = config.fromOperation(resourcePath, httpMethod, operation, schemas, openAPI);
codegenOperation.tags = new ArrayList<>(tags);
config.addOperationToGroup(config.sanitizeTag(tag.getName()), resourcePath, operation, codegenOperation, operations);
@@ -1113,6 +1107,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
operations.put("hasImport", true);
}
config.postProcessOperations(operations);
config.postProcessOperationsWithModels(operations, allModels);
if (objs.size() > 0) {
List<CodegenOperation> os = (List<CodegenOperation>) objs.get("operation");
@@ -1126,7 +1121,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
}
private Map<String, Object> processModels(CodegenConfig config, Map<String, Schema> definitions) {
private Map<String, Object> processModels(CodegenConfig config, Map<String, Schema> definitions, Map<String, Schema> allDefinitions) {
Map<String, Object> objs = new HashMap<String, Object>();
objs.put("package", config.modelPackage());
List<Object> models = new ArrayList<Object>();
@@ -1135,7 +1130,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
Schema schema = definitions.get(key);
if (schema == null)
throw new RuntimeException("schema cannot be null in processMoels");
CodegenModel cm = config.fromModel(key, schema);
CodegenModel cm = config.fromModel(key, schema, allDefinitions);
Map<String, Object> mo = new HashMap<String, Object>();
mo.put("model", cm);
mo.put("importPath", config.toModelImport(cm.classname));
@@ -1187,36 +1182,4 @@ public class DefaultGenerator extends AbstractGenerator implements Generator {
}
return authMethods;
}
private boolean hasOAuthMethods(List<CodegenSecurity> authMethods) {
for (CodegenSecurity cs : authMethods) {
if (cs.isOAuth) {
return true;
}
}
return false;
}
private boolean hasBearerMethods(List<CodegenSecurity> authMethods) {
for (CodegenSecurity cs : authMethods) {
if (cs.isBasicBearer) {
return true;
}
}
return false;
}
private List<CodegenSecurity> getOAuthMethods(List<CodegenSecurity> authMethods) {
List<CodegenSecurity> oauthMethods = new ArrayList<>();
for (CodegenSecurity cs : authMethods) {
if (cs.isOAuth) {
oauthMethods.add(cs);
}
}
return oauthMethods;
}
}

View File

@@ -17,19 +17,28 @@
package org.openapitools.codegen;
import io.swagger.v3.core.util.Json;
import io.swagger.v3.oas.models.*;
import io.swagger.v3.oas.models.OpenAPI;
import io.swagger.v3.oas.models.media.Schema;
import io.swagger.v3.oas.models.media.ArraySchema;
import io.swagger.v3.oas.models.media.ObjectSchema;
import io.swagger.v3.oas.models.media.*;
import io.swagger.v3.oas.models.responses.ApiResponse;
import io.swagger.v3.oas.models.Operation;
import io.swagger.v3.oas.models.PathItem;
import io.swagger.v3.oas.models.parameters.Parameter;
import io.swagger.v3.oas.models.parameters.RequestBody;
import io.swagger.v3.oas.models.responses.ApiResponse;
import io.swagger.v3.oas.models.responses.ApiResponses;
import io.swagger.v3.core.util.Json;
import org.openapitools.codegen.utils.ModelUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import io.swagger.v3.oas.models.media.Content;
import io.swagger.v3.oas.models.media.MediaType;
import java.util.*;
import io.swagger.v3.oas.models.media.XML;
public class InlineModelResolver {
private OpenAPI openapi;
private Map<String, Schema> addedModels = new HashMap<String, Schema>();
@@ -40,271 +49,266 @@ public class InlineModelResolver {
this.openapi = openapi;
if (openapi.getComponents() == null) {
openapi.setComponents(new Components());
return; // There's nothing here
}
if (openapi.getComponents().getSchemas() == null) {
openapi.getComponents().setSchemas(new HashMap<String, Schema>());
}
// operations
Map<String, PathItem> paths = openapi.getPaths();
Map<String, Schema> models = openapi.getComponents().getSchemas();
if (paths != null) {
for (String pathname : paths.keySet()) {
PathItem path = paths.get(pathname);
for (Operation operation : path.readOperations()) {
RequestBody requestBody = operation.getRequestBody();
if (requestBody != null) {
Schema model = ModelUtils.getSchemaFromRequestBody(requestBody);
if (model instanceof ObjectSchema) {
Schema obj = (Schema) model;
if (obj.getType() == null || "object".equals(obj.getType())) {
if (obj.getProperties() != null && obj.getProperties().size() > 0) {
flattenProperties(obj.getProperties(), pathname);
// for model name, use "title" if defined, otherwise default to 'inline_object'
String modelName = resolveModelName(obj.getTitle(), "inline_object");
addGenerated(modelName, model);
openapi.getComponents().addSchemas(modelName, model);
flattenPaths(openapi);
flattenComponents(openapi);
}
// create request body
RequestBody rb = new RequestBody();
Content content = new Content();
MediaType mt = new MediaType();
Schema schema = new Schema();
schema.set$ref(modelName);
mt.setSchema(schema);
/**
* Flatten inline models in Paths
*
* @param openAPI target spec
*/
private void flattenPaths(OpenAPI openAPI) {
Paths paths = openAPI.getPaths();
if (paths == null) {
return;
}
// get "consumes", e.g. application/xml, application/json
Set<String> consumes;
if (requestBody == null || requestBody.getContent() == null || requestBody.getContent().isEmpty()) {
consumes = new HashSet<>();
consumes.add("application/json"); // default to application/json
LOGGER.info("Default to application/json for inline body schema");
} else {
consumes = requestBody.getContent().keySet();
}
for (String pathname : paths.keySet()) {
PathItem path = paths.get(pathname);
for (Operation operation : path.readOperations()) {
flattenRequestBody(openAPI, pathname, operation);
flattenParameters(openAPI, pathname, operation);
flattenResponses(openAPI, pathname, operation);
}
}
}
for (String consume : consumes) {
content.addMediaType(consume, mt);
}
/**
* Flatten inline models in RequestBody
*
* @param openAPI target spec
* @param pathname target pathname
* @param operation target operation
*/
private void flattenRequestBody(OpenAPI openAPI, String pathname, Operation operation) {
RequestBody requestBody = operation.getRequestBody();
if (requestBody == null) {
return;
}
rb.setContent(content);
Schema model = ModelUtils.getSchemaFromRequestBody(requestBody);
if (model instanceof ObjectSchema) {
Schema obj = (Schema) model;
if (obj.getType() == null || "object".equals(obj.getType())) {
if (obj.getProperties() != null && obj.getProperties().size() > 0) {
flattenProperties(obj.getProperties(), pathname);
// for model name, use "title" if defined, otherwise default to 'inline_object'
String modelName = resolveModelName(obj.getTitle(), "inline_object");
addGenerated(modelName, model);
openAPI.getComponents().addSchemas(modelName, model);
// add to openapi "components"
if (openapi.getComponents().getRequestBodies() == null) {
Map<String, RequestBody> requestBodies = new HashMap<String, RequestBody>();
requestBodies.put(modelName, rb);
openapi.getComponents().setRequestBodies(requestBodies);
} else {
openapi.getComponents().getRequestBodies().put(modelName, rb);
}
// create request body
RequestBody rb = new RequestBody();
rb.setRequired(requestBody.getRequired());
Content content = new Content();
MediaType mt = new MediaType();
Schema schema = new Schema();
schema.set$ref(modelName);
mt.setSchema(schema);
// update requestBody to use $ref instead of inline def
requestBody.set$ref(modelName);
// get "consumes", e.g. application/xml, application/json
Set<String> consumes;
if (requestBody == null || requestBody.getContent() == null || requestBody.getContent().isEmpty()) {
consumes = new HashSet<>();
consumes.add("application/json"); // default to application/json
LOGGER.info("Default to application/json for inline body schema");
} else {
consumes = requestBody.getContent().keySet();
}
}
} else if (model instanceof ArraySchema) {
ArraySchema am = (ArraySchema) model;
Schema inner = am.getItems();
if (inner instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) inner;
if (op.getProperties() != null && op.getProperties().size() > 0) {
flattenProperties(op.getProperties(), pathname);
String modelName = resolveModelName(op.getTitle(), null);
Schema innerModel = modelFromProperty(op, modelName);
String existing = matchGenerated(innerModel);
if (existing != null) {
Schema schema = new Schema().$ref(existing);
schema.setRequired(op.getRequired());
am.setItems(schema);
} else {
Schema schema = new Schema().$ref(modelName);
schema.setRequired(op.getRequired());
am.setItems(schema);
addGenerated(modelName, innerModel);
openapi.getComponents().addSchemas(modelName, innerModel);
}
}
}
}
}
for (String consume : consumes) {
content.addMediaType(consume, mt);
List<Parameter> parameters = operation.getParameters();
if (parameters != null) {
for (Parameter parameter : parameters) {
if (parameter.getSchema() != null) {
Schema model = parameter.getSchema();
if (model instanceof ObjectSchema) {
Schema obj = (Schema) model;
if (obj.getType() == null || "object".equals(obj.getType())) {
if (obj.getProperties() != null && obj.getProperties().size() > 0) {
flattenProperties(obj.getProperties(), pathname);
String modelName = resolveModelName(obj.getTitle(), parameter.getName());
parameter.$ref(modelName);
addGenerated(modelName, model);
openapi.getComponents().addSchemas(modelName, model);
}
}
} else if (model instanceof ArraySchema) {
ArraySchema am = (ArraySchema) model;
Schema inner = am.getItems();
if (inner instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) inner;
if (op.getProperties() != null && op.getProperties().size() > 0) {
flattenProperties(op.getProperties(), pathname);
String modelName = resolveModelName(op.getTitle(), parameter.getName());
Schema innerModel = modelFromProperty(op, modelName);
String existing = matchGenerated(innerModel);
if (existing != null) {
Schema schema = new Schema().$ref(existing);
schema.setRequired(op.getRequired());
am.setItems(schema);
} else {
Schema schema = new Schema().$ref(modelName);
schema.setRequired(op.getRequired());
am.setItems(schema);
addGenerated(modelName, innerModel);
openapi.getComponents().addSchemas(modelName, innerModel);
}
}
}
}
}
}
}
rb.setContent(content);
// add to openapi "components"
if (openAPI.getComponents().getRequestBodies() == null) {
Map<String, RequestBody> requestBodies = new HashMap<String, RequestBody>();
requestBodies.put(modelName, rb);
openAPI.getComponents().setRequestBodies(requestBodies);
} else {
openAPI.getComponents().getRequestBodies().put(modelName, rb);
}
// update requestBody to use $ref instead of inline def
requestBody.set$ref(modelName);
}
}
} else if (model instanceof ArraySchema) {
ArraySchema am = (ArraySchema) model;
Schema inner = am.getItems();
if (inner instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) inner;
if (op.getProperties() != null && op.getProperties().size() > 0) {
flattenProperties(op.getProperties(), pathname);
String modelName = resolveModelName(op.getTitle(), null);
Schema innerModel = modelFromProperty(op, modelName);
String existing = matchGenerated(innerModel);
if (existing != null) {
Schema schema = new Schema().$ref(existing);
schema.setRequired(op.getRequired());
am.setItems(schema);
} else {
Schema schema = new Schema().$ref(modelName);
schema.setRequired(op.getRequired());
am.setItems(schema);
addGenerated(modelName, innerModel);
openAPI.getComponents().addSchemas(modelName, innerModel);
}
}
}
}
}
/**
* Flatten inline models in parameters
*
* @param openAPI target spec
* @param pathname target pathname
* @param operation target operation
*/
private void flattenParameters(OpenAPI openAPI, String pathname, Operation operation) {
List<Parameter> parameters = operation.getParameters();
if (parameters == null) {
return;
}
for (Parameter parameter : parameters) {
if (parameter.getSchema() == null) {
continue;
}
Schema model = parameter.getSchema();
if (model instanceof ObjectSchema) {
Schema obj = (Schema) model;
if (obj.getType() == null || "object".equals(obj.getType())) {
if (obj.getProperties() != null && obj.getProperties().size() > 0) {
flattenProperties(obj.getProperties(), pathname);
String modelName = resolveModelName(obj.getTitle(), parameter.getName());
parameter.$ref(modelName);
addGenerated(modelName, model);
openAPI.getComponents().addSchemas(modelName, model);
}
}
} else if (model instanceof ArraySchema) {
ArraySchema am = (ArraySchema) model;
Schema inner = am.getItems();
if (inner instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) inner;
if (op.getProperties() != null && op.getProperties().size() > 0) {
flattenProperties(op.getProperties(), pathname);
String modelName = resolveModelName(op.getTitle(), parameter.getName());
Schema innerModel = modelFromProperty(op, modelName);
String existing = matchGenerated(innerModel);
if (existing != null) {
Schema schema = new Schema().$ref(existing);
schema.setRequired(op.getRequired());
am.setItems(schema);
} else {
Schema schema = new Schema().$ref(modelName);
schema.setRequired(op.getRequired());
am.setItems(schema);
addGenerated(modelName, innerModel);
openAPI.getComponents().addSchemas(modelName, innerModel);
Map<String, ApiResponse> responses = operation.getResponses();
if (responses != null) {
for (String key : responses.keySet()) {
ApiResponse response = responses.get(key);
if (ModelUtils.getSchemaFromResponse(response) != null) {
Schema property = ModelUtils.getSchemaFromResponse(response);
if (property instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) property;
if (op.getProperties() != null && op.getProperties().size() > 0) {
String modelName = resolveModelName(op.getTitle(), "inline_response_" + key);
Schema model = modelFromProperty(op, modelName);
String existing = matchGenerated(model);
Content content = response.getContent();
for (MediaType mediaType : content.values()) {
if (existing != null) {
Schema schema = this.makeSchema(existing, property);
schema.setRequired(op.getRequired());
mediaType.setSchema(schema);
} else {
Schema schema = this.makeSchema(modelName, property);
schema.setRequired(op.getRequired());
mediaType.setSchema(schema);
addGenerated(modelName, model);
openapi.getComponents().addSchemas(modelName, model);
}
}
}
} else if (property instanceof ArraySchema) {
ArraySchema ap = (ArraySchema) property;
Schema inner = ap.getItems();
if (inner instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) inner;
if (op.getProperties() != null && op.getProperties().size() > 0) {
flattenProperties(op.getProperties(), pathname);
String modelName = resolveModelName(op.getTitle(),
"inline_response_" + key);
Schema innerModel = modelFromProperty(op, modelName);
String existing = matchGenerated(innerModel);
if (existing != null) {
Schema schema = this.makeSchema(existing, op);
schema.setRequired(op.getRequired());
ap.setItems(schema);
} else {
Schema schema = this.makeSchema(modelName, op);
schema.setRequired(op.getRequired());
ap.setItems(schema);
addGenerated(modelName, innerModel);
openapi.getComponents().addSchemas(modelName, innerModel);
}
}
}
} else if (property instanceof MapSchema) {
MapSchema mp = (MapSchema) property;
Schema innerProperty = ModelUtils.getAdditionalProperties(mp);
if (innerProperty instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) innerProperty;
if (op.getProperties() != null && op.getProperties().size() > 0) {
flattenProperties(op.getProperties(), pathname);
String modelName = resolveModelName(op.getTitle(),
"inline_response_" + key);
Schema innerModel = modelFromProperty(op, modelName);
String existing = matchGenerated(innerModel);
if (existing != null) {
Schema schema = new Schema().$ref(existing);
schema.setRequired(op.getRequired());
mp.setAdditionalProperties(schema);
} else {
Schema schema = new Schema().$ref(modelName);
schema.setRequired(op.getRequired());
mp.setAdditionalProperties(schema);
addGenerated(modelName, innerModel);
openapi.getComponents().addSchemas(modelName, innerModel);
}
}
}
}
}
}
}
}
}
}
}
/**
* Flatten inline models in ApiResponses
*
* @param openAPI target spec
* @param pathname target pathname
* @param operation target operation
*/
private void flattenResponses(OpenAPI openAPI, String pathname, Operation operation) {
ApiResponses responses = operation.getResponses();
if (responses == null) {
return;
}
for (String key : responses.keySet()) {
ApiResponse response = responses.get(key);
if (ModelUtils.getSchemaFromResponse(response) == null) {
continue;
}
Schema property = ModelUtils.getSchemaFromResponse(response);
if (property instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) property;
if (op.getProperties() != null && op.getProperties().size() > 0) {
String modelName = resolveModelName(op.getTitle(), "inline_response_" + key);
Schema model = modelFromProperty(op, modelName);
String existing = matchGenerated(model);
Content content = response.getContent();
for (MediaType mediaType : content.values()) {
if (existing != null) {
Schema schema = this.makeSchema(existing, property);
schema.setRequired(op.getRequired());
mediaType.setSchema(schema);
} else {
Schema schema = this.makeSchema(modelName, property);
schema.setRequired(op.getRequired());
mediaType.setSchema(schema);
addGenerated(modelName, model);
openAPI.getComponents().addSchemas(modelName, model);
// definitions
if (models != null) {
List<String> modelNames = new ArrayList<String>(models.keySet());
for (String modelName : modelNames) {
Schema model = models.get(modelName);
if (model instanceof Schema) {
Schema m = (Schema) model;
Map<String, Schema> properties = m.getProperties();
flattenProperties(properties, modelName);
fixStringModel(m);
} else if (ModelUtils.isArraySchema(model)) {
ArraySchema m = (ArraySchema) model;
Schema inner = m.getItems();
if (inner instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) inner;
if (op.getProperties() != null && op.getProperties().size() > 0) {
String innerModelName = resolveModelName(op.getTitle(), modelName + "_inner");
Schema innerModel = modelFromProperty(op, innerModelName);
String existing = matchGenerated(innerModel);
if (existing == null) {
openapi.getComponents().addSchemas(innerModelName, innerModel);
addGenerated(innerModelName, innerModel);
Schema schema = new Schema().$ref(innerModelName);
schema.setRequired(op.getRequired());
m.setItems(schema);
} else {
Schema schema = new Schema().$ref(existing);
schema.setRequired(op.getRequired());
m.setItems(schema);
}
}
}
}
} else if (property instanceof ArraySchema) {
ArraySchema ap = (ArraySchema) property;
Schema inner = ap.getItems();
if (inner instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) inner;
if (op.getProperties() != null && op.getProperties().size() > 0) {
flattenProperties(op.getProperties(), pathname);
String modelName = resolveModelName(op.getTitle(),
"inline_response_" + key);
Schema innerModel = modelFromProperty(op, modelName);
String existing = matchGenerated(innerModel);
if (existing != null) {
Schema schema = this.makeSchema(existing, op);
schema.setRequired(op.getRequired());
ap.setItems(schema);
} else {
Schema schema = this.makeSchema(modelName, op);
schema.setRequired(op.getRequired());
ap.setItems(schema);
addGenerated(modelName, innerModel);
openAPI.getComponents().addSchemas(modelName, innerModel);
} else if (ModelUtils.isComposedSchema(model)) {
ComposedSchema m = (ComposedSchema) model;
if (m.getAllOf() != null && !m.getAllOf().isEmpty()) {
Schema child = null;
for (Schema component : m.getAllOf()) {
if (component.get$ref() == null) {
child = component;
}
}
}
}
} else if (property instanceof MapSchema) {
MapSchema mp = (MapSchema) property;
Schema innerProperty = ModelUtils.getAdditionalProperties(mp);
if (innerProperty instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) innerProperty;
if (op.getProperties() != null && op.getProperties().size() > 0) {
flattenProperties(op.getProperties(), pathname);
String modelName = resolveModelName(op.getTitle(),
"inline_response_" + key);
Schema innerModel = modelFromProperty(op, modelName);
String existing = matchGenerated(innerModel);
if (existing != null) {
Schema schema = new Schema().$ref(existing);
schema.setRequired(op.getRequired());
mp.setAdditionalProperties(schema);
} else {
Schema schema = new Schema().$ref(modelName);
schema.setRequired(op.getRequired());
mp.setAdditionalProperties(schema);
addGenerated(modelName, innerModel);
openAPI.getComponents().addSchemas(modelName, innerModel);
if (child != null) {
Map<String, Schema> properties = child.getProperties();
flattenProperties(properties, modelName);
}
}
}
@@ -312,65 +316,6 @@ public class InlineModelResolver {
}
}
/**
* Flatten inline models in components
*
* @param openAPI target spec
*/
private void flattenComponents(OpenAPI openAPI) {
Map<String, Schema> models = openAPI.getComponents().getSchemas();
if (models == null) {
return;
}
List<String> modelNames = new ArrayList<String>(models.keySet());
for (String modelName : modelNames) {
Schema model = models.get(modelName);
if (model instanceof Schema) {
Schema m = (Schema) model;
Map<String, Schema> properties = m.getProperties();
flattenProperties(properties, modelName);
fixStringModel(m);
} else if (ModelUtils.isArraySchema(model)) {
ArraySchema m = (ArraySchema) model;
Schema inner = m.getItems();
if (inner instanceof ObjectSchema) {
ObjectSchema op = (ObjectSchema) inner;
if (op.getProperties() != null && op.getProperties().size() > 0) {
String innerModelName = resolveModelName(op.getTitle(), modelName + "_inner");
Schema innerModel = modelFromProperty(op, innerModelName);
String existing = matchGenerated(innerModel);
if (existing == null) {
openAPI.getComponents().addSchemas(innerModelName, innerModel);
addGenerated(innerModelName, innerModel);
Schema schema = new Schema().$ref(innerModelName);
schema.setRequired(op.getRequired());
m.setItems(schema);
} else {
Schema schema = new Schema().$ref(existing);
schema.setRequired(op.getRequired());
m.setItems(schema);
}
}
}
} else if (ModelUtils.isComposedSchema(model)) {
ComposedSchema m = (ComposedSchema) model;
if (m.getAllOf() != null && !m.getAllOf().isEmpty()) {
Schema child = null;
for (Schema component : m.getAllOf()) {
if (component.get$ref() == null) {
child = component;
}
}
if (child != null) {
Map<String, Schema> properties = child.getProperties();
flattenProperties(properties, modelName);
}
}
}
}
}
/**
* This function fix models that are string (mostly enum). Before this fix, the
* example would look something like that in the doc: "\"example from def\""
@@ -413,7 +358,6 @@ public class InlineModelResolver {
}
int count = 0;
boolean done = false;
key = key.replaceAll("/", "_"); // e.g. /me/videos => _me_videos
key = key.replaceAll("[^a-z_\\.A-Z0-9 ]", ""); // FIXME: a parameter
// should not be assigned. Also declare the methods parameters as 'final'.
while (!done) {

View File

@@ -26,9 +26,26 @@ import io.swagger.v3.parser.core.models.AuthorizationValue;
import io.swagger.v3.parser.core.models.ParseOptions;
import io.swagger.v3.parser.core.models.SwaggerParseResult;
import org.apache.commons.lang3.Validate;
import org.openapitools.codegen.*;
import org.openapitools.codegen.CliOption;
import org.openapitools.codegen.ClientOptInput;
import org.openapitools.codegen.ClientOpts;
import org.openapitools.codegen.CodegenConfig;
import org.openapitools.codegen.CodegenConfigLoader;
import org.openapitools.codegen.CodegenConstants;
import org.openapitools.codegen.SpecValidationException;
import org.openapitools.codegen.auth.AuthParser;
import org.openapitools.codegen.languages.*;
import org.openapitools.codegen.languages.CSharpNancyFXServerCodegen;
import org.openapitools.codegen.languages.CppQt5ClientCodegen;
import org.openapitools.codegen.languages.CppRestSdkClientCodegen;
import org.openapitools.codegen.languages.CppTizenClientCodegen;
import org.openapitools.codegen.languages.JavaJerseyServerCodegen;
import org.openapitools.codegen.languages.PhpLumenServerCodegen;
import org.openapitools.codegen.languages.PhpSlimServerCodegen;
import org.openapitools.codegen.languages.PhpZendExpressivePathHandlerServerCodegen;
import org.openapitools.codegen.languages.RubySinatraServerCodegen;
import org.openapitools.codegen.languages.ScalaAkkaClientCodegen;
import org.openapitools.codegen.languages.ScalaHttpClientCodegen;
import org.openapitools.codegen.languages.SwiftClientCodegen;
import org.openapitools.codegen.utils.ModelUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@@ -37,7 +54,12 @@ import java.io.File;
import java.io.IOException;
import java.io.Serializable;
import java.nio.file.Paths;
import java.util.*;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
import static org.apache.commons.lang3.StringUtils.isNotEmpty;
@@ -73,7 +95,6 @@ public class CodegenConfigurator implements Serializable {
private boolean verbose;
private boolean skipOverwrite;
private boolean removeOperationIdPrefix;
private boolean logToStderr;
private boolean validateSpec;
private boolean enablePostProcessFile;
private String templateDir;
@@ -199,24 +220,6 @@ public class CodegenConfigurator implements Serializable {
return this;
}
public boolean getLogToStderr() {
return logToStderr;
}
public CodegenConfigurator setLogToStderr(boolean logToStderrte) {
this.logToStderr = logToStderr;
return this;
}
public boolean isGenerateAliasAsModel() {
return ModelUtils.isGenerateAliasAsModel();
}
public CodegenConfigurator setGenerateAliasAsModel(boolean generateAliasAsModel) {
ModelUtils.setGenerateAliasAsModel(generateAliasAsModel);
return this;
}
public String getModelNameSuffix() {
return modelNameSuffix;
}

View File

@@ -17,8 +17,8 @@
package org.openapitools.codegen.config;
import org.apache.commons.lang3.tuple.Pair;
import org.openapitools.codegen.utils.OptionUtils;
import org.apache.commons.lang3.tuple.Pair;
import java.util.*;

Some files were not shown because too many files have changed in this diff Show More