我在Scala 2.10.2,Akka 2.2.0上并尝试确定将现有Java类与Actor集成是否有意义。我想到的Java类是Apache Commons FileUpload streaming API。
这是我在不使用演员的情况下工作的
class HelloWorld extends HttpServlet {
override def doGet(req: HttpServletRequest, resp: HttpServletResponse) = {
resp.getWriter().print("Hello World!")
}
override def doPost(req: HttpServletRequest, resp: HttpServletResponse ) = {
if (ServletFileUpload.isMultipartContent(req)) {
val upload = new ServletFileUpload()
// Parse the request
val iter = upload.getItemIterator(req)
while (iter.hasNext()) {
val item = iter.next()
val name = item.getFieldName()
val stream = item.openStream()
if (item.isFormField()) {
println("Form field " + name + " with value " + Streams.asString(stream) + " detected.")
} else {
println("File field " + name + " with file name " + item.getName() + " detected.")
saveAttachment(item.getName(), stream)
}
}
resp.getWriter().print("\nFile uploads success!\n")
} else
resp.getWriter().print("\nNo file upload found!\n")
}
private def saveAttachment(...) {...}
}
通常,actor会在receive
方法中处理其所有消息,但在这种情况下,该类已经有预定义的方法。由于缺乏一个更好的术语,有没有办法实现这一点?我考虑的一个选项是创建一个actor来处理doPost
中的上传,因为它是一个阻塞调用处理潜在的大文件。想法?
答案 0 :(得分:0)
如果有办法“演员”任何界面,我很想知道它。 =)在我看来,最简单的事情就是创建一个值,作为一个可以发送消息的actor,并将流处理实现拉入其中。因此,如果重要的部分被删除,那将看起来像以下......
import akka.actor.ActorDSL._
class HelloWorld extends HttpServlet {
val streamHandler = actor(new Act {
become {
case req: HttpServletRequest =>
val upload = new ServletFileUpload()
// ...
}
})
override def doPost(req: HttpServletRequest, resp: HttpServletResponse) = {
if (ServletFileUpload.isMultipartContent(req)) {
streamHandler ! req
resp.getWriter().print("\nFile uploads success!\n") // This is optimistic; we don't really know for sure
} else {
resp.getWriter().print("\nNo file upload found!\n")
}
}
}
当然,这是一种管道胶带解决方案;如果你发送除了HttpServletRequest以外的任何东西,那么actor会废弃,这显然不是真正可重用的代码。它只是为了演示演员DSL。