Reputation: 31
I installed devise in a rails app. If a user is log in he could access to every other users edit pages.
For example, i'm user_id 2, i can edit profile of user 1/3/4/5.....when i modify params manually in the route.
Here my App Controller :
class ApplicationController < ActionController::Base
protect_from_forgery
before_action :authenticate_user!
before_action :configure_permitted_parameters, if: :devise_controller?
def configure_permitted_parameters
# For additional fields in app/views/devise/registrations/new.html.erb
devise_parameter_sanitizer.permit(:sign_up, keys: [:first_name, :last_name, :company, :position, :office_phone, :mobile_phone, :address, :description, :radius, :photo_company_logo, :photo_presentation, photos_projet_1: [], photos_projet_2: [], photos_projet_3: [], photos_projet_4: []])
# For additional in app/views/devise/registrations/edit.html.erb
devise_parameter_sanitizer.permit(:account_update, keys: [:first_name, :last_name, :company, :position, :office_phone, :mobile_phone, :address, :description, :radius, :photo_company_logo, :photo_presentation, photos_projet_1: [], photos_projet_2: [], photos_projet_3: [], photos_projet_4: []])
end
end
Here my User Controller :
class UsersController < ApplicationController
skip_before_action :authenticate_user!, only: [:index, :show]
before_action :set_user, only: [:show, :edit, :update]
def index
@client = Client.new
@users = User.all
@users = User.where.not(latitude: nil, longitude: nil)
@hash = Gmaps4rails.build_markers(@users) do |user, marker|
marker.lat user.latitude
marker.lng user.longitude
end
end
def show
@client = Client.new
@user = User.find(params[:id])
end
def new
@user = User.new
end
def create
@user = User.new(user_params)
@user.save
redirect_to users_path
end
def edit
@user = User.find(params[:id])
end
def update
@user = User.find(params[:id])
@user.update(user_params)
redirect_to user_path(@user)
end
private
def user_params
params.require(:user).permit(:company, :first_name, :last_name, :position, :mobile_phone, :office_phone, :email, :address, :description, :radius, :nettoyage_toiture, :photo_company_logo, :photo_presentation, photos_projet_1: [], photos_projet_2: [], photos_projet_3: [], photos_projet_4: [])
end
def set_user
@user = User.find(params[:id])
end
end
Here mu User model :
class User < ApplicationRecord
has_attachment :photo_presentation
has_attachment :photo_company_logo
has_many :projects, dependent: :nullify
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable and :omniauthable
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :trackable, :validatable
#geocoder for google maps
geocoded_by :address
after_validation :geocode, if: :address_changed?
end
Here my routes :
Rails.application.routes.draw do
ActiveAdmin.routes(self)
devise_for :users
root to: 'pages#home'
resources :users do
resources :projects
end
resources :clients, only: [:new, :create, :show]
mount Attachinary::Engine => "/attachinary"
# For details on the DSL available within this file, see http://guides.rubyonrails.org/routing.html
end
Thanks a lot!
Upvotes: 0
Views: 361
Reputation: 717
The problem is this:
def edit
@user = User.find(params[:id])
end
def update
@user = User.find(params[:id])
@user.update(user_params)
redirect_to user_path(@user)
end
If you don't want to users to be able to edit other users then you don't need these 2 methods. You can also change your route file to:
resources :users, except: [:edit, :update] do
resources :projects
end
Update
If you make the previous edits and type rake routes
in the terminal, you should see that Devise provides a controller action for editing users. It should be users/edit
without the :id
param. In the Devise::RegistrationsController, the edit method should just use the current_user
helper method for editing the currently logged in user's account information.
If you do want admin user's to be able to edit other users then you'll want to read about one of the following Gems
With these gems you can define which user "roles" are allowed to edit other users based on their roles. You can also use these gems to give permission to create, read, update, delete other resources.
Upvotes: 1
Reputation: 230296
Devise is an authentication library. You have authorization problem. So, you should use something for the authorization. I use CanCan. With it, you can define privileges like this:
can :edit, User, id: current_user.id
If you don't want to learn another library, you can always do ghetto-authorization in your controllers.
class UsersController
before_action :can_edit_only_self, only: [:edit, :update, :destroy]
private
def can_edit_only_self
redirect_to root_path unless params[:id] == current_user.id
end
end
* authentication - I know who you are
* authorization - I know what you are allowed to do
Upvotes: 1