如何让 Sinatra 使用 CSRF 真实性令牌?

问题描述 投票:0回答:3

我正在使用 Sinatra 框架在 ruby 中构建一个简单的应用程序。它主要基于“获取”——大多数请求都是针对列表数据的。然而,应用程序中有几个关键屏幕将收集用户输入。我想确保应用程序尽可能安全,目前正在尝试找到如何实现以 Rails 形式获得的真实性令牌类型?

我必须去的地方: 好吧,我知道我需要 csrf 的令牌,但我不确定是否需要自己生成它们,或者 Sinatra 是否可以为我生成 - 我已经查看了文档,他们说 Sinatra 正在使用机架保护,但是,我找不到它的任何示例代码,并且似乎不知道如何让它运行 - 任何帮助appreciated - 谢谢!

ruby sinatra csrf
3个回答
28
投票

使用

rack_csrf
宝石。安装它

gem install rack_csrf

rack_csrf
gem 有一个 Sinatra 示例。以下是改编自此页面的更简单示例(似乎离线。存档版本):

require "rack/csrf"

configure do
  use Rack::Session::Cookie, :secret => "some unique secret string here"
  use Rack::Csrf, :raise => true
end

使用

enable :sessions
代替
use Rack::Session::Cookie ...
在大多数情况下也有效(请参阅 Bill 的评论)。

在您看来,您可以使用

Rack::Csrf.csrf_token
Rack::Csrf.csrf_tag
方法获取令牌(或标签)。如果这看起来很长,您可能需要按照以下方式定义一个助手:

helpers do
  def csrf_token
    Rack::Csrf.csrf_token(env)
  end

  def csrf_tag
    Rack::Csrf.csrf_tag(env)
  end
end

使用辅助方法的小示例:

<form method="post" action="/tweet">
  <%= csrf_tag %>
  <input type="text" name="message"/>
  <input type="submit" value="Submit a tweet!"/>
</form>

0
投票

当渲染相同的 erb 视图时,在登录时凭据无效的情况下。现在在提交渲染后会抛出错误。

Rack::Csrf::InvalidCsrfToken at /login
Rack::Csrf::InvalidCsrfToken

我们是否需要进行重定向来代替渲染才能完成这项工作?因为在渲染中旧的 csrf 令牌仍然存在。在完整的重定向中,我们生成了一个新令牌。


0
投票

您可以使用

Rack::Protection
Rack::Protection::AuthenticityToken
来实现此目的。

这是简化的示例:

class MyApp < Sinatra::Base
  use Rack::Protection
  use Rack::Protection::AuthenticityToken

  helpers do
    def csrf_tag
      "<input type='hidden' name='authenticity_token' value='#{session[:csrf]}' />"
    end
  end

  get "/login" do
    erb :login
  end

  post "/login" do
    # handle login logic
  end
end
<form action="/login" method="post">
  <%= csrf_tag %>
  <label>
    Email:
    <input type="email" name="email" required>
  </label>
  <label for="password">
    Password:
    <input type="password" name="password" required>
  </label>
  <button type="submit">
    Login
  </button>
</form>
© www.soinside.com 2019 - 2024. All rights reserved.