2016-06-14 20 views
0

私はcancancanrails_admindeviseの宝石を使用しています。ユーザーがログイン後/adminルートに行くことにしようとしたときadminカンカンにエラーYou are not authorized to access this page.を示し役割を担っているにもかかわらず。CanCan Can not authorizing admin

ここに私のability.rb

#models/ability.rb 
class Ability 
    include CanCan::Ability 
    def initialize(user) 
    can :read, :all     # allow everyone to read everything 
    if user && user.has_role?(:admin) 
     can :access, :rails_admin  # only allow admin users to access Rails Admin 
     can :dashboard     # allow access to dashboard 
     if user.role? :admin 
     can :manage, :all    # allow superadmins to do anything 
     end 
    end 
    end 
end 

だここに私のユーザモデルがここにあります

#models/user.rb 
class User < ActiveRecord::Base 

    ROLES = %i[admin moderator banned] 

    def roles=(roles) 
     roles = [*roles].map { |r| r.to_sym } 
     self.roles_mask = (roles & ROLES).map { |r| 2**ROLES.index(r) }.inject(0, :+) 
    end 

    def roles 
     ROLES.reject do |r| 
      ((roles_mask.to_i || 0) & 2**ROLES.index(r)).zero? 
     end 
    end 

    def has_role?(role) 
     roles.include?(role) 
    end 

    def role?(base_role) 
     ROLES.index(base_role.to_s) <= ROLES.index(role) 
    end 

    def self.find_first_by_auth_conditions(warden_conditions) 
     conditions = warden_conditions.dup 
     if login = conditions.delete(:login) 
      where(conditions).where(["lower(username) = :value OR lower(email) = :value", { :value => login.downcase }]).first 
     else 
      if conditions[:username].nil? 
       where(conditions).first 
      else 
       where(username: conditions[:username]).first 
      end 
     end 
    end 
    validate :validate_username 

    def validate_username 
     if User.where(email: username).exists? 
      errors.add(:username, :invalid) 
     end 
    end 
    validates_format_of :username, with: /^[a-zA-Z0-9_\.]*$/, :multiline => true 
    # Include default devise modules. Others available are: 
    # , :lockable, :timeoutable and :omniauthable 
    devise :database_authenticatable, :confirmable, :registerable, 
    :recoverable, :rememberable, :trackable, :validatable, :authentication_keys => [:login] 
    attr_accessor :login 
    def login=(login) 
    @login = login 
    end 

    def login 
    @login || self.username || self.email 
    end 
end 

ですthe rails_admin.rb

#config/initializers/rails_admin.rb 
RailsAdmin.config do |config| 

    ## == Devise == 
    config.authenticate_with do 
    warden.authenticate! scope: :user 
    end 
    config.current_user_method(&:current_user) 

    ## == Cancan == 
    config.authorize_with :cancan 

    config.actions do 
    dashboard      # mandatory 
    index       # mandatory 
    new 
    export 
    bulk_delete 
    show 
    edit 
    delete 
    show_in_app 

    ## With an audit adapter, you can add: 
    # history_index 
    # history_show 
    end 
end 

は、ここで私は定期的にユーザーを作成したと私は正確にroles_maskの使用を理解していない User.first.update_attribute :role, 'admin'

を使用してadminには役割属性の変更私のschema.rb

create_table "users", force: :cascade do |t| 
    t.string "email",     default: "", null: false 
    t.string "encrypted_password",  default: "", null: false 
    t.string "reset_password_token" 
    t.datetime "reset_password_sent_at" 
    t.datetime "remember_created_at" 
    t.integer "sign_in_count",   default: 0, null: false 
    t.datetime "current_sign_in_at" 
    t.datetime "last_sign_in_at" 
    t.string "current_sign_in_ip" 
    t.string "last_sign_in_ip" 
    t.string "confirmation_token" 
    t.datetime "confirmed_at" 
    t.datetime "confirmation_sent_at" 
    t.string "unconfirmed_email" 
    t.datetime "created_at",       null: false 
    t.datetime "updated_at",       null: false 
    t.string "name" 
    t.string "username" 
    t.string "role" 
    t.integer "roles_mask" 
end 

add_index "users", ["confirmation_token"], name: "index_users_on_confirmation_token", unique: true 
add_index "users", ["email"], name: "index_users_on_email", unique: true 
add_index "users", ["reset_password_token"], name: "index_users_on_reset_password_token", unique: true 
add_index "users", ["username"], name: "index_users_on_username", unique: true 

内のユーザーです。私のデータベースにroleroles_maskの両方を使用する必要がありますか?

答えて

0
  1. 私は完全にUser#rolesで何が起こっているか理解していないが、任意に0のrole_mask(管理者のインデックス)を割り当てた後、私は空の配列を得ました。私はこれがあなたが予期していた行動だとは思わない。

  2. ロールのチェック(has_role?)では、ユーザーの作成後に割り当てられなかったrole_maskが使用されています。

これらの定型コードの一部を削減するために、私はActiveRecord.enumを使用すると便利だと思います。デフォルトの役割を割り当てる

#models/user.rb 
class User < AR::Base 
    enum roles: %i[admin moderator banned] 
end 

ノートでは、あなたのDBまたはafter_createにそれを設定することができます。

#models/ability.rb 
class Ability 
    include CanCan::Ability 
    def initialize(user) 
    can :read, :all     # allow everyone to read everything 
    if user && user.admin? 
     can :access, :rails_admin  # only allow admin users to access Rails Admin 
     can :dashboard     # allow access to dashboard 
     if user.admin? 
     can :manage, :all    # allow superadmins to do anything 
     end 
    end 
    end 
end 

またuser.admin!

することにより、特定のユーザーに役割を割り当てることができます