1

CanCan によって制御されるリンクの存在をテストしています。

before do
  @author = Fabricate(:author)
  visit new_user_session_path
  fill_in 'Email', :with => @author.email
  fill_in 'Password', :with => @author.password
  click_button 'Sign in'
  visit articles_path
end

it { should have_link 'New article', :href => new_article_path }

これは、テストしているビューです。

<% if can? :create, @articles %>
  <%= link_to 'New article', new_article_path %>
<% end %>

テストを実行すると失敗し、次のエラーが発生します。

失敗/エラー: { should have_link 'New article', :href => new_article_path }

   expected link "New article" to return something

ブラウザで手動でテストすると機能するため、これは奇妙です。能力クラスは次のとおりです。

class Ability
  include CanCan::Ability

  def initialize(user)
    user ||= User.new # Guest user

    if user.role? :admin
      can :manage, :all
    else
      can :read, :all

      if user.role?(:author)
        can :create, Article
        can :update, Article do |article|
          article.try(:author) == user
        end
        can :destroy, Article do |article|
          article.try(:author) == user
        end
      end
    end
  end
end

詳細については、ここに私の user および user_fabricator クラスを示します。

class User < ActiveRecord::Base
  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :trackable, :validatable

  attr_accessible :email, :password, :password_confirmation, :remember_me
  attr_accessible :name, :roles

  has_many :articles, :foreign_key => 'author_id', :dependent => :destroy

  ROLES = %w[admin moderator author]

  def roles=(roles)
    self.roles_mask = (roles & ROLES).map { |r| 2**ROLES.index(r) }.sum
  end

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

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

ユーザー ロールのメソッドは、RailsCasts エピソードの 1 つで Ryan Bates のメソッドに基づいています。製作者は次のとおりです。

Fabricator(:user) do
  email { sequence(:email) { |i| "user#{i}@example.com" } }
  name { sequence(:name) { |i| "Example User-#{i}" } }
  password 'foobar'
end

Fabricator(:admin, :from => :user) do
  roles ['admin']
end

Fabricator(:author, :from => :user) do
  roles ['author']
end

能力クラスを定義した方法と関係があるという予感がありますが、どこが間違っていたのかわかりません。どんな助けでも大歓迎です。ありがとう :)

4

1 に答える 1

0

ビューで、あなたがする場所

if can? :create, @articles

に配列を渡していると思いますがcan?、これは少し奇妙に思えます。

私の知る限り、このcan?メソッドはシンボルまたはクラスのいずれかを想定しています。

またはに置き換え@articlesてみてください。Article:articles

于 2012-04-10T13:09:20.200 に答える