Testowanie - nieprzyjemna sprawa. Piszesz program, wszystko wygląda ładnie, schludnie, a tu nagle okazuje się, że coś nie działa. Dodatkowe kilka godzin/dni szukania błędu, szukania przyczyny błędu, poprawiania. Testy są ważne, bo bez tego - jak wiadomo - program nie działa właściwie, użytkownicy wściekli, ogólnie nieprzyjemna sprawa.
Z testowaniem zawsze jest jedna nieprzyjemna sprawa: często można znaleźć przypadek tak ekstremalny, w którym nawet wyglądający na idealny kod nie będzie działał poprawnie. Coś nie działa zaraz po starcie programu, coś przy pewnej specyficznej konfiguracji nie uruchamia się właściwie. Co najzabawniejsze, czasem zdarzy się, że przyczyna wkurzającego błędu znajduje się w dawno napisanej części kodu, który do tego sam w sobie działa idealnie. Weźmy taki przykład: przebieg programu jest następujący: inicjalizacja modułu sieciowego, inicjalizacja i wczytanie do pamięci bazy danych, rozpoczęcie nasłuchu na sockecie. Niby wszystko w porządku... dopóki taka aplikacja nie trafia do autostartu. Tam nagle okazuje się, że pierwszych kilka połączeń jest odrzucanych, ponieważ... aplikacja jeszcze nie nasłuchuje.
Powód? Jak się teraz na to patrzy, powód jest oczywisty - wczytywanie bazy danych blokuje program i opóźnia rozpoczęcie nasłuchu. Każdy z komponentów z osobna działa poprawnie, natomiast razem produkują nieciekawy błąd. Naprawa jest prosta - rozpoczynamy wczytywanie bazy danych, a jednocześnie (np. w osobnym wątku) uruchamiamy nasłuch.
Wniosek z tego jest prosty: testujemy nie tylko każdy komponent z osobna po jego ukończeniu; po kilku zmianach przetestować trzeba ponownie cały program - zwykle ilość wzajemnie na siebie wpływających elementów jest na tyle duża, że nie można wykluczyć różnych dziwnych oraz nieprzewidzianych zachowań. Czyli: poza unit-testami i testami komponentów warto robić też cyklicznie testy całościowe. Zapewniam, oszczędzi to stresu i problemów.
Brak komentarzy:
Prześlij komentarz