2009-06-18 5 views
2

Comme le souligne Anton (merci Anton!) Mon problème est l'association de cache dans les tests et il semble que j'ai créé correctement l'attribut nested_attribute dans l'usine. La syntaxe correcte est:Comment créer des associations RoR Factory avec accept_nested_attributes_for?

Factory.define :job do |f| 
    ... 
    f.vehicles_attributes [{:vin => "1", :model => "ford", :make => "escort"},{:vin => "1", :model => "ford", :make => "escort" }] 
end 

J'utilise accepts_nested__attributes_for dans mon modèle d'emploi et essaie de migrer vers fille usine après presque perdre mes billes « de plongée de fixation » à chaque fois que je change le modèle.

J'ai posté un tas de code ci-dessous, mais ma question est simple:

Comment puis-je utiliser pour créer des usines nested_attributes?

Je suis capable de créer une instance de travail en utilisant le code ci-dessous, mais je ne peux pas créer de véhicules dans mes tests unitaires. Sans les f.vehicles_attributes... mes tests de travail échouent aux validations.

Mes tests unitaires produisent les résultats suivants:

test "factory" do 
    job = Factory(:job) 
    assert(job.valid?) # => true 
    assert(job.vehicles.first.valid?) # => true 
    vehicle = Factory(:vehicle) 
    assert(vehicle.job.vehicles.size == 1) # => true 
    assert_equal(vehicle.job.vehicles.first.vin, "2") # => FALSE. <"1"> expected but was <"2"> 
    end 

Factory.define :job do |f| 
    ... 
    f.vehicles_attributes [:vin => "1", :model => "ford", :make => "escort" ] 
end 

Factory.define :vehicle do |f| 
    f.vin "2" 
    f.model "ford" 
    f.make "escort" 
    f.association :job 
end 

class Job < ActiveRecord::Base 
    has_many :vehicles, :dependent => :destroy 
    validate :job_must_have_at_least_one_vehicle 
    accepts_nested_attributes_for :vehicles, :allow_destroy => :true, :reject_if => proc { |vehicle_attributes| Job.insufficient_vehicle_input?(vehicle_attributes) } 

    def job_must_have_at_least_one_vehicle 
    errors.add(:vehicles, "need to be added") if self.vehicles.empty? 
    end 

    def self.insufficient_vehicle_input?(vehicle_attributes) 
    vehicle_property_keys = vehicle_attributes.keys 
    vehicle_property_keys.delete('_delete') 
    vehicle_property_keys.delete('is_operational') 
    vehicle_property_keys.delete('has_keys') 
    vehicle_property_keys.each do |attribute_to_validate| 
     if(!vehicle_attributes[attribute_to_validate].nil? && !vehicle_attributes[attribute_to_validate].empty?) 
     return false 
     end 
    end 
    return true 
    end 
end 
+0

BTW, l'utilisation correcte de assert_equal est: assert_equal (prévu, réel) –

Répondre

2

Il est tout au sujet de la mise en cache d'association .

Voici comment cela fonctionne:
1. Factory(:vehicle) objet builds vehicle et crée job enregistrement
2. Après cela, il remplit vehicle.job_id et l'enregistre

Mais vehicle.job est signalé un objet job de l'étape 1 .
donc, tout ce que vous avez besoin est de recharger job:

vehicle = Factory(:vehicle) 
vehicle.job.reload.vehicles.size # => 2 
Questions connexes