iT邦幫忙

第 12 屆 iThome 鐵人賽

DAY 11
0
自我挑戰組

Ruby on Rails 新手的30個問題!系列 第 11

Day_11 erb? form helper? strong parameter?

嗨!各位朋友大家好,打給後,歹嘎吼,胎尬喉,我是阿圓,一樣有請今天的one piece:

(應同伴要求,放出可愛的功夫海牛!!)
昨天只有放我的程式碼,沒有寫問題,看到標題就會知道,今天一次來問三個!

  1. erb file ?
  2. form_helper ?
  3. strong parameter?

erb file ?

就目前為止,我知道ruby的檔案檔名為.rb,若要將 ruby 語法放到html裡,必須創建一個.html.erb的為副檔名的檔案,(學到這裡時候驚呆了,副檔名後面居然還可以再接副檔名 =口=")。
到底什麼是erb呢???先有請wiki大大,出來講句話:

eRuby (Embedded Ruby) is a templating system that embeds Ruby into a text document.

不負責任翻譯:
eRuby(嵌入式Ruby)是一個將Ruby嵌入到純文字文件中的templating system。它通常用於將Ruby代碼嵌入HTML文檔中。

完整版請點我

而 erb 是 eRuby 的實現方式,前者為純 ruby 所撰寫,且包含在 ruby 的標準函式庫裡;而後者是用C語言寫的;可以使用<%= %>,將 ruby 語法放入其中,便能動態的去操作、維護我們的HTML畫面。

其中嵌入語法有些些微的差異,稍微提一下:

  1. <% ruby code %> : 會執行,但不會在畫面上印出
  2. <%= ruby code %> :執行且印出在畫面上
  3. <%# ruby code %> : erb註解的寫法
  4. <% ruby code -%> : -%> 後面若是換行符號則刪除

form_helper ?

先看這個普通的頁面

一開始學網頁的時候,就會想,啊!這就是兩個input吧!

寫完了之後測試,登入按下去,結果發現...

WHAAAAT?!

別緊張,這個ActionController::InvalidAuthenticityToken問題是為了確定這個提交表單的動作確定是由網站內所提交的,若單純的使用HTML標籤,要再多設計一個input,裡面放著站內的token,與表單一起提交出去,以免有心人士對你利用其他方式,打資料到你的資料庫。

<input name="authenticity_token" value="<%= form_authenticity_token %>" type="hidden">

不過,Rails 已經幫我們寫好超~好用的helper(可以在view或model中呼叫的方法) 了!!!用form_helper製作出的表單已經幫你長好這個hidden的input:

以下就來簡單介紹一下常用的三種form_helper
先來說一下在rails 5.1 版本之前的,分別為:

form_tag

主要用在沒有model的時候,要指定表單送去的地方,可以直接給他url,也可以用指定controller、action的方式

<% form_tag("/search", method: "get") do %>
<!--  form content -->
<% end %>
<!--  =======or======== -->
<% form_tag(controller: "people", action: "search", method: "get", class: "nifty_form") do %>
<!--  form content -->
<% end %>

form_for

用在有model的時候,先在controller指定一個變數。

# app/controllers/articles_controller.rb
def new
  @article = Article.new
end
# app/views/articles/new.html.erb
<%= form_for @article, url: {action: "create"}, html: {class: "nifty_form"} do |f| %>
  <%= f.text_field :title %>
  <%= f.text_area :body, size: "60x12" %>
  <%= f.submit "Create" %>
<% end %>

url 的部分可以改寫成 path 的方式,看 routes 提供什麼路徑給你

<%= form_for @article, articele_path, methods: "POST" , html: {class: "nifty_form"} do |f| %>
<!--  create 路徑的方式預設是用post方式將資料送過去的,所以加上 methods: "POST" -->
<!--  .... -->
<% end %>

form_with

Rails 5.1 版後出來的,基本上就是懶人寫法了,不再分成form_tagform_for,取決於你傳什麼進去。

<!-- url 的寫法 -->
<%= form_with(url: "/search", method: "get") do %>
  <%= label_tag(:q, "Search for:") %>
  <%= text_field_tag(:q) %>
  <%= submit_tag("Search") %>
<% end %>
<!-- model的寫法 -->
<%= form_with model: @article, class: "nifty_form" do |f| %>
  <%= f.text_field :title %>
  <%= f.text_area :body, size: "60x12" %>
  <%= f.submit "Create" %>
<% end %>

§§ 特別注意,使用form_with做出來的表單預設是用ajax的方式送出,也就是不跳頁,只會送出新的請求,用得好的話,會有很好的使用者的體驗(畢竟不換頁,速度感覺起來就比較快),不過用不好的話可能會發生使用者送出表單,畫面卻沒有動靜(畢竟不換頁嘛)。

§§ 若不想要使用ajax的方式送出表單,可以在 form with 多增加一行 local: true ,這樣就會用瀏覽器本身的表單提交方式。

§§ 一般而言,ajax 通常會搭配個 js 檔案去將畫面做變更,這樣才能讓使用者知道說資料已經寫好了。

至於 form content 的部分有很多可以設定,有空可以翻一些官方文件

strong parameter?

昨天有提到當我們試圖將一大包資料,直接寫進資料庫裡們會出現一個ActiveModel::ForbiddenAttributesError 錯誤訊息,以前的rails 是利用在
model裡設置白名單來允許可以存入資料庫的欄位。而Rails 4 之後提供了一種稱之 Strong Parameters 的做法,將過濾這件事丟給了controller,可以使用 permit 方法,來決定要寫入資料裡的欄位。

  def admin_params
    params.require(:admin).permit(:account, :password)
  end

以上,就是今天的三個問題啦,感謝各位看到這邊,若有任何建議,請各位不吝指教!我們明天見!


上一篇
Day_10 問題中場休息 & 部落格的管理員系統
下一篇
Day_12 migration? & 部落格的個人檔案
系列文
Ruby on Rails 新手的30個問題!30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言