测试控制器在RSpec中的重定向

时间:2016-11-30 17:32:29

标签: ruby-on-rails ruby ruby-on-rails-4 rspec

我有一个测试控制器动作的rspec测试。

class SalesController < ApplicationController
  def create
    # This redirect sends the user to SalesController#go_to_home
    redirect_to '/go_to_home'
  end

  def go_to_home
    redirect_to '/'
  end
end

我的控制器测试看起来像

RSpec.describe SalesController, type: :controller do
  include PathsHelper

  describe 'POST create' do
    post :create

    expect(response).to redirect_to '/'
  end
end

然而,当我运行测试时,它告诉我:

   Expected response to be a redirect to <http://test.host/> but was a redirect to <http://test.host/go_to_home>.
   Expected "http://test.host/" to be === "http://test.host/go_to_home".

/go_to_home会将用户发送到SalesController#go_to_home。如何测试响应最终会导致主页包含网址http://test.host/

2 个答案:

答案 0 :(得分:2)

为什么您希望重定向到&#39; /&#39;在规格? 从您粘贴的控制器代码中,您将被重定向到&#39; / go_to_home&#39;点击创建动作后

尝试将规格更改为:

expect(response).to redirect_to '/go_to_home'

编辑:

这是一个真实的例子还是代码只是为了分享你想要实现的目标? 我不认为rspec会在转到&#39; / go_to_home&#39;之后遵循重定向。我认为没问题。

如果您正在测试创建操作,则可以测试重定向到&#39; / go_to_home&#39;因为那是什么行动。 然后,您可以对其他操作go_to_home执行另一个测试,并期望重定向到root。

您是否正在调用此行动&#39; go_to_home&#39;来自其他地方?

答案 1 :(得分:1)

控制器测试是有效的单元测试 - 您正在测试调用单个操作的效果以及该操作的预期行为。

create操作确实返回状态代码为302的响应,并在标题中包含一个Location,表示新的URI,在调用create的情况下将是Location: http://localhost/go_to_home

这是控制器测试的结果。它模拟了从浏览器到创建操作的调用,并接收了初始重定向。

在现实世界中,浏览器然后会导航到给定位置然后点击go_to_home动作,但这超出了控制器测试的范围......这是在集成测试领域。

所以,

  1. 创建一个集成测试,以便最初调用create操作,按照重定向进行测试,然后测试结果为&#39; /&#39;。
  2. 将控制器测试更改为expect(response).to redirect_to '/go_to_home'
  3. create操作更改为直接重定向到&#39; /&#39;