Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add DurationSchema for java.time.Duration as PrimitiveType #4821

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
import io.swagger.v3.oas.models.media.ComposedSchema;
import io.swagger.v3.oas.models.media.DateSchema;
import io.swagger.v3.oas.models.media.DateTimeSchema;
import io.swagger.v3.oas.models.media.DurationSchema;
import io.swagger.v3.oas.models.media.EmailSchema;
import io.swagger.v3.oas.models.media.IntegerSchema;
import io.swagger.v3.oas.models.media.JsonSchema;
Expand Down Expand Up @@ -75,6 +76,8 @@ public Schema deserialize(JsonParser jp, DeserializationContext ctxt)
schema = Json.mapper().convertValue(node, DateSchema.class);
} else if ("date-time".equals(format)) {
schema = Json.mapper().convertValue(node, DateTimeSchema.class);
} else if ("duration".equals(format)) {
schema = Json.mapper().convertValue(node, DurationSchema.class);
} else if ("email".equals(format)) {
schema = Json.mapper().convertValue(node, EmailSchema.class);
} else if ("password".equals(format)) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
import io.swagger.v3.oas.models.media.ByteArraySchema;
import io.swagger.v3.oas.models.media.DateSchema;
import io.swagger.v3.oas.models.media.DateTimeSchema;
import io.swagger.v3.oas.models.media.DurationSchema;
import io.swagger.v3.oas.models.media.FileSchema;
import io.swagger.v3.oas.models.media.IntegerSchema;
import io.swagger.v3.oas.models.media.NumberSchema;
Expand Down Expand Up @@ -141,6 +142,12 @@ public DateTimeSchema createProperty() {
return new DateTimeSchema();
}
},
DURATION(java.time.Duration.class, "duration") {
@Override
public DurationSchema createProperty() {
return new DurationSchema();
}
},
PARTIAL_TIME(java.time.LocalTime.class, "partial-time") {
@Override
public Schema createProperty() {
Expand Down Expand Up @@ -231,6 +238,7 @@ public Schema createProperty() {
dms.put("string_uuid", "uuid");
dms.put("string_date", "date");
dms.put("string_date-time", "date-time");
dms.put("string_duration", "duration");
dms.put("string_partial-time", "partial-time");
dms.put("string_password", "password");
dms.put("boolean_", "boolean");
Expand Down Expand Up @@ -277,6 +285,7 @@ public Schema createProperty() {
"org.joda.time.ReadableDateTime",
"org.joda.time.DateTime",
"java.time.Instant");
addKeys(externalClasses, DURATION, "org.joda.time.Duration", "java.time.Duration");
EXTERNAL_CLASSES = Collections.unmodifiableMap(externalClasses);

final Map<String, PrimitiveType> names = new TreeMap<>(String.CASE_INSENSITIVE_ORDER);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package io.swagger.v3.core.resolving;

import io.swagger.v3.core.converter.ModelConverters;
import io.swagger.v3.oas.models.media.DurationSchema;
import io.swagger.v3.oas.models.media.Schema;
import org.joda.time.Duration;
import org.testng.annotations.Test;

import java.util.Map;

import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertTrue;

public class JodaDurationConverterTest {

@Test
public void testJodaDuration() {
final Map<String, Schema> models = ModelConverters.getInstance().read(ModelWithJodaDuration.class);
assertEquals(models.size(), 1);

final Schema model = models.get("ModelWithJodaDuration");

final Schema durationProperty = (Schema) model.getProperties().get("measuredDuration");
assertTrue(durationProperty instanceof DurationSchema);
assertTrue(model.getRequired().contains("measuredDuration"));
assertEquals(durationProperty.getDescription(), "Time something took to do");

}

class ModelWithJodaDuration {

@io.swagger.v3.oas.annotations.media.Schema(description = "Time something took to do", required = true)
public Duration measuredDuration;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
import io.swagger.v3.oas.models.media.ArraySchema;
import io.swagger.v3.oas.models.media.DateSchema;
import io.swagger.v3.oas.models.media.DateTimeSchema;
import io.swagger.v3.oas.models.media.DurationSchema;
import io.swagger.v3.oas.models.media.IntegerSchema;
import io.swagger.v3.oas.models.media.Schema;
import io.swagger.v3.oas.models.media.StringSchema;
Expand Down Expand Up @@ -41,6 +42,7 @@ public void convertModel() throws JsonProcessingException {
props.put("longValue", new IntegerSchema().format("int64"));
props.put("dateValue", new DateSchema());
props.put("dateTimeValue", new DateTimeSchema());
props.put("durationValue", new DurationSchema());
pet.setProperties(props);
pet.setRequired(Arrays.asList("intValue", "name"));
final String json = "{\n" +
Expand All @@ -63,6 +65,10 @@ public void convertModel() throws JsonProcessingException {
" \"dateTimeValue\":{\n" +
" \"type\":\"string\",\n" +
" \"format\":\"date-time\"\n" +
" },\n" +
" \"durationValue\":{\n" +
" \"type\":\"string\",\n" +
" \"format\":\"duration\"\n" +
" }\n" +
" }\n" +
"}";
Expand Down Expand Up @@ -91,6 +97,10 @@ public void deserializeModel() throws IOException {
" \"type\":\"string\",\n" +
" \"format\":\"date-time\"\n" +
" },\n" +
" \"durationValue\":{\n" +
" \"type\":\"string\",\n" +
" \"format\":\"duration\"\n" +
" },\n" +
" \"intValue\":{\n" +
" \"type\":\"integer\",\n" +
" \"format\":\"int32\"\n" +
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
import io.swagger.v3.oas.models.media.BooleanSchema;
import io.swagger.v3.oas.models.media.DateSchema;
import io.swagger.v3.oas.models.media.DateTimeSchema;
import io.swagger.v3.oas.models.media.DurationSchema;
import io.swagger.v3.oas.models.media.IntegerSchema;
import io.swagger.v3.oas.models.media.MapSchema;
import io.swagger.v3.oas.models.media.NumberSchema;
Expand Down Expand Up @@ -80,6 +81,23 @@ public void deserializeDateTimeProperty() throws IOException {
assertEquals(m.writeValueAsString(p), json);
}

@Test(description = "it should serialize a DateTimeProperty")
public void serializeDurationProperty() throws IOException {
final DurationSchema p = new DurationSchema();
final String json = "{\"type\":\"string\",\"format\":\"duration\"}";
assertEquals(m.writeValueAsString(p), json);
}

@Test(description = "it should deserialize a DateTimeProperty")
public void deserializeDurationProperty() throws IOException {
final String json = "{\"type\":\"string\",\"format\":\"duration\"}";
final Schema p = m.readValue(json, Schema.class);
assertEquals(p.getType(), "string");
assertEquals(p.getFormat(), "duration");
assertEquals(p.getClass(), DurationSchema.class);
assertEquals(m.writeValueAsString(p), json);
}

@Test(description = "it should serialize a DoubleProperty")
public void serializeDoubleProperty() throws IOException {
final NumberSchema p = new NumberSchema()
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
package io.swagger.v3.oas.models.media;

import java.time.Duration;
import java.util.Objects;

/**
* DurationSchema
*/

public class DurationSchema extends Schema<Duration> {

public DurationSchema() {
super("string", "duration");
}

@Override
public DurationSchema type(String type) {
super.setType(type);
return this;
}

@Override
public DurationSchema format(String format) {
super.setFormat(format);
return this;
}

@Override
public DurationSchema _default(Duration _default) {
super.setDefault(_default);
return this;
}

@Override
protected Duration cast(Object value) {
if (value != null) {
try {
if (value instanceof Duration) {
return (Duration) value;
} else if (value instanceof String) {
return Duration.parse((String)value);
}
} catch (Exception e) {
}
}
return null;
}

public DurationSchema addEnumItem(Duration _enumItem) {
super.addEnumItemObject(_enumItem);
return this;
}

@Override
public boolean equals(Object o) {
if (this == o) {
return true;
}
if (o == null || getClass() != o.getClass()) {
return false;
}
return super.equals(o);
}

@Override
public int hashCode() {
return Objects.hash(super.hashCode());
}

@Override
public String toString() {
StringBuilder sb = new StringBuilder();
sb.append("class DurationSchema {\n");
sb.append(" ").append(toIndentedString(super.toString())).append("\n");
sb.append("}");
return sb.toString();
}
}