acts_as_authenticatedとrole_requirementでロール付きの認証。
acts_as_authenticatedをインストール
$ ruby script/plugin discover $ ruby script/plugin install acts_as_authenticated
ジェネってmigration
$ ./script/generate authenticated user account $ rake db:migrate
その他の機能はあとで
メール認証だの、アクティベーションだのはまた今度。
ログインが必要なコントローラは
before_filter :login_requiredで認証箇所のコントロール
class HogeController < ApplicationController include AuthenticatedSystem before_filter :login_required, :except => [:nologin] def index #ログイン必要 end def nologin #ログイン不要 end end
ロールを追加。
どうせ必要なので。
Acts_as_authenticatedにRole機能を追加する,RoleRequirementっーのがあるみたい。
インストールしる。
$ script/plugin install http://rolerequirement.googlecode.com/svn/tags/role _requirement/ + ./ChangeLog + ./MIT-LICENSE + ./README + ./generators/role/role_generator.rb + ./generators/role/templates/001_add_role_to_users_migration.rb.erb + ./generators/role/templates/_user_functions.erb + ./generators/role_generator_helpers.rb + ./generators/roles/roles_generator.rb + ./generators/roles/templates/001_roles_migration.rb.erb + ./generators/roles/templates/_user_functions.erb + ./generators/roles/templates/role_model.rb.erb + ./generators/roles/templates/roles.yml + ./generators/roles/templates/roles_users.yml + ./generators/roles/templates/users_admin_fixture_with_roles.yml + ./generators/shared_templates/hijacker.rb + ./generators/shared_templates/role_requirement_system.rb.erb + ./generators/shared_templates/role_requirement_test_helper.rb.erb + ./init.rb + ./test/authenticated_system.rb + ./test/controller_stub.rb + ./test/functional/test_role_controller.rb + ./test/test_helper.rb + ./test/user_stub.rb
generate
Role:ロールのモデル名 User:ユーザのモデル名
(ユーザがいくつもロールを持つ:多対多)
script/generate roles Role User
(ユーザは一種類のロールしか持たない:一対多)
script/generate role User
多対多で作っとく。
$ script/generate roles Role User Generating Role against User Added the following to the top of app/models/user.rb: # --------------------------------------- # The following code has been generated by role_requirement. # You may wish to modify it to suit your need has_and_belongs_to_many :roles attr_protected :roles # has_role? simply needs to return true or false whether a user has a role or not. # It may be a good idea to have "admin" roles return true always 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 # --------------------------------------- Added ApplicationController include to /home/xxxx/dev/rails/auth_test/app/controllers/application.rb Added RoleRequirement include to /home/xxxx/dev/rails/auth_test/app/controllers/application.rb Added RoleRequirementTestHelper include to /home/xxxx/dev/rails/auth_test/test/test_helper.rb create test/fixtures/roles_users.yml create test/fixtures/roles.yml create app/models/role.rb create lib/role_requirement_system.rb create lib/role_requirement_test_helper.rb create lib/hijacker.rb exists db/migrate create db/migrate/002_create_roles.rb
migrate
DB反映
$ rake db:migrate (in /home/coek/dev/rails/auth_test) == 2 CreateRoles: migrating =================================================== -- create_table("roles") -> 0.1138s -- create_table("roles_users", {:id=>false}) -> 0.0181s -- add_index("roles_users", "role_id") -> 0.0337s -- add_index("roles_users", "user_id") -> 0.0298s == 2 CreateRoles: migrated (0.1980s) ==========================================
モデルを定義
Roleモデルにhabtmを書き足す
has_and_belongs_to_many :users
ロール設定の画面scaffold
-
- skip-migrationつけて
$ ruby script/generate scaffold role --skip-migration exists app/models/ exists app/controllers/ exists app/helpers/ create app/views/roles exists app/views/layouts/ exists test/functional/ exists test/unit/ create app/views/roles/index.html.erb create app/views/roles/show.html.erb create app/views/roles/new.html.erb create app/views/roles/edit.html.erb create app/views/layouts/roles.html.erb create public/stylesheets/scaffold.css dependency model exists app/models/ exists test/unit/ exists test/fixtures/ skip app/models/role.rb create test/unit/role_test.rb skip test/fixtures/roles.yml create app/controllers/roles_controller.rb create test/functional/roles_controller_test.rb create app/helpers/roles_helper.rb route map.resources :roles
スキーマ情報とらないからviewをチョコチョコ自分でなおして。。
とりあえず、adminとuserを作っておく。
試してみる
さっき作ったroles_controllerに
require_role "admin"
書いてみて、ログインしないでアクセスすると。ログイン画面に飛ばされる
adminロールを持ってないユーザーでログインしてアクセスすると、画面真っ白。。
画面真っ白がヘボイ
http://d.hatena.ne.jp/clayfish/20080101/1199195090
を参考に
applicationコントローラーに手入れるのめんどかったので
とりあえずリダイレクトだけされすようにした。
/lib/role_requirement_system.rb L110
def access_denied if logged_in? #render :nothing => true, :status => 401 redirect_to("/") return false else super end end
ロールがある場合も試す。
とりあえずconsoleでロールを与える
$ ruby script/console Loading development environment (Rails 2.0.2) >> ?> ?> @user = User.find_by_login('admin') => #<User id: 2, login: "admin", email: "xxxx@xxxxx", crypted_password: "xxxxxx", salt: "xxxxxxxx", created_at: "2008-02-12 19:35:08", updated_at: "2008-02-12 19:35:08", remember_token: nil, remember_token_expires_at: nil> >> @user.roles << Role.find_by_name('admin') => [#<Role id: 1, name: "admin">] >> @user.save => true >>
で、さっきのroles_controllerにアクセスしたら、アクセスできた。
参考
http://blog.japan.zdnet.com/yoshimi/a/2007/10/acts_as_authent.html
http://eringi.com/weblog/archives/2007/07/acts_as_authenticated.html
http://idm.s9.xrea.com/ratio/2007/09/Monthly.html#id_20acts_as_authenticatede381a8e381af
http://chn.co.jp/blog/20080107.html#p08
http://d.hatena.ne.jp/clayfish/20080101/1199195090