私は、ユーザーが自分に属していないレコードとの関連付けで「多くのスルー」の関係を作成できないようにしようとしています。
私のユーザーはlocation_usersを通じて多くの場所を持っています。そして、彼らの場所には、location_shopsを通じて多くのショップがあります。現在CanCanで保護されているものがあります。
class User < ActiveRecord::Base
has_many :locationusers
has_many :locations, :through => :locationusers
end
class Location < ActiveRecord::Base
has_many :locationusers
has_many :users, :through => :locationusers
has_many :location_shops
has_many :shops, :through => :location_shops
end
class Shop < ActiveRecord::Base
has_many :location_shops
has_many :locations, :through => :location_shops
end
そして私のカンカン能力
class Ability
can [:manage], Shop, { :locationusers => {:user_id => user.id }}
can [:manage], Location, { :locationusers => {:user_id => user.id }}
end
この設定で場所の作成/編集を処理でき、ユーザーは自分の場所/ショップのみを表示/編集できます。
問題は、これらの関係の作成です。
ユーザーが自分に属していないロケーションIDを投稿すると、関係を作成する権限があるかどうかに関係なく、関係が作成されます。確かに、彼らはこの関係を見ることができませんが、私はそもそも作成を防ぐ必要があります。
たとえば、ID314の単一の場所を持つユーザー
>> User.last.locations.map(&:id)
=> [314]
新しいショップを作成するときに、投稿されたパラメータを変更すると、次のようになります。
:shop=>{:shop_name=>"Ye Old Shoppe", :location_ids => [1,2,3,314]}}
上記は明らかに4つの場所の関係を作成します。リレーションシップを作成する前にロケーションIDを検証するために必要です。
私が思いついたのは、モデルにbefore_addを追加することだけでした。
class Location
has_many :location_shops
has_many :shops, :through => :location_shops, :before_add => :check_location_ownership
end
これは正しい方法ですか?もしそうなら、:check_location_ownershipはどのように見えるべきですか?または、関係の作成を防ぐためのより良い方法はありますか?