PlayRunHook在多模块项目中不起作用

时间:2016-01-24 05:03:27

标签: scala playframework sbt playframework-2.4 multi-module

我们需要一个基础游戏框架项目,其中包含其他play和scala项目作为模块。那些内部独立项目可以有不同的javascript框架,并构建像webpack,gulp等系统。

所以我尝试了来自https://www.playframework.com/documentation/2.4.x/SBTCookbook的PlayRunHook。单个项目挂钩按预期工作。但是,无法在多模块项目上做到正确。一些代码示例......

项目结构

project structure

碱/ build.sbt

name := """base"""

version := "1.0-SNAPSHOT"

lazy val commonSettings = Seq(
  scalaVersion := "2.11.6",
  libraryDependencies ++= Seq(
    jdbc,
    cache,
    ws,
    specs2 % Test
  ),
  resolvers ++= Seq(
    "scalaz-bintray" at "http://dl.bintray.com/scalaz/releases"
  )
)

lazy val root = (project in file("."))
        .settings(commonSettings : _*)
        .enablePlugins(PlayScala)
        .dependsOn(scraper)
        .aggregate(scraper)
        .dependsOn(slider)
        .aggregate(slider)

lazy val scraper = (project in file("modules/scraper"))
        .settings(commonSettings : _*)
        .enablePlugins(PlayScala)

lazy val slider = (project in file("modules/slider"))
        .settings(commonSettings : _*)
        .enablePlugins(PlayScala)

routesGenerator := InjectedRoutesGenerator

碱/模块/刮刀/ build.sbt

import play.sbt.PlayImport.PlayKeys.playRunHooks
import WebPack._

name := """scraper"""

version := "1.0-SNAPSHOT"

lazy val frontendDirectory = baseDirectory {_ / "frontend"}

playRunHooks <+= frontendDirectory.map(WebPack.apply)

routesGenerator := InjectedRoutesGenerator

libraryDependencies ++= Seq(
    "com.corundumstudio.socketio" % "netty-socketio" % "1.7.8"
)

resolvers ++= Seq(
    "Sonatype OSS Snapshots" at "https://oss.sonatype.org/content/repositories/snapshots"
)

碱/模块/滑块/ build.sbt

name := """slider"""

version := "1.0-SNAPSHOT"

scalaVersion := "2.11.6"

routesGenerator := InjectedRoutesGenerator

碱/模块/刮刀/项目/ WebPack.scala

import java.net.InetSocketAddress

import play.sbt.PlayRunHook
import sbt._

object WebPack {
    def apply(base: File): PlayRunHook = {
        object WebpackHook extends PlayRunHook {
            var process: Option[Process] = None

            override def beforeStarted(): Unit = {
                if (isWindows) {
                    Process("cmd /c npm run compile", base).run
                } else {
                    Process("npm run compile", base).run
                }
            }

            override def afterStarted(addr: InetSocketAddress): Unit = {
                if (isWindows) {
                    Some(Process("cmd /c npm start", base).run)
                } else {
                    Some(Process("npm start", base).run)
                }
            }

            private def isWindows: Boolean = {
                System.getProperty("os.name").startsWith("Windows")
            }

            override def afterStopped(): Unit = {
                process.foreach(_.destroy())
                process = None
            }
        }

        WebpackHook
    }
}

但我正在

...../base/modules/scraper/build.sbt:10: error: not found: object WebPack
import WebPack._
       ^
sbt.compiler.EvalException: Type error in expression
        at sbt.compiler.Eval.checkError(Eval.scala:384)
        at sbt.compiler.Eval.compileAndLoad(Eval.scala:183)
        at sbt.compiler.Eval.evalCommon(Eval.scala:152)
        at sbt.compiler.Eval.evalDefinitions(Eval.scala:122)
        at sbt.EvaluateConfigurations$.evaluateDefinitions(EvaluateConfigurations.scala:271)
        at sbt.EvaluateConfigurations$.evaluateSbtFile(EvaluateConfigurations.scala:109)
        at sbt.Load$.sbt$Load$$loadSettingsFile$1(Load.scala:712)
        at sbt.Load$$anonfun$sbt$Load$$memoLoadSettingsFile$1$1.apply(Load.scala:717)
        at sbt.Load$$anonfun$sbt$Load$$memoLoadSettingsFile$1$1.apply(Load.scala:716)
        at scala.collection.MapLike$class.getOrElse(MapLike.scala:128)
        at scala.collection.AbstractMap.getOrElse(Map.scala:58)
        at sbt.Load$.sbt$Load$$memoLoadSettingsFile$1(Load.scala:716)
        at sbt.Load$$anonfun$loadFiles$1$2.apply(Load.scala:723)
        at sbt.Load$$anonfun$loadFiles$1$2.apply(Load.scala:723)
        at scala.collection.TraversableLike$$anonfun$map$1.apply(TraversableLike.scala:244)
        at scala.collection.TraversableLike$$anonfun$map$1.apply(TraversableLike.scala:244)
        at scala.collection.immutable.List.foreach(List.scala:318)
        at scala.collection.TraversableLike$class.map(TraversableLike.scala:244)
        at scala.collection.AbstractTraversable.map(Traversable.scala:105)
        at sbt.Load$.loadFiles$1(Load.scala:723)
        at sbt.Load$.discoverProjects(Load.scala:734)
        at sbt.Load$.discover$1(Load.scala:545)
        at sbt.Load$.discoverAndLoad$1(Load.scala:554)
        at sbt.Load$.loadTransitive(Load.scala:570)
        at sbt.Load$.loadProjects$1(Load.scala:442)
        at sbt.Load$.loadUnit(Load.scala:446)
        at sbt.Load$$anonfun$18$$anonfun$apply$11.apply(Load.scala:281)
        at sbt.Load$$anonfun$18$$anonfun$apply$11.apply(Load.scala:281)
        at sbt.BuildLoader$$anonfun$componentLoader$1$$anonfun$apply$4$$anonfun$apply$5$$anonfun$apply$6.apply(BuildLoader.scala:91)
        at sbt.BuildLoader$$anonfun$componentLoader$1$$anonfun$apply$4$$anonfun$apply$5$$anonfun$apply$6.apply(BuildLoader.scala:90)
        at sbt.BuildLoader.apply(BuildLoader.scala:140)
        at sbt.Load$.loadAll(Load.scala:334)
        at sbt.Load$.loadURI(Load.scala:289)
        at sbt.Load$.load(Load.scala:285)
        at sbt.Load$.load(Load.scala:276)
        at sbt.Load$.apply(Load.scala:130)
        at sbt.Load$.defaultLoad(Load.scala:36)
        at sbt.BuiltinCommands$.doLoadProject(Main.scala:481)
        at sbt.BuiltinCommands$$anonfun$loadProjectImpl$2.apply(Main.scala:475)
        at sbt.BuiltinCommands$$anonfun$loadProjectImpl$2.apply(Main.scala:475)
        at sbt.Command$$anonfun$applyEffect$1$$anonfun$apply$2.apply(Command.scala:58)
        at sbt.Command$$anonfun$applyEffect$1$$anonfun$apply$2.apply(Command.scala:58)
        at sbt.Command$$anonfun$applyEffect$2$$anonfun$apply$3.apply(Command.scala:60)
        at sbt.Command$$anonfun$applyEffect$2$$anonfun$apply$3.apply(Command.scala:60)
        at sbt.Command$.process(Command.scala:92)
        at sbt.MainLoop$$anonfun$1$$anonfun$apply$1.apply(MainLoop.scala:98)
        at sbt.MainLoop$$anonfun$1$$anonfun$apply$1.apply(MainLoop.scala:98)
        at sbt.State$$anon$1.process(State.scala:184)
        at sbt.MainLoop$$anonfun$1.apply(MainLoop.scala:98)
        at sbt.MainLoop$$anonfun$1.apply(MainLoop.scala:98)
        at sbt.ErrorHandling$.wideConvert(ErrorHandling.scala:17)
        at sbt.MainLoop$.next(MainLoop.scala:98)
        at sbt.MainLoop$.run(MainLoop.scala:91)
        at sbt.MainLoop$$anonfun$runWithNewLog$1.apply(MainLoop.scala:70)
        at sbt.MainLoop$$anonfun$runWithNewLog$1.apply(MainLoop.scala:65)
        at sbt.Using.apply(Using.scala:24)
        at sbt.MainLoop$.runWithNewLog(MainLoop.scala:65)
        at sbt.MainLoop$.runAndClearLast(MainLoop.scala:48)
        at sbt.MainLoop$.runLoggedLoop(MainLoop.scala:32)
        at sbt.MainLoop$.runLogged(MainLoop.scala:24)
        at sbt.StandardMain$.runManaged(Main.scala:53)
        at sbt.xMain.run(Main.scala:28)
        at xsbt.boot.Launch$$anonfun$run$1.apply(Launch.scala:109)
        at xsbt.boot.Launch$.withContextLoader(Launch.scala:128)
        at xsbt.boot.Launch$.run(Launch.scala:109)
        at xsbt.boot.Launch$$anonfun$apply$1.apply(Launch.scala:35)
        at xsbt.boot.Launch$.launch(Launch.scala:117)
        at xsbt.boot.Launch$.apply(Launch.scala:18)
        at xsbt.boot.Boot$.runImpl(Boot.scala:41)
        at xsbt.boot.Boot$.main(Boot.scala:17)
        at xsbt.boot.Boot.main(Boot.scala)
[error] sbt.compiler.EvalException: Type error in expression
[error] Use 'last' for the full log.
Project loading failed: (r)etry, (q)uit, (l)ast, or (i)gnore?

我正在尝试游戏框架,我对此很新。提前致谢

1 个答案:

答案 0 :(得分:2)

  1. 在sbt中只保留一个build.sbt文件和一个project目录(带* .sbt和* .scala配置文件)
  2. WebPack.scala复制到project目录。
  3. 将根项目移动到子项目(基础)。
  4. 重写build.sbt
  5.     import play.sbt.PlayImport.PlayKeys.playRunHooks
    
        name := """root"""
    
        version := "1.0-SNAPSHOT"
    
        val scraperDir = "modules/scraper"
    
        val sliderDir = "modules/slider"
    
        lazy val commonSettings = Seq(
            scalaVersion := "2.11.7",
            libraryDependencies ++= Seq(
               jdbc,
               cache,
               ws,
               specs2 % Test
            ),
            resolvers ++= Seq(
               "scalaz-bintray" at "http://dl.bintray.com/scalaz/releases"
            )
        )
    
        lazy val base = projectName("base","base").settings(
            playRunHooks += WebPack.apply(file(scraperDir))
        )
       .dependsOn(scraper,slider)
    
        lazy val scraper = projectName("scraper", scraperDir).settings(
           libraryDependencies ++= Seq(
               "com.corundumstudio.socketio" % "netty-socketio" % "1.7.8"
           ),
           resolvers ++= Seq(
              "Sonatype OSS Snapshots" at "https://oss.sonatype.org/content/repositories/snapshots")
        )
    
        lazy val slider = projectName("slider", sliderDir)
    
        def projectName(name: String, path: String): Project =
         Project(name,file(path))
         .settings(
             commonSettings,
             routesGenerator := InjectedRoutesGenerator
         )
         .enablePlugins(PlayScala)