我正在使用Versionist对我的API进行版本控制,所以现在我的路径文件看起来像
Rails.application.routes.draw do
api_version(:module => "V1", :path => {:value => "v1"}) do
resources :concepts, except: [:new, :edit]
end
end
我的控制器位于app/controllers/v1/concepts_controller.rb
。
在spec/controllers/v1/concepts_controller_spec.rb
里面我有
...
describe "POST #create" do
context "with valid params" do
it "creates a new Concept" do
expect {
post :create, {:concept => valid_attributes}, valid_session
}.to change(Concept, :count).by(1)
end
...
end
end
...
describe "PUT #update" do
context "with valid params" do
let(:new_attributes) { {description: 'Sample description.'} }
it "updates the requested concept" do
concept = Concept.create! valid_attributes
put :update, {:id => concept.to_param, :concept => new_attributes}, valid_session
concept.reload
expect(concept.description).to eq('Sample description.')
end
...
PUT #update测试工作正常,但所有POST #create测试都给了我
1) V1::ConceptsController POST #create with valid params creates a new Concept
Failure/Error: post :create, {:concept => valid_attributes}, valid_session
NoMethodError:
undefined method `concept_url' for #<V1::ConceptsController:0x007fd6e6d8ed38>
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_dispatch/routing/polymorphic_routes.rb:268:in `handle_model_call'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_dispatch/routing/url_for.rb:167:in `url_for'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/rendering.rb:95:in `_process_options'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/renderers.rb:43:in `block in _render_to_body_with_renderer'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/renderers.rb:41:in `_render_to_body_with_renderer'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/renderers.rb:37:in `render_to_body'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/abstract_controller/rendering.rb:25:in `render'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/rendering.rb:16:in `render'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/instrumentation.rb:44:in `block (2 levels) in render'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/core_ext/benchmark.rb:12:in `block in ms'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/core_ext/benchmark.rb:12:in `ms'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/instrumentation.rb:44:in `block in render'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/instrumentation.rb:87:in `cleanup_view_runtime'
# /usr/local/bundle/gems/activerecord-4.2.2/lib/active_record/railties/controller_runtime.rb:25:in `cleanup_view_runtime'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/instrumentation.rb:43:in `render'
# ./app/controllers/v1/concepts_controller.rb:24:in `create'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/abstract_controller/base.rb:198:in `process_action'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/rendering.rb:10:in `process_action'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/abstract_controller/callbacks.rb:20:in `block in process_action'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/callbacks.rb:117:in `call'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/callbacks.rb:117:in `call'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/callbacks.rb:555:in `block (2 levels) in compile'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/callbacks.rb:505:in `call'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/callbacks.rb:505:in `call'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/callbacks.rb:92:in `_run_callbacks'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/callbacks.rb:776:in `_run_process_action_callbacks'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/callbacks.rb:81:in `run_callbacks'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/abstract_controller/callbacks.rb:19:in `process_action'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/rescue.rb:29:in `process_action'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/instrumentation.rb:32:in `block in process_action'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/notifications.rb:164:in `block in instrument'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/notifications/instrumenter.rb:20:in `instrument'
# /usr/local/bundle/gems/activesupport-4.2.2/lib/active_support/notifications.rb:164:in `instrument'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/metal/instrumentation.rb:30:in `process_action'
# /usr/local/bundle/gems/activerecord-4.2.2/lib/active_record/railties/controller_runtime.rb:18:in `process_action'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/abstract_controller/base.rb:137:in `process'
# /usr/local/bundle/gems/actionview-4.2.2/lib/action_view/rendering.rb:30:in `process'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/test_case.rb:632:in `process'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/test_case.rb:65:in `process'
# /usr/local/bundle/gems/actionpack-4.2.2/lib/action_controller/test_case.rb:514:in `post'
# ./spec/controllers/v1/concepts_controller_spec.rb:38:in `block (5 levels) in <top (required)>'
# ./spec/controllers/v1/concepts_controller_spec.rb:37:in `block (4 levels) in <top (required)>'
我的佣金路线:
Prefix Verb URI Pattern Controller#Action
v1_concepts GET /v1/concepts(.:format) v1/concepts#index
POST /v1/concepts(.:format) v1/concepts#create
v1_concept GET /v1/concepts/:id(.:format) v1/concepts#show
PATCH /v1/concepts/:id(.:format) v1/concepts#update
PUT /v1/concepts/:id(.:format) v1/concepts#update
DELETE /v1/concepts/:id(.:format) v1/concepts#destroy
如何让它使用v1_concept_url
代替?为什么即使是GET请求,它甚至会调用concept_url
?&#39;
编辑我的控制器:
class V1::ConceptsController < V1::BaseController
before_action :set_concept, only: [:show, :update, :destroy]
# GET /concepts
# GET /concepts.json
def index
@concepts = Concept.all
render json: @concepts
end
# GET /concepts/1
# GET /concepts/1.json
def show
render json: @concept
end
# POST /concepts
# POST /concepts.json
def create
@concept = Concept.new(concept_params)
if @concept.save
render json: @concept, status: :created, location: @concept
else
render json: @concept.errors, status: :unprocessable_entity
end
end
...
答案 0 :(得分:1)
显然location
标题是罪魁祸首。传入实例变量@concept
会导致Rails调用concept_url
帮助程序。
您可以通过自己调用帮助程序来覆盖它:
location: v1_concept_url(@concept)