Ruby Sinatra 网络应用程序中的身份验证问题

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

我有一个简单的 Sinatra 应用程序,带有两个控制器和 api 助手

# ApplicationController

class ApplicationController < Sinatra::Base
  register Sinatra::ActiveRecordExtension
  helpers ApiHelper

  configure :production, :development do
    enable :logging
  end

  before do
    content_type :json
  end

  get '/hello' do
    { message: 'Hello!' }.to_json
  end
end
# ArticlesController

class ArticlesController < ApplicationController
  before do
    authenticate!
  end

  get '/articles' do
    articles = Article.all
    articles.map { |article| serialize(article) }
  end

  ...
end
# ApiHelper

module ApiHelper
  def authenticate!
    halt 403, { message: 'Unauthorized!' }.to_json unless authorized?
  end

  private

  def authorized?
    request.env['HTTP_AUTHORIZATION'] == 'Bearer 123qweasd'
  end
end

当我做

curl -X GET -i -H 'Accept: application/json' http://localhost:4567/hello

做健康检查我得到 403 Unauthorized。为什么?我不需要在 /hello 端点中进行身份验证,只需要在 /articles CRUD 端点中进行身份验证,所以我不明白为什么它在 /hello 中进行身份验证。根据文档 before 块用于在其他操作运行之前执行某些操作,但我不会在 authenticate! 中的 before 块中调用 ApplicationController。我错过了什么?

ruby sinatra
1个回答
0
投票

如果你想要求对除 /hello 端点之外的所有端点进行身份验证,你可以修改你的身份验证!方法仅在当前端点不是 /hello 时才需要身份验证,如下所示:

module ApiHelper
  def authenticate!
    halt 403, { message: 'Unauthorized!' }.to_json unless authorized? || request.path_info == '/hello'
  end

  ...
end

这将允许对 /hello 端点的请求绕过身份验证检查。


或者:

你可以移动身份验证!方法仅适用于 ArticlesController,并将其从 ApiHelper 模块中删除。然后,您可以仅在 ApplicationController 中包含 ApiHelper 模块,如下所示:

# ArticlesController

class ArticlesController < ApplicationController
  before do
    authenticate!
  end

  get '/articles' do
    articles = Article.all
    articles.map { |article| serialize(article) }
  end

  private

  def authenticate!
    halt 403, { message: 'Unauthorized!' }.to_json unless authorized?
  end

  def authorized?
    request.env['HTTP_AUTHORIZATION'] == 'Bearer 123qweasd'
  end
end

# ApiHelper

module ApiHelper
  def serialize(object)
    # ... same as before ...
  end
end

不清楚为什么你的 before 中的 ArticlesController 块似乎适用于 /hello 中的 ApplicationController 端点。上面定义的方法将使 /hello 动作不可能受到 authenticate 方法的影响,因为我们确保它甚至没有被定义。这可能不是理想的,但它可能有助于解决在向 authenticate!.

发出请求时导致调用 /hello 方法的任何问题
© www.soinside.com 2019 - 2024. All rights reserved.