2011-10-21 1 views
1

Vous devenez fou ici. N'importe quel pointeur reçu avec reconnaissance!Variable de modèle de Rails changeant de façon inattendue

J'ai un modèle de livraison et j'essaye d'ajouter une méthode pour mettre à jour l'état de livraison, basé sur des lignes de livraison. Cette fonction est définie dans la classe modèle et delivery_state est l'un des modèles les attributs:

def updateDeliveryState 
    expectedLines = DeliveryLine.where(:delivery_id => id, 
             :line_state => 'EXPECTED') 
    logger.debug "State1: #{delivery_state}" 

    if expectedLines.length == 0 
    if delivery_state == 'EXPECTED' || delivery_state == 'RECEIVING' 
     delivery_state = 'RECEIVED'    # commenting this line fixes it 
     save 
    end 
    else 
    logger.debug "State2: #{delivery_state}" 
    if delivery_state == 'EXPECTED' 
     logger.debug "Updating to receiving" 
     delivery_state = 'RECEIVING' 
     save 
    end 
    end 
end 

Ce que je vois dans le journal est que entre les 2 logger.debug lignes, la delivery_state a été dégagé:

State1: EXPECTED 
DeliveryLine Load (4.5ms) SELECT "delivery_lines".* FROM "delivery_lines" 
WHERE "delivery_lines"."line_state" = 'EXPECTED' 
AND "delivery_lines"."delivery_id" = 227 
State2: 

Si je commente la ligne marquée dans le code ci-dessus, il semble fonctionner OK:

State1: EXPECTED 
DeliveryLine Load (9.6ms) SELECT "delivery_lines".* FROM "delivery_lines" 
WHERE "delivery_lines"."line_state" = 'EXPECTED' 
AND "delivery_lines"."delivery_id" = 227 
State2: EXPECTED 
Updating to receiving 

Cependant, je peux voir après avoir rafraîchi que la livraison est sti Attendez-vous après cela ??

+0

Pouvez-vous essayer 'self.delivery_state = « RECEIVED'' l'intérieur du premier 'if' à Assurez-vous que vous ne créez pas de variable locale et appelez le setter à la place? –

Répondre

3

Pour des détails sur mon commentaire: il semble que vous créez une variable locale dans le if. Regardez:

class Foo 
    attr_accessor :bar 

    def test 
    unless bar 
     bar = 1 
    end 
    end 
end 

f = Foo.new 
f.test 
puts f.bar # empty line, bar is nil 

Maintenant, nous allons nous assurer que nous appelons le poseur:

class Foo 
    attr_accessor :bar 

    def test 
    unless bar 
     self.bar = 1 
    end 
    end 
end 

f = Foo.new 
f.test 
puts f.bar # prints 1 

Voir: Why do ruby setters need “self.” qualification within the class?

+0

Merci! Ça marche et merci surtout pour le lien expliquant ce qui se passe! J'avais d'abord écrit ce code dans le contrôleur, et donc je savais que cela devrait fonctionner, mais je ne savais pas ce que j'avais cassé. – asc99c

0

pouvez-vous essayer d'utiliser save(:validate => false)?

Parfois, Rails a cette vilaine habitude d'échouer silencieusement aux validations et de ne pas enregistrer.

Vous voulez probablement enregistrer votre état peu importe ... :)

+0

Il a un bug dans son code - c'est assez évident - alors pourquoi le downvvote? – Tilo

+0

Je suis corrigé – Tilo

+0

Je suis d'accord, votre réponse est correcte - je suppose que je n'ai jamais rencontré celui-là, parce que j'écris toujours explicitement soi-même. – Tilo

Questions connexes