简体   繁体   中英

ActionController::UrlGenerationError: No route matches {:action=>“edit”, :controller=>“posts”} - rake test fails but app works correctly

When I run my rake test it comes up with two errors. However, when I run my blog, the index, show, new, and edit views all work correctly and do not generate errors in the browser. How do my tests fail but my blog doesn't? I've looked through other answers on this topic but most seem to do with links or nested elements in methods. I have neither.

1) Error:
PostsControllerTest#test_should_get_edit:
ActionController::UrlGenerationError: No route matches {:action=>"edit", :controller=>"posts"}
test/controllers/posts_controller_test.rb:25:in `block in <class:PostsControllerTest>'


2) Error:
PostsControllerTest#test_should_get_show:
ActionController::UrlGenerationError: No route matches {:action=>"show", :controller=>"posts"}
test/controllers/posts_controller_test.rb:15:in `block in <class:PostsControllerTest>'

Here is my show.html.erb

<h1><%= @post.title %></h1>
<h3> Posted: <%= @post.created_at.strftime("%I:%M %p") %> by Tarrence</h3>
<p><%= @post.body %></p>

</div>
<%= render 'sidebar' %>

Here is my edit.html.erb

<h1>Edit</h1>
<%= render 'form' %>
</div>

Here is my _form.html.erb

<%= form_for(@post) do |f| %>
  <%= f.label :title %>
  <%= f.text_field :title, class: "form-control" %>

  <%= f.label :topic %>
  <%= f.text_field :topic, class: "form-control" %>

  <%= f.label :body %>
  <%= f.text_area :body, class: "form-control" %>

  <%= f.submit "Post", class: "btn btn-primary submit" %>
<% end %>

Here is my index.html.erb

<div class="blog-post">
        <% @posts.each do |post| %>
            <h3><%= post.title %></h3>
            <span>Posted by Tarrence <%= post.created_at.strftime("at %I:%M %p") %></span><br>
            <span>Topic: <%= post.topic %></span>

            <% if post.body.length > 100 %>
                <p><%= truncate(post.body, length: 100, separator: ' ') %>
                <%= link_to "Read More", post_path(post) %></p>
            <% else %>
                <p><%= post.body %></p>
            <% end %>

            <hr>
        <% end %>

    </div>

    <nav class="pager">
        <%= will_paginate @posts %>
    </nav>


</div>

Here is my routes.rb

root 'posts#index'
#get 'post' => 'posts#show'
#get 'post/edit' => 'posts#edit'
resources :posts

Here is my posts_controller.rb

class PostsController < ApplicationController
  def index
   # @posts = Post.all
   @posts = Post.paginate(:page => params[:page], :per_page => 2)
  end

  def show
    @post = Post.find(params[:id])
  end

  def new
    @post = Post.new
  end

  def create
    logger.info "---params ==> #{params.inspect}---"
    @post = Post.new(post_params)
    if @post.save
      redirect_to root_path
    else
      render 'new'
    end
  end

  def edit
    @post = Post.find(params[:id])
  end

  def update
    @post = Post.find(params[:id])
    if @post.update_attributes(post_params)
      redirect_to post_path(@post)
    else
      render 'edit'
    end
  end

  def destroy
  end

  private 

    def post_params
      params.require(:post).permit(:title, :topic, :body)
    end
end

Here is my test

require 'test_helper'

class PostsControllerTest < ActionController::TestCase

  def setup
    @post = Post.create(title: "This is a post", topic: "Random", body: "This is some text in the body.")
  end

  test "should get index" do
    get :index
    assert_response :success
  end

  test "should get show" do
    get :show, id: @post.id
    assert_response :success
  end

  test "should get new" do
    get :new
    assert_response :success
  end

  test "should get edit" do
    get :edit, id: @post.id
    assert_response :success
  end

  test "should be valid" do
    assert @post.valid?
  end

end

It seems that the only thing you didn't show is the one place where the error is - your test!

...it doesn't matter though because it's clear what the problem is, you're not providing the :id in your test calls, ie. you'll be doing something like this in test/controllers/posts_controller_test.rb

get :show
get :edit

...whereas what you should be doing is something like this:

post = Post.create attributes: "required", for: "a post"  # or maybe you use FactoryGirl, you get the idea though - create a post
get :show, id: post.id

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM