[英]User Roles in Ruby on Rails
這可能更像是一個概念性問題。 我有一個用戶表,我需要為每個用戶提供角色。 例如,我希望一些用戶創建客戶,一些用戶只能查看客戶。 我想我可以創建一個這樣的關聯:
User has_one :role
Role belongs_to :user
通過這種結構,我可以在Role
模型上創建boolean
字段,例如can_create_customer
。 如果我這樣做,那么我可以使用以下代碼來檢查基於每個用戶的權限:
if role.can_create_customer?
Customer.create(name: "Test")
end
有沒有更好的方法來完成同樣的事情?
這就是我如何做用戶角色和權利。
我創建了以下模型:
class Role < ApplicationRecord
has_and_belongs_to_many :users
has_and_belongs_to_many :rights
validates :name, presence: true
end
class Right < ApplicationRecord
has_and_belongs_to_many :roles
validates :name, presence: true
end
確保在數據庫中設置了適當的約束和索引:
add_index :roles, :name, unique: true
add_index :rights, :name, unique: true
從那里,您將需要roles_users
和rights_roles
連接表(因為它是多對多的)
然后在種子中我創建了一些角色和權利:
role_admin = Role.create!(name: 'admin')
role_admin.rights.create!(name: 'full_access')
role_cm = Role.create!(name: 'company_manager')
role_cm.rights.create!(name: 'edit_company')
role_cm.rights.create!(name: 'edit_all_invoices')
role_cm.rights.create!(name: 'edit_all_users')
然后,您需要為用戶分配一個或多個角色
current_user.roles << Role.find_by(name: 'company_manager')
現在,我只需檢查登錄時的角色/權限,並將其與user_id
一起存儲在會話中
def session_login(user)
session[:user_id] = user.id
session[:rights] = user.list_rights
end
並且您可以有效地訪問多個JOIN
sql語句的角色/權限。 您希望在登錄時將其存儲在會話中,因此您無需為每個請求進行此查詢。 但這確實意味着如果您在用戶會話中間更改角色/權限,則需要重新登錄並再次登錄以查看更新的更改
class User < ApplicationRecord
def list_roles
roles.map(&:name)
end
def list_rights
Right.joins(roles: :roles_users).where('roles_users.user_id = ?', id).map(&:name)
end
end
最后的筆記
現在,當您進行'檢查'時,請確保您根據權利進行驗證(不檢查用戶的角色)
你可以制作這個幫助方法
def current_user_has_right?(right)
return false unless session[:rights]
session[:rights].include? right
end
你可以授權! 例如,整個控制器以這種方式:
def authorize!
not_found unless current_user_has_right?('full_access')
end
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.