package scalaz
package http
package servlet
import javax.servlet.{ServletException, ServletConfig}
import Class.forName
import HttpServletRequest._
import HttpServletResponse._
abstract class ScalazServlet[IN[_], OUT[_], A <: { def application: ServletApplication[IN, OUT] }](cl: Class[A])(implicit in: InputStreamer[IN], e: Each[OUT]) extends javax.servlet.http.HttpServlet {
type App = { def application: ServletApplication[IN, OUT] }
private[servlet] var application: App = _
val applicationInitParam = "application"
override final def init(config: ServletConfig) {
super.init(config)
val p = config.getInitParameter(applicationInitParam)
if(p == null)
throw new ServletException("Specify the " + applicationInitParam + " init parameter")
else {
val c = forName(p)
if(cl isAssignableFrom c) {
application = c.newInstance.asInstanceOf[App]
} else
throw new ServletException(c + " must be assignable to " + cl)
}
}
override final def service(request: javax.servlet.http.HttpServletRequest, response: javax.servlet.http.HttpServletResponse) {
request.asRequest[IN].foreach(r => {
val res = application.application(this, request, r)
response.respond[OUT](res)
})
}
}