如何测试 Rails 中的嵌套属性?

发布于 2024-10-21 11:47:02 字数 857 浏览 2 评论 0原文

我有一个 Rails 控制器,定义如下:

https://github.com/abonec /Simple-Store/blob/master/app/controllers/carts_controller.rb

购物车页面用户可以通过发布嵌套属性来指定line_items的数量。参数如下所示:

{ "cart" => {
  "line_items_attributes" => {
    "0" => {
      "quantity" => "2",
      "id" => "36" } } },
  "commit" => "Update Cart",
  "authenticity_token" => "UdtQ+lchSKaHHkN2E1bEX00KcdGIekGjzGKgKfH05So=",
  "utf8"=>"\342\234\223" }

在我的控制器操作中,这些参数保存如下:

@cart.update_attributes(params[:cart])

但我不知道如何在测试中测试此行为。 @cart.attributes 仅生成模型属性,而不生成嵌套属性。

我如何测试这种行为?如何在功能测试中使用嵌套属性模拟发布请求?

I have a rails controller, defined here:

https://github.com/abonec/Simple-Store/blob/master/app/controllers/carts_controller.rb

On the cart page a user can specify the quantity of line_items by posting nested attributes. The parameters look like this:

{ "cart" => {
  "line_items_attributes" => {
    "0" => {
      "quantity" => "2",
      "id" => "36" } } },
  "commit" => "Update Cart",
  "authenticity_token" => "UdtQ+lchSKaHHkN2E1bEX00KcdGIekGjzGKgKfH05So=",
  "utf8"=>"\342\234\223" }

In my controller action these params are saved like this:

@cart.update_attributes(params[:cart])

But I don't know how to test this behavior in a test. @cart.attributes only generates model attributes not nested attributes.

How can I test this behavior? How to simulate post request with nested attributes in my functional tests?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

<逆流佳人身旁 2024-10-28 11:47:02

虽然有点晚了,但您不应该从控制器测试该行为。嵌套属性是模型行为。控制器只是将任何内容传递给模型。在您的控制器示例中,没有提及任何嵌套属性。您想要测试模型中是否存在由 accepts_nested_attributes_for 创建的行为

您可以使用 rSpec 进行测试,如下所示:

it "should accept nested attributes for units" do
  expect {
    Cart.update_attributes(:cart => {:line_items_attributes=>{'0'=>{'quantity'=>2, 'other_attr'=>"value"}})
  }.to change { LineItems.count }.by(1)
end

A little late to the party, but you shouldn't be testing that behavior from the controller. Nested attributes is model behavior. The controller just passes anything to the model. In your controller example, there is no mention of any nested attributes. You want to test for the existence of the behavior created by accepts_nested_attributes_for in your model

You can test this with rSpec like this:

it "should accept nested attributes for units" do
  expect {
    Cart.update_attributes(:cart => {:line_items_attributes=>{'0'=>{'quantity'=>2, 'other_attr'=>"value"}})
  }.to change { LineItems.count }.by(1)
end
你没皮卡萌 2024-10-28 11:47:02

假设您正在使用 Test::Unit,并且您在设置中的 @cart 中有一个购物车,请在更新测试中尝试如下操作:

cart_attributes = @cart.attributes
line_items_attributes = @cart.line_items.map(&:attributes)
cart_attributes[:line_items] = line_items_attributes
put :update, :id => @cart.to_param, :cart => cart_attributes

Assuming you're using Test::Unit, and you have a cart in @cart in the setup, try something like this in your update test:

cart_attributes = @cart.attributes
line_items_attributes = @cart.line_items.map(&:attributes)
cart_attributes[:line_items] = line_items_attributes
put :update, :id => @cart.to_param, :cart => cart_attributes
如梦亦如幻 2024-10-28 11:47:02

在 Rails3 中使用 test/unit ,首先生成一个集成测试:

rails g integration_test cart_flows_test

在生成的文件中包含您的测试,类似于:

test "if it adds line_item through the cart" do
  line_items_before = LineItem.all
  # don't forget to sign in some user or you can be redirected to login page
  post_via_redirect '/carts', :cart => {:line_items_attributes=>{'0'=>{'quantity'=>2, 'other_attr'=>"value"}}}

  assert_template 'show'
  assert_equal line_items_before+1, LineItem.all
end

我希望有所帮助。

Using test/unit in Rails3, first generate a integration test:

rails g integration_test cart_flows_test

in the generated file you include you test, something like:

test "if it adds line_item through the cart" do
  line_items_before = LineItem.all
  # don't forget to sign in some user or you can be redirected to login page
  post_via_redirect '/carts', :cart => {:line_items_attributes=>{'0'=>{'quantity'=>2, 'other_attr'=>"value"}}}

  assert_template 'show'
  assert_equal line_items_before+1, LineItem.all
end

I hope that helped.

小姐丶请自重 2024-10-28 11:47:02

使用嵌套属性更新购物车后,您可以通过执行以下操作来访问嵌套属性

@cart.line_items

After you update the cart with the nested attributes, you can access the nested attributes by doing

@cart.line_items
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文