Spray REST API应用程序结构 - 需要的建议

时间:2015-11-06 15:58:51

标签: scala spray

我使用sbt:

构建了以下多模块项目结构
myProject-api
myProject-core

myProject-core的组织如下:

它包含某些作为我服务外观的角色。例如,我有一个位于UserService前面的UserActor。位于NotificationService前面的NotificationActor,依此类推。

我还有另一个特点,即将演员暴露给任何感兴趣的人:

trait MyProjectCoreActors {

  def myAppCfg = MyProjConfig.appCfg      

  def userActor = myAppCfg.userActor
  def notifyActor = myAppCfg.notifyActor
}
object MyProjectCoreActors {

  ... some initialization routing that initializes the MyProjConfig
}

我的UserActor因此被定义为:

class UserActor(service: UserService) extends Actor {

  ...
  ...
}

我的UserService如下:

class UserService(dbConfig: DbConfig) {

  ...
  ...
}

我有另一个名为MyProjectConfig的类,我使用application.conf文件进行初始化。在这个文件中,我有数据库的连接细节,等等。 MyProjectConfig初始化如下:

trait MyProjectConfig {

  def actorSystem: ActorSystem

  // the actors
  def userActor: ActorRef
}
object MyProjectConfig {

  def apply(appConfig: Config, system: ActorSystem): MyProjectConfig = {

    new MyProjectConfig {
      private val dbConfig = loadDBConfig(appConfig)

      override val actorSystem = system

      // each actor gets its own DBConfigInstance instance
      override val userActor =
        actorSystem.actorOf(
          Props(new UserActor(UserService(dbConfig)))
        )
    }
  }
}

我现在有如下定义的喷涂路线:

trait MyProjectService extends HttpService with MyProjectCoreActors {

  def pingRoute = path("ping") {
    get {
      userActor ! "newUser"
      complete("pong!")
    }
  }

  def pongRoute = path("pong") {
    get { complete("pong!?") }
  }

  def route = pingRoute ~ pongRoute
}

现在缺少的是一种调用MyProjectConfig.apply(....)方法并传入Actor系统和底层application.conf的方法!

这最初是一个基于Play的应用程序,我有一个Lifecycle插件,可以从我获得配置和actor系统访问底层应用程序。我怎么能在这里用Spray得到同样的东西?

我有一个看起来像这样的Boot类:

object MyBootHttpService extends App {

  implicit val actorSystem = ActorSystem("myproj-actor-system")

}

我怎么能将这个ActorSytem传递给MyProjectConfig.apply(....)?从哪里可以得到application.conf?

1 个答案:

答案 0 :(得分:0)

我认为你可以在MyBootHttpService课程中做这些事情(DI)。

例如

object MyBootHttpService extends App {

  implicit val actorSystem = ActorSystem("myproj-actor-system")
  private val config = ConfigFactory.load
  private val myAppConfig = MyProjectConfig(config, actorSystem)

  // Initialise classes that depend on config and actorsystem....
  private val service = new MyProjectService with HttpServiceActor {
     override implicit val actorRefFactory = actorSystem
  }
  // Bind our service
  IO(Http) ? Bind(listener = service, interface = "0.0.0.0", port = config.getInt("port"))

}

Typesafe配置库对象ConfigFactory通常用于加载配置文件。没有args的ConfigFactory.load会尝试从类路径加载application.conf