2013-09-23 68 views
23

Tôi đang cố gắng tạo ứng dụng Scala bao gồm dự án thư viện (hãy gọi đây là common), dự án máy chủ tiết kiệm (gọi số server) này và chơi dự án ứng dụng web (sau đây gọi là web). Cả ba đều được viết bằng Scala và được xây dựng với sbt.Cách tạo ứng dụng Play Scala 2.2 dưới dạng tiểu dự án SBT

cấu trúc dự án của tôi trông như thế này:

myproject/ 
-common/ 
    ... 
-server/ 
    ... 
-web/ 
    -app/ 
    -conf/ 
    ... 
-project/ 
    -Build.scala 
    -build.properties 
-build.sbt 

build.sbt tập tin của tôi (đơn giản hóa một chút) trông như thế này:

import play.Project._ 

name := "myproject" 

version := "1.0-SNAPSHOT" 

lazy val common = project 

lazy val web = project 
    .settings(playScalaSettings: _*) 
    .dependsOn(common) 

lazy val server = project 
    .dependsOn(common) 

lazy val root = project.in(file(".")) 
    .aggregate(common, web, server) 

Vấn đề ở đây là các dự án gốc không phải là một Play dự án, do đó, lệnh play không hoạt động (nó lỗi với

java.lang.RuntimeException: */*:playRunHooks is undefined. 
at scala.sys.package$.error(package.scala:27) 

Tôi có thể sửa lỗi này bằng cách tạo dự án gốc trông giống như dự án Play nếu tôi chèn dòng playScalaSettings sau dòng version vào tệp SBT, nhưng sau đó tôi gặp sự cố khác: lệnh play run cố gắng chạy dự án gốc chứ không phải web tiểu dự án. Rõ ràng lệnh play run không hoạt động khi chạy trong thư mục con web vì không có tệp SBT ở đó để mô tả dự án và các phụ thuộc của dự án.

Tôi đang tìm một giải pháp cho phép tôi giữ lại cấu trúc dự án này (nghĩa là dự án Play là một trong nhiều dự án phụ trong ứng dụng của tôi), trong khi giữ lại tất cả độ nóng của khung chơi như cập nhật nóng khi thay đổi mã mã trong các thư viện phụ thuộc như common).

tôi nghĩ rằng tôi tìm thấy giải pháp bằng cách chạy play để có được giao diện điều khiển tương tác, và sau đó

project web 
run 

đó làm việc, nhưng nó không hoạt động trên dòng lệnh. play web/run vì một số lý do chạy lệnh gốc cấp run, như đã nêu ở trên không hoạt động vì ứng dụng gốc không phải là ứng dụng Play.

Lưu ý: Câu hỏi tương tự đã được hỏi trước trong ngữ cảnh của Play 2.0 tại Play Framework as SBT Non-Root Module, nhưng câu trả lời là không thỏa đáng, tôi cũng không tin nó vẫn chính xác như của Play 2.2.

Trả lời

14

nếu

play (entering shell) 
project web 
run 

công trình, sau đó bạn có thể làm cho nó hoạt động từ dòng lệnh:

play "project web" "run" 

Bạn có thể làm gì trong dòng lệnh bất cứ điều gì bạn có thể làm trong vỏ.

Tôi có cùng cấu trúc dự án và đó là cách để làm việc đó tốt cho tôi.

Nhân tiện, tôi không nghĩ rằng nội dung tải lại có liên quan đến Play. Nó là biên dịch gia tăng được cung cấp bởi SBT được sử dụng bởi Play. Lệnh play chỉ là một số launcher SBT bị tấn công mà tôi nghĩ.

Lệnh sau hoạt động tốt đối với tôi:

sbt "project web" "run" 

Và nó bắt đầu dự án Chơi với tải lại nóng.


Tôi nghĩ rằng bạn thậm chí có thể sử dụng

sbt "project web" "~run" 

Mà sẽ cố gắng biên dịch lại mỗi khi bạn thay đổi một tập tin nguồn, thay vì chờ đợi một refresh trình duyệt, và sẽ làm cho chiến thắng một thời gian.

0

Tôi nghĩ đây là lỗi trong Play 2.2, vì vậy tôi đã báo cáo lỗi đó là Error "/:playRunHooks is undefined" on running as web/run. Ngoài ra nó có vẻ đã được cố định trong 2.3.x, do đó có khả năng nó sẽ không được sửa cho 2.2. Dưới đây là một chút giải pháp khác tôi đã đưa ra:

lazy val root = (project in file(".")). 
    settings(
    playRunHooks := Nil, 
    playInteractionMode := play.PlayConsoleInteractionMode, 
    playDefaultPort := 9000, 
    playMonitoredFiles := (Def.taskDyn { 
     val s = state.value 
     s.history.current.split("/").headOption match { 
     case Some(ref) => 
      Def.task { 
      (playMonitoredFiles in LocalProject(ref)).value 
      } 
     case _ => 
      Def.task { 
      playMonitoredFiles.value 
      } 
     } 
    }).value 
)