2013-08-04 7 views
6

Próbuję napisać testy i kod aplikacji, aby przekierować użytkowników, którzy są już zalogowani na ścieżkę root, jeśli próbują utworzyć użytkownika lub przejść do nowej ścieżki użytkownika .Samouczek poręczy Ch. 9 Ćwiczenie 6: Oczekiwana odpowiedź to <redirect>, ale była to <200>

Oto testy pisałem w user_pages_spec.rb:

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

     describe "using a 'new' action" do 
     before { get new_user_path } 
     specify { response.should redirect_to(root_path) } 
     end 

     describe "using a 'create' action" do 
     before { post users_path } 
     specify { response.should redirect_to(root_path) } 
     end   
    end 

UsersController:

class UsersController < ApplicationController 
    before_action :unsigned_in_user, only: [:create, :new] 

    def new 
    @user = User.new 
    end 

    def create 
    @user = User.new(user_params) 
    if @user.save 
     sign_in @user 
      flash[:success] = "Welcome to the Sample App!" 
      redirect_to @user 
    else 
      render 'new' 
    end 
    end 

    private 
    # Before filters 

    def user_params 
     params.require(:user).permit(:name, :email, :password, 
           :password_confirmation) 
    end 

    def unsigned_in_user 
     puts signed_in? 
     redirect_to root_url, notice: "You are already signed in." unless !signed_in? 
    end 
end 

W puts signed_in? zwraca false. Zakładam, że to jest problem, ponieważ oczekiwałbym, że zwróci prawdziwy. Oto błędy po uruchomieniu testów za pomocą rspec. Każda pomoc jest doceniana.

Failures: 

    1) User pages for signed in users using a 'create' action 
    Failure/Error: before { post users_path } 
    ActionController::ParameterMissing: 
     param not found: user 
    # ./app/controllers/users_controller.rb:52:in `user_params' 
    # ./app/controllers/users_controller.rb:20:in `create' 
    # ./spec/requests/user_pages_spec.rb:162:in `block (4 levels) in <top (required)>' 

    2) User pages for signed in users using a 'new' action 
    Failure/Error: specify { response.should redirect_to(root_path) } 
     Expected response to be a <redirect>, but was <200> 
    # ./spec/requests/user_pages_spec.rb:158:in `block (4 levels) in <top (required)>' 

w pliku sessions_helper.rb:

def signed_in? 
    !current_user.nil? 
end 

W specyfikacji/support/utilities.rb:

def sign_in(user, options={}) 
    if options[:no_capybara] 
    # Sign in when not using Capybara. 
    remember_token = User.new_remember_token 
    cookies[:remember_token] = remember_token 
    user.update_attribute(:remember_token, User.encrypt(remember_token)) 
    else 
    visit signin_path 
    fill_in "Email", with: user.email 
    fill_in "Password", with: user.password 
    click_button "Sign in" 
    end 
end 
+0

Po napisaniu kodu dla signed_in? metoda. Ponieważ zwraca coś, czego się nie spodziewałeś, problem prawdopodobnie tam leży. Dodano – amb110395

+0

. Jestem nowy na szynach, ale zastanawiam się, czy fakt, że signed_in? jest zdefiniowany w session_helper.rb i próbuję go użyć w kontrolerze użytkowników (a nie kontroler sesji) stwarza problem .. – IkegawaTaro

+0

Z pewnością spowodowałoby to problem, chyba że włączysz SessionHelper w swoim ApplicationController. Czy ty to zrobiłeś? – amb110395

Odpowiedz

4

byłeś w stanie uzyskać testy przekazać?

Jeśli nie byłeś, miałem taki sam problem jak dzisiaj i udało mi się przejść testy, wprowadzając dwie zmiany w testach - przekazując mieszanie user podczas POSTING i używając opcji no_capybara na metoda sign_in, ponieważ get i post nie są metodami kapibara i myślę, że RSpec nie zachowuje się tak, jak moglibyśmy się spodziewać, jeśli przerzucimy z metody kapibara na nie-kapibara w ramach tego samego testu.

describe "for signed-in users" do 
    let(:user) { FactoryGirl.create(:user) } 
    before { sign_in user, no_capybara: true } 

    describe "using a 'new' action" do 
    before { get new_user_path }  
    specify { response.should redirect_to(root_path) } 
    end 

    describe "using a 'create' action" do 
    before do 
     @user_new = {name: "Example User", 
        email: "[email protected]", 
        password: "foobar", 
        password_confirmation: "foobar"} 
     post users_path, user: @user_new 
    end 

    specify { response.should redirect_to(root_path) } 
    end 
end 
+1

Nice! Dodałem opcję no_capybara: true do pierwszego testu, a teraz obydwa. Nie przekazałem skrótu użytkownika do utworzenia, ale teraz przechodzi. Myślę, że to nie jest wymaganie ... tj.z testów mikropost: opisz "przesyłając do akcji tworzenia" do przed {post mikropost_path} określ {spodziewać (odpowiedź) .to redirect_to (signin_path)} koniec – IkegawaTaro

+1

Och, to ma sens, ponieważ skrót użytkownika byłby tylko potrzebne, jeśli Rails faktycznie wykonuje metodę create, co staramy się zapobiec. Dzięki - oboje wypełniamy swoje luki :) – najwa

3

samą odpowiedź jak Najwa, ale użyłem FactoryGirl użytkownikowi z szynami atrybutów sposób, aby uniknąć dublowania:

describe "using a 'create' action" do 
    before { post users_path, user: user.attributes } 

    specify { response.should redirect_to(root_path) } 
end 

Pomaga zachować dane oddzielone od kodu testowego.

Powiązane problemy