2014-08-29 114 views
-1

我接近Hartl rails教程的末尾,并遇到一个我似乎无法弄清楚的Rspec问题。在http://www.railstutorial.org/book/user_microposts#sec-access_control清单10.23引入的2个测试与以下消息失败:Hartl ROR教程第10章Rspec测试失败

Failures: 

    1) Authentication authorization for non-signed-in users in the Microposts controller submitting to the create action 
Failure/Error: before { post microposts_path } 
ActionController::ParameterMissing: 
    param is missing or the value is empty: micropost 
# ./app/controllers/microposts_controller.rb:20:in `micropost_params' 
# ./app/controllers/microposts_controller.rb:5:in `create' 
# ./spec/requests/authentication_pages_spec.rb:107:in `block (6 levels) in <top (required)>' 

    2) Authentication authorization for non-signed-in users in the Microposts controller submitting to the destroy action 
Failure/Error: before { delete micropost_path(FactoryGirl.create(:micropost)) } 
ActionView::MissingTemplate: 
    Missing template microposts/destroy, application/destroy with {:locale=>[:en], :formats=>[:html], :handlers=>[:erb, :builder, :raw, :ruby, :jbuilder, :coffee]}. Searched in: 
    * "/Users/name/Sites/sample_app/app/views" 
# ./spec/requests/authentication_pages_spec.rb:112:in `block (6 levels) in <top (required)>' 

这里是我的authentication_pages_spec.rb:

require 'spec_helper' 

describe "Authentication" do 

    subject { page } 

    describe "signin page" do 
    before { visit signin_path } 

    it { should have_content('Sign in') } 
    it { should have_title('Sign in') } 
    end 

    describe "signin" do 
    before { visit signin_path } 

    describe "with invalid information" do 
     before { click_button "Sign in" } 

     it { should have_title('Sign in') } 
     it { should have_error_message('Invalid') } 
     it { should_not have_link('Users',  href: users_path) } 
     it { should_not have_link('Sign out', href: signout_path) } 
     it { should have_link('Help',   href: help_path) } 
     it { should have_link('Home',   href: root_path) } 
     it { should have_link('Sign in',   href: signin_path) } 

     describe "after visiting another page" do 
     before { click_link "Home" } 
     it { should_not have_selector('div.alert.alert-error') } 
     end 
    end 

    describe "with valid information" do 
     let(:user) { FactoryGirl.create(:user) } 
    before { sign_in user } 

     it { should have_title(user.name) } 
     it { should have_link('Users',  href: users_path) } 
     it { should have_link('Profile',  href: user_path(user)) } 
     it { should have_link('Settings', href: edit_user_path(user)) } 
     it { should have_link('Sign out', href: signout_path) } 
     it { should_not have_link('Sign in', href: signin_path) } 

     describe "create new user goes to root_path" do 
     before { visit new_user_path } 
     it { should_not have_title('Sign up') } 
     end 

     describe "followed by signout" do 
     before { click_link "Sign out" } 
     it { should have_link('Sign in') } 
     end 
    end 
    end 

    describe "authorization" do 

    describe "as admin user" 
     let(:admin) { FactoryGirl.create(:admin) } 
     before { sign_in admin, no_capybara: true } 

     describe "prohibit admin for self deletion" do 
     specify do 
      expect { delete user_path(admin) }.not_to change(User, :count).by(-1) 
     end 
    end 


    describe "for non-signed-in users" do 
     let(:user) { FactoryGirl.create(:user) } 


     describe "when attempting to visit a protected page" do 
     before do 
      visit edit_user_path(user) 
      fill_in "Email", with: user.email 
      fill_in "Password", with: user.password 
      click_button "Sign in" 
     end 

     describe "after signing in" do 

      it "should render the desired protected page" do 
      expect(page).to have_title('Edit user') 
      end 

      describe "when signing in again" do 
      before do 
       click_link "Sign out" 
       visit signin_path 
       fill_in "Email", with: user.email 
       fill_in "Password", with: user.password 
       click_button "Sign in" 
      end 

      it "should render the default (profile) page" do 
       expect(page).to have_title(user.name) 
      end 
      end 
     end 
     end 

     describe "in the Microposts controller" do 

     describe "submitting to the create action" do 
      before { post microposts_path } 
      specify { expect(response).to redirect_to(signin_path) } 
     end 

     describe "submitting to the destroy action" do 
      before { delete micropost_path(FactoryGirl.create(:micropost)) } 
      specify { expect(response).to redirect_to(signin_path) } 
     end 
     end 

     describe "in the Users controller" do 

     describe "visiting the user index" do 
      before { visit users_path } 
      it { should have_title('Sign in') } 
     end 

     describe "visiting the edit page" do 
      before { visit edit_user_path(user) } 
      it { should have_title('Sign in') } 
     end 

     describe "when attempting to visit a protected page" do 
     before do 
      visit edit_user_path(user) 
      fill_in "Email", with: user.email 
      fill_in "Password", with: user.password 
      click_button "Sign in" 
     end 

     describe "after signing in" do 

      it "should render the desired protected page" do 
      expect(page).to have_title('Edit user') 
      end 
     end 
     end 

     describe "submitting to the update action" do 
      before { patch user_path(user) } 
      specify { expect(response).to redirect_to(root_url) } 
     end 
     end 

     describe "as non-admin user" do 
     let(:user) { FactoryGirl.create(:user) } 
     let(:non_admin) { FactoryGirl.create(:user) } 

     before { sign_in non_admin, no_capybara: true } 

     describe "submitting a DELETE request to the Users#destroy action" do 
     before { delete user_path(user) } 
     specify { expect(response).to redirect_to(root_url) } 
     end 
    end 
    end 
end 

    describe "as wrong user" do 
     let(:user) { FactoryGirl.create(:user) } 
     let(:wrong_user) { FactoryGirl.create(:user, email: "[email protected]") } 
     before { sign_in user, no_capybara: true } 

     describe "submitting a GET request to the Users#edit action" do 
     before { get edit_user_path(wrong_user) } 
     specify { expect(response.body).not_to match(full_title('Edit user')) } 
     specify { expect(response).to redirect_to(root_url) } 
     end 

     describe "submitting a PATCH request to the Users#update action" do 
     before { patch user_path(wrong_user) } 
     specify { expect(response).to redirect_to(root_url) } 
     end 
    end 
    end 

对于1号),看起来它寻找一个尚未微柱它应该通过完全传递,然后转到登录页面(正如您可以在微博控制器下面看到的那样,在之前的操作设置中检查用户是否已登录,并且他们是否不将它们转发到登录页面..这适用于所有行为)。

对于2号)它正在寻找一个不存在也不会存在的观点?它为什么这样做?我该如何阻止这种行为。

这似乎是应用程序绕过microposts控制器之前的过滤器?

这里是我的microposts_controller.rb:

class MicropostsController < ApplicationController 
    before_action :signed_in_user 

    def create 
    @micropost = current_user.microposts.build(micropost_params) 
    if @micropost.save 
     flash[:success] = "Micropost created!" 
     redirect_to root_url 
    else 
     render 'static_pages/home' 
    end 
    end 

    def destroy 
    end 

    private 

    def micropost_params 
     params.require(:micropost).permit(:content) 
    end 
end 

&我signed_in_user和sign_in?方法坐在我sessions_helper.rb

def signed_in_user 
    unless signed_in? 
     store_location 
     redirect_to signin_url, notice: "Please sign in." 
    end 
    end 

def signed_in? 
    !current_user.nil? 
    end 

任何洞察到为什么我的测试失败?

回答

0

问题解决。不知道我是如何错过的,但运行测试时我仍然登录。在运行Microposts非登录用户发布并销毁测试之前注销是所有需要的。我在authenication_pages_spec.rb中添加了注销码,如下所示:

describe "in the Microposts controller" do 
     before do 

     click_link "Sign out" 

     describe "submitting to the create action" do 
      before { post microposts_path } 
      specify { expect(response).to redirect_to(signin_path) } 
     end 

     describe "submitting to the destroy action" do 
      before { delete micropost_path(FactoryGirl.create(:micropost)) } 
      specify { expect(response).to redirect_to(signin_path) } 
     end 
     end 
    end 
相关问题