Po pierwsze, prawie nigdy nie siedzę i nie piszę testów jednostkowych. Testy jednostkowe są środkiem do celu, a nie celem samym w sobie. Są sposobem na odpowiedź „czy ten kod wykonuje podstawowe zadanie, które powinien”.
Na przykład niektóre osoby napiszą funkcję, a następnie otworzą sesję interaktywną, aby przetestować ją na kilku wartościach i upewnić się, że działa:
def fact x
if x == 0
1
else
x * fact(x-1)
end
end
>> fact 10
=> 3628800
>> fact 7
=> 5040
Ale teraz odkrywasz błąd:
>> fact -1
SystemStackError: stack level too deep
from (irb):2:in `fact'
from (irb):5:in `fact'
from (irb):10
Więc to naprawisz:
def fact x
if x < 0
raise "Can't take the factorial of a negative number"
elsif x == 0
1
else
x * fact(x-1)
end
end
>> fact -1
RuntimeError: Can't take the factorial of a negative number
from (irb):3:in `fact'
from (irb):10
Ale teraz naprawdę powinieneś przetestować, aby upewnić się, że nadal działa:
>> fact 10
=> 3628800
>> fact 7
=> 5040
Jak widać, ciągle powtarzasz te same testy ... i musisz porównywać wyniki wizualnie. Testowanie jednostkowe jest sposobem na uniknięcie powtórzeń w tym przypadku; zmniejsza ilość pracy, którą musisz wykonać. I choć jest to głupiutki przykład, w prawdziwym świecie staje się coraz ważniejszy i coraz trudniejszy do ręcznego przetestowania. Oznacza to oczywiście, że ludzie po prostu nie testują poszczególnych składników; po prostu testują cały program. Ale wtedy pojawiają się błędy i są znacznie trudniejsze do znalezienia. Lub błędy się zdarzają i są naprawiane, ale ktoś ponownie wprowadza ten sam błąd, ponieważ nikt nie dodał przypadku testowego, aby upewnić się, że tak się nie stało. Albo ktoś patrzy na duży fragment kodu i mówi: „Nie mam pojęcia, co to ma zrobić, ponieważ nie jest to udokumentowane i nie ma testów ... jeśli naprawię ten błąd, nie mam pojęcia, czy w zależności od tego rozwiążę coś innego; może po prostu przepiszę to od nowa. ”
Testy jednostkowe zmniejszają wszystkie dodatkowe prace w tych przypadkach. Najlepszym sposobem na zapewnienie im dobrej zabawy jest upewnienie się, że ludzie rozumieją całą pracę, którą zastępują, oraz dodatkową elastyczność wynikającą z wiedzy o tym, co każdy element kodu powinien wykonać. Do pewnego stopnia ludzie muszą mieć trochę więcej doświadczenia w pisaniu i utrzymywaniu dużej bazy kodu, aby zrozumieć, jak ważne może być testowanie jednostkowe; jeśli cały ich kod jest czymś, co piszą i wyrzucają, nigdy tego nie zrozumieją.
Testy jednostkowe nie powinny być pisane po fakcie, jako dodatkowy obowiązek, gdy masz już „znany” kod, który już działa. Testy jednostkowe powinny być napisane jako pierwsze, a przynajmniej (ponieważ czasami zapomina się je najpierw napisać) zaraz po napisaniu danego kodu. Nazywa się to programowaniem opartym na testach i może pomóc w ulepszeniu interfejsów API; jeśli napiszesz testy, które najpierw wykonują interfejsy API, dowiesz się, gdzie korzystanie z interfejsów API jest trudne, zanim jeszcze napiszesz kod, i możesz przeprojektować znacznie łatwiej niż wtedy, gdy dodasz testy dopiero później.
MbUnit
Biblioteka zmieniła moje życie. Automatyczne testowanie jest ważne. Automatyczne testowanie oszczędza czas. Automatyczne testowanie oszczędza pieniądze. Automatyczne testowanie może uratować życie. Automatyczne testowanie jest jedynym sposobem. Autotestowanie to kolejna siatka bezpieczeństwa. Kiedy jestem jedną z 50 osób pracujących nad ogromną architekturą, czuję się jak kolejna cegła w ścianie. Dzięki testom jednostkowym mam kontrolę.