2012-03-20 19 views
32

我試圖做一個特定的靜態文件的路由,但我試圖結束一個錯誤。路線到Play中的靜態文件! 2.0

我做了3次不同的嘗試:

1.

GET /file staticFile:/public/html/file.html 

的錯誤,我得到:

Compilation error 
string matching regex `\z' expected but `:' found 

2.

GET /file controllers.Assets.at(path="/public/html", "file.html") 

我得到的錯誤:

Compilation error 
Identifier expected 

3.

GET /file controllers.Assets.at(path="/public/html", file="file.html") 

我得到的錯誤:(這是最古怪的)

Compilation error 
not enough arguments for method at: (path: String, file: String)play.api.mvc.Call. Unspecified value parameter file. 

關於第三個錯誤怪異的部分是,它是在一個不同的文件拋出( app/views/main.scala.html)在以下行上:

<link rel="stylesheet" media="screen" href="@routes.Assets.at("stylesheets/main.css")"> 

所有這些e方法在官方文檔和/或線程中發現在stackoverflow上。 我在這裏錯過了什麼?

謝謝。

+1

我認爲第三個錯誤發生在默認模板中提到公共路由的第一個實例。我有完全相同的問題。我期望你/我嘗試添加靜態鏈接會擾亂反向路由。 – flurdy 2012-03-31 19:14:46

+0

什麼?兩年,沒有被接受的答案。這個問題解決了嗎? – Jus12 2014-10-05 16:19:14

+0

@ Jus12對不起,這只是我沒有繼續使用遊戲(不是我的選擇,這是不幸的),我不知道哪個答案是正確的。那個得票最多的人當時沒有解決問題(正如我的評論所解釋的)。如果有人會讓我知道任何答案是否正確,我會很樂意將其標記爲已接受。 – 2014-10-05 17:10:08

回答

18

IIRC,改變

<link rel="stylesheet" media="screen" href="@routes.Assets.at("stylesheets/main.css")"> 

<link rel="stylesheet" media="screen" href="@routes.Assets.at("stylesheets/", "main.css")"> 

我談論你的第三次嘗試

此外,注意額外/

編輯

GET /assets/main.css controllers.Assets.at(path="/public", file="/stylesheets/main.css") 

假設你的資源是/public/stylesheets/main.css

+2

這只是解決了另一個錯誤,但你改變的不是問題,當我註釋掉這條路由線路時一切正常(除非該文件未被提供)。第三次嘗試的錯誤是主要的模板文件,這正是我從_play新的app-name_命令中得到的,我沒有改變它,並且正如我寫的,沒有這個路由,它運行良好。 – 2012-03-21 21:13:59

3

我遇到同樣的問題,而我試圖配置一些額外的CSS。它在「路由」文件中使用此語法

GET /css/*file      controllers.Assets.at(path="/public/css", file) 
+0

與上面相同,但它的工作原理,但我們似乎無法知道爲什麼 – BlueSky 2017-03-26 11:57:10

4

我有完全相同的問題。我遵循了@Jamil的建議,並設法使這個靜態文件(在我的情況下是一個圖標)工作,並設法讓模板編譯,但嘗試使用視圖時在運行時得到一個新的錯誤。下面相關的代碼,

切換到路徑(這條路線現在可以解決正確)

GET  /favicon.ico    controllers.Assets.at(path="/public/images", file="favicon.png") 

切換到視圖(編譯)

<link rel="stylesheet" media="screen" href="@routes.Assets.at("stylesheets/","main.css")"> 

新的錯誤(僅在運行時)

[MatchError: (stylesheets/,main.css) (of class scala.Tuple2)] 

// @LINE:29 
// @LINE:28 
def at(path:String, file:String) = { 
    (path, file) match { 
// @LINE:28 
case (path, file) if path == "/public" => Call("GET", "/assets/" + implicitly[PathBindable[String]].unbind("file", file)) 

我知道這不是一個答案,但也許它會讓某人得到一個答案。

+0

感謝您的答覆,我沒有辦法嘗試這個目前爲止,我希望能回到它並將回報。 – 2012-08-02 08:11:33

+2

正確的路線是這樣的: 「GET /favicon.ico controllers.Assets.at(path =」/ public「,file =」images/favicon.ico「)」 – AlexV 2013-12-31 04:56:27

13

我不能完全確定這是否是正確的,但是這是我們使用映射一個公用文件夾包含我們的圖像,JavaScript ...等什麼..

# Map static resources from the /public folder to the /assets URL path 
GET  /assets/*file    controllers.Assets.at(path="/public", file) 
+0

感謝您的回覆,我無法嘗試這到目前爲止,我希望能回到它並將回報。 – 2012-08-02 08:11:42

+0

如果我將「public」文件夾重命名爲「assets」,這似乎不起作用(使用'path =「/ assets」',...)。任何想法爲什麼? – 2014-10-14 02:38:37

+0

這適用於我在Play 2.5上,這是奇怪的 – BlueSky 2017-03-26 11:52:12

13

這種能力仍然沒有據我所知,已被添加。在航線配置

GET /    controllers.StaticFile.html(file = "public/index.html") 
1

我碰到了同樣的問題

object StaticFile extends Controller { 

    def html(file: String) = Action { 
    var f = new File(file) 

    if (f.exists()) 
     Ok(scala.io.Source.fromFile(f.getCanonicalPath()).mkString).as("text/html"); 
    else 
     NotFound 
    } 

} 

,然後:但是,如果有人需要的答案,作爲一個選項,幫助控制器可以爲這些目的而創建的。當我加入了第二controllers.Assets.at路線像

GET /assets/*file controllers.Assets.at(path="/public", file) 
GET /assets2/*file controllers.Assets.at(path="/public2", file) 

默認在main.scala.html @routes.Assets.at調用失敗編譯

Compilation error 
not enough arguments for method at: (path: String, file: String)play.api.mvc.Call. Unspecified value parameter file. 

這似乎是因爲其中有多個隱式參數匹配對象。解決的辦法是增加一個領先的位置參數:

href="@routes.Assets.at("/public","/css/main.css")" 

不幸的是,如果你回到其在路線只有一個資產線,你將不得不更改爲一個參數的形式,以避免編譯錯誤。對我來說就像一個錯誤。

10

最乾淨的解決方案是創建您自己的AssetsBuilder,它將構建您的靜態頁面。

在控制器包來創建這個文件 - Static.scala

package controllers 

object Static extends AssetsBuilder 

然後在你的路線,你可以定義靜態終結

GET /file controllers.Static.at(path="/public/html", "file.html") 

完成。現在,在/public/html/file.html文件將送達斷localhost:9000/file

如果更換上面一個更通用的硬代碼:

GET /*file controllers.Static.at(path="/public/html", *file + ".html") 

然後/foo將成爲/public/html/foo.html/bar將成爲/public/html/bar.html

+1

測試和工作! +1 – Jus12 2014-10-05 16:43:47

+1

這是一個不錯的訣竅! +1 – 2014-11-12 18:22:59

5

你的第三次嘗試幾乎是正確的。 而不是

GET /file controllers.Assets.at(path="/public/html", file="file.html") 

做這樣的

GET /file controllers.Assets.at(path="/public", file="html/file.html") 

我之前得到了同樣的問題。我的路由文件看起來像這樣。

# Application 
GET/  controllers.Assets.at(path="/public/html", file="static.html") 
GET /exmpl controllers.Examples.index 

# Resources 
GET /assets/*file controllers.Assets.at(path="/public", file) 

而且我有反向路由低於內部意見(examples.scala.html

@routes.Assets.at("imagefolder") #try to generate path to /public/imagefolder. 

當我打開http://localhost:9000/exmpl,這個錯誤出現了。

not enough arguments for method at: (path: String, file: String)play.api.mvc.Call. Unspecified value parameter file. 

要解決這個問題,我只是改變這條路線

GET/ controllers.Assets.at(path="/public/html", file="static.html") 

這個

GET/ controllers.Assets.at(path="/public", file="html/static.html") 

該解決方案對我的作品。我希望它也適用於你和其他人。

1

在jar文件中播放java包公用文件夾,如果您想要提供解析爲服務器中絕對文件位置的靜態文件,則會出現問題。正確的做法是擁有自己的控制器並使用它來提供靜態文件。

對於離,以服務文件「mystatic.html」,也就是在

<your playhome> 
    |-----<myfolder> 
     |------mystatic.html 

你會配置你的路由文件,這條路線。

GET /mystatic   mypackage.mycontrollers.Static.getFile(path="/myfolder/mystatic.html") 

和您的控制器將實施如下。

package mypackage.mycontroller; 

import java.io.File; 
import com.google.inject.Inject; 
import com.google.inject.Provider; 

import play.Application; 
import play.mvc.Controller; 
import play.mvc.Result; 
import play.mvc.Results; 

public class Static extends Controller { 

    @Inject 
    Provider<Application> app; 

    public Result getFile(String path){ 
     File file = app.get().getFile(path); 
     if(file.exists()){ 
      return ok(file);    
     }else{ 
      return Results.notFound(); 
     } 
    } 
}