summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLi Haoyi <haoyi.sg@gmail.com>2018-07-21 16:01:59 +0800
committerLi Haoyi <haoyi.sg@gmail.com>2018-07-21 16:04:56 +0800
commitc1dcd6b5794bd1ceb3d92edc8a7f730c93098ef3 (patch)
tree3b6f37d73b48f5ae8c80fb51cb9aba2f8929bb10
parent9da5084d27b1d5ed08e7d457817943cebe59580a (diff)
downloadcask-c1dcd6b5794bd1ceb3d92edc8a7f730c93098ef3.tar.gz
cask-c1dcd6b5794bd1ceb3d92edc8a7f730c93098ef3.tar.bz2
cask-c1dcd6b5794bd1ceb3d92edc8a7f730c93098ef3.zip
Tidying up
-rw-r--r--cask/src/cask/Annotations.scala21
-rw-r--r--cask/src/cask/Main.scala129
-rw-r--r--cask/src/cask/ParamReader.scala23
-rw-r--r--cask/src/cask/Routes.scala46
4 files changed, 114 insertions, 105 deletions
diff --git a/cask/src/cask/Annotations.scala b/cask/src/cask/Annotations.scala
new file mode 100644
index 0000000..83534e6
--- /dev/null
+++ b/cask/src/cask/Annotations.scala
@@ -0,0 +1,21 @@
+package cask
+
+import scala.annotation.StaticAnnotation
+
+
+trait AnnotationBase{
+ def wrapMethodOutput(t: Response): Any
+ def parseMethodInput[T](implicit p: ParamReader[T]) = p
+}
+trait RouteBase extends AnnotationBase{
+ val path: String
+ def wrapMethodOutput(t: Response) = t
+}
+class get(val path: String) extends StaticAnnotation with RouteBase
+class post(val path: String) extends StaticAnnotation with RouteBase
+class put(val path: String) extends StaticAnnotation with RouteBase
+class route(val path: String, val methods: Seq[String]) extends StaticAnnotation with RouteBase
+
+class static(val path: String) extends StaticAnnotation{
+ def wrapOutput(t: String) = t
+}
diff --git a/cask/src/cask/Main.scala b/cask/src/cask/Main.scala
index b9a02de..1d86de1 100644
--- a/cask/src/cask/Main.scala
+++ b/cask/src/cask/Main.scala
@@ -18,78 +18,81 @@ abstract class BaseMain{
def servers: Seq[Routes]
val port: Int = 8080
val host: String = "localhost"
- def main(args: Array[String]): Unit = {
- val allRoutes = for{
- server <- servers
- route <- server.caskMetadata.value.map(x => x: Routes.RouteMetadata[_])
- } yield (server, route)
- val server = Undertow.builder
- .addHttpListener(port, host)
- .setHandler(new BlockingHandler(new HttpHandler() {
- def handleRequest(exchange: HttpServerExchange): Unit = {
- val routeOpt =
- allRoutes
- .iterator
- .map { case (s: Routes, r: Routes.RouteMetadata[_]) =>
- Util.matchRoute(r.metadata.path, exchange.getRequestPath).map((s, r, _))
- }
- .flatten
- .toStream
- .headOption
+ val allRoutes = for{
+ server <- servers
+ route <- server.caskMetadata.value.map(x => x: Routes.RouteMetadata[_])
+ } yield (server, route)
+ val defaultHandler = new HttpHandler() {
+ def handleRequest(exchange: HttpServerExchange): Unit = {
+ val routeOpt =
+ allRoutes
+ .iterator
+ .map { case (s: Routes, r: Routes.RouteMetadata[_]) =>
+ Util.matchRoute(r.metadata.path, exchange.getRequestPath).map((s, r, _))
+ }
+ .flatten
+ .toStream
+ .headOption
- routeOpt match{
- case None =>
- exchange.setStatusCode(404)
- exchange.getResponseHeaders.put(Headers.CONTENT_TYPE, "text/plain")
- exchange.getResponseSender.send("404 Not Found")
- case Some((server, route, bindings)) =>
- import collection.JavaConverters._
- val allBindings =
- bindings.toSeq ++
- exchange.getQueryParameters
- .asScala
- .toSeq
- .flatMap{case (k, vs) => vs.asScala.map((k, _))}
-
- val result = route.entryPoint
- .asInstanceOf[EntryPoint[server.type, HttpServerExchange]]
- .invoke(server, exchange, allBindings.map{case (k, v) => (k, Some(v))})
-
- result match{
- case Router.Result.Success(response: Response) =>
- response.headers.foreach{case (k, v) =>
- exchange.getResponseHeaders.put(new HttpString(k), v)
- }
+ routeOpt match{
+ case None =>
+
+ exchange.setStatusCode(404)
+ exchange.getResponseHeaders.put(Headers.CONTENT_TYPE, "text/plain")
+ exchange.getResponseSender.send("404 Not Found")
+ case Some((server, route, bindings)) =>
+ import collection.JavaConverters._
+ val allBindings =
+ bindings.toSeq ++
+ exchange.getQueryParameters
+ .asScala
+ .toSeq
+ .flatMap{case (k, vs) => vs.asScala.map((k, _))}
+
+ val result = route.entryPoint
+ .asInstanceOf[EntryPoint[server.type, HttpServerExchange]]
+ .invoke(server, exchange, allBindings.map{case (k, v) => (k, Some(v))})
- exchange.setStatusCode(response.statusCode)
-
-
- response.data.write(
- new OutputStream {
- def write(b: Int) = {
- exchange.getResponseSender.send(ByteBuffer.wrap(Array(b.toByte)))
- }
- override def write(b: Array[Byte]) = {
- exchange.getResponseSender.send(ByteBuffer.wrap(b))
- }
- override def write(b: Array[Byte], off: Int, len: Int) = {
- exchange.getResponseSender.send(ByteBuffer.wrap(b.slice(off, off + len)))
- }
- }
- )
- case err: Router.Result.Error =>
- exchange.setStatusCode(400)
- exchange.getResponseHeaders.put(Headers.CONTENT_TYPE, "text/plain")
- exchange.getResponseSender.send("400 Not Found " + result)
+ result match{
+ case Router.Result.Success(response: Response) =>
+ response.headers.foreach{case (k, v) =>
+ exchange.getResponseHeaders.put(new HttpString(k), v)
}
+ exchange.setStatusCode(response.statusCode)
+
+ response.data.write(
+ new OutputStream {
+ def write(b: Int) = {
+ exchange.getResponseSender.send(ByteBuffer.wrap(Array(b.toByte)))
+ }
+ override def write(b: Array[Byte]) = {
+ exchange.getResponseSender.send(ByteBuffer.wrap(b))
+ }
+ override def write(b: Array[Byte], off: Int, len: Int) = {
+ exchange.getResponseSender.send(ByteBuffer.wrap(b.slice(off, off + len)))
+ }
+ }
+ )
+ case err: Router.Result.Error =>
+ exchange.setStatusCode(400)
+ exchange.getResponseHeaders.put(Headers.CONTENT_TYPE, "text/plain")
+ exchange.getResponseSender.send("400 Not Found " + result)
}
- }
- }))
+
+
+ }
+ }
+ }
+
+ def main(args: Array[String]): Unit = {
+ val server = Undertow.builder
+ .addHttpListener(port, host)
+ .setHandler(new BlockingHandler(defaultHandler))
.build
server.start()
}
diff --git a/cask/src/cask/ParamReader.scala b/cask/src/cask/ParamReader.scala
new file mode 100644
index 0000000..8cb7c1f
--- /dev/null
+++ b/cask/src/cask/ParamReader.scala
@@ -0,0 +1,23 @@
+package cask
+
+import io.undertow.server.HttpServerExchange
+
+class ParamReader[T](val arity: Int,
+ val read0: (HttpServerExchange, Seq[String]) => T)
+ extends Router.ArgReader[T, HttpServerExchange]{
+ def read(ctx: HttpServerExchange, v: Seq[String]): T = read0(ctx, v)
+}
+object ParamReader{
+ implicit object StringParam extends ParamReader[String](1, (h, x) => x.head)
+ implicit object BooleanParam extends ParamReader[Boolean](1, (h, x) => x.head.toBoolean)
+ implicit object ByteParam extends ParamReader[Byte](1, (h, x) => x.head.toByte)
+ implicit object ShortParam extends ParamReader[Short](1, (h, x) => x.head.toShort)
+ implicit object IntParam extends ParamReader[Int](1, (h, x) => x.head.toInt)
+ implicit object LongParam extends ParamReader[Long](1, (h, x) => x.head.toLong)
+ implicit object DoubleParam extends ParamReader[Double](1, (h, x) => x.head.toDouble)
+ implicit object FloatParam extends ParamReader[Float](1, (h, x) => x.head.toFloat)
+ implicit def SeqParam[T: ParamReader] =
+ new ParamReader[Seq[T]](1, (h, s) => s.map(x => implicitly[ParamReader[T]].read(h, Seq(x))))
+
+ implicit object HttpExchangeParam extends ParamReader[HttpServerExchange](0, (h, x) => h)
+} \ No newline at end of file
diff --git a/cask/src/cask/Routes.scala b/cask/src/cask/Routes.scala
index 757eb48..0e88a5e 100644
--- a/cask/src/cask/Routes.scala
+++ b/cask/src/cask/Routes.scala
@@ -5,47 +5,8 @@ import java.io.OutputStream
import cask.Router.EntryPoint
import io.undertow.server.HttpServerExchange
-import scala.annotation.StaticAnnotation
import scala.reflect.macros.blackbox.Context
-class ParamType[T](val arity: Int,
- val read0: (HttpServerExchange, Seq[String]) => T)
- extends Router.ArgReader[T, HttpServerExchange]{
- def read(ctx: HttpServerExchange, v: Seq[String]): T = read0(ctx, v)
-}
-object ParamType{
- def findImplicitly[T](implicit p: ParamType[T]) = p
-
- implicit object StringParam extends ParamType[String](1, (h, x) => x.head)
- implicit object BooleanParam extends ParamType[Boolean](1, (h, x) => x.head.toBoolean)
- implicit object ByteParam extends ParamType[Byte](1, (h, x) => x.head.toByte)
- implicit object ShortParam extends ParamType[Short](1, (h, x) => x.head.toShort)
- implicit object IntParam extends ParamType[Int](1, (h, x) => x.head.toInt)
- implicit object LongParam extends ParamType[Long](1, (h, x) => x.head.toLong)
- implicit object DoubleParam extends ParamType[Double](1, (h, x) => x.head.toDouble)
- implicit object FloatParam extends ParamType[Float](1, (h, x) => x.head.toFloat)
- implicit def SeqParam[T: ParamType] =
- new ParamType[Seq[T]](1, (h, s) => s.map(x => implicitly[ParamType[T]].read(h, Seq(x))))
-
- implicit object HttpExchangeParam extends ParamType[HttpServerExchange](0, (h, x) => h)
-}
-
-trait AnnotationBase{
- def wrapOutput(t: Response): Any
-// def wrapInput(t: Response): Any
-}
-trait RouteBase extends AnnotationBase{
- val path: String
- def wrapOutput(t: Response) = t
-}
-class get(val path: String) extends StaticAnnotation with RouteBase
-class post(val path: String) extends StaticAnnotation with RouteBase
-class put(val path: String) extends StaticAnnotation with RouteBase
-class route(val path: String, val methods: Seq[String]) extends StaticAnnotation with RouteBase
-
-class static(val path: String) extends StaticAnnotation{
- def wrapOutput(t: String) = t
-}
case class Response(data: Response.Data,
statusCode: Int = 200,
@@ -80,15 +41,16 @@ object Routes{
annot <- m.annotations.filter(_.tree.tpe <:< c.weakTypeOf[RouteBase])
} yield {
val annotObject = q"new ${annot.tree.tpe}(..${annot.tree.children.tail})"
+ val annotObjectSym = c.universe.TermName(c.freshName("annotObject"))
val route = router.extractMethod(
m.asInstanceOf[MethodSymbol],
weakTypeOf[T],
- (t: router.c.universe.Tree) => q"$annotObject.wrapOutput($t)",
+ (t: router.c.universe.Tree) => q"$annotObjectSym.wrapMethodOutput($t)",
c.weakTypeOf[io.undertow.server.HttpServerExchange],
- q"cask.ParamType.findImplicitly"
+ q"$annotObjectSym.parseMethodInput"
)
- val annotObjectSym = c.universe.TermName(c.freshName("annotObject"))
+
q"""{
val $annotObjectSym = $annotObject
cask.Routes.RouteMetadata($annotObjectSym, $route)