Reputation: 437
Hi I have an Rspec test:
require "rails_helper"
describe PostsController do
let(:user){create(:user)}
describe "POST #create" do
it "creates a Post" do
expect {post :create, post: attributes_for(:post)}.to change(Post, :count).by 1
end
end
end
That is throwing the following error:
ActionController::UrlGenerationError:
No route matches {:action=>"create", :controller=>"posts", :post=>{:content=>"this is post content!"}}
Which means it can't find the route right?
instead of passing :create as the first argument to post I have tried, passing it the route helper user_posts_path(user) <--- (this is the route for my posts create action), but I get pretty much the same error. Here is that attempt:
it "creates a Post" do
expect {post user_posts_path(user), post: attributes_for(:post)}.to change(Post, :count).by 1
end
which throws this error:
ActionController::UrlGenerationError:
No route matches {:action=>"/users/1/posts", :controller=>"posts", :post=>{:content=>"this is post content!"}}
I've also attempted to pass in the id manually:
id: user.id
as the second argument to post.
Here is the post_factory.rb since I am calling attributes_for(:post):
FactoryGirl.define do
factory :post do
content "this is post content!"
user
end
end
My relevant rake routes:
user_posts GET /users/:user_id/posts(.:format) posts#index
POST /users/:user_id/posts(.:format) posts#create
new_user_post GET /users/:user_id/posts/new(.:format) posts#new
edit_post GET /posts/:id/edit(.:format) posts#edit
post GET /posts/:id(.:format) posts#show
PATCH /posts/:id(.:format) posts#update
PUT /posts/:id(.:format) posts#update
DELETE /posts/:id(.:format) posts#destroy
My PostsController create action is alive and well too.
So I know my route is there and I have tried passing the post method an explicit route instead of :create, but I still get the same error. I believe the problem is occurring because my routes are nested, but I need them to be nested, and would like to test them in that form so I can't change the nesting. I'm not sure what else to do, so I've come here for help. Thanks.
Upvotes: 1
Views: 902
Reputation: 11915
The posts#create
action requires an user_id
to be passed as a part of the url.
expect {post :create, post: attributes_for(:post)}.to change(Post, :count).by 1
should be
expect {post :create, user_id: user.id, post: attributes_for(:post)}.to change(Post, :count).by 1
user
is available from the user
factory which is lazily created(since you used let
and not let!
) when you call it inside the block.
Upvotes: 2