使用路由中的选项编写 Sinatra 扩展

发布于 2024-09-26 21:21:56 字数 829 浏览 1 评论 0原文

假设我正在编写一个 sinatra 扩展,它在给定的安装点安装第二个 public 目录。

require 'sinatra'
require 'sinatra/moar-public'

set :moar_local, './downloads/'
set :moar_remote, 'dls'

我现在希望访问 http://myapp.com/downloads/thing.bin 的用户能够获得位于 [sinatra_root]/dls/thing.bin 的文件。

编写此扩展(显然,这是一个简化的示例),我有这样的内容:

require 'sinatra/base'
module Sinatra
  module MoarPublic
    def self.registered(app)
      app.set :moar_local, './downloads/'
      app.set :moar_remote, 'downloads'

      app.get "/#{app.options.moar_remote}/:filename" do
        # Logic
      end
    end
  end
  register MoarPublic
end

但是 app.get 已经使用 moar_remote 的默认值调用,因此下载文件是可在 /downloads/thing.bin 处获取,而不是在 /dls/thing.bin 处获取,如我所愿。有什么想法吗?

Lets say I'm writing a sinatra extension which mounts a second public directory at a given mount point.

require 'sinatra'
require 'sinatra/moar-public'

set :moar_local, './downloads/'
set :moar_remote, 'dls'

I now expect a user going to http://myapp.com/downloads/thing.bin to be given the file at [sinatra_root]/dls/thing.bin.

Writing this extension (obviously, it's a simplified example) I have something like this:

require 'sinatra/base'
module Sinatra
  module MoarPublic
    def self.registered(app)
      app.set :moar_local, './downloads/'
      app.set :moar_remote, 'downloads'

      app.get "/#{app.options.moar_remote}/:filename" do
        # Logic
      end
    end
  end
  register MoarPublic
end

But app.get has already been called with the default value for moar_remote so the download files are available at /downloads/thing.bin, not at /dls/thing.bin as I'd like. Any ideas?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

寒尘 2024-10-03 21:21:56

您要求动态路线,但 Sinatra 会编译路线信息,因此它不会按照您想要的方式工作。

作为解决方法,您可以考虑定义一个包罗万象的路线,并检查包罗万象中的路线信息,例如,

get %r{^/(*)/bar$} do |capture|
  if settings.url_prefix == capture # or perhaps check against request.path_info
    # get file
  else
    status 404
  end
end

显然,那里仍然有很多事情要做,但您已经明白了。

You're asking for dynamic routes, but Sinatra compiles the route information so it won't work the way you're looking for.

As a work around, you might consider defining a catch-all route, and checking the route information inside the catch-all, e.g.

get %r{^/(*)/bar$} do |capture|
  if settings.url_prefix == capture # or perhaps check against request.path_info
    # get file
  else
    status 404
  end
end

Obviously, there are still many things to be done there, but you get the drift.

抚笙 2024-10-03 21:21:56

我在模块化配置中明确注册扩展没有任何问题。下图所示。

class Service < Sinatra::Base
  set :url_prefix, 'foo'
  register Common      
end

module Common
  def self.registered(app)
    app.get "/#{app.options.url_prefix}/bar" do
      "hello world"
    end
  end
end

I had no problem registering an extension explicitily in a modular configuration. Illustration below.

class Service < Sinatra::Base
  set :url_prefix, 'foo'
  register Common      
end

module Common
  def self.registered(app)
    app.get "/#{app.options.url_prefix}/bar" do
      "hello world"
    end
  end
end
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文