Не знам точно каква е идеята на ТДД, но аз съм стигнал до няколко извода и гледам, че тук ги коментирате и тях.
1. По време на дизайна (на архитектурата) мисли и за тестването. Код (архитектура) която не е мислена за тестване много трудно се тества.
Един стар проект имаме без да е замислен за юнит тестове. Ми то, за да му тестваш персистансето ти трябва апликейшън сървър.
Сега всичко ново, което правим го мислим и как да се тества. Т.е. архитектурата да позволява тестване на всички нива отделно като юнит тестове и като интеграционни тестове като няма такива зависимости.
2. При рефакторинг тестовете ти дават сигурност, че нищо не си счупил. Т.е. правиш рефакторинг на корем без да се притесняваш. И това подобрява кода/архитектурата неимоверно много. До сега никога не съм виждал архитектура, която да не се променя. Обикновено идват нови изисквания или пък виждаш, че архитектурата не е толкова добра колкото сме си мислели в началото. Имаш ли тестове можеш да променяш без да се притесняваш. Нямаш ли тестове почваш да кърпиш отстрани, да добавяш код, да дублираш код с малки промени, да се притесняваш да пипаш стария код, щото не знаеш какво можеш да счупиш.
3. Тестване на всички нива, на които можеш да тестваш.
Преди 2-3 седмици бях пуснал една тема за тестване на сървлети. Те такова тестване нямахме още и аз не бях правил, та реших да направя сега. Споделям опит и какво направихме по темата.
Значи до момента имаме пълно разделение на логиката от презентацията. ПОЖО класове + персистансе. За тях имаме юнит тестове тестващи логиката, доколкото я има (щото няма много логика) и персистансето (всъщност това е по-важно за тестване).
После другото ниво са сървлетите, които изпълняват няколко задачи: секюрити; диспетчинг; инициализиране на обекти като се четат параметри от рекюеста; викане на някакви методи на тези обекти било за запис, търсене или каквото друго трябва; пъхане на разни неща из сесията, които ще трябват при следваща заявка от страна на браузъра и неща от сорта.
Презентационното ниво е JSP. Сървлета прави каквото прави и пъха разни неща в контекста на рекюеста и после вика някакво JSP, което показва нещата на екрана. Стандартна (даже малко остаряла) архитектура. :)
Та идеята ми беше как да се хвани логиката в сървлетите. И ви питах за опит. Та мислих, мислих и какво измислих.
Значи редиректа към JSP минава през едно място (един метод). Сървлетите си викат едно методче с параметър името на JSP страницата и метода вика JSP-то. Перфектно място да се "хванат" нещата.
Та този метод в тестов режим вместо да вика JSP-то сериализира рекюеста в ХМЛ и го праща към браузъра. Това включва: всички параметри изпратени от браузъра; хедърите на рекюеста; атрибутите на рекюест контекста; атрибутите на сесията; и още каквото може да се докопа.
Та всичко това се праща от сървъра в ХМЛ формат към клиента.
От страната на клиента ХМЛ се десериализира обратно в съответните обекти и с JUnit правя съответните assert-и да видя състоянието на обектите и дали изобщо го има.
Ползвам XStream за ХМЛ сериализация и HttpClient от Апаче за клиент. Това последното поддържа кукита и съответно автоматично си поддържа сесията.
Понаписах около 100 реда код да направя нещата по-лесни за викане. HttpClient има супер флексибъл архитектура и може да прави всичко, ама аз искам с един метод да си сетна параметрите, а не да инициализирам 20 неща за да сетна един параметър. Та си понаписах малко код около XStream и HttpClient.
Недостатъците са, че е хоме майд солюшън. Обаче мен ме кефи в няколко аспекта:
1. Кодът се изпълнява както в продакшън без никакви допълнения.
2. Тестовият код симулира браузър.
3. Получавам обектите в сесията и рекюеста. Мога да ги контролирам по бройка и размер. Мога да следя във всеки един момент какви боклуци има в сесията и да ги разкарвам когато не ми трябват. Т.е. мога да гледам ако съм вкарал нещо повече в сесията или в рекюеста. Така се намалява използваната памет.
4. Това симулира интеграционен тест на всички нива без последното (презентационното).
5. Много ясно, точно и конкретно се тества логиката, която я има в сървлетите. Значи сървлета получава такива и такива параметри. На базата на тях очаквам в сесията да имам този и този обект, а в рекюест контекста този и онзи обект. Просто перфектно - все едно тестваш публични методи на класове, а те колко прайвът методи викат си е тяхна работа.
Това се доближава до Кактус на Апаче за тестване на J2EE код, ама Кактуса ми се стори прекалено сложен и реших да ходя с хоме мейд солюшън. :)
Това не заменя тестването със Селениум или нещо друго в браузъра. Защото може да има грешки в JSP (JS) кода, които няма как да се хванат тук.
Сега обмислям идеята да пусна 2 клиента, които да са синхронизирани и да тестват логиката по едновременно обновяване на един и същ обект.
|