use of io.swagger.v3.parser.ResolverCache in project swagger-parser by swagger-api.
the class ResolverCacheTest method testLoadExternalRefResponseWithNoContent.
@Test
public void testLoadExternalRefResponseWithNoContent() throws Exception {
final RefFormat format = RefFormat.URL;
final String ref = "http://my.company.com/path/to/main.yaml";
final String contentsOfExternalFile = "openapi: 3.0.0\n" + "\n" + "info:\n" + " version: 1.0.0\n" + " title: Response include test case child\n" + "\n" + "components:\n" + " responses:\n" + " 200:\n" + " description: Success\n";
new Expectations() {
{
RefUtils.readExternalUrlRef(ref, format, auths, "http://my.company.com/path/parent.json");
times = 1;
result = contentsOfExternalFile;
}
};
ResolverCache cache = new ResolverCache(openAPI, auths, "http://my.company.com/path/parent.json");
ApiResponse response = cache.loadRef(ref + "#/components/responses/200", RefFormat.URL, ApiResponse.class);
assertNotNull(response);
assertEquals(response.getDescription(), "Success");
assertNull(response.getContent());
}
use of io.swagger.v3.parser.ResolverCache in project swagger-parser by swagger-api.
the class ResolverCacheTest method testLoadInternalResponseRefWithSpaces.
@Test
public void testLoadInternalResponseRefWithSpaces(@Injectable ApiResponse mockedResponse) throws Exception {
OpenAPI openAPI = new OpenAPI();
openAPI.components(new Components().addResponses("foo bar", mockedResponse));
ResolverCache cache = new ResolverCache(openAPI, auths, null);
ApiResponse actualResult = cache.loadRef("#/components/responses/foo bar", RefFormat.INTERNAL, ApiResponse.class);
assertEquals(actualResult, mockedResponse);
}
use of io.swagger.v3.parser.ResolverCache in project swagger-parser by swagger-api.
the class OpenAPIDeserializer method getSchema.
public Schema getSchema(ObjectNode node, String location, ParseResult result) {
if (node == null) {
return null;
}
// Added to handle NPE from ResolverCache when Trying to dereference a schema
if (result == null) {
result = new ParseResult();
result.setAllowEmptyStrings(true);
}
Schema schema = null;
ArrayNode oneOfArray = getArray("oneOf", node, false, location, result);
ArrayNode allOfArray = getArray("allOf", node, false, location, result);
ArrayNode anyOfArray = getArray("anyOf", node, false, location, result);
ObjectNode itemsNode = getObject("items", node, false, location, result);
if ((allOfArray != null) || (anyOfArray != null) || (oneOfArray != null)) {
ComposedSchema composedSchema = new ComposedSchema();
if (allOfArray != null) {
for (JsonNode n : allOfArray) {
if (n.isObject()) {
schema = getSchema((ObjectNode) n, location, result);
composedSchema.addAllOfItem(schema);
}
}
schema = composedSchema;
}
if (anyOfArray != null) {
for (JsonNode n : anyOfArray) {
if (n.isObject()) {
schema = getSchema((ObjectNode) n, location, result);
composedSchema.addAnyOfItem(schema);
}
}
schema = composedSchema;
}
if (oneOfArray != null) {
for (JsonNode n : oneOfArray) {
if (n.isObject()) {
schema = getSchema((ObjectNode) n, location, result);
composedSchema.addOneOfItem(schema);
}
}
schema = composedSchema;
}
}
if (itemsNode != null) {
ArraySchema items = new ArraySchema();
if (itemsNode.getNodeType().equals(JsonNodeType.OBJECT)) {
items.setItems(getSchema(itemsNode, location, result));
} else if (itemsNode.getNodeType().equals(JsonNodeType.ARRAY)) {
for (JsonNode n : itemsNode) {
if (n.isValueNode()) {
items.setItems(getSchema(itemsNode, location, result));
}
}
}
schema = items;
}
Boolean additionalPropertiesBoolean = getBoolean("additionalProperties", node, false, location, result);
ObjectNode additionalPropertiesObject = additionalPropertiesBoolean == null ? getObject("additionalProperties", node, false, location, result) : null;
Object additionalProperties = additionalPropertiesObject != null ? getSchema(additionalPropertiesObject, location, result) : additionalPropertiesBoolean;
if (additionalProperties != null) {
if (schema == null) {
schema = additionalProperties.equals(Boolean.FALSE) ? new ObjectSchema() : new MapSchema();
}
schema.setAdditionalProperties(additionalProperties);
}
if (schema == null) {
schema = SchemaTypeUtil.createSchemaByType(node);
}
JsonNode ref = node.get("$ref");
if (ref != null) {
if (ref.getNodeType().equals(JsonNodeType.STRING)) {
if (location.startsWith("paths")) {
try {
String[] components = ref.asText().split("#/components");
if ((ref.asText().startsWith("#/components")) && (components.length > 1)) {
String[] childComponents = components[1].split("/");
String[] newChildComponents = Arrays.copyOfRange(childComponents, 1, childComponents.length);
boolean isValidComponent = ReferenceValidator.valueOf(newChildComponents[0]).validateComponent(this.components, newChildComponents[1]);
if (!isValidComponent) {
result.missing(location, ref.asText());
}
}
} catch (Exception e) {
result.missing(location, ref.asText());
}
}
String mungedRef = mungedRef(ref.textValue());
if (mungedRef != null) {
schema.set$ref(mungedRef);
} else {
schema.set$ref(ref.asText());
}
return schema;
} else {
result.invalidType(location, "$ref", "string", node);
return null;
}
}
String value = getString("title", node, false, location, result);
if ((result.isAllowEmptyStrings() && value != null) || (!result.isAllowEmptyStrings() && !StringUtils.isBlank(value))) {
schema.setTitle(value);
}
ObjectNode discriminatorNode = getObject("discriminator", node, false, location, result);
if (discriminatorNode != null) {
schema.setDiscriminator(getDiscriminator(discriminatorNode, location, result));
}
BigDecimal bigDecimal = getBigDecimal("multipleOf", node, false, location, result);
if (bigDecimal != null) {
if (bigDecimal.compareTo(BigDecimal.ZERO) > 0) {
schema.setMultipleOf(bigDecimal);
} else {
result.warning(location, "multipleOf value must be > 0");
}
}
bigDecimal = getBigDecimal("maximum", node, false, location, result);
if (bigDecimal != null) {
schema.setMaximum(bigDecimal);
}
Boolean bool = getBoolean("exclusiveMaximum", node, false, location, result);
if (bool != null) {
schema.setExclusiveMaximum(bool);
}
bigDecimal = getBigDecimal("minimum", node, false, location, result);
if (bigDecimal != null) {
schema.setMinimum(bigDecimal);
}
bool = getBoolean("exclusiveMinimum", node, false, location, result);
if (bool != null) {
schema.setExclusiveMinimum(bool);
}
Integer integer = getInteger("minLength", node, false, location, result);
if (integer != null) {
schema.setMinLength(integer);
}
integer = getInteger("maxLength", node, false, location, result);
if (integer != null) {
schema.setMaxLength(integer);
}
String pattern = getString("pattern", node, false, location, result);
if (result.isAllowEmptyStrings() && pattern != null) {
schema.setPattern(pattern);
}
integer = getInteger("maxItems", node, false, location, result);
if (integer != null) {
schema.setMaxItems(integer);
}
integer = getInteger("minItems", node, false, location, result);
if (integer != null) {
schema.setMinItems(integer);
}
bool = getBoolean("uniqueItems", node, false, location, result);
if (bool != null) {
schema.setUniqueItems(bool);
}
integer = getInteger("maxProperties", node, false, location, result);
if (integer != null) {
schema.setMaxProperties(integer);
}
integer = getInteger("minProperties", node, false, location, result);
if (integer != null) {
schema.setMinProperties(integer);
}
ArrayNode required = getArray("required", node, false, location, result);
if (required != null) {
List<String> requiredList = new ArrayList<>();
for (JsonNode n : required) {
if (n.getNodeType().equals(JsonNodeType.STRING)) {
requiredList.add(((TextNode) n).textValue());
} else {
result.invalidType(location, "required", "string", n);
}
}
if (requiredList.size() > 0) {
schema.setRequired(requiredList);
}
}
ArrayNode enumArray = getArray("enum", node, false, location, result);
if (enumArray != null) {
for (JsonNode n : enumArray) {
if (n.isNumber()) {
schema.addEnumItemObject(n.numberValue());
} else if (n.isBoolean()) {
schema.addEnumItemObject(n.booleanValue());
} else if (n.isValueNode()) {
try {
schema.addEnumItemObject(getDecodedObject(schema, n.asText(null)));
} catch (ParseException e) {
result.invalidType(location, String.format("enum=`%s`", e.getMessage()), schema.getFormat(), n);
}
} else if (n.isContainerNode()) {
schema.addEnumItemObject(n.isNull() ? null : n);
} else {
result.invalidType(location, "enum", "value", n);
}
}
}
value = getString("type", node, false, location, result);
if (StringUtils.isBlank(schema.getType())) {
if ((result.isAllowEmptyStrings() && value != null) || (!result.isAllowEmptyStrings() && !StringUtils.isBlank(value))) {
schema.setType(value);
} else {
// may have an enum where type can be inferred
JsonNode enumNode = node.get("enum");
if (enumNode != null && enumNode.isArray()) {
String type = inferTypeFromArray((ArrayNode) enumNode);
schema.setType(type);
}
}
if ("array".equals(schema.getType()) && !(schema instanceof ArraySchema && ((ArraySchema) schema).getItems() != null)) {
result.missing(location, "items");
}
}
ObjectNode notObj = getObject("not", node, false, location, result);
if (notObj != null) {
Schema not = getSchema(notObj, location, result);
if (not != null) {
schema.setNot(not);
}
}
Map<String, Schema> properties = new LinkedHashMap<>();
ObjectNode propertiesObj = getObject("properties", node, false, location, result);
Schema property = null;
Set<String> keys = getKeys(propertiesObj);
for (String name : keys) {
JsonNode propertyValue = propertiesObj.get(name);
if (!propertyValue.getNodeType().equals(JsonNodeType.OBJECT)) {
result.invalidType(location, "properties", "object", propertyValue);
} else {
if (propertiesObj != null) {
property = getSchema((ObjectNode) propertyValue, location, result);
if (property != null) {
properties.put(name, property);
}
}
}
}
if (propertiesObj != null) {
schema.setProperties(properties);
}
value = getString("description", node, false, location, result);
if ((result.isAllowEmptyStrings() && value != null) || (!result.isAllowEmptyStrings() && !StringUtils.isBlank(value))) {
schema.setDescription(value);
}
value = getString("format", node, false, location, result);
if ((result.isAllowEmptyStrings() && value != null) || (!result.isAllowEmptyStrings() && !StringUtils.isBlank(value))) {
schema.setFormat(value);
}
// sets default value according to the schema type
if (node.get("default") != null) {
if (!StringUtils.isBlank(schema.getType())) {
if (schema.getType().equals("array")) {
ArrayNode array = getArray("default", node, false, location, result);
if (array != null) {
schema.setDefault(array);
}
} else if (schema.getType().equals("string")) {
value = getString("default", node, false, location, result);
if ((result.isAllowEmptyStrings() && value != null) || (!result.isAllowEmptyStrings() && !StringUtils.isBlank(value))) {
try {
schema.setDefault(getDecodedObject(schema, value));
} catch (ParseException e) {
result.invalidType(location, String.format("default=`%s`", e.getMessage()), schema.getFormat(), node);
}
}
} else if (schema.getType().equals("boolean")) {
bool = getBoolean("default", node, false, location, result);
if (bool != null) {
schema.setDefault(bool);
}
} else if (schema.getType().equals("object")) {
Object object = getObject("default", node, false, location, result);
if (object != null) {
schema.setDefault(object);
}
} else if (schema.getType().equals("integer")) {
Integer number = getInteger("default", node, false, location, result);
if (number != null) {
schema.setDefault(number);
}
} else if (schema.getType().equals("number")) {
BigDecimal number = getBigDecimal("default", node, false, location, result);
if (number != null) {
schema.setDefault(number);
}
}
}
}
bool = getBoolean("nullable", node, false, location, result);
if (bool != null) {
schema.setNullable(bool);
}
bool = getBoolean("readOnly", node, false, location, result);
if (bool != null) {
schema.setReadOnly(bool);
}
bool = getBoolean("writeOnly", node, false, location, result);
if (bool != null) {
schema.setWriteOnly(bool);
}
bool = Optional.ofNullable(getBoolean("writeOnly", node, false, location, result)).orElse(false) && Optional.ofNullable(getBoolean("readOnly", node, false, location, result)).orElse(false);
if (bool == true) {
result.warning(location, " writeOnly and readOnly are both present");
}
ObjectNode xmlNode = getObject("xml", node, false, location, result);
if (xmlNode != null) {
XML xml = getXml(xmlNode, location, result);
if (xml != null) {
schema.setXml(xml);
}
}
ObjectNode externalDocs = getObject("externalDocs", node, false, location, result);
if (externalDocs != null) {
ExternalDocumentation docs = getExternalDocs(externalDocs, location, result);
if (docs != null) {
schema.setExternalDocs(docs);
}
}
Object example = getAnyExample("example", node, location, result);
if (example != null) {
schema.setExample(example instanceof NullNode ? null : example);
}
bool = getBoolean("deprecated", node, false, location, result);
if (bool != null) {
schema.setDeprecated(bool);
}
Map<String, Object> extensions = getExtensions(node);
if (extensions != null && extensions.size() > 0) {
schema.setExtensions(extensions);
}
Set<String> schemaKeys = getKeys(node);
for (String key : schemaKeys) {
if (!SCHEMA_KEYS.contains(key) && !key.startsWith("x-")) {
result.extra(location, key, node.get(key));
}
}
return schema;
}
use of io.swagger.v3.parser.ResolverCache in project swagger-parser by swagger-api.
the class ExternalRefProcessorTest method testRelativeRefIncludingUrlRef.
@Test
public void testRelativeRefIncludingUrlRef(@Injectable final Schema mockedModel) throws Exception {
final RefFormat refFormat = RefFormat.RELATIVE;
final String url = "https://my.example.remote.url.com/globals.yaml";
final String expectedResult = "components:\n" + " schemas:\n" + " link-object:\n" + " type: object\n" + " additionalProperties:\n" + " \"$ref\": \"#/components/schemas/rel-data\"\n" + " rel-data:\n" + " type: object\n" + " required:\n" + " - href\n" + " properties:\n" + " href:\n" + " type: string\n" + " note:\n" + " type: string\n" + " result:\n" + " type: object\n" + " properties:\n" + " name:\n" + " type: string\n" + " _links:\n" + " \"$ref\": \"#/components/schemas/link-object\"\n" + "";
List<AuthorizationValue> auths = null;
new Expectations() {
{
RemoteUrl.urlToString(url, auths);
times = 1;
result = expectedResult;
}
};
OpenAPI mockedOpenAPI = new OpenAPI();
mockedOpenAPI.setComponents(new Components());
mockedOpenAPI.getComponents().setSchemas(new HashMap<>());
ResolverCache mockedResolverCache = new ResolverCache(mockedOpenAPI, null, null);
ExternalRefProcessor processor = new ExternalRefProcessor(mockedResolverCache, mockedOpenAPI);
processor.processRefToExternalSchema("./relative-with-url/relative-with-url.yaml#/relative-with-url", refFormat);
assertThat(((Schema) mockedOpenAPI.getComponents().getSchemas().get("relative-with-url").getProperties().get("Foo")).get$ref(), is("https://my.example.remote.url.com/globals.yaml#/components/schemas/link-object"));
assertThat(mockedOpenAPI.getComponents().getSchemas().keySet().contains("link-object"), is(true));
assertThat(mockedOpenAPI.getComponents().getSchemas().keySet().contains("rel-data"), is(true));
// assert that ref is relative ref is resolved. and the file path is from root yaml file.
assertThat(((Schema) mockedOpenAPI.getComponents().getSchemas().get("relative-with-url").getProperties().get("Bar")).get$ref(), is("./relative-with-url/relative-with-local.yaml#/relative-same-file"));
}
use of io.swagger.v3.parser.ResolverCache in project swagger-parser by swagger-api.
the class ComponentsProcessorTest method testDefinitionsProcessor_RefModelInDefinitionsMap.
@Test
public void testDefinitionsProcessor_RefModelInDefinitionsMap(@Injectable final Schema resolvedModel) throws Exception {
final OpenAPI openAPI = new OpenAPI();
final String ref = "http://my.company.com/path/to/file.json#/foo/bar";
final Schema refModel = new Schema().$ref(ref);
openAPI.components(new Components().addSchemas("foo", refModel));
final MockUp<ResolverCache> mockup = new MockUp<ResolverCache>() {
@Mock
String getRenamedRef(String ref) {
openAPI.getComponents().getSchemas().put("bar", resolvedModel);
return "bar";
}
};
final ResolverCache mockResolverCache = mockup.getMockInstance();
new StrictExpectations() {
{
new SchemaProcessor(mockResolverCache, openAPI);
times = 1;
result = schemaProcessor;
new ResponseProcessor(mockResolverCache, openAPI);
times = 1;
result = responseProcessor;
new RequestBodyProcessor(mockResolverCache, openAPI);
times = 1;
result = requestBodyProcessor;
new ParameterProcessor(mockResolverCache, openAPI);
times = 1;
result = parameterProcessor;
new HeaderProcessor(mockResolverCache, openAPI);
times = 1;
result = headerProcessor;
new ExampleProcessor(mockResolverCache, openAPI);
times = 1;
result = exampleProcessor;
new LinkProcessor(mockResolverCache, openAPI);
times = 1;
result = linkProcessor;
new CallbackProcessor(mockResolverCache, openAPI);
times = 1;
result = callbackProcessor;
new SecuritySchemeProcessor(mockResolverCache, openAPI);
times = 1;
result = securitySchemeProcessor;
schemaProcessor.processSchema(refModel);
times = 1;
resolvedModel.getProperties();
times = 1;
}
};
new ComponentsProcessor(openAPI, mockResolverCache).processComponents();
new FullVerifications() {
{
}
};
final Map<String, Schema> definitions = openAPI.getComponents().getSchemas();
assertEquals(definitions.size(), 1);
final Schema foo = definitions.get("foo");
assertEquals(foo, resolvedModel);
}
Aggregations