Ruby on Rails にて acts_as_authenticatedとrole_requirement に関してはいろいろ資料が出てきていたのですが、これの設定等が具体的になかったのでここにメモを残しておこうと思う。
controller ごとに権限を設定してアクセス制御を行うんですが、その設定で引っかかったのでその解決法というか考え方。
上の資料の通りに userモデル と roleモデル等を作成。
app/models/user.rb に
def has_role?(role_in_question)
@_list ||= self.roles.collect(&:name)
return true if @_list.include?('admin')
(@_list.include?(role_in_question.to_s) )
end
と記述されいるため
def has_role?(role_in_question)
@_list ||= self.roles.collect(&:name)
return true if @_list.include?(role_in_question.to_s)
# (@_list.include?(role_in_question.to_s) )
end
と書き直す。前のままだと、 admin ロールのみアクセスを許可される。
これを他のロールにも権限を与えたいので、 role_in_question.to_s に書き換え。
{RAILSROOT}/lib/role_requirement_system.rb の中身を見てみると、各コントローラに require_role を記述しての使用法が書かれています。
# Add this to the top of your controller to require a role in order to access it.
# Example Usage:
#
# require_role "contractor"
# require_role "admin", :only => :destroy # don't allow contractors to destroy
# require_role "admin", :only => :update, :unless => "current_user.authorized_for_listing?(params[:id]) "
#
# Valid options
#
# * :only - Only require the role for the given actions
# * :except - Require the role for everything but
# * :if - a Proc or a string to evaluate. If it evaluates to true, the role is required.
# * :unless - The inverse of :if
#
オプションの説明等が書かれていますが、他にもオプション(for 等)があることがコード内をみてわかる。
使用例として、例えば contentadmin_controller.rb の各アクションに対して権限をわけて設定する方法を書いてみる。
このコントローラは
- show
- list
- new
- create
- edit
- update
- delete
- onair
- not_onair
- 管理者は全てのアクション
- 閲覧者は list,show
- 編集者は show,list,new,create,edit,update,destroy
- 決裁者は show,list,edit,update,onair,not_onair
class ContentadminController [:list,:show]
require_role ["admin","editer","publisher"], :for => [:edit, :update]
require_role ["admin","editer"], :for => [:new,:create,:delete]
require_role ["admin","publisher"], :for => [:onair,:no_onair]
....
こんな風に記述していきます。
考え方のこつとして、アクションに対してロールを設定すると考えた方が良い。
後に書いたコードが前のコードを上書きしてしまうためそこは注意が必要。