如何在Play 2.5.x中创建线程池?

时间:2016-09-27 18:02:10

标签: scala playframework threadpool playframework-2.5

我目前在Play 2.4.2上并使用以下方法成功创建了线程池:

package threads

import scala.concurrent.ExecutionContext
import play.api.libs.concurrent.Akka
import play.api.Play.current

object Contexts {
  implicit val db: ExecutionContext = Akka.system.dispatchers.lookup("contexts.db-context")
  implicit val pdf: ExecutionContext = Akka.system.dispatchers.lookup("contexts.pdf-context")
  implicit val email: ExecutionContext = Akka.system.dispatchers.lookup("contexts.email-context")
}

然后在代码中......

Future{....}(threads.Contexts.db)

我们已准备好升级到Play 2.5并且无法理解文档。 2.4.2的文档使用Akka.system.dispatchers.lookup,我们使用它没有问题。 2.5.x的文档使用app.actorSystem.dispatchers.lookup。据我所知,我必须将应用程序注入类,而不是对象。然而,文档显然使用了一个Object作为示例!

是否有人在Play 2.5.x中成功创建了可以提供帮助的线程池?是否像将上下文更改为类一样简单,然后将其注入到我想要使用此线程的任何位置?看起来很奇怪,因为要使用默认的ExecutionContext,我只需要进行隐式导入。

此外,我们正在使用Play scala。

1 个答案:

答案 0 :(得分:4)

如果您只是将Contexts更改为某个类,则必须处理如何获取该类的实例。

在我看来,如果你想要使用多个线程池,那么命名绑定就是你的选择。在下面的例子中,我将向您展示如何使用guice实现此目的。

请注意,guice会注入依赖项at runtime,但也可以在compile time注入依赖项。

我将以db上下文作为示例来展示它。首先,这就是你将如何使用它:

class MyService @Inject() (@Named("db") dbCtx: ExecutionContext) {
  // make db access here
}

以下是如何定义绑定:

bind[ExecutionContext].qualifiedWith("db").toProvider[DbExecutionContextProvider]

在某处定义提供者:

class DbExecutionContextProvider @Inject() (actorSystem: ActorSystem) extends Provider[ExecutionContext] {
  override def get(): ExecutionContext = actorSystem.dispatchers.lookup("contexts.db-context")
}

您必须为每个上下文执行此操作。我知道这可能有点麻烦,实际上可能有更优雅的方法来定义guice中的绑定。

请注意,我还没试过。您可能偶然发现的一个问题可能是您最终会遇到冲突,因为Play已经为ExecutionContext中的BuiltinModule定义了绑定。您可能需要覆盖绑定才能解决此问题。