2012-01-09 4 views
1

Что является самым простым способом проверить, чтобы создание новой записи включало создание связанной записи через has_and_belongs_to_many? Например, у меня есть:has_and_belongs_to_many validations

class Person < ActiveRecord::Base 
    has_and_belongs_to_many :groups 
end 

class Group < ActiveRecord::Base 
    has_and_belongs_to_many :people 
end 

Я хочу валидацию огня по созданию нового человека, чтобы убедиться, что они принадлежат, по крайней мере, одной группе.

Кроме того, как бы я построил это в контроллере? Сейчас у меня есть:

def create 
    @person = current_user.people.new(params[:person]) 
end 

Я хотел бы Params включить группу хэша, а также, чтобы действовать как своего рода гнездовой ресурса.

Я просмотрел документацию Rails, и я не смог найти что-либо в этом конкретном случае. Если бы кто-то мог объяснить это мне или указать мне в правильном направлении, я был бы очень доволен. Благодаря!

ответ

3

Если вы хотите дать пользователю возможность создать одну или несколько групп во время создания человека, а затем подтвердить, что эти группы были созданы, укажите, пожалуйста. В противном случае оставшаяся часть этого ответа будет посвящена созданию Лица и проверке того, что он связан с хотя бы одной существующей группой.

Если вы спрашиваете, как проверить существование ассоциации Person-Group в таблице join group_people, это можно сделать с помощью странных запросов sql и нецелесообразно. Просто верьте, что хорошо протестированный ActiveRecord работает правильно.

Вы можете, однако, подтвердить существование одной или нескольких групп в записи Person перед ее сохранением.

Пока вы мигрировали таблицы объединения под названием groups_people:

# db/migrate/xxxxxxxxxxxxxx_create_groups_people 
class CreateGroupsPeople < ActiveRecord::Migration 
    def change 
    create_table :groups_people, :id => false do |t| 
     t.string :group_id, :null => false 
     t.string :person_id, :null => false 
    end 
    end 
end 

# $ rake db:migrate 

, и контроллер правильно:

# app/controllers/people_controller.rb 
class PeopleController < ApplicationController 
    def new 
    @groups = Group.all 
    @person = Person.new 
    end 

    def create 
    @person= Person.new(params[:person]) 
    if @person.save 
     # render/redirect_to and/or flash stuff 
    else 
     # render and/or flash stuff 
    end 
    end 
end 

, и у Вас есть все существующие варианты группы как флажки:

# app/views/people/new.html.erb 
<%= form_for @person do |f| %> 
    <%= f.label :name %> 
    <%= f.text_field :name %> 
    # same for other person attributes 

    <% @groups.each do |g| %> 
    <%= check_box_tag 'person[group_ids][]', g.id, false, :id => g.group_name_attr %> 
    <%= label_tag g.group_name_attr %> 
    <% end %> 

    <%= f.submit 'Create!' %> 
<% end %> 

, то вы можете подтвердить наличие групп в вашей Личной записи:

class Person < ActiveRecord::Base 
    validates_presence_of :groups 

    has_and_belongs_to_many :groups 
end 

Существует validates_associated helper, но не было бы необходимости в этом случае, когда вы показываете Group.all в качестве checkboxed опций.

Для этого не требуется accept_nested_attributes_for. Это было бы, если бы вы создавали группу для человека при создании Лица. Опять же, пожалуйста, укажите, если это так.

Просто примечание: проверка входящей формы, которая включает Group.all в качестве опций и, дает возможность создать группу вместе с человеком, но это сложно, но сложно. Это предполагает обход существующих валидаций на модели Группы, если таковые имеются, что, вероятно, есть.