昨日、has_and_belongs_to_many を利用したモデルを作成しました。
モデルを作ったはいいものの、ビュー/コントローラからの利用方法が分からず、またいろいろと調べたのでメモ。
画面
グループにユーザーを追加するUIを作ってみたので、その手順です。
ひな形はscaffold_controllerで作成。
$ rails generate scaffold_controller user
$ rails generate scaffold_controller group
scaffold_controllerではモデルの項目がビューに反映されないので、そこは付け足しました。
以下、この状態からの変更点をメモ。
ビュー
<div class="field">
<strong>Users</strong>
<ul>
<% @users.each do |user| %>
<li>
<label>
<% checked = user.groups.exists?(@group.id) ? true : false %>
<%= f.check_box 'user_ids', { :name => 'group[user_ids][]', :checked => checked }, user.id, nil %>
<%= user.name %>
</label>
</li>
<% end %>
</ul>
</div>
入力フォームにユーザー選択のチェックボックスを追加。
:name => 'group[user_ids][]'
としてユーザIDを配列で渡します。
コントローラー
before_action :set_users, only: [:new, :edit]
private
def set_users
@users = User.all
end
def group_params
p = params.require(:group).permit(:name, :description, :user_ids => [])
p[:user_ids] = [] if p[:user_ids].nil?
p
end
パラメータ取得のメソッドを変更してuser_idsを受け取るようにします。
p[:user_ids] = [] if p[:user_ids].nil?
の部分は、チェックボックスがひとつも選択されなかった場合に、すべてのユーザーをグループから削除するために追加してます。
以上。
これだけのことを調べるのに結構かかってしまった・・・
追記
後日試してみたところ、上記の方法は has_many :through のアソシエーションでも使えました。
collection_singular_ids=ids
のメソッドが定義されるアソシエーションで使えるのかな?と思います。