0%

Ruby on Rails 網站開發 練習 - 007 (新增候選人,存檔失敗的情況)

什麼是新增候選人失敗,驗證表單該填的欄位是否填寫,資料格式是否正確,沒有通過驗證,即是存檔失敗。

  • 進入mondel/candidate.rb 在這個model裡面,我們來增加驗證的內容。 需要驗證Name欄位,是否有存在validates :name, presence: true

接著我們回到CandidatesControllercreate action,來寫驗證失敗的話,我們要怎麼做。
create action else 輸入redirect_to '/candidate/new'
表示如果驗證失敗,就將頁面導入到”新增候選人”頁面


打開瀏覽器來試試看,我們先在新增的表單頁面,故意空著Name欄位。


按下送出按鈕,看看網址列,確實有導回新增候選人頁面,但我們也可以發現剛剛有填寫的欄位資料也 一併被清空了


要如何做到保留原本填寫的資料,然後又可以提醒使用者有欄位忘記填寫。

  • 目前可以確定的事情,使用 redirect_to '/candidate/new' 不是好的做法。因為會直接把頁面整個清空,讓使用者重新填寫。

我們來修改一下,使用render :new方法來重新導入頁面。如果存檔失敗的話,我們就去借 new 這個 template,把畫面重新「畫」出來。

這裡需要注意的地方,render :new其中的:new 並不是指同樣CandidatesControllernew action
而是我們去借用view/new.html.erb這個檔案,重新將畫面「渲染」出來,本質上我們還是在create action當中執行。


我們再試一次,這次一樣空著Name欄位不填。送出表單試試看。


咦?這次的畫面有跟上次不一樣了,剛剛填寫過的資料還是有保留起來,Name欄位也是維持空著的狀態。可以達到這樣的效果,就是form_for()它神奇的地方。


因為在new.htaml.erb檔案中的form_for(@candidate),它會去接@candidate這個變數。

另外我們在CandidatesController裡面的new actioncreate action 也都有用到@candidate變數。


這個就是我們取變數名稱時,「故意」取同名的用意,製造「巧合」。
透過這個「巧合」,當它在render這個new.html.erb這個過程中,會去抓變數@candidate。當抓到@candidate,它不是空的,它裡面是「有料的」**(candidate_params)** 。因為我們仍然在執行create acion

form helper 神奇黑魔法

接著就是new.html.erb裡面form_for()它厲害的地方。它會根據我們給它的那包東西參數(@candidate)裡面相對應的值,放到相對應的欄位。
因此當我們按下送出按鈕後,會看到畫面上欄位裡還保留著剛剛填入的資料。

因為HTTP沒有所謂的「狀態」,所以如果今天使用redirect_to,把它轉址轉過去,就會整個頁面重新整理,欄位當然就被清空。

在驗證不過,存檔失敗時,去借用「現有的」表單重新畫一次

  • 要記得,不是重新執行CandidatesControllernew action!!!
  • 是借用view/new.html.erb這個檔案,重新把它render出來!!!

失敗時頁面是有了,但是似乎少了醒目的提示。


下一堂課程,我們就使用CSS來製作一些醒目的提示

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
class CandidatesController < ApplicationController

def index
end

def new
@candidate = Candidate.new
end

def create

@candidate = Candidate.new(candidate_params)
if @candidate.save
flash[:notice] = "Candidate created!!!"
redirect_to '/candidates'
else
#NG
render :new
end
end

private
def candidate_params
params.require(:candidate).permit(:name, :party, :age, :politics)
end

end

參考來源:為你自己學 Ruby on Rails (https://railsbook.tw/)