Skip to content

Commit

Permalink
Merge pull request #112 from blast-hardcheese/custom-number-types
Browse files Browse the repository at this point in the history
Making x-scala-type work for non-string types
  • Loading branch information
blast-hardcheese authored Oct 9, 2018
2 parents cba626a + bcb6a77 commit 76804c4
Show file tree
Hide file tree
Showing 3 changed files with 88 additions and 11 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -235,6 +235,7 @@ object SwaggerUtil {

customType.flatMap(liftCustomType _).getOrElse {
(typeName, format) match {
case ("string", Some("date")) => t"java.time.LocalDate"
case ("string", Some("date-time")) => t"java.time.OffsetDateTime"
case ("string", o @ Some(fmt)) => log(o, Type.Name(fmt))
case ("string", None) => log(None, t"String")
Expand Down Expand Up @@ -295,33 +296,33 @@ object SwaggerUtil {
.fromOption(Option(r.getSimpleRef()), "Malformed $ref")
.map(Deferred.apply _)
case b: BooleanProperty =>
Target.pure(Resolved(t"Boolean", None, Default(b).extract[Boolean].map(Lit.Boolean(_))))
Target.pure(Resolved(typeName("boolean", None, ScalaType(b)), None, Default(b).extract[Boolean].map(Lit.Boolean(_))))
case s: StringProperty =>
Target.pure(Resolved(typeName("string", Option(s.getFormat()), ScalaType(s)), None, Default(s).extract[String].map(Lit.String(_))))

case d: DateProperty =>
Target.pure(Resolved(t"java.time.LocalDate", None, None))
Target.pure(Resolved(typeName("string", Some("date"), ScalaType(d)), None, None))
case d: DateTimeProperty =>
Target.pure(Resolved(t"java.time.OffsetDateTime", None, None))
Target.pure(Resolved(typeName("string", Some("date-time"), ScalaType(d)), None, None))

case l: LongProperty =>
Target.pure(Resolved(t"Long", None, Default(l).extract[Long].map(Lit.Long(_))))
Target.pure(Resolved(typeName("integer", Some("int64"), ScalaType(l)), None, Default(l).extract[Long].map(Lit.Long(_))))
case i: IntegerProperty =>
Target.pure(Resolved(t"Int", None, Default(i).extract[Int].map(Lit.Int(_))))
Target.pure(Resolved(typeName("integer", Some("int32"), ScalaType(i)), None, Default(i).extract[Int].map(Lit.Int(_))))
case f: FloatProperty =>
Target.pure(Resolved(t"Float", None, Default(f).extract[Float].map(Lit.Float(_))))
Target.pure(Resolved(typeName("number", Some("float"), ScalaType(f)), None, Default(f).extract[Float].map(Lit.Float(_))))
case d: DoubleProperty =>
Target.pure(Resolved(t"Double", None, Default(d).extract[Double].map(Lit.Double(_))))
Target.pure(Resolved(typeName("number", Some("double"), ScalaType(d)), None, Default(d).extract[Double].map(Lit.Double(_))))
case d: DecimalProperty =>
Target.pure(Resolved(t"BigDecimal", None, None))
Target.pure(Resolved(typeName("number", None, ScalaType(d)), None, None))
case u: UntypedProperty =>
Target.pure(Resolved(gs.jsonType, None, None))
case p: AbstractProperty if Option(p.getType).exists(_.toLowerCase == "integer") =>
Target.pure(Resolved(t"BigInt", None, None))
Target.pure(Resolved(typeName("integer", None, ScalaType(p)), None, None))
case p: AbstractProperty if Option(p.getType).exists(_.toLowerCase == "number") =>
Target.pure(Resolved(t"BigDecimal", None, None))
Target.pure(Resolved(typeName("number", None, ScalaType(p)), None, None))
case p: AbstractProperty if Option(p.getType).exists(_.toLowerCase == "string") =>
Target.pure(Resolved(t"String", None, None))
Target.pure(Resolved(typeName("string", None, ScalaType(p)), None, None))
case x =>
Target.error(s"Unsupported swagger class ${x.getClass().getName()} (${x})")
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ object VendorExtension {
implicit val defaultVendorExtensibleSwagger: VendorExtensible[Swagger] =
build[Swagger](m => key => m.getVendorExtensions.get(key))

implicit val defaultVendorExtensibleAbstractProperty: VendorExtensible[AbstractProperty] =
build[AbstractProperty](m => key => m.getVendorExtensions.get(key))
implicit val defaultVendorExtensibleArrayProperty: VendorExtensible[ArrayProperty] =
build[ArrayProperty](m => key => m.getVendorExtensions.get(key))
implicit val defaultVendorExtensibleBaseIntegerProperty: VendorExtensible[BaseIntegerProperty] =
Expand All @@ -47,6 +49,8 @@ object VendorExtension {
build[DoubleProperty](m => key => m.getVendorExtensions.get(key))
implicit val defaultVendorExtensibleFloatProperty: VendorExtensible[FloatProperty] =
build[FloatProperty](m => key => m.getVendorExtensions.get(key))
implicit val defaultVendorExtensibleIntegerProperty: VendorExtensible[IntegerProperty] =
build[IntegerProperty](m => key => m.getVendorExtensions.get(key))
implicit val defaultVendorExtensibleLongProperty: VendorExtensible[LongProperty] =
build[LongProperty](m => key => m.getVendorExtensions.get(key))
implicit val defaultVendorExtensibleMapProperty: VendorExtensible[MapProperty] =
Expand Down
72 changes: 72 additions & 0 deletions modules/codegen/src/test/scala/core/issues/Issue105.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
package tests.core.issues

import _root_.io.swagger.parser.SwaggerParser
import cats.instances.all._
import com.twilio.swagger._
import com.twilio.guardrail.generators.AkkaHttp
import com.twilio.guardrail.{
ClassDefinition,
Client,
ClientGenerator,
Clients,
CodegenApplication,
Context,
ProtocolDefinitions,
ProtocolGenerator,
RandomType,
Target
}
import com.twilio.guardrail.tests._
import org.scalatest.{ FunSuite, Matchers }
import support.SwaggerSpecRunner

import scala.meta._

class Issue105 extends FunSuite with Matchers with SwaggerSpecRunner {
val swagger: String = s"""
|swagger: "2.0"
|info:
| title: Whatever
| version: 1.0.0
|host: localhost:1234
|schemes:
| - http
|definitions:
| Foo:
| type: object
| properties:
| nonEmptyString:
| type: string
| format: int64
| x-scala-type: String Refined NonEmpty
| positiveLong:
| type: integer
| format: int64
| x-scala-type: Long Refined Positive
|""".stripMargin

test("Generate plain array alias definition") {
val (
ProtocolDefinitions(ClassDefinition(_, _, cls, cmp) :: Nil, _, _, _),
_,
_
) = runSwaggerSpec(swagger)(Context.empty, AkkaHttp, defaults.akkaGeneratorSettings)

val definition = q"""
case class Foo(nonEmptyString: Option[String Refined NonEmpty] = None, positiveLong: Option[Long Refined Positive] = None)
"""

val companion = q"""
object Foo {
implicit val encodeFoo = {
val readOnlyKeys = Set[String]()
Encoder.forProduct2("nonEmptyString", "positiveLong")((o: Foo) => (o.nonEmptyString, o.positiveLong) ).mapJsonObject(_.filterKeys(key => !(readOnlyKeys contains key)))
}
implicit val decodeFoo = Decoder.forProduct2("nonEmptyString", "positiveLong")(Foo.apply _)
}
"""

cls.structure shouldBe definition.structure
cmp.structure shouldBe companion.structure
}
}

0 comments on commit 76804c4

Please sign in to comment.