14

使用 Rails 3.2。

我有六个控制器,并且想用http_basic_authenticate_with.

我不想手动添加http_basic_authenticate_with到每个控制器(我将来可以添加另一个控制器而忘记保护它!)。似乎答案是把它放在application_controller.rb一个:exceptarg 中,它会列出应该受到保护的控制器。问题是, :except 子句需要方法名称而不是外部控制器模块名称,例如:

http_basic_authenticate_with :name => 'xxx', :password => 'yyy', :except => :foo, :bar

所以然后我想“等等,既然我已经将受保护的控制器分组在routes.rb,让我们把它放在那里。” 所以我在我的路线中尝试了这个:

  scope "/billing" do
    http_basic_authenticate_with :name ...
    resources :foo, :bar ...
  end

但现在我明白了

undefined method `http_basic_authenticate_with'

解决这个问题的最佳方法是什么?

4

1 回答 1

45

像 Rails 那样做。

# rails/actionpack/lib/action_controller/metal/http_authentication.rb

def http_basic_authenticate_with(options = {})
  before_action(options.except(:name, :password, :realm)) do
    authenticate_or_request_with_http_basic(options[:realm] || "Application") do |name, password|
      name == options[:name] && password == options[:password]
    end
  end
end

所做http_basic_authenticate_with的只是添加一个before_action. 您也可以自己轻松地做同样的事情:

# application_controller.rb

before_action :http_basic_authenticate

def http_basic_authenticate
  authenticate_or_request_with_http_basic do |name, password|
    name == 'xxx' && password == 'yyy'
  end
end

这意味着您可以skip_before_action在不需要这种行为的控制器中使用:

# unprotected_controller.rb

skip_before_action :http_basic_authenticate
于 2014-03-10T04:18:52.793 回答