1717package za .co .absa .springdocopenapiscala
1818
1919import io .swagger .v3 .oas .models .Components
20- import io .swagger .v3 .oas .models .media .{Discriminator , Schema }
20+ import io .swagger .v3 .oas .models .media .{ArraySchema , BooleanSchema , Discriminator , IntegerSchema , NumberSchema , ObjectSchema , Schema , StringSchema , UUIDSchema }
2121
2222import java .time .{Instant , LocalDate , LocalDateTime , LocalTime , ZonedDateTime }
2323import java .util .UUID
@@ -27,6 +27,7 @@ import scala.reflect.runtime.universe._
2727import OpenAPIModelRegistration ._
2828
2929import java .sql .Timestamp
30+ import scala .collection .Seq
3031
3132class OpenAPIModelRegistration (
3233 components : Components ,
@@ -69,8 +70,6 @@ class OpenAPIModelRegistration(
6970 handleType(tpe)
7071 }
7172
72- private case class OpenAPISimpleType (tpe : String , format : Option [String ] = None )
73-
7473 @ tailrec
7574 private def handleType (tpe : Type ): Schema [_] = {
7675 if (extraTypesHandler.isDefinedAt(tpe)) handleExtraTypes(tpe)
@@ -96,8 +95,7 @@ class OpenAPIModelRegistration(
9695
9796 private def handleCaseType (tpe : Type ): Schema [_] = {
9897 val name = tpe.typeSymbol.name.toString.trim
99- val schema = new Schema
100- schema.setType(" object" )
98+ val schema = new ObjectSchema
10199 val fields = tpe.decls.collect {
102100 case field : TermSymbol if field.isVal => field
103101 }
@@ -114,17 +112,15 @@ class OpenAPIModelRegistration(
114112
115113 private def handleMap (keyType : Type , valueType : Type ): Schema [_] = keyType match {
116114 case _ if keyType <:< typeOf[String ] =>
117- val schema = new Schema
118- schema.setType(" object" )
115+ val schema = new ObjectSchema
119116 schema.setAdditionalProperties(handleType(valueType))
120117 schema
121118 case _ => throw new IllegalArgumentException (" In OpenAPI 3.0.x Map must have String key type." )
122119 }
123120
124121 private def handleSeqLike (tpe : Type ): Schema [_] = {
125- val schema = new Schema
122+ val schema = new ArraySchema
126123 val innerSchema = handleType(tpe.typeArgs.head)
127- schema.setType(" array" )
128124 schema.setItems(innerSchema)
129125 schema
130126 }
@@ -139,8 +135,7 @@ class OpenAPIModelRegistration(
139135 val enumValues = parentObjectType.members.filter(isSymbolEnumerationValue)
140136 val enumValuesAsStrings = enumValues.map(_.name.toString.trim)
141137
142- val schema = new Schema [String ]
143- schema.setType(" string" )
138+ val schema = new StringSchema
144139 schema.setEnum(enumValuesAsStrings.toList.asJava)
145140 schema
146141 }
@@ -197,7 +192,7 @@ class OpenAPIModelRegistration(
197192 // - case objects = registered as reference
198193 // - sealed trait/abstract class = registered as reference
199194 val childrenRefs = children.map(s => (new Schema ).$ref(s.name.toString.trim)).toSeq
200- val schema = new Schema
195+ val schema = new ObjectSchema
201196 schema.setOneOf(childrenRefs.asJava)
202197 val schemaRef = registerAsReference(name, schema)
203198 children.map(_.asType.toType).foreach(handleType)
@@ -223,34 +218,61 @@ class OpenAPIModelRegistration(
223218 }
224219 }
225220
226- private def handleSimpleType (tpe : Type ): Schema [_] = {
227- val schema = new Schema
228- val OpenAPISimpleType (terminalTpe, format) = getOpenAPISimpleType(tpe)
229- schema.setType(terminalTpe)
230- format.foreach(f => schema.setFormat(f))
231- schema
232- }
233-
234- private def getOpenAPISimpleType (tpe : Type ): OpenAPISimpleType = tpe.dealias match {
235- case t if t =:= typeOf[Byte ] => OpenAPISimpleType (" integer" , Some (" int32" ))
236- case t if t =:= typeOf[Short ] => OpenAPISimpleType (" integer" , Some (" int32" ))
237- case t if t =:= typeOf[Int ] => OpenAPISimpleType (" integer" , Some (" int32" ))
238- case t if t =:= typeOf[Long ] => OpenAPISimpleType (" integer" , Some (" int64" ))
239- case t if t =:= typeOf[Float ] => OpenAPISimpleType (" number" , Some (" float" ))
240- case t if t =:= typeOf[Double ] => OpenAPISimpleType (" number" , Some (" double" ))
241- case t if t =:= typeOf[Char ] => OpenAPISimpleType (" string" )
242- case t if t =:= typeOf[String ] => OpenAPISimpleType (" string" )
243- case t if t =:= typeOf[UUID ] => OpenAPISimpleType (" string" , Some (" uuid" ))
244- case t if t =:= typeOf[Boolean ] => OpenAPISimpleType (" boolean" )
245- case t if t =:= typeOf[Unit ] => OpenAPISimpleType (" null" )
246- case t if t =:= typeOf[ZonedDateTime ] => OpenAPISimpleType (" string" , Some (" date-time" ))
247- case t if t =:= typeOf[Instant ] => OpenAPISimpleType (" string" , Some (" date-time" ))
248- case t if t =:= typeOf[LocalDateTime ] => OpenAPISimpleType (" string" , Some (" date-time" ))
249- case t if t =:= typeOf[LocalDate ] => OpenAPISimpleType (" string" , Some (" date" ))
250- case t if t =:= typeOf[LocalTime ] => OpenAPISimpleType (" string" , Some (" time" ))
251- case t if t =:= typeOf[Timestamp ] => OpenAPISimpleType (" string" , Some (" date-time" ))
252- case t if t =:= typeOf[BigDecimal ] => OpenAPISimpleType (" number" )
253- case t if t =:= typeOf[BigInt ] => OpenAPISimpleType (" integer" )
221+ private def handleSimpleType (tpe : Type ): Schema [_] = tpe.dealias match {
222+ case t if t =:= typeOf[Byte ] =>
223+ val s = new IntegerSchema ()
224+ s.setFormat(" int32" )
225+ s
226+ case t if t =:= typeOf[Short ] =>
227+ val s = new IntegerSchema ()
228+ s.setFormat(" int32" )
229+ s
230+ case t if t =:= typeOf[Int ] =>
231+ val s = new IntegerSchema ()
232+ s.setFormat(" int32" )
233+ s
234+ case t if t =:= typeOf[Long ] =>
235+ val s = new IntegerSchema ()
236+ s.setFormat(" int64" )
237+ s
238+ case t if t =:= typeOf[Float ] =>
239+ val s = new NumberSchema ()
240+ s.setFormat(" float" )
241+ s
242+ case t if t =:= typeOf[Double ] =>
243+ val s = new NumberSchema ()
244+ s.setFormat(" double" )
245+ s
246+ case t if t =:= typeOf[Char ] =>
247+ new StringSchema ()
248+ case t if t =:= typeOf[String ] =>
249+ new StringSchema ()
250+ case t if t =:= typeOf[UUID ] =>
251+ val s = new UUIDSchema ()
252+ s.setFormat(" uuid" )
253+ s
254+ case t if t =:= typeOf[Boolean ] =>
255+ new BooleanSchema ()
256+ case t if t =:= typeOf[Unit ] =>
257+ val s = new Schema [Unit ]()
258+ s.setType(" null" )
259+ s
260+ case t if t =:= typeOf[ZonedDateTime ] || t =:= typeOf[Instant ] || t =:= typeOf[LocalDateTime ] || t =:= typeOf[Timestamp ] =>
261+ val s = new StringSchema ()
262+ s.setFormat(" date-time" )
263+ s
264+ case t if t =:= typeOf[LocalDate ] =>
265+ val s = new StringSchema ()
266+ s.setFormat(" date" )
267+ s
268+ case t if t =:= typeOf[LocalTime ] =>
269+ val s = new StringSchema ()
270+ s.setFormat(" time" )
271+ s
272+ case t if t =:= typeOf[BigDecimal ] =>
273+ new NumberSchema ()
274+ case t if t =:= typeOf[BigInt ] =>
275+ new IntegerSchema ()
254276 }
255277
256278 private def registerAsReference (name : String , schema : Schema [_]): Schema [_] = {
0 commit comments