はじめに
「〇〇さんのブログ記事」のようなページを作成する際、ルーティングの書き方を迷ったのでネストされたリソースのルーティングについてまとめます
やりたいこと
〇〇さんのブログ記事ページを作成したい
(〇〇さん以外のブログ記事はページに表示しない)
この場合、〇〇さんにブログ記事をネストすると簡単にできる
MemberとEntryモデルが存在し、1対多で関連づけられているモデル
has_many :entries
belongs_to :member
→Memberモデルの下にEntryモデルをネストする
ルーティングの書き方
resources :members do
resource :entries
end
このルーティングによって、entriesControllerのアクションは以下のパスでアクセスできるようになる
アクション | パス | HTTP |
---|---|---|
index | members/123/entries | GET |
show | members/123/entries/456 | GET |
new | members/123/entries/new | GET |
edit | members/123/entries/456/edit | GET |
create | members/123/entries | POST |
update | members/123/entries/456 | PATCH |
destroy | members/123/entries/456 | DELETE |
idが123の会員の記事一覧ページ・・・indexアクション
members/123/entriesでアクセスが可能
idが123の会員の456の記事詳細ページ・・・showアクション
members/123/entries/456でアクセスが可能
パラメータ取得について
123・・・params[:member_id]
456・・・params[:id]
ネストされたリソースへのリンクを作成する場合
アクション | パスを返すメソッド |
---|---|
index | member_entries_path(@member) |
show | member_entries_path(@member, @entry) |
〜省略〜 |
entriesControllerのアクションのパスでidを指定するモデルを引数に指定する必要があります
※members/123/entriesの場合はmember.idが指定されているので引数にmemberは必要となる
パスを返すメソッドの代わりの配列を指定する場合
アクション | パスを表す配列 |
---|---|
index | [@member, :entries] |
show | [@member, @entry] |
new | [:new, @member, :entries] |
edit | [:edit, @member, @entry] |
create | [@member, :entries] |
update | [@member, @entry] |
destroy | [@member, @entry] |
ネストする・しない混合したルーティングも可能
resources :members do
resource :entries, only: [:index]
end
resource :entries
indexアクションはネストしたパスmembers/123/entriesでも、ネストしていないentriesでもアクセスが可能となる
余談・・・
only: [:index, :show]
の記載をすると、indexアクション・showアクションのみのルーテングが作成されるが、only: []
の記載をすると、すべてのアクションを無効化することができる
参考
【Rails】1対1のアソシエーションにおけるネストされたリソース設計について
【Rails】ネストしたresourcesをフル活用したアプリケーションの作成方法|_url, _path, form_with modelのエラー対処法