Rails 中的验证冲突
Validations conflicts in Rails
我正在做一个项目,我遇到了一个我试图解决但没有进展的问题。
所有这些都是在我开始实现 Forgot Password
重置密码功能时发生的。我有一个 User Model
,它验证了 password
和 password_confirmation
。我使用这些进行注册并且工作正常。
但是对于此功能,我使用了一个名为 PasswordResets
的新控制器。我正在为我的用户 table 生成一个名为 password_reset_token
的字符串。还有password_reset_sent_at
记录了用户要求重置的时间。过程是这样的;
1) The User clicks Forgot Password
?
2) He is redirected to a page where he is asked to enter his email.
3) Controller checks if the email is present in database, if yes then ;
3.1) I generate a random password_token
by using SecureRandom
and also time when he started the request.
3.2) Now the save happens here for sending the mail to user. Here the problem occurs. The password_reset_token
is not getting saved into table.
其背后的原因是我在 User.rb
中使用 password
和 password _confirmation
的验证。这里发生的动作是 :update
,因此在更新记录时要求 password
和 password_confirmation
与 password_reset_token
和时间一起发送。
但我尝试通过将验证保持为 :on => :create
来解决,现在它运行良好,但是当我使用 link 重置时,我的验证将不适用于 password
和 password_confirmation
。这对我来说就像一个僵局。我知道这有点令人困惑,我正在粘贴一些代码来理解问题。
我的 PasswordResets Controller
创建操作:
def create
user= User.find_by_email(params[:email])
if user
user.send_password_reset
UserMailer.password_reset(self).deliver
flash[:success] = "Email sent with password reset instructions."
redirect_to root_url
else
flash[:error] = "Email doesn't exit."
render 'password_resets/new'
end
end
我的 User Model
(user.rb)
class User < ActiveRecord::Base
has_secure_password
EMAIL_REGEX = /\A[a-z0-9._%+-]+@[a-z0-9.-]+\.[a-z]{2,4}\Z/i
validates_confirmation_of :password_confirmation
validates :username, :presence => true,
:uniqueness => true,
:length => {:within => 8..25}
validates :email, :presence => true,
:uniqueness => true,
:format => EMAIL_REGEX
validates :password, :length => {:within => 8..25}
validates :password_confirmation, :presence => true
def send_password_reset
generate_token(:password_reset_token)
self.password_reset_sent_at = Time.zone.now
save!
UserMailer.password_reset(self).deliver
end
def generate_token(column)
begin
self[column] = SecureRandom.urlsafe_base64
end while User.exists?(column => self[column])
end
end
错误显示在 send_password_reset
中的 save!
处。我附上一张图片。
我知道这个问题可以通过使用 :on=>:create
进行验证来解决,因为 :update
请求正在发生。但是当我在我的控制台中得到确认 link 并使用它时,密码验证和 password_confirmation 不起作用,因为这里的操作是 :update
。这就像一个僵局。
我真的很感谢任何帮助我走出迷宫的人。
谢谢。
您可以使用以下示例跳过验证。
def send_password_reset
generate_token(:password_reset_token)
self.password_reset_sent_at = Time.zone.now
self.save(validate: false)
UserMailer.password_reset(self).deliver
end
我正在做一个项目,我遇到了一个我试图解决但没有进展的问题。
所有这些都是在我开始实现 Forgot Password
重置密码功能时发生的。我有一个 User Model
,它验证了 password
和 password_confirmation
。我使用这些进行注册并且工作正常。
但是对于此功能,我使用了一个名为 PasswordResets
的新控制器。我正在为我的用户 table 生成一个名为 password_reset_token
的字符串。还有password_reset_sent_at
记录了用户要求重置的时间。过程是这样的;
1) The User clicks
Forgot Password
?2) He is redirected to a page where he is asked to enter his email.
3) Controller checks if the email is present in database, if yes then ;
3.1) I generate a randompassword_token
by usingSecureRandom
and also time when he started the request.
3.2) Now the save happens here for sending the mail to user. Here the problem occurs. Thepassword_reset_token
is not getting saved into table.
其背后的原因是我在 User.rb
中使用 password
和 password _confirmation
的验证。这里发生的动作是 :update
,因此在更新记录时要求 password
和 password_confirmation
与 password_reset_token
和时间一起发送。
但我尝试通过将验证保持为 :on => :create
来解决,现在它运行良好,但是当我使用 link 重置时,我的验证将不适用于 password
和 password_confirmation
。这对我来说就像一个僵局。我知道这有点令人困惑,我正在粘贴一些代码来理解问题。
我的 PasswordResets Controller
创建操作:
def create
user= User.find_by_email(params[:email])
if user
user.send_password_reset
UserMailer.password_reset(self).deliver
flash[:success] = "Email sent with password reset instructions."
redirect_to root_url
else
flash[:error] = "Email doesn't exit."
render 'password_resets/new'
end
end
我的 User Model
(user.rb)
class User < ActiveRecord::Base
has_secure_password
EMAIL_REGEX = /\A[a-z0-9._%+-]+@[a-z0-9.-]+\.[a-z]{2,4}\Z/i
validates_confirmation_of :password_confirmation
validates :username, :presence => true,
:uniqueness => true,
:length => {:within => 8..25}
validates :email, :presence => true,
:uniqueness => true,
:format => EMAIL_REGEX
validates :password, :length => {:within => 8..25}
validates :password_confirmation, :presence => true
def send_password_reset
generate_token(:password_reset_token)
self.password_reset_sent_at = Time.zone.now
save!
UserMailer.password_reset(self).deliver
end
def generate_token(column)
begin
self[column] = SecureRandom.urlsafe_base64
end while User.exists?(column => self[column])
end
end
错误显示在 send_password_reset
中的 save!
处。我附上一张图片。
我知道这个问题可以通过使用 :on=>:create
进行验证来解决,因为 :update
请求正在发生。但是当我在我的控制台中得到确认 link 并使用它时,密码验证和 password_confirmation 不起作用,因为这里的操作是 :update
。这就像一个僵局。
我真的很感谢任何帮助我走出迷宫的人。
谢谢。
您可以使用以下示例跳过验证。
def send_password_reset
generate_token(:password_reset_token)
self.password_reset_sent_at = Time.zone.now
self.save(validate: false)
UserMailer.password_reset(self).deliver
end