2

我有一个 api 服务类,它依赖于 play 的 Configuration 和 WSClient 实例。

而且我不想使用 @Inject() 注释,因为我想在 Macwire 上使用编译时注入,所以我所做的是:

// this is a trait that here im wiring all the dependencies that my api service needs
trait ApiDependencies {

  lazy val conf: Configuration = wire[Configuration]
  lazy val wsc: WSClient = wire[WSClient]

}


// this is the api service

class ApiService extends ApiDependencies {

  def getInfo (id: String): Future[Option[Info]] = {
    wsc.url("...").withHttpHeaders(("Content-Type", "application/json")).get.map { response =>
      response.status match {
        case Status.OK => ...
        case Status.NO_CONTENT => ...
        case _ => throw new Exception()
      }
    }
  }
}

但我得到一个编译器错误:

错误:找不到类型的值:[com.typesafe.config.Config]
lazy val conf:Configuration = wire[Configuration]

错误:找不到公共构造函数或 [play.api.libs.ws.WSClient] 的伴随对象lazy val wsc:WSClient = wire[WSClient]

有人知道我该如何解决这个问题...?为什么会这样:/

谢谢!

4

1 回答 1

0

Configuration是一个playframework Configuration,内部使用Typesafe的Config library。引用Playframework 文档

Play 使用的配置文件基于Typesafe 配置库

您得到的异常确切地告诉您这一点 - macwire 无法创建实例,Configuration因为范围内没有Config实例。

要修复它,您显然需要提供这样的实例。最简单的方法可能如下所示:

import com.typesafe.config.{Config, ConfigFactory}
trait ApiDependencies {
    lazy val configuration: Config = ConfigFactory.load()
    lazy val conf: Configuration = wire[Configuration]
}

请注意,基本上ConfigFactory.Load()使用默认配置文件application.conf

用户可以使用 Java 系统属性覆盖配置,java -Dmyapp.foo.bar=10


关于WSClient:这是因为它WSClient不是一个类,而是一个 trait。您需要连接实际的实现,即NingWSClient,像这样:

trait ApiDependencies {
  lazy val conf: Configuration = wire[Configuration]
  lazy val wsc: WSClient = wire[NingWSClient]
}

请参阅WSClientscaladoc 以获取实现类的列表(在“所有已知的实现类”下) - 在撰写本文时只有NingWSClientand AhcWSClient。哪个更好是一个不同的(并且可能是基于意见的问题)。

于 2017-07-04T13:30:48.923 回答