Только что столкнулся с этой проблемой сегодня, мое решение было основано на методе object_attributes=
, который предоставляется accepts_nested_attributes_for, я думаю, что это создает меньше беспорядка вместо переопределения стандартного метода установки ассоциации. Немного погрузившись в источник рельсов, чтобы найти это решение, вот ссылка github . Код:
class Report < ActiveRecord::Base
# attr: name :: String
# attr: report_detail_id :: Integer
belongs_to :report_detail
accepts_nested_attributes_for :report_detail
def report_detail_attributes=(attributes)
report_detail = ReportDetail.find_or_create_by_duration_and_display_duration_and_starting_month_and_period_offset(attrs[:duration],attrs[:display_duration],attrs[:starting_month],attrs[:period_offset])
attributes[:id]=report_detail.id
assign_nested_attributes_for_one_to_one_association(:report_detail, attributes)
end
end
Некоторое объяснение, если вы предоставите идентификатор, будет считаться обновлением, поэтому больше не будет создавать новые объекты. Также я знаю, что для этого подхода нужен запрос в плюсе, но пока не могу найти лучшего решения.
Кроме того, похоже, что у вас есть связь has_one между отчетом и подробностями отчета, если вы используете этот вариант, попробуйте следующее:
class Report < ActiveRecord::Base
# attr: name :: String
# attr: report_detail_id :: Integer
has_one :report_detail
accepts_nested_attributes_for :report_detail, :update_only=>true
end
Согласно документации это должно работать для вас.
Из рельсов3 документация:
: update_only
Позволяет указать, что существующая запись может обновляться только.
Новая запись может быть создана только тогда, когда
нет существующей записи это
опция работает только для одного к одному
ассоциации и игнорируется для
Коллекционные ассоциации. Этот вариант
по умолчанию отключено.
Надеюсь, это поможет, в любом случае, если вы найдете лучшее решение, пожалуйста, дайте мне знать.