【问题标题】:How to test updating user's password in RSpec如何在 RSpec 中测试更新用户密码
【发布时间】:2020-11-06 11:56:24
【问题描述】:

我正在使用 Rails 5.2、Ruby 2.4.1 和 Rspec。我正在尝试使用 Rspec 进行自动化测试来更新用户的密码。我知道代码可以通过手动测试来工作。

RSpec 测试没有通过控制器中的@user.update_attributes(user_params) 条件,然后进入 else 条件。因此,我的 RSpec 测试表明密码仍然彼此相等。如何让我的 RSpec 测试通过条件?

方法如下

# Creates user, saves old password, generates a url for user to go to, updates password, reloads user, and test if old password equals new password
context "with a valid token" do
    it "updates the user's password and resets the token" do
        test_users = User.create(first_name: 'chase', last_name: 'dougherty', email: 'chase@gmail.com', password: '1', password_confirmation: '1')
        old_password = test_users.password
        test_users.generate_password_reset_token!
        patch :update, params: { id: test_users.password_reset_token, user: { password: 'newpassword', password_confirmation: 'newpassword' } }
        test_users.reload
        expect(test_users.password).to_not eq(old_password)
      end
    end

这里是控制器

# Finds user, test if update_attributes is true, updates password, logs user in, redirects user, displays flash
def update
    @user = User.find_by(password_reset_token: params[:id])
    if @user && @user.update_attributes(user_params)
      @user.update_attribute(:password_reset_token, nil)
      session[:user_id] = @user.id
      redirect_to '/maps'
      flash[:notice] = "Password updated"
    else
      flash[:notice] = "Password reset failure."
      render action: 'edit'
    end
  end

  private
  def user_params
    params.require(:user).permit(:password, :password_confirmation)
  end

【问题讨论】:

    标签: ruby-on-rails rspec automated-tests


    【解决方案1】:

    如果 update_attributes 行失败,您可能对 User 模型进行了一些验证,这些验证正在触发并导致它返回 false。

    另外,我建议不要在测试文件中“创建”用户对象。特别是因为第一次运行测试时它会创建条目,但之后每次它都会返回一个未保存到数据库中的用户实例(因为数据中的唯一性违规)并且测试可能不会运行为预计。

    除非您想在测试运行后清理您创建的用户对象。否则,您将需要使用 factory_bot 并将大多数模型和数据库调用存根。

    【讨论】:

    • 但这就是测试数据库的用途。
    【解决方案2】:

    如果您在user 模型中使用has_secure_password 方法,则可以使用此语法检查密码是否已更改:

    it "changes user's password" do
      expect { send_request }.to change { user.reload.authenticate(password) }.from(false).to(user)
    end
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-10-18
      • 1970-01-01
      • 2023-04-09
      • 1970-01-01
      相关资源
      最近更新 更多