2009-09-30 3 views
16

ActiveRecord ha alcuni metodi di callback diversi utilizzati per semplificare la logica del modello. Ad esempio i metodi after_find e before_create.Perché i callback di ActiveRecord richiedono che le variabili di istanza oi metodi di istanza siano preceduti da una parola chiave self?

Considerate questo esempio di codice:

class ExternalPrintingCard < ActiveRecord::Base 
    belongs_to :user 
    belongs_to :ph_user 

    after_create :change_pin 

    def change_pin 
    self.user.randomize_printer_pin 
    end 

    def after_find 
    return if self.card_status == false 
    self.card_status = false if self.is_used_up? 
    self.card_status = false if self.is_expired? 
    self.save! 
    end 
end 

Se rimuovo tutti i self prefissi dalle variabili di istanza o metodi di istanza, saranno chiamati questi 2 callback, ma è come se fossero variabili locali all'interno di questi callback metodi.

Questa variabile istanza (card_status), metodi di istanza (save!, is_used_up? e is_expired?) e associazione (user) funzionava bene fuori di questi 2 metodi di callback senza il prefisso self.

Il codice di esempio nella documentazione delle guide per i metodi di callback (metodi di istanza), sembra di utilizzare sempre il prefisso self anche se sta chiamando variabili di istanza o metodi, che per diritto essi sono accessibili senza il prefisso di self normalmente.

Spero che qualcuno con una migliore comprensione dei callback di ActiveRecord possa aiutare a far luce su questo comportamento.

Acclamazioni

risposta

14

Tecnicamente è solo bisogno di utilizzare l'auto di fronte ai metodi di assegnazione. Questo è necessario per distinguere tra un metodo di istanza con trailing = e un'assegnazione a una variabile locale.

+5

Vedere questo articolo Thoughtbot per molti dettagli: http://robots.thoughtbot.com/post/185504560/to-self-or-not-to-self –

+0

un altro articolo che lo spiega http: //www.rubyfleebie. com/uso-auto-esplicito / –

1

Nasmorn è corretto.

ActiveRecord :: Base ha inserito tutti i nomi di colonna all'interno della variabile di istanza @attributes (Hash) e crea metodi di istanza per i nomi di tali colonne.

Ad esempio:

card_status è una colonna della tabella external_printing_cards, esso avrà metodi di accesso con il nome card_status e card_status=

Da rubino definizione variabile locale è dinamico, la linea

def after_find 
    .... 
    card_status = false if self.is_used_up? 
    .... 
end 

significa che stiamo definendo e assegnando a una variabile locale card_status anziché il metodo di istanza card_status=

L'articolo pubblicato da Peer Allan fornisce ulteriori spiegazioni al riguardo.