Rails has_many :through with Checkboxes

2012-09-25

Seems like every few months I need to build a Rails form that sets a many-to-many relationship with checkboxes. This happens when the form lets you edit model A, which has zero or more Bs, and there are few enough Bs that it makes sense to present them all as a list of checkboxes.

There are lots of blog posts around the Internet that tell you how to do this with elaborate ActiveRecord callbacks and other custom methods, but all that is unnecessary. I know Rails can do everything automatically, but I always wind up leaving out some detail so that it doesn’t work. Here is a nice blog post that gives everything you need:

http://millarian.com/programming/ruby-on-rails/quick-tip-has_many-through-checkboxes/

Here is the code just in case that link disappears:

# app/models/user.rb
class User < ActiveRecord::Base
  has_many :memberships, :dependent => :destroy
  has_many :groups, :through => :memberships
end


# app/models/group.rb
class Group < ActiveRecord::Base
  has_many :memberships, :dependent => :destroy
  has_many :users, :through => :memberships
end


# app/models/membership.rb
class Membership < ActiveRecord::Base
  belongs_to :group
  belongs_to :user
end


# app/views/users/edit.html.erb
<h1>User <%= @user.id -%></h1>
<h2>Group Memberships</h2>
<% form_for @user do -%>
  <% Group.all.each do |group| -%>
    <div>
      <%= check_box_tag :group_ids, group.id, @user.groups.include?(group), :name => 'user[group_ids][]' -%>
      <%= label_tag :group_ids, group.id -%>
    </div>
  <% end -%>
  <%= submit_tag -%>
<% end -%>
blog comments powered by Disqus Prev: db_leftovers gets CHECK constraints Next: Fonts, Credibility, and "Statistically Significant"