Tisíc pohledů na TDD

TDD (Test-Driven Development) je hype. Každý opravdový vývojář dneska dělá “TDD”, a kdo ho nedělá, je začátečník nebo naopak patří do starého železa, to je snad nad slunce jasné. Jenže co je vlastně TDD? Je to něco přesně definovaného nebo se tímto pojmem vývojáři ohání jen proto, že je dneska cool?

hype

Texy.js

K zamyšlení v tomto článku mě přivedl projekt Texy.js, reimplementace Texy! v JavaScriptu od Aleše Roubíčka, který podle Alešových slov TDD používá. Byl jsem nadšený, když jsem se o projektu dozvěděl, protože jednak stojím o Texy.js samotné, a pak jsem taky chtěl konečně vidět, jak bude TDD vypadat na projektu, který je pro testování jak stvořený, a od vývojáře, který TDD dlouhodobě praktikuje a propaguje. Kód je navíc (zatím) jednoduchý a relativně přímočarý, takže se jedná o skutečně skvělý studijní materiál.

Jak jsem začal koukat na zdrojové kódy Texy.js, něco mě zarazilo (kromě neznámých obratů v JavaScriptu, detailů zpracování textu atd.). Takhle nějak vypadala naše GTalk konverzace s Alešem pár minut poté:

BB: Ty Texy.js neděláš pomocí TDD, viď?
AR: Samozřejmě že dělám, proč myslíš, že ne?

Proč jsem myslel, že ne? Protože v commitu 4dbb4e4 se objevilo jakési UTF-8 kódování a dekódování a tato změna přitom nebyla diktována žádným testem. Podle Alešových slov byl tento commit přidán omylem a měl jít ruku v ruce s commitem následujícím (7b496fc), který si údajně kódování UTF-8 vynucuje, ale zaprvé si to nemyslím (test lze uspokojit jednodušším způsobem než zavedením UTF-8 knihovny) a zadruhé mám spíš pocit, že ten pozdější commit 7b496fc jen fixuje test, který byl předtím napsaný špatně a po změně produkčního kódu padal (stringy v JavaScriptu jsou UTF-16 a test na zalamovací pomlčku ji z nějakého důvodu zapisoval v UTF-8). Až později Aleš na svém blogu vysvětlil, jaká byla motivace k některým obratům, a tam jsem si právě uvědomil, že každý pod TDD možná vidíme něco jiného.

Můj pohled na TDD

Například můj pohled je ten, že odlišujícím faktorem TDD a “prostého” test-first development je právě ten, že testy by v TDD měly posouvat produkční kód kupředu, měly by být jeho řídícím faktorem, hnací silou. Testy v TDD by IMO měly dávat tvar produkčnímu kódu a proto se taky TDD někdy (podle mého názoru správně) označuje za technika agilního designu.

Možná si ale různí lidé pod TDD představují různé věci nebo je to také o tom, že hodně záleží na konkrétním projektu. Pokud se vrátíme k Texy.js, tak veřejné API této knihovny je tak primitivní (jedna metoda process() se stringem na vstupu a jiným na výstupu), že tady o nějakém přínosu TDD na úrovni designu těžko může být řeč. (Naopak bychom mohli diskutovat o tom, co pro API znamená, že se kvůli testování musela zpřístupnit jinak interní metoda normalize(), ale zaprvé je to IMO OK a zadruhé by to bylo na jinou debatu.)

Jindy se zase paušálně říká, že TDD vede k “čistšímu kódu” (správnější je říkat k “čistému návrhu”, ale zůstaňme na okamžik u tohoto zjednodušení). Znovu na příkladu Texy.js, podle mého názoru jsou v kódu jak věci hezké, např. použití funkcí map / reduce pro aplikování filtrů, tak věci trochu kontroverzní, např. interní kódování do UTF-8 nebo použití regulárních výrazů na zpracování neregulárního jazyka. Souvisí nějak tyto věci s tím, jestli se kód psal stylem test-first, test-after, TDD, BDD nebo jakýmkoliv jiným? Podle mě ne.

Pragmatický přístup k vývoji

Jestli mě léta strávená s Flexem něco naučila, tak to, že se nikdy nic nedá hodnotit paušálně, a zatímco např. testy nepokrytý kód v .NETu znamená v agilních kruzích téměř smrtelný hřích, GUI ve Flexu se automatizovanými testy nepokrývá téměř nikdy a obecně se to považuje za racionálnější přístup, než se o to pokoušet. K řadě věcí tak přistupuji s otevřeným hledím a snažím se koukat, jaký konkrétní přístup by se hodil pro daný konkrétní problém.

Jak bych k vývoji Texy.js přistoupoval já?

  1. Rozhodně bych kód intenzivně testoval, jako Aleš. Dokážu si představit jen málo typů projektů, kde by se testy hodily víc než u konvertovátka textu nebo obecně čehokoliv.
  2. Patrně bych tomu neříkal TDD a dost možná bych se TDD ani nesnažil přiblížit.
  3. Ohledně interní implementace bych před samotným psaním produkčního kódu strávil dost času výzkumem. Zpracování gramatik je matematický problém, nepochybně důkladně prozkoumaný a “vyřešený”. Doufat, že přijdu s implementací blížící se té “optimální”, mi připadá nerealistické. Tak trochu NIH, mohu-li si popíchnout :)

Jak jsem už mnohokrát naznačil, nejde mi o nějakou polemiku s Texy.js. Aleš může mít různé motivace k psaní Texy.js způsobem, jakým to dělá, a lidi s jiným pohledem na TDD navíc můžou stoprocentně souhlasit. Je to ale IMO krásný příklad toho, že TDD pro jednoho nemusí vždy znamenat TDD pro druhého.

Nutné P.S. na závěr: Pohledů na TDD samozřejmě není tisíc, ale zní to líp než osm :)