Le plus grand con avec has_and_belongs_to_many
est qu'il ne permet pas de joindre des données à la table de jointure. Au lieu d'utiliser une jointure modèle:
class User < ApplicationRecord
has_many :user_pages
has_many :pages, through: :user_pages
end
class Page < ApplicationRecord
has_many :user_pages
has_many :users, through: :user_pages
end
class UserPage < ApplicationRecord
belongs_to :user
belongs_to :page
end
Cela fonctionne comme has_and_belongs_to_many
sauf son pas sans tête - vous pouvez interroger directement UserPage
. La seule chose que vous devez faire en plus de créer le modèle UserPage est de renommer la table de users_pages
à user_pages
(ou pages_users
à page_users
).
class RenameUsersPages < ActiveRecord::Migration[5.0]
def change
rename_table('users_pages', 'user_pages')
end
end
Cela est nécessaire car les rails relieront la table à la constante Users::Page
autrement.
Maintenant vous pouvez facilement attacher un drapeau admin
sur le tableau UserPage
.
class AddPageAdministratorToUserPages < ActiveRecord::Migration[5.0]
change_table :users do |t|
t.boolean :admin, default: false
end
end
Maintenant, nous pouvons vérifier si un utilisateur est un administrateur en vérifiant si un enregistrement existe dans user_pages
:
class Ability
include CanCan::Ability
def initialize(user)
can :manage, Page do |p|
p.user_pages.exists?(admin: true, user: user)
end
end
end
Vous pouvez consulter le [joyau rolify] (https: // GitHub. com/RolifyCommunity/rolify) qui fournit un cadre pour l'autorisation basée sur les rôles dans de nombreuses classes. – max