Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Rails: Only allow admin user to create new users in Rails with Devise (No external modules)

Currently, my Users database has a column called "admin" with a boolean value and the default set to false. I have one admin user seeded into the database.

How do write my application so that users who are the admin can create new users, but users who are not cannot? (Also, users should be created only by the admin)

It seems like there should be a simple way to do this in devise that does not involve using some external module. So far however, I have not been able to find a satisfactory answer.

I would be more likely to mark the solution which is devise only. (One that is simply standard MVC/Rails solution a plus) However, if there really is a better way to do it that doesn't involve CanCan I may accept that too.

NOTE:

I have been searching around for a while and I've found several other stackoverflow questions that are very similar to this one, but either don't quite answer the question, or use other non-devise modules. (Or both)

like image 634
0112 Avatar asked Jul 21 '14 21:07

0112


1 Answers

To implement the authorization, use a method on the controller

Exactly as suggested by @diego.greyrobot

class UsersController < ApplicationController
  before_filter :authorize_admin, only: :create

  def create
    # admins only
  end

  private

  # This should probably be abstracted to ApplicationController
  # as shown by diego.greyrobot
  def authorize_admin
    return unless !current_user.admin?
    redirect_to root_path, alert: 'Admins only!'
  end
end

To sidestep the Devise 'already logged in' problem, define a new route for creating users.

We will simply define a new route to handle the creation of users and then point the form to that location. This way, the form submission does not pass through the devise controller so you can feel free to use it anywhere you want in the normal Rails way.

# routes.rb
Rails.application.routes.draw do

  devise_for :users
  resources :users, except: :create

  # Name it however you want
  post 'create_user' => 'users#create', as: :create_user      

end

# users/new.html.erb
# notice the url argument
<%= form_for User.new, url: create_user_path do |f| %>
  # The form content
<% end %>
like image 158
Adam Waselnuk Avatar answered Sep 17 '22 15:09

Adam Waselnuk