1. 是什么
Routes 的存在是為了匹配請(qǐng)求中的URL
和定義的controller#action
.
讓我來簡(jiǎn)單地舉個(gè)例子:config/routes.rb
是你程序的大門买乃,門后有許多細(xì)小的路徑通向你想要真正到達(dá)的目的地饭弓,每條路徑的入口處都有一個(gè)路牌斋荞,告訴你目的地的名稱盲憎,通過辨別路牌你就可以到達(dá)最終想要的目的地而不用擔(dān)心迷路幼驶。那么分析一下上述例子汇鞭,每一條路徑就是你定義的一個(gè)你定義的route
規(guī)則,路口的路牌是請(qǐng)求中HTTP動(dòng)詞 + URL
的組合碌冶,道路通向的目的地是某個(gè)控制器的特定行為湿痢。除匹配功能之外,路徑還提供了些附帶功能扑庞,比如自動(dòng)生成_url 和 _path
幫助方法譬重,分別用來表示該路徑的絕對(duì)路徑和相對(duì)路徑,而不需要使用硬編碼字符串罐氨。
2. 在哪定義
快速瀏覽routes.rb
: 所有路徑的定義在傳給 Rails.application.routes.draw
的一個(gè)大大的block
中臀规。定義路徑的代碼是簡(jiǎn)單的紅寶石代碼,你需要按照特定的規(guī)則定義路徑栅隐,主要的定義方式有兩種: 普通路徑和資源路徑塔嬉,稍后會(huì)詳細(xì)介紹狠怨。當(dāng)有請(qǐng)求進(jìn)入時(shí),代碼塊中的代碼自頂向下執(zhí)行邑遏,請(qǐng)求會(huì)查看每個(gè)路徑的路牌是否匹配,并被分發(fā)到第一個(gè)匹配的路徑恰矩,如果沒有匹配的路徑记盒,程序會(huì)返回給調(diào)用者一個(gè)HTTP 404
.
3. 普通路徑
普通路徑又稱為非資源路徑,雖然大多數(shù)情況下你使用的都是資源型的路徑外傅,但是某些特定的情況纪吮,普通路徑會(huì)更加合理,比如某些無法抽象成資源的時(shí)候萎胰,或是在遺留系統(tǒng)中給老的URL
匹配一些新的行為等等碾盟。下面列出了一些常見的例子:
root to: 'pages#main'
get 'users/:id', to: 'users#show'
get 'users/:id', to: 'users#show', defaults: { format: 'json' }
get 'users/:id', to: 'users#show', as: :members # members_path(@user)
4. 資源路徑
資源路徑使用一條語句可以快速定義多條路徑規(guī)則,這些路徑規(guī)則符合特定規(guī)律技竟,所以便于其他程序員閱讀代碼冰肴。在學(xué)習(xí)資源路徑之前先要理解兩個(gè)概念: CRUD, RESTful.
RESTful 把事物抽象成資源,在不同層次統(tǒng)一操作類型榔组。如用戶注冊(cè)操作熙尉,發(fā)送一個(gè)對(duì)用戶資源的創(chuàng)建操作請(qǐng)求 -> 通過路徑匹配到了控制器的創(chuàng)建行為 -> 在數(shù)據(jù)庫(kù)中插一條新的用戶記錄。CRUD 把對(duì)資源的操作抽象為四類 CREATE, READ, UPDATE, DELETE
.
4.1 幫助方法
RESTful
路徑會(huì)自動(dòng)生成一堆helper
:
photos_url/path
映射到 index, create
new_photo_url/path
映射到 new
edit_photo_url/path
映射到 edit
photo_url/path
映射到 show, update, destroy
Tip: 可以在控制臺(tái)里通過使用 app.xxx_path
來查看路徑
Tip: 可以在控制臺(tái)里通過使用 app.url_for(@user)
來查看完整路徑
Tip: 若URL
中包含subdomain
要使用_url
來確保路徑是完整的
4.2 單資源
單資源沒有index
單資源生成如下的helper
:
new_geocoder_url/path
映射到 new
edit_geocoder_url/path
映射到 edit
geocoder_url/path
映射到 create, show, update, destroy
Tip: 資源名是單數(shù)形式搓扯,但是對(duì)應(yīng)的controller
名稱依然是復(fù)數(shù)
Tip: 單資源在使用form_for
定義表單時(shí)检痰,要制定url
,否則會(huì)錯(cuò)誤
form_for @geocoder, url: geocoder_path do |f|
5. 路徑高級(jí)用法
(1) 一次定義多個(gè)資源:resources :photos, :books, :videos
(2) 嵌套資源:多層嵌套會(huì)污染路徑锨推,降低可讀性铅歼,保持單層嵌套
(3) 嵌套資源最佳實(shí)現(xiàn):淺嵌套,使用shallow
只嵌套index, create, new
(4) 在資源中添加額外路徑:member, collection
注意兩者邏輯區(qū)別
(5) 使用controller
來指定資源所對(duì)應(yīng)的控制器
例如:map.resources :photos, :controller => "images"
幫助方法時(shí)會(huì)依據(jù)資源的名稱生成换可,而不是controller
的名稱
因此椎椰,在這個(gè)例子里,就會(huì)得到photos_path, new_photo_path
等等.
(6) 使用namespace
來管理你的路徑和控制器
控制器必須包裹在命名空間模塊中沾鳄,并所屬與相應(yīng)的文件目錄下俭识;
路徑包含相同的命名空間來和控制器相匹配
(7) 若想打破路徑命名空間和控制器模塊相匹配的規(guī)則,使用scope
使用module
選項(xiàng)可以去除url
路徑和幫助方法中的命名空間名稱洞渔,保持簡(jiǎn)潔
使用path
選項(xiàng)可以在url
中增添虛擬的命名空間名稱套媚,增加路徑的邏輯結(jié)構(gòu)
使用as
選項(xiàng)可以在生成的幫助方法中添加前綴名稱
(8) 使用concern
來共享某個(gè)路徑,如共享子資源磁椒,命名空間包含路徑等
(9) 使用only 和 except
限制自動(dòng)生成的路徑規(guī)則
(10) 使用constraints
生成自定義限制
constraints: { id: /^\d/ }
限制參數(shù)格式
constraints subdomain: 'admin'
限制子域名
6. 路徑的查看和測(cè)試
個(gè)人覺得給路徑寫測(cè)試沒什么必要堤瘤,使用以下方式看看一就好啦
網(wǎng)頁版查看路徑信息:http://localhost:3000/rails/info/routes
命令行查看路徑信息:$ rake routes # -g 過濾請(qǐng)求條件, -c 過濾控制器條件
$ rake routes -g new_user
$ rake routes -g POST
$ rake routes -g /admin/users/:id
$ rake routes -c users
$ rake routes -c admin/users