如何在Rails 3.1可安装引擎中测试路由

Cam*_*ope 20 ruby-on-rails rspec2 ruby-on-rails-3

我正在尝试为可安装的rails 3.1引擎编写一些路由规范.我有工作模型和控制器规格,但我无法弄清楚如何指定路线.

对于示例引擎'testy',我尝试的每种方法都以相同的错误结束:

 ActionController::RoutingError:
   No route matches "/testy"
Run Code Online (Sandbox Code Playgroud)

我已经尝试了Rspec和Test :: Unit语法(spec/routing/index_routing_spec.rb):

describe "test controller routing" do
  it "Routs the root to the test controller's index action" do
    { :get => '/testy/' }.should route_to(:controller => 'test', :action => 'index')
  end

  it "tries the same thing using Test::Unit syntax" do
    assert_routing({:method => :get, :path => '/testy/', :use_route => :testy}, {:controller => 'test', :action => 'index'})
  end
end
Run Code Online (Sandbox Code Playgroud)

我已经正确布局了路由(config/routes.rb):

Testy::Engine.routes.draw do
  root :to => 'test#index'
end
Run Code Online (Sandbox Code Playgroud)

并将它们安装在虚拟应用程序中(spec/dummy/config/routes.rb):

Rails.application.routes.draw do
  mount Testy::Engine => "/testy"
end
Run Code Online (Sandbox Code Playgroud)

运行rails server和请求http://localhost:3000/testy/工作正常.

我错过了任何明显的东西,或者这只是没有适当地融入框架中了吗?

更新:正如@andrerobot指出的那样,rspec人员已经在2.14版本中解决了这个问题,所以我相应地改变了我接受的答案.

and*_*bot 12

从RSpec 2.14开始,您可以使用以下内容:

describe "test controller routing" do
  routes { Testy::Engine.routes }
  # ...
end
Run Code Online (Sandbox Code Playgroud)

资料来源:https://github.com/rspec/rspec-rails/pull/668

  • 如果我既需要引擎的路由又需要main_app的路由怎么办? (2认同)

小智 11

尝试使用以下内容添加前块:

before(:each) { @routes = Testy::Engine.routes }
Run Code Online (Sandbox Code Playgroud)

这对我有用,因为路由规范使用顶级实例变量来测试他们的路由.


Cam*_*ope 11

Steven Anderson的答案让我大部分都在那里,但需要相对于引擎而不是应用程序进行请求 - 可能是因为这种技术用引擎的路线替换了应用程序的路线,所以现在一切都相对于发动机.这对我来说似乎有点脆弱,但我还没有看到另一种有效的方式.如果有人发布了更清洁的方式,我会很乐意接受这个答案.

在'dummy'应用程序中,如果引擎安装如下(spec/dummy/config/routes.rb):

Rails.application.routes.draw do
  mount Testy::Engine => "/testy"
end
Run Code Online (Sandbox Code Playgroud)

以下规范将使用rspec和test :: unit语法(spec/routing/index_route_spec.rb)正确测试引擎的根路由:

require 'spec_helper'

describe "test controller routing" do
  before(:each) { @routes = Testy::Engine.routes }

  it "Routes the root to the test controller's index action" do
    { :get => '/' }.should route_to(:controller => 'testy/test', :action => 'index')
  end

  it "tries the same thing using Test::Unit syntax" do
    assert_routing({:method => :get, :path => '/'}, {:controller => 'testy/test', :action => 'index'})
  end
end
Run Code Online (Sandbox Code Playgroud)