2012-08-10 5 views
5

Sto tentando di creare un modulo che mi consenta di inviare nuovi record per un'associazione in cui sono raggruppati gli input di associazione.raggruppamento e campi_per

class Product < AR::Base 
    has_many :properties 
    accepts_nested_attributes_for :properties 
    end 

noti che nel controllore una serie di proprietà sono costruiti per il prodotto, in modo @product.properties.empty? # => false.

Il valore sotto fields_for fornisce gli ingressi corretti con nomi come product[properties_attributes][0][value].

= form.fields_for :properties do |pform|                                
    = pform.input :value 

Ma non appena cerco di gruppo l'associazione che non genera più ingressi con i nomi corretti:

- @product.properties.group_by(&:group_name).each do |group_name, properties| 
    %h3= group_name              
    = form.fields_for properties do |pform|                                
    = pform.input :value 

Questo crea ingressi che l'attributo name come product[product_property][value] quando in realtà dovrebbe essere product[property_attributes][0][value] come al primo esempio.

The Rails documentazione suggerisce che si può fare questo:

= form.fields_for :properties_attributes, properties do |pform| 

Ma questo dà un errore "valore di metodo non definito Array".

risposta

6

È necessario impostare in questo modo:

- @product.properties.group_by(&:group_name).each do |group_name, properties| 
    %h3= group_name 
    = form.fields_for :properties, properties do |pform| 
    = pform.text_field :value 

dovrebbe funzionare bene, dal momento che hai accepts_nested_attributes_for :properties rotaie sapere che si suppone di creare campi per properties_attributes. Inoltre si consiglia di aggiungere attr_accessible :properties_attributes se si utilizza uno dei più nuovi Rails e se non avete aggiunto al vostro modello di ancora;)

Inoltre, se si vuole fare un po 'di base di decisione sulla singola proprietà si può usare il seguente modulo così:

- @product.properties.group_by(&:group_name).each do |group_name, properties| 
    %h3= group_name 
    - properties.each do |property| 
    = form.fields_for :properties, property do |pform| 
     = pform.text_field :value 

Entrambi sono ben descritto qui: http://api.rubyonrails.org/classes/ActionView/Helpers/FormHelper.html#method-i-fields_for sotto One-To-Many sezione

+0

Questo sembra funzionare, non so il motivo per cui non ho provato ': properties' invece di ': property_attributes'. Accettiamo a breve. – Kris

1

Non conosco una soluzione "Rails" pulita per questo genere di cose, ma gestisco spesso questi tipi di situazioni in modo più manuale. es. - Passa attraverso i gruppi e mostra condizionatamente solo le proprietà che si trovano in un particolare gruppo.

class Product < AR::Base 
    has_many :properties 
    accepts_nested_attributes_for :properties 

    def group_names 
    properties.map(&:group_name).uniq.sort 
    end 
end 

Nella vista

- for group_name in product.group_names 
    = form.fields_for :properties do |pform| 
    %h3= group_name 
    - if pform.object.group_name.eql?(group_name) 
     = pform.input :value 

Ci può essere un po 'in testa con questo, ottenendo l'elenco dei prodotti oggetti di volte. Potresti essere in grado di modificare has_many: associazione delle proprietà per recuperare le proprietà nell'ordine group_name, quindi potresti aggiungere% h3 quando è un nuovo gruppo.

- previous_group_name = nil 
= form.fields_for :properties do |pform| 
    - if pform.object.group_name != previous_group_name 
    %h3= pform.object.group_name 
    = pform.input :value 
    - previous_group_name = pform.object.group_name 

Alcune idee per voi ...