0

我正在学习一门让我创建基本维基的课程。我绝对是新手。我需要限制用户简单地输入他们想直接在 URL 中查看的 wiki id(例如:wikis/5)。唯一能够查看 wiki 的人应该是该 wiki 的所有者、管理员或协作者。

我已经成功地限制了索引视图,以便登录用户只能看到他们自己的 wiki、公共 wiki 或他们合作的 wiki。

我试图在我的 WikiPolicy 中实现类似的代码,但它不起作用,我似乎找不到解决方案。如果用户登录,我现在的代码将显示 wiki。我知道我的逻辑是好的,因为我可以将 params[:id] 的值替换为“5”,它可以按预期工作。

wikis_controller.rb

def show
    @wiki = Wiki.find(params[:id])
    authorize @wiki
  end

wiki_policy.rb

def show?
    scope.where(:id => record.id).exists?
    current_wiki = Wiki.find(params[:id])
    collaborations = Collaboration.where(:user_id => user)
    collab_wikis = Wiki.where(id: collaborations.pluck(:wiki_id))
    collab_wikis.include?(current_wiki)
  end

这是我在 wiki_policy.rb 中使用的代码,用于返回一组特定用户有权查看的 wiki。我相信这是可行的,因为它正在查看所有 wiki,而不是依赖于用户试图查看的特定 wiki。

class Scope
     attr_reader :user, :scope

     def initialize(user, scope)
       @user = user
       @scope = scope
     end

     def resolve
       wikis = []
       if user.role?(:admin)
         wikis = scope.all # if the user is an admin, show them all the wikis
       elsif user.role?(:premium)
         collaborations = Collaboration.where(:user_id => user)
         collab_wikis = Wiki.where(id: collaborations.pluck(:wiki_id))
         all_wikis = scope.all
         all_wikis.each do |wiki|
           if !wiki.is_private || wiki.user_id == user.id || collab_wikis.include?(wiki)
              wikis << wiki # if the user is premium, only show them public wikis, or that private wikis they created, or private wikis they are a collaborator on
           end
         end
        else # this is the lowly standard user
          collaborations = Collaboration.where(:user_id => user)
          collab_wikis = Wiki.where(id: collaborations.pluck(:wiki_id))
          all_wikis = scope.all
          wikis = []
          all_wikis.each do |wiki|
            if !wiki.is_private? || wiki.user_id == user.id || collab_wikis.include?(wiki)
              wikis << wiki # only show standard users public wikis and private wikis they are a collaborator on
            end
          end
       end
       wikis # return the wikis array we've built up
     end
   end
4

1 回答 1

1

params在 wiki_policy.rb 中不可用,因为它没有在authorize方法中传递。authorize传递记录(因此Wiki找到的对象)和current_user对象。您可以再次跳过查找当前 wiki。此外,在此方法和其他动作(update?edit?等)中,您需要返回 true 或 false。因此,您需要根据您的规范确定用户是管理员、协作者还是所有者。

def show?
  record.user_id == user.id or Wiki.where(id: Collaboration.where(:user_id => user.id).pluck(:wiki_id)).include?(record) or user.role?(:admin)
end

这将为您提供真实或虚假的退货,并检查您需要授权的所有三项。如果你想改变它,你可以使用 if/else 语句,只要确保你return truereturn false所有可能性。

于 2015-01-21T18:27:38.960 回答