我想通过Rack提供静态文件以及动态内容。以前,我使用WEBrick 而不使用Rack ,使用这样的代码,并且它有效:
@s = WEBrick::HTTPServer.new(
Port: 3000,
BindAddress: "localhost",
Logger: WEBrick::Log.new(File::NULL),
AccessLog: [nil, nil]
)
%w[INT TERM].each{|signal| trap(signal){@s.shutdown}}
@s.mount("/", self)
@s.mount("/resource/", WEBrick::HTTPServlet::FileHandler, "/")
@s.start
在上文中,localhost:3000
的请求将由动态内容响应,localhost:3000/resource/path_to_file
的请求将由位于我计算机上/path_to_file
的静态文件响应。
现在,我想切换到使用Rack with Thin server的系统。我写了以下内容,但无法获取所提供的静态文件。应如何改变以使其有效?
Rack::Handler::Thin.run(->env{
h = Rack::Utils.parse_nested_query(env["QUERY_STRING"])
# I tried the following three lines one at a time, but neither worked.
use(Rack::Static, urls: "/resource/", root: "/") # First try
Rack::File.new("/resource").call(env) # Second try
Rack::Directory.new("/resource").call(env) # Third try
[200, {}, [some_dyamically_generated_content]]
}, Port: 3000)
我知道这是一个类似的问题:How to serve static files via Rack?,但我无法使其发挥作用。我不确定如何使用Rack::Static
,Rack::File
或Rack::Directory
。请教我。
答案 0 :(得分:6)
您需要使用Rack::Builder
才能在普通Ruby脚本中使用use SomeMiddleware
语法(通常在config.ru
文件中使用)。您的申请还需要run
。请注意,urls
的{{1}}键采用数组,而不是单个字符串:
Rack::Static
此处require 'rack'
Rack::Handler::Thin.run(Rack::Builder.new {
use(Rack::Static, urls: ["/resource/"], root: "/")
run ->env{[200, {}, [some_dyamically_generated_content]]}
}, Port: 3000)
正在为您的应用程序Rack::Builder
提供->env{[200, {}, [some_dyamically_generated_content]]}
中间件并创建一个新的组合应用程序,然后将其传递给Thin运行。
Rack::Static
是一个中间件组件,您可以将其添加到现有的机架应用程序中。 Rack::Static
和Rack::File
都是机架应用程序,而不是中间件(Rack::Directory
在内部使用Rack::Static
,默认情况下Rack::File
也是如此。您可以使用Rack::Directory
和Rack::File
命令获得与上述相同的效果:
map
更常见的方法是将传递给require 'rack'
Rack::Handler::Thin.run(Rack::Builder.new {
map "/resource/" do
run Rack::File.new "/"
end
map "/" do
run ->env{[200, {}, [some_dyamically_generated_content]]}
end
}, Port: 3000)
的{{1}}块的内容放在Rack::Bundler.new
文件中:
config.ru
然后,您可以使用use(Rack::Static, urls: ["/resource/"], root: "/")
run ->env{[200, {}, [some_dyamically_generated_content]]}
运行此选项,如果从同一目录运行,则应查找thin start
,或者您可以使用config.ru
选项指定文件。如果要将Thin指定为服务器,也可以使用-R
命令rackup
。
答案 1 :(得分:1)
如果在提供文件之前不需要身份验证/授权,则应该能够将文件添加到/public
并让它们由底层服务器提供服务。
因此,如果您的应用布局看起来像这样
my_app/
- app.rb
- config.ru
- public/
- a_static_file.png
- another_static_file.png
启动应用后(使用瘦,webrick或apache或任何底层服务器),您可以从http://localhost:4567/a_static_file.png