This is an automated email from the ASF dual-hosted git repository.
jamesbognar pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/juneau.git
The following commit(s) were added to refs/heads/master by this push:
new d09b3c1 Fix invalid field type for SchemaInfo.required.
d09b3c1 is described below
commit d09b3c16cb99bd485232593756251ef991ff7f47
Author: JamesBognar <[email protected]>
AuthorDate: Thu Mar 15 18:41:23 2018 -0400
Fix invalid field type for SchemaInfo.required.
---
.../apache/juneau/dto/swagger/SchemaInfoTest.java | 38 +-
.../org/apache/juneau/dto/swagger/SchemaInfo.java | 65 +-
.../org/apache/juneau/json/JsonParserSession.java | 11 +-
juneau-doc/src/main/javadoc/overview.html | 7 +
.../juneau/examples/rest/StaticFilesResource.java | 9 +
.../juneau/examples/rest/files/petstore.html | 213 ----
.../juneau/examples/rest/files/petstore.html | 522 ++++++++++
.../juneau/examples/rest/files/petstore.json | 1055 ++++++++++++++++++++
.../java/org/apache/juneau/rest/RestContext.java | 2 +-
9 files changed, 1674 insertions(+), 248 deletions(-)
diff --git
a/juneau-core/juneau-core-test/src/test/java/org/apache/juneau/dto/swagger/SchemaInfoTest.java
b/juneau-core/juneau-core-test/src/test/java/org/apache/juneau/dto/swagger/SchemaInfoTest.java
index 4aac32a..41b52ce 100644
---
a/juneau-core/juneau-core-test/src/test/java/org/apache/juneau/dto/swagger/SchemaInfoTest.java
+++
b/juneau-core/juneau-core-test/src/test/java/org/apache/juneau/dto/swagger/SchemaInfoTest.java
@@ -438,19 +438,19 @@ public class SchemaInfoTest {
public void testRequired() {
SchemaInfo t = new SchemaInfo();
- t.required(true);
- assertEquals(true, t.getRequired());
- assertType(Boolean.class, t.getRequired());
+ t.required("['x']");
+ assertEquals("[x]", t.getRequired().toString());
+ assertType(List.class, t.getRequired());
- t.required("true");
- assertEquals(true, t.getRequired());
- assertType(Boolean.class, t.getRequired());
+ t.required("['x']");
+ assertEquals("[x, x]", t.getRequired().toString());
+ assertType(List.class, t.getRequired());
- t.required(new StringBuilder("true"));
- assertEquals(true, t.getRequired());
- assertType(Boolean.class, t.getRequired());
+ t.required(new StringBuilder("['x']"));
+ assertEquals("[x, x, x]", t.getRequired().toString());
+ assertType(List.class, t.getRequired());
- t.required(null);
+ t.setRequired(null);
assertNull(t.getRequired());
}
@@ -861,14 +861,14 @@ public class SchemaInfoTest {
.set("pattern", "k")
.set("properties", new
AMap<String,Map<String,Object>>().append("l", new
AMap<String,Object>().append("l1", 1)))
.set("readOnly", true)
- .set("required", true)
+ .set("required", new ASet<String>().appendAll("x"))
.set("title", "m")
.set("type", "n")
.set("uniqueItems", true)
.set("xml", xml().name("o"))
.set("$ref", "ref");
-
assertObjectEquals("{format:'i',title:'m',description:'e','default':'a',multipleOf:123.0,maximum:123.0,exclusiveMaximum:true,minimum:123.0,exclusiveMinimum:true,maxLength:123,minLength:123,pattern:'k',maxItems:123,minItems:123,uniqueItems:true,maxProperties:123,minProperties:123,required:true,'enum':['b'],type:'n',items:{type:'j'},allOf:['d'],properties:{l:{l1:1}},additionalProperties:{c:['c1']},discriminator:'f',readOnly:true,xml:{name:'o'},externalDocs:{url:'h'},example:'g','$ref':'r
[...]
+
assertObjectEquals("{format:'i',title:'m',description:'e','default':'a',multipleOf:123.0,maximum:123.0,exclusiveMaximum:true,minimum:123.0,exclusiveMinimum:true,maxLength:123,minLength:123,pattern:'k',maxItems:123,minItems:123,uniqueItems:true,maxProperties:123,minProperties:123,required:['x'],'enum':['b'],type:'n',items:{type:'j'},allOf:['d'],properties:{l:{l1:1}},additionalProperties:{c:['c1']},discriminator:'f',readOnly:true,xml:{name:'o'},externalDocs:{url:'h'},example:'g','$ref':'
[...]
t
.set("default", "a")
@@ -895,14 +895,14 @@ public class SchemaInfoTest {
.set("pattern", "k")
.set("properties", "{l:{l1:1}}")
.set("readOnly", "true")
- .set("required", "true")
+ .set("required", "['x']")
.set("title", "m")
.set("type", "n")
.set("uniqueItems", "true")
.set("xml", "{name:'o'}")
.set("$ref", "ref");
-
assertObjectEquals("{format:'i',title:'m',description:'e','default':'a',multipleOf:123.0,maximum:123.0,exclusiveMaximum:true,minimum:123.0,exclusiveMinimum:true,maxLength:123,minLength:123,pattern:'k',maxItems:123,minItems:123,uniqueItems:true,maxProperties:123,minProperties:123,required:true,'enum':['b'],type:'n',items:{type:'j'},allOf:['d'],properties:{l:{l1:1}},additionalProperties:{c:['c1']},discriminator:'f',readOnly:true,xml:{name:'o'},externalDocs:{url:'h'},example:'g','$ref':'r
[...]
+
assertObjectEquals("{format:'i',title:'m',description:'e','default':'a',multipleOf:123.0,maximum:123.0,exclusiveMaximum:true,minimum:123.0,exclusiveMinimum:true,maxLength:123,minLength:123,pattern:'k',maxItems:123,minItems:123,uniqueItems:true,maxProperties:123,minProperties:123,required:['x'],'enum':['b'],type:'n',items:{type:'j'},allOf:['d'],properties:{l:{l1:1}},additionalProperties:{c:['c1']},discriminator:'f',readOnly:true,xml:{name:'o'},externalDocs:{url:'h'},example:'g','$ref':'
[...]
t
.set("default", new StringBuilder("a"))
@@ -929,14 +929,14 @@ public class SchemaInfoTest {
.set("pattern", new StringBuilder("k"))
.set("properties", new StringBuilder("{l:{l1:1}}"))
.set("readOnly", new StringBuilder("true"))
- .set("required", new StringBuilder("true"))
+ .set("required", new StringBuilder("['x']"))
.set("title", new StringBuilder("m"))
.set("type", new StringBuilder("n"))
.set("uniqueItems", new StringBuilder("true"))
.set("xml", new StringBuilder("{name:'o'}"))
.set("$ref", new StringBuilder("ref"));
-
assertObjectEquals("{format:'i',title:'m',description:'e','default':'a',multipleOf:123.0,maximum:123.0,exclusiveMaximum:true,minimum:123.0,exclusiveMinimum:true,maxLength:123,minLength:123,pattern:'k',maxItems:123,minItems:123,uniqueItems:true,maxProperties:123,minProperties:123,required:true,'enum':['b'],type:'n',items:{type:'j'},allOf:['d'],properties:{l:{l1:1}},additionalProperties:{c:['c1']},discriminator:'f',readOnly:true,xml:{name:'o'},externalDocs:{url:'h'},example:'g','$ref':'r
[...]
+
assertObjectEquals("{format:'i',title:'m',description:'e','default':'a',multipleOf:123.0,maximum:123.0,exclusiveMaximum:true,minimum:123.0,exclusiveMinimum:true,maxLength:123,minLength:123,pattern:'k',maxItems:123,minItems:123,uniqueItems:true,maxProperties:123,minProperties:123,required:['x'],'enum':['b'],type:'n',items:{type:'j'},allOf:['d'],properties:{l:{l1:1}},additionalProperties:{c:['c1']},discriminator:'f',readOnly:true,xml:{name:'o'},externalDocs:{url:'h'},example:'g','$ref':'
[...]
assertEquals("a", t.get("default", String.class));
assertEquals("['b']", t.get("enum", String.class));
@@ -962,7 +962,7 @@ public class SchemaInfoTest {
assertEquals("k", t.get("pattern", String.class));
assertEquals("{l:{l1:1}}", t.get("properties", String.class));
assertEquals("true", t.get("readOnly", String.class));
- assertEquals("true", t.get("required", String.class));
+ assertEquals("['x']", t.get("required", String.class));
assertEquals("m", t.get("title", String.class));
assertEquals("n", t.get("type", String.class));
assertEquals("true", t.get("uniqueItems", String.class));
@@ -993,7 +993,7 @@ public class SchemaInfoTest {
assertType(String.class, t.get("pattern", Object.class));
assertType(Map.class, t.get("properties", Object.class));
assertType(Boolean.class, t.get("readOnly", Object.class));
- assertType(Boolean.class, t.get("required", Object.class));
+ assertType(List.class, t.get("required", Object.class));
assertType(String.class, t.get("title", Object.class));
assertType(String.class, t.get("type", Object.class));
assertType(Boolean.class, t.get("uniqueItems", Object.class));
@@ -1005,7 +1005,7 @@ public class SchemaInfoTest {
assertNull(t.get(null, Object.class));
assertNull(t.get("foo", Object.class));
- String s =
"{format:'i',title:'m',description:'e','default':'a',multipleOf:123.0,maximum:123.0,exclusiveMaximum:true,minimum:123.0,exclusiveMinimum:true,maxLength:123,minLength:123,pattern:'k',maxItems:123,minItems:123,uniqueItems:true,maxProperties:123,minProperties:123,required:true,'enum':['b'],type:'n',items:{type:'j'},allOf:['d'],properties:{l:{l1:1}},additionalProperties:{c:['c1']},discriminator:'f',readOnly:true,xml:{name:'o'},externalDocs:{url:'h'},example:'g','$ref':'ref'}";
+ String s =
"{format:'i',title:'m',description:'e','default':'a',multipleOf:123.0,maximum:123.0,exclusiveMaximum:true,minimum:123.0,exclusiveMinimum:true,maxLength:123,minLength:123,pattern:'k',maxItems:123,minItems:123,uniqueItems:true,maxProperties:123,minProperties:123,required:['x'],'enum':['b'],type:'n',items:{type:'j'},allOf:['d'],properties:{l:{l1:1}},additionalProperties:{c:['c1']},discriminator:'f',readOnly:true,xml:{name:'o'},externalDocs:{url:'h'},example:'g','$ref':'ref'}";
assertObjectEquals(s, JsonParser.DEFAULT.parse(s,
SchemaInfo.class));
}
}
diff --git
a/juneau-core/juneau-dto/src/main/java/org/apache/juneau/dto/swagger/SchemaInfo.java
b/juneau-core/juneau-dto/src/main/java/org/apache/juneau/dto/swagger/SchemaInfo.java
index 613a618..90438a0 100644
---
a/juneau-core/juneau-dto/src/main/java/org/apache/juneau/dto/swagger/SchemaInfo.java
+++
b/juneau-core/juneau-dto/src/main/java/org/apache/juneau/dto/swagger/SchemaInfo.java
@@ -80,7 +80,6 @@ public class SchemaInfo extends SwaggerElement {
exclusiveMaximum,
exclusiveMinimum,
uniqueItems,
- required,
readOnly;
private Object
_default,
@@ -91,6 +90,8 @@ public class SchemaInfo extends SwaggerElement {
private List<Object>
_enum,
allOf;
+ private List<String>
+ required;
private Map<String,Map<String,Object>> properties;
private Map<String,Object> additionalProperties;
@@ -705,36 +706,78 @@ public class SchemaInfo extends SwaggerElement {
/**
* Bean property getter: <property>required</property>.
*
+ * <p>
+ * The list of required properties.
+ *
* @return The property value, or <jk>null</jk> if it is not set.
*/
- public Boolean getRequired() {
+ public List<String> getRequired() {
return required;
}
/**
* Bean property setter: <property>required</property>.
*
+ * <p>
+ * The list of required properties.
+ *
* @param value
* The new value for this property.
+ * <br>Valid values:
+ * <ul>
+ * <li><js>"http"</js>
+ * <li><js>"https"</js>
+ * <li><js>"ws"</js>
+ * <li><js>"wss"</js>
+ * </ul>
* <br>Can be <jk>null</jk> to unset the property.
* @return This object (for method chaining).
*/
- public SchemaInfo setRequired(Boolean value) {
- required = value;
+ public SchemaInfo setRequired(Collection<String> value) {
+ required = newList(value);
return this;
}
/**
- * Same as {@link #setRequired(Boolean)}.
+ * Adds one or more values to the <property>required</property>
property.
*
- * @param value
+ * <p>
+ * The list of required properties.
+ *
+ * @param value
+ * The values to add to this property.
+ * <br>Ignored if <jk>null</jk>.
+ * @return This object (for method chaining).
+ */
+ public SchemaInfo addRequired(Collection<String> value) {
+ required = addToList(required, value);
+ return this;
+ }
+
+ /**
+ * Same as {@link #addRequired(Collection)}.
+ *
+ * @param values
* The new value for this property.
- * <br>Non-boolean values will be converted to boolean using
<code>Boolean.<jsm>valueOf</jsm>(value.toString())</code>.
- * <br>Can be <jk>null</jk> to unset the property.
+ * <br>Valid types:
+ * <ul>
+ * <li><code>Collection<String></code>
+ * <li><code>String</code> - JSON array representation of
<code>Collection<String></code>
+ * <h5 class='figure'>Example:</h5>
+ * <p class='bcode'>
+ * schemes(<js>"['scheme1','scheme2']"</js>);
+ * </p>
+ * <li><code>String</code> - Individual values
+ * <h5 class='figure'>Example:</h5>
+ * <p class='bcode'>
+ * schemes(<js>"scheme1</js>, <js>"scheme2"</js>);
+ * </p>
+ * </ul>
* @return This object (for method chaining).
*/
- public SchemaInfo required(Object value) {
- return setRequired(toBoolean(value));
+ public SchemaInfo required(Object...values) {
+ required = addToList(required, values, String.class);
+ return this;
}
/**
@@ -1323,7 +1366,7 @@ public class SchemaInfo extends SwaggerElement {
case "uniqueItems": return uniqueItems(value);
case "maxProperties": return maxProperties(value);
case "minProperties": return minProperties(value);
- case "required": return required(value);
+ case "required": return
setRequired(null).required(value);
case "enum": return setEnum(null)._enum(value);
case "type": return type(value);
case "items": return items(value);
diff --git
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/json/JsonParserSession.java
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/json/JsonParserSession.java
index e0d7a86..e244aa6 100644
---
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/json/JsonParserSession.java
+++
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/json/JsonParserSession.java
@@ -285,9 +285,12 @@ public final class JsonParserSession extends
ReaderParserSession {
if (c == 't') {
parseKeyword("true", r);
return Boolean.TRUE;
+ } else if (c == 'f') {
+ parseKeyword("false", r);
+ return Boolean.FALSE;
+ } else {
+ throw new ParseException(loc(r), "Unrecognized syntax.
Expected boolean value, actual=''{0}''", r.read(100));
}
- parseKeyword("false", r);
- return Boolean.FALSE;
}
@@ -627,9 +630,9 @@ public final class JsonParserSession extends
ReaderParserSession {
String s = r.read(keyword.length());
if (s.equals(keyword))
return;
- throw new ParseException(loc(r), "Unrecognized
syntax.");
+ throw new ParseException(loc(r), "Unrecognized syntax.
Expected=''{0}'', Actual=''{1}''", keyword, s);
} catch (IndexOutOfBoundsException e) {
- throw new ParseException(loc(r), "Unrecognized
syntax.");
+ throw new ParseException(loc(r), "Unrecognized syntax.
Expected=''{0}'', found end-of-file.", keyword);
}
}
diff --git a/juneau-doc/src/main/javadoc/overview.html
b/juneau-doc/src/main/javadoc/overview.html
index dbd8f70..e10f7f1 100644
--- a/juneau-doc/src/main/javadoc/overview.html
+++ b/juneau-doc/src/main/javadoc/overview.html
@@ -21247,6 +21247,13 @@
</ul>
</ul>
+ <h5 class='topic w800'>juneau-dto</h5>
+ <ul class='spaced-list'>
+ <li>
+ Fixed bug where Swagger {@link
org.apache.juneau.dto.swagger.SchemaInfo#required(Object)} was defined as a
boolean
+ instead of a list of strings.
+ </ul>
+
<h5 class='topic w800'>juneau-rest-server</h5>
<ul class='spaced-list'>
<li>
diff --git
a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/StaticFilesResource.java
b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/StaticFilesResource.java
index 0966ccf..d0b9597 100644
---
a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/StaticFilesResource.java
+++
b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/StaticFilesResource.java
@@ -15,6 +15,8 @@ package org.apache.juneau.examples.rest;
import static org.apache.juneau.http.HttpMethodName.*;
import org.apache.juneau.dto.*;
+import org.apache.juneau.dto.swagger.*;
+import org.apache.juneau.http.*;
import org.apache.juneau.microservice.*;
import org.apache.juneau.rest.annotation.*;
import org.apache.juneau.rest.widget.*;
@@ -56,4 +58,11 @@ public class StaticFilesResource extends
BasicRestServletJena {
new LinkString("petstore.html","static/petstore.html")
};
}
+
+ @RestMethod(name=GET, path="/swagger", summary="xxx")
+ public Swagger testSwagger() throws Exception {
+ Swagger s = getContext().getClasspathResource(Swagger.class,
MediaType.JSON, "files/petstore.json", null);
+ return s;
+ }
+
}
diff --git
a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/files/petstore.html
b/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/files/petstore.html
deleted file mode 100644
index ef4bcbe..0000000
---
a/juneau-examples/juneau-examples-rest/src/main/java/org/apache/juneau/examples/rest/files/petstore.html
+++ /dev/null
@@ -1,213 +0,0 @@
-<!--
-
***************************************************************************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file *
- * distributed with this work for additional information regarding copyright
ownership. The ASF licenses this file *
- * to you under the Apache License, Version 2.0 (the "License"); you may not
use this file except in compliance *
- * with the License. You may obtain a copy of the License at
*
- *
*
- * http://www.apache.org/licenses/LICENSE-2.0
*
- *
*
- * Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an *
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
or implied. See the License for the *
- * specific language governing permissions and limitations under the License.
*
-
***************************************************************************************************************************
--->
-
-<html>
-<head>
-
-<style class='text/css'>
-
-.method-button {
- display: inline-block;
- font-size: 14px;
- font-weight: 700;
- min-width: 60px;
- padding: 6px 15px;
- text-align: center;
- border-radius: 3px;
- text-shadow: 0 1px 0 rgba(0,0,0,.1);
- font-family: Titillium Web,sans-serif;
- color: #fff;
-}
-
-.get .method-button { background: rgb(97,175,254); }
-.put .method-button { background: rgb(252,161,48); }
-.post .method-button { background: rgb(73,204,144); }
-.delete .method-button { background: rgb(249,62,62); }
-.options .method-button { background: rgb(153,102,255); }
-.deprecated .method-button { background: rgb(170,170,170); }
-.other .method-button { background: rgb(230,230,0); }
-
-.opblock {
- margin: 0 0 15px;
- font-family: Open Sans,sans-serif;
- align-items: center;
- cursor: pointer;
- border-radius: 4px;
-}
-
-.opblock.get { background: rgba(97,175,254,.1); border: 1px solid
rgb(97,175,254); }
-.opblock.put { background: rgba(252,161,48,.1); border: 1px solid
rgb(252,161,48); }
-.opblock.post { background: rgba(73,204,144,.1); border: 1px solid
rgb(73,204,144); }
-.opblock.options { background: rgba(153,102,255,.1); border: 1px solid
rgb(153,102,255); }
-.opblock.delete { background: rgba(249,62,62,.1); border: 1px solid
rgb(249,62,62); }
-.opblock.deprecated { background: rgba(170,170,170,.1); border: 1px solid
rgb(170,170,170); }
-.opblock.other { background: rgba(230,230,0,0.1); border: 1px solid
rgb(230,230,0); }
-
-.opblock-summary {
- padding:5px;
-}
-
-.opblock-summary .path {
- font-size: 16px;
- word-break: break-all;
- font-family: Source Code Pro,monospace;
- font-weight: 600;
- color: #3b4151;
- padding:10px;
-}
-
-.opblock.deprecated .opblock-summary .path { color: #8f9199; text-decoration:
line-through;}
-.opblock.deprecated .opblock-summary .description { color: #8f9199 }
-
-.opblock-summary .description {
- font-family: Open Sans,sans-serif;
- color: #3b4151;
- font-size: 13px;
- padding:10px;
-}
-
-.opblock-section-header {
- padding: 8px 20px;
- background: hsla(0,0%,100%,.8);
- box-shadow: 0 1px 2px rgba(0,0,0,.1);
- font-family: Open Sans,sans-ser;
- color: #8f9199;
-}
-
-.opblock-section-header .title {
- font-size: 14px;
- font-family: Titillium Web,sans-serif;
- color: #3b4151;
- margin: 0px;
-}
-
-.is-open .opblock-contents {
- display: block;
-}
-.is-closed .opblock-contents {
- display: none;
-}
-
-.parameters {
- padding: 0 10px;
- border-collapse: collapse;
- margin: 20px;
- width: 95%;
-}
-
-.parameters th {
- font-size: 12px;
- font-weight: 700;
- padding: 12px 0;
- text-align: left;
- border-bottom: 1px solid rgba(59,65,81,.2);
- font-family: Open Sans,sans-serif;
- color: #3b4151;
-}
-
- </style>
- <script>
-
- function toggle(e) {
- var isOpen = e.classList.contains("is-open");
- if (isOpen) {
- e.classList.add("is-closed");
- e.classList.remove("is-open");
- } else {
- e.classList.add("is-open");
- e.classList.remove("is-closed");
- }
- window.getSelection().removeAllRanges();
- }
- </script>
-</head>
-<body>
-
-<div class='opblock get is-open' onclick='toggle(this)'>
- <div class='opblock-summary'>
- <span class='method-button'>GET</span>
- <span class='path'>/pet</span>
- <span class='description'>Everything about your Pets</span>
- </div>
- <div class='opblock-contents'>
- <div class="table-container">
- <div class="opblock-section-header">
- <h4 class="title">Parameters</h4>
- </div>
- <table class="parameters">
- <tr>
- <th>Name</th>
- <th>Description</th>
- </tr>
- <tr>
- <td>foo</td>
- <td>bar</td>
- </tr>
- </table>
- </div>
- </div>
-
-</div>
-
-<div class='opblock put is-closed' onclick='toggle(this)'>
- <div class='opblock-summary'>
- <span class='method-button'>PUT</span>
- <span class='path'>/pet</span>
- <span class='description'>Everything about your Pets</span>
- </div>
-</div>
-
-<div class='opblock post is-closed' onclick='toggle(this)'>
- <div class='opblock-summary'>
- <span class='method-button'>POST</span>
- <span class='path'>/pet</span>
- <span class='description'>Everything about your Pets</span>
- </div>
-</div>
-<div class='opblock delete is-closed' onclick='toggle(this)'>
- <div class='opblock-summary'>
- <span class='method-button'>DELETE</span>
- <span class='path'>/pet</span>
- <span class='description'>Everything about your Pets</span>
- </div>
-</div>
-<div class='opblock deprecated is-closed' onclick='toggle(this)'>
- <div class='opblock-summary'>
- <span class='method-button'>GET</span>
- <span class='path'>/pet</span>
- <span class='description'>Everything about your Pets</span>
- </div>
-</div>
-
-<div class='opblock other is-closed' onclick='toggle(this)'>
- <div class='opblock-summary'>
- <span class='method-button'>OTHER</span>
- <span class='path'>/pet</span>
- <span class='description'>Everything about your Pets</span>
- </div>
-</div>
-
-<div class='opblock options is-closed' onclick='toggle(this)'>
- <div class='opblock-summary'>
- <span class='method-button'>OPTIONS</span>
- <span class='path'>/pet</span>
- <span class='description'>Everything about your Pets</span>
- </div>
-</div>
-
-
-</body>
-
-</html>
\ No newline at end of file
diff --git
a/juneau-examples/juneau-examples-rest/src/main/resources/org/apache/juneau/examples/rest/files/petstore.html
b/juneau-examples/juneau-examples-rest/src/main/resources/org/apache/juneau/examples/rest/files/petstore.html
new file mode 100644
index 0000000..b3a42d4
--- /dev/null
+++
b/juneau-examples/juneau-examples-rest/src/main/resources/org/apache/juneau/examples/rest/files/petstore.html
@@ -0,0 +1,522 @@
+<!--
+
***************************************************************************************************************************
+ * Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file *
+ * distributed with this work for additional information regarding copyright
ownership. The ASF licenses this file *
+ * to you under the Apache License, Version 2.0 (the "License"); you may not
use this file except in compliance *
+ * with the License. You may obtain a copy of the License at
*
+ *
*
+ * http://www.apache.org/licenses/LICENSE-2.0
*
+ *
*
+ * Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an *
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
or implied. See the License for the *
+ * specific language governing permissions and limitations under the License.
*
+
***************************************************************************************************************************
+-->
+
+<html>
+<head>
+
+<style class='text/css'>
+
+.method-button {
+ display: inline-block;
+ font-size: 14px;
+ font-weight: 700;
+ min-width: 60px;
+ padding: 6px 15px;
+ text-align: center;
+ border-radius: 3px;
+ text-shadow: 0 1px 0 rgba(0,0,0,.1);
+ font-family: Titillium Web,sans-serif;
+ color: #fff;
+}
+
+.get .method-button { background: rgb(97,175,254); }
+.put .method-button { background: rgb(252,161,48); }
+.post .method-button { background: rgb(73,204,144); }
+.delete .method-button { background: rgb(249,62,62); }
+.options .method-button { background: rgb(153,102,255); }
+.deprecated .method-button { background: rgb(170,170,170); }
+.other .method-button { background: rgb(230,230,0); }
+
+.op-block {
+ margin: 0 0 15px;
+ font-family: Open Sans,sans-serif;
+ align-items: center;
+ cursor: pointer;
+ border-radius: 4px;
+}
+
+.tag-block-summary {
+ margin: 10px 0px;
+ padding: 10px 0px;
+ font-family: Open Sans,sans-serif;
+ align-items: center;
+ cursor: pointer;
+ border-bottom: 1px solid rgba(59,65,81,.2);
+}
+
+.tag-block-summary .name {
+ font-family: Titillium Web,sans-serif;
+ font-size: 22px;
+ padding: 0px 20px;
+}
+.tag-block-summary .description {
+ font-size: 16px;
+ font-weight: 400;
+ padding: 0px 20px;
+}
+.tag-block-summary .extdocs {
+ float: right;
+ font-size: 14px;
+ font-weight: 400;
+ padding: 0px 20px;
+}
+
+
+.op-block.get { background: rgba(97,175,254,.1); border: 1px solid
rgb(97,175,254); }
+.op-block.put { background: rgba(252,161,48,.1); border: 1px solid
rgb(252,161,48); }
+.op-block.post { background: rgba(73,204,144,.1); border: 1px solid
rgb(73,204,144); }
+.op-block.options { background: rgba(153,102,255,.1); border: 1px solid
rgb(153,102,255); }
+.op-block.delete { background: rgba(249,62,62,.1); border: 1px solid
rgb(249,62,62); }
+.op-block.deprecated { background: rgba(170,170,170,.1); border: 1px solid
rgb(170,170,170); }
+.op-block.other { background: rgba(230,230,0,0.1); border: 1px solid
rgb(230,230,0); }
+
+.op-block-summary {
+ padding:5px;
+}
+
+.op-block-summary .path {
+ font-size: 16px;
+ word-break: break-all;
+ font-family: Source Code Pro,monospace;
+ font-weight: 600;
+ color: #3b4151;
+ padding:10px;
+}
+
+.op-block.deprecated .op-block-summary .path { color: #8f9199;
text-decoration: line-through;}
+.op-block.deprecated .op-block-summary .description { color: #8f9199 }
+
+.op-block-summary .description {
+ font-family: Open Sans,sans-serif;
+ color: #3b4151;
+ font-size: 13px;
+ padding:10px;
+}
+
+.op-block-section-header {
+ padding: 8px 20px;
+ background: hsla(0,0%,100%,.8);
+ box-shadow: 0 1px 2px rgba(0,0,0,.1);
+ font-family: Open Sans,sans-ser;
+ color: #8f9199;
+}
+
+.op-block-section-header .title {
+ font-size: 14px;
+ font-family: Titillium Web,sans-serif;
+ color: #3b4151;
+ margin: 0px;
+}
+
+.is-tag-block-open .tag-block-contents {
+ display: block;
+}
+.is-tag-block-closed .tag-block-contents {
+ display: none;
+}
+
+.is-op-block-open .op-block-contents {
+ display: block;
+}
+.is-op-block-closed .op-block-contents {
+ display: none;
+}
+
+.parameters, .responses {
+ border-collapse: collapse;
+ margin: 20px;
+ width: 95%;
+ border-bottom: 1px solid rgba(59,65,81,.2);
+}
+
+.parameters th, .responses th {
+ font-size: 12px;
+ font-weight: 700;
+ padding: 5px 0;
+ text-align: left;
+ border-bottom: 1px solid rgba(59,65,81,.2);
+ font-family: Open Sans,sans-serif;
+ color: #3b4151;
+}
+
+.parameters td, .responses td {
+ padding: 12px 0;
+ text-align: left;
+ border-bottom: 1px solid rgba(59,65,81,.2);
+}
+
+.parameter-key .in {
+ font-size: 12px;
+ font-family: Source Code Pro,monospace;
+ font-weight: 600;
+ font-style: italic;
+ color: gray;
+}
+
+.parameter-key .name {
+ font-size: 16px;
+ font-weight: 400;
+ font-family: Titillium Web,sans-serif;
+ color: #3b4151;
+}
+
+.parameter-key .name.required {
+ font-weight: 700;
+}
+
+.parameter-key .type {
+ font-size: 12px;
+ padding: 5px 0;
+ font-family: Source Code Pro,monospace;
+ font-weight: 600;
+ color: #3b4151;
+}
+
+.tab {
+ display: flex;
+ margin: 20px 0 10px;
+ padding: 0;
+ list-style: none;
+ cursor: pointer;
+ font-family: Titillium Web,sans-serif;
+ color: #3b4151;
+ font-size: 12px;
+}
+
+.tab li {
+ margin: 0px 2px;
+}
+
+.tab .active {
+ font-weight: 700;
+}
+
+.tab li:not(:last-child):after {
+ content: " -";
+ font-weight:400;
+ box-sizing: inherit;
+}
+
+.tab li:hover {
+ font-weight:700;
+}
+
+.example {
+ font-size: 12px;
+ margin: 0;
+ padding: 5px 20px;
+ white-space: pre-wrap;
+ word-wrap: break-word;
+ hyphens: auto;
+ border-radius: 4px;
+ background: #41444e;
+ overflow-wrap: break-word;
+ font-family: Source Code Pro,monospace;
+ font-weight: 400;
+ color: #fff;
+ display:none;
+}
+
+.example.active {
+ display:block;
+}
+
+.section {
+ font-size: 12px;
+ font-weight: 700;
+ padding: 5px 0;
+ text-align: left;
+ font-family: Open Sans,sans-serif;
+ color: #3b4151;
+}
+
+.headers .name {
+ font-size: 12px;
+ padding: 5px 0;
+ font-family: Source Code Pro,monospace;
+ font-weight: 600;
+ color: #3b4151;
+}
+
+div.headers {
+ margin: 20px 0px;
+}
+
+.headers .type {
+ font-size: 12px;
+ padding: 5px 0;
+ font-family: Source Code Pro,monospace;
+ font-weight: 600;
+ color: #3b4151;
+}
+
+.section-name {
+ display: inline-block;
+ vertical-align: top;
+ margin-right: 20px;
+ font-size: 12px;
+ font-weight: 700;
+ padding: 5px 0;
+ text-align: left;
+ font-family: Open Sans,sans-serif;
+ color: #3b4151;
+
+}
+
+.section-table {
+ display: inline-block;
+}
+
+.responses .section-table td {
+ padding: 5px 20px 5px 0px;
+ text-align: left;
+ border-bottom: 1px solid rgba(59,65,81,.2);
+}
+
+
+ </style>
+ <script>
+
+ function toggleOpBlock(e) {
+ e = e.parentNode;
+ var isOpen = e.classList.contains("is-op-block-open");
+ if (isOpen) {
+ e.classList.add("is-op-block-closed");
+ e.classList.remove("is-op-block-open");
+ } else {
+ e.classList.add("is-op-block-open");
+ e.classList.remove("is-op-block-closed");
+ }
+ window.getSelection().removeAllRanges();
+ }
+
+ function toggleTagBlock(e) {
+ e = e.parentNode;
+ var isOpen = e.classList.contains("is-tag-block-open");
+ if (isOpen) {
+ e.classList.add("is-tag-block-closed");
+ e.classList.remove("is-tag-block-open");
+ } else {
+ e.classList.add("is-tag-block-open");
+ e.classList.remove("is-tag-block-closed");
+ }
+ window.getSelection().removeAllRanges();
+ }
+
+ function selectExample(e) {
+ var dataName = e.getAttribute("data-name");
+ var examplesNode = e.parentNode.parentNode;
+ var lis = examplesNode.getElementsByTagName("li");
+ var divs = examplesNode.getElementsByTagName("div");
+
+ for (var i in lis) {
+ var li = lis[i], div = divs[i];
+ if (li.getAttribute("data-name") == dataName) {
+ li.classList.add("active");
+ div.classList.add("active");
+ } else {
+ li.classList.remove("active");
+ div.classList.remove("active");
+ }
+ }
+ }
+ </script>
+</head>
+<body>
+
+<div class='tag-block is-tag-block-open'>
+ <div class='tag-block-summary' onclick='toggleTagBlock(this)'>
+ <span class='name'>pet</span>
+ <span class='description'>Everything about your Pets</span>
+ <span class='extdocs'><a href='http://apache.org'>Find out
more</a></span>
+ </div>
+ <div class='tag-block-contents'>
+ <div class='op-block get is-op-block-open'>
+ <div class='op-block-summary'
onclick='toggleOpBlock(this)'>
+ <span class='method-button'>GET</span>
+ <span class='path'>/pet</span>
+ <span class='description'>Everything about your
Pets</span>
+ </div>
+ <div class='op-block-contents'>
+ <div class="table-container">
+ <div class="op-block-section-header">
+ <h4
class="title">Parameters</h4>
+ </div>
+ <table class="parameters">
+ <tr>
+ <th>Name</th>
+ <th>Description</th>
+ </tr>
+ <tr>
+ <td
class='parameter-key'>
+ <div
class='name required'>body</div>
+ <div
class='type'>integer</div>
+ <div
class='deprecated'></div>
+ <div
class='in'>(body)</div>
+ </td>
+ <td
class='parameter-value'>
+ <div
class='description'>Pet object that needs to be added to the store.</div>
+ <div
class='examples'>
+ <ul
class="tab">
+
<li class="active" data-name='model' onclick='selectExample(this)'>Model</li>
+
<li data-name='application/json'
onclick='selectExample(this)'>application/json</li>
+
<li data-name='text/xml' onclick='selectExample(this)'>text/xml</li>
+
<li data-name='text/html' onclick='selectExample(this)'>text/html</li>
+
<li data-name='octal/messagepack'
onclick='selectExample(this)'>octal/messagepack</li>
+ </ul>
+ <div
data-name='model' class='example active'>
+ MODEL
+ </div>
+ <div
data-name='application/json' class='example'>
+ APPLICATION/JSON
+ </div>
+ <div
data-name='text/xml' class='example'>
+ TEXT/XML
+ </div>
+ <div
data-name='text/html' class='example'>
+ TEXT/HTML
+ </div>
+ <div
data-name='octal/messagepack' class='example'>
+ OCTAL/MESSAGEPACK
+ </div>
+ </div>
+ </td>
+ </tr>
+ </table>
+ <div class="op-block-section-header">
+ <h4 class="title">Responses</h4>
+ </div>
+ <table class="responses">
+ <tr>
+ <th>Code</th>
+ <th>Description</th>
+ </tr>
+ <tr>
+ <td>200</td>
+ <td>
+ <div
class='description'>Successful operation</div>
+ <div
class='examples'>
+ <ul
class="tab">
+
<li class="active" data-name='model' onclick='selectExample(this)'>Model</li>
+
<li data-name='application/json'
onclick='selectExample(this)'>application/json</li>
+
<li data-name='text/xml' onclick='selectExample(this)'>text/xml</li>
+
<li data-name='text/html' onclick='selectExample(this)'>text/html</li>
+
<li data-name='octal/messagepack'
onclick='selectExample(this)'>octal/messagepack</li>
+ </ul>
+ <div
data-name='model' class='example active'>
+ MODEL
+ </div>
+ <div
data-name='application/json' class='example'>
+ APPLICATION/JSON
+ </div>
+ <div
data-name='text/xml' class='example'>
+ TEXT/XML
+ </div>
+ <div
data-name='text/html' class='example'>
+ TEXT/HTML
+ </div>
+ <div
data-name='octal/messagepack' class='example'>
+ OCTAL/MESSAGEPACK
+ </div>
+ </div>
+ <div
class='headers'>
+ <div
class='section-name'>Headers:</div>
+ <table
class='section-table'>
+
<tr>
+
<th>Name</th>
+
<th>Description</th>
+
<th>Type</th>
+
</tr>
+
<tr>
+
<td class='name'>X-Rate-Limit</td>
+
<td class='description'>Calls per hour allowed by the user</td>
+
<td class='type'>integer</td>
+
</tr>
+ </table>
+ </div>
+ </td>
+ </tr>
+ <tr>
+ <td>400</td>
+ <td>
+ <div
class='description'>Bad thing happened</div>
+ </td>
+ </tr>
+ </table>
+ </div>
+ </div>
+
+ </div>
+
+ <div class='op-block put is-closed' onclick='toggle(this)'>
+ <div class='op-block-summary'>
+ <span class='method-button'>PUT</span>
+ <span class='path'>/pet</span>
+ <span class='description'>Everything about your
Pets</span>
+ </div>
+ </div>
+
+ <div class='op-block post is-closed' onclick='toggle(this)'>
+ <div class='op-block-summary'>
+ <span class='method-button'>POST</span>
+ <span class='path'>/pet</span>
+ <span class='description'>Everything about your
Pets</span>
+ </div>
+ </div>
+ </div>
+</div>
+<div class='tag-block is-tag-block-open'>
+ <div class='tag-block-summary' onclick='toggleTagBlock(this)'>
+ <span class='name'>owner</span>
+ <span class='description'>Everything about your Owner</span>
+ <span class='extdocs'><a href='http://apache.org'>Find out
more</a></span>
+ </div>
+ <div class='tag-block-contents'>
+ <div class='op-block delete is-closed' onclick='toggle(this)'>
+ <div class='op-block-summary'>
+ <span class='method-button'>DELETE</span>
+ <span class='path'>/pet</span>
+ <span class='description'>Everything about your
Pets</span>
+ </div>
+ </div>
+ <div class='op-block deprecated is-closed'
onclick='toggle(this)'>
+ <div class='op-block-summary'>
+ <span class='method-button'>GET</span>
+ <span class='path'>/pet</span>
+ <span class='description'>Everything about your
Pets</span>
+ </div>
+ </div>
+
+ <div class='op-block other is-closed' onclick='toggle(this)'>
+ <div class='op-block-summary'>
+ <span class='method-button'>OTHER</span>
+ <span class='path'>/pet</span>
+ <span class='description'>Everything about your
Pets</span>
+ </div>
+ </div>
+
+ <div class='op-block options is-closed' onclick='toggle(this)'>
+ <div class='op-block-summary'>
+ <span class='method-button'>OPTIONS</span>
+ <span class='path'>/pet</span>
+ <span class='description'>Everything about your
Pets</span>
+ </div>
+ </div>
+ </div>
+</div>
+
+</body>
+
+</html>
\ No newline at end of file
diff --git
a/juneau-examples/juneau-examples-rest/src/main/resources/org/apache/juneau/examples/rest/files/petstore.json
b/juneau-examples/juneau-examples-rest/src/main/resources/org/apache/juneau/examples/rest/files/petstore.json
new file mode 100644
index 0000000..54791ba
--- /dev/null
+++
b/juneau-examples/juneau-examples-rest/src/main/resources/org/apache/juneau/examples/rest/files/petstore.json
@@ -0,0 +1,1055 @@
+//
***************************************************************************************************************************
+// * Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file *
+// * distributed with this work for additional information regarding copyright
ownership. The ASF licenses this file *
+// * to you under the Apache License, Version 2.0 (the "License"); you may not
use this file except in compliance *
+// * with the License. You may obtain a copy of the License at
*
+// *
*
+// * http://www.apache.org/licenses/LICENSE-2.0
*
+// *
*
+// * Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an *
+// * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
express or implied. See the License for the *
+// * specific language governing permissions and limitations under the
License. *
+//
***************************************************************************************************************************
+
+{
+ "swagger": "2.0",
+ "info": {
+ "description": "This is a sample server Petstore server. You
can find out more about Swagger at [http://swagger.io](http://swagger.io) or on
[irc.freenode.net, #swagger](http://swagger.io/irc/). 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://swagger.io/terms/",
+ "contact": {
+ "email": "[email protected]"
+ },
+ "license": {
+ "name": "Apache 2.0",
+ "url": "http://www.apache.org/licenses/LICENSE-2.0.html"
+ }
+ },
+ "host": "petstore.swagger.io",
+ "basePath": "/v2",
+ "tags": [
+ {
+ "name": "pet",
+ "description": "Everything about your Pets",
+ "externalDocs": {
+ "description": "Find out more",
+ "url": "http://swagger.io"
+ }
+ },
+ {
+ "name": "store",
+ "description": "Access to Petstore orders"
+ },
+ {
+ "name": "user",
+ "description": "Operations about user",
+ "externalDocs": {
+ "description": "Find out more about our store",
+ "url": "http://swagger.io"
+ }
+ }
+ ],
+ "schemes": [
+ "http"
+ ],
+ "paths": {
+ "/pet": {
+ "post": {
+ "tags": [
+ "pet"
+ ],
+ "summary": "Add a new pet to the store",
+ "description": "",
+ "operationId": "addPet",
+ "consumes": [
+ "application/json",
+ "application/xml"
+ ],
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "in": "body",
+ "name": "body",
+ "description": "Pet object that
needs to be added to the store",
+ "required": true,
+ "schema": {
+ "$ref":
"#/definitions/Pet"
+ }
+ }
+ ],
+ "responses": {
+ "405": {
+ "description": "Invalid input"
+ }
+ },
+ "security": [
+ {
+ "petstore_auth": [
+ "write:pets",
+ "read:pets"
+ ]
+ }
+ ]
+ },
+ "put": {
+ "tags": [
+ "pet"
+ ],
+ "summary": "Update an existing pet",
+ "description": "",
+ "operationId": "updatePet",
+ "consumes": [
+ "application/json",
+ "application/xml"
+ ],
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "in": "body",
+ "name": "body",
+ "description": "Pet object that
needs to be added to the store",
+ "required": true,
+ "schema": {
+ "$ref":
"#/definitions/Pet"
+ }
+ }
+ ],
+ "responses": {
+ "400": {
+ "description": "Invalid ID
supplied"
+ },
+ "404": {
+ "description": "Pet not found"
+ },
+ "405": {
+ "description": "Validation
exception"
+ }
+ },
+ "security": [
+ {
+ "petstore_auth": [
+ "write:pets",
+ "read:pets"
+ ]
+ }
+ ]
+ }
+ },
+ "/pet/findByStatus": {
+ "get": {
+ "tags": [
+ "pet"
+ ],
+ "summary": "Finds Pets by status",
+ "description": "Multiple status values can be
provided with comma separated strings",
+ "operationId": "findPetsByStatus",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "status",
+ "in": "query",
+ "description": "Status values
that need to be considered for filter",
+ "required": true,
+ "type": "array",
+ "items": {
+ "type": "string",
+ "enum": [
+ "available",
+ "pending",
+ "sold"
+ ],
+ "default": "available"
+ },
+ "collectionFormat": "multi"
+ }
+ ],
+ "responses": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "type": "array",
+ "items": {
+ "$ref":
"#/definitions/Pet"
+ }
+ }
+ },
+ "400": {
+ "description": "Invalid status
value"
+ }
+ },
+ "security": [
+ {
+ "petstore_auth": [
+ "write:pets",
+ "read:pets"
+ ]
+ }
+ ]
+ }
+ },
+ "/pet/findByTags": {
+ "get": {
+ "tags": [
+ "pet"
+ ],
+ "summary": "Finds Pets by tags",
+ "description": "Muliple tags can be provided
with comma separated strings. Use tag1, tag2, tag3 for testing.",
+ "operationId": "findPetsByTags",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "tags",
+ "in": "query",
+ "description": "Tags to filter
by",
+ "required": true,
+ "type": "array",
+ "items": {
+ "type": "string"
+ },
+ "collectionFormat": "multi"
+ }
+ ],
+ "responses": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "type": "array",
+ "items": {
+ "$ref":
"#/definitions/Pet"
+ }
+ }
+ },
+ "400": {
+ "description": "Invalid tag
value"
+ }
+ },
+ "security": [
+ {
+ "petstore_auth": [
+ "write:pets",
+ "read:pets"
+ ]
+ }
+ ],
+ "deprecated": true
+ }
+ },
+ "/pet/{petId}": {
+ "get": {
+ "tags": [
+ "pet"
+ ],
+ "summary": "Find pet by ID",
+ "description": "Returns a single pet",
+ "operationId": "getPetById",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "petId",
+ "in": "path",
+ "description": "ID of pet to
return",
+ "required": true,
+ "type": "integer",
+ "format": "int64"
+ }
+ ],
+ "responses": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "$ref":
"#/definitions/Pet"
+ }
+ },
+ "400": {
+ "description": "Invalid ID
supplied"
+ },
+ "404": {
+ "description": "Pet not found"
+ }
+ },
+ "security": [
+ {
+ "api_key": []
+ }
+ ]
+ },
+ "post": {
+ "tags": [
+ "pet"
+ ],
+ "summary": "Updates a pet in the store with
form data",
+ "description": "",
+ "operationId": "updatePetWithForm",
+ "consumes": [
+ "application/x-www-form-urlencoded"
+ ],
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "petId",
+ "in": "path",
+ "description": "ID of pet that
needs to be updated",
+ "required": true,
+ "type": "integer",
+ "format": "int64"
+ },
+ {
+ "name": "name",
+ "in": "formData",
+ "description": "Updated name of
the pet",
+ "required": false,
+ "type": "string"
+ },
+ {
+ "name": "status",
+ "in": "formData",
+ "description": "Updated status
of the pet",
+ "required": false,
+ "type": "string"
+ }
+ ],
+ "responses": {
+ "405": {
+ "description": "Invalid input"
+ }
+ },
+ "security": [
+ {
+ "petstore_auth": [
+ "write:pets",
+ "read:pets"
+ ]
+ }
+ ]
+ },
+ "delete": {
+ "tags": [
+ "pet"
+ ],
+ "summary": "Deletes a pet",
+ "description": "",
+ "operationId": "deletePet",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "api_key",
+ "in": "header",
+ "required": false,
+ "type": "string"
+ },
+ {
+ "name": "petId",
+ "in": "path",
+ "description": "Pet id to
delete",
+ "required": true,
+ "type": "integer",
+ "format": "int64"
+ }
+ ],
+ "responses": {
+ "400": {
+ "description": "Invalid ID
supplied"
+ },
+ "404": {
+ "description": "Pet not found"
+ }
+ },
+ "security": [
+ {
+ "petstore_auth": [
+ "write:pets",
+ "read:pets"
+ ]
+ }
+ ]
+ }
+ },
+ "/pet/{petId}/uploadImage": {
+ "post": {
+ "tags": [
+ "pet"
+ ],
+ "summary": "uploads an image",
+ "description": "",
+ "operationId": "uploadFile",
+ "consumes": [
+ "multipart/form-data"
+ ],
+ "produces": [
+ "application/json"
+ ],
+ "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": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "$ref":
"#/definitions/ApiResponse"
+ }
+ }
+ },
+ "security": [
+ {
+ "petstore_auth": [
+ "write:pets",
+ "read:pets"
+ ]
+ }
+ ]
+ }
+ },
+ "/store/inventory": {
+ "get": {
+ "tags": [
+ "store"
+ ],
+ "summary": "Returns pet inventories by status",
+ "description": "Returns a map of status codes
to quantities",
+ "operationId": "getInventory",
+ "produces": [
+ "application/json"
+ ],
+ "parameters": [],
+ "responses": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "type": "object",
+ "additionalProperties":
{
+ "type":
"integer",
+ "format":
"int32"
+ }
+ }
+ }
+ },
+ "security": [
+ {
+ "api_key": []
+ }
+ ]
+ }
+ },
+ "/store/order": {
+ "post": {
+ "tags": [
+ "store"
+ ],
+ "summary": "Place an order for a pet",
+ "description": "",
+ "operationId": "placeOrder",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "in": "body",
+ "name": "body",
+ "description": "order placed
for purchasing the pet",
+ "required": true,
+ "schema": {
+ "$ref":
"#/definitions/Order"
+ }
+ }
+ ],
+ "responses": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "$ref":
"#/definitions/Order"
+ }
+ },
+ "400": {
+ "description": "Invalid Order"
+ }
+ }
+ }
+ },
+ "/store/order/{orderId}": {
+ "get": {
+ "tags": [
+ "store"
+ ],
+ "summary": "Find purchase order by ID",
+ "description": "For valid response try integer
IDs with value >= 1 and <= 10. Other values will generated exceptions",
+ "operationId": "getOrderById",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "orderId",
+ "in": "path",
+ "description": "ID of pet that
needs to be fetched",
+ "required": true,
+ "type": "integer",
+ "maximum": 10.0,
+ "minimum": 1.0,
+ "format": "int64"
+ }
+ ],
+ "responses": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "$ref":
"#/definitions/Order"
+ }
+ },
+ "400": {
+ "description": "Invalid ID
supplied"
+ },
+ "404": {
+ "description": "Order not found"
+ }
+ }
+ },
+ "delete": {
+ "tags": [
+ "store"
+ ],
+ "summary": "Delete purchase order by ID",
+ "description": "For valid response try integer
IDs with positive integer value. Negative or non-integer values will generate
API errors",
+ "operationId": "deleteOrder",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "orderId",
+ "in": "path",
+ "description": "ID of the order
that needs to be deleted",
+ "required": true,
+ "type": "integer",
+ "minimum": 1.0,
+ "format": "int64"
+ }
+ ],
+ "responses": {
+ "400": {
+ "description": "Invalid ID
supplied"
+ },
+ "404": {
+ "description": "Order not found"
+ }
+ }
+ }
+ },
+ "/user": {
+ "post": {
+ "tags": [
+ "user"
+ ],
+ "summary": "Create user",
+ "description": "This can only be done by the
logged in user.",
+ "operationId": "createUser",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "in": "body",
+ "name": "body",
+ "description": "Created user
object",
+ "required": true,
+ "schema": {
+ "$ref":
"#/definitions/User"
+ }
+ }
+ ],
+ "responses": {
+ "default": {
+ "description": "successful
operation"
+ }
+ }
+ }
+ },
+ "/user/createWithArray": {
+ "post": {
+ "tags": [
+ "user"
+ ],
+ "summary": "Creates list of users with given
input array",
+ "description": "",
+ "operationId": "createUsersWithArrayInput",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "in": "body",
+ "name": "body",
+ "description": "List of user
object",
+ "required": true,
+ "schema": {
+ "type": "array",
+ "items": {
+ "$ref":
"#/definitions/User"
+ }
+ }
+ }
+ ],
+ "responses": {
+ "default": {
+ "description": "successful
operation"
+ }
+ }
+ }
+ },
+ "/user/createWithList": {
+ "post": {
+ "tags": [
+ "user"
+ ],
+ "summary": "Creates list of users with given
input array",
+ "description": "",
+ "operationId": "createUsersWithListInput",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "in": "body",
+ "name": "body",
+ "description": "List of user
object",
+ "required": true,
+ "schema": {
+ "type": "array",
+ "items": {
+ "$ref":
"#/definitions/User"
+ }
+ }
+ }
+ ],
+ "responses": {
+ "default": {
+ "description": "successful
operation"
+ }
+ }
+ }
+ },
+ "/user/login": {
+ "get": {
+ "tags": [
+ "user"
+ ],
+ "summary": "Logs user into the system",
+ "description": "",
+ "operationId": "loginUser",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "username",
+ "in": "query",
+ "description": "The user name
for login",
+ "required": true,
+ "type": "string"
+ },
+ {
+ "name": "password",
+ "in": "query",
+ "description": "The password
for login in clear text",
+ "required": true,
+ "type": "string"
+ }
+ ],
+ "responses": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "type": "string"
+ },
+ "headers": {
+ "X-Rate-Limit": {
+ "type":
"integer",
+ "format":
"int32",
+ "description":
"calls per hour allowed by the user"
+ },
+ "X-Expires-After": {
+ "type":
"string",
+ "format":
"date-time",
+ "description":
"date in UTC when token expires"
+ }
+ }
+ },
+ "400": {
+ "description": "Invalid
username/password supplied"
+ }
+ }
+ }
+ },
+ "/user/logout": {
+ "get": {
+ "tags": [
+ "user"
+ ],
+ "summary": "Logs out current logged in user
session",
+ "description": "",
+ "operationId": "logoutUser",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [],
+ "responses": {
+ "default": {
+ "description": "successful
operation"
+ }
+ }
+ }
+ },
+ "/user/{username}": {
+ "get": {
+ "tags": [
+ "user"
+ ],
+ "summary": "Get user by user name",
+ "description": "",
+ "operationId": "getUserByName",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "username",
+ "in": "path",
+ "description": "The name that
needs to be fetched. Use user1 for testing. ",
+ "required": true,
+ "type": "string"
+ }
+ ],
+ "responses": {
+ "200": {
+ "description": "successful
operation",
+ "schema": {
+ "$ref":
"#/definitions/User"
+ }
+ },
+ "400": {
+ "description": "Invalid
username supplied"
+ },
+ "404": {
+ "description": "User not found"
+ }
+ }
+ },
+ "put": {
+ "tags": [
+ "user"
+ ],
+ "summary": "Updated user",
+ "description": "This can only be done by the
logged in user.",
+ "operationId": "updateUser",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "username",
+ "in": "path",
+ "description": "name that need
to be updated",
+ "required": true,
+ "type": "string"
+ },
+ {
+ "in": "body",
+ "name": "body",
+ "description": "Updated user
object",
+ "required": true,
+ "schema": {
+ "$ref":
"#/definitions/User"
+ }
+ }
+ ],
+ "responses": {
+ "400": {
+ "description": "Invalid user
supplied"
+ },
+ "404": {
+ "description": "User not found"
+ }
+ }
+ },
+ "delete": {
+ "tags": [
+ "user"
+ ],
+ "summary": "Delete user",
+ "description": "This can only be done by the
logged in user.",
+ "operationId": "deleteUser",
+ "produces": [
+ "application/xml",
+ "application/json"
+ ],
+ "parameters": [
+ {
+ "name": "username",
+ "in": "path",
+ "description": "The name that
needs to be deleted",
+ "required": true,
+ "type": "string"
+ }
+ ],
+ "responses": {
+ "400": {
+ "description": "Invalid
username supplied"
+ },
+ "404": {
+ "description": "User not found"
+ }
+ }
+ }
+ }
+ },
+ "securityDefinitions": {
+ "petstore_auth": {
+ "type": "oauth2",
+ "authorizationUrl":
"http://petstore.swagger.io/oauth/dialog",
+ "flow": "implicit",
+ "scopes": {
+ "write:pets": "modify pets in your account",
+ "read:pets": "read your pets"
+ }
+ },
+ "api_key": {
+ "type": "apiKey",
+ "name": "api_key",
+ "in": "header"
+ }
+ },
+ "definitions": {
+ "Order": {
+ "type": "object",
+ "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",
+ "default": false
+ }
+ },
+ "xml": {
+ "name": "Order"
+ }
+ },
+ "User": {
+ "type": "object",
+ "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": {
+ "type": "object",
+ "properties": {
+ "id": {
+ "type": "integer",
+ "format": "int64"
+ },
+ "name": {
+ "type": "string"
+ }
+ },
+ "xml": {
+ "name": "Category"
+ }
+ },
+ "Tag": {
+ "type": "object",
+ "properties": {
+ "id": {
+ "type": "integer",
+ "format": "int64"
+ },
+ "name": {
+ "type": "string"
+ }
+ },
+ "xml": {
+ "name": "Tag"
+ }
+ },
+ "Pet": {
+ "type": "object",
+ "required": [
+ "name",
+ "photoUrls"
+ ],
+ "properties": {
+ "id": {
+ "type": "integer",
+ "format": "int64"
+ },
+ "category": {
+ "$ref": "#/definitions/Category"
+ },
+ "name": {
+ "type": "string",
+ "example": "doggie"
+ },
+ "photoUrls": {
+ "type": "array",
+ "xml": {
+ "name": "photoUrl",
+ "wrapped": true
+ },
+ "items": {
+ "type": "string"
+ }
+ },
+ "tags": {
+ "type": "array",
+ "xml": {
+ "name": "tag",
+ "wrapped": true
+ },
+ "items": {
+ "$ref": "#/definitions/Tag"
+ }
+ },
+ "status": {
+ "type": "string",
+ "description": "pet status in the
store",
+ "enum": [
+ "available",
+ "pending",
+ "sold"
+ ]
+ }
+ },
+ "xml": {
+ "name": "Pet"
+ },
+ "x-examples": {
+ "model": "{foo:}",
+ "application/json": "{foo:'bar'}",
+ "text/xml": "<foo>bar</foo>",
+ "text/html": "<table>foo</table>",
+ "octal-messagepack": "123456ABCDEF"
+ },
+ },
+ "ApiResponse": {
+ "type": "object",
+ "properties": {
+ "code": {
+ "type": "integer",
+ "format": "int32"
+ },
+ "type": {
+ "type": "string"
+ },
+ "message": {
+ "type": "string"
+ }
+ }
+ }
+ },
+ "externalDocs": {
+ "description": "Find out more about Swagger",
+ "url": "http://swagger.io"
+ }
+}
\ No newline at end of file
diff --git
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContext.java
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContext.java
index 73cb895..f2be599 100644
---
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContext.java
+++
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContext.java
@@ -3534,7 +3534,7 @@ public final class RestContext extends BeanContext {
return p.parse(in, c);
}
} catch (ParseException e) {
- throw new ServletException("Could not
parse resource '' as media type '"+mediaType+"'.");
+ throw new ServletException("Could not
parse resource '"+name+" as media type '"+mediaType+"'.", e);
}
}
throw new ServletException("Unknown media type
'"+mediaType+"'");
--
To stop receiving notification emails like this one, please contact
[email protected].