Defining Roles Using Rolify

I am trying to create an application with Rails 4.

I am looking at role management and want to use Rolify because it supports instance level role assignment.

For others who are looking at the same issue, there are 2 really good answers below (I can only mention one, but I used both). See the answers of lorefnon and Cyb3rDud3 below). I still understand this, but did the migration with an array (as lorefnon shows) and controller / route functions (as Cyb3rDud3 shows).

What completely puzzles me is that all the documents for Rolify pearls use a console to define roles.

How to define roles in my code?

Others on this board have asked questions that reference them, defining roles in the db: seed file. I do not want to do this because I want to control who uses my seed file more tightly than who can create roles.

Where are you doing this?

All examples show that this is done from the console. I want to define a list of roles, and then I want to grant permissions for roles (I want to use pundit for this part).

I have a user model. The other gem that I looked at was a role model. He asks to create an array of roles in the user model. It's just so obvious that you have to do it in Rolify - that none of the docs give you this step?

Where do you define the roles?

+4
3

, , Rolify .

Rolify - ​​, . , , . , - - .


, , - ?

:

1. .

, / .

(, , ..) (, , ..).

, , - . :

1.1. - , // . Rails.

, . , , (. ).

:

//20151204083556_create_application_roles.rb

class CreateApplicationRoles < ActiveRecord::Migration
  def up
    ['admin', 'support', 'editor'].each do |role_name|
      Role.create! name: role_name
    end
  end
  def down
    Role.where(name: ['admin', 'support', 'editor']).destroy_all
  end

end

, , . data-migrate - , .

add_role remove_role, rolit. .

1.2 // . .

. create , .. , .

2.

, // . , - / .

1.2, // rails.


, .

Rolify ( ), , .

Rollify tables

+5

, , @user2860931, , , , . , , - , pmo .

, . Devise Rolify .

, Devise, . Rolify gem. . , : https://github.com/RolifyCommunity/rolify. GEM, , . .

has_and_belongs_to_many Users.

, Create Read (show) Update Delete (CRUD) , seeds.rb, .

#Seeding the Role table
#
p "Removing existing #{Role.all.count} roles"
Role.destroy_all
p "Creating 7 roles"
[:user, :admin, :portfolio_manager, :programme_manager,     :project_manager, :coordinator, :pmo].each do |role|
  Role.create( name: role )
end
p "Should have created 7 Roles, roles created: #{Role.all.count}"

, , , . ,

rake db: seed

. , .

. Devise , , , , , . , .

users_controller.rb

class UsersController < ApplicationController
  before_action :set_user, only: [:show, :edit, :update]

  def index
    @users = User.all
  end

  def show
  end

  def edit
  end

  def update
    respond_to do |format|
      if @user.update(user_params)
        # TODO: Move hardcode flash message into language file
        format.html { redirect_to @user, notice: 'User was successfully updated.'}
        format.json { render :show, status: :ok, location: @user }
      else
        format.html { render :edit }
        format.json { render json: @user.errors, status: :unprocessable_entity }
      end
    end
  end

  private

  def set_user
    @user = User.find(params[:id])
  end

  def user_params
    params.require(:user).permit(:username, :email, {role_ids: []})
  end
end

, Devise. , , , , , .

routes.rb

Rails.appliction.routes.draw do
  devise_for :users
  root 'pages#home'
  resources :users    #must be after devise
end

, , . :

                  Prefix Verb   URI Pattern                      Controller#Action
        new_user_session GET    /users/sign_in(.:format)       devise/sessions#new
            user_session POST   /users/sign_in(.:format)       devise/sessions#create
    destroy_user_session DELETE /users/sign_out(.:format)      devise/sessions#destroy
           user_password POST   /users/password(.:format)      devise/passwords#create
       new_user_password GET    /users/password/new(.:format)  devise/passwords#new
      edit_user_password GET    /users/password/edit(.:format) devise/passwords#edit
                         PATCH  /users/password(.:format)      devise/passwords#update
                         PUT    /users/password(.:format)      devise/passwords#update
cancel_user_registration GET    /users/cancel(.:format)        devise/registrations#cancel
       user_registration POST   /users(.:format)               devise/registrations#create
   new_user_registration GET    /users/sign_up(.:format)       devise/registrations#new
  edit_user_registration GET    /users/edit(.:format)          devise/registrations#edit
                         PATCH  /users(.:format)               devise/registrations#update
                         PUT    /users(.:format)               devise/registrations#update
                         DELETE /users(.:format)               devise/registrations#destroy
             user_unlock POST   /users/unlock(.:format)        devise/unlocks#create
         new_user_unlock GET    /users/unlock/new(.:format)    devise/unlocks#new
                         GET    /users/unlock(.:format)        devise/unlocks#show
                    root GET    /                              pages#home
                   about GET    /about(.:format)               pages#about
                 contact GET    /contact(.:format)             pages#about
                   users GET    /users(.:format)               users#index
                         POST   /users(.:format)               users#create
                new_user GET    /users/new(.:format)           users#new
               edit_user GET    /users/:id/edit(.:format)      users#edit
                    user GET    /users/:id(.:format)           users#show
                         PATCH  /users/:id(.:format)           users#update
                         PUT    /users/:id(.:format)           users#update
                         DELETE /users/:id(.:format)           users#destroy

, , , , . , css, , .

, index.html.erb /app/views/users. show.html.erb , . .

index.html.erb

<!-- TODO: Tidy up this file and make it look good -->
<!-- TODO: Remove hard coded text to a locale file -->
<% @users.each do |user| %>
  <p>
    <%= link_to "#{user.username}<#{user.email}>", user %>
    <%= link_to "edit", edit_user_path(user) %>
  </p>
<% end %>

show.html.erb

<!-- TODO: Tidy up this file and make it look good -->
<!-- TODO: Remove hard coded text to a locale file -->
<p>
  Username: <%= @user.username %>
</p>
<p>
  Email address: <%= @user.email %>  
</p>

<%= link_to "Back", users_path %>

edit.html.erb

<!-- TODO: Tidy up this file and make it look good -->
<!-- TODO: Remove hard coded text to a locale file -->
<p>
 Username: <%= @user.username %>
</p>
<p>
 Email address: <%= @user.email %>
</p>

<%= form_for @user do |f| %>
  <% Role.all.each do |role| %>
    <%= check_box_tag "user[role_ids][]", role.id, @user.role_ids.include?(role.id) %>
    <%= role.name %></br>
  <% end %>
  <%= f.submit %>
<% end %>

<%= link_to "Back", users_path %>

, , , . :

, , , .

+5

, , , . : ( , , ):

, "" , , . ,

  • role: integer User . ( , , )
  • user.rb () enum, :

    class User < ActiveRecord::Base
      devise :registerable, #...
    
      enum role: [:admin, :normal, :premium, :moreRolesHere ]
      after_initialize :set_default_role, :if => :new_record?
    
      def set_default_role
        self.role ||= :normal
      end
    
    end
    
  • def , , , :

    #let suppose we want to make premium the current user
    current_user.premium!
    
    #or someone else to be admin
    user = User.first
    user.admin!
    
  • , , :

    #see if the current user is admin
    if current_user.role == "admin"
      #do some admin stuff
    end    
    

, ,

, . , , . , , :

  • Role role: string
  • , , roles_controller.rb
  • , , (, , ), , . , , .
  • , , , . role_ids: text ( , , , ), . user.rb get_roles def, :

    class User < ActiveRecord::Base
      devise :registerable, #...
    
      serialize :role_ids
    
      #will return you an array of roles-(strings) of the user
      def get_roles
        roles = []
        role_ids.each do |role_id|
          roles << Role.find(role_id).role
        end
        return roles      
      end
    
      #ask if this user has some role-(string)
      def has_role(role)
        roles = get_roles
        return roles.include?(role)
      end
    
    end
    
  • , , , , def, .

,

This approach does not use any gems related to role management or authorization, such as in the market: pundit , cancan , rolify . Leave some links to you if you are skeptical of my approach and want your hands to be dirty.

+2
source

Source: https://habr.com/ru/post/1617686/


All Articles