2012-12-15 17 views
7

io non sono sicuro di come controllare i messaggi istantanei con i test funzionali. Il mio problema ha qualcosa a che fare con redirect_to perché il mio test per flash[:error] passa. Ecco ciò che il mio create azione assomiglia:test funzionali per messaggi flash dopo reindirizzamento

def create 
    @user = User.new(params[:user]) 
    if @user.save 
    redirect_to @user, flash: { success: "Welcome!" } 
    else 
    flash.now[:error] = "Signup failed:" 
    render 'new' 
    end 
end 

Ho un test di passaggio per flash[:error] che 1) controlla che flash[:error] è il valore corretto, 2) controlla la pagina per la div flash, e 3) ottiene un nuovo pagina e controlla che il messaggio flash sia stato cancellato. Ho provato a fare un test analogo per flash[:success] ma non riesce quando tenta di trovare il div sulla pagina. Ecco la prova di non aver:

should "show flash[:success] message" do 
    post :create, user: { name: "valid user", 
          password: "userpw", 
          password_confirmation: "userpw", 
          email: "[email protected]" }   
    assert_redirected_to user_path(assigns(:user)), "user isn't being redirected to their page after registration" 
    assert_equal flash[:success], "Welcome!", "flash[:success] isn't being set properly" 
    assert_select "div.alert-success", flash[:success] 
    get :new 
    assert flash.empty?, "there shouldn't be any flash messages left after getting new page" 
    end 

quando i test manualmente in un browser, si comporta come previsto, ma non sono sicuro di come scrivere i test per riflettere questa. Le prime due asserzioni passano (quindi il test riconosce che viene ridiretta correttamente e che flash[:success] viene impostato "Welcome!"). Sulla base di questo, vorrei che la dichiarazione assert_select sarebbe in grado di trovare il div, ma se non riesce con questo messaggio di errore:

Expected at least 1 element matching "div.alert-success", found 0. 

Così ho provato ad aggiungere puts @response.body a destra prima del assert_select dichiarazione, che stampato questo:

Questo spiega perché non è stato possibile trovare il flash div, ma non sono sicuro di come "terminare" il reindirizzamento in modo da rendere la vista corretta con il flash div. Se aggiungo un diritto get dichiarazione prima dell'istruzione assert_select, il test viene superato, perché ora ha la @response.body div flash. Tuttavia, questo non sembra un test efficace perché non riflette il comportamento della mia applicazione - l'utente non deve fare una nuova richiesta per vedere il messaggio flash.

Inoltre non garantisce che il messaggio flash si presenta sulla pagina corretta. Se utilizzo la dichiarazione get :new, l'asserzione passa ancora, il che implica che il messaggio flash sarebbe presente nella vista users#new. Anche se uso

get :show, id: assigns(:user).id 

per assicurarsi che il messaggio flash compare sulla pagina corretta, questo si sente ancora sbagliata perché 1) ora si tratta di una risposta, invece di una risposta redirectsuccess, e 2) è ancora doesn' t spiegare perché ho richiedere manualmente qualsiasi pagina per trovare il div flash - secondo il docs "il flash è una parte speciale della sessione che è eliminato con ogni richiesta"

in ogni caso, c'è un modo per verificare che un messaggio flash venga visualizzato correttamente dopo un reindirizzamento?

+0

Ho lo stesso problema. Ho scoperto che quando eseguo il reindirizzamento da un'azione invocata da get sembra funzionare, ovvero che assert_select ha accesso alla vista reindirizzata, ma quando reindirizzo da un'azione invocata da 'post', viene visualizzato solo 'Stai reindirizzato ...' pagina. Molto noioso. Ho provato a usare follow_redirect! ma questo non è disponibile nei test funzionali. –

risposta

3

che sto rispondere a questa domanda dal POV che ciò che si sta cercando di testare sarebbe meglio testato altrove. Se hai un sacco di problemi dello svolgimento della prova, le probabilità sono c'è un modo migliore per provarlo :)

  1. test che lampeggiano i messaggi vengono cancellati - messaggi flash sono incorporati in Rails, in modo che doesn' Ho molto senso testare qualcosa che il framework sta gestendo per te.

  2. test che mostrano gli elementi sulla pagina - vista spec non appartengono a controllori.Ecco una descrizione del ruolo del controller:

    Un controller può quindi essere pensato come un intermediario tra i modelli e le viste . Rende i dati del modello disponibili alla vista in modo che possa visualizzare i dati all'utente.

    Il controllore deve rendere i dati disponibili per la vista, non per specificare come viene eseguito il rendering dei dati. Immagina di aver cambiato il nome della tua classe CSS, quindi dovresti aggiornare anche le specifiche del controller.

    Se vuoi veramente testare i messaggi flash, userei un test di integrazione.