0
votes

I'm trying to test the routing of a namespaced Rails controller action, and something isn't set up correctly.

I've already looked at the following issues, none of them even seemed to answer the questions at hand, much less give me an answer to my issue:

It's not so much that I'm passing incorrect parameters to the action, it's that the route doesn't match at all when in the context of this test. What am I missing here?

config/routes.rb (using versionist gem):

...
api_version(module: 'api/v1', path: {value: 'v1'}) do
  namespace :nphase do
    resource :device_service, controller: 'device_service', only: :none, format: :json do
      collection do
        post :get_device_information
      end
    end
  end
end
...

app/controllers/api/v1/device_service_controller.rb:

module Api                                               
  module V1                                              

    class DeviceServiceController < ApplicationController
      respond_to :json                                   

      def get_device_information                       
        respond_with json: {"success" => true}           
      end                                                
    end                                                  

  end                                                    
end                                                      

output of rake routes |grep nphase:

get_device_information_v1_nphase_device_service POST    /v1/nphase/device_service/get_device_information(.:format) api/v1/nphase/device_service#get_device_information {:format=>:json}

spec/routing/api/v1/device_service_routing_spec.rb:

require 'spec_helper'

describe 'routes for DeviceService' do
  it 'routes correctly' do
    expect(post('/v1/nphase/device_service/get_device_information')).to route_to(
      controller: 'api/v1/device_service',
      action: 'get_device_information'
    )
  end
end

Test failure:

Failure/Error: expect(post('/v1/nphase/device_service/get_device_information')).to route_to(
  No route matches "/v1/nphase/device_service/get_device_information"
1
The generated route is a GET yet you're performing a POST. I see you attempt to create a POST in routes.rb, can't figure out why that doesn't work.Jesper
I just pasted your routes into a local rails app and the correct route, a POST. Which version of Rails and versionist are you using?Jesper
@Jesper sorry, I had bounced back and forth between GET and POST to see if that was the issue. On my system, it is a POST request across the board. I get the aforementioned failure when the request is actually set up correctly.Brad Rice
@Jesper I'm running versionist v1.3.0, rspec-rails v2.99.0, and rails v3.2.13Brad Rice
If you're saying that rake routes actually shows a POST route, you really should update the body of your question.Peter Alfvin

1 Answers

2
votes

By running your spec (albeit in Rails 4), I got this error:

Failure/Error: expect(post: '/v1/nphase/device_service/get_device_information').to route_to(
       A route matches "/v1/nphase/device_service/get_device_information", but references missing controller: Api::V1::Nphase::DeviceServiceController
     # ./spec/controller_spec.rb:5:in `block (2 levels) in <top (required)>'

This tells us that your controller isn't in the Nphase module.

By using namespace, you're telling Rails to search for the controller in particular module.

So either put the controller in the correct module (and change the directory structure accordingly), or tell rails to look for the controller in the correct place (from the Rails guides):

If you want to route /admin/articles to ArticlesController (without the Admin:: module prefix), you could use:

 scope '/admin' do
   resources :articles, :comments
 end