Warning: Creating default object from empty value in /chroot/home/zerotohe/zerotohero.hu/html/wp-content/themes/salient/nectar/redux-framework/ReduxCore/inc/class.redux_filesystem.php on line 29
Refactoring bevezető | zeroToHero

Refactoring bevezető

Helló!

Jelentem, ezen résszel elindul a refactoring-ról szóló blog sorozatunk!

Szóval miért van a refactoring-ra szükséged?

Ahhoz, hogy ezt meg tudjam neked válaszolni, meg kell értened a szituációt, ami az igényt szüli:
Most képzeld el, hogy egy 5-7 fős fejlesztői csapat tagja vagy. Körülbelül mindannyian ugyan azon a szinten értetek a fejlesztéshez, ugyan olyan jól értitek a programozási nyelvet. (Jelen esetben mondjuk a Java-t)
A csapattagok mind nagyon elhivatottak, nagyon szeretnének már végre alkotni valamit. Viszont egyikőtök sem dolgozott még komolyan csapatban egy nagy projekten. Mindenki írt már spagetti kódot, amire aztán soha többet nem kellett visszanézni.

A csapat megkapja az első feladatát és mindenki beleveti magát a munkába.
Az első hét még rendben telik, mindenki a saját kis kódrészletén ügyködik, mindenki a saját szigetén fejleszt, öröm és boldogság van. :)
A második héten azonban el kell kezdeni egymás kódját használni, mert ugye minden rendes rendszerben, így ebben is, a modulok kommunikációja adja a teljes működést.
Ekkor kell szembesülnöd először azzal, hogy a Pista konstruktorba írja a fél rendszert, a Béla képtelen formázni, a Jóska meg csak statikus metódusokat használ…
Ekkor még türelmes vagy, megpróbálod megérteni a kódjaikat, még ha annyira kusza is mintha csak random karaktereket ütögettek volna össze-vissza. Oké, már-már kezded érteni a kusza kódot. No, de ekkor jön a kérdés, hogy a Pista által a konstruktorba rakott listenerből indított szálban lévő névtelen osztály kódját Te hogy fogod meghívni?
A válasz természetesen a sehogy, át kell írnod a kódot, vagy oda kell menned Pistához, hogy szólj neki, hogy drága Pistukám, ez így nem lesz az igazi. :)
A második héten még megy is ez a dolog, mert Pista elfogadja az álláspontod, bár mond valamit arról, hogy szerinte azt a kódot neked nem is kéne hívni, de nem aggodalmaskodik annyit.

Viszont a harmadik héten… Pista visszaadja a kölcsön kenyeret! :) Jön és most ő köt bele a kódodba, mert minden metódusod package láthatóságú, ő meg ugye másik csomagon dolgozik, és így nem tud ráhívni a dolgaidra. Meg egyébként is amit írtál az „úgy vacak ahogy van”, mert minden metódusod int-el tér vissza – mondja ezt ő, akinél az osztályban csak konstruktor van, de az biza 2000 soros.

A negyedik héten ezekbe a kis vitákba bekapcsolódnak a többiek is. Az ötödik héten az első demókor semmi nem működik és ekkor elszabadul a pokol.
Mindenki kijelenti a csapatban, hogy a másik hülye és egyébként sem lehet más fejlesztőkkel együtt dolgozni…

Ez a kis elnagyolt történet azért kellett, mert ha még nem dolgoztál csapatban, akkor az első tapasztalat hasonló lesz, főleg, ha nincs köztetek egy-két tapasztalt róka, aki megmondja, hogy merre van az előre.

Mitől vagyok benne biztos, hogy ez hasonlóan lesz?

Mert én is tapasztaltam ezt. Sőt az első pár tapasztalat majdnem mind ilyen volt.
A dolgon az enyhített, hogy volt egy sokat látott mágus a csapatban, aki rettentő gyorsan tanult meg mindenfélét.

Az első komoly projektemen, amin közösen dolgoztam pár másik fejlesztővel tapasztaltam először, mennyire nehéz is a csapatban fejlesztés. Mindenkinek más stílusú kódja született.
Rettentő sok kódolási hibát követtem el én is, de akkoriban meg voltam győződve róla, hogy bizony én jól kódolok, csak mások nem értik. :)

Ebben a fejlesztésben kezdett el foglalkozni az említett mágusunk azzal, hogy a kódokat széppé varázsolja. Általában nem szólt semmit, ha azt látta rossz kódot írtam, csak pusztán másnap reggelre ő átírta úgy, hogy jó legyen, majd leült mellém, és elmesélte, hogy mit mire írt át, és hogy ez nekem mitől lesz jobb így.

Eleinte az egóm nehezen viselte ezeket a módosításokat, de nem volt pofám rászólni, hiszen egész este ezen dolgozott és végülis működik, bár így már nem értem a kódot, de működik. :)

Aztán, ahogy ez egyre sűrűbben történt, elkezdtem rájönni, hogy mennyivel jobb az ő átalakított kódja, értelmesebb, logikusabb felépítésű. Később elkezdtem „ellesni”, hogy hogyan is csinálja ezeket az átalakításokat és észrevettem, hogy amit az én kódommal csinál, azt csinálja a sajátjával is csak épp fejlesztés közben.

Ezek után a tapasztalatok után elkezdtem utána olvasni a refactoring-nak, a mintáknak, a kód szagoknak (code smells), a bevált módszereknek, és hogy hogyan lehet ezt hatékonyan csinálni.

Később más projekteken én annyiban módosítottam „a mágusunk” módszerét, hogy rögtön a módosítások után próbáltam elmondani ezeket a kód szerzőjének és próbáltam rávenni a projektben dolgozókat, hogy ők is refactoráljanak.

A történet tanulságai:

  1. Amikor még nem dolgoztál csapatban, akkor szinte biztos lehetsz benne, hogy rossz kódot írsz. Ez nem a Te hibád, nem azért írsz rossz kódot, mert figyelmetlen vagy buta vagy, hanem mert egyszerűen nincs rá szükséged, hogy szép / tiszta kódot írj. Rajtad kívül senki nem olvassa, Te meg elég nagy valséggel érteni fogod.
  2. Elsőre más kódját megérteni nehéz. Nagyon sok gyakorlás kell hozzá. A sokféle stílus és az eltérő kódolási szokások pedig még nehezebbé teszik a dolgot.
  3. Mások kódjai is tele vannak randa dolgokkal és ezekkel ritkán lehet együtt élni.
  4. Meg lehet tanulni, hogyan lehet átalakítani a kódokat, hogy jók legyenek, és el lehet kezdeni rendet rakni mások után is, de muszáj elmondani nekik, hogy mit miért csináltál. Ha elmondod a hogyant, akkor az még jobb.

Szóval a refactoring-nak és annak, hogy ezt megtanulod sok áldásos hatása van. Először is tanulsz egy kicsit kódot olvasni. Minden bejegyzésben kódokkal fogom illusztrálni, hogy mi is történik. Másodszor megtanulod észrevenni azokat a típus hibákat, amik rosszá teszik a kódot (code smells) és megtanulod, hogy milyen válaszokat lehet ezekre adni, hogyan lehet megszüntetni ezeket. Arra törekszem majd minden posztban, hogy a code smell-től induljunk, és a megoldás a jól begyakorolható refactoring minta legyen.

Oké, mielőtt azonban beleugranánk a dolgokba előbb tisztázzunk pár fogalmat. Csak röviden.

 

Mi is az a refactoring?

A fejlesztett szoftveren végzett belső strukturális változtatás, amit annak érdekében végzünk, hogy a forráskód könnyebben értelmezhető és „olcsóbban” változtatható legyen, a felhasználó által érzékelhető viselkedésbeli változások nélkül.

Huh, ez így egy szuszra komoly definíció. Szóval tördeljük:

  • Belső strukturális változás: Tehát például egy-egy modul interfészeinek érintése nélkül kell változtatnunk. A fontos és megtervezett kapcsolódási pontokat csak akkor szabad változtatnunk, ha azt a többi fejlesztővel egyeztettük, különben kihúzzuk a szőnyeget mások alól, amit nem fognak értékelni. :)
  • Annak érdekében, hogy a forráskód könnyebben értelmezhető … legyen: Ugye a fenti mese jól példázza, hogy csapatban mennyire fontos, hogy értsük egymás kódját. De ugyan így igaz ez a saját kód olvashatóságára is. Van, hogy egy hét távlatából már nem emlékszünk a saját kódunkra, és ilyenkor nekünk is el kell olvasni azt. (Arról nem is beszélve, hogy a különböző alkohol tartalmú italok fogyasztása könnyen csökkentheti is ezt az időtartamot :) ) Tehát a kódunknak olvashatónak kell lennie, mások és magunk számára is. Az ember arra lett tervezve, hogy mintákat ismerjen fel és asszociáljon, tehát a kódod annál jobb, minél könnyebben felismerhetőek benne ezek a minták. Tehát ki kell alakuljon egy közös minta halmaz, amit a többi fejlesztő is ért, így könnyebben olvasható lesz egymás számára a kód. Ezek a minták az úgynevezett tervezési minták, ezekre az egyes részekben, ahol szükség lesz rá, ki fogok térni, de részletesen nem fejtem ki őket, mert van hozzá egy nagyon jó könyv, amiből megtanulhatóak: http://www.amazon.com/exec/obidos/ASIN/0201633612
  • Annak érdekében, hogy a forráskód … „olcsóbban” változtatható legyen: Soha a szoftverfejlesztés történelmében, egyetlen egyszer sem volt még olyan, hogy előre definiált pontos elképzelések mentén pontosan úgy, és az a szoftver fejlődjön ki, amit terveztek. Valószínűleg hallottál már a vízesés modellről, amiben előre megtervezünk mindent, minden részletet, majd egyszerűen megírjuk a kódot, és kész. Erre korábban azt mondtam, hogy ez egy vágyálom, de tudod mit, nem, ez egy RÉMÁLOM. Miért? Mert ha ilyen lenne, akkor az megölné az összes kreativitást az életünkből, gyári munkásokká változnánk. Szerencsére a világ helyesen működik, így olyan nincs, hogy nem kell változtatni valamin, nem kell módosítani a kódunkon. Ehhez azonban az kell, hogy a kód olyan formában legyen, amit könnyű változtatni. A helyes refactoring-al ezt is el tudod érni.
  • A felhasználó által érzékelhető viselkedésbeli változások nélkül: Ez egyszerű, olyannak kell lennie a változtatásnak, hogy abból a felhasználó semmit ne vegyen észre. Ugye itt nem új funkciókat vezetünk be, nem bugokat javítunk, hanem egyszerűen azt, ami már eddig is működött ,alakítjuk át olyanra, hogy érthető, szép és könnyebben változtatható legyen. (Az, hogy hogyan tudod változtatni a kódot úgy, hogy az garantáltan ne okozzon változást a felhasználó felé, az egy nagyon érdekes kérdés, erről szoktam beszélni a tantermi oktatásokon, viszont sajnos ebbe a sorozatba nem fér majd bele, hogy ezzel is foglalkozzak. Maradjunk annyiban, hogy ha a mintáknak megfelelően refactorálsz, akkor olyan nagy baj nem lehet. De ha biztosra akarsz menni, akkor gyere le a következő oktatásra és ott megtudod, hogyan mehetsz biztosra. :) )

 

Honnan tudom, hogy egy kódot refactorozni kell?

Ha azt érzed róla, hogy bűzlik. :) Ehhez az érzékelési készséghez azt kell megtanulni, hogy milyen kód szagok (code smell) vannak. A code smell egy olyan tipikus hiba, amit a kód átolvasásakor észre tudsz venni, be tudod kategorizálni és tudod, hogy milyen refactoring tudja megszüntetni. Ennél jobban sajnos nem lehet definiálni, viszont azonnal meg fogod érteni a példákon keresztül.

Oké, ennyi bevezetés után szerintem már képben vagy, hogy miről is lesz szó, és valószínűleg szeretnél végre beleugrani a közepébe, pont ezért még a héten fel is kerül az első része ennek a sorozatnak. Szóval türelem, hamarosan jön a folytatás, amiben már kód is lesz. :)