Rails 5 - 如何使用Pundit

4

我已经有很长时间没有继续学习如何在我的Rails应用程序中使用Pundit,这已经是我两年的努力。现在我回来了,并且正在尝试学习如何使用Pundit。

我创建了一个全新的Rails 5应用程序并安装了Pundit。

我有一个用户资源,一个应用策略和一个用户策略。每个都有:

用户控制器:

def index
    # @users = User.all
    @users = policy_scope(User)
  end

应用策略

class ApplicationPolicy
  attr_reader :user, :record

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

  def index?
    true
  end

  def show?
    scope.where(:id => record.id).exists?
  end

  def create?
    false
  end

  def new?
    create?
  end

  def update?
    false
  end

  def edit?
    update?
  end

  def destroy?
    false
  end

  def scope
    Pundit.policy_scope!(user, record.class)
  end

  class Scope
    attr_reader :user, :scope

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

    def resolve
      scope
    end
  end
end

用户政策

class UserPolicy < ApplicationPolicy
  class Scope < Scope
    def resolve
      scope.where(user: user)
    end
  end


end

在我的用户索引中,我正在尝试按照 pundit gem 文档中的说明进行操作:

<% policy_scope(@users).each do |user| %>

我遇到了这个错误:
PG::UndefinedColumn: ERROR:  column users.user does not exist
LINE 1: SELECT "users".* FROM "users" WHERE "users"."user" = '566119...
                                            ^
: SELECT "users".* FROM "users" WHERE "users"."user" = '566119d2-54d8-4ab2-b7c5-f17c80b517f3' AND "users"."user" = '566119d2-54d8-4ab2-b7c5-f17c80b517f3'

有人能看出我是怎么开始走错路的吗?我甚至还没有尝试按照自己想要的方式定义范围,但目前为止这并不起作用。


1
也许你的意思是 scope.where(id: user.try(:id)) - slowjack2k
1个回答

1
class UserPolicy < ApplicationPolicy
  class Scope < Scope
    def resolve
      scope.where(user: user)
    end
  end
end

scope.where指的是User类(user.where),因为它在用户策略内部。

用户值是当前用户,由应用程序范围继承。

我猜测您想展示只有当前用户记录的作用域示例。然后,您可以按照上面的注释执行以下操作:

scope.where(id: user.try(:id))

同时因为您在控制器中定义了作用域

def index
  # @users = User.all
  @users = policy_scope(User)
end

在视图中不需要再定义另一个。

 <% policy_scope(@users).each do |user| %>

这是二选一的情况。在视图中,您可以简单地使用“users.each do...”。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接