changing password with authlogic - validation not catching blank inputs

假装没事ソ 提交于 2020-01-03 18:58:09

问题


I am trying to create a form to allow users to change their password:

View:

- form_tag change_password_users_path do

  = error_messages_for :user, :header_message => "Please Try Again", :message => "We had some problems updating your account" 
  %br

  = label_tag :password, "New password:"
  = password_field_tag "password"
  %br

  = label_tag :password_confirmation, "NConfirm new password:"
  = password_field_tag "password_confirmation"
  %br

  = submit_tag "Update Account"

Controller:

def change_password
  @user = current_user
  if request.post?
    @user.password = params[:password]
    @user.password_confirmation = params[:password_confirmation]
    if @user.save
      redirect_to user_path(current_user)
    else
      render :action => "change_password"
    end        
  end
end

Authlogic is catching validation errors when the password is 'too short' or the password doesn't match the confirmation, but doesn't do anything when the form is submitted with both fields blank. @user.save must be returning true, because I am redirected to 'user_path(current_user)'.

The password is not actually changed in the database.

Thanks for your help.


回答1:


I suggest you call @user.changed? like the following example to check for blank passwords:

def change_password
  @user = current_user
  if request.post?
    @user.password = params[:user][:password]
    @user.password_confirmation = params[:user][:password_confirmation]
    if @user.changed? && @user.save
      redirect_to user_path(current_user)
    else
      render :action => "change_password"
    end
  end
end



回答2:


I think you should also provide the params[:user][:current_password], otherwise you can not save the @user. And when I tested, I found the current_user will be lost after changing password, so you need update usersession.

Add a 'current_password' accessor to your user model

class User < ActiveRecord::Base   
  act_as_authentic   
  attr_accessor :current_password 
end

In the user controller

def change_password
  @user = current_user
  if @user.valid_password? params[:user][:current_password]
    @user.password = params[:user][:password]
    @user.password_confirmation = params[:user][:password_confirmation]
    if @user.changed? && @user.save
      UserSession.create(:login => @user.login, :password => params[:user][:password])
      redirect_to user_path(current_user)
    else
      render :action => "change_password"
    end
  end
end



回答3:


Apparently this is the intended behavior.

http://www.ruby-forum.com/topic/198836

At least I know now...

Thanks.




回答4:


Another way to do it is to exploit ActiveModel validation contexts. You will need to add a context-dependent validation to your User model:

validates :password, # :password_confirmation,
          :presence => {:message => 'Please enter your new password.'},
          :on => :reset_password

Then, in the controller it will be just:

def change_password
  @user = current_user
  if request.post?
    @user.password = params[:password]
    @user.password_confirmation = params[:password_confirmation]
    if @user.save(:context => :reset_password)
      redirect_to user_path(current_user)
    else
      render :action => "change_password"
    end        
  end
end

Hope it will suite ones who were not satisfied with other suggested solutions.



来源:https://stackoverflow.com/questions/1753822/changing-password-with-authlogic-validation-not-catching-blank-inputs

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!