From 60bd56b91cb5ae429530740c0c6d63ae7aa6c258 Mon Sep 17 00:00:00 2001 From: Dan Peschman Date: Thu, 15 Jan 2015 22:42:59 +0000 Subject: [PATCH 01/70] python3: support more iso8601 datetime formats - http://xml2rfc.ietf.org/public/rfc/html/rfc3339.html#date.and.time.format.examples --- src/main/resources/python3/swagger.mustache | 38 ++++++++++++++++----- 1 file changed, 30 insertions(+), 8 deletions(-) diff --git a/src/main/resources/python3/swagger.mustache b/src/main/resources/python3/swagger.mustache index a01b69794e..ae8d671671 100644 --- a/src/main/resources/python3/swagger.mustache +++ b/src/main/resources/python3/swagger.mustache @@ -43,7 +43,6 @@ class ApiClient: data = None - if queryParams: # Need to remove None values, these should not be sent sentQueryParams = {} @@ -119,6 +118,34 @@ class ApiClient: for (key, val) in objDict.items() if key != 'swaggerTypes'} + def _iso8601Format(self, timesep, microsecond, zulu): + """Format for parsing a datetime string with given properties. + + Args: + timesep -- string separating time from date ('T' or 't') + microsecond -- microsecond portion of time ('.XXX') + zulu -- 'Z' or 'z' for UTC, or None for time offset (+/-XX:XX) + + Returns: + str - format string for datetime.strptime""" + + return '%Y-%m-%d{}%H:%M:%S{}{}'.format( + timesep, + '.%f' if microsecond else '', + zulu or '%z') + + # http://xml2rfc.ietf.org/public/rfc/html/rfc3339.html#anchor14 + _iso8601Regex = re.compile( + r'^\d\d\d\d-\d\d-\d\d([Tt])\d\d:\d\d:\d\d(\.\d+)?(([Zz])|(\+|-)\d\d:?\d\d)$') + + def _parseDatetime(self, d): + m = ApiClient._iso8601Regex.match(d) + timesep, microsecond, offset, zulu, plusminus = m.groups() + format = self._iso8601Format(timesep, microsecond, zulu) + if not zulu: + d = d.rsplit(sep=plusminus, maxsplit=1)[0] + offset.replace(':', '') + return datetime.datetime.strptime(d, format) + def deserialize(self, obj, objClass): """Derialize a JSON string into an object. @@ -145,11 +172,7 @@ class ApiClient: if objClass in [int, float, dict, list, str, bool]: return objClass(obj) elif objClass == datetime: - # Server will always return a time stamp in UTC, but with - # trailing +0000 indicating no offset from UTC. So don't process - # last 5 characters. - return datetime.datetime.strptime(obj[:-5], - "%Y-%m-%dT%H:%M:%S.%f") + return self._parseDatetime(obj) instance = objClass() @@ -167,8 +190,7 @@ class ApiClient: value = value setattr(instance, attr, value) elif (attrType == 'datetime'): - setattr(instance, attr, datetime.datetime.strptime(value[:-5], - "%Y-%m-%dT%H:%M:%S.%f")) + setattr(instance, attr, self._parseDatetime(value)) elif 'list[' in attrType: match = re.match('list\[(.*)\]', attrType) subClass = match.group(1) From 527fca5a8bc9f884e72a586457b571c2d902b7ef Mon Sep 17 00:00:00 2001 From: Dan Peschman Date: Thu, 15 Jan 2015 23:19:01 +0000 Subject: [PATCH 02/70] python3 parseDatetime: return None if passed None --- src/main/resources/python3/swagger.mustache | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/main/resources/python3/swagger.mustache b/src/main/resources/python3/swagger.mustache index ae8d671671..4986b8548d 100644 --- a/src/main/resources/python3/swagger.mustache +++ b/src/main/resources/python3/swagger.mustache @@ -139,6 +139,8 @@ class ApiClient: r'^\d\d\d\d-\d\d-\d\d([Tt])\d\d:\d\d:\d\d(\.\d+)?(([Zz])|(\+|-)\d\d:?\d\d)$') def _parseDatetime(self, d): + if d is None: + return None m = ApiClient._iso8601Regex.match(d) timesep, microsecond, offset, zulu, plusminus = m.groups() format = self._iso8601Format(timesep, microsecond, zulu) From 42ad403e5eb91b917148768a814760d4fa405d85 Mon Sep 17 00:00:00 2001 From: Dan Peschman Date: Fri, 16 Jan 2015 23:09:54 +0000 Subject: [PATCH 03/70] python3 parseDatetime: return None if passed '' --- src/main/resources/python3/swagger.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/resources/python3/swagger.mustache b/src/main/resources/python3/swagger.mustache index 4986b8548d..8985d1a1b4 100644 --- a/src/main/resources/python3/swagger.mustache +++ b/src/main/resources/python3/swagger.mustache @@ -139,7 +139,7 @@ class ApiClient: r'^\d\d\d\d-\d\d-\d\d([Tt])\d\d:\d\d:\d\d(\.\d+)?(([Zz])|(\+|-)\d\d:?\d\d)$') def _parseDatetime(self, d): - if d is None: + if not d: return None m = ApiClient._iso8601Regex.match(d) timesep, microsecond, offset, zulu, plusminus = m.groups() From 711d2c8cf46afa40444da6d4df2a7b441a0230d6 Mon Sep 17 00:00:00 2001 From: Dan Peschman Date: Fri, 16 Jan 2015 23:44:02 +0000 Subject: [PATCH 04/70] revert previous: no special handling for '' in python3 parseDatetime --- src/main/resources/python3/swagger.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/resources/python3/swagger.mustache b/src/main/resources/python3/swagger.mustache index 8985d1a1b4..4986b8548d 100644 --- a/src/main/resources/python3/swagger.mustache +++ b/src/main/resources/python3/swagger.mustache @@ -139,7 +139,7 @@ class ApiClient: r'^\d\d\d\d-\d\d-\d\d([Tt])\d\d:\d\d:\d\d(\.\d+)?(([Zz])|(\+|-)\d\d:?\d\d)$') def _parseDatetime(self, d): - if not d: + if d is None: return None m = ApiClient._iso8601Regex.match(d) timesep, microsecond, offset, zulu, plusminus = m.groups() From 4198779b5bf137cd362eb5571a1d68df268d093f Mon Sep 17 00:00:00 2001 From: Dan Peschman Date: Sat, 17 Jan 2015 00:41:37 +0000 Subject: [PATCH 05/70] python3: support datetime produced by datetime.isoformat like '2015-01-17T00:15:29.515' --- src/main/resources/python3/swagger.mustache | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/src/main/resources/python3/swagger.mustache b/src/main/resources/python3/swagger.mustache index 4986b8548d..3b00a14dc9 100644 --- a/src/main/resources/python3/swagger.mustache +++ b/src/main/resources/python3/swagger.mustache @@ -118,12 +118,13 @@ class ApiClient: for (key, val) in objDict.items() if key != 'swaggerTypes'} - def _iso8601Format(self, timesep, microsecond, zulu): + def _iso8601Format(self, timesep, microsecond, offset, zulu): """Format for parsing a datetime string with given properties. Args: timesep -- string separating time from date ('T' or 't') microsecond -- microsecond portion of time ('.XXX') + offset -- time offset (+/-XX:XX) or None zulu -- 'Z' or 'z' for UTC, or None for time offset (+/-XX:XX) Returns: @@ -132,19 +133,21 @@ class ApiClient: return '%Y-%m-%d{}%H:%M:%S{}{}'.format( timesep, '.%f' if microsecond else '', - zulu or '%z') + zulu or ('%z' if offset else '')) # http://xml2rfc.ietf.org/public/rfc/html/rfc3339.html#anchor14 _iso8601Regex = re.compile( - r'^\d\d\d\d-\d\d-\d\d([Tt])\d\d:\d\d:\d\d(\.\d+)?(([Zz])|(\+|-)\d\d:?\d\d)$') + r'^\d\d\d\d-\d\d-\d\d([Tt])\d\d:\d\d:\d\d(\.\d+)?(([Zz])|(\+|-)\d\d:?\d\d)?$') def _parseDatetime(self, d): if d is None: return None m = ApiClient._iso8601Regex.match(d) + if not m: + raise Exception('datetime regex match failed "%s"' % d) timesep, microsecond, offset, zulu, plusminus = m.groups() - format = self._iso8601Format(timesep, microsecond, zulu) - if not zulu: + format = self._iso8601Format(timesep, microsecond, offset, zulu) + if offset and not zulu: d = d.rsplit(sep=plusminus, maxsplit=1)[0] + offset.replace(':', '') return datetime.datetime.strptime(d, format) From ec995838fba479fa35e9926379e26010ac83731a Mon Sep 17 00:00:00 2001 From: Dan Peschman Date: Sat, 24 Jan 2015 21:58:33 +0000 Subject: [PATCH 06/70] python3: support PATCH verb for partial updates - http://tools.ietf.org/html/rfc5789 --- src/main/resources/python3/swagger.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/resources/python3/swagger.mustache b/src/main/resources/python3/swagger.mustache index 3b00a14dc9..722a60a634 100644 --- a/src/main/resources/python3/swagger.mustache +++ b/src/main/resources/python3/swagger.mustache @@ -56,7 +56,7 @@ class ApiClient: #Options to add statements later on and for compatibility pass - elif method in ['POST', 'PUT', 'DELETE']: + elif method in ['PATCH', 'POST', 'PUT', 'DELETE']: if postData: headers['Content-type'] = 'application/json' From bd9192207270c3ec2a13c5a57bcdaccb9899d1b0 Mon Sep 17 00:00:00 2001 From: russellb337 Date: Fri, 6 Feb 2015 16:26:33 -0800 Subject: [PATCH 07/70] Add API Version to Codeine Additional Properties Also updated htmlDocs template so html documentation shows API version. --- .../java/com/wordnik/swagger/codegen/DefaultGenerator.java | 3 +++ .../swagger-codegen/src/main/resources/htmlDocs/index.mustache | 1 + 2 files changed, 4 insertions(+) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java index a6ce42f712..5a7d29bd14 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java @@ -54,6 +54,9 @@ public class DefaultGenerator implements Generator { if(license.getUrl() != null) config.additionalProperties().put("licenseUrl", license.getUrl()); } + if(info.getVersion() != null) { + config.additionalProperties().put("version", info.getVersion()); + } } StringBuilder hostBuilder = new StringBuilder(); diff --git a/modules/swagger-codegen/src/main/resources/htmlDocs/index.mustache b/modules/swagger-codegen/src/main/resources/htmlDocs/index.mustache index ccd35c8723..dd2a573d75 100644 --- a/modules/swagger-codegen/src/main/resources/htmlDocs/index.mustache +++ b/modules/swagger-codegen/src/main/resources/htmlDocs/index.mustache @@ -9,6 +9,7 @@
{{{appDescription}}} for {{partner}}
{{#infoUrl}}
More information: {{{infoUrl}}}
{{/infoUrl}} {{#infoEmail}}
Contact Info: {{{infoEmail}}}
{{/infoEmail}} + {{#version}}
Version: {{{version}}}
{{/version}}
{{{licenseInfo}}}
{{{licenseUrl}}}

Access

From c82dfa3a64a3ed308c9b5da697814aa26e89154e Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 23 Feb 2015 23:03:18 -0800 Subject: [PATCH 08/70] updated version --- README.md | 2 +- modules/swagger-codegen-distribution/pom.xml | 4 ++-- modules/swagger-codegen/pom.xml | 4 ++-- modules/swagger-generator/pom.xml | 2 +- pom.xml | 2 +- 5 files changed, 7 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 63b7fa386b..bf580e3e75 100644 --- a/README.md +++ b/README.md @@ -18,7 +18,7 @@ The Swagger Specification has undergone 3 revisions since initial creation in 20 Swagger Codegen Version | Release Date | Swagger Spec compatability | Notes ----------------------- | ------------ | -------------------------- | ----- -2.1.2-M1 | 2015-02-23 | 1.0, 1.1, 1.2, 2.0 | [tag v2.1.0-M1](https://github.com/swagger-api/swagger-codegen) +2.1.3-M1-SNAPSHOT | 2015-02-23 | 1.0, 1.1, 1.2, 2.0 | [tag v2.1.0-M1](https://github.com/swagger-api/swagger-codegen) 2.0.17 | 2014-08-22 | 1.1, 1.2 | [tag v2.0.17](https://github.com/swagger-api/swagger-codegen/tree/v2.0.17) 1.0.4 | 2012-04-12 | 1.0, 1.1 | [tag v1.0.4](https://github.com/swagger-api/swagger-codegen/tree/swagger-codegen_2.9.1-1.1) diff --git a/modules/swagger-codegen-distribution/pom.xml b/modules/swagger-codegen-distribution/pom.xml index a91d5d0cc8..634ad084c0 100644 --- a/modules/swagger-codegen-distribution/pom.xml +++ b/modules/swagger-codegen-distribution/pom.xml @@ -2,7 +2,7 @@ com.wordnik swagger-codegen-project - 2.1.2-M1 + 2.1.3-M1-SNAPSHOT ../.. 4.0.0 @@ -10,7 +10,7 @@ swagger-codegen-distribution jar swagger-codegen (executable) - 2.1.2-M1 + 2.1.3-M1-SNAPSHOT src/test/scala target/classes diff --git a/modules/swagger-codegen/pom.xml b/modules/swagger-codegen/pom.xml index a11e0a719d..1abd2689b5 100644 --- a/modules/swagger-codegen/pom.xml +++ b/modules/swagger-codegen/pom.xml @@ -2,7 +2,7 @@ com.wordnik swagger-codegen-project - 2.1.2-M1 + 2.1.3-M1-SNAPSHOT ../.. 4.0.0 @@ -10,7 +10,7 @@ swagger-codegen jar swagger-codegen (core library) - 2.1.2-M1 + 2.1.3-M1-SNAPSHOT src/main/java install diff --git a/modules/swagger-generator/pom.xml b/modules/swagger-generator/pom.xml index 653ea27861..7da33b880a 100644 --- a/modules/swagger-generator/pom.xml +++ b/modules/swagger-generator/pom.xml @@ -3,7 +3,7 @@ com.wordnik swagger-codegen-project - 2.1.2-M1 + 2.1.3-M1-SNAPSHOT ../.. com.wordnik diff --git a/pom.xml b/pom.xml index 549fb18330..544dd4c8c0 100644 --- a/pom.xml +++ b/pom.xml @@ -9,7 +9,7 @@ swagger-codegen-project pom swagger-codegen-project - 2.1.2-M1 + 2.1.3-M1-SNAPSHOT https://github.com/swagger-api/swagger-codegen scm:git:git@github.com:swagger-api/swagger-codegen.git From 69be95d586abd44d5405715d5709edc01332f9b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Herve=CC=81=20Darritchon?= Date: Tue, 24 Feb 2015 08:20:49 +0100 Subject: [PATCH 09/70] Defect (Issue #445) : change the call of initialCaps for getter and setter with Introspector.decapitalize from pakage java.beans. --- .../swagger/codegen/DefaultCodegen.java | 21 ++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index 014a595ae1..1070453489 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -4,14 +4,12 @@ import com.wordnik.swagger.models.*; import com.wordnik.swagger.models.parameters.*; import com.wordnik.swagger.models.properties.*; import com.wordnik.swagger.util.Json; - import org.apache.commons.lang.StringUtils; - import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import java.util.*; import java.io.File; +import java.util.*; public class DefaultCodegen { Logger LOGGER = LoggerFactory.getLogger(DefaultCodegen.class); @@ -439,6 +437,19 @@ public class DefaultCodegen { return m; } + public static String getterAndSetterCapitalize(String name) { + if (name == null || name.length() == 0) { + return name; + } + if (name.length() > 1 && Character.isUpperCase(name.charAt(1)) && + Character.isLowerCase(name.charAt(0))){ + return name; + } + char chars[] = name.toCharArray(); + chars[0] = Character.toUpperCase(chars[0]); + return new String(chars); + } + public CodegenProperty fromProperty(String name, Property p) { if(p == null) { LOGGER.error("unexpected missing property for name " + null); @@ -449,8 +460,8 @@ public class DefaultCodegen { property.name = toVarName(name); property.baseName = name; property.description = escapeText(p.getDescription()); - property.getter = "get" + initialCaps(name); - property.setter = "set" + initialCaps(name); + property.getter = "get" + getterAndSetterCapitalize(name); + property.setter = "set" + getterAndSetterCapitalize(name); property.example = p.getExample(); property.defaultValue = toDefaultValue(p); From e5c70d596165e105b9e402e3a3bd79d8790290ed Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 23 Feb 2015 23:23:37 -0800 Subject: [PATCH 10/70] updated online version, added tag example --- modules/swagger-generator/pom.xml | 4 ++-- .../generator/resource/SwaggerResource.java | 16 +++++++++++----- 2 files changed, 13 insertions(+), 7 deletions(-) diff --git a/modules/swagger-generator/pom.xml b/modules/swagger-generator/pom.xml index 7da33b880a..104e2ef6d4 100644 --- a/modules/swagger-generator/pom.xml +++ b/modules/swagger-generator/pom.xml @@ -10,7 +10,7 @@ swagger-generator war swagger-generator - 1.0.0 + 2.1.3-M1-SNAPSHOT src/main/java @@ -232,7 +232,7 @@ 1.3.2 9.0.7.v20131107 2.4.1 - 1.5.1-M1 + 1.5.2-M1 3.1.5 2.10.0 diff --git a/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java b/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java index 2e3a480e11..baf8220275 100644 --- a/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java +++ b/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java @@ -36,7 +36,8 @@ public class SwaggerResource { @Path("/download/{fileId}") @Produces({"application/zip"}) @ApiOperation(value = "Downloads a pre-generated file", - response = String.class) + response = String.class, + tags = {@Tag(value = "clients"), @Tag(value = "servers")}) public Response downloadFile(@PathParam("fileId") String fileId) throws Exception { Generated g = fileMap.get(fileId); System.out.println("looking for fileId " + fileId); @@ -59,7 +60,9 @@ public class SwaggerResource { @Path("/clients/{language}") @Produces({"application/zip", "application/json"}) @ApiOperation( - value = "Generates a client library based on the config") + value = "Generates a client library based on the config", + response = ResponseCode.class, + tags = {@Tag(value = "clients", description = "client operations")}) public Response generateClient( @ApiParam(value = "The target language for the client library", allowableValues = "android,java,php,objc,docs", required = true) @PathParam("language") String language, @ApiParam(value = "Configuration for building the client library", required = true) GeneratorInput opts) throws Exception { @@ -85,7 +88,8 @@ public class SwaggerResource { @Path("/clients") @ApiOperation(value = "Gets languages supported by the client generator", response = String.class, - responseContainer = "List") + responseContainer = "List", + tags = {@Tag(value = "clients", description = "client operations")}) public Response clientOptions() { String[] languages = new String[clients.size()]; languages = clients.toArray(languages); @@ -96,7 +100,8 @@ public class SwaggerResource { @Path("/servers") @ApiOperation(value = "Gets languages supported by the server generator", response = String.class, - responseContainer = "List") + responseContainer = "List", + tags = {@Tag(value = "servers", description = "server operations")}) public Response serverOptions() { String[] languages = new String[servers.size()]; languages = servers.toArray(languages); @@ -106,7 +111,8 @@ public class SwaggerResource { @POST @Path("/servers/{framework}") @ApiOperation(value = "Generates a server library for the supplied server framework", - notes = "The model representing this is not accurate, it needs to contain a consolidated JSON structure") + response = ResponseCode.class, + tags = {@Tag(value = "servers", description = "server operations")}) public Response generateServerForLanguage( @ApiParam(value = "framework", allowableValues = "jaxrs,nodejs", required = true) @PathParam("framework") String framework, @ApiParam(value = "parameters", required = true) GeneratorInput opts) From b339db65bef17e6d38a48a1c199223b808be0d6f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Herve=CC=81=20Darritchon?= Date: Tue, 24 Feb 2015 09:23:07 +0100 Subject: [PATCH 11/70] Pull request #452 : Add some unit tests for this PR --- .../src/test/scala/Java/JavaModelTest.scala | 26 +++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala b/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala index 513786e460..90f0168db5 100644 --- a/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala +++ b/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala @@ -265,4 +265,30 @@ class JavaModelTest extends FlatSpec with Matchers { vars.get(0).required should equal (true) vars.get(0).isNotContainer should equal (true) } + + it should "convert a model with a 2nd char upper-case property names" in { + val model = new ModelImpl() + .description("a model with a 2nd char upper-case property names") + .property("pId", new StringProperty()) + .required("pId") + + val codegen = new JavaClientCodegen() + val cm = codegen.fromModel("sample", model) + + cm.name should be ("sample") + cm.classname should be ("Sample") + cm.vars.size should be (1) + + val vars = cm.vars + vars.get(0).baseName should be ("pId") + vars.get(0).getter should be ("getpId") + vars.get(0).setter should be ("setpId") + vars.get(0).datatype should be ("String") + vars.get(0).name should be ("pId") + vars.get(0).defaultValue should be ("null") + vars.get(0).baseType should be ("String") + vars.get(0).hasMore should equal (null) + vars.get(0).required should equal (true) + vars.get(0).isNotContainer should equal (true) + } } From 292fc99bd51a1ca7e5398859d4e73c390ec1b0c5 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Tue, 24 Feb 2015 11:03:00 -0800 Subject: [PATCH 12/70] fixed response types --- .../wordnik/swagger/generator/resource/SwaggerResource.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java b/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java index baf8220275..b4592a4afc 100644 --- a/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java +++ b/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java @@ -34,7 +34,7 @@ public class SwaggerResource { @GET @Path("/download/{fileId}") - @Produces({"application/zip"}) + @Produces({MediaType.APPLICATION_OCTET_STREAM}) @ApiOperation(value = "Downloads a pre-generated file", response = String.class, tags = {@Tag(value = "clients"), @Tag(value = "servers")}) @@ -58,7 +58,6 @@ public class SwaggerResource { @POST @Path("/clients/{language}") - @Produces({"application/zip", "application/json"}) @ApiOperation( value = "Generates a client library based on the config", response = ResponseCode.class, From 1a0d2d19f51780d7284ea922aa674f5b89745ecf Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Tue, 24 Feb 2015 18:07:13 -0800 Subject: [PATCH 13/70] updated template --- .../src/main/resources/JavaJaxRS/api.mustache | 7 ++++++- .../jaxrs/src/main/java/io/swagger/api/PetApi.java | 7 ++++++- .../jaxrs/src/main/java/io/swagger/api/StoreApi.java | 7 ++++++- .../jaxrs/src/main/java/io/swagger/api/UserApi.java | 7 ++++++- 4 files changed, 24 insertions(+), 4 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/JavaJaxRS/api.mustache b/modules/swagger-codegen/src/main/resources/JavaJaxRS/api.mustache index 3b5001b9e1..e93d4c14f8 100644 --- a/modules/swagger-codegen/src/main/resources/JavaJaxRS/api.mustache +++ b/modules/swagger-codegen/src/main/resources/JavaJaxRS/api.mustache @@ -2,7 +2,12 @@ package {{package}}; import {{modelPackage}}.*; -import com.wordnik.swagger.annotations.*; +import com.wordnik.swagger.annotations.Api; +import com.wordnik.swagger.annotations.ApiParam; +import com.wordnik.swagger.annotations.ApiOperation; +import com.wordnik.swagger.annotations.ApiResponse; +import com.wordnik.swagger.annotations.ApiResponses; + import com.sun.jersey.multipart.FormDataParam; {{#imports}}import {{import}}; diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java index 77d30c736a..c9ab276214 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java @@ -2,7 +2,12 @@ package io.swagger.api; import io.swagger.model.*; -import com.wordnik.swagger.annotations.*; +import com.wordnik.swagger.annotations.Api; +import com.wordnik.swagger.annotations.ApiParam; +import com.wordnik.swagger.annotations.ApiOperation; +import com.wordnik.swagger.annotations.ApiResponse; +import com.wordnik.swagger.annotations.ApiResponses; + import com.sun.jersey.multipart.FormDataParam; import io.swagger.model.Pet; diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java index cc49b9340c..a005554473 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java @@ -2,7 +2,12 @@ package io.swagger.api; import io.swagger.model.*; -import com.wordnik.swagger.annotations.*; +import com.wordnik.swagger.annotations.Api; +import com.wordnik.swagger.annotations.ApiParam; +import com.wordnik.swagger.annotations.ApiOperation; +import com.wordnik.swagger.annotations.ApiResponse; +import com.wordnik.swagger.annotations.ApiResponses; + import com.sun.jersey.multipart.FormDataParam; import java.util.Map; diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java index c06d88e41f..1c40c0409b 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java @@ -2,7 +2,12 @@ package io.swagger.api; import io.swagger.model.*; -import com.wordnik.swagger.annotations.*; +import com.wordnik.swagger.annotations.Api; +import com.wordnik.swagger.annotations.ApiParam; +import com.wordnik.swagger.annotations.ApiOperation; +import com.wordnik.swagger.annotations.ApiResponse; +import com.wordnik.swagger.annotations.ApiResponses; + import com.sun.jersey.multipart.FormDataParam; import io.swagger.model.User; From 05297e05a5b99625eba9d42edb75272ddc566a94 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Tue, 24 Feb 2015 21:12:08 -0800 Subject: [PATCH 14/70] made annotations FQ to avoid collisions --- .../src/main/resources/JavaJaxRS/api.mustache | 13 ++-- .../src/main/java/io/swagger/api/PetApi.java | 66 ++++++++----------- .../main/java/io/swagger/api/StoreApi.java | 36 ++++------ .../src/main/java/io/swagger/api/UserApi.java | 60 +++++++---------- 4 files changed, 69 insertions(+), 106 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/JavaJaxRS/api.mustache b/modules/swagger-codegen/src/main/resources/JavaJaxRS/api.mustache index e93d4c14f8..b5ebb30f19 100644 --- a/modules/swagger-codegen/src/main/resources/JavaJaxRS/api.mustache +++ b/modules/swagger-codegen/src/main/resources/JavaJaxRS/api.mustache @@ -2,11 +2,7 @@ package {{package}}; import {{modelPackage}}.*; -import com.wordnik.swagger.annotations.Api; import com.wordnik.swagger.annotations.ApiParam; -import com.wordnik.swagger.annotations.ApiOperation; -import com.wordnik.swagger.annotations.ApiResponse; -import com.wordnik.swagger.annotations.ApiResponses; import com.sun.jersey.multipart.FormDataParam; @@ -25,7 +21,7 @@ import javax.ws.rs.core.Response; import javax.ws.rs.*; @Path("/{{baseName}}") -@Api(value = "/{{baseName}}", description = "the {{baseName}} API") +@com.wordnik.swagger.annotations.Api(value = "/{{baseName}}", description = "the {{baseName}} API") {{#operations}} public class {{classname}} { {{#operation}} @@ -33,10 +29,9 @@ public class {{classname}} { {{#subresourceOperation}}@Path("{{path}}"){{/subresourceOperation}} {{#hasConsumes}}@Consumes({ {{#consumes}}"{{mediaType}}"{{#hasMore}}, {{/hasMore}}{{/consumes}} }){{/hasConsumes}} {{#hasProduces}}@Produces({ {{#produces}}"{{mediaType}}"{{#hasMore}}, {{/hasMore}}{{/produces}} }){{/hasProduces}} - // {{returnType}} - @ApiOperation(value = "{{{summary}}}", notes = "{{{notes}}}", response = {{{returnType}}}.class{{#returnContainer}}, responseContainer = "{{{returnContainer}}}"{{/returnContainer}}) - @ApiResponses(value = { {{#responses}} - @ApiResponse(code = {{{code}}}, message = "{{{message}}}"){{#hasMore}}, + @com.wordnik.swagger.annotations.ApiOperation(value = "{{{summary}}}", notes = "{{{notes}}}", response = {{{returnType}}}.class{{#returnContainer}}, responseContainer = "{{{returnContainer}}}"{{/returnContainer}}) + @com.wordnik.swagger.annotations.ApiResponses(value = { {{#responses}} + @com.wordnik.swagger.annotations.ApiResponse(code = {{{code}}}, message = "{{{message}}}"){{#hasMore}}, {{/hasMore}}{{/responses}} }) public Response {{nickname}}({{#allParams}}{{>queryParams}}{{>pathParams}}{{>headerParams}}{{>bodyParams}}{{>formParams}}{{#hasMore}}, diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java index c9ab276214..bdf4ecec3d 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java @@ -2,11 +2,7 @@ package io.swagger.api; import io.swagger.model.*; -import com.wordnik.swagger.annotations.Api; import com.wordnik.swagger.annotations.ApiParam; -import com.wordnik.swagger.annotations.ApiOperation; -import com.wordnik.swagger.annotations.ApiResponse; -import com.wordnik.swagger.annotations.ApiResponses; import com.sun.jersey.multipart.FormDataParam; @@ -25,21 +21,20 @@ import javax.ws.rs.core.Response; import javax.ws.rs.*; @Path("/pet") -@Api(value = "/pet", description = "the pet API") +@com.wordnik.swagger.annotations.Api(value = "/pet", description = "the pet API") public class PetApi { @PUT @Consumes({ "application/json", "application/xml" }) @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Update an existing pet", notes = "", response = Void.class) - @ApiResponses(value = { - @ApiResponse(code = 405, message = "Validation exception"), + @com.wordnik.swagger.annotations.ApiOperation(value = "Update an existing pet", notes = "", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 405, message = "Validation exception"), - @ApiResponse(code = 404, message = "Pet not found"), + @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "Pet not found"), - @ApiResponse(code = 400, message = "Invalid ID supplied") }) + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid ID supplied") }) public Response updatePet(@ApiParam(value = "Pet object that needs to be added to the store" ) Pet body) throws NotFoundException { @@ -52,10 +47,9 @@ public class PetApi { @Consumes({ "application/json", "application/xml" }) @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Add a new pet to the store", notes = "", response = Void.class) - @ApiResponses(value = { - @ApiResponse(code = 405, message = "Invalid input") }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Add a new pet to the store", notes = "", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 405, message = "Invalid input") }) public Response addPet(@ApiParam(value = "Pet object that needs to be added to the store" ) Pet body) throws NotFoundException { @@ -68,10 +62,9 @@ public class PetApi { @Path("/findByStatus") @Produces({ "application/json", "application/xml" }) - // Pet - @ApiOperation(value = "Finds Pets by status", notes = "Multiple status values can be provided with comma seperated strings", response = Pet.class, responseContainer = "List") - @ApiResponses(value = { - @ApiResponse(code = 400, message = "Invalid status value") }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Finds Pets by status", notes = "Multiple status values can be provided with comma seperated strings", response = Pet.class, responseContainer = "List") + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid status value") }) public Response findPetsByStatus(@ApiParam(value = "Status values that need to be considered for filter") @QueryParam("status") List status) throws NotFoundException { @@ -84,10 +77,9 @@ public class PetApi { @Path("/findByTags") @Produces({ "application/json", "application/xml" }) - // Pet - @ApiOperation(value = "Finds Pets by tags", notes = "Muliple tags can be provided with comma seperated strings. Use tag1, tag2, tag3 for testing.", response = Pet.class, responseContainer = "List") - @ApiResponses(value = { - @ApiResponse(code = 400, message = "Invalid tag value") }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Finds Pets by tags", notes = "Muliple tags can be provided with comma seperated strings. Use tag1, tag2, tag3 for testing.", response = Pet.class, responseContainer = "List") + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid tag value") }) public Response findPetsByTags(@ApiParam(value = "Tags to filter by") @QueryParam("tags") List tags) throws NotFoundException { @@ -100,12 +92,11 @@ public class PetApi { @Path("/{petId}") @Produces({ "application/json", "application/xml" }) - // Pet - @ApiOperation(value = "Find pet by ID", notes = "Returns a pet when ID < 10. ID > 10 or nonintegers will simulate API error conditions", response = Pet.class) - @ApiResponses(value = { - @ApiResponse(code = 404, message = "Pet not found"), + @com.wordnik.swagger.annotations.ApiOperation(value = "Find pet by ID", notes = "Returns a pet when ID < 10. ID > 10 or nonintegers will simulate API error conditions", response = Pet.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "Pet not found"), - @ApiResponse(code = 400, message = "Invalid ID supplied") }) + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid ID supplied") }) public Response getPetById(@ApiParam(value = "ID of pet that needs to be fetched",required=true ) @PathParam("petId") Long petId) throws NotFoundException { @@ -118,10 +109,9 @@ public class PetApi { @Path("/{petId}") @Consumes({ "application/x-www-form-urlencoded" }) @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Updates a pet in the store with form data", notes = "", response = Void.class) - @ApiResponses(value = { - @ApiResponse(code = 405, message = "Invalid input") }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Updates a pet in the store with form data", notes = "", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 405, message = "Invalid input") }) public Response updatePetWithForm(@ApiParam(value = "ID of pet that needs to be updated",required=true ) @PathParam("petId") String petId, @ApiParam(value = "Updated name of the pet" )@FormParam("name") String name, @@ -136,10 +126,9 @@ public class PetApi { @Path("/{petId}") @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Deletes a pet", notes = "", response = Void.class) - @ApiResponses(value = { - @ApiResponse(code = 400, message = "Invalid pet value") }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Deletes a pet", notes = "", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid pet value") }) public Response deletePet(@ApiParam(value = "" )@HeaderParam("api_key") String api_key, @ApiParam(value = "Pet id to delete",required=true ) @PathParam("petId") Long petId) @@ -153,9 +142,8 @@ public class PetApi { @Path("/{petId}/uploadImage") @Consumes({ "multipart/form-data" }) @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "uploads an image", notes = "", response = Void.class) - @ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiOperation(value = "uploads an image", notes = "", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { }) public Response uploadFile(@ApiParam(value = "ID of pet to update",required=true ) @PathParam("petId") Long petId, @ApiParam(value = "Additional data to pass to server" )@FormParam("additionalMetadata") String additionalMetadata, diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java index a005554473..a61879188c 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java @@ -2,11 +2,7 @@ package io.swagger.api; import io.swagger.model.*; -import com.wordnik.swagger.annotations.Api; import com.wordnik.swagger.annotations.ApiParam; -import com.wordnik.swagger.annotations.ApiOperation; -import com.wordnik.swagger.annotations.ApiResponse; -import com.wordnik.swagger.annotations.ApiResponses; import com.sun.jersey.multipart.FormDataParam; @@ -25,16 +21,15 @@ import javax.ws.rs.core.Response; import javax.ws.rs.*; @Path("/store") -@Api(value = "/store", description = "the store API") +@com.wordnik.swagger.annotations.Api(value = "/store", description = "the store API") public class StoreApi { @GET @Path("/inventory") @Produces({ "application/json", "application/xml" }) - // Integer - @ApiOperation(value = "Returns pet inventories by status", notes = "Returns a map of status codes to quantities", response = Integer.class, responseContainer = "map") - @ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Returns pet inventories by status", notes = "Returns a map of status codes to quantities", response = Integer.class, responseContainer = "map") + @com.wordnik.swagger.annotations.ApiResponses(value = { }) public Response getInventory() throws NotFoundException { @@ -47,10 +42,9 @@ public class StoreApi { @Path("/order") @Produces({ "application/json", "application/xml" }) - // Order - @ApiOperation(value = "Place an order for a pet", notes = "", response = Order.class) - @ApiResponses(value = { - @ApiResponse(code = 400, message = "Invalid Order") }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Place an order for a pet", notes = "", response = Order.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid Order") }) public Response placeOrder(@ApiParam(value = "order placed for purchasing the pet" ) Order body) throws NotFoundException { @@ -63,12 +57,11 @@ public class StoreApi { @Path("/order/{orderId}") @Produces({ "application/json", "application/xml" }) - // Order - @ApiOperation(value = "Find purchase order by ID", notes = "For valid response try integer IDs with value <= 5 or > 10. Other values will generated exceptions", response = Order.class) - @ApiResponses(value = { - @ApiResponse(code = 404, message = "Order not found"), + @com.wordnik.swagger.annotations.ApiOperation(value = "Find purchase order by ID", notes = "For valid response try integer IDs with value <= 5 or > 10. Other values will generated exceptions", response = Order.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "Order not found"), - @ApiResponse(code = 400, message = "Invalid ID supplied") }) + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid ID supplied") }) public Response getOrderById(@ApiParam(value = "ID of pet that needs to be fetched",required=true ) @PathParam("orderId") String orderId) throws NotFoundException { @@ -81,12 +74,11 @@ public class StoreApi { @Path("/order/{orderId}") @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Delete purchase order by ID", notes = "For valid response try integer IDs with value < 1000. Anything above 1000 or nonintegers will generate API errors", response = Void.class) - @ApiResponses(value = { - @ApiResponse(code = 404, message = "Order not found"), + @com.wordnik.swagger.annotations.ApiOperation(value = "Delete purchase order by ID", notes = "For valid response try integer IDs with value < 1000. Anything above 1000 or nonintegers will generate API errors", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "Order not found"), - @ApiResponse(code = 400, message = "Invalid ID supplied") }) + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid ID supplied") }) public Response deleteOrder(@ApiParam(value = "ID of the order that needs to be deleted",required=true ) @PathParam("orderId") String orderId) throws NotFoundException { diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java index 1c40c0409b..2bccc374bf 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java @@ -2,11 +2,7 @@ package io.swagger.api; import io.swagger.model.*; -import com.wordnik.swagger.annotations.Api; import com.wordnik.swagger.annotations.ApiParam; -import com.wordnik.swagger.annotations.ApiOperation; -import com.wordnik.swagger.annotations.ApiResponse; -import com.wordnik.swagger.annotations.ApiResponses; import com.sun.jersey.multipart.FormDataParam; @@ -25,16 +21,15 @@ import javax.ws.rs.core.Response; import javax.ws.rs.*; @Path("/user") -@Api(value = "/user", description = "the user API") +@com.wordnik.swagger.annotations.Api(value = "/user", description = "the user API") public class UserApi { @POST @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Create user", notes = "This can only be done by the logged in user.", response = Void.class) - @ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Create user", notes = "This can only be done by the logged in user.", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { }) public Response createUser(@ApiParam(value = "Created user object" ) User body) throws NotFoundException { @@ -47,9 +42,8 @@ public class UserApi { @Path("/createWithArray") @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Creates list of users with given input array", notes = "", response = Void.class) - @ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Creates list of users with given input array", notes = "", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { }) public Response createUsersWithArrayInput(@ApiParam(value = "List of user object" ) List body) throws NotFoundException { @@ -62,9 +56,8 @@ public class UserApi { @Path("/createWithList") @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Creates list of users with given input array", notes = "", response = Void.class) - @ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Creates list of users with given input array", notes = "", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { }) public Response createUsersWithListInput(@ApiParam(value = "List of user object" ) List body) throws NotFoundException { @@ -77,10 +70,9 @@ public class UserApi { @Path("/login") @Produces({ "application/json", "application/xml" }) - // String - @ApiOperation(value = "Logs user into the system", notes = "", response = String.class) - @ApiResponses(value = { - @ApiResponse(code = 400, message = "Invalid username/password supplied") }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Logs user into the system", notes = "", response = String.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid username/password supplied") }) public Response loginUser(@ApiParam(value = "The user name for login") @QueryParam("username") String username, @ApiParam(value = "The password for login in clear text") @QueryParam("password") String password) @@ -94,9 +86,8 @@ public class UserApi { @Path("/logout") @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Logs out current logged in user session", notes = "", response = Void.class) - @ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiOperation(value = "Logs out current logged in user session", notes = "", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { }) public Response logoutUser() throws NotFoundException { @@ -109,12 +100,11 @@ public class UserApi { @Path("/{username}") @Produces({ "application/json", "application/xml" }) - // User - @ApiOperation(value = "Get user by user name", notes = "", response = User.class) - @ApiResponses(value = { - @ApiResponse(code = 404, message = "User not found"), + @com.wordnik.swagger.annotations.ApiOperation(value = "Get user by user name", notes = "", response = User.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "User not found"), - @ApiResponse(code = 400, message = "Invalid username supplied") }) + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid username supplied") }) public Response getUserByName(@ApiParam(value = "The name that needs to be fetched. Use user1 for testing. ",required=true ) @PathParam("username") String username) throws NotFoundException { @@ -127,12 +117,11 @@ public class UserApi { @Path("/{username}") @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Updated user", notes = "This can only be done by the logged in user.", response = Void.class) - @ApiResponses(value = { - @ApiResponse(code = 404, message = "User not found"), + @com.wordnik.swagger.annotations.ApiOperation(value = "Updated user", notes = "This can only be done by the logged in user.", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "User not found"), - @ApiResponse(code = 400, message = "Invalid user supplied") }) + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid user supplied") }) public Response updateUser(@ApiParam(value = "name that need to be deleted",required=true ) @PathParam("username") String username, @ApiParam(value = "Updated user object" ) User body) @@ -146,12 +135,11 @@ public class UserApi { @Path("/{username}") @Produces({ "application/json", "application/xml" }) - // Void - @ApiOperation(value = "Delete user", notes = "This can only be done by the logged in user.", response = Void.class) - @ApiResponses(value = { - @ApiResponse(code = 404, message = "User not found"), + @com.wordnik.swagger.annotations.ApiOperation(value = "Delete user", notes = "This can only be done by the logged in user.", response = Void.class) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "User not found"), - @ApiResponse(code = 400, message = "Invalid username supplied") }) + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid username supplied") }) public Response deleteUser(@ApiParam(value = "The name that needs to be deleted",required=true ) @PathParam("username") String username) throws NotFoundException { From 23e848b43733d73509b9f1c29ee3e609779912ea Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 25 Feb 2015 07:35:05 -0800 Subject: [PATCH 15/70] added ignored test for #453, nested containers --- .../src/test/scala/Java/JavaModelTest.scala | 31 +++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala b/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala index 513786e460..a93c2676d3 100644 --- a/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala +++ b/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala @@ -124,6 +124,37 @@ class JavaModelTest extends FlatSpec with Matchers { vars.get(0).isContainer should equal (true) } + + ignore should "convert a model with a map with complex list property" in { + val model = new ModelImpl() + .description("a sample model") + .property("translations", new MapProperty() + .additionalProperties( + new ArrayProperty().items(new RefProperty("Pet"))) + ) + .required("id") + + val codegen = new JavaClientCodegen() + val cm = codegen.fromModel("sample", model) + + cm.name should be ("sample") + cm.classname should be ("Sample") + cm.description should be ("a sample model") + cm.vars.size should be (1) + + val vars = cm.vars + vars.get(0).baseName should be ("translations") + vars.get(0).getter should be ("getTranslations") + vars.get(0).setter should be ("setTranslations") + vars.get(0).datatype should be ("Map>") + vars.get(0).name should be ("translations") + vars.get(0).defaultValue should be ("new HashMap>() ") + vars.get(0).baseType should be ("Map") + vars.get(0).containerType should be ("map") + vars.get(0).required should equal (false) + vars.get(0).isContainer should equal (true) + } + it should "convert a model with complex properties" in { val model = new ModelImpl() .description("a sample model") From 5713dce00a8f7d13de1f9c566775901a2dee1662 Mon Sep 17 00:00:00 2001 From: Camille Chafer Date: Wed, 25 Feb 2015 15:01:07 +0100 Subject: [PATCH 16/70] add missing types on the Responses Object implementation( CodegenResponse.java) (part of #293) --- .../swagger/codegen/CodegenResponse.java | 5 +++ .../swagger/codegen/DefaultCodegen.java | 34 +++++++++++++++++++ 2 files changed, 39 insertions(+) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java index 92b908759b..d940e4922e 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java @@ -6,5 +6,10 @@ public class CodegenResponse { public String code, message; public Boolean hasMore; public List> examples; + public String dataType, baseType, containerType; + public Boolean simpleType; + public Boolean primitiveType; + public Boolean isMapContainer; + public Boolean isListContainer; Object schema; } \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index 014a595ae1..e971eff343 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -752,6 +752,40 @@ public class DefaultCodegen { r.message = response.getDescription(); r.schema = response.getSchema(); r.examples = toExamples(response.getExamples()); + + if (r.schema != null) { + Property responseProperty = response.getSchema(); + responseProperty.setRequired(true); + CodegenProperty cm = fromProperty("response", responseProperty); + + if(responseProperty instanceof ArrayProperty) { + ArrayProperty ap = (ArrayProperty) responseProperty; + CodegenProperty innerProperty = fromProperty("response", ap.getItems()); + r.baseType = innerProperty.baseType; + } + else { + if(cm.complexType != null) + r.baseType = cm.complexType; + else + r.baseType = cm.baseType; + } + r.dataType = cm.datatype; + if(cm.isContainer != null) { + r.simpleType = false; + r.containerType = cm.containerType; + r.isMapContainer = "map".equals(cm.containerType); + r.isListContainer = "list".equals(cm.containerType); + } + else + r.simpleType = true; + r.primitiveType = (r.baseType == null ||languageSpecificPrimitives().contains(r.baseType)); + } + if (r.baseType == null) { + r.isMapContainer = false; + r.isListContainer = false; + r.primitiveType = true; + r.simpleType = true; + } return r; } From f9a16d856ce28f61b8c3ea89a5451f6441f7fcc0 Mon Sep 17 00:00:00 2001 From: Camille Chafer Date: Wed, 25 Feb 2015 16:23:58 +0100 Subject: [PATCH 17/70] Add 'default' response (200) to responses list, and add Types to the CodegenResponse object (#293). In the same time, clarify, simplfy and factorize code. --- .../swagger/codegen/DefaultCodegen.java | 111 ++++++-------- .../resources/2_0/responseSelectionTest.json | 139 ++++++++++++++++++ .../src/test/scala/CodegenTest.scala | 27 ++++ 3 files changed, 214 insertions(+), 63 deletions(-) create mode 100644 modules/swagger-codegen/src/test/resources/2_0/responseSelectionTest.json diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index e971eff343..7b600ff488 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -142,6 +142,8 @@ public class DefaultCodegen { return name; } + public String toOperationId(String operationId) { return operationId; } + public String toVarName(String name) { if(reservedWords.contains(name)) return escapeReservedWord(name); @@ -156,6 +158,7 @@ public class DefaultCodegen { return name; } + public String escapeReservedWord(String name) { throw new RuntimeException("reserved word " + name + " not allowed"); } @@ -537,6 +540,20 @@ public class DefaultCodegen { return property; } + private Response findMethodResponse(Map responses) { + String code = null; + for(String responseCode : responses.keySet()) { + if (responseCode.startsWith("2") || responseCode.equals("default")) { + if (code == null || code.compareTo(responseCode) > 0) { + code = responseCode; + } + } + } + if (code == null) + return null; + return responses.get(code); + } + public CodegenOperation fromOperation(String path, String httpMethod, Operation operation){ CodegenOperation op = CodegenModelFactory.newInstance(CodegenModelType.OPERATION); Set imports = new HashSet(); @@ -566,13 +583,11 @@ public class DefaultCodegen { LOGGER.warn("generated operationId " + operationId); } op.path = path; - op.operationId = operationId; + op.operationId = toOperationId(operationId); op.summary = escapeText(operation.getSummary()); op.notes = escapeText(operation.getDescription()); op.tags = operation.getTags(); - Response methodResponse = null; - if(operation.getConsumes() != null && operation.getConsumes().size() > 0) { List> c = new ArrayList>(); int count = 0; @@ -603,69 +618,39 @@ public class DefaultCodegen { op.hasProduces = true; } - if(operation.getResponses() != null) { - for(String responseCode: new TreeSet(operation.getResponses().keySet())) { - Response response = operation.getResponses().get(responseCode); - if (responseCode.startsWith("2")) { - // use the first, i.e. the smallest 2xx response status as methodResponse - methodResponse = response; - break; + if (operation.getResponses() != null && !operation.getResponses().isEmpty()) { + + Response methodResponse = findMethodResponse(operation.getResponses()); + CodegenResponse methodCodegenResponse = null; + + for (Map.Entry entry : operation.getResponses().entrySet()) { + Response response = entry.getValue(); + CodegenResponse r = fromResponse(entry.getKey(), response); + r.hasMore = true; + if (response == methodResponse) + methodCodegenResponse = r; + op.responses.add(r); + } + op.responses.get(op.responses.size() - 1).hasMore = false; + + if (methodResponse != null) { + op.returnType = methodCodegenResponse.dataType; + op.returnBaseType = methodCodegenResponse.baseType; + op.returnSimpleType = methodCodegenResponse.simpleType; + op.returnTypeIsPrimitive = methodCodegenResponse.primitiveType; + op.returnContainer = methodCodegenResponse.containerType; + op.isListContainer = methodCodegenResponse.isListContainer; + op.isMapContainer = methodCodegenResponse.isMapContainer; + if (methodResponse.getSchema() != null) { + Property responseProperty = methodResponse.getSchema(); + responseProperty.setRequired(true); + CodegenProperty cm = fromProperty("response", responseProperty); + op.examples = toExamples(methodResponse.getExamples()); + op.defaultResponse = toDefaultValue(responseProperty); + addHeaders(methodResponse, op.responseHeaders); } - } - if(methodResponse == null && operation.getResponses().keySet().contains("default")) { - methodResponse = operation.getResponses().get("default"); - } - for(String responseCode: operation.getResponses().keySet()) { - Response response = operation.getResponses().get(responseCode); - if(response != methodResponse) { - CodegenResponse r = fromResponse(responseCode, response); - op.responses.add(r); - } - for(int i = 0; i < op.responses.size() - 1; i++) { - CodegenResponse r = op.responses.get(i); - r.hasMore = new Boolean(true); - } - } - } - if(methodResponse != null) { - if (methodResponse.getSchema() != null) { - CodegenProperty cm = fromProperty("response", methodResponse.getSchema()); - - Property responseProperty = methodResponse.getSchema(); - - if(responseProperty instanceof ArrayProperty) { - ArrayProperty ap = (ArrayProperty) responseProperty; - CodegenProperty innerProperty = fromProperty("response", ap.getItems()); - op.returnBaseType = innerProperty.baseType; } - else { - if(cm.complexType != null) - op.returnBaseType = cm.complexType; - else - op.returnBaseType = cm.baseType; - } - op.examples = toExamples(methodResponse.getExamples()); - op.defaultResponse = toDefaultValue(responseProperty); - op.returnType = cm.datatype; - if(cm.isContainer != null) { - op.returnContainer = cm.containerType; - if("map".equals(cm.containerType)) - op.isMapContainer = Boolean.TRUE; - else if ("list".equalsIgnoreCase(cm.containerType)) - op.isListContainer = Boolean.TRUE; - } - else - op.returnSimpleType = true; - if (languageSpecificPrimitives().contains(op.returnBaseType) || op.returnBaseType == null) - op.returnTypeIsPrimitive = true; - } - addHeaders(methodResponse, op.responseHeaders); - } - - if(op.returnBaseType == null) { - op.returnTypeIsPrimitive = true; - op.returnSimpleType = true; } if(op.returnBaseType != null && diff --git a/modules/swagger-codegen/src/test/resources/2_0/responseSelectionTest.json b/modules/swagger-codegen/src/test/resources/2_0/responseSelectionTest.json new file mode 100644 index 0000000000..f698c96425 --- /dev/null +++ b/modules/swagger-codegen/src/test/resources/2_0/responseSelectionTest.json @@ -0,0 +1,139 @@ +{ + "swagger": "2.0", + "info": { + "description": "This is a sample server Petstore server. You can find out more about Swagger at http://swagger.io or on irc.freenode.net, #swagger. For this sample, you can use the api key \"special-key\" to test the authorization filters", + "version": "1.0.0", + "title": "Swagger Petstore", + "termsOfService": "http://helloreverb.com/terms/", + "contact": { + "email": "apiteam@wordnik.com" + }, + "license": { + "name": "Apache 2.0", + "url": "http://www.apache.org/licenses/LICENSE-2.0.html" + } + }, + "host": "petstore.swagger.io", + "basePath": "/v2", + "schemes": [ + "http" + ], + "paths": { + "/tests/withTwoHundredAndDefault": { + "get": { + "summary": "Operation with several unordered 2XX results and one default", + "description": "", + "operationId": "withTwoHundredAndDefault", + "produces": [ + "application/json" + ], + "responses": { + "default": { + "description": "default response", + "schema": { + "type": "integer", + "format": "int32" + } + }, + "100": { + "description": "100 response", + "schema": { + "type": "integer", + "format": "int32" + } + }, + "202": { + "description": "201 response", + "schema": { + "type": "integer", + "format": "int64" + } + }, + "203": { + "description": "202 response", + "schema": { + "type": "integer", + "format": "int32" + } + }, + "400": { + "description": "400 response", + "schema": { + "type": "integer", + "format": "int32" + } + }, + "201": { + "description": "200 response", + "schema": { + "type": "string" + } + } + } + } + }, + "/tests/withoutTwoHundredButDefault": { + "get": { + "summary": "Operation with several unordered 2XX results and one default", + "description": "", + "operationId": "withoutTwoHundredButDefault", + "produces": [ + "application/json" + ], + "responses": { + "default": { + "description": "default response", + "schema": { + "type": "string" + } + }, + "100": { + "description": "100 response", + "schema": { + "type": "integer", + "format": "int32" + } + }, + "301": { + "description": "301 response", + "schema": { + "type": "integer", + "format": "int64" + } + } + } + } + } + }, + "securityDefinitions": { + "api_key": { + "type": "apiKey", + "name": "api_key", + "in": "header" + }, + "petstore_auth": { + "type": "oauth2", + "authorizationUrl": "http://petstore.swagger.io/api/oauth/dialog", + "flow": "implicit", + "scopes": { + "write:pets": "modify pets in your account", + "read:pets": "read your pets" + } + } + }, + "definitions": { + "CustomModel": { + "required": ["id"], + "properties": { + "id": { + "type": "integer", + "format": "int64" + }, + "name": { + "type": "string", + "example": "doggie" + } + } + } + } +} \ No newline at end of file diff --git a/modules/swagger-codegen/src/test/scala/CodegenTest.scala b/modules/swagger-codegen/src/test/scala/CodegenTest.scala index a9ccbd9f0f..91f0c5dba2 100644 --- a/modules/swagger-codegen/src/test/scala/CodegenTest.scala +++ b/modules/swagger-codegen/src/test/scala/CodegenTest.scala @@ -94,4 +94,31 @@ class CodegenTest extends FlatSpec with Matchers { statusParam.required should equal (false) statusParam.hasMore should be (null) } + + it should "select main response from a 2.0 spec using the lowest 2XX code" in { + val model = new SwaggerParser() + .read("src/test/resources/2_0/responseSelectionTest.json") + + val codegen = new DefaultCodegen() + + val path = "/tests/withTwoHundredAndDefault" + val p = model.getPaths().get(path).getGet() + val op = codegen.fromOperation(path, "get", p) + op.returnType should be("String") + + } + + it should "select main response from a 2.0 spec using the default keyword when no 2XX code" in { + val model = new SwaggerParser() + .read("src/test/resources/2_0/responseSelectionTest.json") + + val codegen = new DefaultCodegen() + + val path = "/tests/withoutTwoHundredButDefault" + val p = model.getPaths().get(path).getGet() + val op = codegen.fromOperation(path, "get", p) + op.returnType should be("String") + + } + } \ No newline at end of file From c15ac0b6d4c946b6b78822cc7f8cb25ace2cdffc Mon Sep 17 00:00:00 2001 From: Camille Chafer Date: Wed, 25 Feb 2015 17:12:28 +0100 Subject: [PATCH 18/70] Each type used by any response is now added to the imports list --- .../com/wordnik/swagger/codegen/DefaultCodegen.java | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index 7b600ff488..5e60c425c3 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -541,6 +541,7 @@ public class DefaultCodegen { } private Response findMethodResponse(Map responses) { + String code = null; for(String responseCode : responses.keySet()) { if (responseCode.startsWith("2") || responseCode.equals("default")) { @@ -627,6 +628,11 @@ public class DefaultCodegen { Response response = entry.getValue(); CodegenResponse r = fromResponse(entry.getKey(), response); r.hasMore = true; + if(r.baseType != null && + !defaultIncludes.contains(r.baseType) && + !languageSpecificPrimitives.contains(r.baseType)) + imports.add(r.baseType); + if (response == methodResponse) methodCodegenResponse = r; op.responses.add(r); @@ -653,11 +659,6 @@ public class DefaultCodegen { } } - if(op.returnBaseType != null && - !defaultIncludes.contains(op.returnBaseType) && - !languageSpecificPrimitives.contains(op.returnBaseType)) - imports.add(op.returnBaseType); - List parameters = operation.getParameters(); CodegenParameter bodyParam = null; List allParams = new ArrayList(); From 8fb180133a36272255f57fc1afc7d2ef0f9a91e2 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 2 Mar 2015 10:59:35 -0800 Subject: [PATCH 19/70] merged from master --- .../src/main/java/com/wordnik/swagger/codegen/Codegen.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/Codegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/Codegen.java index ac3a856624..082039fc1f 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/Codegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/Codegen.java @@ -44,7 +44,7 @@ public class Codegen extends DefaultGenerator { options.addOption("i", "input-spec", true, "location of the swagger spec, as URL or file"); options.addOption("t", "template-dir", true, "folder containing the template files"); options.addOption("d", "debug-info", false, "prints additional info for debugging"); - options.addOption("a", "auth", false, "addes authorization headers when fetching the swagger definitions remotely. Pass in a URL-encoded string of name:header with a comma separating multiple values"); + options.addOption("a", "auth", true, "adds authorization headers when fetching the swagger definitions remotely. Pass in a URL-encoded string of name:header with a comma separating multiple values"); ClientOptInput clientOptInput = new ClientOptInput(); ClientOpts clientOpts = new ClientOpts(); From 6b823b88d9c56ee10cbcda375f8fe3bb56e1f2ee Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 2 Mar 2015 17:29:29 -0800 Subject: [PATCH 20/70] moved logic into abstract class for extensions --- .../swagger/codegen/AbstractGenerator.java | 60 +++++++++++++++++++ .../swagger/codegen/DefaultGenerator.java | 55 +---------------- 2 files changed, 62 insertions(+), 53 deletions(-) create mode 100644 modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/AbstractGenerator.java diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/AbstractGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/AbstractGenerator.java new file mode 100644 index 0000000000..fa5131dbdc --- /dev/null +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/AbstractGenerator.java @@ -0,0 +1,60 @@ +package com.wordnik.swagger.codegen; + +import com.samskivert.mustache.*; + +import java.util.regex.Pattern; +import java.io.*; + +public abstract class AbstractGenerator { + + public File writeToFile(String filename, String contents) throws IOException { + System.out.println("writing file " + filename); + File output = new File(filename); + + if(output.getParent() != null && !new File(output.getParent()).exists()) { + File parent = new File(output.getParent()); + parent.mkdirs(); + } + Writer out = new BufferedWriter(new OutputStreamWriter( + new FileOutputStream(output), "UTF-8")); + + out.write(contents); + out.close(); + return output; + } + + public String readTemplate(String name) { + try{ + Reader reader = getTemplateReader(name); + if(reader == null) + throw new RuntimeException("no file found"); + java.util.Scanner s = new java.util.Scanner(reader).useDelimiter("\\A"); + return s.hasNext() ? s.next() : ""; + } + catch(Exception e) { + e.printStackTrace(); + } + throw new RuntimeException("can't load template " + name); + } + + public Reader getTemplateReader(String name) { + try{ + InputStream is = this.getClass().getClassLoader().getResourceAsStream(getCPResourcePath(name)); + if(is == null) + is = new FileInputStream(new File(name)); + if(is == null) + throw new RuntimeException("no file found"); + return new InputStreamReader(is); + } + catch(Exception e) { + e.printStackTrace(); + } + throw new RuntimeException("can't load template " + name); + } + + private String getCPResourcePath(String name) { + if (!"/".equals(File.separator)) + return name.replaceAll(Pattern.quote(File.separator), "/"); + return name; + } +} \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java index 65355d75b1..9237e1c9c6 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java @@ -10,7 +10,7 @@ import java.util.*; import java.util.regex.*; import java.io.*; -public class DefaultGenerator implements Generator { +public class DefaultGenerator extends AbstractGenerator implements Generator { protected CodegenConfig config; protected ClientOptInput opts = null; protected Swagger swagger = null; @@ -259,58 +259,7 @@ public class DefaultGenerator implements Generator { return buf.toString().replaceAll("[^a-zA-Z ]", ""); } - public File writeToFile(String filename, String contents) throws IOException { - System.out.println("writing file " + filename); - File output = new File(filename); - - if(output.getParent() != null && !new File(output.getParent()).exists()) { - File parent = new File(output.getParent()); - parent.mkdirs(); - } - Writer out = new BufferedWriter(new OutputStreamWriter( - new FileOutputStream(output), "UTF-8")); - - out.write(contents); - out.close(); - return output; - } - - public String readTemplate(String name) { - try{ - Reader reader = getTemplateReader(name); - if(reader == null) - throw new RuntimeException("no file found"); - java.util.Scanner s = new java.util.Scanner(reader).useDelimiter("\\A"); - return s.hasNext() ? s.next() : ""; - } - catch(Exception e) { - e.printStackTrace(); - } - throw new RuntimeException("can't load template " + name); - } - - public Reader getTemplateReader(String name) { - try{ - InputStream is = this.getClass().getClassLoader().getResourceAsStream(getCPResourcePath(name)); - if(is == null) - is = new FileInputStream(new File(name)); - if(is == null) - throw new RuntimeException("no file found"); - return new InputStreamReader(is); - } - catch(Exception e) { - e.printStackTrace(); - } - throw new RuntimeException("can't load template " + name); - } - - private String getCPResourcePath(String name) { - if (!"/".equals(File.separator)) - return name.replaceAll(Pattern.quote(File.separator), "/"); - return name; - } - -public Map processOperations(CodegenConfig config, String tag, List ops) { + public Map processOperations(CodegenConfig config, String tag, List ops) { Map operations = new HashMap(); Map objs = new HashMap(); objs.put("classname", config.toApiName(tag)); From a724cd0780d74895b59c09bb20a46c4e46964fff Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 2 Mar 2015 23:28:59 -0800 Subject: [PATCH 21/70] added meta generator --- .../swagger/codegen/MetaGenerator.java | 180 +++++++++++++++++ .../main/resources/codegen/README.mustache | 74 +++++++ .../src/main/resources/codegen/api.template | 28 +++ .../resources/codegen/generatorClass.mustache | 191 ++++++++++++++++++ .../src/main/resources/codegen/model.template | 0 .../src/main/resources/codegen/pom.mustache | 102 ++++++++++ .../main/resources/codegen/services.mustache | 1 + 7 files changed, 576 insertions(+) create mode 100644 modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/MetaGenerator.java create mode 100644 modules/swagger-codegen/src/main/resources/codegen/README.mustache create mode 100644 modules/swagger-codegen/src/main/resources/codegen/api.template create mode 100644 modules/swagger-codegen/src/main/resources/codegen/generatorClass.mustache create mode 100644 modules/swagger-codegen/src/main/resources/codegen/model.template create mode 100644 modules/swagger-codegen/src/main/resources/codegen/pom.mustache create mode 100644 modules/swagger-codegen/src/main/resources/codegen/services.mustache diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/MetaGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/MetaGenerator.java new file mode 100644 index 0000000000..cc88f9a800 --- /dev/null +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/MetaGenerator.java @@ -0,0 +1,180 @@ +package com.wordnik.swagger.codegen; + +import com.wordnik.swagger.codegen.languages.*; +import com.wordnik.swagger.models.Swagger; +import com.wordnik.swagger.models.auth.AuthorizationValue; +import com.wordnik.swagger.util.*; + +import io.swagger.parser.SwaggerParser; + +import com.samskivert.mustache.*; + +import org.apache.commons.cli.*; +import org.apache.commons.io.FileUtils; + +import java.io.File; +import java.io.Reader; +import java.util.*; + +public class MetaGenerator extends AbstractGenerator { + static Map configs = new HashMap(); + static String configString; + static { + List extensions = getExtensions(); + StringBuilder sb = new StringBuilder(); + + for(CodegenConfig config : extensions) { + if(sb.toString().length() != 0) + sb.append(", "); + sb.append(config.getName()); + configs.put(config.getName(), config); + configString = sb.toString(); + } + } + + public static void main(String[] args) { + new MetaGenerator().generate(args); + } + + protected void generate(String[] args) { + StringBuilder sb = new StringBuilder(); + String targetLanguage = null; + String outputFolder = null; + String name = null; + String targetPackage = "com.wordnik.swagger.codegen"; + final String templateDir = "codegen"; + + Options options = new Options(); + options.addOption("h", "help", false, "shows this message"); + options.addOption("l", "lang", false, "client language to generate.\nAvailable languages include:\n\t[" + configString + "]"); + options.addOption("o", "output", true, "where to write the generated files"); + options.addOption("n", "name", true, "the human-readable name of the generator"); + options.addOption("p", "package", true, "the package to put the main class into (defaults to com.wordnik.swagger.codegen"); + + ClientOptInput clientOptInput = new ClientOptInput(); + Swagger swagger = null; + CommandLine cmd = null; + try { + CommandLineParser parser = new BasicParser(); + + cmd = parser.parse(options, args); + if (cmd.hasOption("h")) { + usage(options); + return; + } + if (cmd.hasOption("n")) + name = cmd.getOptionValue("n"); + else { + System.out.println("name is required"); + usage(options); + return; + } + if (cmd.hasOption("l")) + targetLanguage = cmd.getOptionValue("l"); + if (cmd.hasOption("p")) + targetPackage = cmd.getOptionValue("p"); + if (cmd.hasOption("o")) + outputFolder = cmd.getOptionValue("o"); + else { + System.out.println("output folder is required"); + usage(options); + return; + } + } + catch (Exception e) { + usage(options); + return; + } + System.out.println("writing to folder " + outputFolder); + File outputFolderLocation = new File(outputFolder); + if(!outputFolderLocation.exists()) + outputFolderLocation.mkdirs(); + File sourceFolder = new File(outputFolder + File.separator + "src/main/java/" + targetPackage.replace('.', File.separatorChar)); + if(!sourceFolder.exists()) + sourceFolder.mkdirs(); + File resourcesFolder = new File(outputFolder + File.separator + "src/main/resources/META-INF/services"); + if(!resourcesFolder.exists()) + resourcesFolder.mkdirs(); + + String mainClass = Character.toUpperCase(name.charAt(0)) + name.substring(1) + "Generator"; + + List supportingFiles = new ArrayList(); + supportingFiles.add(new SupportingFile("pom.mustache", "", "pom.xml")); + supportingFiles.add(new SupportingFile("generatorClass.mustache", + "src/main/java/" + File.separator + targetPackage.replace('.', File.separatorChar), + mainClass + ".java")); + supportingFiles.add(new SupportingFile("README.mustache", "", "README.md")); + supportingFiles.add(new SupportingFile("api.template", "src/main/resources" + File.separator + name, "api.mustache")); + supportingFiles.add(new SupportingFile("model.template", "src/main/resources" + File.separator + name, "model.mustache")); + + supportingFiles.add(new SupportingFile("services.mustache", "src/main/resources/META-INF/services", "com.wordnik.swagger.codegen.CodegenConfig")); + + List files = new ArrayList(); + + Map data = new HashMap(); + data.put("generatorPackage", targetPackage); + data.put("generatorClass", mainClass); + data.put("name", name); + data.put("fullyQualifiedGeneratorClass", targetPackage + "." + mainClass); + + for(SupportingFile support : supportingFiles) { + try { + String destinationFolder = outputFolder; + if(support.folder != null && !"".equals(support.folder)) + destinationFolder += File.separator + support.folder; + File of = new File(destinationFolder); + if(!of.isDirectory()) + of.mkdirs(); + String outputFilename = destinationFolder + File.separator + support.destinationFilename; + + if(support.templateFile.endsWith("mustache")) { + String template = readTemplate(templateDir + File.separator + support.templateFile); + Template tmpl = Mustache.compiler() + .withLoader(new Mustache.TemplateLoader() { + public Reader getTemplate (String name) { + return getTemplateReader(templateDir + File.separator + name + ".mustache"); + }; + }) + .defaultValue("") + .compile(template); + + writeToFile(outputFilename, tmpl.execute(data)); + files.add(new File(outputFilename)); + } + else { + String template = readTemplate(templateDir + File.separator + support.templateFile); + FileUtils.writeStringToFile(new File(outputFilename), template); + System.out.println("copying file to " + outputFilename); + files.add(new File(outputFilename)); + } + } + catch (java.io.IOException e) { + e.printStackTrace(); + } + } + } + + public static List getExtensions() { + ServiceLoader loader = ServiceLoader.load(CodegenConfig.class); + List output = new ArrayList(); + Iterator itr = loader.iterator(); + while(itr.hasNext()) { + output.add(itr.next()); + } + return output; + } + + static void usage(Options options) { + HelpFormatter formatter = new HelpFormatter(); + formatter.printHelp( "MetaGenerator. Generator for creating a new template set " + + "and configuration for Codegen. The output will be based on the language you " + + "specify, and includes default templates to include.", options ); + } + + public static CodegenConfig getConfig(String name) { + if(configs.containsKey(name)) { + return configs.get(name); + } + return null; + } +} diff --git a/modules/swagger-codegen/src/main/resources/codegen/README.mustache b/modules/swagger-codegen/src/main/resources/codegen/README.mustache new file mode 100644 index 0000000000..d40b9b3581 --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/codegen/README.mustache @@ -0,0 +1,74 @@ +# Swagger Codegen for the {{name}} library + +## Overview +This is a boiler-plate project to generate your own client library with Swagger. It's goal is +to get you started with the basic plumbing so you can put in your own logic. It won't work without +your changes applied. + +## What's Swagger? +The goal of Swaggerâ„¢ is to define a standard, language-agnostic interface to REST APIs which allows both humans and computers to discover and understand the capabilities of the service without access to source code, documentation, or through network traffic inspection. When properly defined via Swagger, a consumer can understand and interact with the remote service with a minimal amount of implementation logic. Similar to what interfaces have done for lower-level programming, Swagger removes the guesswork in calling the service. + + +Check out [Swagger-Spec](https://github.com/swagger-api/swagger-spec) for additional information about the Swagger project, including additional libraries with support for other languages and more. + +## How do I use this? +At this point, you've likely generated a client setup. It will include something along these lines: + +``` +. +|- README.md // this file +|- pom.xml // build script +|-- src +|--- main +|---- java +|----- {{generatorPackage}}.{{generatorClass}}.java // generator file +|---- resources +|----- {{name}} // template files +|----- META-INF +|------ services +|------- com.wordnik.swagger.codegen.CodegenConfig +``` + +You _will_ need to make changes in at least the following: + +`{{generatorClass}}.java` + +Templates in this folder: + +`src/main/resources/{{name}}` + +Once modified, you can run this: + +``` +mvn package +``` + +In your generator project. A single jar file will be produced in `target`. You can now use that with codegen: + +``` +java -cp /path/to/swagger-codegen-distribution:/path/to/your/jar com.wordnik.swagger.codegen.Codegen -l {{name}} -o ./test +``` + +Now your templates are available to the client generator and you can write output values + +## But how do I modify this? +The `{{generatorClass}}.java` has comments in it--lots of comments. There is no good substitute +for reading the code more, though. See how the `{{generatorClass}}` implements `CodegenConfig`. +That class has the signature of all values that can be overridden. + +For the templates themselves, you have a number of values available to you for generation. +You can execute the `java` command from above while passing different debug flags to show +the object you have available during client generation: + +``` +# The following additional debug options are available for all codegen targets: +# -DdebugSwagger prints the swagger specification as interpreted by the codegen +# -DdebugModels prints models passed to the template engine +# -DdebugOperations prints operations passed to the template engine +# -DdebugSupportingFiles prints additional data passed to the template engine + +java -DdebugOperations -cp /path/to/swagger-codegen-distribution:/path/to/your/jar com.wordnik.swagger.codegen.Codegen -l {{name}} -o ./test +``` + +Will, for example, output the debug info for operations. You can use this info +in the `api.mustache` file. \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/codegen/api.template b/modules/swagger-codegen/src/main/resources/codegen/api.template new file mode 100644 index 0000000000..9dbc8dd4ba --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/codegen/api.template @@ -0,0 +1,28 @@ + +# This is a sample api mustache template. It is representing a ficticous +# language and won't be usable or compile to anything without lots of changes. +# Use it as an example. You can access the variables in the generator object +# like such: + +# use the package from the `apiPackage` variable +package: {{package}} + +# operations block +{{#operations}} +classname: {{classname}} + +# loop over each operation in the API: +{{#operation}} + +# each operation has a `nickname`: +nickname: {{nickname}} + +# and parameters: +{{#allParams}} +{{paramName}}: {{dataType}} +{{/allParams}} + +{{/operation}} + +# end of operations block +{{/operations}} \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/codegen/generatorClass.mustache b/modules/swagger-codegen/src/main/resources/codegen/generatorClass.mustache new file mode 100644 index 0000000000..53b3a60ad1 --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/codegen/generatorClass.mustache @@ -0,0 +1,191 @@ +package {{generatorPackage}}; + +import com.wordnik.swagger.codegen.*; +import com.wordnik.swagger.models.properties.*; + +import java.util.*; +import java.io.File; + +public class {{generatorClass}} extends DefaultCodegen implements CodegenConfig { + + // source folder where to write the files + protected String sourceFolder = "src"; + protected String apiVersion = "1.0.0"; + + /** + * Configures the type of generator. + * + * @return the CodegenType for this generator + * @see com.wordnik.swagger.codegen.CodegenType + */ + public CodegenType getTag() { + return CodegenType.CLIENT; + } + + /** + * Configures a friendly name for the generator. This will be used by the generator + * to select the library with the -l flag. + * + * @return the friendly name for the generator + */ + public String getName() { + return "{{name}}"; + } + + /** + * Returns human-friendly help for the generator. Provide the consumer with help + * tips, parameters here + * + * @return A string value for the help message + */ + public String getHelp() { + return "Generates a {{name}} client library."; + } + + public {{generatorClass}}() { + super(); + + // set the output folder here + outputFolder = "generated-code/{{name}}"; + + /** + * Models. You can write model files using the modelTemplateFiles map. + * if you want to create one template for file, you can do so here. + * for multiple files for model, just put another entry in the `modelTemplateFiles` with + * a different extension + */ + modelTemplateFiles.put( + "model.mustache", // the template to use + ".sample"); // the extension for each file to write + + /** + * Api classes. You can write classes for each Api file with the apiTemplateFiles map. + * as with models, add multiple entries with different extensions for multiple files per + * class + */ + apiTemplateFiles.put( + "api.mustache", // the template to use + ".sample"); // the extension for each file to write + + /** + * Template Location. This is the location which templates will be read from. The generator + * will use the resource stream to attempt to read the templates. + */ + templateDir = "{{name}}"; + + /** + * Api Package. Optional, if needed, this can be used in templates + */ + apiPackage = "io.swagger.client.api"; + + /** + * Model Package. Optional, if needed, this can be used in templates + */ + modelPackage = "io.swagger.client.model"; + + /** + * Reserved words. Override this with reserved words specific to your language + */ + reservedWords = new HashSet ( + Arrays.asList( + "sample1", // replace with static values + "sample2") + ); + + /** + * Additional Properties. These values can be passed to the templates and + * are available in models, apis, and supporting files + */ + additionalProperties.put("apiVersion", apiVersion); + + /** + * Supporting Files. You can write single files for the generator with the + * entire object tree available. If the input file has a suffix of `.mustache + * it will be processed by the template engine. Otherwise, it will be copied + */ + supportingFiles.add(new SupportingFile("myFile.mustache", // the input template or file + "", // the destination folder, relative `outputFolder` + "myFile.sample") // the output file + ); + + /** + * Language Specific Primitives. These types will not trigger imports by + * the client generator + */ + languageSpecificPrimitives = new HashSet( + Arrays.asList( + "Type1", // replace these with your types + "Type2") + ); + } + + /** + * Escapes a reserved word as defined in the `reservedWords` array. Handle escaping + * those terms here. This logic is only called if a variable matches the reseved words + * + * @return the escaped term + */ + @Override + public String escapeReservedWord(String name) { + return "_" + name; // add an underscore to the name + } + + /** + * Location to write model files. You can use the modelPackage() as defined when the class is + * instantiated + */ + public String modelFileFolder() { + return outputFolder + "/" + sourceFolder + "/" + modelPackage().replace('.', File.separatorChar); + } + + /** + * Location to write api files. You can use the apiPackage() as defined when the class is + * instantiated + */ + @Override + public String apiFileFolder() { + return outputFolder + "/" + sourceFolder + "/" + apiPackage().replace('.', File.separatorChar); + } + + /** + * Optional - type declaration. This is a String which is used by the templates to instantiate your + * types. There is typically special handling for different property types + * + * @return a string value used as the `dataType` field for model templates, `returnType` for api templates + */ + @Override + public String getTypeDeclaration(Property p) { + if(p instanceof ArrayProperty) { + ArrayProperty ap = (ArrayProperty) p; + Property inner = ap.getItems(); + return getSwaggerType(p) + "[" + getTypeDeclaration(inner) + "]"; + } + else if (p instanceof MapProperty) { + MapProperty mp = (MapProperty) p; + Property inner = mp.getAdditionalProperties(); + return getSwaggerType(p) + "[String, " + getTypeDeclaration(inner) + "]"; + } + return super.getTypeDeclaration(p); + } + + /** + * Optional - swagger type conversion. This is used to map swagger types in a `Property` into + * either language specific types via `typeMapping` or into complex models if there is not a mapping. + * + * @return a string value of the type or complex model for this property + * @see com.wordnik.swagger.models.properties.Property + */ + @Override + public String getSwaggerType(Property p) { + String swaggerType = super.getSwaggerType(p); + String type = null; + if(typeMapping.containsKey(swaggerType)) { + type = typeMapping.get(swaggerType); + if(languageSpecificPrimitives.contains(type)) + return toModelName(type); + } + else + type = swaggerType; + return toModelName(type); + } +} \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/codegen/model.template b/modules/swagger-codegen/src/main/resources/codegen/model.template new file mode 100644 index 0000000000..e69de29bb2 diff --git a/modules/swagger-codegen/src/main/resources/codegen/pom.mustache b/modules/swagger-codegen/src/main/resources/codegen/pom.mustache new file mode 100644 index 0000000000..f827a2f56b --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/codegen/pom.mustache @@ -0,0 +1,102 @@ + + 4.0.0 + io.swagger + {{name}}-swagger-codegen + jar + {{name}}-swagger-codegen + 1.0.0 + + 2.2.0 + + + + + org.apache.maven.plugins + maven-surefire-plugin + 2.12 + + + + loggerPath + conf/log4j.properties + + + -Xms512m -Xmx1500m + methods + pertest + + + + + + org.apache.maven.plugins + maven-jar-plugin + 2.2 + + + + jar + test-jar + + + + + + + + + org.codehaus.mojo + build-helper-maven-plugin + + + add_sources + generate-sources + + add-source + + + + src/main/java + + + + + add_test_sources + generate-test-sources + + add-test-source + + + + src/test/java + + + + + + + org.apache.maven.plugins + maven-compiler-plugin + 2.3.2 + + 1.6 + 1.6 + + + + + + + com.wordnik + swagger-codegen + ${swagger-codegen-version} + provided + + + + 2.1.2-M1 + 1.0.0 + 4.8.1 + + \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/codegen/services.mustache b/modules/swagger-codegen/src/main/resources/codegen/services.mustache new file mode 100644 index 0000000000..9b16ae65f1 --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/codegen/services.mustache @@ -0,0 +1 @@ +{{fullyQualifiedGeneratorClass}} \ No newline at end of file From ced95d658fcabea2958765863320cf1ec773c66d Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 2 Mar 2015 23:37:21 -0800 Subject: [PATCH 22/70] added instructions for the meta generator --- README.md | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/README.md b/README.md index bf580e3e75..a1462f768a 100644 --- a/README.md +++ b/README.md @@ -93,6 +93,17 @@ Don't like the default swagger client syntax? Want a different language support You can look at `modules/swagger-codegen/src/main/resources/${your-language}` for examples. To make your own templates, create your own files and use the `-t` flag to specify your tempalte folder. It actually is that easy. +### Making your own codegen modules +If you're starting a project with a new language and don't see what you need, swagger-codegen can help you create a project to generate your own libraries: + +``` +java -cp modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.3-M1-SNAPSHOT.jar \ + com.wordnik.swagger.codegen.MetaGenerator \ + -o output/myLibrary -n myClientCodegen -p com.my.company.codegen +``` + +This will write, in the folder `output/myLibrary`, all the files you need to get started, including a README.md. Once modified and compiled, you can load your library with the codegen and generate clients with your own, custom-rolled logic. + ### Where is Javascript??? See our [javascript library](http://github.com/swagger-api/swagger-js)--it's completely dynamic and doesn't require static code generation. From 3a5c03c7781ec5ffeb76badbd80d306977507397 Mon Sep 17 00:00:00 2001 From: Corentin Jabot Date: Tue, 3 Mar 2015 11:13:06 +0100 Subject: [PATCH 23/70] Expose Security schemes of operations. A template can now refer to the type ( oath2.0, apiKey, basic ) as well as the name of the security schemes it rquires. Usage : {{#operations}} {{#authMethods}} {{type}} {{name}} {{/authMethods}} {{/operations}} --- .../swagger/codegen/CodegenConfig.java | 3 ++ .../swagger/codegen/CodegenModelType.java | 3 +- .../swagger/codegen/CodegenOperation.java | 1 + .../swagger/codegen/CodegenSecurity.java | 7 ++++ .../swagger/codegen/DefaultCodegen.java | 18 ++++++++++ .../swagger/codegen/DefaultGenerator.java | 36 +++++++++++++++++-- 6 files changed, 64 insertions(+), 4 deletions(-) create mode 100644 modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenSecurity.java diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenConfig.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenConfig.java index 235a9b5ba6..69db1b9d2d 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenConfig.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenConfig.java @@ -1,6 +1,7 @@ package com.wordnik.swagger.codegen; import com.wordnik.swagger.models.*; +import com.wordnik.swagger.models.auth.SecuritySchemeDefinition; import com.wordnik.swagger.models.properties.*; import java.util.*; @@ -35,6 +36,8 @@ public interface CodegenConfig { CodegenModel fromModel(String name, Model model); CodegenOperation fromOperation(String resourcePath, String httpMethod, Operation operation); + List fromSecurity(Map schemes); + Set defaultIncludes(); Map typeMapping(); Map instantiationTypes(); diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenModelType.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenModelType.java index 41c877532f..62f515b6c6 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenModelType.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenModelType.java @@ -6,7 +6,8 @@ public enum CodegenModelType { OPERATION(CodegenOperation.class), PARAMETER(CodegenParameter.class), PROPERTY(CodegenProperty.class), - RESPONSE(CodegenResponse.class); + RESPONSE(CodegenResponse.class), + SECURITY(CodegenSecurity.class); private final Class defaultImplementation; diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenOperation.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenOperation.java index af192e7e98..12b405edeb 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenOperation.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenOperation.java @@ -18,6 +18,7 @@ public class CodegenOperation { public List queryParams = new ArrayList(); public List headerParams = new ArrayList(); public List formParams = new ArrayList(); + public List authMethods; public List tags; public List responses = new ArrayList(); public final List responseHeaders = new ArrayList(); diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenSecurity.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenSecurity.java new file mode 100644 index 0000000000..7323893106 --- /dev/null +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenSecurity.java @@ -0,0 +1,7 @@ +package com.wordnik.swagger.codegen; + +public class CodegenSecurity { + String name; + String type; + Boolean hasMore; +} diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index e121044b54..2abcfad31e 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -1,6 +1,7 @@ package com.wordnik.swagger.codegen; import com.wordnik.swagger.models.*; +import com.wordnik.swagger.models.auth.SecuritySchemeDefinition; import com.wordnik.swagger.models.parameters.*; import com.wordnik.swagger.models.properties.*; import com.wordnik.swagger.util.Json; @@ -880,6 +881,23 @@ public class DefaultCodegen { return p; } + public List fromSecurity(Map schemes) { + if(schemes == null) + return null; + + List secs = new ArrayList(); + for(Iterator entries = schemes.entrySet().iterator(); entries.hasNext(); ) { + Map.Entry entry = (Map.Entry) entries.next(); + + CodegenSecurity sec = CodegenModelFactory.newInstance(CodegenModelType.SECURITY); + sec.name = entry.getKey(); + sec.type = entry.getValue().getType(); + sec.hasMore = entries.hasNext(); + secs.add(sec); + } + return secs; + } + protected List> toExamples(Map examples) { if(examples == null) return null; diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java index 9237e1c9c6..5a405bd2ed 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java @@ -1,6 +1,7 @@ package com.wordnik.swagger.codegen; import com.wordnik.swagger.models.*; +import com.wordnik.swagger.models.auth.SecuritySchemeDefinition; import com.wordnik.swagger.util.*; import com.samskivert.mustache.*; @@ -227,20 +228,49 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { return ops; } + public SecuritySchemeDefinition fromSecurity(String name) { + Map map = swagger.getSecurityDefinitions(); + if(map == null) + return null; + SecuritySchemeDefinition scheme = map.get(name); + if(scheme == null) + return null; + return scheme; + } + + + public void processOperation(String resourcePath, String httpMethod, Operation operation, Map> operations) { if(operation != null) { List tags = operation.getTags(); - if(tags == null) { + if (tags == null) { tags = new ArrayList(); tags.add("default"); } - for(String tag : tags) { + for (String tag : tags) { CodegenOperation co = config.fromOperation(resourcePath, httpMethod, operation); co.tags = new ArrayList(); co.tags.add(sanitizeTag(tag)); - config.addOperationToGroup(sanitizeTag(tag), resourcePath, operation, co, operations); + + List>> securities = operation.getSecurity(); + if(securities == null) + continue; + Map authMethods = new HashMap(); + for (Map> security : securities) { + if (security.size() != 1) { + //Not sure what to do + continue; + } + String securityName = security.keySet().iterator().next(); + SecuritySchemeDefinition securityDefinition = fromSecurity(securityName); + if(securityDefinition != null) + authMethods.put(securityName, securityDefinition); + } + if(!authMethods.isEmpty()) { + co.authMethods = config.fromSecurity(authMethods); + } } } } From 156055fdd504a3a5e5b2c0e1e03bd4c22f2a8749 Mon Sep 17 00:00:00 2001 From: Corentin Jabot Date: Thu, 26 Feb 2015 11:25:14 +0100 Subject: [PATCH 24/70] Fix {{basePath}} value in support files. Make {{basePath}} value in support files be the same as in operation files, aka host/path, instead of /path. --- .../main/java/com/wordnik/swagger/codegen/DefaultGenerator.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java index 9237e1c9c6..e57b944621 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java @@ -150,7 +150,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { Map apis = new HashMap(); apis.put("apis", allOperations); if(swagger.getBasePath() != null) { - bundle.put("basePath", swagger.getBasePath()); + bundle.put("basePath", basePath); } bundle.put("apiInfo", apis); bundle.put("models", allModels); From dc5ee9dcf52d9025cec0c82a2fa03c491a6b0f3f Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 4 Mar 2015 20:44:26 -0800 Subject: [PATCH 25/70] added reserved words --- .../codegen/languages/AndroidClientCodegen.java | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/AndroidClientCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/AndroidClientCodegen.java index 915ff34c7f..72e0985d22 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/AndroidClientCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/AndroidClientCodegen.java @@ -34,6 +34,17 @@ public class AndroidClientCodegen extends DefaultCodegen implements CodegenConfi apiPackage = "io.swagger.client.api"; modelPackage = "io.swagger.client.model"; + reservedWords = new HashSet ( + Arrays.asList( + "abstract", "continue", "for", "new", "switch", "assert", + "default", "if", "package", "synchronized", "boolean", "do", "goto", "private", + "this", "break", "double", "implements", "protected", "throw", "byte", "else", + "import", "public", "throws", "case", "enum", "instanceof", "return", "transient", + "catch", "extends", "int", "short", "try", "char", "final", "interface", "static", + "void", "class", "finally", "long", "strictfp", "volatile", "const", "float", + "native", "super", "while") + ); + additionalProperties.put("invokerPackage", invokerPackage); additionalProperties.put("groupId", groupId); additionalProperties.put("artifactId", artifactId); From 7c23eedf075811f85f3bae4f4316a61a99e39018 Mon Sep 17 00:00:00 2001 From: William Cheng Date: Mon, 9 Mar 2015 23:15:12 +0800 Subject: [PATCH 26/70] use baseName for parameter name in PHP api --- .../swagger-codegen/src/main/resources/php/api.mustache | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/php/api.mustache b/modules/swagger-codegen/src/main/resources/php/api.mustache index 4fd50fa898..9a360aa7ff 100644 --- a/modules/swagger-codegen/src/main/resources/php/api.mustache +++ b/modules/swagger-codegen/src/main/resources/php/api.mustache @@ -50,20 +50,20 @@ class {{classname}} { {{#queryParams}}// query params if(${{paramName}} !== null) { - $queryParams['{{paramName}}'] = $this->apiClient->toQueryValue(${{paramName}}); + $queryParams['{{baseName}}'] = $this->apiClient->toQueryValue(${{paramName}}); }{{/queryParams}} {{#headerParams}}// header params if(${{paramName}} !== null) { - $headerParams['{{paramName}}'] = $this->apiClient->toHeaderValue(${{paramName}}); + $headerParams['{{baseName}}'] = $this->apiClient->toHeaderValue(${{paramName}}); }{{/headerParams}} {{#pathParams}}// path params if(${{paramName}} !== null) { - $resourcePath = str_replace("{" . "{{paramName}}" . "}", + $resourcePath = str_replace("{" . "{{baseName}}" . "}", $this->apiClient->toPathValue(${{paramName}}), $resourcePath); }{{/pathParams}} {{#formParams}} if (${{paramName}} !== null) { - $formParams[{{paramName}}] = {{#isFile}}'@' . {{/isFile}}${{paramName}}; + $formParams[{{baseName}}] = {{#isFile}}'@' . {{/isFile}}${{paramName}}; }{{/formParams}} {{#bodyParams}}// body params $body = null; From e9d0619358d19d58c88825acddd89032429f8e07 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 9 Mar 2015 08:59:16 -0700 Subject: [PATCH 27/70] updated versions --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 544dd4c8c0..3f3458c3f2 100644 --- a/pom.xml +++ b/pom.xml @@ -347,10 +347,10 @@ - 1.0.1 + 1.0.3-SNAPSHOT 2.11.1 2.3.4 - 1.5.2-M1 + 1.5.3-M1-SNAPSHOT 2.1.4 2.3 1.2 From 9c7774204632cb07db48536f413119ab91675b3b Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 9 Mar 2015 09:31:34 -0700 Subject: [PATCH 28/70] updated links --- README.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index a1462f768a..d6e54e6e16 100644 --- a/README.md +++ b/README.md @@ -46,7 +46,7 @@ You can build a client against the swagger sample [petstore](http://petstore.swa This will run the generator with this command: ``` -java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.0-M1.jar \ +java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.3-M1-SNAPSHOT.jar \ -i http://petstore.swagger.io/v2/swagger.json \ -l java \ -o samples/client/petstore/java @@ -200,7 +200,7 @@ You can also use the codegen to generate a server for a couple different framewo ### node.js ``` -java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.0-M1.jar \ +java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.3-M1-SNAPSHOT.jar \ -i http://petstore.swagger.io/v2/swagger.json \ -l nodejs \ -o samples/server/petstore/nodejs @@ -212,7 +212,7 @@ java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distributi ### scala scalatra ``` -java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.0-M1.jar \ +java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.3-M1-SNAPSHOT.jar \ -i http://petstore.swagger.io/v2/swagger.json \ -l scalatra \ -o samples/server/petstore/scalatra @@ -221,7 +221,7 @@ java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distributi ### java jax-rs ``` -java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.0-M1.jar \ +java -jar modules/swagger-codegen-distribution/target/swagger-codegen-distribution-2.1.3-M1-SNAPSHOT.jar \ -i http://petstore.swagger.io/v2/swagger.json \ -l jaxrs \ -o samples/server/petstore/jaxrs From 6207c2b5e9667e33df00484c7a525f0a619425e0 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 9 Mar 2015 10:09:33 -0700 Subject: [PATCH 29/70] fix for #475 building on java8 --- modules/swagger-generator/pom.xml | 8 -------- 1 file changed, 8 deletions(-) diff --git a/modules/swagger-generator/pom.xml b/modules/swagger-generator/pom.xml index 104e2ef6d4..c9a9eb8d56 100644 --- a/modules/swagger-generator/pom.xml +++ b/modules/swagger-generator/pom.xml @@ -221,20 +221,12 @@ - 2.3.4 2.5 1.0.1 - 4.8.1 1.0.0 - 2.4 - 1.6.3 2.5 1.3.2 9.0.7.v20131107 2.4.1 - 1.5.2-M1 - - 3.1.5 - 2.10.0 From 17435212edda9b254aeaad32feac189b330b77c2 Mon Sep 17 00:00:00 2001 From: Brad Figler Date: Mon, 9 Mar 2015 19:00:35 +0000 Subject: [PATCH 30/70] Properly serailze the correct object type versus the parent objClass --- src/main/resources/python3/swagger.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/resources/python3/swagger.mustache b/src/main/resources/python3/swagger.mustache index 722a60a634..f99f0d4d25 100644 --- a/src/main/resources/python3/swagger.mustache +++ b/src/main/resources/python3/swagger.mustache @@ -209,7 +209,7 @@ class ApiClient: setattr(instance, attr, subValues) else: setattr(instance, attr, self.deserialize(value, - objClass)) + attrType)) return instance From 941f6e7757bc0693e5357647e409d3f844fbf7ec Mon Sep 17 00:00:00 2001 From: William Cheng Date: Tue, 10 Mar 2015 18:13:55 +0800 Subject: [PATCH 31/70] add PATCH support to PHP API client --- .../swagger-codegen/src/main/resources/php/Swagger.mustache | 3 +++ 1 file changed, 3 insertions(+) diff --git a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache index a7a1886634..d797bb53e9 100644 --- a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache +++ b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache @@ -107,6 +107,9 @@ class APIClient { if ($method == self::$POST) { curl_setopt($curl, CURLOPT_POST, true); curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); + } else if ($method == self::$PATCH) { + curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PATCH"); + curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); } else if ($method == self::$PUT) { curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PUT"); curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); From 7555dda2bfffacceb2746c1a0d94620f202a0d50 Mon Sep 17 00:00:00 2001 From: William Cheng Date: Wed, 11 Mar 2015 01:37:39 +0800 Subject: [PATCH 32/70] add logic to handle all 2xx response code, bug fix for string response, bug fix for showing error message using serialize --- .../src/main/resources/php/Swagger.mustache | 7 +++++-- samples/client/petstore/php/Swagger.php | 10 ++++++++-- 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache index d797bb53e9..8aed52e290 100644 --- a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache +++ b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache @@ -129,11 +129,14 @@ class APIClient { if ($response_info['http_code'] == 0) { throw new Exception("TIMEOUT: api call to " . $url . " took more than 5s to return" ); - } else if ($response_info['http_code'] == 200) { + } else if ($response_info['http_code'] >= 200 && $response_info['http_code'] <= 299 ) { $data = json_decode($response); + if (json_last_error() > 0) { // if response is a string + $data = $response; + } } else if ($response_info['http_code'] == 401) { throw new Exception("Unauthorized API request to " . $url . - ": ".json_decode($response)->message ); + ": ".serialize($response)); } else if ($response_info['http_code'] == 404) { $data = null; } else { diff --git a/samples/client/petstore/php/Swagger.php b/samples/client/petstore/php/Swagger.php index a7a1886634..8aed52e290 100644 --- a/samples/client/petstore/php/Swagger.php +++ b/samples/client/petstore/php/Swagger.php @@ -107,6 +107,9 @@ class APIClient { if ($method == self::$POST) { curl_setopt($curl, CURLOPT_POST, true); curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); + } else if ($method == self::$PATCH) { + curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PATCH"); + curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); } else if ($method == self::$PUT) { curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PUT"); curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); @@ -126,11 +129,14 @@ class APIClient { if ($response_info['http_code'] == 0) { throw new Exception("TIMEOUT: api call to " . $url . " took more than 5s to return" ); - } else if ($response_info['http_code'] == 200) { + } else if ($response_info['http_code'] >= 200 && $response_info['http_code'] <= 299 ) { $data = json_decode($response); + if (json_last_error() > 0) { // if response is a string + $data = $response; + } } else if ($response_info['http_code'] == 401) { throw new Exception("Unauthorized API request to " . $url . - ": ".json_decode($response)->message ); + ": ".serialize($response)); } else if ($response_info['http_code'] == 404) { $data = null; } else { From 939b4c713d2fb5483fc835d7e525069efec95183 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Tue, 10 Mar 2015 11:42:31 -0700 Subject: [PATCH 33/70] per #458 --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index d6e54e6e16..fc140685e7 100644 --- a/README.md +++ b/README.md @@ -160,7 +160,7 @@ public class MyObjcCodegen extends ObjcClientCodegen { and specify the `classname` when running the generator: ``` --i com.mycompany.swagger.codegen.MyObjcCodegen +-l com.mycompany.swagger.codegen.MyObjcCodegen ``` Your subclass will now be loaded and overrides the `PREFIX` value in the superclass. From d0edb836ac2b9bce7194db2153e7a593035cccb7 Mon Sep 17 00:00:00 2001 From: William Cheng Date: Wed, 11 Mar 2015 15:47:28 +0800 Subject: [PATCH 34/70] fix syntax error at 223, update array comparision (case insensitive) --- .../src/main/resources/php/Swagger.mustache | 5 +++-- samples/client/petstore/php/Swagger.php | 8 ++++++-- 2 files changed, 9 insertions(+), 4 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache index d797bb53e9..b65add845c 100644 --- a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache +++ b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache @@ -223,13 +223,14 @@ class APIClient { $inner = substr($class, 4, -1); $values = array(); if(strrpos($inner, ",") !== false) { - $subClass = explode(',', $inner, 2)[1]; + $subClass_array = explode(',', $inner, 2); + $subClass = $subClass_array[1]; foreach ($data as $key => $value) { $values[] = array($key => self::deserialize($value, $subClass)); } } $deserialized = $values; - } elseif (substr($class, 0, 6) == 'array[') { + } elseif (strcasecmp(substr($class, 0, 6),'array[') == 0) { $subClass = substr($class, 6, -1); $values = array(); foreach ($data as $key => $value) { diff --git a/samples/client/petstore/php/Swagger.php b/samples/client/petstore/php/Swagger.php index a7a1886634..b65add845c 100644 --- a/samples/client/petstore/php/Swagger.php +++ b/samples/client/petstore/php/Swagger.php @@ -107,6 +107,9 @@ class APIClient { if ($method == self::$POST) { curl_setopt($curl, CURLOPT_POST, true); curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); + } else if ($method == self::$PATCH) { + curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PATCH"); + curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); } else if ($method == self::$PUT) { curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PUT"); curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); @@ -220,13 +223,14 @@ class APIClient { $inner = substr($class, 4, -1); $values = array(); if(strrpos($inner, ",") !== false) { - $subClass = explode(',', $inner, 2)[1]; + $subClass_array = explode(',', $inner, 2); + $subClass = $subClass_array[1]; foreach ($data as $key => $value) { $values[] = array($key => self::deserialize($value, $subClass)); } } $deserialized = $values; - } elseif (substr($class, 0, 6) == 'array[') { + } elseif (strcasecmp(substr($class, 0, 6),'array[') == 0) { $subClass = substr($class, 6, -1); $values = array(); foreach ($data as $key => $value) { From 5347915c12269f26882f5c2e24395507525f2554 Mon Sep 17 00:00:00 2001 From: William Cheng Date: Wed, 11 Mar 2015 21:14:17 +0800 Subject: [PATCH 35/70] form parameter(single quote), add more comment --- .../src/main/resources/php/api.mustache | 5 ++-- samples/client/petstore/php/PetApi.php | 24 ++++++++++++------- samples/client/petstore/php/StoreApi.php | 4 ++++ samples/client/petstore/php/Swagger.php | 3 +++ samples/client/petstore/php/UserApi.php | 8 +++++++ 5 files changed, 34 insertions(+), 10 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/php/api.mustache b/modules/swagger-codegen/src/main/resources/php/api.mustache index 9a360aa7ff..7a36c9aa0a 100644 --- a/modules/swagger-codegen/src/main/resources/php/api.mustache +++ b/modules/swagger-codegen/src/main/resources/php/api.mustache @@ -61,9 +61,9 @@ class {{classname}} { $resourcePath = str_replace("{" . "{{baseName}}" . "}", $this->apiClient->toPathValue(${{paramName}}), $resourcePath); }{{/pathParams}} - {{#formParams}} + {{#formParams}}// form params if (${{paramName}} !== null) { - $formParams[{{baseName}}] = {{#isFile}}'@' . {{/isFile}}${{paramName}}; + $formParams['{{baseName}}'] = {{#isFile}}'@' . {{/isFile}}${{paramName}}; }{{/formParams}} {{#bodyParams}}// body params $body = null; @@ -71,6 +71,7 @@ class {{classname}} { $body = ${{paramName}}; }{{/bodyParams}} + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { diff --git a/samples/client/petstore/php/PetApi.php b/samples/client/petstore/php/PetApi.php index da31002dcb..8c7d74cb47 100644 --- a/samples/client/petstore/php/PetApi.php +++ b/samples/client/petstore/php/PetApi.php @@ -57,6 +57,7 @@ class PetApi { $body = $body; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -102,6 +103,7 @@ class PetApi { $body = $body; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -146,6 +148,7 @@ class PetApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -196,6 +199,7 @@ class PetApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -247,6 +251,7 @@ class PetApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -297,15 +302,16 @@ class PetApi { $resourcePath = str_replace("{" . "petId" . "}", $this->apiClient->toPathValue($petId), $resourcePath); } - + // form params if ($name !== null) { - $formParams[name] = $name; - } + $formParams['name'] = $name; + }// form params if ($status !== null) { - $formParams[status] = $status; + $formParams['status'] = $status; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -355,6 +361,7 @@ class PetApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -399,15 +406,16 @@ class PetApi { $resourcePath = str_replace("{" . "petId" . "}", $this->apiClient->toPathValue($petId), $resourcePath); } - + // form params if ($additionalMetadata !== null) { - $formParams[additionalMetadata] = $additionalMetadata; - } + $formParams['additionalMetadata'] = $additionalMetadata; + }// form params if ($file !== null) { - $formParams[file] = '@' . $file; + $formParams['file'] = '@' . $file; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { diff --git a/samples/client/petstore/php/StoreApi.php b/samples/client/petstore/php/StoreApi.php index 0496c08d2e..780012f09a 100644 --- a/samples/client/petstore/php/StoreApi.php +++ b/samples/client/petstore/php/StoreApi.php @@ -52,6 +52,7 @@ class StoreApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -103,6 +104,7 @@ class StoreApi { $body = $body; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -154,6 +156,7 @@ class StoreApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -205,6 +208,7 @@ class StoreApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { diff --git a/samples/client/petstore/php/Swagger.php b/samples/client/petstore/php/Swagger.php index a7a1886634..d797bb53e9 100644 --- a/samples/client/petstore/php/Swagger.php +++ b/samples/client/petstore/php/Swagger.php @@ -107,6 +107,9 @@ class APIClient { if ($method == self::$POST) { curl_setopt($curl, CURLOPT_POST, true); curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); + } else if ($method == self::$PATCH) { + curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PATCH"); + curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); } else if ($method == self::$PUT) { curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PUT"); curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); diff --git a/samples/client/petstore/php/UserApi.php b/samples/client/petstore/php/UserApi.php index 697af96328..cd5d197394 100644 --- a/samples/client/petstore/php/UserApi.php +++ b/samples/client/petstore/php/UserApi.php @@ -57,6 +57,7 @@ class UserApi { $body = $body; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -102,6 +103,7 @@ class UserApi { $body = $body; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -147,6 +149,7 @@ class UserApi { $body = $body; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -195,6 +198,7 @@ class UserApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -241,6 +245,7 @@ class UserApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -286,6 +291,7 @@ class UserApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -342,6 +348,7 @@ class UserApi { $body = $body; } + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { @@ -387,6 +394,7 @@ class UserApi { + // for HTTP post (form) $body = $body ?: $formParams; if (strpos($headerParams['Content-Type'], "application/x-www-form-urlencoded") > -1) { From 56ff34dc47390167122530c43485fc75de1a2d5a Mon Sep 17 00:00:00 2001 From: James Ebentier Date: Thu, 12 Mar 2015 12:12:07 -0700 Subject: [PATCH 36/70] PHP Bindings: exposing response and response info to be accessible through thrown exceptions when non 200 response code is received --- .../src/main/resources/php/Swagger.mustache | 29 +++++++++++++++---- 1 file changed, 23 insertions(+), 6 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache index d797bb53e9..d9da156c50 100644 --- a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache +++ b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache @@ -127,19 +127,19 @@ class APIClient { // Handle the response if ($response_info['http_code'] == 0) { - throw new Exception("TIMEOUT: api call to " . $url . - " took more than 5s to return" ); + throw new APIClientException("TIMEOUT: api call to " . $url . + " took more than 5s to return", 0, $response_info, $response); } else if ($response_info['http_code'] == 200) { $data = json_decode($response); } else if ($response_info['http_code'] == 401) { - throw new Exception("Unauthorized API request to " . $url . - ": ".json_decode($response)->message ); + throw new APIClientException("Unauthorized API request to " . $url . + ": " . json_decode($response)->message, 0, $response_info, $response); } else if ($response_info['http_code'] == 404) { $data = null; } else { - throw new Exception("Can't connect to the api: " . $url . + throw new APIClientException("Can't connect to the api: " . $url . " response code: " . - $response_info['http_code']); + $response_info['http_code'], 0, $response_info, $response); } return $data; } @@ -256,3 +256,20 @@ class APIClient { } +class APIClientException extends Exception { + protected $response, $response_info; + + public class __construct($message="", $code=0, $response_info=null, $response=null) { + parent::__construct($message, $code); + $this->response_info = $response_info; + $this->response = $response; + } + + public function getResponse() { + return $this->response; + } + + public function getResponseInfo() { + return $this->response_info; + } +} From 575967b5de85d9c5d3e1f5196b7207121f4588fc Mon Sep 17 00:00:00 2001 From: James Ebentier Date: Thu, 12 Mar 2015 13:23:46 -0700 Subject: [PATCH 37/70] Fixing bug in new APIClientException This new exception had a typo in it for the construct class declaration. --- modules/swagger-codegen/src/main/resources/php/Swagger.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache index d9da156c50..d25813ae73 100644 --- a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache +++ b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache @@ -259,7 +259,7 @@ class APIClient { class APIClientException extends Exception { protected $response, $response_info; - public class __construct($message="", $code=0, $response_info=null, $response=null) { + public function __construct($message="", $code=0, $response_info=null, $response=null) { parent::__construct($message, $code); $this->response_info = $response_info; $this->response = $response; From 4748af4d59c74cab6113fccfa400f76c4bd5053a Mon Sep 17 00:00:00 2001 From: Michael Burman Date: Fri, 13 Mar 2015 13:18:31 +0200 Subject: [PATCH 38/70] Fix NPE with resourcePath = /, issue #495 (cherry picked from commit 01515e4ded6fa59da87d109dd8056c1b4a64e0f7) --- .../main/java/com/wordnik/swagger/codegen/DefaultCodegen.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index 2abcfad31e..1b3ddc524c 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -314,7 +314,7 @@ public class DefaultCodegen { } public String snakeCase(String name) { - return Character.toLowerCase(name.charAt(0)) + name.substring(1); + return (name.length() > 0) ? (Character.toLowerCase(name.charAt(0)) + name.substring(1)) : ""; } public String initialCaps(String name) { From 470ba201d85b4370c75f83cb72ce1d682b26c8c1 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Fri, 13 Mar 2015 10:45:12 -0700 Subject: [PATCH 39/70] build error fix --- .../swagger/generator/resource/SwaggerResource.java | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java b/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java index b4592a4afc..9cf93ef570 100644 --- a/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java +++ b/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/resource/SwaggerResource.java @@ -37,7 +37,7 @@ public class SwaggerResource { @Produces({MediaType.APPLICATION_OCTET_STREAM}) @ApiOperation(value = "Downloads a pre-generated file", response = String.class, - tags = {@Tag(value = "clients"), @Tag(value = "servers")}) + tags = {"clients", "servers"}) public Response downloadFile(@PathParam("fileId") String fileId) throws Exception { Generated g = fileMap.get(fileId); System.out.println("looking for fileId " + fileId); @@ -61,7 +61,7 @@ public class SwaggerResource { @ApiOperation( value = "Generates a client library based on the config", response = ResponseCode.class, - tags = {@Tag(value = "clients", description = "client operations")}) + tags = "clients") public Response generateClient( @ApiParam(value = "The target language for the client library", allowableValues = "android,java,php,objc,docs", required = true) @PathParam("language") String language, @ApiParam(value = "Configuration for building the client library", required = true) GeneratorInput opts) throws Exception { @@ -88,7 +88,7 @@ public class SwaggerResource { @ApiOperation(value = "Gets languages supported by the client generator", response = String.class, responseContainer = "List", - tags = {@Tag(value = "clients", description = "client operations")}) + tags = "clients") public Response clientOptions() { String[] languages = new String[clients.size()]; languages = clients.toArray(languages); @@ -100,7 +100,7 @@ public class SwaggerResource { @ApiOperation(value = "Gets languages supported by the server generator", response = String.class, responseContainer = "List", - tags = {@Tag(value = "servers", description = "server operations")}) + tags = "servers") public Response serverOptions() { String[] languages = new String[servers.size()]; languages = servers.toArray(languages); @@ -111,7 +111,7 @@ public class SwaggerResource { @Path("/servers/{framework}") @ApiOperation(value = "Generates a server library for the supplied server framework", response = ResponseCode.class, - tags = {@Tag(value = "servers", description = "server operations")}) + tags = "servers") public Response generateServerForLanguage( @ApiParam(value = "framework", allowableValues = "jaxrs,nodejs", required = true) @PathParam("framework") String framework, @ApiParam(value = "parameters", required = true) GeneratorInput opts) From 6ca34e362def122e10d858e4c462508a987f21b2 Mon Sep 17 00:00:00 2001 From: James Ebentier Date: Fri, 13 Mar 2015 09:21:13 -0700 Subject: [PATCH 40/70] PHP Models: updating the models generated for PHP to be array accessable and have a simple constructor --- .../src/main/resources/php/model.mustache | 22 ++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/resources/php/model.mustache b/modules/swagger-codegen/src/main/resources/php/model.mustache index 13a9356d58..6de69cbafd 100644 --- a/modules/swagger-codegen/src/main/resources/php/model.mustache +++ b/modules/swagger-codegen/src/main/resources/php/model.mustache @@ -24,7 +24,7 @@ {{#models}} {{#model}} -class {{classname}} { +class {{classname}} implements ArrayAccess { static $swaggerTypes = array( {{#vars}}'{{name}}' => '{{{datatype}}}'{{#hasMore}}, {{/hasMore}}{{/vars}} @@ -35,6 +35,26 @@ class {{classname}} { * {{{description}}} */{{/description}} public ${{name}}; /* {{{datatype}}} */{{/vars}} + + public function __construct(array $data) { + {{#vars}}$this->{{name}} = $data["{{name}}"]{{/vars}} + } + + public function offsetExists($offset) { + return isset($this->$offset); + } + + public function offsetGet($offset) { + return $this->$offset; + } + + public function offsetSet($offset, $value) { + $this->$offset = $value; + } + + public function offsetUnset($offset) { + unset($this->$offset); + } } {{/model}} {{/models}} From 0854ca5ce53b159d92f1672d53a100a8c15e080d Mon Sep 17 00:00:00 2001 From: James Ebentier Date: Fri, 13 Mar 2015 09:23:55 -0700 Subject: [PATCH 41/70] PHP Models: updating the models generated for PHP styling --- modules/swagger-codegen/src/main/resources/php/model.mustache | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/resources/php/model.mustache b/modules/swagger-codegen/src/main/resources/php/model.mustache index 6de69cbafd..606203f894 100644 --- a/modules/swagger-codegen/src/main/resources/php/model.mustache +++ b/modules/swagger-codegen/src/main/resources/php/model.mustache @@ -37,7 +37,8 @@ class {{classname}} implements ArrayAccess { public ${{name}}; /* {{{datatype}}} */{{/vars}} public function __construct(array $data) { - {{#vars}}$this->{{name}} = $data["{{name}}"]{{/vars}} + {{#vars}}$this->{{name}} = $data["{{name}}"];{{#hasMore}}, + {{/hasMore}}{{/vars}} } public function offsetExists($offset) { From 24842d4a29213efe9b7f49c2581f546af7a252ef Mon Sep 17 00:00:00 2001 From: James Ebentier Date: Fri, 13 Mar 2015 09:36:24 -0700 Subject: [PATCH 42/70] PHP Models: fixing an issue with commas being where they shouldn't --- modules/swagger-codegen/src/main/resources/php/model.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/resources/php/model.mustache b/modules/swagger-codegen/src/main/resources/php/model.mustache index 606203f894..f11a154716 100644 --- a/modules/swagger-codegen/src/main/resources/php/model.mustache +++ b/modules/swagger-codegen/src/main/resources/php/model.mustache @@ -37,7 +37,7 @@ class {{classname}} implements ArrayAccess { public ${{name}}; /* {{{datatype}}} */{{/vars}} public function __construct(array $data) { - {{#vars}}$this->{{name}} = $data["{{name}}"];{{#hasMore}}, + {{#vars}}$this->{{name}} = $data["{{name}}"];{{#hasMore}} {{/hasMore}}{{/vars}} } From a0dc2097eb2f6e947fc0e58e4c05163f814ff011 Mon Sep 17 00:00:00 2001 From: William Cheng Date: Sat, 14 Mar 2015 23:48:05 +0800 Subject: [PATCH 43/70] update php api client to support datetime (iso8601) for parameters (header, path, url, form) --- .../src/main/resources/php/Swagger.mustache | 38 +++++++++-- .../src/main/resources/php/api.mustache | 2 +- samples/client/petstore/php/PetApi.php | 8 +-- samples/client/petstore/php/Swagger.php | 67 ++++++++++++++++--- 4 files changed, 94 insertions(+), 21 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache index d332cbc2e7..1247be83f3 100644 --- a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache +++ b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache @@ -178,7 +178,7 @@ class APIClient { * @return string the serialized object */ public static function toPathValue($value) { - return rawurlencode($value); + return rawurlencode(toString($value)); } /** @@ -193,20 +193,48 @@ class APIClient { if (is_array($object)) { return implode(',', $object); } else { - return $object; + return toString($object); } } /** - * Just pass through the header value for now. Placeholder in case we - * find out we need to do something with header values. + * Take value and turn it into a string suitable for inclusion in + * the header. If it's a string, pass through unchanged + * If it's a datetime object, format it in ISO8601 * @param string $value a string which will be part of the header * @return string the header string */ public static function toHeaderValue($value) { - return $value; + return toString($value); } + /** + * Take value and turn it into a string suitable for inclusion in + * the http body (form parameter). If it's a string, pass through unchanged + * If it's a datetime object, format it in ISO8601 + * @param string $value the value of the form parameter + * @return string the form string + */ + public static function toFormValue($value) { + return toString($value); + } + + /** + * Take value and turn it into a string suitable for inclusion in + * the parameter. If it's a string, pass through unchanged + * If it's a datetime object, format it in ISO8601 + * @param string $value the value of the parameter + * @return string the header string + */ + public static function toString($value) { + if ($value instanceof \DateTime) { // datetime in ISO8601 format + return $value->format(\DateTime::ISO8601); + } + else { + return $value; + } + } + /** * Deserialize a JSON string into an object * diff --git a/modules/swagger-codegen/src/main/resources/php/api.mustache b/modules/swagger-codegen/src/main/resources/php/api.mustache index 7a36c9aa0a..bdf66defca 100644 --- a/modules/swagger-codegen/src/main/resources/php/api.mustache +++ b/modules/swagger-codegen/src/main/resources/php/api.mustache @@ -63,7 +63,7 @@ class {{classname}} { }{{/pathParams}} {{#formParams}}// form params if (${{paramName}} !== null) { - $formParams['{{baseName}}'] = {{#isFile}}'@' . {{/isFile}}${{paramName}}; + $formParams['{{baseName}}'] = {{#isFile}}'@' . {{/isFile}}$this->apiClient->toFormValue(${{paramName}}); }{{/formParams}} {{#bodyParams}}// body params $body = null; diff --git a/samples/client/petstore/php/PetApi.php b/samples/client/petstore/php/PetApi.php index 8c7d74cb47..8993a60959 100644 --- a/samples/client/petstore/php/PetApi.php +++ b/samples/client/petstore/php/PetApi.php @@ -304,10 +304,10 @@ class PetApi { } // form params if ($name !== null) { - $formParams['name'] = $name; + $formParams['name'] = $this->apiClient->toFormValue($name); }// form params if ($status !== null) { - $formParams['status'] = $status; + $formParams['status'] = $this->apiClient->toFormValue($status); } @@ -408,10 +408,10 @@ class PetApi { } // form params if ($additionalMetadata !== null) { - $formParams['additionalMetadata'] = $additionalMetadata; + $formParams['additionalMetadata'] = $this->apiClient->toFormValue($additionalMetadata); }// form params if ($file !== null) { - $formParams['file'] = '@' . $file; + $formParams['file'] = '@' . $this->apiClient->toFormValue($file); } diff --git a/samples/client/petstore/php/Swagger.php b/samples/client/petstore/php/Swagger.php index b65add845c..1247be83f3 100644 --- a/samples/client/petstore/php/Swagger.php +++ b/samples/client/petstore/php/Swagger.php @@ -127,19 +127,19 @@ class APIClient { // Handle the response if ($response_info['http_code'] == 0) { - throw new Exception("TIMEOUT: api call to " . $url . - " took more than 5s to return" ); + throw new APIClientException("TIMEOUT: api call to " . $url . + " took more than 5s to return", 0, $response_info, $response); } else if ($response_info['http_code'] == 200) { $data = json_decode($response); } else if ($response_info['http_code'] == 401) { - throw new Exception("Unauthorized API request to " . $url . - ": ".json_decode($response)->message ); + throw new APIClientException("Unauthorized API request to " . $url . + ": " . json_decode($response)->message, 0, $response_info, $response); } else if ($response_info['http_code'] == 404) { $data = null; } else { - throw new Exception("Can't connect to the api: " . $url . + throw new APIClientException("Can't connect to the api: " . $url . " response code: " . - $response_info['http_code']); + $response_info['http_code'], 0, $response_info, $response); } return $data; } @@ -178,7 +178,7 @@ class APIClient { * @return string the serialized object */ public static function toPathValue($value) { - return rawurlencode($value); + return rawurlencode(toString($value)); } /** @@ -193,20 +193,48 @@ class APIClient { if (is_array($object)) { return implode(',', $object); } else { - return $object; + return toString($object); } } /** - * Just pass through the header value for now. Placeholder in case we - * find out we need to do something with header values. + * Take value and turn it into a string suitable for inclusion in + * the header. If it's a string, pass through unchanged + * If it's a datetime object, format it in ISO8601 * @param string $value a string which will be part of the header * @return string the header string */ public static function toHeaderValue($value) { - return $value; + return toString($value); } + /** + * Take value and turn it into a string suitable for inclusion in + * the http body (form parameter). If it's a string, pass through unchanged + * If it's a datetime object, format it in ISO8601 + * @param string $value the value of the form parameter + * @return string the form string + */ + public static function toFormValue($value) { + return toString($value); + } + + /** + * Take value and turn it into a string suitable for inclusion in + * the parameter. If it's a string, pass through unchanged + * If it's a datetime object, format it in ISO8601 + * @param string $value the value of the parameter + * @return string the header string + */ + public static function toString($value) { + if ($value instanceof \DateTime) { // datetime in ISO8601 format + return $value->format(\DateTime::ISO8601); + } + else { + return $value; + } + } + /** * Deserialize a JSON string into an object * @@ -257,3 +285,20 @@ class APIClient { } +class APIClientException extends Exception { + protected $response, $response_info; + + public function __construct($message="", $code=0, $response_info=null, $response=null) { + parent::__construct($message, $code); + $this->response_info = $response_info; + $this->response = $response; + } + + public function getResponse() { + return $this->response; + } + + public function getResponseInfo() { + return $this->response_info; + } +} From b8166f283a53bf2fffe35a03c5efd39be263e1db Mon Sep 17 00:00:00 2001 From: William Cheng Date: Sun, 15 Mar 2015 16:33:57 +0800 Subject: [PATCH 44/70] update php to support user agent --- .../src/main/resources/php/Swagger.mustache | 20 ++++++++++++++++++- samples/client/petstore/php/Swagger.php | 20 ++++++++++++++++++- 2 files changed, 38 insertions(+), 2 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache index 1247be83f3..03b73f5775 100644 --- a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache +++ b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache @@ -48,6 +48,18 @@ class APIClient { $this->headerValue = $headerValue; } + /** + * Set the user agent of the API client + * + * @param string $user_agent The user agent of the API client + */ + public function setUserAgent($user_agent) { + if (!is_string($user_agent)) { + throw new Exception('User-agent must be a string.'); + } + $this->user_agent= $user_agent; + } + /** * @param integer $seconds Number of seconds before timing out [set to 0 for no timeout] */ @@ -58,7 +70,6 @@ class APIClient { $this->curl_timout = $seconds; } - /** * @param string $resourcePath path to method endpoint * @param string $method method to call @@ -121,6 +132,13 @@ class APIClient { } curl_setopt($curl, CURLOPT_URL, $url); + // Set user agent + if ($this->user_agent) { + curl_setopt($curl, CURLOPT_USERAGENT, $this->user_agent); + } else { // use PHP-Swagger as the default user agent + curl_setopt($curl, CURLOPT_USERAGENT, 'PHP-Swagger'); + } + // Make the request $response = curl_exec($curl); $response_info = curl_getinfo($curl); diff --git a/samples/client/petstore/php/Swagger.php b/samples/client/petstore/php/Swagger.php index 1247be83f3..03b73f5775 100644 --- a/samples/client/petstore/php/Swagger.php +++ b/samples/client/petstore/php/Swagger.php @@ -48,6 +48,18 @@ class APIClient { $this->headerValue = $headerValue; } + /** + * Set the user agent of the API client + * + * @param string $user_agent The user agent of the API client + */ + public function setUserAgent($user_agent) { + if (!is_string($user_agent)) { + throw new Exception('User-agent must be a string.'); + } + $this->user_agent= $user_agent; + } + /** * @param integer $seconds Number of seconds before timing out [set to 0 for no timeout] */ @@ -58,7 +70,6 @@ class APIClient { $this->curl_timout = $seconds; } - /** * @param string $resourcePath path to method endpoint * @param string $method method to call @@ -121,6 +132,13 @@ class APIClient { } curl_setopt($curl, CURLOPT_URL, $url); + // Set user agent + if ($this->user_agent) { + curl_setopt($curl, CURLOPT_USERAGENT, $this->user_agent); + } else { // use PHP-Swagger as the default user agent + curl_setopt($curl, CURLOPT_USERAGENT, 'PHP-Swagger'); + } + // Make the request $response = curl_exec($curl); $response_info = curl_getinfo($curl); From 6bc8de1230342be471e70f62c5515e4881ee4ad6 Mon Sep 17 00:00:00 2001 From: William Cheng Date: Sun, 15 Mar 2015 22:02:16 +0800 Subject: [PATCH 45/70] rebase on develop_2.0 --- .../src/main/resources/php/Swagger.mustache | 7 +++++-- samples/client/petstore/php/Swagger.php | 14 ++++++++++++++ 2 files changed, 19 insertions(+), 2 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache index 1247be83f3..5c6ac13430 100644 --- a/modules/swagger-codegen/src/main/resources/php/Swagger.mustache +++ b/modules/swagger-codegen/src/main/resources/php/Swagger.mustache @@ -129,11 +129,14 @@ class APIClient { if ($response_info['http_code'] == 0) { throw new APIClientException("TIMEOUT: api call to " . $url . " took more than 5s to return", 0, $response_info, $response); - } else if ($response_info['http_code'] == 200) { + } else if ($response_info['http_code'] >= 200 && $response_info['http_code'] <= 299 ) { $data = json_decode($response); + if (json_last_error() > 0) { // if response is a string + $data = $response; + } } else if ($response_info['http_code'] == 401) { throw new APIClientException("Unauthorized API request to " . $url . - ": " . json_decode($response)->message, 0, $response_info, $response); + ": " . serialize($response), 0, $response_info, $response); } else if ($response_info['http_code'] == 404) { $data = null; } else { diff --git a/samples/client/petstore/php/Swagger.php b/samples/client/petstore/php/Swagger.php index 1247be83f3..1d5e7dbda5 100644 --- a/samples/client/petstore/php/Swagger.php +++ b/samples/client/petstore/php/Swagger.php @@ -127,13 +127,27 @@ class APIClient { // Handle the response if ($response_info['http_code'] == 0) { +<<<<<<< HEAD throw new APIClientException("TIMEOUT: api call to " . $url . " took more than 5s to return", 0, $response_info, $response); } else if ($response_info['http_code'] == 200) { +======= + throw new Exception("TIMEOUT: api call to " . $url . + " took more than 5s to return" ); + } else if ($response_info['http_code'] >= 200 && $response_info['http_code'] <= 299 ) { +>>>>>>> add logic to handle all 2xx response code, bug fix for string response, $data = json_decode($response); + if (json_last_error() > 0) { // if response is a string + $data = $response; + } } else if ($response_info['http_code'] == 401) { +<<<<<<< HEAD throw new APIClientException("Unauthorized API request to " . $url . ": " . json_decode($response)->message, 0, $response_info, $response); +======= + throw new Exception("Unauthorized API request to " . $url . + ": ".serialize($response)); +>>>>>>> add logic to handle all 2xx response code, bug fix for string response, } else if ($response_info['http_code'] == 404) { $data = null; } else { From bcdee4e03822d6356ed175fc61aa9706b966e267 Mon Sep 17 00:00:00 2001 From: William Cheng Date: Sun, 15 Mar 2015 22:06:42 +0800 Subject: [PATCH 46/70] update php petstore sample code --- samples/client/petstore/php/Swagger.php | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/samples/client/petstore/php/Swagger.php b/samples/client/petstore/php/Swagger.php index 1d5e7dbda5..5c6ac13430 100644 --- a/samples/client/petstore/php/Swagger.php +++ b/samples/client/petstore/php/Swagger.php @@ -127,27 +127,16 @@ class APIClient { // Handle the response if ($response_info['http_code'] == 0) { -<<<<<<< HEAD throw new APIClientException("TIMEOUT: api call to " . $url . " took more than 5s to return", 0, $response_info, $response); - } else if ($response_info['http_code'] == 200) { -======= - throw new Exception("TIMEOUT: api call to " . $url . - " took more than 5s to return" ); } else if ($response_info['http_code'] >= 200 && $response_info['http_code'] <= 299 ) { ->>>>>>> add logic to handle all 2xx response code, bug fix for string response, $data = json_decode($response); if (json_last_error() > 0) { // if response is a string $data = $response; } } else if ($response_info['http_code'] == 401) { -<<<<<<< HEAD throw new APIClientException("Unauthorized API request to " . $url . - ": " . json_decode($response)->message, 0, $response_info, $response); -======= - throw new Exception("Unauthorized API request to " . $url . - ": ".serialize($response)); ->>>>>>> add logic to handle all 2xx response code, bug fix for string response, + ": " . serialize($response), 0, $response_info, $response); } else if ($response_info['http_code'] == 404) { $data = null; } else { From e9227ad7e5cd723d3432cda32fcf3745d8a3f735 Mon Sep 17 00:00:00 2001 From: William Cheng Date: Mon, 16 Mar 2015 18:47:22 +0800 Subject: [PATCH 47/70] add ruby codegen, update sample (petstore) for ruby --- bin/ruby-petstore.sh | 36 ++ .../codegen/languages/RubyClientCodegen.java | 120 ++++++ .../com.wordnik.swagger.codegen.CodegenConfig | 1 + .../src/main/resources/ruby/model.mustache | 17 +- samples/client/petstore/ruby/lib/PetApi.rb | 359 ++++++++++++++++ samples/client/petstore/ruby/lib/StoreApi.rb | 176 ++++++++ samples/client/petstore/ruby/lib/UserApi.rb | 384 ++++++++++++++++++ samples/client/petstore/ruby/lib/monkey.rb | 2 +- samples/client/petstore/ruby/lib/swagger.rb | 2 +- .../ruby/lib/swagger/configuration.rb | 2 +- .../petstore/ruby/lib/swagger/request.rb | 2 +- .../petstore/ruby/lib/swagger/response.rb | 2 +- .../petstore/ruby/lib/swagger/version.rb | 1 - .../client/petstore/ruby/models/Category.rb | 20 +- samples/client/petstore/ruby/models/Order.rb | 64 ++- samples/client/petstore/ruby/models/Pet.rb | 70 ++-- samples/client/petstore/ruby/models/Tag.rb | 20 +- samples/client/petstore/ruby/models/User.rb | 88 ++-- .../petstore/ruby/swagger/configuration.rb | 22 + .../client/petstore/ruby/swagger/request.rb | 199 +++++++++ .../client/petstore/ruby/swagger/response.rb | 70 ++++ .../client/petstore/ruby/swagger/version.rb | 4 + 22 files changed, 1561 insertions(+), 100 deletions(-) create mode 100755 bin/ruby-petstore.sh create mode 100644 modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/RubyClientCodegen.java create mode 100644 samples/client/petstore/ruby/lib/PetApi.rb create mode 100644 samples/client/petstore/ruby/lib/StoreApi.rb create mode 100644 samples/client/petstore/ruby/lib/UserApi.rb create mode 100644 samples/client/petstore/ruby/swagger/configuration.rb create mode 100644 samples/client/petstore/ruby/swagger/request.rb create mode 100644 samples/client/petstore/ruby/swagger/response.rb create mode 100644 samples/client/petstore/ruby/swagger/version.rb diff --git a/bin/ruby-petstore.sh b/bin/ruby-petstore.sh new file mode 100755 index 0000000000..bd7c30496b --- /dev/null +++ b/bin/ruby-petstore.sh @@ -0,0 +1,36 @@ +#!/bin/sh + +SCRIPT="$0" + +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 + +root=./modules/swagger-codegen-distribution/pom.xml + +# gets version of swagger-codegen +version=$(sed '//,/<\/project>/d;//!d;s/ *<\/\?version> *//g' $root | sed -n '2p' | sed -e 's,.*\([^<]*\).*,\1,g') + +executable="./modules/swagger-codegen-distribution/target/swagger-codegen-distribution-$version.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} -XX:MaxPermSize=256M -Xmx1024M -DloggerPath=conf/log4j.properties" +ags="$@ -i modules/swagger-codegen/src/test/resources/2_0/petstore.json -l ruby -o samples/client/petstore/ruby" + +java $JAVA_OPTS -jar $executable $ags diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/RubyClientCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/RubyClientCodegen.java new file mode 100644 index 0000000000..ee65073be1 --- /dev/null +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/RubyClientCodegen.java @@ -0,0 +1,120 @@ +package com.wordnik.swagger.codegen.languages; + +import com.wordnik.swagger.codegen.*; +import com.wordnik.swagger.util.Json; +import com.wordnik.swagger.models.properties.*; + +import java.util.*; +import java.io.File; + +public class RubyClientCodegen extends DefaultCodegen implements CodegenConfig { + protected String invokerPackage = "com.wordnik.client"; + protected String groupId = "com.wordnik"; + protected String artifactId = "swagger-client"; + protected String artifactVersion = "1.0.0"; + + public CodegenType getTag() { + return CodegenType.CLIENT; + } + + public String getName() { + return "ruby"; + } + + public String getHelp() { + return "Generates a Ruby client library."; + } + + public RubyClientCodegen() { + super(); + modelPackage = "models"; + apiPackage = "lib"; + outputFolder = "generated-code/ruby"; + modelTemplateFiles.put("model.mustache", ".rb"); + apiTemplateFiles.put("api.mustache", ".rb"); + templateDir = "ruby"; + + typeMapping.clear(); + languageSpecificPrimitives.clear(); + + reservedWords = new HashSet ( + Arrays.asList( + "int") + ); + + additionalProperties.put("invokerPackage", invokerPackage); + additionalProperties.put("groupId", groupId); + additionalProperties.put("artifactId", artifactId); + additionalProperties.put("artifactVersion", artifactVersion); + + languageSpecificPrimitives.add("int"); + languageSpecificPrimitives.add("array"); + languageSpecificPrimitives.add("map"); + languageSpecificPrimitives.add("string"); + languageSpecificPrimitives.add("DateTime"); + + typeMapping.put("long", "int"); + typeMapping.put("integer", "int"); + typeMapping.put("Array", "array"); + typeMapping.put("String", "string"); + typeMapping.put("List", "array"); + typeMapping.put("map", "map"); + + supportingFiles.add(new SupportingFile("swagger.mustache", "", "lib/swagger.rb")); + supportingFiles.add(new SupportingFile("monkey.mustache", "", "lib/monkey.rb")); + supportingFiles.add(new SupportingFile("swagger/request.mustache", "", "lib/swagger/request.rb")); + supportingFiles.add(new SupportingFile("swagger/response.mustache", "", "lib/swagger/response.rb")); + supportingFiles.add(new SupportingFile("swagger/version.mustache", "", "lib/swagger/version.rb")); + supportingFiles.add(new SupportingFile("swagger/configuration.mustache", "", "lib/swagger/configuration.rb")); + } + + @Override + public String escapeReservedWord(String name) { + return "_" + name; + } + + @Override + public String apiFileFolder() { + return outputFolder + "/" + apiPackage().replace('.', File.separatorChar); + } + + public String modelFileFolder() { + return outputFolder + "/" + modelPackage().replace('.', File.separatorChar); + } + + @Override + public String getTypeDeclaration(Property p) { + if(p instanceof ArrayProperty) { + ArrayProperty ap = (ArrayProperty) p; + Property inner = ap.getItems(); + return getSwaggerType(p) + "[" + getTypeDeclaration(inner) + "]"; + } + else if (p instanceof MapProperty) { + MapProperty mp = (MapProperty) p; + Property inner = mp.getAdditionalProperties(); + return getSwaggerType(p) + "[string," + getTypeDeclaration(inner) + "]"; + } + return super.getTypeDeclaration(p); + } + + @Override + public String getSwaggerType(Property p) { + String swaggerType = super.getSwaggerType(p); + String type = null; + if(typeMapping.containsKey(swaggerType)) { + type = typeMapping.get(swaggerType); + if(languageSpecificPrimitives.contains(type)) { + return type; + } + } + else + type = swaggerType; + if(type == null) + return null; + return type; + } + + public String toDefaultValue(Property p) { + return "null"; + } +} diff --git a/modules/swagger-codegen/src/main/resources/META-INF/services/com.wordnik.swagger.codegen.CodegenConfig b/modules/swagger-codegen/src/main/resources/META-INF/services/com.wordnik.swagger.codegen.CodegenConfig index bc7554b95f..8aa08f9599 100644 --- a/modules/swagger-codegen/src/main/resources/META-INF/services/com.wordnik.swagger.codegen.CodegenConfig +++ b/modules/swagger-codegen/src/main/resources/META-INF/services/com.wordnik.swagger.codegen.CodegenConfig @@ -11,4 +11,5 @@ com.wordnik.swagger.codegen.languages.StaticHtmlGenerator com.wordnik.swagger.codegen.languages.SwaggerGenerator com.wordnik.swagger.codegen.languages.TizenClientCodegen com.wordnik.swagger.codegen.languages.PhpClientCodegen +com.wordnik.swagger.codegen.languages.RubyClientCodegen com.wordnik.swagger.codegen.languages.PythonClientCodegen diff --git a/modules/swagger-codegen/src/main/resources/ruby/model.mustache b/modules/swagger-codegen/src/main/resources/ruby/model.mustache index c587f12cb4..ef3b2fe48f 100644 --- a/modules/swagger-codegen/src/main/resources/ruby/model.mustache +++ b/modules/swagger-codegen/src/main/resources/ruby/model.mustache @@ -7,9 +7,8 @@ class {{classname}} def self.attribute_map { {{#vars}} - :{{{name}}} => :{{{baseName}}}{{#hasMore}}, - {{/hasMore}} - {{/vars}}{{newline}} + :{{{name}}} => :{{{baseName}}}{{#hasMore}},{{/hasMore}} + {{/vars}} } end @@ -19,14 +18,14 @@ class {{classname}} {{#vars}} if self.class.attribute_map[:"{{{name}}}"] {{#isContainer}} - if (value = attributes["{{{baseName}}}"]).is_a?(Array) - @{{{name}}} = value{{#complexType}}.map{ |v| {{complexType}}.new(v) }{{/complexType}}{{newline}} - end + if (value = attributes["{{{baseName}}}"]).is_a?(Array) + @{{{name}}} = value{{#complexType}}.map{ |v| {{complexType}}.new(v) }{{/complexType}}{{newline}} + end {{/isContainer}}{{^isContainer}} - @{{{name}}} = attributes["{{{baseName}}}"] - {{/isContainer}} + @{{{name}}} = attributes["{{{baseName}}}"] + {{/isContainer}} end - {{/vars}}{{newline}} + {{/vars}} end def to_body diff --git a/samples/client/petstore/ruby/lib/PetApi.rb b/samples/client/petstore/ruby/lib/PetApi.rb new file mode 100644 index 0000000000..41b4f4122c --- /dev/null +++ b/samples/client/petstore/ruby/lib/PetApi.rb @@ -0,0 +1,359 @@ +require "uri" + +class PetApi + basePath = "http://petstore.swagger.io/v2" + # apiInvoker = APIInvoker + + def self.escapeString(string) + URI.encode(string.to_s) + end + + + def self.updatePet (body, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :body => body + + }.merge(opts) + + #resource path + path = "/pet".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + if body != nil + if body.is_a?(Array) + array = Array.new + body.each do |item| + if item.respond_to?("to_body".to_sym) + array.push item.to_body + else + array.push item + end + end + post_body = array + + else + if body.respond_to?("to_body".to_sym) + post_body = body.to_body + else + post_body = body + end + end + end + + + + + Swagger::Request.new(:PUT, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.addPet (body, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :body => body + + }.merge(opts) + + #resource path + path = "/pet".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + if body != nil + if body.is_a?(Array) + array = Array.new + body.each do |item| + if item.respond_to?("to_body".to_sym) + array.push item.to_body + else + array.push item + end + end + post_body = array + + else + if body.respond_to?("to_body".to_sym) + post_body = body.to_body + else + post_body = body + end + end + end + + + + + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.findPetsByStatus (status, opts={}) + query_param_keys = [:status] + + + + # set default values and merge with input + options = { + + :status => status + + }.merge(opts) + + #resource path + path = "/pet/findByStatus".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + response.map {|response| Pet.new(response) } + + + + end + + + def self.findPetsByTags (tags, opts={}) + query_param_keys = [:tags] + + + + # set default values and merge with input + options = { + + :tags => tags + + }.merge(opts) + + #resource path + path = "/pet/findByTags".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + response.map {|response| Pet.new(response) } + + + + end + + + def self.getPetById (petId, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :petId => petId + + }.merge(opts) + + #resource path + path = "/pet/{petId}".sub('{format}','json').sub('{' + 'petId' + '}', escapeString(petId)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + Pet.new(response) + + + + end + + + def self.updatePetWithForm (petId,name,status, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :petId => petId, + + + :name => name, + + + :status => status + + }.merge(opts) + + #resource path + path = "/pet/{petId}".sub('{format}','json').sub('{' + 'petId' + '}', escapeString(petId)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.deletePet (api_key,petId, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :api_key => api_key, + + + :petId => petId + + }.merge(opts) + + #resource path + path = "/pet/{petId}".sub('{format}','json').sub('{' + 'petId' + '}', escapeString(petId)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + headers = { + api_key: api_key, + } + + + + post_body = nil + + + + + Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.uploadFile (petId,additionalMetadata,file, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :petId => petId, + + + :additionalMetadata => additionalMetadata, + + + :file => file + + }.merge(opts) + + #resource path + path = "/pet/{petId}/uploadImage".sub('{format}','json').sub('{' + 'petId' + '}', escapeString(petId)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + +end diff --git a/samples/client/petstore/ruby/lib/StoreApi.rb b/samples/client/petstore/ruby/lib/StoreApi.rb new file mode 100644 index 0000000000..b5d33010cc --- /dev/null +++ b/samples/client/petstore/ruby/lib/StoreApi.rb @@ -0,0 +1,176 @@ +require "uri" + +class StoreApi + basePath = "http://petstore.swagger.io/v2" + # apiInvoker = APIInvoker + + def self.escapeString(string) + URI.encode(string.to_s) + end + + + def self.getInventory ( opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + }.merge(opts) + + #resource path + path = "/store/inventory".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + response.map {|response| map.new(response) } + + + + end + + + def self.placeOrder (body, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :body => body + + }.merge(opts) + + #resource path + path = "/store/order".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + if body != nil + if body.is_a?(Array) + array = Array.new + body.each do |item| + if item.respond_to?("to_body".to_sym) + array.push item.to_body + else + array.push item + end + end + post_body = array + + else + if body.respond_to?("to_body".to_sym) + post_body = body.to_body + else + post_body = body + end + end + end + + + + response = Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + Order.new(response) + + + + end + + + def self.getOrderById (orderId, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :orderId => orderId + + }.merge(opts) + + #resource path + path = "/store/order/{orderId}".sub('{format}','json').sub('{' + 'orderId' + '}', escapeString(orderId)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + Order.new(response) + + + + end + + + def self.deleteOrder (orderId, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :orderId => orderId + + }.merge(opts) + + #resource path + path = "/store/order/{orderId}".sub('{format}','json').sub('{' + 'orderId' + '}', escapeString(orderId)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + + Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + +end diff --git a/samples/client/petstore/ruby/lib/UserApi.rb b/samples/client/petstore/ruby/lib/UserApi.rb new file mode 100644 index 0000000000..40051e7c9f --- /dev/null +++ b/samples/client/petstore/ruby/lib/UserApi.rb @@ -0,0 +1,384 @@ +require "uri" + +class UserApi + basePath = "http://petstore.swagger.io/v2" + # apiInvoker = APIInvoker + + def self.escapeString(string) + URI.encode(string.to_s) + end + + + def self.createUser (body, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :body => body + + }.merge(opts) + + #resource path + path = "/user".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + if body != nil + if body.is_a?(Array) + array = Array.new + body.each do |item| + if item.respond_to?("to_body".to_sym) + array.push item.to_body + else + array.push item + end + end + post_body = array + + else + if body.respond_to?("to_body".to_sym) + post_body = body.to_body + else + post_body = body + end + end + end + + + + + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.createUsersWithArrayInput (body, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :body => body + + }.merge(opts) + + #resource path + path = "/user/createWithArray".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + if body != nil + if body.is_a?(Array) + array = Array.new + body.each do |item| + if item.respond_to?("to_body".to_sym) + array.push item.to_body + else + array.push item + end + end + post_body = array + + else + if body.respond_to?("to_body".to_sym) + post_body = body.to_body + else + post_body = body + end + end + end + + + + + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.createUsersWithListInput (body, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :body => body + + }.merge(opts) + + #resource path + path = "/user/createWithList".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + if body != nil + if body.is_a?(Array) + array = Array.new + body.each do |item| + if item.respond_to?("to_body".to_sym) + array.push item.to_body + else + array.push item + end + end + post_body = array + + else + if body.respond_to?("to_body".to_sym) + post_body = body.to_body + else + post_body = body + end + end + end + + + + + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.loginUser (username,password, opts={}) + query_param_keys = [:username,:password] + + + + # set default values and merge with input + options = { + + :username => username, + + + :password => password + + }.merge(opts) + + #resource path + path = "/user/login".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + string.new(response) + + + + end + + + def self.logoutUser ( opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + }.merge(opts) + + #resource path + path = "/user/logout".sub('{format}','json') + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + + Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.getUserByName (username, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :username => username + + }.merge(opts) + + #resource path + path = "/user/{username}".sub('{format}','json').sub('{' + 'username' + '}', escapeString(username)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + User.new(response) + + + + end + + + def self.updateUser (username,body, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :username => username, + + + :body => body + + }.merge(opts) + + #resource path + path = "/user/{username}".sub('{format}','json').sub('{' + 'username' + '}', escapeString(username)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + if body != nil + if body.is_a?(Array) + array = Array.new + body.each do |item| + if item.respond_to?("to_body".to_sym) + array.push item.to_body + else + array.push item + end + end + post_body = array + + else + if body.respond_to?("to_body".to_sym) + post_body = body.to_body + else + post_body = body + end + end + end + + + + + Swagger::Request.new(:PUT, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + + + def self.deleteUser (username, opts={}) + query_param_keys = [] + + + + # set default values and merge with input + options = { + + :username => username + + }.merge(opts) + + #resource path + path = "/user/{username}".sub('{format}','json').sub('{' + 'username' + '}', escapeString(username)) + + + # pull querystring keys from options + queryopts = options.select do |key,value| + query_param_keys.include? key + end + + + headers = nil + + + post_body = nil + + + + + Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + + + end + +end diff --git a/samples/client/petstore/ruby/lib/monkey.rb b/samples/client/petstore/ruby/lib/monkey.rb index 54cd22170e..28932890af 100644 --- a/samples/client/petstore/ruby/lib/monkey.rb +++ b/samples/client/petstore/ruby/lib/monkey.rb @@ -87,4 +87,4 @@ end end -# end +# end \ No newline at end of file diff --git a/samples/client/petstore/ruby/lib/swagger.rb b/samples/client/petstore/ruby/lib/swagger.rb index de48af3a33..1cc3ea456c 100644 --- a/samples/client/petstore/ruby/lib/swagger.rb +++ b/samples/client/petstore/ruby/lib/swagger.rb @@ -81,4 +81,4 @@ class ServerError < StandardError end class ClientError < StandardError -end +end \ No newline at end of file diff --git a/samples/client/petstore/ruby/lib/swagger/configuration.rb b/samples/client/petstore/ruby/lib/swagger/configuration.rb index 905ff261c2..c0b3c46268 100644 --- a/samples/client/petstore/ruby/lib/swagger/configuration.rb +++ b/samples/client/petstore/ruby/lib/swagger/configuration.rb @@ -19,4 +19,4 @@ module Swagger end -end +end \ No newline at end of file diff --git a/samples/client/petstore/ruby/lib/swagger/request.rb b/samples/client/petstore/ruby/lib/swagger/request.rb index a38c4643a4..7836cb0bf0 100644 --- a/samples/client/petstore/ruby/lib/swagger/request.rb +++ b/samples/client/petstore/ruby/lib/swagger/request.rb @@ -196,4 +196,4 @@ module Swagger end end -end +end \ No newline at end of file diff --git a/samples/client/petstore/ruby/lib/swagger/response.rb b/samples/client/petstore/ruby/lib/swagger/response.rb index a42cf99d4d..02a1a458eb 100644 --- a/samples/client/petstore/ruby/lib/swagger/response.rb +++ b/samples/client/petstore/ruby/lib/swagger/response.rb @@ -67,4 +67,4 @@ module Swagger end end -end +end \ No newline at end of file diff --git a/samples/client/petstore/ruby/lib/swagger/version.rb b/samples/client/petstore/ruby/lib/swagger/version.rb index dfd2ddad20..39357c0ed6 100644 --- a/samples/client/petstore/ruby/lib/swagger/version.rb +++ b/samples/client/petstore/ruby/lib/swagger/version.rb @@ -2,4 +2,3 @@ module Swagger VERSION = "4.06.08" end - diff --git a/samples/client/petstore/ruby/models/Category.rb b/samples/client/petstore/ruby/models/Category.rb index 54bd6a5245..0f15c43a70 100644 --- a/samples/client/petstore/ruby/models/Category.rb +++ b/samples/client/petstore/ruby/models/Category.rb @@ -1,26 +1,33 @@ + class Category attr_accessor :id, :name - # :internal => :external def self.attribute_map { + :id => :id, + :name => :name - + } end def initialize(attributes = {}) return if attributes.empty? # Morph attribute keys into undescored rubyish style + if self.class.attribute_map[:"id"] + @id = attributes["id"] - end - if self.class.attribute_map[:"name"] - @name = attributes["name"] + + end + + if self.class.attribute_map[:"name"] + + @name = attributes["name"] + end - end def to_body @@ -31,4 +38,3 @@ class Category body end end - diff --git a/samples/client/petstore/ruby/models/Order.rb b/samples/client/petstore/ruby/models/Order.rb index 81bc6d5a4d..45a0864cfc 100644 --- a/samples/client/petstore/ruby/models/Order.rb +++ b/samples/client/petstore/ruby/models/Order.rb @@ -1,38 +1,65 @@ -class Order - attr_accessor :id, :pet_id, :quantity, :status, :ship_date +class Order + attr_accessor :id, :petId, :quantity, :shipDate, :status, :complete # :internal => :external def self.attribute_map { + :id => :id, - :pet_id => :petId, + + :petId => :petId, + :quantity => :quantity, + + :shipDate => :shipDate, + :status => :status, - :ship_date => :shipDate - + + :complete => :complete + } end def initialize(attributes = {}) return if attributes.empty? # Morph attribute keys into undescored rubyish style + if self.class.attribute_map[:"id"] + @id = attributes["id"] - end - if self.class.attribute_map[:"pet_id"] - @pet_id = attributes["petId"] - end - if self.class.attribute_map[:"quantity"] - @quantity = attributes["quantity"] - end - if self.class.attribute_map[:"status"] - @status = attributes["status"] - end - if self.class.attribute_map[:"ship_date"] - @ship_date = attributes["shipDate"] + + end + + if self.class.attribute_map[:"petId"] + + @petId = attributes["petId"] + + end + + if self.class.attribute_map[:"quantity"] + + @quantity = attributes["quantity"] + + end + + if self.class.attribute_map[:"shipDate"] + + @shipDate = attributes["shipDate"] + + end + + if self.class.attribute_map[:"status"] + + @status = attributes["status"] + + end + + if self.class.attribute_map[:"complete"] + + @complete = attributes["complete"] + end - end def to_body @@ -43,4 +70,3 @@ class Order body end end - diff --git a/samples/client/petstore/ruby/models/Pet.rb b/samples/client/petstore/ruby/models/Pet.rb index f4b3eb2e4c..f67067e6f9 100644 --- a/samples/client/petstore/ruby/models/Pet.rb +++ b/samples/client/petstore/ruby/models/Pet.rb @@ -1,44 +1,69 @@ -class Pet - attr_accessor :id, :category, :name, :photo_urls, :tags, :status +class Pet + attr_accessor :id, :category, :name, :photoUrls, :tags, :status # :internal => :external def self.attribute_map { + :id => :id, + :category => :category, + :name => :name, - :photo_urls => :photoUrls, + + :photoUrls => :photoUrls, + :tags => :tags, + :status => :status - + } end def initialize(attributes = {}) return if attributes.empty? # Morph attribute keys into undescored rubyish style + if self.class.attribute_map[:"id"] + @id = attributes["id"] - end - if self.class.attribute_map[:"category"] - @category = attributes["category"] - end - if self.class.attribute_map[:"name"] - @name = attributes["name"] - end - if self.class.attribute_map[:"photo_urls"] - if (value = attributes["photoUrls"]).is_a?(Array) - @photo_urls = valueend - end - if self.class.attribute_map[:"tags"] - if (value = attributes["tags"]).is_a?(Array) - @tags = value.map{ |v| Tag.new(v) }end - end - if self.class.attribute_map[:"status"] - @status = attributes["status"] + + end + + if self.class.attribute_map[:"category"] + + @category = attributes["category"] + + end + + if self.class.attribute_map[:"name"] + + @name = attributes["name"] + + end + + if self.class.attribute_map[:"photoUrls"] + + if (value = attributes["photoUrls"]).is_a?(Array) + @photoUrls = value + end + + end + + if self.class.attribute_map[:"tags"] + + if (value = attributes["tags"]).is_a?(Array) + @tags = value.map{ |v| Tag.new(v) } + end + + end + + if self.class.attribute_map[:"status"] + + @status = attributes["status"] + end - end def to_body @@ -49,4 +74,3 @@ class Pet body end end - diff --git a/samples/client/petstore/ruby/models/Tag.rb b/samples/client/petstore/ruby/models/Tag.rb index abe4929a3d..9a9193b8e8 100644 --- a/samples/client/petstore/ruby/models/Tag.rb +++ b/samples/client/petstore/ruby/models/Tag.rb @@ -1,26 +1,33 @@ + class Tag attr_accessor :id, :name - # :internal => :external def self.attribute_map { + :id => :id, + :name => :name - + } end def initialize(attributes = {}) return if attributes.empty? # Morph attribute keys into undescored rubyish style + if self.class.attribute_map[:"id"] + @id = attributes["id"] - end - if self.class.attribute_map[:"name"] - @name = attributes["name"] + + end + + if self.class.attribute_map[:"name"] + + @name = attributes["name"] + end - end def to_body @@ -31,4 +38,3 @@ class Tag body end end - diff --git a/samples/client/petstore/ruby/models/User.rb b/samples/client/petstore/ruby/models/User.rb index a6c2f05296..b7981a2bc4 100644 --- a/samples/client/petstore/ruby/models/User.rb +++ b/samples/client/petstore/ruby/models/User.rb @@ -1,50 +1,81 @@ -class User - attr_accessor :id, :first_name, :username, :last_name, :email, :password, :phone, :user_status +class User + attr_accessor :id, :username, :firstName, :lastName, :email, :password, :phone, :userStatus # :internal => :external def self.attribute_map { + :id => :id, - :first_name => :firstName, + :username => :username, - :last_name => :lastName, + + :firstName => :firstName, + + :lastName => :lastName, + :email => :email, + :password => :password, + :phone => :phone, - :user_status => :userStatus - + + :userStatus => :userStatus + } end def initialize(attributes = {}) return if attributes.empty? # Morph attribute keys into undescored rubyish style + if self.class.attribute_map[:"id"] + @id = attributes["id"] - end - if self.class.attribute_map[:"first_name"] - @first_name = attributes["firstName"] - end - if self.class.attribute_map[:"username"] - @username = attributes["username"] - end - if self.class.attribute_map[:"last_name"] - @last_name = attributes["lastName"] - end - if self.class.attribute_map[:"email"] - @email = attributes["email"] - end - if self.class.attribute_map[:"password"] - @password = attributes["password"] - end - if self.class.attribute_map[:"phone"] - @phone = attributes["phone"] - end - if self.class.attribute_map[:"user_status"] - @user_status = attributes["userStatus"] + + end + + if self.class.attribute_map[:"username"] + + @username = attributes["username"] + + end + + if self.class.attribute_map[:"firstName"] + + @firstName = attributes["firstName"] + + end + + if self.class.attribute_map[:"lastName"] + + @lastName = attributes["lastName"] + + end + + if self.class.attribute_map[:"email"] + + @email = attributes["email"] + + end + + if self.class.attribute_map[:"password"] + + @password = attributes["password"] + + end + + if self.class.attribute_map[:"phone"] + + @phone = attributes["phone"] + + end + + if self.class.attribute_map[:"userStatus"] + + @userStatus = attributes["userStatus"] + end - end def to_body @@ -55,4 +86,3 @@ class User body end end - diff --git a/samples/client/petstore/ruby/swagger/configuration.rb b/samples/client/petstore/ruby/swagger/configuration.rb new file mode 100644 index 0000000000..c0b3c46268 --- /dev/null +++ b/samples/client/petstore/ruby/swagger/configuration.rb @@ -0,0 +1,22 @@ +module Swagger + + class Configuration + require 'swagger/version' + + attr_accessor :format, :api_key, :username, :password, :auth_token, :scheme, :host, :base_path, :user_agent, :logger, :inject_format, :force_ending_format, :camelize_params + + # Defaults go in here.. + def initialize + @format = 'json' + @scheme = 'http' + @host = 'api.wordnik.com' + @base_path = '/v4' + @user_agent = "ruby-#{Swagger::VERSION}" + @inject_format = true + @force_ending_format = false + @camelize_params = true + end + + end + +end \ No newline at end of file diff --git a/samples/client/petstore/ruby/swagger/request.rb b/samples/client/petstore/ruby/swagger/request.rb new file mode 100644 index 0000000000..7836cb0bf0 --- /dev/null +++ b/samples/client/petstore/ruby/swagger/request.rb @@ -0,0 +1,199 @@ +module Swagger + + class Request + require 'uri' + require 'addressable/uri' + require 'typhoeus' + require "swagger/version" + + attr_accessor :host, :path, :format, :params, :body, :http_method, :headers + + + # All requests must have an HTTP method and a path + # Optionals parameters are :params, :headers, :body, :format, :host + # + def initialize(http_method, path, attributes={}) + attributes[:format] ||= Swagger.configuration.format + attributes[:params] ||= {} + + # Set default headers + default_headers = { + 'Content-Type' => "application/#{attributes[:format].downcase}", + :api_key => Swagger.configuration.api_key + } + + # api_key from headers hash trumps the default, even if its value is blank + if attributes[:headers].present? && attributes[:headers].has_key?(:api_key) + default_headers.delete(:api_key) + end + + # api_key from params hash trumps all others (headers and default_headers) + if attributes[:params].present? && attributes[:params].has_key?(:api_key) + default_headers.delete(:api_key) + attributes[:headers].delete(:api_key) if attributes[:headers].present? + end + + # Merge argument headers into defaults + attributes[:headers] = default_headers.merge(attributes[:headers] || {}) + + # Stick in the auth token if there is one + if Swagger.authenticated? + attributes[:headers].merge!({:auth_token => Swagger.configuration.auth_token}) + end + + self.http_method = http_method.to_sym + self.path = path + attributes.each do |name, value| + send("#{name.to_s.underscore.to_sym}=", value) + end + end + + # Construct a base URL + # + def url(options = {}) + u = Addressable::URI.new( + :scheme => Swagger.configuration.scheme, + :host => Swagger.configuration.host, + :path => self.interpreted_path, + :query => self.query_string.sub(/\?/, '') + ).to_s + + # Drop trailing question mark, if present + u.sub! /\?$/, '' + + # Obfuscate API key? + u.sub! /api\_key=\w+/, 'api_key=YOUR_API_KEY' if options[:obfuscated] + + u + end + + # Iterate over the params hash, injecting any path values into the path string + # + # e.g. /word.{format}/{word}/entries => /word.json/cat/entries + def interpreted_path + p = self.path.dup + + # Fill in the path params + self.params.each_pair do |key, value| + p = p.gsub("{#{key}}", value.to_s) + end + + # Stick a .{format} placeholder into the path if there isn't + # one already or an actual format like json or xml + # e.g. /words/blah => /words.{format}/blah + if Swagger.configuration.inject_format + unless ['.json', '.xml', '{format}'].any? {|s| p.downcase.include? s } + p = p.sub(/^(\/?\w+)/, "\\1.#{format}") + end + end + + # Stick a .{format} placeholder on the end of the path if there isn't + # one already or an actual format like json or xml + # e.g. /words/blah => /words/blah.{format} + if Swagger.configuration.force_ending_format + unless ['.json', '.xml', '{format}'].any? {|s| p.downcase.include? s } + p = "#{p}.#{format}" + end + end + + p = p.sub("{format}", self.format.to_s) + + URI.encode [Swagger.configuration.base_path, p].join("/").gsub(/\/+/, '/') + end + + # Massage the request body into a state of readiness + # If body is a hash, camelize all keys then convert to a json string + # + def body=(value) + if value.is_a?(Hash) + value = value.inject({}) do |memo, (k,v)| + memo[k.to_s.camelize(:lower).to_sym] = v + memo + end + end + @body = value + end + + # If body is an object, JSONify it before making the actual request. + # + def outgoing_body + body.is_a?(String) ? body : body.to_json + end + + # Construct a query string from the query-string-type params + def query_string + + # Iterate over all params, + # .. removing the ones that are part of the path itself. + # .. stringifying values so Addressable doesn't blow up. + query_values = {} + self.params.each_pair do |key, value| + next if self.path.include? "{#{key}}" # skip path params + next if value.blank? && value.class != FalseClass # skip empties + if Swagger.configuration.camelize_params + key = key.to_s.camelize(:lower).to_sym unless key.to_sym == :api_key # api_key is not a camelCased param + end + query_values[key] = value.to_s + end + + # We don't want to end up with '?' as our query string + # if there aren't really any params + return "" if query_values.blank? + + # Addressable requires query_values to be set after initialization.. + qs = Addressable::URI.new + qs.query_values = query_values + qs.to_s + end + + def make + logger = Logger.new STDOUT + logger.debug self.url + response = case self.http_method.to_sym + when :get,:GET + Typhoeus::Request.get( + self.url, + :headers => self.headers.stringify_keys, + ) + + when :post,:POST + Typhoeus::Request.post( + self.url, + :body => self.outgoing_body, + :headers => self.headers.stringify_keys, + ) + + when :put,:PUT + Typhoeus::Request.put( + self.url, + :body => self.outgoing_body, + :headers => self.headers.stringify_keys, + ) + + when :delete,:DELETE + Typhoeus::Request.delete( + self.url, + :body => self.outgoing_body, + :headers => self.headers.stringify_keys, + ) + end + Response.new(response) + end + + def response + self.make + end + + def response_code_pretty + return unless @response.present? + @response.code.to_s + end + + def response_headers_pretty + return unless @response.present? + # JSON.pretty_generate(@response.headers).gsub(/\n/, '
') # <- This was for RestClient + @response.headers.gsub(/\n/, '
') # <- This is for Typhoeus + end + + end +end \ No newline at end of file diff --git a/samples/client/petstore/ruby/swagger/response.rb b/samples/client/petstore/ruby/swagger/response.rb new file mode 100644 index 0000000000..02a1a458eb --- /dev/null +++ b/samples/client/petstore/ruby/swagger/response.rb @@ -0,0 +1,70 @@ +module Swagger + + class Response + require 'json' + + attr_accessor :raw + + def initialize(raw) + self.raw = raw + + case self.code + when 500..510 then raise(ServerError, self.error_message) + when 299..426 then raise(ClientError, self.error_message) + end + end + + def code + raw.code + end + + # Account for error messages that take different forms... + def error_message + body['message'] + rescue + body + end + + # If body is JSON, parse it + # Otherwise return raw string + def body + JSON.parse raw.body + rescue + raw.body + end + + # `headers_hash` is a Typhoeus-specific extension of Hash, + # so simplify it back into a regular old Hash. + def headers + h = {} + raw.headers_hash.each {|k,v| h[k] = v } + h + end + + # Extract the response format from the header hash + # e.g. {'Content-Type' => 'application/json'} + def format + headers['Content-Type'].split("/").last.downcase + end + + def json? + format == 'json' + end + + def xml? + format == 'xml' + end + + def pretty_body + return unless body.present? + case format + when 'json' then JSON.pretty_generate(body).gsub(/\n/, '
') + end + end + + def pretty_headers + JSON.pretty_generate(headers).gsub(/\n/, '
') + end + + end +end \ No newline at end of file diff --git a/samples/client/petstore/ruby/swagger/version.rb b/samples/client/petstore/ruby/swagger/version.rb new file mode 100644 index 0000000000..39357c0ed6 --- /dev/null +++ b/samples/client/petstore/ruby/swagger/version.rb @@ -0,0 +1,4 @@ +module Swagger + VERSION = "4.06.08" +end + From d580d294b6ea638b0077da838332d0a496444fdd Mon Sep 17 00:00:00 2001 From: Camille Chafer Date: Mon, 16 Mar 2015 11:53:58 +0100 Subject: [PATCH 48/70] Adding defintion of security schemes in CodegenSecurity --- .../swagger/codegen/CodegenSecurity.java | 6 +++++- .../swagger/codegen/DefaultCodegen.java | 20 ++++++++++++++++++- 2 files changed, 24 insertions(+), 2 deletions(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenSecurity.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenSecurity.java index 7323893106..889a9419c6 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenSecurity.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenSecurity.java @@ -3,5 +3,9 @@ package com.wordnik.swagger.codegen; public class CodegenSecurity { String name; String type; - Boolean hasMore; + Boolean hasMore, isBasic, isOAuth, isApiKey; + // ApiKey specific + String keyParamName; + Boolean isKeyInQuery, isKeyInHeader; + } diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index 2abcfad31e..c21d43bb1e 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -1,6 +1,9 @@ package com.wordnik.swagger.codegen; import com.wordnik.swagger.models.*; +import com.wordnik.swagger.models.auth.ApiKeyAuthDefinition; +import com.wordnik.swagger.models.auth.BasicAuthDefinition; +import com.wordnik.swagger.models.auth.In; import com.wordnik.swagger.models.auth.SecuritySchemeDefinition; import com.wordnik.swagger.models.parameters.*; import com.wordnik.swagger.models.properties.*; @@ -888,10 +891,25 @@ public class DefaultCodegen { List secs = new ArrayList(); for(Iterator entries = schemes.entrySet().iterator(); entries.hasNext(); ) { Map.Entry entry = (Map.Entry) entries.next(); + final SecuritySchemeDefinition schemeDefinition = entry.getValue(); CodegenSecurity sec = CodegenModelFactory.newInstance(CodegenModelType.SECURITY); sec.name = entry.getKey(); - sec.type = entry.getValue().getType(); + sec.type = schemeDefinition.getType(); + + if (schemeDefinition instanceof ApiKeyAuthDefinition) { + final ApiKeyAuthDefinition apiKeyDefinition = (ApiKeyAuthDefinition) schemeDefinition; + sec.isBasic = sec.isOAuth = false; + sec.isApiKey = true; + sec.keyParamName = apiKeyDefinition.getName(); + sec.isKeyInHeader = apiKeyDefinition.getIn() == In.HEADER; + sec.isKeyInQuery = !sec.isKeyInHeader; + } else { + sec.isKeyInHeader = sec.isKeyInQuery = sec.isApiKey = false; + sec.isBasic = schemeDefinition instanceof BasicAuthDefinition; + sec.isOAuth = !sec.isBasic; + } + sec.hasMore = entries.hasNext(); secs.add(sec); } From fc9d6325221f56998c8aa0c49b733715a25e959f Mon Sep 17 00:00:00 2001 From: William Cheng Date: Tue, 17 Mar 2015 05:24:43 +0800 Subject: [PATCH 49/70] update ruby client to support form parameters, add PATCH support, update ruby petstore client --- .../src/main/resources/ruby/api.mustache | 16 +++- .../resources/ruby/swagger/request.mustache | 24 ++++- samples/client/petstore/ruby/lib/PetApi.rb | 92 ++++++++++++++----- samples/client/petstore/ruby/lib/StoreApi.rb | 44 ++++++--- samples/client/petstore/ruby/lib/UserApi.rb | 88 +++++++++++++----- .../petstore/ruby/lib/swagger/request.rb | 24 ++++- 6 files changed, 215 insertions(+), 73 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/ruby/api.mustache b/modules/swagger-codegen/src/main/resources/ruby/api.mustache index b2c546b011..1448e52bdf 100644 --- a/modules/swagger-codegen/src/main/resources/ruby/api.mustache +++ b/modules/swagger-codegen/src/main/resources/ruby/api.mustache @@ -37,14 +37,15 @@ class {{classname}} queryopts = options.select do |key,value| query_param_keys.include? key end - + {{#headerParams}}headers = { {{{paramName}}}: {{{paramName}}}, } {{/headerParams}} {{^headerParams}}headers = nil {{/headerParams}} - + + # http body (model) post_body = nil {{#bodyParam}} if body != nil @@ -69,17 +70,22 @@ class {{classname}} end {{/bodyParam}} + # form parameters + form_parameter_hash = {} + {{#formParams}}{{#optional}}form_parameter_hash["{{baseName}}"] = options[:'{{paramName}}'] if options[:'{{paramName}}']{{/optional}} + {{^optional}}form_parameter_hash["{{baseName}}"] = {{paramName}}{{/optional}}{{/formParams}} + {{#returnType}} - response = Swagger::Request.new(:{{httpMethod}}, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + response = Swagger::Request.new(:{{httpMethod}}, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body {{#returnContainer}} response.map {|response|{{/returnContainer}} {{returnBaseType}}.new(response){{#returnContainer}} }{{/returnContainer}} {{/returnType}} {{^returnType}} - Swagger::Request.new(:{{httpMethod}}, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:{{httpMethod}}, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make {{/returnType}} {{newline}} end {{/operation}} end -{{/operations}} \ No newline at end of file +{{/operations}} diff --git a/modules/swagger-codegen/src/main/resources/ruby/swagger/request.mustache b/modules/swagger-codegen/src/main/resources/ruby/swagger/request.mustache index 7836cb0bf0..92b5cba810 100644 --- a/modules/swagger-codegen/src/main/resources/ruby/swagger/request.mustache +++ b/modules/swagger-codegen/src/main/resources/ruby/swagger/request.mustache @@ -6,7 +6,7 @@ module Swagger require 'typhoeus' require "swagger/version" - attr_accessor :host, :path, :format, :params, :body, :http_method, :headers + attr_accessor :host, :path, :format, :params, :body, :http_method, :headers, :form_params # All requests must have an HTTP method and a path @@ -115,9 +115,18 @@ module Swagger end # If body is an object, JSONify it before making the actual request. - # + # For form parameters, remove empty value def outgoing_body - body.is_a?(String) ? body : body.to_json + # http form + if @body.nil? && @form_params && !@form_params.empty? + data = form_params.dup + data.each do |key, value| + data[key] = value.to_s if value && !value.is_a?(File) # remove emtpy form parameter + end + data + else # http body is JSON + @body.is_a?(String) ? @body : @body.to_json + end end # Construct a query string from the query-string-type params @@ -163,6 +172,13 @@ module Swagger :headers => self.headers.stringify_keys, ) + when :patch,:PATCH + Typhoeus::Request.patch( + self.url, + :body => self.outgoing_body, + :headers => self.headers.stringify_keys, + ) + when :put,:PUT Typhoeus::Request.put( self.url, @@ -196,4 +212,4 @@ module Swagger end end -end \ No newline at end of file +end diff --git a/samples/client/petstore/ruby/lib/PetApi.rb b/samples/client/petstore/ruby/lib/PetApi.rb index 41b4f4122c..d7d55a7c32 100644 --- a/samples/client/petstore/ruby/lib/PetApi.rb +++ b/samples/client/petstore/ruby/lib/PetApi.rb @@ -28,11 +28,12 @@ class PetApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil if body != nil @@ -57,9 +58,13 @@ class PetApi end + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:PUT, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:PUT, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -84,11 +89,12 @@ class PetApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil if body != nil @@ -113,9 +119,13 @@ class PetApi end + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -140,16 +150,21 @@ class PetApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} - response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body response.map {|response| Pet.new(response) } @@ -177,16 +192,21 @@ class PetApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} - response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body response.map {|response| Pet.new(response) } @@ -215,16 +235,21 @@ class PetApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} - response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body Pet.new(response) @@ -258,17 +283,24 @@ class PetApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} + + form_parameter_hash["name"] = name + form_parameter_hash["status"] = status + - Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -297,19 +329,24 @@ class PetApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = { api_key: api_key, } - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -341,17 +378,24 @@ class PetApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} + + form_parameter_hash["additionalMetadata"] = additionalMetadata + form_parameter_hash["file"] = file + - Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end diff --git a/samples/client/petstore/ruby/lib/StoreApi.rb b/samples/client/petstore/ruby/lib/StoreApi.rb index b5d33010cc..31513cc832 100644 --- a/samples/client/petstore/ruby/lib/StoreApi.rb +++ b/samples/client/petstore/ruby/lib/StoreApi.rb @@ -26,16 +26,21 @@ class StoreApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} - response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body response.map {|response| map.new(response) } @@ -63,11 +68,12 @@ class StoreApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil if body != nil @@ -92,8 +98,12 @@ class StoreApi end + # form parameters + form_parameter_hash = {} - response = Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + + response = Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body Order.new(response) @@ -121,16 +131,21 @@ class StoreApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} - response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body Order.new(response) @@ -158,17 +173,22 @@ class StoreApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end diff --git a/samples/client/petstore/ruby/lib/UserApi.rb b/samples/client/petstore/ruby/lib/UserApi.rb index 40051e7c9f..4b24bf1f48 100644 --- a/samples/client/petstore/ruby/lib/UserApi.rb +++ b/samples/client/petstore/ruby/lib/UserApi.rb @@ -28,11 +28,12 @@ class UserApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil if body != nil @@ -57,9 +58,13 @@ class UserApi end + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -84,11 +89,12 @@ class UserApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil if body != nil @@ -113,9 +119,13 @@ class UserApi end + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -140,11 +150,12 @@ class UserApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil if body != nil @@ -169,9 +180,13 @@ class UserApi end + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:POST, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -199,16 +214,21 @@ class UserApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} - response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body string.new(response) @@ -233,17 +253,22 @@ class UserApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -269,16 +294,21 @@ class UserApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} - response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body }).make.body + + + response = Swagger::Request.new(:GET, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make.body User.new(response) @@ -309,11 +339,12 @@ class UserApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil if body != nil @@ -338,9 +369,13 @@ class UserApi end + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:PUT, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:PUT, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end @@ -366,17 +401,22 @@ class UserApi queryopts = options.select do |key,value| query_param_keys.include? key end - + headers = nil - + + # http body (model) post_body = nil + # form parameters + form_parameter_hash = {} + + - Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body}).make + Swagger::Request.new(:DELETE, path, {:params=>queryopts,:headers=>headers, :body=>post_body, :form_params => form_parameter_hash }).make end diff --git a/samples/client/petstore/ruby/lib/swagger/request.rb b/samples/client/petstore/ruby/lib/swagger/request.rb index 7836cb0bf0..92b5cba810 100644 --- a/samples/client/petstore/ruby/lib/swagger/request.rb +++ b/samples/client/petstore/ruby/lib/swagger/request.rb @@ -6,7 +6,7 @@ module Swagger require 'typhoeus' require "swagger/version" - attr_accessor :host, :path, :format, :params, :body, :http_method, :headers + attr_accessor :host, :path, :format, :params, :body, :http_method, :headers, :form_params # All requests must have an HTTP method and a path @@ -115,9 +115,18 @@ module Swagger end # If body is an object, JSONify it before making the actual request. - # + # For form parameters, remove empty value def outgoing_body - body.is_a?(String) ? body : body.to_json + # http form + if @body.nil? && @form_params && !@form_params.empty? + data = form_params.dup + data.each do |key, value| + data[key] = value.to_s if value && !value.is_a?(File) # remove emtpy form parameter + end + data + else # http body is JSON + @body.is_a?(String) ? @body : @body.to_json + end end # Construct a query string from the query-string-type params @@ -163,6 +172,13 @@ module Swagger :headers => self.headers.stringify_keys, ) + when :patch,:PATCH + Typhoeus::Request.patch( + self.url, + :body => self.outgoing_body, + :headers => self.headers.stringify_keys, + ) + when :put,:PUT Typhoeus::Request.put( self.url, @@ -196,4 +212,4 @@ module Swagger end end -end \ No newline at end of file +end From fd792ef180bb1fe46e9ed0db7fccc1aa5fda8ad9 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 16 Mar 2015 20:53:34 -0700 Subject: [PATCH 50/70] added more helpful error trace --- .../java/com/wordnik/swagger/codegen/DefaultCodegen.java | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index 2abcfad31e..4057d2975c 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -399,7 +399,14 @@ public class DefaultCodegen { LOGGER.warn("null property for " + key); } else { - CodegenProperty cp = fromProperty(key, prop); + CodegenProperty cp; + try{ + cp = fromProperty(key, prop); + } + catch(Exception e) { + System.out.println("failed to process model " + name); + throw new RuntimeException(e); + } cp.required = false; if(impl.getRequired() != null) { for(String req : impl.getRequired()) { From ebec85fd543b9d54e56a9cbb46f14f35a8644dcf Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 16 Mar 2015 20:53:48 -0700 Subject: [PATCH 51/70] added context path --- .../java/com/wordnik/swagger/codegen/DefaultGenerator.java | 3 +++ 1 file changed, 3 insertions(+) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java index be143e4ec5..01fb25423a 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java @@ -66,8 +66,10 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { else hostBuilder.append("https://"); hostBuilder.append(swagger.getHost()).append(swagger.getBasePath()); + String contextPath = swagger.getBasePath(); String basePath = hostBuilder.toString(); + List allOperations = new ArrayList(); List allModels = new ArrayList(); @@ -111,6 +113,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { List ops = paths.get(tag); Map operation = processOperations(config, tag, ops); operation.put("basePath", basePath); + operation.put("contextPath", contextPath); operation.put("baseName", tag); operation.put("modelPackage", config.modelPackage()); operation.putAll(config.additionalProperties()); From fd72ff56bf7a408000fa0a4dbb7f8a81cf6ef499 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 16 Mar 2015 20:54:01 -0700 Subject: [PATCH 52/70] fixed context path --- .../src/main/resources/JavaJaxRS/pom.mustache | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/JavaJaxRS/pom.mustache b/modules/swagger-codegen/src/main/resources/JavaJaxRS/pom.mustache index f2d2907717..9ead2787b3 100644 --- a/modules/swagger-codegen/src/main/resources/JavaJaxRS/pom.mustache +++ b/modules/swagger-codegen/src/main/resources/JavaJaxRS/pom.mustache @@ -31,7 +31,7 @@ ${jetty-version} - {{^basePath}}/{{/basePath}}{{#basePath}}{{basePath}}{{/basePath}} + {{^contextPath}}/{{/contextPath}}{{#contextPath}}{{contextPath}}{{/contextPath}} target/${project.artifactId}-${project.version} ${project.basedir}/conf/jetty/webdefault.xml @@ -123,8 +123,17 @@ ${servlet-api-version} + + + sonatype-snapshots + https://oss.sonatype.org/content/repositories/snapshots + + true + + + - 1.5.1-M1 + 1.5.3-M1-SNAPSHOT 8.1.11.v20130520 1.13 1.6.3 From a8aebec9bae3bab7de988cc5d2a546965c90d090 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 16 Mar 2015 20:54:08 -0700 Subject: [PATCH 53/70] removed description --- modules/swagger-codegen/src/main/resources/nodejs/api.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/resources/nodejs/api.mustache b/modules/swagger-codegen/src/main/resources/nodejs/api.mustache index 82f0145ce8..e2f94f7a55 100644 --- a/modules/swagger-codegen/src/main/resources/nodejs/api.mustache +++ b/modules/swagger-codegen/src/main/resources/nodejs/api.mustache @@ -19,7 +19,7 @@ exports.models = models = require("../models.js"); {{#operation}} exports.{{nickname}} = { 'spec': { - "description" : "Operations about pets", + "description" : "the {{baseName}} API", "path" : "{{path}}", "notes" : "{{{notes}}}", "summary" : "{{{summary}}}", From 46d1950fbdcf4759fda0b530e6942adb439a9119 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 16 Mar 2015 21:04:21 -0700 Subject: [PATCH 54/70] removed unnecessary file --- .../com/wordnik/swagger/codegen/haproxy.cfg | 86 ------------------- 1 file changed, 86 deletions(-) delete mode 100644 modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/haproxy.cfg diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/haproxy.cfg b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/haproxy.cfg deleted file mode 100644 index 9fd8d61f2c..0000000000 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/haproxy.cfg +++ /dev/null @@ -1,86 +0,0 @@ -#--------------------------------------------------------------------- -# Global settings -#--------------------------------------------------------------------- -global - log 127.0.0.1 local2 - chroot /var/lib/haproxy - pidfile /var/run/haproxy.pid - maxconn 4000 - user haproxy - group haproxy - daemon - -#--------------------------------------------------------------------- -# common defaults that all the 'listen' and 'backend' sections will -# use if not designated in their block -#--------------------------------------------------------------------- -defaults - mode http - log global - option dontlognull - option httpclose - option httplog - option forwardfor - option redispatch - timeout connect 10000 # default 10 second time out if a backend is not found - timeout client 300000 - timeout server 300000 - maxconn 60000 - retries 3 - -#--------------------------------------------------------------------- -# main frontend which proxys to the backends -#--------------------------------------------------------------------- -frontend main *:80 - default_backend app - - acl is_swagger_online hdr_beg(host) -i online.swagger.io - acl is_swagger_io hdr_beg(host) -i swagger.io - acl is_old hdr_beg(host) -i swagger.wordnik.com - acl is_old_editor hdr_beg(host) -i editor.swagger.wordnik.com - acl is_validator_swagger path_beg /swagger.json - - # online spec validator - reqrep ([^\ ]*)\ /validator/(.*) \1\ /validator/validator/\2 if is_swagger_online - - # something that didn't work - reqrep ([^\ ]*)\ /swagger.json(.*) \1\ /validator/swagger.json if is_validator_swagger - - # swagger schema - reqrep ^([^\ :]*)\ /v2/schema.json(.*) \1\ /swagger-api/swagger-spec/master/schemas/v2.0/schema.json\2 - acl is_swagger_spec path_beg /swagger-api/swagger-spec - - # swagger docs - reqrep ^([^\ :]*)\ /swagger-core/documentation/annotations/apidocs/current(.*) \1\ /swagger-core/apidocs/\2 - acl is_swagger_docs path_beg /swagger-core/apidocs - - use_backend github_swagger_io if is_swagger_docs - use_backend validator if is_swagger_online - use_backend validator if is_validator_swagger - use_backend github_swagger_io if is_swagger_io !is_swagger_spec - use_backend github_swagger_spec if is_swagger_spec - - redirect location http://editor.swagger.io if is_old_editor - redirect location http://swagger.io if is_old - -#--------------------------------------------------------------------- -# round robin balancing between the various backends -#--------------------------------------------------------------------- -backend github_swagger_io - balance roundrobin - server gh1 swagger-api.github.io:80 check - -backend github_swagger_spec - http-request set-header Host raw.githubusercontent.com - rspirep ^Content-type:(.*) Content-Type:\ application/json - rspirep ^Access-Control-Allow-Origin:(.*) Access-Control-Allow-Origin:* - balance roundrobin - server gh2 raw.githubusercontent.com:443 check ssl verify none - -backend validator - balance roundrobin - server app1 127.0.0.1:8000 check - -backend app - balance roundrobin - server app1 127.0.0.1:8000 check From c215d8ab919de78dfc98a6887c10a86a25410b18 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Mon, 16 Mar 2015 22:10:35 -0700 Subject: [PATCH 55/70] fix and tests for #503 --- .../swagger/codegen/DefaultCodegen.java | 23 ++++++++++--------- .../codegen/languages/JavaClientCodegen.java | 9 ++++++++ .../src/test/scala/Java/JavaModelTest.scala | 15 +++++++++++- 3 files changed, 35 insertions(+), 12 deletions(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index 4057d2975c..d0a169b787 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -448,18 +448,19 @@ public class DefaultCodegen { return m; } - public static String getterAndSetterCapitalize(String name) { - if (name == null || name.length() == 0) { - return name; - } - if (name.length() > 1 && Character.isUpperCase(name.charAt(1)) && - Character.isLowerCase(name.charAt(0))){ - return name; - } - char chars[] = name.toCharArray(); - chars[0] = Character.toUpperCase(chars[0]); - return new String(chars); + public String getterAndSetterCapitalize(String name) { + if (name == null || name.length() == 0) { + return name; } + name = toVarName(name); + if (name.length() > 1 && Character.isUpperCase(name.charAt(1)) && + Character.isLowerCase(name.charAt(0))){ + return name; + } + char chars[] = name.toCharArray(); + chars[0] = Character.toUpperCase(chars[0]); + return new String(chars); + } public CodegenProperty fromProperty(String name, Property p) { if(p == null) { diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/JavaClientCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/JavaClientCodegen.java index 1475db64bf..b4698ecc71 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/JavaClientCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/JavaClientCodegen.java @@ -87,6 +87,15 @@ public class JavaClientCodegen extends DefaultCodegen implements CodegenConfig { return outputFolder + "/" + sourceFolder + "/" + modelPackage().replace('.', File.separatorChar); } + @Override + public String toVarName(String name) { + if(reservedWords.contains(name)) + return escapeReservedWord(name); + else { + return name.replaceAll("-", "_"); + } + } + @Override public String getTypeDeclaration(Property p) { if(p instanceof ArrayProperty) { diff --git a/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala b/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala index 1e39a715eb..33eb5f75b9 100644 --- a/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala +++ b/modules/swagger-codegen/src/test/scala/Java/JavaModelTest.scala @@ -14,7 +14,6 @@ import scala.collection.JavaConverters._ @RunWith(classOf[JUnitRunner]) class JavaModelTest extends FlatSpec with Matchers { - it should "convert a simple java model" in { val model = new ModelImpl() .description("a sample model") @@ -322,4 +321,18 @@ class JavaModelTest extends FlatSpec with Matchers { vars.get(0).required should equal (true) vars.get(0).isNotContainer should equal (true) } + + it should "convert hyphens per issue 503" in { + val model = new ModelImpl() + .description("a sample model") + .property("created-at", new DateTimeProperty()) + + val codegen = new JavaClientCodegen() + val cm = codegen.fromModel("sample", model) + val vars = cm.vars + vars.get(0).baseName should be("created-at") + vars.get(0).getter should be ("getCreated_at") + vars.get(0).setter should be ("setCreated_at") + vars.get(0).name should be ("created_at") + } } From b2da6dc8a2e157d340dba35e9038477fc1d2a9e3 Mon Sep 17 00:00:00 2001 From: Xu Hui Hui Date: Tue, 17 Mar 2015 16:34:01 +0800 Subject: [PATCH 56/70] update null comparison for query params in Java to make it clear and also allow a query parameter to be set with string value: "null" (4 characters string) --- modules/swagger-codegen/src/main/resources/Java/api.mustache | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/resources/Java/api.mustache b/modules/swagger-codegen/src/main/resources/Java/api.mustache index c0a697e40b..4a1ab1dc77 100644 --- a/modules/swagger-codegen/src/main/resources/Java/api.mustache +++ b/modules/swagger-codegen/src/main/resources/Java/api.mustache @@ -58,7 +58,7 @@ public class {{classname}} { Map headerParams = new HashMap(); Map formParams = new HashMap(); - {{#queryParams}}if(!"null".equals(String.valueOf({{paramName}}))) + {{#queryParams}}if ({{paramName}} != null) queryParams.put("{{baseName}}", String.valueOf({{paramName}})); {{/queryParams}} {{#headerParams}}headerParams.put("{{baseName}}", {{paramName}}); From a1d02785afa37b4e981617bf4f6dc373c0383dbb Mon Sep 17 00:00:00 2001 From: William Cheng Date: Wed, 18 Mar 2015 00:14:39 +0800 Subject: [PATCH 57/70] update README with ruby on the codegen usage --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index fc140685e7..1e5c000f5b 100644 --- a/README.md +++ b/README.md @@ -64,9 +64,9 @@ usage: Codegen -i,--input-spec location of the swagger spec, as URL or file -l,--lang client language to generate. Available languages include: - [android, java, jaxrs, nodejs, objc, scalatra, - scala, dynamic-html, html, swagger, tizen, php, - python] + [android, async-scala, java, jaxrs, nodejs, + objc, scalatra, scala, dynamic-html, html, + swagger, tizen, php, ruby, python] -o,--output where to write the generated files -t,--template-dir folder containing the template files ``` From df39fe5d081a2f84b1139134971aac300c89f7da Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Tue, 17 Mar 2015 16:30:42 -0700 Subject: [PATCH 58/70] added Json schema fields --- .../swagger/codegen/CodegenOperation.java | 3 ++- .../swagger/codegen/CodegenParameter.java | 3 +++ .../swagger/codegen/CodegenProperty.java | 1 + .../swagger/codegen/CodegenResponse.java | 3 ++- .../swagger/codegen/DefaultCodegen.java | 5 +++-- .../swagger/codegen/DefaultGenerator.java | 21 ++++++++++++++++--- 6 files changed, 29 insertions(+), 7 deletions(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenOperation.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenOperation.java index 12b405edeb..7f8d390f37 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenOperation.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenOperation.java @@ -6,7 +6,8 @@ import java.util.*; public class CodegenOperation { public Boolean hasConsumes, hasProduces, hasParams, returnTypeIsPrimitive, - returnSimpleType, subresourceOperation, isMapContainer, isListContainer; + returnSimpleType, subresourceOperation, isMapContainer, isListContainer, + hasMore = Boolean.TRUE; public String path, operationId, returnType, httpMethod, returnBaseType, returnContainer, summary, notes, baseName, defaultResponse; diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenParameter.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenParameter.java index 4480c172c3..04cecabad9 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenParameter.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenParameter.java @@ -4,6 +4,8 @@ public class CodegenParameter { public Boolean isFormParam, isQueryParam, isPathParam, isHeaderParam, isCookieParam, isBodyParam, isFile, notFile, hasMore, isContainer, secondaryParam; public String baseName, paramName, dataType, collectionFormat, description, baseType; + public String jsonSchema; + /** * Determines whether this parameter is mandatory. If the parameter is in "path", * this property is required and its value MUST be true. Otherwise, the property @@ -31,6 +33,7 @@ public class CodegenParameter { output.isCookieParam = this.isCookieParam; output.isBodyParam = this.isBodyParam; output.required = this.required; + output.jsonSchema = this.jsonSchema; return output; } diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenProperty.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenProperty.java index c5ea8a0da4..b00c962ba6 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenProperty.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenProperty.java @@ -15,6 +15,7 @@ public class CodegenProperty { /** A free-form property to include an example of an instance for this schema. */ public String example; + public String jsonSchema; public Double minimum, maximum, exclusiveMinimum, exclusiveMaximum; public Boolean hasMore = null, required = null, secondaryParam = null; public Boolean isPrimitiveType, isContainer, isNotContainer; diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java index d940e4922e..82f0babc48 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java @@ -11,5 +11,6 @@ public class CodegenResponse { public Boolean primitiveType; public Boolean isMapContainer; public Boolean isListContainer; - Object schema; + public Object schema; + public String jsonSchema; } \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index d0a169b787..7d22dc1ec2 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -476,9 +476,9 @@ public class DefaultCodegen { property.setter = "set" + getterAndSetterCapitalize(name); property.example = p.getExample(); property.defaultValue = toDefaultValue(p); + property.jsonSchema = Json.pretty(p); String type = getSwaggerType(p); - if(p instanceof AbstractNumericProperty) { AbstractNumericProperty np = (AbstractNumericProperty) p; property.minimum = np.getMinimum(); @@ -640,7 +640,6 @@ public class DefaultCodegen { } if (operation.getResponses() != null && !operation.getResponses().isEmpty()) { - Response methodResponse = findMethodResponse(operation.getResponses()); CodegenResponse methodCodegenResponse = null; @@ -758,6 +757,7 @@ public class DefaultCodegen { r.message = response.getDescription(); r.schema = response.getSchema(); r.examples = toExamples(response.getExamples()); + r.jsonSchema = Json.pretty(response); if (r.schema != null) { Property responseProperty = response.getSchema(); @@ -800,6 +800,7 @@ public class DefaultCodegen { p.baseName = param.getName(); p.description = param.getDescription(); p.required = param.getRequired(); + p.jsonSchema = Json.pretty(param); if(param instanceof SerializableParameter) { SerializableParameter qp = (SerializableParameter) param; diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java index 01fb25423a..a9be9f7889 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java @@ -65,8 +65,15 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { } else hostBuilder.append("https://"); - hostBuilder.append(swagger.getHost()).append(swagger.getBasePath()); - String contextPath = swagger.getBasePath(); + if(swagger.getHost() != null) + hostBuilder.append(swagger.getHost()); + else + hostBuilder.append("localhost"); + if(swagger.getBasePath() != null) + hostBuilder.append(swagger.getBasePath()); + else + hostBuilder.append("/"); + String contextPath = swagger.getBasePath() == null ? "/" : swagger.getBasePath(); String basePath = hostBuilder.toString(); @@ -119,7 +126,7 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { operation.putAll(config.additionalProperties()); operation.put("classname", config.toApiName(tag)); operation.put("classVarName", config.toApiVarName(tag)); - allOperations.add(operation); + allOperations.add(new HashMap(operation)); for(String templateName : config.apiTemplateFiles().keySet()) { String suffix = config.apiTemplateFiles().get(templateName); String filename = config.apiFileFolder() + @@ -319,6 +326,14 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { operations.put("imports", imports); config.postProcessOperations(operations); + if(objs.size() > 0) { + List os = (List) objs.get("operation"); + + if(os != null && os.size() > 0) { + CodegenOperation op = os.get(os.size() - 1); + op.hasMore = null; + } + } return operations; } From d0dcb2fb433d65203f7339baccdf6e8d3054b49e Mon Sep 17 00:00:00 2001 From: William Cheng Date: Wed, 18 Mar 2015 16:33:00 +0800 Subject: [PATCH 59/70] fix bug with ruby header parameter, remove extra linebreak in generated code --- .../src/main/resources/ruby/api.mustache | 16 ++--- .../src/main/resources/ruby/model.mustache | 13 ++-- samples/client/petstore/ruby/lib/PetApi.rb | 62 ++++++++----------- samples/client/petstore/ruby/lib/StoreApi.rb | 23 +++---- samples/client/petstore/ruby/lib/UserApi.rb | 51 +++++++-------- .../client/petstore/ruby/models/Category.rb | 10 +-- samples/client/petstore/ruby/models/Order.rb | 30 ++------- samples/client/petstore/ruby/models/Pet.rb | 30 ++------- samples/client/petstore/ruby/models/Tag.rb | 10 +-- samples/client/petstore/ruby/models/User.rb | 40 +++--------- 10 files changed, 95 insertions(+), 190 deletions(-) diff --git a/modules/swagger-codegen/src/main/resources/ruby/api.mustache b/modules/swagger-codegen/src/main/resources/ruby/api.mustache index 1448e52bdf..c045a46f69 100644 --- a/modules/swagger-codegen/src/main/resources/ruby/api.mustache +++ b/modules/swagger-codegen/src/main/resources/ruby/api.mustache @@ -23,10 +23,8 @@ class {{classname}} # set default values and merge with input options = { - {{#allParams}} - :{{paramName}} => {{paramName}}{{#hasMore}}, - {{/hasMore}} - {{/allParams}} + {{#allParams}}:'{{paramName}}' => {{paramName}}{{#hasMore}},{{/hasMore}} + {{/allParams}} }.merge(opts) #resource path @@ -38,12 +36,10 @@ class {{classname}} query_param_keys.include? key end - {{#headerParams}}headers = { - {{{paramName}}}: {{{paramName}}}, - } - {{/headerParams}} - {{^headerParams}}headers = nil - {{/headerParams}} + # header parameters, if any + headers = {} + {{#headerParams}}{{#optional}}headers[:'{{{baseName}}}'] = options[:'{{{paramName}}}'] if options[:'{{{paramName}}}']{{/optional}}{{/headerParams}} + {{#headerParams}}{{^optional}}headers[:'{{{baseName}}}'] = {{{paramName}}}{{/optional}}{{/headerParams}} # http body (model) post_body = nil diff --git a/modules/swagger-codegen/src/main/resources/ruby/model.mustache b/modules/swagger-codegen/src/main/resources/ruby/model.mustache index ef3b2fe48f..397a64f647 100644 --- a/modules/swagger-codegen/src/main/resources/ruby/model.mustache +++ b/modules/swagger-codegen/src/main/resources/ruby/model.mustache @@ -6,8 +6,7 @@ class {{classname}} # :internal => :external def self.attribute_map { - {{#vars}} - :{{{name}}} => :{{{baseName}}}{{#hasMore}},{{/hasMore}} + {{#vars}}:{{{name}}} => :'{{{baseName}}}'{{#hasMore}},{{/hasMore}} {{/vars}} } end @@ -17,13 +16,9 @@ class {{classname}} # Morph attribute keys into undescored rubyish style {{#vars}} if self.class.attribute_map[:"{{{name}}}"] - {{#isContainer}} - if (value = attributes["{{{baseName}}}"]).is_a?(Array) - @{{{name}}} = value{{#complexType}}.map{ |v| {{complexType}}.new(v) }{{/complexType}}{{newline}} - end - {{/isContainer}}{{^isContainer}} - @{{{name}}} = attributes["{{{baseName}}}"] - {{/isContainer}} + {{#isContainer}}if (value = attributes["{{{baseName}}}"]).is_a?(Array) + @{{{name}}} = value{{#complexType}}.map{ |v| {{complexType}}.new(v) }{{/complexType}} + end{{/isContainer}}{{^isContainer}}@{{{name}}} = attributes["{{{baseName}}}"]{{/isContainer}} end {{/vars}} end diff --git a/samples/client/petstore/ruby/lib/PetApi.rb b/samples/client/petstore/ruby/lib/PetApi.rb index d7d55a7c32..3beeca44da 100644 --- a/samples/client/petstore/ruby/lib/PetApi.rb +++ b/samples/client/petstore/ruby/lib/PetApi.rb @@ -16,9 +16,8 @@ class PetApi # set default values and merge with input options = { - :body => body - + }.merge(opts) #resource path @@ -29,8 +28,9 @@ class PetApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -77,9 +77,8 @@ class PetApi # set default values and merge with input options = { - :body => body - + }.merge(opts) #resource path @@ -90,8 +89,9 @@ class PetApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -138,9 +138,8 @@ class PetApi # set default values and merge with input options = { - :status => status - + }.merge(opts) #resource path @@ -151,8 +150,9 @@ class PetApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -180,9 +180,8 @@ class PetApi # set default values and merge with input options = { - :tags => tags - + }.merge(opts) #resource path @@ -193,8 +192,9 @@ class PetApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -222,9 +222,8 @@ class PetApi # set default values and merge with input options = { - :petId => petId - + }.merge(opts) #resource path @@ -236,8 +235,9 @@ class PetApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -264,15 +264,10 @@ class PetApi # set default values and merge with input options = { - :petId => petId, - - :name => name, - - :status => status - + }.merge(opts) #resource path @@ -284,8 +279,9 @@ class PetApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -313,12 +309,9 @@ class PetApi # set default values and merge with input options = { - :api_key => api_key, - - :petId => petId - + }.merge(opts) #resource path @@ -330,11 +323,10 @@ class PetApi query_param_keys.include? key end - headers = { - api_key: api_key, - } - + # header parameters, if any + headers = {} + headers[:'api_key'] = api_key # http body (model) post_body = nil @@ -359,15 +351,10 @@ class PetApi # set default values and merge with input options = { - :petId => petId, - - :additionalMetadata => additionalMetadata, - - :file => file - + }.merge(opts) #resource path @@ -379,8 +366,9 @@ class PetApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) diff --git a/samples/client/petstore/ruby/lib/StoreApi.rb b/samples/client/petstore/ruby/lib/StoreApi.rb index 31513cc832..c66c7678e7 100644 --- a/samples/client/petstore/ruby/lib/StoreApi.rb +++ b/samples/client/petstore/ruby/lib/StoreApi.rb @@ -16,7 +16,7 @@ class StoreApi # set default values and merge with input options = { - + }.merge(opts) #resource path @@ -27,8 +27,9 @@ class StoreApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -56,9 +57,8 @@ class StoreApi # set default values and merge with input options = { - :body => body - + }.merge(opts) #resource path @@ -69,8 +69,9 @@ class StoreApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -118,9 +119,8 @@ class StoreApi # set default values and merge with input options = { - :orderId => orderId - + }.merge(opts) #resource path @@ -132,8 +132,9 @@ class StoreApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -160,9 +161,8 @@ class StoreApi # set default values and merge with input options = { - :orderId => orderId - + }.merge(opts) #resource path @@ -174,8 +174,9 @@ class StoreApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) diff --git a/samples/client/petstore/ruby/lib/UserApi.rb b/samples/client/petstore/ruby/lib/UserApi.rb index 4b24bf1f48..ab4ce49e95 100644 --- a/samples/client/petstore/ruby/lib/UserApi.rb +++ b/samples/client/petstore/ruby/lib/UserApi.rb @@ -16,9 +16,8 @@ class UserApi # set default values and merge with input options = { - :body => body - + }.merge(opts) #resource path @@ -29,8 +28,9 @@ class UserApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -77,9 +77,8 @@ class UserApi # set default values and merge with input options = { - :body => body - + }.merge(opts) #resource path @@ -90,8 +89,9 @@ class UserApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -138,9 +138,8 @@ class UserApi # set default values and merge with input options = { - :body => body - + }.merge(opts) #resource path @@ -151,8 +150,9 @@ class UserApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -199,12 +199,9 @@ class UserApi # set default values and merge with input options = { - :username => username, - - :password => password - + }.merge(opts) #resource path @@ -215,8 +212,9 @@ class UserApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -243,7 +241,7 @@ class UserApi # set default values and merge with input options = { - + }.merge(opts) #resource path @@ -254,8 +252,9 @@ class UserApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -281,9 +280,8 @@ class UserApi # set default values and merge with input options = { - :username => username - + }.merge(opts) #resource path @@ -295,8 +293,9 @@ class UserApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -323,12 +322,9 @@ class UserApi # set default values and merge with input options = { - :username => username, - - :body => body - + }.merge(opts) #resource path @@ -340,8 +336,9 @@ class UserApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) @@ -388,9 +385,8 @@ class UserApi # set default values and merge with input options = { - :username => username - + }.merge(opts) #resource path @@ -402,8 +398,9 @@ class UserApi query_param_keys.include? key end + # header parameters, if any + headers = {} - headers = nil # http body (model) diff --git a/samples/client/petstore/ruby/models/Category.rb b/samples/client/petstore/ruby/models/Category.rb index 0f15c43a70..64ca857e17 100644 --- a/samples/client/petstore/ruby/models/Category.rb +++ b/samples/client/petstore/ruby/models/Category.rb @@ -4,10 +4,8 @@ class Category # :internal => :external def self.attribute_map { - - :id => :id, - - :name => :name + :id => :'id', + :name => :'name' } end @@ -17,15 +15,11 @@ class Category # Morph attribute keys into undescored rubyish style if self.class.attribute_map[:"id"] - @id = attributes["id"] - end if self.class.attribute_map[:"name"] - @name = attributes["name"] - end end diff --git a/samples/client/petstore/ruby/models/Order.rb b/samples/client/petstore/ruby/models/Order.rb index 45a0864cfc..e7db88e16c 100644 --- a/samples/client/petstore/ruby/models/Order.rb +++ b/samples/client/petstore/ruby/models/Order.rb @@ -4,18 +4,12 @@ class Order # :internal => :external def self.attribute_map { - - :id => :id, - - :petId => :petId, - - :quantity => :quantity, - - :shipDate => :shipDate, - - :status => :status, - - :complete => :complete + :id => :'id', + :petId => :'petId', + :quantity => :'quantity', + :shipDate => :'shipDate', + :status => :'status', + :complete => :'complete' } end @@ -25,39 +19,27 @@ class Order # Morph attribute keys into undescored rubyish style if self.class.attribute_map[:"id"] - @id = attributes["id"] - end if self.class.attribute_map[:"petId"] - @petId = attributes["petId"] - end if self.class.attribute_map[:"quantity"] - @quantity = attributes["quantity"] - end if self.class.attribute_map[:"shipDate"] - @shipDate = attributes["shipDate"] - end if self.class.attribute_map[:"status"] - @status = attributes["status"] - end if self.class.attribute_map[:"complete"] - @complete = attributes["complete"] - end end diff --git a/samples/client/petstore/ruby/models/Pet.rb b/samples/client/petstore/ruby/models/Pet.rb index f67067e6f9..b279ad5eb3 100644 --- a/samples/client/petstore/ruby/models/Pet.rb +++ b/samples/client/petstore/ruby/models/Pet.rb @@ -4,18 +4,12 @@ class Pet # :internal => :external def self.attribute_map { - - :id => :id, - - :category => :category, - - :name => :name, - - :photoUrls => :photoUrls, - - :tags => :tags, - - :status => :status + :id => :'id', + :category => :'category', + :name => :'name', + :photoUrls => :'photoUrls', + :tags => :'tags', + :status => :'status' } end @@ -25,43 +19,31 @@ class Pet # Morph attribute keys into undescored rubyish style if self.class.attribute_map[:"id"] - @id = attributes["id"] - end if self.class.attribute_map[:"category"] - @category = attributes["category"] - end if self.class.attribute_map[:"name"] - @name = attributes["name"] - end if self.class.attribute_map[:"photoUrls"] - if (value = attributes["photoUrls"]).is_a?(Array) @photoUrls = value end - end if self.class.attribute_map[:"tags"] - if (value = attributes["tags"]).is_a?(Array) @tags = value.map{ |v| Tag.new(v) } end - end if self.class.attribute_map[:"status"] - @status = attributes["status"] - end end diff --git a/samples/client/petstore/ruby/models/Tag.rb b/samples/client/petstore/ruby/models/Tag.rb index 9a9193b8e8..24e3d1d070 100644 --- a/samples/client/petstore/ruby/models/Tag.rb +++ b/samples/client/petstore/ruby/models/Tag.rb @@ -4,10 +4,8 @@ class Tag # :internal => :external def self.attribute_map { - - :id => :id, - - :name => :name + :id => :'id', + :name => :'name' } end @@ -17,15 +15,11 @@ class Tag # Morph attribute keys into undescored rubyish style if self.class.attribute_map[:"id"] - @id = attributes["id"] - end if self.class.attribute_map[:"name"] - @name = attributes["name"] - end end diff --git a/samples/client/petstore/ruby/models/User.rb b/samples/client/petstore/ruby/models/User.rb index b7981a2bc4..f70f6794eb 100644 --- a/samples/client/petstore/ruby/models/User.rb +++ b/samples/client/petstore/ruby/models/User.rb @@ -4,22 +4,14 @@ class User # :internal => :external def self.attribute_map { - - :id => :id, - - :username => :username, - - :firstName => :firstName, - - :lastName => :lastName, - - :email => :email, - - :password => :password, - - :phone => :phone, - - :userStatus => :userStatus + :id => :'id', + :username => :'username', + :firstName => :'firstName', + :lastName => :'lastName', + :email => :'email', + :password => :'password', + :phone => :'phone', + :userStatus => :'userStatus' } end @@ -29,51 +21,35 @@ class User # Morph attribute keys into undescored rubyish style if self.class.attribute_map[:"id"] - @id = attributes["id"] - end if self.class.attribute_map[:"username"] - @username = attributes["username"] - end if self.class.attribute_map[:"firstName"] - @firstName = attributes["firstName"] - end if self.class.attribute_map[:"lastName"] - @lastName = attributes["lastName"] - end if self.class.attribute_map[:"email"] - @email = attributes["email"] - end if self.class.attribute_map[:"password"] - @password = attributes["password"] - end if self.class.attribute_map[:"phone"] - @phone = attributes["phone"] - end if self.class.attribute_map[:"userStatus"] - @userStatus = attributes["userStatus"] - end end From f8a5e900f8ee4734bb5f21611312a13cf8caa4f6 Mon Sep 17 00:00:00 2001 From: xhh Date: Wed, 18 Mar 2015 18:55:18 +0800 Subject: [PATCH 60/70] Add parameterToString to normalize parameters for Java client * Convert values to string for query/header/form parameters. * For parameter of type Date, convert to ISO 8601 format. * Also add utility methods to parse date in ISO 8601 format. --- .../swagger/codegen/DefaultCodegen.java | 4 ++ .../src/main/resources/Java/api.mustache | 8 +-- .../main/resources/Java/apiInvoker.mustache | 61 ++++++++++++++++++- .../java/io/swagger/client/ApiInvoker.java | 61 ++++++++++++++++++- .../java/io/swagger/client/api/PetApi.java | 22 +++---- .../java/io/swagger/client/api/UserApi.java | 8 +-- 6 files changed, 143 insertions(+), 21 deletions(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index bcbd71f374..0aae418b83 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -621,6 +621,8 @@ public class DefaultCodegen { count += 1; if (count < operation.getConsumes().size()) mediaType.put("hasMore", "true"); + else + mediaType.put("hasMore", null); c.add(mediaType); } op.consumes = c; @@ -636,6 +638,8 @@ public class DefaultCodegen { count += 1; if (count < operation.getProduces().size()) mediaType.put("hasMore", "true"); + else + mediaType.put("hasMore", null); c.add(mediaType); } op.produces = c; diff --git a/modules/swagger-codegen/src/main/resources/Java/api.mustache b/modules/swagger-codegen/src/main/resources/Java/api.mustache index 4a1ab1dc77..ad26268d71 100644 --- a/modules/swagger-codegen/src/main/resources/Java/api.mustache +++ b/modules/swagger-codegen/src/main/resources/Java/api.mustache @@ -59,9 +59,9 @@ public class {{classname}} { Map formParams = new HashMap(); {{#queryParams}}if ({{paramName}} != null) - queryParams.put("{{baseName}}", String.valueOf({{paramName}})); + queryParams.put("{{baseName}}", ApiInvoker.parameterToString({{paramName}})); {{/queryParams}} - {{#headerParams}}headerParams.put("{{baseName}}", {{paramName}}); + {{#headerParams}}headerParams.put("{{baseName}}", ApiInvoker.parameterToString({{paramName}})); {{/headerParams}} String[] contentTypes = { {{#consumes}}"{{mediaType}}"{{#hasMore}},{{/hasMore}}{{/consumes}} @@ -74,7 +74,7 @@ public class {{classname}} { FormDataMultiPart mp = new FormDataMultiPart(); {{#formParams}}{{#notFile}} hasFields = true; - mp.field("{{baseName}}", {{paramName}}, MediaType.MULTIPART_FORM_DATA_TYPE); + mp.field("{{baseName}}", ApiInvoker.parameterToString({{paramName}}), MediaType.MULTIPART_FORM_DATA_TYPE); {{/notFile}}{{#isFile}} hasFields = true; mp.field("{{baseName}}", {{paramName}}, MediaType.MULTIPART_FORM_DATA_TYPE); @@ -83,7 +83,7 @@ public class {{classname}} { postBody = mp; } else { - {{#formParams}}{{#notFile}}formParams.put("{{baseName}}", {{paramName}});{{/notFile}} + {{#formParams}}{{#notFile}}formParams.put("{{baseName}}", ApiInvoker.parameterToString({{paramName}}));{{/notFile}} {{/formParams}} } diff --git a/modules/swagger-codegen/src/main/resources/Java/apiInvoker.mustache b/modules/swagger-codegen/src/main/resources/Java/apiInvoker.mustache index 26379c6010..9a8ac94bae 100644 --- a/modules/swagger-codegen/src/main/resources/Java/apiInvoker.mustache +++ b/modules/swagger-codegen/src/main/resources/Java/apiInvoker.mustache @@ -19,16 +19,75 @@ import javax.ws.rs.core.MediaType; import java.util.Map; import java.util.HashMap; import java.util.List; -import java.io.IOException; +import java.util.Date; +import java.util.TimeZone; + import java.net.URLEncoder; + +import java.io.IOException; import java.io.UnsupportedEncodingException; +import java.text.SimpleDateFormat; +import java.text.ParseException; + public class ApiInvoker { private static ApiInvoker INSTANCE = new ApiInvoker(); private Map hostMap = new HashMap(); private Map defaultHeaderMap = new HashMap(); private boolean isDebug = false; + /** + * ISO 8601 date time format. + * @see https://en.wikipedia.org/wiki/ISO_8601 + */ + public static final SimpleDateFormat DATE_TIME_FORMAT = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssXXX"); + + /** + * ISO 8601 date format. + * @see https://en.wikipedia.org/wiki/ISO_8601 + */ + public static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("yyyy-MM-dd"); + + static { + // Use UTC as the default time zone. + DATE_TIME_FORMAT.setTimeZone(TimeZone.getTimeZone("UTC")); + DATE_FORMAT.setTimeZone(TimeZone.getTimeZone("UTC")); + } + + public static Date parseDateTime(String str) { + try { + return DATE_TIME_FORMAT.parse(str); + } catch (java.text.ParseException e) { + throw new RuntimeException(e); + } + } + + public static Date parseDate(String str) { + try { + return DATE_FORMAT.parse(str); + } catch (java.text.ParseException e) { + throw new RuntimeException(e); + } + } + + public static String formatDateTime(Date datetime) { + return DATE_TIME_FORMAT.format(datetime); + } + + public static String formatDate(Date date) { + return DATE_FORMAT.format(date); + } + + public static String parameterToString(Object param) { + if (param == null) { + return ""; + } else if (param instanceof Date) { + return formatDateTime((Date) param); + } else { + return String.valueOf(param); + } + } + public void enableDebug() { isDebug = true; } diff --git a/samples/client/petstore/java/src/main/java/io/swagger/client/ApiInvoker.java b/samples/client/petstore/java/src/main/java/io/swagger/client/ApiInvoker.java index 966a141c03..abe51bb710 100644 --- a/samples/client/petstore/java/src/main/java/io/swagger/client/ApiInvoker.java +++ b/samples/client/petstore/java/src/main/java/io/swagger/client/ApiInvoker.java @@ -19,16 +19,75 @@ import javax.ws.rs.core.MediaType; import java.util.Map; import java.util.HashMap; import java.util.List; -import java.io.IOException; +import java.util.Date; +import java.util.TimeZone; + import java.net.URLEncoder; + +import java.io.IOException; import java.io.UnsupportedEncodingException; +import java.text.SimpleDateFormat; +import java.text.ParseException; + public class ApiInvoker { private static ApiInvoker INSTANCE = new ApiInvoker(); private Map hostMap = new HashMap(); private Map defaultHeaderMap = new HashMap(); private boolean isDebug = false; + /** + * ISO 8601 date time format. + * @see https://en.wikipedia.org/wiki/ISO_8601 + */ + public static final SimpleDateFormat DATE_TIME_FORMAT = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssXXX"); + + /** + * ISO 8601 date format. + * @see https://en.wikipedia.org/wiki/ISO_8601 + */ + public static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("yyyy-MM-dd"); + + static { + // Use UTC as the default time zone. + DATE_TIME_FORMAT.setTimeZone(TimeZone.getTimeZone("UTC")); + DATE_FORMAT.setTimeZone(TimeZone.getTimeZone("UTC")); + } + + public static Date parseDateTime(String str) { + try { + return DATE_TIME_FORMAT.parse(str); + } catch (java.text.ParseException e) { + throw new RuntimeException(e); + } + } + + public static Date parseDate(String str) { + try { + return DATE_FORMAT.parse(str); + } catch (java.text.ParseException e) { + throw new RuntimeException(e); + } + } + + public static String formatDateTime(Date datetime) { + return DATE_TIME_FORMAT.format(datetime); + } + + public static String formatDate(Date date) { + return DATE_FORMAT.format(date); + } + + public static String parameterToString(Object param) { + if (param == null) { + return ""; + } else if (param instanceof Date) { + return formatDateTime((Date) param); + } else { + return String.valueOf(param); + } + } + public void enableDebug() { isDebug = true; } diff --git a/samples/client/petstore/java/src/main/java/io/swagger/client/api/PetApi.java b/samples/client/petstore/java/src/main/java/io/swagger/client/api/PetApi.java index 53c1d55fb6..686deae12e 100644 --- a/samples/client/petstore/java/src/main/java/io/swagger/client/api/PetApi.java +++ b/samples/client/petstore/java/src/main/java/io/swagger/client/api/PetApi.java @@ -148,8 +148,8 @@ public class PetApi { Map headerParams = new HashMap(); Map formParams = new HashMap(); - if(!"null".equals(String.valueOf(status))) - queryParams.put("status", String.valueOf(status)); + if (status != null) + queryParams.put("status", ApiInvoker.parameterToString(status)); String[] contentTypes = { @@ -200,8 +200,8 @@ public class PetApi { Map headerParams = new HashMap(); Map formParams = new HashMap(); - if(!"null".equals(String.valueOf(tags))) - queryParams.put("tags", String.valueOf(tags)); + if (tags != null) + queryParams.put("tags", ApiInvoker.parameterToString(tags)); String[] contentTypes = { @@ -317,17 +317,17 @@ public class PetApi { FormDataMultiPart mp = new FormDataMultiPart(); hasFields = true; - mp.field("name", name, MediaType.MULTIPART_FORM_DATA_TYPE); + mp.field("name", ApiInvoker.parameterToString(name), MediaType.MULTIPART_FORM_DATA_TYPE); hasFields = true; - mp.field("status", status, MediaType.MULTIPART_FORM_DATA_TYPE); + mp.field("status", ApiInvoker.parameterToString(status), MediaType.MULTIPART_FORM_DATA_TYPE); if(hasFields) postBody = mp; } else { - formParams.put("name", name); - formParams.put("status", status); + formParams.put("name", ApiInvoker.parameterToString(name)); + formParams.put("status", ApiInvoker.parameterToString(status)); } @@ -364,7 +364,7 @@ public class PetApi { Map formParams = new HashMap(); - headerParams.put("api_key", api_key); + headerParams.put("api_key", ApiInvoker.parameterToString(api_key)); String[] contentTypes = { @@ -428,7 +428,7 @@ public class PetApi { FormDataMultiPart mp = new FormDataMultiPart(); hasFields = true; - mp.field("additionalMetadata", additionalMetadata, MediaType.MULTIPART_FORM_DATA_TYPE); + mp.field("additionalMetadata", ApiInvoker.parameterToString(additionalMetadata), MediaType.MULTIPART_FORM_DATA_TYPE); hasFields = true; mp.field("file", file, MediaType.MULTIPART_FORM_DATA_TYPE); @@ -437,7 +437,7 @@ public class PetApi { postBody = mp; } else { - formParams.put("additionalMetadata", additionalMetadata); + formParams.put("additionalMetadata", ApiInvoker.parameterToString(additionalMetadata)); } diff --git a/samples/client/petstore/java/src/main/java/io/swagger/client/api/UserApi.java b/samples/client/petstore/java/src/main/java/io/swagger/client/api/UserApi.java index 2da4c6ae32..7b8b2cad83 100644 --- a/samples/client/petstore/java/src/main/java/io/swagger/client/api/UserApi.java +++ b/samples/client/petstore/java/src/main/java/io/swagger/client/api/UserApi.java @@ -198,10 +198,10 @@ public class UserApi { Map headerParams = new HashMap(); Map formParams = new HashMap(); - if(!"null".equals(String.valueOf(username))) - queryParams.put("username", String.valueOf(username)); - if(!"null".equals(String.valueOf(password))) - queryParams.put("password", String.valueOf(password)); + if (username != null) + queryParams.put("username", ApiInvoker.parameterToString(username)); + if (password != null) + queryParams.put("password", ApiInvoker.parameterToString(password)); String[] contentTypes = { From 9cfbd8bde04ca24a4a96f6f33a26b2f531c91d29 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 18 Mar 2015 09:32:18 -0700 Subject: [PATCH 61/70] updated sample --- .../io/swagger/client/ApiInvoker.scala | 0 .../io/swagger/client/api/PetApi.scala | 0 .../io/swagger/client/api/StoreApi.scala | 0 .../io/swagger/client/api/UserApi.scala | 0 .../io/swagger/client/model/Category.scala | 0 .../io/swagger/client/model/Order.scala | 0 .../io/swagger/client/model/Pet.scala | 0 .../io/swagger/client/model/Tag.scala | 0 .../io/swagger/client/model/User.scala | 0 .../scala/src/test/scala/PetApiTest.scala | 13 +++---- .../scala/src/test/scala/StoreApiTest.scala | 36 ++++++++++--------- .../scala/src/test/scala/UserApiTest.scala | 5 +-- 12 files changed, 29 insertions(+), 25 deletions(-) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/ApiInvoker.scala (100%) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/api/PetApi.scala (100%) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/api/StoreApi.scala (100%) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/api/UserApi.scala (100%) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/model/Category.scala (100%) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/model/Order.scala (100%) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/model/Pet.scala (100%) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/model/Tag.scala (100%) rename samples/client/petstore/scala/src/main/{java => scala}/io/swagger/client/model/User.scala (100%) diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/ApiInvoker.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/ApiInvoker.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/ApiInvoker.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/ApiInvoker.scala diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/api/PetApi.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/api/PetApi.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/api/PetApi.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/api/PetApi.scala diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/api/StoreApi.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/api/StoreApi.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/api/StoreApi.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/api/StoreApi.scala diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/api/UserApi.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/api/UserApi.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/api/UserApi.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/api/UserApi.scala diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/model/Category.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/model/Category.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/model/Category.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/model/Category.scala diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/model/Order.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/model/Order.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/model/Order.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/model/Order.scala diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/model/Pet.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/model/Pet.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/model/Pet.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/model/Pet.scala diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/model/Tag.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/model/Tag.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/model/Tag.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/model/Tag.scala diff --git a/samples/client/petstore/scala/src/main/java/io/swagger/client/model/User.scala b/samples/client/petstore/scala/src/main/scala/io/swagger/client/model/User.scala similarity index 100% rename from samples/client/petstore/scala/src/main/java/io/swagger/client/model/User.scala rename to samples/client/petstore/scala/src/main/scala/io/swagger/client/model/User.scala diff --git a/samples/client/petstore/scala/src/test/scala/PetApiTest.scala b/samples/client/petstore/scala/src/test/scala/PetApiTest.scala index c06a207299..24ce4826fc 100644 --- a/samples/client/petstore/scala/src/test/scala/PetApiTest.scala +++ b/samples/client/petstore/scala/src/test/scala/PetApiTest.scala @@ -1,5 +1,6 @@ -import com.wordnik.petstore.api._ -import com.wordnik.petstore.model._ +import io.swagger.client._ +import io.swagger.client.api._ +import io.swagger.client.model._ import org.junit.runner.RunWith import org.scalatest.junit.JUnitRunner @@ -30,7 +31,7 @@ class PetApiTest extends FlatSpec with Matchers { Category(1, "sold"), "dragon", (for (i <- (1 to 10)) yield "http://foo.com/photo/" + i).toList, - (for (i <- (1 to 5)) yield com.wordnik.petstore.model.Tag(i, "tag-" + i)).toList, + (for (i <- (1 to 5)) yield io.swagger.client.model.Tag(i, "tag-" + i)).toList, "lost" ) @@ -55,7 +56,7 @@ class PetApiTest extends FlatSpec with Matchers { Category(1, "sold"), "programmer", (for (i <- (1 to 10)) yield "http://foo.com/photo/" + i).toList, - (for (i <- (1 to 5)) yield com.wordnik.petstore.model.Tag(i, "tag-" + i)).toList, + (for (i <- (1 to 5)) yield io.swagger.client.model.Tag(i, "tag-" + i)).toList, "confused" ) @@ -80,7 +81,7 @@ class PetApiTest extends FlatSpec with Matchers { } it should "find pets by status" in { - api.findPetsByStatus("available") match { + api.findPetsByStatus(List("available")) match { case Some(pets) => { pets.foreach(pet => pet.status should be("available")) } @@ -90,7 +91,7 @@ class PetApiTest extends FlatSpec with Matchers { it should "find pets by tag" in { println("finding by tags") - api.findPetsByTags("tag1,tag2") match { + api.findPetsByTags(List("tag1", "tag2")) match { case Some(pets) => { pets.foreach(pet => { val tags = (for (tag <- pet.tags) yield tag.name).toSet diff --git a/samples/client/petstore/scala/src/test/scala/StoreApiTest.scala b/samples/client/petstore/scala/src/test/scala/StoreApiTest.scala index 2d453ab225..053dffd055 100644 --- a/samples/client/petstore/scala/src/test/scala/StoreApiTest.scala +++ b/samples/client/petstore/scala/src/test/scala/StoreApiTest.scala @@ -1,6 +1,6 @@ -import com.wordnik.client._ -import com.wordnik.petstore.api._ -import com.wordnik.petstore.model._ +import io.swagger.client._ +import io.swagger.client.api._ +import io.swagger.client.model._ import org.junit.runner.RunWith import org.scalatest.junit.JUnitRunner @@ -30,13 +30,14 @@ class StoreApiTest extends FlatSpec with Matchers { } it should "place an order" in { - val now = new java.util.Date + val now = new org.joda.time.DateTime val order = Order ( - 10, - 1000, - 101, - "pending", - now) + petId = 10, + id = 1000, + quantity = 101, + status = "pending", + shipDate = now, + complete = true) api.placeOrder(order) @@ -45,20 +46,21 @@ class StoreApiTest extends FlatSpec with Matchers { order.id should be(1000) order.petId should be(10) order.quantity should be(101) - order.shipDate should be (now) + order.shipDate.equals(now) should be (true) } case None => } } it should "delete an order" in { - val now = new java.util.Date + val now = new org.joda.time.DateTime val order = Order( - 1001, - 10, - 101, - "pending", - now) + id = 1001, + petId = 10, + quantity = 101, + status = "pending", + shipDate = now, + complete = true) api.placeOrder(order) @@ -67,7 +69,7 @@ class StoreApiTest extends FlatSpec with Matchers { order.id should be(1001) order.petId should be(10) order.quantity should be(101) - order.shipDate should be (now) + order.shipDate.equals(now) should be (true) } case None => } diff --git a/samples/client/petstore/scala/src/test/scala/UserApiTest.scala b/samples/client/petstore/scala/src/test/scala/UserApiTest.scala index 73f90342ad..37b80815c8 100644 --- a/samples/client/petstore/scala/src/test/scala/UserApiTest.scala +++ b/samples/client/petstore/scala/src/test/scala/UserApiTest.scala @@ -1,5 +1,6 @@ -import com.wordnik.petstore.api._ -import com.wordnik.petstore.model._ +import io.swagger.client._ +import io.swagger.client.api._ +import io.swagger.client.model._ import org.junit.runner.RunWith import org.scalatest.junit.JUnitRunner From 86c6892eb67ac27591fef99096fb3a6c2d9e64c0 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 18 Mar 2015 09:32:45 -0700 Subject: [PATCH 62/70] rebuilt samples --- .../client/petstore/objc/client/SWGPetApi.m | 88 ------------------- .../client/petstore/objc/client/SWGStoreApi.m | 22 ----- .../client/petstore/objc/client/SWGUserApi.m | 44 ---------- .../client/petstore/php/models/Category.php | 23 ++++- samples/client/petstore/php/models/Order.php | 27 +++++- samples/client/petstore/php/models/Pet.php | 27 +++++- samples/client/petstore/php/models/Tag.php | 23 ++++- samples/client/petstore/php/models/User.php | 29 +++++- .../petstore/tizen/client/SamiCategory.cpp | 12 +-- .../petstore/tizen/client/SamiCategory.h | 8 +- .../petstore/tizen/client/SamiOrder.cpp | 36 ++++---- .../client/petstore/tizen/client/SamiOrder.h | 24 ++--- .../client/petstore/tizen/client/SamiPet.cpp | 36 ++++---- .../client/petstore/tizen/client/SamiPet.h | 24 ++--- .../client/petstore/tizen/client/SamiTag.cpp | 12 +-- .../client/petstore/tizen/client/SamiTag.h | 8 +- .../client/petstore/tizen/client/SamiUser.cpp | 48 +++++----- .../client/petstore/tizen/client/SamiUser.h | 32 +++---- 18 files changed, 244 insertions(+), 279 deletions(-) diff --git a/samples/client/petstore/objc/client/SWGPetApi.m b/samples/client/petstore/objc/client/SWGPetApi.m index bf968a2776..1305f552c8 100644 --- a/samples/client/petstore/objc/client/SWGPetApi.m +++ b/samples/client/petstore/objc/client/SWGPetApi.m @@ -110,28 +110,6 @@ static NSString * basePath = @"http://petstore.swagger.io/v2"; - // primitive response type - - - // no return base type - return [client stringWithCompletionBlock: requestUrl - method: @"PUT" - queryParams: queryParams - body: bodyDictionary - headerParams: headerParams - requestContentType: requestContentType - responseContentType: responseContentType - completionBlock: ^(NSString *data, NSError *error) { - if (error) { - completionBlock(error); - return; - } - completionBlock(nil); - }]; - - - - } -(NSNumber*) addPetWithCompletionBlock: (SWGPet*) body @@ -193,28 +171,6 @@ static NSString * basePath = @"http://petstore.swagger.io/v2"; - // primitive response type - - - // no return base type - return [client stringWithCompletionBlock: requestUrl - method: @"POST" - queryParams: queryParams - body: bodyDictionary - headerParams: headerParams - requestContentType: requestContentType - responseContentType: responseContentType - completionBlock: ^(NSString *data, NSError *error) { - if (error) { - completionBlock(error); - return; - } - completionBlock(nil); - }]; - - - - } -(NSNumber*) findPetsByStatusWithCompletionBlock: (NSArray*) status @@ -443,28 +399,6 @@ static NSString * basePath = @"http://petstore.swagger.io/v2"; - // primitive response type - - - // no return base type - return [client stringWithCompletionBlock: requestUrl - method: @"POST" - queryParams: queryParams - body: bodyDictionary - headerParams: headerParams - requestContentType: requestContentType - responseContentType: responseContentType - completionBlock: ^(NSString *data, NSError *error) { - if (error) { - completionBlock(error); - return; - } - completionBlock(nil); - }]; - - - - } -(NSNumber*) deletePetWithCompletionBlock: (NSString*) api_key @@ -509,28 +443,6 @@ static NSString * basePath = @"http://petstore.swagger.io/v2"; - // primitive response type - - - // no return base type - return [client stringWithCompletionBlock: requestUrl - method: @"DELETE" - queryParams: queryParams - body: bodyDictionary - headerParams: headerParams - requestContentType: requestContentType - responseContentType: responseContentType - completionBlock: ^(NSString *data, NSError *error) { - if (error) { - completionBlock(error); - return; - } - completionBlock(nil); - }]; - - - - } -(NSNumber*) uploadFileWithCompletionBlock: (NSNumber*) petId diff --git a/samples/client/petstore/objc/client/SWGStoreApi.m b/samples/client/petstore/objc/client/SWGStoreApi.m index b81d127eb5..b0c42e7d98 100644 --- a/samples/client/petstore/objc/client/SWGStoreApi.m +++ b/samples/client/petstore/objc/client/SWGStoreApi.m @@ -303,28 +303,6 @@ static NSString * basePath = @"http://petstore.swagger.io/v2"; - // primitive response type - - - // no return base type - return [client stringWithCompletionBlock: requestUrl - method: @"DELETE" - queryParams: queryParams - body: bodyDictionary - headerParams: headerParams - requestContentType: requestContentType - responseContentType: responseContentType - completionBlock: ^(NSString *data, NSError *error) { - if (error) { - completionBlock(error); - return; - } - completionBlock(nil); - }]; - - - - } diff --git a/samples/client/petstore/objc/client/SWGUserApi.m b/samples/client/petstore/objc/client/SWGUserApi.m index 4c69415620..fbaafa76fa 100644 --- a/samples/client/petstore/objc/client/SWGUserApi.m +++ b/samples/client/petstore/objc/client/SWGUserApi.m @@ -554,28 +554,6 @@ static NSString * basePath = @"http://petstore.swagger.io/v2"; - // primitive response type - - - // no return base type - return [client stringWithCompletionBlock: requestUrl - method: @"PUT" - queryParams: queryParams - body: bodyDictionary - headerParams: headerParams - requestContentType: requestContentType - responseContentType: responseContentType - completionBlock: ^(NSString *data, NSError *error) { - if (error) { - completionBlock(error); - return; - } - completionBlock(nil); - }]; - - - - } -(NSNumber*) deleteUserWithCompletionBlock: (NSString*) username @@ -617,28 +595,6 @@ static NSString * basePath = @"http://petstore.swagger.io/v2"; - // primitive response type - - - // no return base type - return [client stringWithCompletionBlock: requestUrl - method: @"DELETE" - queryParams: queryParams - body: bodyDictionary - headerParams: headerParams - requestContentType: requestContentType - responseContentType: responseContentType - completionBlock: ^(NSString *data, NSError *error) { - if (error) { - completionBlock(error); - return; - } - completionBlock(nil); - }]; - - - - } diff --git a/samples/client/petstore/php/models/Category.php b/samples/client/petstore/php/models/Category.php index 867cacf771..acd9004d88 100644 --- a/samples/client/petstore/php/models/Category.php +++ b/samples/client/petstore/php/models/Category.php @@ -22,7 +22,7 @@ * */ -class Category { +class Category implements ArrayAccess { static $swaggerTypes = array( 'id' => 'int', 'name' => 'string' @@ -31,4 +31,25 @@ class Category { public $id; /* int */ public $name; /* string */ + + public function __construct(array $data) { + $this->id = $data["id"]; + $this->name = $data["name"]; + } + + public function offsetExists($offset) { + return isset($this->$offset); + } + + public function offsetGet($offset) { + return $this->$offset; + } + + public function offsetSet($offset, $value) { + $this->$offset = $value; + } + + public function offsetUnset($offset) { + unset($this->$offset); + } } diff --git a/samples/client/petstore/php/models/Order.php b/samples/client/petstore/php/models/Order.php index d5e10a5940..c7abef02d6 100644 --- a/samples/client/petstore/php/models/Order.php +++ b/samples/client/petstore/php/models/Order.php @@ -22,7 +22,7 @@ * */ -class Order { +class Order implements ArrayAccess { static $swaggerTypes = array( 'id' => 'int', 'petId' => 'int', @@ -42,4 +42,29 @@ class Order { */ public $status; /* string */ public $complete; /* boolean */ + + public function __construct(array $data) { + $this->id = $data["id"]; + $this->petId = $data["petId"]; + $this->quantity = $data["quantity"]; + $this->shipDate = $data["shipDate"]; + $this->status = $data["status"]; + $this->complete = $data["complete"]; + } + + public function offsetExists($offset) { + return isset($this->$offset); + } + + public function offsetGet($offset) { + return $this->$offset; + } + + public function offsetSet($offset, $value) { + $this->$offset = $value; + } + + public function offsetUnset($offset) { + unset($this->$offset); + } } diff --git a/samples/client/petstore/php/models/Pet.php b/samples/client/petstore/php/models/Pet.php index d3231bdc8a..f8fa832cf8 100644 --- a/samples/client/petstore/php/models/Pet.php +++ b/samples/client/petstore/php/models/Pet.php @@ -22,7 +22,7 @@ * */ -class Pet { +class Pet implements ArrayAccess { static $swaggerTypes = array( 'id' => 'int', 'category' => 'Category', @@ -42,4 +42,29 @@ class Pet { * pet status in the store */ public $status; /* string */ + + public function __construct(array $data) { + $this->id = $data["id"]; + $this->category = $data["category"]; + $this->name = $data["name"]; + $this->photoUrls = $data["photoUrls"]; + $this->tags = $data["tags"]; + $this->status = $data["status"]; + } + + public function offsetExists($offset) { + return isset($this->$offset); + } + + public function offsetGet($offset) { + return $this->$offset; + } + + public function offsetSet($offset, $value) { + $this->$offset = $value; + } + + public function offsetUnset($offset) { + unset($this->$offset); + } } diff --git a/samples/client/petstore/php/models/Tag.php b/samples/client/petstore/php/models/Tag.php index 238d768e68..bb85524762 100644 --- a/samples/client/petstore/php/models/Tag.php +++ b/samples/client/petstore/php/models/Tag.php @@ -22,7 +22,7 @@ * */ -class Tag { +class Tag implements ArrayAccess { static $swaggerTypes = array( 'id' => 'int', 'name' => 'string' @@ -31,4 +31,25 @@ class Tag { public $id; /* int */ public $name; /* string */ + + public function __construct(array $data) { + $this->id = $data["id"]; + $this->name = $data["name"]; + } + + public function offsetExists($offset) { + return isset($this->$offset); + } + + public function offsetGet($offset) { + return $this->$offset; + } + + public function offsetSet($offset, $value) { + $this->$offset = $value; + } + + public function offsetUnset($offset) { + unset($this->$offset); + } } diff --git a/samples/client/petstore/php/models/User.php b/samples/client/petstore/php/models/User.php index 6178042052..7cdff02ad0 100644 --- a/samples/client/petstore/php/models/User.php +++ b/samples/client/petstore/php/models/User.php @@ -22,7 +22,7 @@ * */ -class User { +class User implements ArrayAccess { static $swaggerTypes = array( 'id' => 'int', 'username' => 'string', @@ -46,4 +46,31 @@ class User { * User Status */ public $userStatus; /* int */ + + public function __construct(array $data) { + $this->id = $data["id"]; + $this->username = $data["username"]; + $this->firstName = $data["firstName"]; + $this->lastName = $data["lastName"]; + $this->email = $data["email"]; + $this->password = $data["password"]; + $this->phone = $data["phone"]; + $this->userStatus = $data["userStatus"]; + } + + public function offsetExists($offset) { + return isset($this->$offset); + } + + public function offsetGet($offset) { + return $this->$offset; + } + + public function offsetSet($offset, $value) { + $this->$offset = $value; + } + + public function offsetUnset($offset) { + unset($this->$offset); + } } diff --git a/samples/client/petstore/tizen/client/SamiCategory.cpp b/samples/client/petstore/tizen/client/SamiCategory.cpp index 0e79da7beb..def45c6578 100644 --- a/samples/client/petstore/tizen/client/SamiCategory.cpp +++ b/samples/client/petstore/tizen/client/SamiCategory.cpp @@ -148,31 +148,31 @@ SamiCategory::asJsonObject() { JsonString *pIdKey = new JsonString(L"id"); - pJsonObject->Add(pIdKey, toJson(getId(), "Long", "")); + pJsonObject->Add(pIdKey, toJson(getpId(), "Long", "")); JsonString *pNameKey = new JsonString(L"name"); - pJsonObject->Add(pNameKey, toJson(getName(), "String", "")); + pJsonObject->Add(pNameKey, toJson(getpName(), "String", "")); return pJsonObject; } Long* -SamiCategory::getId() { +SamiCategory::getpId() { return pId; } void -SamiCategory::setId(Long* pId) { +SamiCategory::setpId(Long* pId) { this->pId = pId; } String* -SamiCategory::getName() { +SamiCategory::getpName() { return pName; } void -SamiCategory::setName(String* pName) { +SamiCategory::setpName(String* pName) { this->pName = pName; } diff --git a/samples/client/petstore/tizen/client/SamiCategory.h b/samples/client/petstore/tizen/client/SamiCategory.h index 6cb0565358..17fb537094 100644 --- a/samples/client/petstore/tizen/client/SamiCategory.h +++ b/samples/client/petstore/tizen/client/SamiCategory.h @@ -42,11 +42,11 @@ public: SamiCategory* fromJson(String* obj); - Long* getId(); - void setId(Long* pId); + Long* getpId(); + void setpId(Long* pId); - String* getName(); - void setName(String* pName); + String* getpName(); + void setpName(String* pName); private: diff --git a/samples/client/petstore/tizen/client/SamiOrder.cpp b/samples/client/petstore/tizen/client/SamiOrder.cpp index 35da0ca6de..b029b2aeef 100644 --- a/samples/client/petstore/tizen/client/SamiOrder.cpp +++ b/samples/client/petstore/tizen/client/SamiOrder.cpp @@ -208,83 +208,83 @@ SamiOrder::asJsonObject() { JsonString *pIdKey = new JsonString(L"id"); - pJsonObject->Add(pIdKey, toJson(getId(), "Long", "")); + pJsonObject->Add(pIdKey, toJson(getpId(), "Long", "")); JsonString *pPetIdKey = new JsonString(L"petId"); - pJsonObject->Add(pPetIdKey, toJson(getPetId(), "Long", "")); + pJsonObject->Add(pPetIdKey, toJson(getpPetId(), "Long", "")); JsonString *pQuantityKey = new JsonString(L"quantity"); - pJsonObject->Add(pQuantityKey, toJson(getQuantity(), "Integer", "")); + pJsonObject->Add(pQuantityKey, toJson(getpQuantity(), "Integer", "")); JsonString *pShipDateKey = new JsonString(L"shipDate"); - pJsonObject->Add(pShipDateKey, toJson(getShipDate(), "DateTime", "")); + pJsonObject->Add(pShipDateKey, toJson(getpShipDate(), "DateTime", "")); JsonString *pStatusKey = new JsonString(L"status"); - pJsonObject->Add(pStatusKey, toJson(getStatus(), "String", "")); + pJsonObject->Add(pStatusKey, toJson(getpStatus(), "String", "")); JsonString *pCompleteKey = new JsonString(L"complete"); - pJsonObject->Add(pCompleteKey, toJson(getComplete(), "Boolean", "")); + pJsonObject->Add(pCompleteKey, toJson(getpComplete(), "Boolean", "")); return pJsonObject; } Long* -SamiOrder::getId() { +SamiOrder::getpId() { return pId; } void -SamiOrder::setId(Long* pId) { +SamiOrder::setpId(Long* pId) { this->pId = pId; } Long* -SamiOrder::getPetId() { +SamiOrder::getpPetId() { return pPetId; } void -SamiOrder::setPetId(Long* pPetId) { +SamiOrder::setpPetId(Long* pPetId) { this->pPetId = pPetId; } Integer* -SamiOrder::getQuantity() { +SamiOrder::getpQuantity() { return pQuantity; } void -SamiOrder::setQuantity(Integer* pQuantity) { +SamiOrder::setpQuantity(Integer* pQuantity) { this->pQuantity = pQuantity; } DateTime* -SamiOrder::getShipDate() { +SamiOrder::getpShipDate() { return pShipDate; } void -SamiOrder::setShipDate(DateTime* pShipDate) { +SamiOrder::setpShipDate(DateTime* pShipDate) { this->pShipDate = pShipDate; } String* -SamiOrder::getStatus() { +SamiOrder::getpStatus() { return pStatus; } void -SamiOrder::setStatus(String* pStatus) { +SamiOrder::setpStatus(String* pStatus) { this->pStatus = pStatus; } Boolean* -SamiOrder::getComplete() { +SamiOrder::getpComplete() { return pComplete; } void -SamiOrder::setComplete(Boolean* pComplete) { +SamiOrder::setpComplete(Boolean* pComplete) { this->pComplete = pComplete; } diff --git a/samples/client/petstore/tizen/client/SamiOrder.h b/samples/client/petstore/tizen/client/SamiOrder.h index 88dcda6739..bc1cf4af22 100644 --- a/samples/client/petstore/tizen/client/SamiOrder.h +++ b/samples/client/petstore/tizen/client/SamiOrder.h @@ -45,23 +45,23 @@ public: SamiOrder* fromJson(String* obj); - Long* getId(); - void setId(Long* pId); + Long* getpId(); + void setpId(Long* pId); - Long* getPetId(); - void setPetId(Long* pPetId); + Long* getpPetId(); + void setpPetId(Long* pPetId); - Integer* getQuantity(); - void setQuantity(Integer* pQuantity); + Integer* getpQuantity(); + void setpQuantity(Integer* pQuantity); - DateTime* getShipDate(); - void setShipDate(DateTime* pShipDate); + DateTime* getpShipDate(); + void setpShipDate(DateTime* pShipDate); - String* getStatus(); - void setStatus(String* pStatus); + String* getpStatus(); + void setpStatus(String* pStatus); - Boolean* getComplete(); - void setComplete(Boolean* pComplete); + Boolean* getpComplete(); + void setpComplete(Boolean* pComplete); private: diff --git a/samples/client/petstore/tizen/client/SamiPet.cpp b/samples/client/petstore/tizen/client/SamiPet.cpp index c45c850e35..6c5d101db4 100644 --- a/samples/client/petstore/tizen/client/SamiPet.cpp +++ b/samples/client/petstore/tizen/client/SamiPet.cpp @@ -208,83 +208,83 @@ SamiPet::asJsonObject() { JsonString *pIdKey = new JsonString(L"id"); - pJsonObject->Add(pIdKey, toJson(getId(), "Long", "")); + pJsonObject->Add(pIdKey, toJson(getpId(), "Long", "")); JsonString *pCategoryKey = new JsonString(L"category"); - pJsonObject->Add(pCategoryKey, toJson(getCategory(), "SamiCategory", "")); + pJsonObject->Add(pCategoryKey, toJson(getpCategory(), "SamiCategory", "")); JsonString *pNameKey = new JsonString(L"name"); - pJsonObject->Add(pNameKey, toJson(getName(), "String", "")); + pJsonObject->Add(pNameKey, toJson(getpName(), "String", "")); JsonString *pPhotoUrlsKey = new JsonString(L"photoUrls"); - pJsonObject->Add(pPhotoUrlsKey, toJson(getPhotoUrls(), "String", "array")); + pJsonObject->Add(pPhotoUrlsKey, toJson(getpPhotoUrls(), "String", "array")); JsonString *pTagsKey = new JsonString(L"tags"); - pJsonObject->Add(pTagsKey, toJson(getTags(), "SamiTag", "array")); + pJsonObject->Add(pTagsKey, toJson(getpTags(), "SamiTag", "array")); JsonString *pStatusKey = new JsonString(L"status"); - pJsonObject->Add(pStatusKey, toJson(getStatus(), "String", "")); + pJsonObject->Add(pStatusKey, toJson(getpStatus(), "String", "")); return pJsonObject; } Long* -SamiPet::getId() { +SamiPet::getpId() { return pId; } void -SamiPet::setId(Long* pId) { +SamiPet::setpId(Long* pId) { this->pId = pId; } SamiCategory* -SamiPet::getCategory() { +SamiPet::getpCategory() { return pCategory; } void -SamiPet::setCategory(SamiCategory* pCategory) { +SamiPet::setpCategory(SamiCategory* pCategory) { this->pCategory = pCategory; } String* -SamiPet::getName() { +SamiPet::getpName() { return pName; } void -SamiPet::setName(String* pName) { +SamiPet::setpName(String* pName) { this->pName = pName; } IList* -SamiPet::getPhotoUrls() { +SamiPet::getpPhotoUrls() { return pPhotoUrls; } void -SamiPet::setPhotoUrls(IList* pPhotoUrls) { +SamiPet::setpPhotoUrls(IList* pPhotoUrls) { this->pPhotoUrls = pPhotoUrls; } IList* -SamiPet::getTags() { +SamiPet::getpTags() { return pTags; } void -SamiPet::setTags(IList* pTags) { +SamiPet::setpTags(IList* pTags) { this->pTags = pTags; } String* -SamiPet::getStatus() { +SamiPet::getpStatus() { return pStatus; } void -SamiPet::setStatus(String* pStatus) { +SamiPet::setpStatus(String* pStatus) { this->pStatus = pStatus; } diff --git a/samples/client/petstore/tizen/client/SamiPet.h b/samples/client/petstore/tizen/client/SamiPet.h index 9e3ab43bdc..30ae887294 100644 --- a/samples/client/petstore/tizen/client/SamiPet.h +++ b/samples/client/petstore/tizen/client/SamiPet.h @@ -45,23 +45,23 @@ public: SamiPet* fromJson(String* obj); - Long* getId(); - void setId(Long* pId); + Long* getpId(); + void setpId(Long* pId); - SamiCategory* getCategory(); - void setCategory(SamiCategory* pCategory); + SamiCategory* getpCategory(); + void setpCategory(SamiCategory* pCategory); - String* getName(); - void setName(String* pName); + String* getpName(); + void setpName(String* pName); - IList* getPhotoUrls(); - void setPhotoUrls(IList* pPhotoUrls); + IList* getpPhotoUrls(); + void setpPhotoUrls(IList* pPhotoUrls); - IList* getTags(); - void setTags(IList* pTags); + IList* getpTags(); + void setpTags(IList* pTags); - String* getStatus(); - void setStatus(String* pStatus); + String* getpStatus(); + void setpStatus(String* pStatus); private: diff --git a/samples/client/petstore/tizen/client/SamiTag.cpp b/samples/client/petstore/tizen/client/SamiTag.cpp index 61cc00f35f..3e6b947c60 100644 --- a/samples/client/petstore/tizen/client/SamiTag.cpp +++ b/samples/client/petstore/tizen/client/SamiTag.cpp @@ -148,31 +148,31 @@ SamiTag::asJsonObject() { JsonString *pIdKey = new JsonString(L"id"); - pJsonObject->Add(pIdKey, toJson(getId(), "Long", "")); + pJsonObject->Add(pIdKey, toJson(getpId(), "Long", "")); JsonString *pNameKey = new JsonString(L"name"); - pJsonObject->Add(pNameKey, toJson(getName(), "String", "")); + pJsonObject->Add(pNameKey, toJson(getpName(), "String", "")); return pJsonObject; } Long* -SamiTag::getId() { +SamiTag::getpId() { return pId; } void -SamiTag::setId(Long* pId) { +SamiTag::setpId(Long* pId) { this->pId = pId; } String* -SamiTag::getName() { +SamiTag::getpName() { return pName; } void -SamiTag::setName(String* pName) { +SamiTag::setpName(String* pName) { this->pName = pName; } diff --git a/samples/client/petstore/tizen/client/SamiTag.h b/samples/client/petstore/tizen/client/SamiTag.h index 53a4134a51..af77f48ec4 100644 --- a/samples/client/petstore/tizen/client/SamiTag.h +++ b/samples/client/petstore/tizen/client/SamiTag.h @@ -42,11 +42,11 @@ public: SamiTag* fromJson(String* obj); - Long* getId(); - void setId(Long* pId); + Long* getpId(); + void setpId(Long* pId); - String* getName(); - void setName(String* pName); + String* getpName(); + void setpName(String* pName); private: diff --git a/samples/client/petstore/tizen/client/SamiUser.cpp b/samples/client/petstore/tizen/client/SamiUser.cpp index 9701a45f28..48c615e008 100644 --- a/samples/client/petstore/tizen/client/SamiUser.cpp +++ b/samples/client/petstore/tizen/client/SamiUser.cpp @@ -238,109 +238,109 @@ SamiUser::asJsonObject() { JsonString *pIdKey = new JsonString(L"id"); - pJsonObject->Add(pIdKey, toJson(getId(), "Long", "")); + pJsonObject->Add(pIdKey, toJson(getpId(), "Long", "")); JsonString *pUsernameKey = new JsonString(L"username"); - pJsonObject->Add(pUsernameKey, toJson(getUsername(), "String", "")); + pJsonObject->Add(pUsernameKey, toJson(getpUsername(), "String", "")); JsonString *pFirstNameKey = new JsonString(L"firstName"); - pJsonObject->Add(pFirstNameKey, toJson(getFirstName(), "String", "")); + pJsonObject->Add(pFirstNameKey, toJson(getpFirstName(), "String", "")); JsonString *pLastNameKey = new JsonString(L"lastName"); - pJsonObject->Add(pLastNameKey, toJson(getLastName(), "String", "")); + pJsonObject->Add(pLastNameKey, toJson(getpLastName(), "String", "")); JsonString *pEmailKey = new JsonString(L"email"); - pJsonObject->Add(pEmailKey, toJson(getEmail(), "String", "")); + pJsonObject->Add(pEmailKey, toJson(getpEmail(), "String", "")); JsonString *pPasswordKey = new JsonString(L"password"); - pJsonObject->Add(pPasswordKey, toJson(getPassword(), "String", "")); + pJsonObject->Add(pPasswordKey, toJson(getpPassword(), "String", "")); JsonString *pPhoneKey = new JsonString(L"phone"); - pJsonObject->Add(pPhoneKey, toJson(getPhone(), "String", "")); + pJsonObject->Add(pPhoneKey, toJson(getpPhone(), "String", "")); JsonString *pUserStatusKey = new JsonString(L"userStatus"); - pJsonObject->Add(pUserStatusKey, toJson(getUserStatus(), "Integer", "")); + pJsonObject->Add(pUserStatusKey, toJson(getpUserStatus(), "Integer", "")); return pJsonObject; } Long* -SamiUser::getId() { +SamiUser::getpId() { return pId; } void -SamiUser::setId(Long* pId) { +SamiUser::setpId(Long* pId) { this->pId = pId; } String* -SamiUser::getUsername() { +SamiUser::getpUsername() { return pUsername; } void -SamiUser::setUsername(String* pUsername) { +SamiUser::setpUsername(String* pUsername) { this->pUsername = pUsername; } String* -SamiUser::getFirstName() { +SamiUser::getpFirstName() { return pFirstName; } void -SamiUser::setFirstName(String* pFirstName) { +SamiUser::setpFirstName(String* pFirstName) { this->pFirstName = pFirstName; } String* -SamiUser::getLastName() { +SamiUser::getpLastName() { return pLastName; } void -SamiUser::setLastName(String* pLastName) { +SamiUser::setpLastName(String* pLastName) { this->pLastName = pLastName; } String* -SamiUser::getEmail() { +SamiUser::getpEmail() { return pEmail; } void -SamiUser::setEmail(String* pEmail) { +SamiUser::setpEmail(String* pEmail) { this->pEmail = pEmail; } String* -SamiUser::getPassword() { +SamiUser::getpPassword() { return pPassword; } void -SamiUser::setPassword(String* pPassword) { +SamiUser::setpPassword(String* pPassword) { this->pPassword = pPassword; } String* -SamiUser::getPhone() { +SamiUser::getpPhone() { return pPhone; } void -SamiUser::setPhone(String* pPhone) { +SamiUser::setpPhone(String* pPhone) { this->pPhone = pPhone; } Integer* -SamiUser::getUserStatus() { +SamiUser::getpUserStatus() { return pUserStatus; } void -SamiUser::setUserStatus(Integer* pUserStatus) { +SamiUser::setpUserStatus(Integer* pUserStatus) { this->pUserStatus = pUserStatus; } diff --git a/samples/client/petstore/tizen/client/SamiUser.h b/samples/client/petstore/tizen/client/SamiUser.h index dd24429dba..24cc7b5563 100644 --- a/samples/client/petstore/tizen/client/SamiUser.h +++ b/samples/client/petstore/tizen/client/SamiUser.h @@ -43,29 +43,29 @@ public: SamiUser* fromJson(String* obj); - Long* getId(); - void setId(Long* pId); + Long* getpId(); + void setpId(Long* pId); - String* getUsername(); - void setUsername(String* pUsername); + String* getpUsername(); + void setpUsername(String* pUsername); - String* getFirstName(); - void setFirstName(String* pFirstName); + String* getpFirstName(); + void setpFirstName(String* pFirstName); - String* getLastName(); - void setLastName(String* pLastName); + String* getpLastName(); + void setpLastName(String* pLastName); - String* getEmail(); - void setEmail(String* pEmail); + String* getpEmail(); + void setpEmail(String* pEmail); - String* getPassword(); - void setPassword(String* pPassword); + String* getpPassword(); + void setpPassword(String* pPassword); - String* getPhone(); - void setPhone(String* pPhone); + String* getpPhone(); + void setpPhone(String* pPhone); - Integer* getUserStatus(); - void setUserStatus(Integer* pUserStatus); + Integer* getpUserStatus(); + void setpUserStatus(Integer* pUserStatus); private: From 64fbcb6045559f1ba09c5b22926b967040914f95 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 18 Mar 2015 09:34:19 -0700 Subject: [PATCH 63/70] rebuilt client --- samples/server/petstore/jaxrs/pom.xml | 11 ++++++++++- .../src/main/java/io/swagger/api/PetApi.java | 9 ++++++++- .../src/main/java/io/swagger/api/StoreApi.java | 7 ++++++- .../src/main/java/io/swagger/api/UserApi.java | 16 ++++++++++++---- 4 files changed, 36 insertions(+), 7 deletions(-) diff --git a/samples/server/petstore/jaxrs/pom.xml b/samples/server/petstore/jaxrs/pom.xml index fa94509ad5..0a7f0f935c 100644 --- a/samples/server/petstore/jaxrs/pom.xml +++ b/samples/server/petstore/jaxrs/pom.xml @@ -123,8 +123,17 @@ ${servlet-api-version} + + + sonatype-snapshots + https://oss.sonatype.org/content/repositories/snapshots + + true + + + - 1.5.1-M1 + 1.5.3-M1-SNAPSHOT 8.1.11.v20130520 1.13 1.6.3 diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java index bdf4ecec3d..d3a57a3ad0 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/PetApi.java @@ -64,6 +64,8 @@ public class PetApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Finds Pets by status", notes = "Multiple status values can be provided with comma seperated strings", response = Pet.class, responseContainer = "List") @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 200, message = "successful operation"), + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid status value") }) public Response findPetsByStatus(@ApiParam(value = "Status values that need to be considered for filter") @QueryParam("status") List status) @@ -79,6 +81,8 @@ public class PetApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Finds Pets by tags", notes = "Muliple tags can be provided with comma seperated strings. Use tag1, tag2, tag3 for testing.", response = Pet.class, responseContainer = "List") @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 200, message = "successful operation"), + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid tag value") }) public Response findPetsByTags(@ApiParam(value = "Tags to filter by") @QueryParam("tags") List tags) @@ -96,6 +100,8 @@ public class PetApi { @com.wordnik.swagger.annotations.ApiResponses(value = { @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "Pet not found"), + @com.wordnik.swagger.annotations.ApiResponse(code = 200, message = "successful operation"), + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid ID supplied") }) public Response getPetById(@ApiParam(value = "ID of pet that needs to be fetched",required=true ) @PathParam("petId") Long petId) @@ -143,7 +149,8 @@ public class PetApi { @Consumes({ "multipart/form-data" }) @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "uploads an image", notes = "", response = Void.class) - @com.wordnik.swagger.annotations.ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 0, message = "successful operation") }) public Response uploadFile(@ApiParam(value = "ID of pet to update",required=true ) @PathParam("petId") Long petId, @ApiParam(value = "Additional data to pass to server" )@FormParam("additionalMetadata") String additionalMetadata, diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java index a61879188c..d2bde7cf35 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/StoreApi.java @@ -29,7 +29,8 @@ public class StoreApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Returns pet inventories by status", notes = "Returns a map of status codes to quantities", response = Integer.class, responseContainer = "map") - @com.wordnik.swagger.annotations.ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 200, message = "successful operation") }) public Response getInventory() throws NotFoundException { @@ -44,6 +45,8 @@ public class StoreApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Place an order for a pet", notes = "", response = Order.class) @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 200, message = "successful operation"), + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid Order") }) public Response placeOrder(@ApiParam(value = "order placed for purchasing the pet" ) Order body) @@ -61,6 +64,8 @@ public class StoreApi { @com.wordnik.swagger.annotations.ApiResponses(value = { @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "Order not found"), + @com.wordnik.swagger.annotations.ApiResponse(code = 200, message = "successful operation"), + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid ID supplied") }) public Response getOrderById(@ApiParam(value = "ID of pet that needs to be fetched",required=true ) @PathParam("orderId") String orderId) diff --git a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java index 2bccc374bf..3f6da2c5d9 100644 --- a/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java +++ b/samples/server/petstore/jaxrs/src/main/java/io/swagger/api/UserApi.java @@ -29,7 +29,8 @@ public class UserApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Create user", notes = "This can only be done by the logged in user.", response = Void.class) - @com.wordnik.swagger.annotations.ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 0, message = "successful operation") }) public Response createUser(@ApiParam(value = "Created user object" ) User body) throws NotFoundException { @@ -43,7 +44,8 @@ public class UserApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Creates list of users with given input array", notes = "", response = Void.class) - @com.wordnik.swagger.annotations.ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 0, message = "successful operation") }) public Response createUsersWithArrayInput(@ApiParam(value = "List of user object" ) List body) throws NotFoundException { @@ -57,7 +59,8 @@ public class UserApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Creates list of users with given input array", notes = "", response = Void.class) - @com.wordnik.swagger.annotations.ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 0, message = "successful operation") }) public Response createUsersWithListInput(@ApiParam(value = "List of user object" ) List body) throws NotFoundException { @@ -72,6 +75,8 @@ public class UserApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Logs user into the system", notes = "", response = String.class) @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 200, message = "successful operation"), + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid username/password supplied") }) public Response loginUser(@ApiParam(value = "The user name for login") @QueryParam("username") String username, @@ -87,7 +92,8 @@ public class UserApi { @Produces({ "application/json", "application/xml" }) @com.wordnik.swagger.annotations.ApiOperation(value = "Logs out current logged in user session", notes = "", response = Void.class) - @com.wordnik.swagger.annotations.ApiResponses(value = { }) + @com.wordnik.swagger.annotations.ApiResponses(value = { + @com.wordnik.swagger.annotations.ApiResponse(code = 0, message = "successful operation") }) public Response logoutUser() throws NotFoundException { @@ -104,6 +110,8 @@ public class UserApi { @com.wordnik.swagger.annotations.ApiResponses(value = { @com.wordnik.swagger.annotations.ApiResponse(code = 404, message = "User not found"), + @com.wordnik.swagger.annotations.ApiResponse(code = 200, message = "successful operation"), + @com.wordnik.swagger.annotations.ApiResponse(code = 400, message = "Invalid username supplied") }) public Response getUserByName(@ApiParam(value = "The name that needs to be fetched. Use user1 for testing. ",required=true ) @PathParam("username") String username) From dd78de1ed8a2db8e68bf75f8012ca4df93e45c8b Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 18 Mar 2015 09:34:38 -0700 Subject: [PATCH 64/70] updated basePath, contextPath --- .../wordnik/swagger/codegen/DefaultGenerator.java | 13 +++++++++++-- .../codegen/languages/ScalaClientCodegen.java | 2 +- .../src/main/resources/scala/apiInvoker.mustache | 2 ++ 3 files changed, 14 insertions(+), 3 deletions(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java index a9be9f7889..bc09cc261e 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultGenerator.java @@ -126,7 +126,14 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { operation.putAll(config.additionalProperties()); operation.put("classname", config.toApiName(tag)); operation.put("classVarName", config.toApiVarName(tag)); + allOperations.add(new HashMap(operation)); + for(int i = 0; i < allOperations.size(); i++) { + Map oo = (Map) allOperations.get(i); + if(i < (allOperations.size() -1)) + oo.put("hasMore", "true"); + } + for(String templateName : config.apiTemplateFiles().keySet()) { String suffix = config.apiTemplateFiles().get(templateName); String filename = config.apiFileFolder() + @@ -160,9 +167,11 @@ public class DefaultGenerator extends AbstractGenerator implements Generator { Map apis = new HashMap(); apis.put("apis", allOperations); - if(swagger.getBasePath() != null) { - bundle.put("basePath", basePath); + if(swagger.getHost() != null) { + bundle.put("host", swagger.getHost()); } + bundle.put("basePath", basePath); + bundle.put("contextPath", contextPath); bundle.put("apiInfo", apis); bundle.put("models", allModels); bundle.put("apiFolder", config.apiPackage().replace('.', File.separatorChar)); diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/ScalaClientCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/ScalaClientCodegen.java index 85eeee98b9..ffef50b76e 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/ScalaClientCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/ScalaClientCodegen.java @@ -11,7 +11,7 @@ public class ScalaClientCodegen extends DefaultCodegen implements CodegenConfig protected String groupId = "com.wordnik"; protected String artifactId = "swagger-client"; protected String artifactVersion = "1.0.0"; - protected String sourceFolder = "src/main/java"; + protected String sourceFolder = "src/main/scala"; protected String authScheme = ""; protected boolean authPreemptive = false; protected boolean asyncHttpClient = !authScheme.isEmpty(); diff --git a/modules/swagger-codegen/src/main/resources/scala/apiInvoker.mustache b/modules/swagger-codegen/src/main/resources/scala/apiInvoker.mustache index 186be36401..c8bd041965 100644 --- a/modules/swagger-codegen/src/main/resources/scala/apiInvoker.mustache +++ b/modules/swagger-codegen/src/main/resources/scala/apiInvoker.mustache @@ -17,6 +17,7 @@ import scala.collection.JavaConverters._ import scala.collection.mutable.HashMap import com.fasterxml.jackson.module.scala.DefaultScalaModule +import com.fasterxml.jackson.datatype.joda.JodaModule import com.fasterxml.jackson.core.JsonGenerator.Feature import com.fasterxml.jackson.databind._ import com.fasterxml.jackson.annotation._ @@ -26,6 +27,7 @@ object ScalaJsonUtil { def getJsonMapper = { val mapper = new ObjectMapper() mapper.registerModule(new DefaultScalaModule()) + mapper.registerModule(new JodaModule()); mapper.setSerializationInclusion(JsonInclude.Include.NON_NULL); mapper.setSerializationInclusion(JsonInclude.Include.NON_DEFAULT) mapper.configure(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS, false) From ac78c15fbf4ba76610969db5698b48bc05741045 Mon Sep 17 00:00:00 2001 From: Camille Chafer Date: Wed, 18 Mar 2015 18:29:18 +0100 Subject: [PATCH 65/70] Add defined response headers in CodegenResponse. at this time, only the headers of the 'default' response are included in the operation. --- .../main/java/com/wordnik/swagger/codegen/CodegenResponse.java | 1 + .../main/java/com/wordnik/swagger/codegen/DefaultCodegen.java | 1 + 2 files changed, 2 insertions(+) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java index 82f0babc48..f90e38833b 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java @@ -6,6 +6,7 @@ public class CodegenResponse { public String code, message; public Boolean hasMore; public List> examples; + public List headers; public String dataType, baseType, containerType; public Boolean simpleType; public Boolean primitiveType; diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java index 0aae418b83..26fe8bdfac 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/DefaultCodegen.java @@ -765,6 +765,7 @@ public class DefaultCodegen { r.schema = response.getSchema(); r.examples = toExamples(response.getExamples()); r.jsonSchema = Json.pretty(response); + addHeaders(response, r.headers); if (r.schema != null) { Property responseProperty = response.getSchema(); From 081757c59252827d571ddabcdff272faf21511a4 Mon Sep 17 00:00:00 2001 From: Camille Chafer Date: Wed, 18 Mar 2015 19:01:45 +0100 Subject: [PATCH 66/70] headers list is CodegenResponse is always defined (no null list) --- .../main/java/com/wordnik/swagger/codegen/CodegenResponse.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java index f90e38833b..15931c9fd2 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/CodegenResponse.java @@ -6,7 +6,7 @@ public class CodegenResponse { public String code, message; public Boolean hasMore; public List> examples; - public List headers; + public final List headers = new ArrayList(); public String dataType, baseType, containerType; public Boolean simpleType; public Boolean primitiveType; From b6e5c558174ccdcba8c8ab3ddc9162b0411fa7d2 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 18 Mar 2015 16:10:54 -0700 Subject: [PATCH 67/70] updated nodejs server to swagger-tools, supports 2.0 spec --- .../languages/NodeJSServerCodegen.java | 196 +++--- .../src/main/resources/nodejs/README.mustache | 18 +- .../src/main/resources/nodejs/api.mustache | 62 -- .../main/resources/nodejs/controller.mustache | 17 + .../src/main/resources/nodejs/index.mustache | 38 ++ .../src/main/resources/nodejs/main.mustache | 53 -- .../src/main/resources/nodejs/models.mustache | 3 - .../main/resources/nodejs/package.mustache | 25 +- .../main/resources/nodejs/swagger.mustache | 42 ++ samples/server/petstore/nodejs/README.md | 8 - .../server/petstore/nodejs/api/swagger.json | 559 ++++++++++++++++++ .../server/petstore/nodejs/app/apis/PetApi.js | 203 ------- .../petstore/nodejs/app/apis/StoreApi.js | 108 ---- .../petstore/nodejs/app/apis/UserApi.js | 195 ------ samples/server/petstore/nodejs/app/models.js | 132 ----- .../server/petstore/nodejs/controllers/Pet.js | 81 +++ .../petstore/nodejs/controllers/Store.js | 39 ++ .../petstore/nodejs/controllers/User.js | 77 +++ samples/server/petstore/nodejs/index.js | 38 ++ samples/server/petstore/nodejs/main.js | 65 -- samples/server/petstore/nodejs/package.json | 25 +- 21 files changed, 1060 insertions(+), 924 deletions(-) delete mode 100644 modules/swagger-codegen/src/main/resources/nodejs/api.mustache create mode 100644 modules/swagger-codegen/src/main/resources/nodejs/controller.mustache create mode 100644 modules/swagger-codegen/src/main/resources/nodejs/index.mustache delete mode 100644 modules/swagger-codegen/src/main/resources/nodejs/main.mustache delete mode 100644 modules/swagger-codegen/src/main/resources/nodejs/models.mustache mode change 100755 => 100644 modules/swagger-codegen/src/main/resources/nodejs/package.mustache create mode 100644 modules/swagger-codegen/src/main/resources/nodejs/swagger.mustache delete mode 100644 samples/server/petstore/nodejs/README.md create mode 100644 samples/server/petstore/nodejs/api/swagger.json delete mode 100644 samples/server/petstore/nodejs/app/apis/PetApi.js delete mode 100644 samples/server/petstore/nodejs/app/apis/StoreApi.js delete mode 100644 samples/server/petstore/nodejs/app/apis/UserApi.js delete mode 100644 samples/server/petstore/nodejs/app/models.js create mode 100644 samples/server/petstore/nodejs/controllers/Pet.js create mode 100644 samples/server/petstore/nodejs/controllers/Store.js create mode 100644 samples/server/petstore/nodejs/controllers/User.js create mode 100644 samples/server/petstore/nodejs/index.js delete mode 100644 samples/server/petstore/nodejs/main.js diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/NodeJSServerCodegen.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/NodeJSServerCodegen.java index 74632b622f..c173c853fe 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/NodeJSServerCodegen.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/NodeJSServerCodegen.java @@ -1,110 +1,170 @@ package com.wordnik.swagger.codegen.languages; import com.wordnik.swagger.codegen.*; -import com.wordnik.swagger.models.Model; -import com.wordnik.swagger.models.properties.*; import com.wordnik.swagger.util.Json; - -import com.fasterxml.jackson.databind.JsonNode; -import com.fasterxml.jackson.databind.node.*; +import com.wordnik.swagger.models.properties.*; import java.util.*; import java.io.File; public class NodeJSServerCodegen extends DefaultCodegen implements CodegenConfig { - protected String invokerPackage = "com.wordnik.client"; - protected String groupId = "com.wordnik"; - protected String artifactId = "swagger-client"; - protected String artifactVersion = "1.0.0"; + protected String apiVersion = "1.0.0"; + protected int serverPort = 8080; + protected String projectName = "swagger-server"; + public String apiPackage() { + return "controllers"; + } + + /** + * Configures the type of generator. + * + * @return the CodegenType for this generator + * @see com.wordnik.swagger.codegen.CodegenType + */ public CodegenType getTag() { return CodegenType.SERVER; } + /** + * Configures a friendly name for the generator. This will be used by the generator + * to select the library with the -l flag. + * + * @return the friendly name for the generator + */ public String getName() { return "nodejs"; } + /** + * Returns human-friendly help for the generator. Provide the consumer with help + * tips, parameters here + * + * @return A string value for the help message + */ public String getHelp() { - return "Generates a node.js server application compatible with the 1.2 swagger specification."; + return "Generates a nodejs server library."; } public NodeJSServerCodegen() { super(); + + // set the output folder here outputFolder = "generated-code/nodejs"; - apiTemplateFiles.put("api.mustache", ".js"); + + /** + * Models. You can write model files using the modelTemplateFiles map. + * if you want to create one template for file, you can do so here. + * for multiple files for model, just put another entry in the `modelTemplateFiles` with + * a different extension + */ + modelTemplateFiles.clear(); + + /** + * Api classes. You can write classes for each Api file with the apiTemplateFiles map. + * as with models, add multiple entries with different extensions for multiple files per + * class + */ + apiTemplateFiles.put( + "controller.mustache", // the template to use + ".js"); // the extension for each file to write + + /** + * Template Location. This is the location which templates will be read from. The generator + * will use the resource stream to attempt to read the templates. + */ templateDir = "nodejs"; - apiPackage = "app.apis"; - modelPackage = "app"; - additionalProperties.put("invokerPackage", invokerPackage); - additionalProperties.put("groupId", groupId); - additionalProperties.put("artifactId", artifactId); - additionalProperties.put("artifactVersion", artifactVersion); - - supportingFiles.add(new SupportingFile("package.mustache", "", "package.json")); - supportingFiles.add(new SupportingFile("models.mustache", modelPackage, "models.js")); - supportingFiles.add(new SupportingFile("main.mustache", "", "main.js")); - supportingFiles.add(new SupportingFile("README.mustache", "", "README.md")); - - languageSpecificPrimitives = new HashSet( + /** + * Reserved words. Override this with reserved words specific to your language + */ + reservedWords = new HashSet ( Arrays.asList( - "String", - "boolean", - "Boolean", - "Double", - "Integer", - "Long", - "Float") - ); - typeMapping.put("array", "array"); + "break", "case", "class", "catch", "const", "continue", "debugger", + "default", "delete", "do", "else", "export", "extends", "finally", + "for", "function", "if", "import", "in", "instanceof", "let", "new", + "return", "super", "switch", "this", "throw", "try", "typeof", "var", + "void", "while", "with", "yield") + ); + + /** + * Additional Properties. These values can be passed to the templates and + * are available in models, apis, and supporting files + */ + additionalProperties.put("apiVersion", apiVersion); + additionalProperties.put("serverPort", serverPort); + + /** + * Supporting Files. You can write single files for the generator with the + * entire object tree available. If the input file has a suffix of `.mustache + * it will be processed by the template engine. Otherwise, it will be copied + */ + // supportingFiles.add(new SupportingFile("controller.mustache", + // "controllers", + // "controller.js") + // ); + supportingFiles.add(new SupportingFile("swagger.mustache", + "api", + "swagger.json") + ); + supportingFiles.add(new SupportingFile("index.mustache", + "", + "index.js") + ); + supportingFiles.add(new SupportingFile("package.mustache", + "", + "package.json") + ); } + @Override + public String toApiName(String name) { + if(name.length() == 0) + return "DefaultController"; + return initialCaps(name); + } + + @Override + public String toApiFilename(String name) { + return toApiName(name); + } + /** + * Escapes a reserved word as defined in the `reservedWords` array. Handle escaping + * those terms here. This logic is only called if a variable matches the reseved words + * + * @return the escaped term + */ @Override public String escapeReservedWord(String name) { - return "_" + name; - } - - @Override - public Map postProcessSupportingFileData(Map objs) { - List> o = (List>)objs.get("models"); - - for(Map modelMap : o) { - try { - CodegenModel m = (CodegenModel) modelMap.get("model"); - ObjectNode on = (ObjectNode) Json.mapper().readTree(m.modelJson); - // inject the id field - on.put("id", m.name); - - // remove the definitions qualifier with this nasty hack - m.modelJson = Json.pretty(on).replaceAll("\"#/definitions/", "\""); - } - catch (Exception e) { - e.printStackTrace(); - // skip conversion - } - } - return objs; + return "_" + name; // add an underscore to the name } + /** + * Location to write api files. You can use the apiPackage() as defined when the class is + * instantiated + */ @Override public String apiFileFolder() { return outputFolder + File.separator + apiPackage().replace('.', File.separatorChar); } - public String modelFileFolder() { - return outputFolder + File.separator + modelPackage().replace('.', File.separatorChar); - } - @Override - public String getSwaggerType(Property p) { - String swaggerType = super.getSwaggerType(p); - String type = null; - if(typeMapping.containsKey(swaggerType)) { - return typeMapping.get(swaggerType); + public Map postProcessOperations(Map objs) { + Map objectMap = (Map)objs.get("operations"); + List operations = (List)objectMap.get("operation"); + for(CodegenOperation operation : operations) { + operation.httpMethod = operation.httpMethod.toLowerCase(); + List params = operation.allParams; + if(params != null && params.size() == 0) + operation.allParams = null; + List responses = operation.responses; + if(responses != null) { + for(CodegenResponse resp : responses) { + if("0".equals(resp.code)) + resp.code = "default"; + } + } } - else - type = swaggerType; - return toModelName(type); + return objs; } } \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/nodejs/README.mustache b/modules/swagger-codegen/src/main/resources/nodejs/README.mustache index ac6dc37d3d..a8da1d0a9e 100644 --- a/modules/swagger-codegen/src/main/resources/nodejs/README.mustache +++ b/modules/swagger-codegen/src/main/resources/nodejs/README.mustache @@ -5,4 +5,20 @@ This server was generated by the [swagger-codegen](https://github.com/swagger-ap This example uses the [expressjs](http://expressjs.com/) framework. To see how to make this your own, look here: -[README](https://github.com/wordnik/swagger-codegen/README.md) \ No newline at end of file +[README](https://github.com/wordnik/swagger-codegen/README.md) + +### Running the server +To run the server, follow these simple steps: + +``` +npm install +node . +``` + +To view the Swagger UI interface: + +``` +open http://localhost:8080/docs +``` + +This project leverages the mega-awesome [swagger-tools](https://github.com/apigee-127/swagger-tools) middleware which does most all the work. \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/nodejs/api.mustache b/modules/swagger-codegen/src/main/resources/nodejs/api.mustache deleted file mode 100644 index e2f94f7a55..0000000000 --- a/modules/swagger-codegen/src/main/resources/nodejs/api.mustache +++ /dev/null @@ -1,62 +0,0 @@ -var swagger = require("swagger-node-express"); -var url = require("url"); -var errors = swagger.errors; -var params = swagger.params; - -/* add model includes */ - -function writeResponse (response, data) { - response.header('Access-Control-Allow-Origin', "*"); - response.header("Access-Control-Allow-Methods", "GET, POST, DELETE, PUT"); - response.header("Access-Control-Allow-Headers", "Content-Type"); - response.header("Content-Type", "application/json; charset=utf-8"); - response.send(JSON.stringify(data)); -} - -exports.models = models = require("../models.js"); - -{{#operations}} -{{#operation}} -exports.{{nickname}} = { - 'spec': { - "description" : "the {{baseName}} API", - "path" : "{{path}}", - "notes" : "{{{notes}}}", - "summary" : "{{{summary}}}", - "method": "{{httpMethod}}", - "params" : [{{#queryParams}} - params.query("{{paramName}}", "{{description}}", "{{swaggerDataType}}", {{#required}}true{{/required}}{{^required}}false{{/required}}, {{#allowMultiple}}true{{/allowMultiple}}{{^allowMultiple}}false{{/allowMultiple}}, "{{{allowableValues}}}"{{#defaultValue}}, {{{defaultValue}}}{{/defaultValue}}){{#hasMore}},{{/hasMore}} - {{/queryParams}}].concat([{{#pathParams}} - params.path("{{paramName}}", "{{description}}"){{#hasMore}},{{/hasMore}} - {{/pathParams}}]).concat([{{#headerParams}} - params.header("{{paramName}}", "{{description}}"){{#hasMore}},{{/hasMore}} - {{/headerParams}}]).concat([{{#bodyParams}} - params.body("body", "{{swaggerDataType}}", "{{description}}", {{#required}}{{required}}{{/required}}{{^required}}false{{/required}}) - {{/bodyParams}}]), - {{#returnContainer}} - "type": "{{returnType}}", - "items": { - {{#returnTypeIsPrimitive}}"type": "{{returnContainer}}"{{/returnTypeIsPrimitive}} - {{^returnTypeIsPrimitive}}"$ref": "{{returnContainer}}"{{/returnTypeIsPrimitive}} - }, - // container - {{/returnContainer}} - {{^returnContainer}} - "type" : "{{returnType}}", - {{/returnContainer}} - "responseMessages" : [errors.invalid('id'), errors.notFound('{{returnType}}')], - "nickname" : "{{nickname}}" - }, - 'action': function (req,res) { - {{#requiredParamCount}} - {{#requiredParams}} - if (!req.params.{{baseName}}) { - throw errors.invalid('{{baseName}}'); - } - {{/requiredParams}} - {{/requiredParamCount}} - writeResponse(res, {message: "how about implementing {{nickname}} as a {{httpMethod}} method?"}); - } -}; -{{/operation}} -{{/operations}} \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/nodejs/controller.mustache b/modules/swagger-codegen/src/main/resources/nodejs/controller.mustache new file mode 100644 index 0000000000..1755f1817e --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/nodejs/controller.mustache @@ -0,0 +1,17 @@ +'use strict'; + +var url = require('url'); + +{{#operations}} +{{#operation}} + +module.exports.{{nickname}} = function {{nickname}} (req, res, next) { + {{#allParams}}var {{paramName}} = req.swagger.params['{{baseName}}'].value; + {{/allParams}} + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; +{{/operation}} +{{/operations}} \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/nodejs/index.mustache b/modules/swagger-codegen/src/main/resources/nodejs/index.mustache new file mode 100644 index 0000000000..0562c2f0c3 --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/nodejs/index.mustache @@ -0,0 +1,38 @@ +'use strict'; + +var app = require('connect')(); +var http = require('http'); +var swaggerTools = require('swagger-tools'); + +var serverPort = {{serverPort}}; + +// swaggerRouter configuration +var options = { + swaggerUi: '/swagger.json', + controllers: './controllers', + useStubs: process.env.NODE_ENV === 'development' ? true : false // Conditionally turn on stubs (mock mode) +}; + +// The Swagger document (require it, build it programmatically, fetch it from a URL, ...) +var swaggerDoc = require('./api/swagger.json'); + +// Initialize the Swagger middleware +swaggerTools.initializeMiddleware(swaggerDoc, function (middleware) { + // Interpret Swagger resources and attach metadata to request - must be first in swagger-tools middleware chain + app.use(middleware.swaggerMetadata()); + + // Validate Swagger requests + app.use(middleware.swaggerValidator()); + + // Route validated requests to appropriate controller + app.use(middleware.swaggerRouter(options)); + + // Serve the Swagger documents and Swagger UI + app.use(middleware.swaggerUi()); + + // Start the server + http.createServer(app).listen({{serverPort}}, function () { + console.log('Your server is listening on port %d (http://localhost:%d)', {{serverPort}}, {{serverPort}}); + console.log('Swagger-ui is available on http://localhost:%d/docs', {{serverPort}}); + }); +}); \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/nodejs/main.mustache b/modules/swagger-codegen/src/main/resources/nodejs/main.mustache deleted file mode 100644 index 7f4ef64598..0000000000 --- a/modules/swagger-codegen/src/main/resources/nodejs/main.mustache +++ /dev/null @@ -1,53 +0,0 @@ -var express = require("express") - , url = require("url") - , cors = require("cors") - , app = express() - , swagger = require("swagger-node-express") - , db = false - - -var corsOptions = { - credentials: true, - origin: function(origin,callback) { - if(origin===undefined) { - callback(null,false); - } else { - callback(null,true); - } - } -}; - -app.use(express.json()); -app.use(express.urlencoded()); -app.use(cors(corsOptions)); - -{{#basePath}} -var subpath = express(); - -app.use("{{{basePath}}}", subpath); - -swagger.setAppHandler(subpath); -{{/basePath}} -{{^basePath}} -swagger.setAppHandler(app); -{{/basePath}} - -swagger.configureSwaggerPaths("", "api-docs", "") - -var models = require("./app/models.js"); - -{{#apiInfo}} -{{#apis}} -var {{classname}} = require("./{{apiFolder}}/{{classname}}.js"); -{{/apis}} -{{/apiInfo}} - -swagger.addModels(models) - {{#apiInfo}}{{#apis}}{{#operations}}{{#operation}}.add{{httpMethod}}({{classname}}.{{nickname}}) - {{/operation}}{{/operations}}{{/apis}}{{/apiInfo}}; - -// configures the app -swagger.configure("http://localhost:8002{{basePath}}", "0.1"); - -// start the server -app.listen(8002); diff --git a/modules/swagger-codegen/src/main/resources/nodejs/models.mustache b/modules/swagger-codegen/src/main/resources/nodejs/models.mustache deleted file mode 100644 index 133fe7c151..0000000000 --- a/modules/swagger-codegen/src/main/resources/nodejs/models.mustache +++ /dev/null @@ -1,3 +0,0 @@ -exports.models = { - {{#models}}{{#model}}"{{classVarName}}": {{{modelJson}}}{{#hasMoreModels}},{{/hasMoreModels}}{{/model}}{{/models}} -} \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/nodejs/package.mustache b/modules/swagger-codegen/src/main/resources/nodejs/package.mustache old mode 100755 new mode 100644 index bfd94cb064..7add6e813f --- a/modules/swagger-codegen/src/main/resources/nodejs/package.mustache +++ b/modules/swagger-codegen/src/main/resources/nodejs/package.mustache @@ -1,16 +1,15 @@ { - "name": "{{{artifactId}}}", - "description": "Wordnik node.js server generator", - "version": "{{{artifactVersion}}}", - "homepage": "{{{homepage}}}", - "main": "./main.js", - "engines": { - "node": ">= 0.8.x" - }, + "name": "{{projectName}}", + "version": "{{appVersion}}", + "description": "{{appDescription}}", + "main": "index.js", + "keywords": [ + "swagger" + ], + "license": "MIT", + "private": true, "dependencies": { - "swagger-node-express": ">= 2.0.x", - "connect": ">= 1.8.x", - "cors": "2.1.1", - "express": "3.x" + "connect": "^3.2.0", + "swagger-tools": "0.8.*" } -} \ No newline at end of file +} diff --git a/modules/swagger-codegen/src/main/resources/nodejs/swagger.mustache b/modules/swagger-codegen/src/main/resources/nodejs/swagger.mustache new file mode 100644 index 0000000000..ef9c6857e3 --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/nodejs/swagger.mustache @@ -0,0 +1,42 @@ +{ + "swagger": "2.0", + "info": { + "title": "{{appName}}", + "description": "{{appDescription}}", + "version": "{{apiVersion}}" + }, +{{#apiInfo}} + "produces": ["application/json"], + "host": "{{host}}", + "basePath": "{{contextPath}}", + "paths": { +{{#apis}} +{{#operations}} + {{#operation}} + "{{{path}}}": { + "{{httpMethod}}": { + "x-swagger-router-controller": "{{classname}}", + "tags": ["{{baseName}}"], + "operationId": "{{operationId}}",{{#hasParams}} + "parameters": [ + {{#allParams}} + {{{jsonSchema}}}{{#hasMore}},{{/hasMore}} + {{/allParams}} + ],{{/hasParams}} + "responses": { + {{#responses}} + "{{code}}": {{{jsonSchema}}} + {{#hasMore}},{{/hasMore}} + {{/responses}} + } + } + } {{#hasMore}},{{/hasMore}} + {{/operation}} + {{#hasMore}},{{/hasMore}} +{{/operations}} +{{/apis}} +{{/apiInfo}} + }, "definitions": { + {{#models}}{{#model}}"{{classVarName}}": {{{modelJson}}}{{#hasMoreModels}},{{/hasMoreModels}}{{/model}}{{/models}} + } +} diff --git a/samples/server/petstore/nodejs/README.md b/samples/server/petstore/nodejs/README.md deleted file mode 100644 index ac6dc37d3d..0000000000 --- a/samples/server/petstore/nodejs/README.md +++ /dev/null @@ -1,8 +0,0 @@ -# Swagger generated server - -## Overview -This server was generated by the [swagger-codegen](https://github.com/swagger-api/swagger-codegen) project. By using the [swagger-spec](https://github.com/swagger-api/swagger-spec) from a remote server, you can easily generate a server stub. This is an example of building a node.js server. - -This example uses the [expressjs](http://expressjs.com/) framework. To see how to make this your own, look here: - -[README](https://github.com/wordnik/swagger-codegen/README.md) \ No newline at end of file diff --git a/samples/server/petstore/nodejs/api/swagger.json b/samples/server/petstore/nodejs/api/swagger.json new file mode 100644 index 0000000000..f0d408596e --- /dev/null +++ b/samples/server/petstore/nodejs/api/swagger.json @@ -0,0 +1,559 @@ +{ + "swagger": "2.0", + "info": { + "title": "Swagger Petstore", + "description": "This is a sample server Petstore server. You can find out more about Swagger at <a href="http://swagger.io">http://swagger.io</a> or on irc.freenode.net, #swagger. For this sample, you can use the api key "special-key" to test the authorization filters", + "version": "1.0.0" + }, + "produces": [ + "application/json" + ], + "host": "petstore.swagger.io", + "basePath": "/v2", + "paths": { + "/user": { + "post": { + "x-swagger-router-controller": "User", + "tags": [ + "User" + ], + "operationId": "createUser", + "parameters": [ + { + "in": "body", + "name": "body", + "description": "Created user object", + "required": false, + "schema": { + "$ref": "#/definitions/User" + } + } + ], + "responses": { + "default": { + "description": "successful operation" + } + } + } + }, + "/user/createWithArray": { + "post": { + "x-swagger-router-controller": "User", + "tags": [ + "User" + ], + "operationId": "createUsersWithArrayInput", + "parameters": [ + { + "in": "body", + "name": "body", + "description": "List of user object", + "required": false, + "schema": { + "type": "array", + "items": { + "$ref": "#/definitions/User" + } + } + } + ], + "responses": { + "default": { + "description": "successful operation" + } + } + } + }, + "/user/createWithList": { + "post": { + "x-swagger-router-controller": "User", + "tags": [ + "User" + ], + "operationId": "createUsersWithListInput", + "parameters": [ + { + "in": "body", + "name": "body", + "description": "List of user object", + "required": false, + "schema": { + "type": "array", + "items": { + "$ref": "#/definitions/User" + } + } + } + ], + "responses": { + "default": { + "description": "successful operation" + } + } + } + }, + "/user/login": { + "get": { + "x-swagger-router-controller": "User", + "tags": [ + "User" + ], + "operationId": "loginUser", + "parameters": [ + { + "name": "username", + "in": "query", + "description": "The user name for login", + "required": false, + "type": "string" + }, + { + "name": "password", + "in": "query", + "description": "The password for login in clear text", + "required": false, + "type": "string" + } + ], + "responses": { + "200": { + "description": "successful operation", + "schema": { + "type": "string" + } + }, + "400": { + "description": "Invalid username/password supplied" + } + } + } + }, + "/user/logout": { + "get": { + "x-swagger-router-controller": "User", + "tags": [ + "User" + ], + "operationId": "logoutUser", + "responses": { + "default": { + "description": "successful operation" + } + } + } + }, + "/user/{username}": { + "delete": { + "x-swagger-router-controller": "User", + "tags": [ + "User" + ], + "operationId": "deleteUser", + "parameters": [ + { + "name": "username", + "in": "path", + "description": "The name that needs to be deleted", + "required": true, + "type": "string" + } + ], + "responses": { + "404": { + "description": "User not found" + }, + "400": { + "description": "Invalid username supplied" + } + } + } + }, + "/pet": { + "post": { + "x-swagger-router-controller": "Pet", + "tags": [ + "Pet" + ], + "operationId": "addPet", + "parameters": [ + { + "in": "body", + "name": "body", + "description": "Pet object that needs to be added to the store", + "required": false, + "schema": { + "$ref": "#/definitions/Pet" + } + } + ], + "responses": { + "405": { + "description": "Invalid input" + } + } + } + }, + "/pet/findByStatus": { + "get": { + "x-swagger-router-controller": "Pet", + "tags": [ + "Pet" + ], + "operationId": "findPetsByStatus", + "parameters": [ + { + "name": "status", + "in": "query", + "description": "Status values that need to be considered for filter", + "required": false, + "type": "array", + "items": { + "type": "string" + }, + "collectionFormat": "multi", + "default": "available" + } + ], + "responses": { + "200": { + "description": "successful operation", + "schema": { + "type": "array", + "items": { + "$ref": "#/definitions/Pet" + } + } + }, + "400": { + "description": "Invalid status value" + } + } + } + }, + "/pet/findByTags": { + "get": { + "x-swagger-router-controller": "Pet", + "tags": [ + "Pet" + ], + "operationId": "findPetsByTags", + "parameters": [ + { + "name": "tags", + "in": "query", + "description": "Tags to filter by", + "required": false, + "type": "array", + "items": { + "type": "string" + }, + "collectionFormat": "multi" + } + ], + "responses": { + "200": { + "description": "successful operation", + "schema": { + "type": "array", + "items": { + "$ref": "#/definitions/Pet" + } + } + }, + "400": { + "description": "Invalid tag value" + } + } + } + }, + "/pet/{petId}": { + "delete": { + "x-swagger-router-controller": "Pet", + "tags": [ + "Pet" + ], + "operationId": "deletePet", + "parameters": [ + { + "name": "api_key", + "in": "header", + "description": "", + "required": false, + "type": "string" + }, + { + "name": "petId", + "in": "path", + "description": "Pet id to delete", + "required": true, + "type": "integer", + "format": "int64" + } + ], + "responses": { + "400": { + "description": "Invalid pet value" + } + } + } + }, + "/pet/{petId}/uploadImage": { + "post": { + "x-swagger-router-controller": "Pet", + "tags": [ + "Pet" + ], + "operationId": "uploadFile", + "parameters": [ + { + "name": "petId", + "in": "path", + "description": "ID of pet to update", + "required": true, + "type": "integer", + "format": "int64" + }, + { + "name": "additionalMetadata", + "in": "formData", + "description": "Additional data to pass to server", + "required": false, + "type": "string" + }, + { + "name": "file", + "in": "formData", + "description": "file to upload", + "required": false, + "type": "file" + } + ], + "responses": { + "default": { + "description": "successful operation" + } + } + } + }, + "/store/inventory": { + "get": { + "x-swagger-router-controller": "Store", + "tags": [ + "Store" + ], + "operationId": "getInventory", + "responses": { + "200": { + "description": "successful operation", + "schema": { + "type": "object", + "additionalProperties": { + "type": "integer", + "format": "int32" + } + } + } + } + } + }, + "/store/order": { + "post": { + "x-swagger-router-controller": "Store", + "tags": [ + "Store" + ], + "operationId": "placeOrder", + "parameters": [ + { + "in": "body", + "name": "body", + "description": "order placed for purchasing the pet", + "required": false, + "schema": { + "$ref": "#/definitions/Order" + } + } + ], + "responses": { + "200": { + "description": "successful operation", + "schema": { + "$ref": "#/definitions/Order" + } + }, + "400": { + "description": "Invalid Order" + } + } + } + }, + "/store/order/{orderId}": { + "delete": { + "x-swagger-router-controller": "Store", + "tags": [ + "Store" + ], + "operationId": "deleteOrder", + "parameters": [ + { + "name": "orderId", + "in": "path", + "description": "ID of the order that needs to be deleted", + "required": true, + "type": "string" + } + ], + "responses": { + "404": { + "description": "Order not found" + }, + "400": { + "description": "Invalid ID supplied" + } + } + } + } + }, + "definitions": { + "User": { + "properties": { + "id": { + "type": "integer", + "format": "int64" + }, + "username": { + "type": "string" + }, + "firstName": { + "type": "string" + }, + "lastName": { + "type": "string" + }, + "email": { + "type": "string" + }, + "password": { + "type": "string" + }, + "phone": { + "type": "string" + }, + "userStatus": { + "type": "integer", + "format": "int32", + "description": "User Status" + } + }, + "xml": { + "name": "User" + } + }, + "Category": { + "properties": { + "id": { + "type": "integer", + "format": "int64" + }, + "name": { + "type": "string" + } + }, + "xml": { + "name": "Category" + } + }, + "Pet": { + "required": [ + "name", + "photoUrls" + ], + "properties": { + "id": { + "type": "integer", + "format": "int64" + }, + "category": { + "$ref": "#/definitions/Category" + }, + "name": { + "type": "string", + "example": "doggie" + }, + "photoUrls": { + "type": "array", + "items": { + "type": "string" + } + }, + "tags": { + "type": "array", + "items": { + "$ref": "#/definitions/Tag" + } + }, + "status": { + "type": "string", + "description": "pet status in the store", + "enum": [ + "available", + "pending", + "sold" + ] + } + }, + "xml": { + "name": "Pet" + } + }, + "Tag": { + "properties": { + "id": { + "type": "integer", + "format": "int64" + }, + "name": { + "type": "string" + } + }, + "xml": { + "name": "Tag" + } + }, + "Order": { + "properties": { + "id": { + "type": "integer", + "format": "int64" + }, + "petId": { + "type": "integer", + "format": "int64" + }, + "quantity": { + "type": "integer", + "format": "int32" + }, + "shipDate": { + "type": "string", + "format": "date-time" + }, + "status": { + "type": "string", + "description": "Order Status", + "enum": [ + "placed", + "approved", + "delivered" + ] + }, + "complete": { + "type": "boolean" + } + }, + "xml": { + "name": "Order" + } + } + } +} \ No newline at end of file diff --git a/samples/server/petstore/nodejs/app/apis/PetApi.js b/samples/server/petstore/nodejs/app/apis/PetApi.js deleted file mode 100644 index 630b323595..0000000000 --- a/samples/server/petstore/nodejs/app/apis/PetApi.js +++ /dev/null @@ -1,203 +0,0 @@ -var swagger = require("swagger-node-express"); -var url = require("url"); -var errors = swagger.errors; -var params = swagger.params; - -/* add model includes */ - -function writeResponse (response, data) { - response.header('Access-Control-Allow-Origin', "*"); - response.header("Access-Control-Allow-Methods", "GET, POST, DELETE, PUT"); - response.header("Access-Control-Allow-Headers", "Content-Type"); - response.header("Content-Type", "application/json; charset=utf-8"); - response.send(JSON.stringify(data)); -} - -exports.models = models = require("../models.js"); - -exports.updatePet = { - 'spec': { - "description" : "Operations about pets", - "path" : "/pet", - "notes" : "", - "summary" : "Update an existing pet", - "method": "PUT", - "params" : [].concat([]).concat([]).concat([ - params.body("body", "", "Pet object that needs to be added to the store", false) - ]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "updatePet" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing updatePet as a PUT method?"}); - } -}; -exports.addPet = { - 'spec': { - "description" : "Operations about pets", - "path" : "/pet", - "notes" : "", - "summary" : "Add a new pet to the store", - "method": "POST", - "params" : [].concat([]).concat([]).concat([ - params.body("body", "", "Pet object that needs to be added to the store", false) - ]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "addPet" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing addPet as a POST method?"}); - } -}; -exports.findPetsByStatus = { - 'spec': { - "description" : "Operations about pets", - "path" : "/pet/findByStatus", - "notes" : "Multiple status values can be provided with comma seperated strings", - "summary" : "Finds Pets by status", - "method": "GET", - "params" : [ - params.query("status", "Status values that need to be considered for filter", "", false, false, "") - ].concat([]).concat([]).concat([]), - - "type": "array", - "items": { - - "$ref": "array" - }, - // container - - - "responseMessages" : [errors.invalid('id'), errors.notFound('array')], - "nickname" : "findPetsByStatus" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing findPetsByStatus as a GET method?"}); - } -}; -exports.findPetsByTags = { - 'spec': { - "description" : "Operations about pets", - "path" : "/pet/findByTags", - "notes" : "Muliple tags can be provided with comma seperated strings. Use tag1, tag2, tag3 for testing.", - "summary" : "Finds Pets by tags", - "method": "GET", - "params" : [ - params.query("tags", "Tags to filter by", "", false, false, "") - ].concat([]).concat([]).concat([]), - - "type": "array", - "items": { - - "$ref": "array" - }, - // container - - - "responseMessages" : [errors.invalid('id'), errors.notFound('array')], - "nickname" : "findPetsByTags" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing findPetsByTags as a GET method?"}); - } -}; -exports.getPetById = { - 'spec': { - "description" : "Operations about pets", - "path" : "/pet/{petId}", - "notes" : "Returns a pet when ID < 10. ID > 10 or nonintegers will simulate API error conditions", - "summary" : "Find pet by ID", - "method": "GET", - "params" : [].concat([ - params.path("petId", "ID of pet that needs to be fetched") - ]).concat([]).concat([]), - - - "type" : "Pet", - - "responseMessages" : [errors.invalid('id'), errors.notFound('Pet')], - "nickname" : "getPetById" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing getPetById as a GET method?"}); - } -}; -exports.updatePetWithForm = { - 'spec': { - "description" : "Operations about pets", - "path" : "/pet/{petId}", - "notes" : "", - "summary" : "Updates a pet in the store with form data", - "method": "POST", - "params" : [].concat([ - params.path("petId", "ID of pet that needs to be updated") - ]).concat([]).concat([]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "updatePetWithForm" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing updatePetWithForm as a POST method?"}); - } -}; -exports.deletePet = { - 'spec': { - "description" : "Operations about pets", - "path" : "/pet/{petId}", - "notes" : "", - "summary" : "Deletes a pet", - "method": "DELETE", - "params" : [].concat([ - params.path("petId", "Pet id to delete") - ]).concat([ - params.header("api_key", "") - ]).concat([]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "deletePet" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing deletePet as a DELETE method?"}); - } -}; -exports.uploadFile = { - 'spec': { - "description" : "Operations about pets", - "path" : "/pet/{petId}/uploadImage", - "notes" : "", - "summary" : "uploads an image", - "method": "POST", - "params" : [].concat([]).concat([]).concat([]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "uploadFile" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing uploadFile as a POST method?"}); - } -}; diff --git a/samples/server/petstore/nodejs/app/apis/StoreApi.js b/samples/server/petstore/nodejs/app/apis/StoreApi.js deleted file mode 100644 index bbe929bd49..0000000000 --- a/samples/server/petstore/nodejs/app/apis/StoreApi.js +++ /dev/null @@ -1,108 +0,0 @@ -var swagger = require("swagger-node-express"); -var url = require("url"); -var errors = swagger.errors; -var params = swagger.params; - -/* add model includes */ - -function writeResponse (response, data) { - response.header('Access-Control-Allow-Origin', "*"); - response.header("Access-Control-Allow-Methods", "GET, POST, DELETE, PUT"); - response.header("Access-Control-Allow-Headers", "Content-Type"); - response.header("Content-Type", "application/json; charset=utf-8"); - response.send(JSON.stringify(data)); -} - -exports.models = models = require("../models.js"); - -exports.getInventory = { - 'spec': { - "description" : "Operations about pets", - "path" : "/store/inventory", - "notes" : "Returns a map of status codes to quantities", - "summary" : "Returns pet inventories by status", - "method": "GET", - "params" : [].concat([]).concat([]).concat([]), - - "type": "Map", - "items": { - - "$ref": "map" - }, - // container - - - "responseMessages" : [errors.invalid('id'), errors.notFound('Map')], - "nickname" : "getInventory" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing getInventory as a GET method?"}); - } -}; -exports.placeOrder = { - 'spec': { - "description" : "Operations about pets", - "path" : "/store/order", - "notes" : "", - "summary" : "Place an order for a pet", - "method": "POST", - "params" : [].concat([]).concat([]).concat([ - params.body("body", "", "order placed for purchasing the pet", false) - ]), - - - "type" : "Order", - - "responseMessages" : [errors.invalid('id'), errors.notFound('Order')], - "nickname" : "placeOrder" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing placeOrder as a POST method?"}); - } -}; -exports.getOrderById = { - 'spec': { - "description" : "Operations about pets", - "path" : "/store/order/{orderId}", - "notes" : "For valid response try integer IDs with value <= 5 or > 10. Other values will generated exceptions", - "summary" : "Find purchase order by ID", - "method": "GET", - "params" : [].concat([ - params.path("orderId", "ID of pet that needs to be fetched") - ]).concat([]).concat([]), - - - "type" : "Order", - - "responseMessages" : [errors.invalid('id'), errors.notFound('Order')], - "nickname" : "getOrderById" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing getOrderById as a GET method?"}); - } -}; -exports.deleteOrder = { - 'spec': { - "description" : "Operations about pets", - "path" : "/store/order/{orderId}", - "notes" : "For valid response try integer IDs with value < 1000. Anything above 1000 or nonintegers will generate API errors", - "summary" : "Delete purchase order by ID", - "method": "DELETE", - "params" : [].concat([ - params.path("orderId", "ID of the order that needs to be deleted") - ]).concat([]).concat([]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "deleteOrder" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing deleteOrder as a DELETE method?"}); - } -}; diff --git a/samples/server/petstore/nodejs/app/apis/UserApi.js b/samples/server/petstore/nodejs/app/apis/UserApi.js deleted file mode 100644 index 02a17bff08..0000000000 --- a/samples/server/petstore/nodejs/app/apis/UserApi.js +++ /dev/null @@ -1,195 +0,0 @@ -var swagger = require("swagger-node-express"); -var url = require("url"); -var errors = swagger.errors; -var params = swagger.params; - -/* add model includes */ - -function writeResponse (response, data) { - response.header('Access-Control-Allow-Origin', "*"); - response.header("Access-Control-Allow-Methods", "GET, POST, DELETE, PUT"); - response.header("Access-Control-Allow-Headers", "Content-Type"); - response.header("Content-Type", "application/json; charset=utf-8"); - response.send(JSON.stringify(data)); -} - -exports.models = models = require("../models.js"); - -exports.createUser = { - 'spec': { - "description" : "Operations about pets", - "path" : "/user", - "notes" : "This can only be done by the logged in user.", - "summary" : "Create user", - "method": "POST", - "params" : [].concat([]).concat([]).concat([ - params.body("body", "", "Created user object", false) - ]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "createUser" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing createUser as a POST method?"}); - } -}; -exports.createUsersWithArrayInput = { - 'spec': { - "description" : "Operations about pets", - "path" : "/user/createWithArray", - "notes" : "", - "summary" : "Creates list of users with given input array", - "method": "POST", - "params" : [].concat([]).concat([]).concat([ - params.body("body", "", "List of user object", false) - ]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "createUsersWithArrayInput" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing createUsersWithArrayInput as a POST method?"}); - } -}; -exports.createUsersWithListInput = { - 'spec': { - "description" : "Operations about pets", - "path" : "/user/createWithList", - "notes" : "", - "summary" : "Creates list of users with given input array", - "method": "POST", - "params" : [].concat([]).concat([]).concat([ - params.body("body", "", "List of user object", false) - ]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "createUsersWithListInput" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing createUsersWithListInput as a POST method?"}); - } -}; -exports.loginUser = { - 'spec': { - "description" : "Operations about pets", - "path" : "/user/login", - "notes" : "", - "summary" : "Logs user into the system", - "method": "GET", - "params" : [ - params.query("username", "The user name for login", "", false, false, ""), - - params.query("password", "The password for login in clear text", "", false, false, "") - ].concat([]).concat([]).concat([]), - - - "type" : "String", - - "responseMessages" : [errors.invalid('id'), errors.notFound('String')], - "nickname" : "loginUser" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing loginUser as a GET method?"}); - } -}; -exports.logoutUser = { - 'spec': { - "description" : "Operations about pets", - "path" : "/user/logout", - "notes" : "", - "summary" : "Logs out current logged in user session", - "method": "GET", - "params" : [].concat([]).concat([]).concat([]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "logoutUser" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing logoutUser as a GET method?"}); - } -}; -exports.getUserByName = { - 'spec': { - "description" : "Operations about pets", - "path" : "/user/{username}", - "notes" : "", - "summary" : "Get user by user name", - "method": "GET", - "params" : [].concat([ - params.path("username", "The name that needs to be fetched. Use user1 for testing. ") - ]).concat([]).concat([]), - - - "type" : "User", - - "responseMessages" : [errors.invalid('id'), errors.notFound('User')], - "nickname" : "getUserByName" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing getUserByName as a GET method?"}); - } -}; -exports.updateUser = { - 'spec': { - "description" : "Operations about pets", - "path" : "/user/{username}", - "notes" : "This can only be done by the logged in user.", - "summary" : "Updated user", - "method": "PUT", - "params" : [].concat([ - params.path("username", "name that need to be deleted") - ]).concat([]).concat([ - params.body("body", "", "Updated user object", false) - ]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "updateUser" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing updateUser as a PUT method?"}); - } -}; -exports.deleteUser = { - 'spec': { - "description" : "Operations about pets", - "path" : "/user/{username}", - "notes" : "This can only be done by the logged in user.", - "summary" : "Delete user", - "method": "DELETE", - "params" : [].concat([ - params.path("username", "The name that needs to be deleted") - ]).concat([]).concat([]), - - - "type" : "", - - "responseMessages" : [errors.invalid('id'), errors.notFound('')], - "nickname" : "deleteUser" - }, - 'action': function (req,res) { - - writeResponse(res, {message: "how about implementing deleteUser as a DELETE method?"}); - } -}; diff --git a/samples/server/petstore/nodejs/app/models.js b/samples/server/petstore/nodejs/app/models.js deleted file mode 100644 index f54703af71..0000000000 --- a/samples/server/petstore/nodejs/app/models.js +++ /dev/null @@ -1,132 +0,0 @@ -exports.models = { - "User": { - "properties" : { - "id" : { - "type" : "integer", - "format" : "int64" - }, - "username" : { - "type" : "string" - }, - "firstName" : { - "type" : "string" - }, - "lastName" : { - "type" : "string" - }, - "email" : { - "type" : "string" - }, - "password" : { - "type" : "string" - }, - "phone" : { - "type" : "string" - }, - "userStatus" : { - "type" : "integer", - "format" : "int32", - "description" : "User Status" - } - }, - "xml" : { - "name" : "User" - }, - "id" : "User" -},"Category": { - "properties" : { - "id" : { - "type" : "integer", - "format" : "int64" - }, - "name" : { - "type" : "string" - } - }, - "xml" : { - "name" : "Category" - }, - "id" : "Category" -},"Pet": { - "required" : [ "name", "photoUrls" ], - "properties" : { - "id" : { - "type" : "integer", - "format" : "int64" - }, - "category" : { - "$ref" : "Category" - }, - "name" : { - "type" : "string", - "example" : "doggie" - }, - "photoUrls" : { - "type" : "array", - "items" : { - "type" : "string" - } - }, - "tags" : { - "type" : "array", - "items" : { - "$ref" : "Tag" - } - }, - "status" : { - "type" : "string", - "description" : "pet status in the store", - "enum" : [ "available", "pending", "sold" ] - } - }, - "xml" : { - "name" : "Pet" - }, - "id" : "Pet" -},"Tag": { - "properties" : { - "id" : { - "type" : "integer", - "format" : "int64" - }, - "name" : { - "type" : "string" - } - }, - "xml" : { - "name" : "Tag" - }, - "id" : "Tag" -},"Order": { - "properties" : { - "id" : { - "type" : "integer", - "format" : "int64" - }, - "petId" : { - "type" : "integer", - "format" : "int64" - }, - "quantity" : { - "type" : "integer", - "format" : "int32" - }, - "shipDate" : { - "type" : "string", - "format" : "date-time" - }, - "status" : { - "type" : "string", - "description" : "Order Status", - "enum" : [ "placed", "approved", "delivered" ] - }, - "complete" : { - "type" : "boolean" - } - }, - "xml" : { - "name" : "Order" - }, - "id" : "Order" -} -} \ No newline at end of file diff --git a/samples/server/petstore/nodejs/controllers/Pet.js b/samples/server/petstore/nodejs/controllers/Pet.js new file mode 100644 index 0000000000..e3f451a14d --- /dev/null +++ b/samples/server/petstore/nodejs/controllers/Pet.js @@ -0,0 +1,81 @@ +'use strict'; + +var url = require('url'); + + +module.exports.updatePet = function updatePet (req, res, next) { + var body = req.swagger.params['body'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.addPet = function addPet (req, res, next) { + var body = req.swagger.params['body'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.findPetsByStatus = function findPetsByStatus (req, res, next) { + var status = req.swagger.params['status'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.findPetsByTags = function findPetsByTags (req, res, next) { + var tags = req.swagger.params['tags'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.getPetById = function getPetById (req, res, next) { + var petId = req.swagger.params['petId'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.updatePetWithForm = function updatePetWithForm (req, res, next) { + var petId = req.swagger.params['petId'].value; + var name = req.swagger.params['name'].value; + var status = req.swagger.params['status'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.deletePet = function deletePet (req, res, next) { + var api_key = req.swagger.params['api_key'].value; + var petId = req.swagger.params['petId'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.uploadFile = function uploadFile (req, res, next) { + var petId = req.swagger.params['petId'].value; + var additionalMetadata = req.swagger.params['additionalMetadata'].value; + var file = req.swagger.params['file'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; diff --git a/samples/server/petstore/nodejs/controllers/Store.js b/samples/server/petstore/nodejs/controllers/Store.js new file mode 100644 index 0000000000..c6f68fec93 --- /dev/null +++ b/samples/server/petstore/nodejs/controllers/Store.js @@ -0,0 +1,39 @@ +'use strict'; + +var url = require('url'); + + +module.exports.getInventory = function getInventory (req, res, next) { + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.placeOrder = function placeOrder (req, res, next) { + var body = req.swagger.params['body'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.getOrderById = function getOrderById (req, res, next) { + var orderId = req.swagger.params['orderId'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.deleteOrder = function deleteOrder (req, res, next) { + var orderId = req.swagger.params['orderId'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; diff --git a/samples/server/petstore/nodejs/controllers/User.js b/samples/server/petstore/nodejs/controllers/User.js new file mode 100644 index 0000000000..02e5cb33d7 --- /dev/null +++ b/samples/server/petstore/nodejs/controllers/User.js @@ -0,0 +1,77 @@ +'use strict'; + +var url = require('url'); + + +module.exports.createUser = function createUser (req, res, next) { + var body = req.swagger.params['body'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.createUsersWithArrayInput = function createUsersWithArrayInput (req, res, next) { + var body = req.swagger.params['body'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.createUsersWithListInput = function createUsersWithListInput (req, res, next) { + var body = req.swagger.params['body'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.loginUser = function loginUser (req, res, next) { + var username = req.swagger.params['username'].value; + var password = req.swagger.params['password'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.logoutUser = function logoutUser (req, res, next) { + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.getUserByName = function getUserByName (req, res, next) { + var username = req.swagger.params['username'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.updateUser = function updateUser (req, res, next) { + var username = req.swagger.params['username'].value; + var body = req.swagger.params['body'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; + +module.exports.deleteUser = function deleteUser (req, res, next) { + var username = req.swagger.params['username'].value; + + + console.log('do some magic!'); + res.setHeader('Content-Type', 'application/json'); + res.end(); +}; diff --git a/samples/server/petstore/nodejs/index.js b/samples/server/petstore/nodejs/index.js new file mode 100644 index 0000000000..c73b630ed2 --- /dev/null +++ b/samples/server/petstore/nodejs/index.js @@ -0,0 +1,38 @@ +'use strict'; + +var app = require('connect')(); +var http = require('http'); +var swaggerTools = require('swagger-tools'); + +var serverPort = 8080; + +// swaggerRouter configuration +var options = { + swaggerUi: '/swagger.json', + controllers: './controllers', + useStubs: process.env.NODE_ENV === 'development' ? true : false // Conditionally turn on stubs (mock mode) +}; + +// The Swagger document (require it, build it programmatically, fetch it from a URL, ...) +var swaggerDoc = require('./api/swagger.json'); + +// Initialize the Swagger middleware +swaggerTools.initializeMiddleware(swaggerDoc, function (middleware) { + // Interpret Swagger resources and attach metadata to request - must be first in swagger-tools middleware chain + app.use(middleware.swaggerMetadata()); + + // Validate Swagger requests + app.use(middleware.swaggerValidator()); + + // Route validated requests to appropriate controller + app.use(middleware.swaggerRouter(options)); + + // Serve the Swagger documents and Swagger UI + app.use(middleware.swaggerUi()); + + // Start the server + http.createServer(app).listen(8080, function () { + console.log('Your server is listening on port %d (http://localhost:%d)', 8080, 8080); + console.log('Swagger-ui is available on http://localhost:%d/docs', 8080); + }); +}); \ No newline at end of file diff --git a/samples/server/petstore/nodejs/main.js b/samples/server/petstore/nodejs/main.js deleted file mode 100644 index bd84d18c3e..0000000000 --- a/samples/server/petstore/nodejs/main.js +++ /dev/null @@ -1,65 +0,0 @@ -var express = require("express") - , url = require("url") - , cors = require("cors") - , app = express() - , swagger = require("swagger-node-express") - , db = false - - -var corsOptions = { - credentials: true, - origin: function(origin,callback) { - if(origin===undefined) { - callback(null,false); - } else { - callback(null,true); - } - } -}; - -app.use(express.json()); -app.use(express.urlencoded()); -app.use(cors(corsOptions)); - -var subpath = express(); - -app.use("/v2", subpath); - -swagger.setAppHandler(subpath); - -swagger.configureSwaggerPaths("", "api-docs", "") - -var models = require("./app/models.js"); - -var UserApi = require("./app/apis/UserApi.js"); -var StoreApi = require("./app/apis/StoreApi.js"); -var PetApi = require("./app/apis/PetApi.js"); - -swagger.addModels(models) - .addPOST(UserApi.createUser) - .addPOST(UserApi.createUsersWithArrayInput) - .addPOST(UserApi.createUsersWithListInput) - .addGET(UserApi.loginUser) - .addGET(UserApi.logoutUser) - .addGET(UserApi.getUserByName) - .addPUT(UserApi.updateUser) - .addDELETE(UserApi.deleteUser) - .addGET(StoreApi.getInventory) - .addPOST(StoreApi.placeOrder) - .addGET(StoreApi.getOrderById) - .addDELETE(StoreApi.deleteOrder) - .addPUT(PetApi.updatePet) - .addPOST(PetApi.addPet) - .addGET(PetApi.findPetsByStatus) - .addGET(PetApi.findPetsByTags) - .addGET(PetApi.getPetById) - .addPOST(PetApi.updatePetWithForm) - .addDELETE(PetApi.deletePet) - .addPOST(PetApi.uploadFile) - ; - -// configures the app -swagger.configure("http://localhost:8002/v2", "0.1"); - -// start the server -app.listen(8002); diff --git a/samples/server/petstore/nodejs/package.json b/samples/server/petstore/nodejs/package.json index 09424acf15..4d0356c8e6 100644 --- a/samples/server/petstore/nodejs/package.json +++ b/samples/server/petstore/nodejs/package.json @@ -1,16 +1,15 @@ { - "name": "swagger-client", - "description": "Wordnik node.js server generator", - "version": "1.0.0", - "homepage": "", - "main": "./main.js", - "engines": { - "node": ">= 0.8.x" - }, + "name": "", + "version": "", + "description": "This is a sample server Petstore server. You can find out more about Swagger at <a href="http://swagger.io">http://swagger.io</a> or on irc.freenode.net, #swagger. For this sample, you can use the api key "special-key" to test the authorization filters", + "main": "index.js", + "keywords": [ + "swagger" + ], + "license": "MIT", + "private": true, "dependencies": { - "swagger-node-express": ">= 2.0.x", - "connect": ">= 1.8.x", - "cors": "2.1.1", - "express": "3.x" + "connect": "^3.2.0", + "swagger-tools": "0.8.*" } -} \ No newline at end of file +} From cbdb31048e759d4002e2970e58030e05ec39900e Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 18 Mar 2015 22:40:41 -0700 Subject: [PATCH 68/70] updated to release version --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 3f3458c3f2..13cfee6ca6 100644 --- a/pom.xml +++ b/pom.xml @@ -347,7 +347,7 @@ - 1.0.3-SNAPSHOT + 1.0.3 2.11.1 2.3.4 1.5.3-M1-SNAPSHOT From 9311bdf972a1f244e42fdefbb7536725703ae99a Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 18 Mar 2015 23:24:47 -0700 Subject: [PATCH 69/70] added yaml generator --- .../codegen/languages/SwaggerGenerator.java | 3 ++ .../languages/SwaggerYamlGenerator.java | 44 +++++++++++++++++++ .../src/main/resources/swagger/README.md | 2 + .../swagger/generator/online/Generator.java | 1 + 4 files changed, 50 insertions(+) create mode 100644 modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/SwaggerYamlGenerator.java create mode 100644 modules/swagger-codegen/src/main/resources/swagger/README.md diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/SwaggerGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/SwaggerGenerator.java index 8ad75ae3e2..c0560e2a1b 100644 --- a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/SwaggerGenerator.java +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/SwaggerGenerator.java @@ -23,7 +23,10 @@ public class SwaggerGenerator extends DefaultCodegen implements CodegenConfig { public SwaggerGenerator() { super(); + templateDir = "swagger"; outputFolder = "generated-code/swagger"; + + supportingFiles.add(new SupportingFile("README.md", "", "README.md")); } @Override diff --git a/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/SwaggerYamlGenerator.java b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/SwaggerYamlGenerator.java new file mode 100644 index 0000000000..7c65168546 --- /dev/null +++ b/modules/swagger-codegen/src/main/java/com/wordnik/swagger/codegen/languages/SwaggerYamlGenerator.java @@ -0,0 +1,44 @@ +package com.wordnik.swagger.codegen.languages; + +import com.wordnik.swagger.codegen.*; +import com.wordnik.swagger.util.*; +import com.wordnik.swagger.models.Swagger; + +import org.apache.commons.io.FileUtils; + +import java.io.File; + +public class SwaggerYamlGenerator extends DefaultCodegen implements CodegenConfig { + public CodegenType getTag() { + return CodegenType.DOCUMENTATION; + } + + public String getName() { + return "swagger-yaml"; + } + + public String getHelp() { + return "Creates a static swagger.yaml file."; + } + + public SwaggerYamlGenerator() { + super(); + templateDir = "swagger"; + outputFolder = "generated-code/swagger"; + + supportingFiles.add(new SupportingFile("README.md", "", "README.md")); + } + + @Override + public void processSwagger(Swagger swagger) { + try{ + String swaggerString = Yaml.mapper().writeValueAsString(swagger); + String outputFile = outputFolder + File.separator + "swagger.yaml"; + FileUtils.writeStringToFile(new File(outputFile), swaggerString); + System.out.println("wrote file to " + outputFile); + } + catch(Exception e) { + e.printStackTrace(); + } + } +} \ No newline at end of file diff --git a/modules/swagger-codegen/src/main/resources/swagger/README.md b/modules/swagger-codegen/src/main/resources/swagger/README.md new file mode 100644 index 0000000000..0c2b69a24d --- /dev/null +++ b/modules/swagger-codegen/src/main/resources/swagger/README.md @@ -0,0 +1,2 @@ +# Swagger JSON +This is a swagger JSON built by the [swagger-codegen](https://github.com/swagger-api/swagger-codegen) project. \ No newline at end of file diff --git a/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/online/Generator.java b/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/online/Generator.java index 6bbbfec4f7..996a724bb6 100644 --- a/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/online/Generator.java +++ b/modules/swagger-generator/src/main/java/com/wordnik/swagger/generator/online/Generator.java @@ -66,6 +66,7 @@ public class Generator { List files = new Codegen().opts(clientOptInput).generate(); if(files.size() > 0) { List filesToAdd = new ArrayList(); + System.out.println("adding to " + outputFolder); filesToAdd.add(new File(outputFolder)); ZipUtil zip = new ZipUtil(); zip.compressFiles(filesToAdd, outputFilename); From c109c11bea1931e8144ae3da3a1bd3409bc79c41 Mon Sep 17 00:00:00 2001 From: Tony Tam Date: Wed, 18 Mar 2015 23:26:45 -0700 Subject: [PATCH 70/70] added yaml output --- .../META-INF/services/com.wordnik.swagger.codegen.CodegenConfig | 1 + 1 file changed, 1 insertion(+) diff --git a/modules/swagger-codegen/src/main/resources/META-INF/services/com.wordnik.swagger.codegen.CodegenConfig b/modules/swagger-codegen/src/main/resources/META-INF/services/com.wordnik.swagger.codegen.CodegenConfig index 8aa08f9599..afaa0dadc9 100644 --- a/modules/swagger-codegen/src/main/resources/META-INF/services/com.wordnik.swagger.codegen.CodegenConfig +++ b/modules/swagger-codegen/src/main/resources/META-INF/services/com.wordnik.swagger.codegen.CodegenConfig @@ -9,6 +9,7 @@ com.wordnik.swagger.codegen.languages.ScalaClientCodegen com.wordnik.swagger.codegen.languages.StaticDocCodegen com.wordnik.swagger.codegen.languages.StaticHtmlGenerator com.wordnik.swagger.codegen.languages.SwaggerGenerator +com.wordnik.swagger.codegen.languages.SwaggerYamlGenerator com.wordnik.swagger.codegen.languages.TizenClientCodegen com.wordnik.swagger.codegen.languages.PhpClientCodegen com.wordnik.swagger.codegen.languages.RubyClientCodegen