ruby-on-rails – Rails功能测试:在POST请求中发送URL查询参数

前端之家收集整理的这篇文章主要介绍了ruby-on-rails – Rails功能测试:在POST请求中发送URL查询参数前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我在Rails功能测试中发送POST请求,如下所示:
post :create,collection: { name: 'New Collection' }

正如预期的那样,集合以JSON编码的表单数据的形式发送.

我无法弄清楚的是如何向URL添加查询. The documentation说我可以访问请求对象并在发送之前对其进行修改.所以我尝试了这个:

@request.GET[:api_key] = 'my key'
post :create,collection: { name: 'New Collection' }

但是,:api_key永远不会出现在服务器上的request.GET哈希中. (但是,当我通过另一个HTTP客户端发送它时,它会这样做.)

解决方法

首先要澄清一些事情:尽管请求不能同时是GET和POST,但是在使用POST时,有 nothing stopping你使用查询字符串和正文表单数据.您甚至可以使用查询字符串 and an empty body中的所有参数进行POST,但这听起来很不寻常.

Rails支持这种情况,实际上您可以使用POST请求轻松发送表单,并且仍然可以在表单的操作中进行查询.该查询可以通过request.GET hash(query_string的别名)访问,而POST主体可以使用request.POST hash(request_parameters的别名)来访问. params哈希实际上是从combined GET and POST hashes构建的.

但是,根据我的研究,似乎Rails不支持功能控制器测试中的POST请求中传递查询字符串.虽然我在任何文档或known issues on github中都找不到任何相关内容,但源代码非常清楚.在下面的文字中,我假设你使用Rails 4.

为什么它不起作用

功能控制器测试的问题在于它们不使用真实的请求/响应,但它们模拟HTTP握手:请求被模拟,其参数填充在适当的位置,并且给定的控制器操作被简单地称为普通的ruby方法.所有这些都在action_controller/test_case classes完成.

事实证明,由于两个原因,此模拟在您的特定情况下不起作用:

>运行测试时传入的参数始终是handed over或者是request_parameters,即使用post请求时的request.POST哈希,或者是用于获取测试请求的query_string(即request.GET).在单次测试运行期间,无法设置这两个哈希值.

这实际上是有道理的,因为功能测试中的get,post等帮助程序只接受params的单个哈希,因此内部测试代码无法知道如何将它们分成两个哈希.
>确实可以在使用@request变量运行测试之前设置请求,但仅在某种程度上,您可以设置标题,例如.但是您无法设置请求的内部属性,因为它们在测试运行期间被回收.回收在here完成,它重置请求对象和底层机架请求对象的所有内部变量.因此,如果您尝试设置请求GET参数,例如@ request.GET [:api_key] =’my key’,它将不会产生任何影响,因为表示此哈希的内部变量将在回收期间被擦除.

解决方案/解决方法

>放弃功能测试并选择集成测试.积分测试allow to set the rack environment variables与主要参数分开.以下集成测试除了普通的post body params之外还传递QUERY_STRING rack env变量,并且应该完美无缺:

class CollectionsTest < ActionDispatch::IntegrationTest
  test 'foo' do
    post collections_path,{ collection: { name: 'New Collection' } },{ "QUERY_STRING" => "api_key=my_api_key" }

    # this proves that the parameters are recognized separately in the controller
    # (you can test this in you controller as well as here in the test):
    puts request.POST.inspect
    # => {"collection"=>{"name"=>"New Collection"}}
    puts request.GET.inspect
    # => {"api_key"=>"my_api_key"}
  end
end

您仍然可以在集成测试中使用功能测试中的大多数功能.例如.您可以使用assignign hash测试控制器中已分配的实例变量.

转换参数也受到以下事实的支持:Rails 5将deprecate功能控制器测试支持集成测试,并且由于Rails 5.1这些功能测试支持将被移出到单独的gem.
>尝试Rails 5:虽然功能测试将被弃用,但它的源代码似乎是在rails master中的heavily rewritten,例如不再使用请求的回收.因此,您可以尝试尝试在测试设置期间设置请求的内部变量.我没有测试过它.
>当然,您总是可以尝试对功能测试进行修补,以便它支持query_string和request_parameters哈希的单独参数,以便在测试中定义.

我去集成测试路线:).

猜你在找的Ruby相关文章