2011-06-08 50 views
1

如何在使用webrick的動態呈現頁面內使用像cssjspng等本地資源?換句話說,像Ruby on Rails linking這樣的東西是如何工作的?我想這是最基本的事情之一,應該有一個簡單的方法來做到這一點。如何在服務器上使用本地資源?

可能的解決方案

我能夠做到什麼,我想用兩個servlet如下:

require 'webrick' 

class WEBrick::HTTPServlet::AbstractServlet 
    def do_GET request, response 
    response.body = '<html> 
     <head><base href="http://localhost:2000"/></head> 
     <body><img src="path/image.png" /></body> 
    </html>' 
    end 
end 

s1 = WEBrick::HTTPServer.new(Port: 2000, BindAddress: "localhost") 
s2 = WEBrick::HTTPServer.new(Port: 3000, BindAddress: "localhost") 
%w[INT TERM].each{|signal| trap(signal){s1.stop}} 
%w[INT TERM].each{|signal| trap(signal){s2.shutdown}} 
s1.mount("/", WEBrick::HTTPServlet::FileHandler, '/') 
s2.mount("/", WEBrick::HTTPServlet::AbstractServlet) 

Thread.new{s1.start} 
s2.start 

這是做正確的方式?我不這麼認爲。另外,我對此並不完全滿意。首先,我不喜歡我必須在身體中指定http://localhost:2000的事實。另一個是使用線程似乎不正確。有一個更好的方法嗎?如果您認爲這是正確的方式,請回答。

+0

它如何「不起作用」?你有錯誤嗎?你有什麼東西嗎?你得到了什麼?你期望什麼? – 2011-06-08 08:14:09

+0

只是一個想法,但檢查文件的權限,以確保它的服務器可讀(不只是由你)。 – hoff2 2011-06-08 16:44:44

+0

@centipedefarmer權限沒問題。當我右鍵單擊圖像並執行「查看圖像信息」時,我可以正確地看到圖片。 – sawa 2011-06-08 20:23:03

回答

0

我終於發現我可以在一臺服務器上掛載多個servlet。我花了很長時間才發現such example

require 'webrick' 

class WEBrick::HTTPServlet::AbstractServlet 
    def do_GET request, response 
    response.body = '<html> 
     <head><base href="/resource/"/></head> 
     <body> 
     <img src="path_to_image/image.png";alt="picture"/> 
     <a href="path_to_directory/" />link</a> 
     ... 
     </body> 
    </html>' 
    end 
end 

server = WEBrick::HTTPServer.new(Port: 3000, BindAddress: "localhost") 
%w[INT TERM].each{|signal| trap(signal){server.shutdown}} 
server.mount("/resource/", WEBrick::HTTPServlet::FileHandler, '/') 
server.mount("/", WEBrick::HTTPServlet::AbstractServlet) 
server.start 

路徑/resource/可以是其他任何東西。該鏈接現在可以正確地重定向到預期的目錄,顯示沒有訪問權限,這表示事情正常;現在只是一個許可問題。

1

嘗試這樣的代碼:

require 'webrick' 

class WEBrick::HTTPServlet::AbstractServlet 
    def do_GET request, response 
    if request.unparsed_uri == "/" 
     response.body = '<html><body><a href = "/path/to/file">test</a></body></html>' 
    end 
    end 
end 

server = WEBrick::HTTPServer.new(Port: 3000, BindAddress: "localhost", DocumentRoot: "/") 
%w[INT TERM].each { |signal| trap(signal) { server.shutdown } } 
server.mount("/", WEBrick::HTTPServlet::AbstractServlet) 
server.start 

這對我的作品,我不知道爲什麼,但它似乎工作,每當我打電話請求對象上至少一個方法。

+0

好的,我用似乎有效的東西更新了回覆。 – robbrit 2011-06-08 03:49:46

+0

我用'/ path/to/file'作爲'/'試過了你的代碼,但它不起作用。難道我做錯了什麼? – sawa 2011-06-08 04:53:05

+0

我在我的問題中添加了一個工作代碼,這可能會讓我清楚自己想要什麼。如果你能幫助我,將不勝感激。 – sawa 2011-06-09 05:39:25

2

一般來說,由於安全問題,瀏覽器可能不會鏈接到來自Internet站點(使用http://或https://模式)的本地文件(使用file://模式)。見Can Google Chrome open local links?。這與任何服務器端技術無關。

除此之外,它似乎你的服務器正在完美工作。你已經做到了,它可以響應所有請求,並通過HTML頁面提供鏈接/。當你點擊那個鏈接時,確實發生了一些事情;發送請求並再次向您提供相同的頁面。

它聽起來像你想通過HTTP公開整個文件系統。如果這是你想完成什麼,你可以簡單地逃脫不安裝一個servlet:像你這樣的困惑,供應與由瀏覽器中打開的網頁的網頁

server = WEBrick::HTTPServer.new(Port: 3000, BindAddress: "localhost", DocumentRoot: "/") 
%w[INT TERM].each{|signal| trap(signal){server.shutdown}} 
server.start 
+0

感謝您的回答。我開始意識到安全的事情。選擇根目錄就是一個例子。我想渲染一個頁面,該頁面鏈接到本地​​計算機上的某些目錄。我也想從我的本地計算機中嵌入圖像,我以類似的方式嘗試了'',但沒有成功。 – sawa 2011-06-08 13:46:58

+1

您可以使用靜態HTML頁面來完成此操作,只需在瀏覽器中打開即可。這不會影響安全問題。或者,您需要通過HTTP服務器公開必要的文件/目錄並鏈接到它們,而不需要文件:// – 2011-06-08 14:09:37

+0

我在我的問題中添加了一個工作代碼,這可能會使其清楚我想要的內容。如果你能幫助我,將不勝感激。 – sawa 2011-06-09 05:38:53

1

這聽起來很直接從您的驅動器,以及file:如何不同於http:,https:ftp:

file:是當從驅動器直接打開頁面時本地可用的資源。其他人是從httpd主機提供頁面時遠程可用的資源。

瀏覽器無法判斷來自服務器的頁面是否來自您的驅動器;它只知道它從某個服務器獲得它,並且不知道或在意該服務器是否在同一個硬件上。瀏覽器不允許從遠程檢索的頁面訪問本地資源。這是一個多年前關閉的漏洞。

查看RFC 1738's specification 3.10 FILES for file: URLs的官方聲明。

+0

好吧,讓我們忘記用'file:'打開。當我們訪問服務器的'index.html'頁面時,我們可以訪問各種文件,比如'css','js','png'。當主頁面動態生成並使用WEBrick時,我們該怎麼做?我想這應該是可能的。這是我想要做的第二部分。 – sawa 2011-06-08 19:57:10

+0

我爲我的問題添加了一個工作代碼,這可能會使我清楚自己想要什麼。如果你能幫助我,將不勝感激。 – sawa 2011-06-09 05:38:36

+0

我想我解決了我的答案。謝謝。 – sawa 2011-06-09 07:00:08

相關問題