2011-08-21 9 views
2

Мне нужно добавить метаданные о связях HABTM. Я хотел использовать has_many: через связь для этого, но это необязательно. Здесь проблема упрощается:has_many: through - Добавление метаданных в сквозные отношения

class Customer < ActiveRecord::Base 
    has_many :customer_teddy_bears 
    has_many :teddy_bears, :through => :customer_teddy_bears 
end 

class CustomerTeddyBear < ActiveRecrod::Base 
    belongs_to :customer 
    belongs_to :teddy_bear 
    attr_accesible :most_favoritest # just to show it exists, boolean 
end 

class TeddyBear < ActiveRecord::Base 
    has_many :cusomter_teddy_bears 
end 

Так что мне нужно сделать, это начать добавлять плюшевых медведей к моим клиентам, плюшевые мишки фиксированный набор данных, позволяет сказать fireman_bear, doctor_bear, dominatrix_bear. Любой клиент может претендовать на то, чтобы иметь своего рода плюшевого мишку, но они также указывают, что является их самым любимым медведем. Поскольку я не могу изменить модель медведей, потому что это глобально распространено среди всех клиентов, я добавляю метаданные (среди других метаданных) к CustomerTeddyBear.

Проблема в том, что следующее не работает.

customer = Customer.new # new record, not yet saved, this must be handled. 
customer.teddy_bears << fireman_bear 
customer.teddy_bears << doctor_bear 
# now to set some metadata 
favoritest_record = customer.customer_teddy_bears.select{|ctb| ctb.teddy_bear == doctor_bear}.first 
favoritest_record.most_favoritest = true 

Приведенный выше код не работает, так как customer_teddy_bears записи заполняются только во время сохранения при создании записей в базе данных. Есть ли другой механизм для этого?

Если нет ничего «автоматизированы», встроенный в рельсах я просто придется вручную управлять эти отношения путем включения teddy_bears когда я выбираю customer_teddy_bears и с использованием таких методов, как

def teddy_bears 
    self.customer_teddy_bears.map(&:teddy_bear) 
end 

наряду с созданием ассоциации вручную, а не используя: через отношения.

Обратите внимание, что все это должно произойти до того, как #save будет выполнен на объекте Customer, поэтому мне нужно установить все соответствующие метаданные, находясь в памяти.

Рекомендации Я получил от #RubyOnRails

ctb = customer.customer_teddy_bears.build({:customer => customer, :teddy_bear => fireman_bear}) 
ctb2 = customer.customer_teddy_bears.build({:customer => customer, :teddy_bear => doctor_bear}) 
... 
ctb.most_favoritest = true 

ответ

0

Решение, которое я был вынужден прибегнуть к вручную построения CustomerTeddyBear объекта и установки как клиента, teddy_bear и most_favoritest. В основном большую часть времени, доступ на customer.customer_teddy_bears.map(&:teddy_bear), по крайней мере, в логике, где возможно, что запись еще не сохранена, в противном случае просто сокращен до customer.teddy_bears.

1

Вы можете просто сделать это:

customer = Customer.new # new record, not yet saved, this must be handled. 
customer.teddy_bears << fireman_bear 
customer.teddy_bears << doctor_bear 
customer.save 

fav = CustomerTeddyBear.where(:customer_id => customer.id, :teddybear_id => doctor_bear.id) 
fav.most_favoritest = true 
fav.save 
+0

Я не могу этого сделать. Сохранение не может произойти до установки fav.most_favoritest = true. –

Смежные вопросы