Ruby on rails 在Rails 4中使用minitest测试强参数

Ruby on rails 在Rails 4中使用minitest测试强参数,ruby-on-rails,ruby-on-rails-4,minitest,Ruby On Rails,Ruby On Rails 4,Minitest,我是Rails新手,我想用控制器测试来测试我设置的书籍模型的强参数。我使用的是Minitest和Rails 4 图书型号: class Book < ActiveRecord::Base validates :title, presence: true, length: { in: 1..150 } end 我对测试的想法——确实失败了,因为它创建了一个条目: assert_no_difference('Book.count') do post :create, book: {

我是Rails新手,我想用控制器测试来测试我设置的书籍模型的强参数。我使用的是Minitest和Rails 4

图书型号:

class Book < ActiveRecord::Base
  validates :title, presence: true, length: { in: 1..150 }
end
我对测试的想法——确实失败了,因为它创建了一个条目:

assert_no_difference('Book.count') do
  post :create, book: {
    id: 123,
    title: "Lorem ipsum"
  }
end

如何使测试变为绿色,以及使用控制器测试来测试强参数是否正确?

由于Rails会删除所有未经许可的参数而不是
许可
,将创建新记录,因此测试将变为红色


尽管如此,当提交未列出的参数时,可以使用该方法引发异常。

我正在寻找几乎相同问题的答案。在使用Rails 5时,我最终提出了一个解决方案(如果您愿意,可以称之为解决方案:-),用于测试不需要的参数是否实际通过。在我(此处简化)的例子中,我希望在创建新用户时不允许传递一些“安全关键”参数

在控制器中(仅允许
电子邮件
密码
):

在集成测试中:

test "not permitted signup data submitted" do
    new_user_email = "tester_" + (0...10).map { ('0'..'9').to_a[rand(26)] }.join + "@testing.net"
    get signup_path
    assert_difference 'User.count', 1 do
        post signup_path, params: { user: { email: new_user_email, password: "testpassword", role_id: 1 } }
    end
    user = User.last
    assert user.email == new_user_email
    assert user.role_id == nil
end

在这里,我提交了一个附加的“敏感”参数
role\u id
,其值为
1
(admin)。我希望创建用户。然后我读到新创建的用户,并希望它具有
role\u id
empty(
nil
)。要使测试失败,我将
:role_id
添加到
用户参数
。移除它,使测试通过。显然,如果属性不能为nil(在SQL中也称为NULL),则可以测试存储的默认值,而不是提交的值。

为什么不创建条目?我的想法是,由于给定的
id
参数,它不应该创建记录。或者Rails——只是大声想一想——会拒绝所有未列入白名单的参数吗?这就是为什么我的测试要创建一个条目?未经允许的参数将被删除。ook。谢谢你的洞察力:)我自己回答了这个问题-希望它能帮助其他刚接触Rails的人。我真的不想在我只希望测试失败/通过时提出一个异常,所以这不是一个真正的解决方案。
    private
        def user_params
            params.require(:user).permit(:email, :password)
        end
test "not permitted signup data submitted" do
    new_user_email = "tester_" + (0...10).map { ('0'..'9').to_a[rand(26)] }.join + "@testing.net"
    get signup_path
    assert_difference 'User.count', 1 do
        post signup_path, params: { user: { email: new_user_email, password: "testpassword", role_id: 1 } }
    end
    user = User.last
    assert user.email == new_user_email
    assert user.role_id == nil
end