Ruby on Rails, две модели в одном виде
У меня есть две очень похожие модели. Предварительная обработка и диагностика, которые относятся к модели. Пациент:
class Pretreatment < ActiveRecord::Base
belongs_to :patient
attr_accessible :content
end
class Diagnosis < ActiveRecord::Base
belongs_to :patient
attr_accessible :content
end
class Patient < ActiveRecord::Base
attr_accessible :age, :name, :city, :street, :number
has_many :anamneses
has_many :befunds
end
На странице Patient
show я показываю две формы: одну для Preatreatment
и другую для Diagnosis
:
<%= form_for([@patient, @patient.preatreatments.build]) do |f| %>
<div class="field">
<%= f.label :conten %><br />
<%= f.text_field :content %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
<%= form_for([@patient, @patient.diagnosiss.build]) do |f| %>
<div class="field">
<%= f.label :content %><br />
<%= f.text_field :content %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
Мой вопрос в том, как я могу объединить две формы, так что пользователю нужно нажать только кнопку отправки? я m not sure but I think nested attributes is not the right thing to handle it, maybe the
fields_for` тег?
Обновление Я попытался использовать тег fields_for
:
<%= form_for([@patient, @patient.pretreatment.build]) do |f| %>
<div class="field">
<%= f.label :content %><br />
<%= f.text_field :content %>
</div>
<%= fields_for([@patient, @patient.diagnosiss.build]) do |u| %>
<div class="field">
<%= u.label :content %><br />
<%= u.text_field :content %>
</div>
<% end %>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
Но я получаю ошибку:
undefined method `model_name' for Array:Class in <%= fields_for([@patient,@patient.befunds.build]) do |u| %>
Ответы
Ответ 1
Используйте fields_for
для связанных моделей.
Не должно быть квадратных скобок вокруг параметров fields_for
В вашем примере кода я не могу найти связь между Patient
и Diagnosis
, а множественное число диагнозов диагнозов, вы можете указать это в config/initializers/inflections.rb
:
ActiveSupport::Inflector.inflections do |inflect|
inflect.irregular 'diagnosis','diagnoses'
end
Итак, ваша модель Patient
должна содержать
class Patient < ActiveRecord::Base
attr_accessible :age, :name, :city, :street, :number
has_many :diagnoses
end
И вы можете написать в своей форме:
<div class="field">
<%= f.label :content %><br />
<%= f.text_field :content %>
</div>
<%= fields_for(@patient, @patient.diagnoses.build) do |u| %>
<div class="field">
<%= u.label :content %><br />
<%= u.text_field :content %>
</div>
<% end %>
<div class="actions">
<%= f.submit %>
</div>
Ответ 2
Вы можете добиться этого, используя вложенные атрибуты:
patient.rb
class Patient < ActiveRecord::Base
attr_accessible :age, :name, :pretreatments_attributes, :diagnosiss_attributes
has_many :pretreatments
has_many :diagnosiss
accepts_nested_attributes_for :pretreatments
accepts_nested_attributes_for :diagnosiss
end
patients_controller.rb
def show
@patient = Patient.find(params[:id])
@patient.pretreatments.build
@patient.diagnosiss.build
respond_to do |format|
format.html # show.html.erb
format.json { render json: @patient }
end
end
пациенты/show.html.erb:
<%= form_for @patient do |f|%>
<h3>Pretreatments:</h3>
<%= f.fields_for :pretreatments do |field| %>
<%= field.label "Content" %></div>
<%= field.text_field :content %>
<% end %>
<h3>Diagnosis:</h3>
<%= f.fields_for :diagnosiss do |field| %>
<%= field.label "Content" %></div>
<%= field.text_field :content %>
<% end %>
<%=f.submit %>
<% end %>
И что все
Ответ 3
Есть несколько способов сделать это:
- Как работает
fields_for
, у вас есть form_for
для родительской модели и внутри него вы можете разместить fields_for
модели, принадлежащие родительскому. Хороший пример приведен в Rails Docs
- Простой и расширяемый вариант с течением времени, но не очень "семантический", можно использовать JavaScript/JQuery. Вы можете запустить
$("form #new_pretreatments").submit();
и то же самое для Диагностики после нажатия кнопки.
- Возможно, вместо этого у вас может быть только одна модель для их хранения. Например, модель под названием "Болезнь". Каждый раз, когда у пациента возникает болезнь, создается новая, и для каждой из них имеются столбцы Диагностика и Предварительная обработка. Вероятно, это лучший вариант, вместо добавления другой модели для каждого бит информации, которую может иметь пациент.
Ответ 4
Вы можете использовать fields_for
для второй модели, которая работает как form_for
, но не генерирует теги формы. См. docs.
Ответ 5
Есть несколько драгоценных камней для вложенных форм. один из них awesome_nested_fields. Я не использовал это раньше, но это показывает хороший код в документации. Другой - simple_form.
Надеюсь, что это поможет!!!