Les gens semblent avoir expliqué certaines des méthodes de base dans lesquelles ils diffèrent, mais laissé de côté avant(:all) et de ne pas expliquer exactement pourquoi ils devraient être utilisés.
C'est ma conviction que les variables d'instance ont pas lieu d'être utilisé dans la grande majorité des specs, en partie à cause des raisons évoquées au début de cet article http://bitfluxx.com/2011/05/23/some-rspec-tips-and-best-practices.html, donc je n'en parle pas comme une option ici.
laissez-blocs
Code à l'intérieur d'un let
bloc est exécuté seulement si elle est référencée, le chargement paresseux cela signifie que la commande de ces blocs n'est pas pertinent. Cela vous donne une grande quantité de puissance pour couper vers le bas sur répétées de l'installation par le biais de vos spécifications.
Un (très artificiel, et petit) exemple de cela est la suivante:
let(:person) { build(:person) }
subject(:result) { Library.calculate_awesome(person, has_moustache) }
context 'with a moustache' do
let(:has_moustache) { true }
its(:is_awesome?) { should be_true }
end
context 'without a moustache' do
let(:has_moustache) { false }
its(:is_awesome?) { should be_false }
end
Quelque chose à noter est que la dernière let
bloc défini dans le contexte actuel sera utilisé. C'est bon pour le paramètre par défaut pour être utilisé pour la majorité des spécifications, qui peuvent être remplacées si nécessaire.
Par exemple, la vérification de la valeur de retour de l' calculate_awesome
si passé un person
modèle top_hat
la valeur true, mais pas de moustache serait fait comme:
context 'with no moustache but with a top hat' do
let(:has_moustache) { false }
let(:person) { build(:person, top_hat: true) }
its(:is_awesome?) { should be_true }
end
Une autre chose à noter à propos de laisser les blocs, c'est qu'ils ne doivent pas être utilisés si vous êtes à la recherche de quelque chose qui a été enregistré dans la base de données (c - Library.find_awesome_people(search_criteria)
) qu'ils ne seront pas enregistrées dans la base de données, sauf si elles ont déjà été citées. let!
ou before
des blocs sont ce qui doit être utilisé ici.
Aussi, ne jamais jamais utiliser before
pour déclencher l'exécution d' let
blocs, c'est ce qu' let!
est faite pour ça!
laissez! les blocs
let!
des blocs sont exécutés dans l'ordre de l'exécution (un peu comme un avant de bloc). La différence essentielle est que vous obtenez une référence explicite à cette variable, plutôt que de les obliger à revenir à des variables d'instance.
Comme avec d' let
blocs, si plusieurs let!
des blocs sont définies avec le même nom, le plus récemment défini est ce qui va être utilisé dans l'exécution. La principale différence étant que l' let!
blocs sera exécutée plusieurs fois si utilisé comme cela, alors que l' let
bloc n'exécutera la dernière fois.
before(:each) blocs
before(:each)
est la valeur par défaut avant de bloc, et peut donc être référencé en tant que before {}
plutôt que de spécifier le plein before(:each) {}
à chaque fois.
C'est ma préférence personnelle pour utiliser before
de blocs dans une base de situations. Je vais utiliser avant que les blocs si:
- Je suis l'aide de moqueries, cogner ou double
- Il est raisonnable de la taille de l'installation (en général c'est un signe que votre usine traits n'ont pas été configuré correctement)
- Il y a un certain nombre de variables qui je n'ai pas besoin de faire référence directement, mais sont requis pour l'installation
- Je suis en train d'écrire fonctionnelle contrôleur de tests dans les rails, et je veux exécuter une requête à l'essai (c -
before { get :index }
). Même si vous pouvez utiliser subject
dans beaucoup de cas, il se sent parfois plus explicite si vous n'avez pas besoin d'une référence.
Si vous vous trouvez l'écriture d'un vaste before
blocs pour vos specs, vérifiez vos usines et assurez-vous de bien comprendre les traits et leur flexibilité.
avant(:all) blocs
Ces ne sont jamais exécutées une fois, avant les specs, dans le contexte actuel (et ses enfants). Elles peuvent être utilisées pour grand avantage s'il est écrit correctement, comme il y a certaines situations, cela peut couper vers le bas sur l'exécution et de l'effort.
Un exemple (qui ne serait guère influer sur le temps d'exécution, en se moquant d'un ENV variable pour un test, qui vous ne devriez jamais avoir besoin de le faire une fois.
Espérons que cela aide :)