У меня возникли проблемы с тем, чтобы незарегистрированные/не зарегистрированные пользователи просматривали индекс и показывали страницы для раздела блога. Я использую Pundit для авторизации и понимаю, что на данный момент у меня есть политики, запрещающие не пользователям просматривать какую-либо часть раздела блога, но я понятия не имею, как обойти это, чтобы не иметь политики для индекса и показать страницу.Разрешить незарегистрированным пользователям просматривать содержимое с помощью pundit
Моя цель состоит в том, чтобы иметь следующее:
Разрешить администратора и редакторы для просмотра, создания, редактирования и удаления блоги
Эта часть работает Pefect
Allow зарегистрировано пользователи для просмотра блогов
Эта часть работает отлично
Разрешить незарегистрированные/не зарегистрированных пользователей, чтобы просмотреть блоги
Эта часть не работает
При попытке просмотра страницы индекса, как незарегистрированный/не зарегистрированный пользователь, я получаю сообщение о запрете доступа, которое выходит из моего контроллера приложения, который делает то, что он должен делать, учитывая текущие политики.
Итак, мой вопрос: как мне изменить свои правила, чтобы пользователи, не зарегистрированные или не зарегистрированные, просматривали только индекс и показывали страницы?
Контроллер Применение
class ApplicationController < ActionController::Base
include Pundit
rescue_from Pundit::NotAuthorizedError, with: :user_not_authorized
# Prevent CSRF attacks by raising an exception.
# For APIs, you may want to use :null_session instead.
protect_from_forgery with: :exception
before_filter :configure_permitted_parameters, if: :devise_controller?
private
def user_not_authorized(exception)
flash[:danger] = "Access denied. You are not authorized to view that page."
redirect_to (request.referrer || root_path)
end
protected
def configure_permitted_parameters
devise_parameter_sanitizer.permit(:sign_up) { |u| u.permit(:username, :email, :password, :password_confirmation, :remember_me) }
devise_parameter_sanitizer.permit(:sign_in) { |u| u.permit(:username, :email, :password, :remember_me) }
devise_parameter_sanitizer.permit(:account_update) {|u| u.permit(:username, :email, :password, :password_confirmation, :current_password)}
end
end
Политика Применение
class ApplicationPolicy
attr_reader :user, :record
def initialize(user, record)
raise Pundit::NotAuthorizedError, "You must be logged in to perform this action" unless user
@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 PostPolicy < ApplicationPolicy
attr_reader :post
class Scope < Scope
def resolve
if user&.admin?&.editor?&.user?
scope.all
else user != admin? || editor? || user?
scope
end
end
end
def permitted_attributes
if user.admin? || user.editor?
[:title, :body, :image, :permalink, :description, :tag_list, :username]
else
[:title, :body, :image, :username]
end
end
def index?
true
end
def show?
true
end
def new?
user.admin? || user.editor?
end
def create?
user.admin? || user.editor?
end
def update?
user.admin? || user.editor?
end
def destroy?
user.admin? || user.editor?
end
end
Сообщение Контроллер
class PostsController < ApplicationController
before_action :set_post, only: [:show, :edit, :update, :destroy]
after_action :verify_authorized, only: [:destroy]
def index
@meta_title = "Blog"
@meta_description = "page description here"
@posts = Post.all.order("created_at DESC").paginate(:page => params[:page], :per_page => 4)
end
def show
@meta_title = @post.title
@meta_description = @post.description
end
def new
@meta_title = "Add New Blog"
@meta_description ="Add a new blog."
@post = Post.new
authorize @post
end
def edit
@meta_title = "Edit Blog"
@meta_description ="Edit an existing blog."
authorize @post
end
def create
@post = Post.new
@post.update_attributes(permitted_attributes(@post))
@post.user = current_user if user_signed_in?
authorize @post
if @post.save
redirect_to @post, notice: 'Post was successfully created.'
else
render :new
end
end
def update
@post = Post.find(params[:id])
if @post.update_attributes(permitted_attributes(@post))
authorize @post
redirect_to @post, notice: 'Post was successfully updated.'
else
render :edit
end
end
def destroy
if @post.present?
@post.destroy
authorize @post
else
skip_authorization
end
redirect_to posts_url, notice: 'Post was successfully deleted.'
end
private
# Use callbacks to share common setup or constraints between actions.
def set_post
@post = Post.find(params[:id])
end
# Only allow the white list through.
def post_params
params.require(:post).permit(policy(@post).permitted_attributes)
end
end
Я видел подобный вопрос спросил Pundit policy_scoper error, но решение, предложенное не кажется, что работать в моем случае.
Похоже, что он даже не должен ударять по вашей политике из указателя или действия шоу, так как вы не вызываете 'authorize' в любом действии. Что произойдет, если вы добавите 'authorize Post' в действие вашего индекса? Я бы подумал, так как вы возвращаетесь в PostPolicy.index? что он должен работать. – Scott
Привет @scott Я попробовал как, так и . не имел эффекта и <@post> создал ошибку . <@post> работает для всех других действий в индексе, как вы можете видеть в контроллере. –
Nate
@Scott есть ли у вас какие-либо другие идеи или идеи? Я все еще изо всех сил пытаюсь преодолеть эту проблему. Я попробовал все: добавив в индекс skip_authorization в индекс, чтобы удалить индекс и показать def из политики для сообщений, а затем как должности, так и политики приложений. Независимо от того, что я до сих пор получаю флеш-сообщение «Не авторизован» при попытке доступа в качестве пользователя без входа/гостя. – Nate