A User can have many roles, but only one role per Brand.
Class User < AR::Base
has_and_belongs_to_many :roles, :join_table => "use开发者_JAVA技巧r_brand_roles"
has_and_belongs_to_many :brands, :join_table => "user_brand_roles"
end
The problem with this setup is, how do I check the brand and the role at the same time?
Or would I better off with a BrandRole model where different roles can be set up for each Brand, and then be able to assign a user to a BrandRole?
Class User < AR::Base has_many :user_brand_roles has_many :brand_roles, :through => :user_brand_roles end
Class BrandRole < AR::Base belongs_to :brand belongs_to :role end
Class UserBrandRole < AR::Base belongs_to :brand_role belongs_to :user end
This way I could do a find on the brand for the user:
br = current_user.brand_roles.where(:brand_id => @brand.id).includes(:brand_role)
if br.blank? or br.role != ADMIN
# reject access, redirect
end
This is a new application and I'm trying to learn from past mistakes and stick to the Rails Way. Am I making any bad assumptions or design decisions here?
Assuming Roles,Brands are reference tables. You can have a single association table Responsibilities with columns user_id, role_id, brand_id. Then you can define
Class User < AR::Base
has_many : responsibilities
has_many :roles, :through => responsibilities
has_many :brands,:through => responsibilities
end
Class Responsibility < AR::Base
belongs_to :user
has_one :role
has_one :brand
end
The you can define
Class User < AR::Base
def has_access?(brand)
responsibility = responsibilities.where(:brand => brand)
responsibility and responsibility.role == ADMIN
end
end
[Not sure if Responsibility is the term used in your domain, but use a domain term instead of calling it as user_brand_role]
This is a conceptual thing. If BrandRole is an entity for your application, then your approach should work. If BrandRole is not an entity by itself in your app, then maybe you can create a UserBrandRole model:
class User < AR::Base
has_many :user_brand_roles
end
class Brand < AR::Base
has_many :user_brand_roles
end
class Role < AR::Base
has_many :user_brand_roles
end
class UserBrandRole < AR::Base
belongs_to :user
belongs_to :brand
belongs_to :role
validates_uniqueness_of :role_id, :scope => [:user_id, :brand_id]
end
精彩评论