目前,我为餐厅设置了 CRUD 资源。一个所有者拥有_许多餐厅和一个餐厅属于_一个所有者。任何用户都可以访问餐厅#index 和#show 视图。然而,为了创建一个新的餐厅,业主必须登录。我实施了设计,这工作正常。我的问题是确保 current_owner 在能够编辑、更新或销毁餐厅之前拥有餐厅。
我在创建 before_filter 时遇到问题,它将检查登录的所有者 (current_owner) 是否是登录的所有者试图查看的那家餐厅的所有者。
在设置 before_filter 之前,我快速创建了一个 #check_if_owner 方法并将其放在编辑操作中。如果所有者不拥有餐厅,则应将其重定向到上一页。但是,由于某种原因,我收到以下错误:
ActiveRecord::RecordNotFound in RestaurantsController#edit
Couldn't find Restaurant with id=4 [WHERE "restaurants"."owner_id" = 1]
我不确定为什么会发生这种情况,因为当我在控制台中运行 #check_ownership 方法时它返回 false,如果 current_owner 不拥有餐厅,这正是我希望该方法执行的操作。如果它在控制台中返回 false,用户不应该被重定向到上一页而不是接收 RecordNotFound 错误吗?我不确定为什么会这样。
发布的是其余的代码...
class RestaurantsController < ApplicationController
before_filter :authenticate_owner!, except: [:index, :show]
# before_filter :check_if_owner, only: [:edit, :update, :destroy]
def index
@restaurants = Restaurant.all
end
def show
@restaurant = Restaurant.find(params[:id])
end
def new
@restaurant = current_owner.restaurants.new
end
def create
@restaurant = current_owner.restaurants.build(params[:restaurant])
if @restaurant.save
redirect_to restaurants_path
else
flash[:error] = "<ul>" + @restaurant.errors.full_messages.map{|o| "<li>" + o + "</li>" }.join("") + "</ul>"
redirect_to new_restaurant_path
end
end
def edit
check_if_owner(Restaurant.find(params[:id]))
@restaurant = current_owner.restaurants.find(params[:id])
end
def update
@restaurant = current_owner.restaurants.find(params[:id])
@restaurant.update_attributes(params[:restaurant])
redirect_to restaurant_path(@restaurant)
end
def destroy
@restaurant = current_owner.restaurants.find(params[:id])
@restaurant.destroy
redirect_to restaurants_path
end
private
def check_if_owner(restaurant)
debugger
if current_owner.check_ownership(restaurant)
return
else
redirect_to :back
end
end
end
class Owner < ActiveRecord::Base
# Include default devise modules. Others available are:
# :token_authenticatable, :confirmable,
# :lockable, :timeoutable and :omniauthable
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :trackable, :validatable
# Setup accessible (or protected) attributes for your model
attr_accessible :email, :password, :password_confirmation, :remember_me, :name
# attr_accessible :title, :body
has_many :restaurants
validates :name, presence: true
validates :email, presence: true
def check_ownership(restaurant)
!self.restaurants.find_by_id(restaurant.id).nil?
end
end