玩法 2.4:使用依赖注入在应用启动时安排周期性任务



>我需要在应用程序启动时安排一个周期性任务,任务本身非常简单,只需向应用程序发送一个即发即弃的HTTP调用即可。我不是游戏专家,买我会认为简单的解决方案就像在Global.onStart中使用play.api.libs.concurrent.Akka.system.schedule一样。从 Play 2.4 开始,Global配置在某种程度上被弃用,取而代之的是新的 Guice DI。从DI文档中获取建议,我无法为此问题提出一个很好的解决方案。我设法得到的最好的方法是在GuiceApplicationLoader调用BuiltInComponentsFromContext的自定义实现之上编写一个包装器,但在这种情况下,我无法使用注入来获取WSClient。使用 Play 2.4 重写此类内容的最佳方法是什么:

object Global extends GlobalSettings {
  override def onStart(app: Application) = {
    Akka.system.schedule(2.hours, 2.hours, theTask)
  }
}

更新:现在在Play 2.6:https://www.playframework.com/documentation/2.6.x/ScheduledTasks 中更好地记录

了这一点

你可以通过创建一个这样的模块来解决这个问题(注意代码注释):

package tasks
import javax.inject.{Singleton, Inject}
import akka.actor.ActorSystem
import com.google.inject.AbstractModule
import play.api.inject.ApplicationLifecycle
// Using the default ExecutionContext, but you can configure
// your own as described here:
// https://www.playframework.com/documentation/2.4.x/ThreadPools
import play.api.libs.concurrent.Execution.Implicits.defaultContext
import scala.concurrent.Future
import scala.concurrent.duration._
class MyRecurrentTaskModule extends AbstractModule {
  override def configure() = {
    // binding the RecurrentTask as a eager singleton will force
    // its initialization even if RecurrentTask is not injected in
    // any other object. In other words, it will starts with when
    // your application starts.
    bind(classOf[RecurrentTask]).asEagerSingleton()
  }
}
@Singleton
class RecurrentTask @Inject() (actorSystem: ActorSystem, lifecycle: ApplicationLifecycle) {
  // Just scheduling your task using the injected ActorSystem
  actorSystem.scheduler.schedule(1.second, 1.second) {
    println("I'm running...")
  }
  // This is necessary to avoid thread leaks, specially if you are
  // using a custom ExecutionContext
  lifecycle.addStopHook{ () =>
    Future.successful(actorSystem.shutdown())
  }
}

之后,您必须启用此模块,在conf/application.conf文件中添加以下行:

play.modules.enabled += "tasks.MyRecurrentTaskModule"

然后,只需启动应用程序,向它发出请求,并查看计划任务将每秒运行一次。

参考资料

  1. 了解播放线程池
  2. 播放 Scala 的运行时依赖注入
  3. 与 Akka 集成

相关问题

  1. 如何在Play Framework 2.4.2 scala中正确安排任务?
  2. 异步作业是否已从 Play 框架中删除?什么是更好的选择?

最新更新