Nem szeretnél szívni a webalkalmazásoddal?

Gyakran előfordul - főleg a PHPs világban - hogy kezdő vagy haladó fejlesztők belevágnak olyan projektekbe, amely messze meghaladja a jelenlegi képességeiket. Ez természetesen nem hiba, hiszen aki nem mer nagyon álmodni, az sehova sem jut. Azonban ha már közhelyeket puffogtatunk ide illik egy másik is: Inkább tanulj más hibájából mint a sajátodból.

A mi kis szakmánkban ez nem is olyan bonyolult. Rá kell szánni az időt hogy az ember szakirodalmat, blogokat olvasson, beszélgessen, levelezzen más szakmabeliekkel és tanuljon. Ez persze nem fog megkímélni a teljes szíváshalmaztól, de azért sokat könnyít a dolgokon. Amikor valaki tapasztalatlanul belevág egy nagyobb webalkalmazásba, akkor jó esetben hall pl. az MVC-ről, nagyon jó esetben pl a Tier2 architektúráról, de pl az AJAXról 100% biztos. Nagy valószínüséggel azonban nem érti hogy miért van erre/ezekre szükség (vagy neki szüksége)?

Az MVC (és a vele kéz-a-kézben járó objektumorientált programozás) véleményem szerint azért ennyire népszerű és elterjedt, mert lehetővé teszi a specializációt a különböző rétegekben. Ugye az MVC-t a Model-View-Controller szavakból képezzük, tehát ezekre specializálódnak a fejlesztők. Például a View réteg elkészítését rábízhatjuk egy kliens oldali programozóra aki HTML-ben és JavaScript-ben jártas, de a szerver oldali nyelvben nem jellemzően. A Controller programozását rábízhatjuk junior programozóinkra. A Model réteg kialakítását pedig a tapasztalt senior programozóinkra.

Azonban a fenti freelancer forgatókönyv esetén nem jellemző az ilyen specializáció hiszen majdnem mindent az adott fejlesztő készít. Akkor tehát hogyan építsünk fel az alkalmazásunkat? Erre természetesen nincs egyöntetű válasz, ám érdemes végiggondolni hogy milyen lehetőségeink vannak és összeállítani a projektnek megfelelő architektúrát.

Az MVC alapötlete egy ilyen one-man-shownál is hasznos lehet, hiszen így a funkcionalitásainkat jól körülzárt kis és kezelhető formába önthetjük. Miért szeretnénk az összetartozó funkciókat közel egymáshoz elhelyezni és elhatárolni a nem annyira releváns kódoktól? Egyszerű: Az emberi agy képtelen egy bizonyos komplexitás és információmennyiség felett átlátni azt amivel foglalkozik. Tehát ha kicsi kódokat kell menedzselnünk, könnyebb lesz koncentrálni, kevesebb stressz ér minket. A kevesebb stressz pedig jó, remélem ezzel senki nem vitatkozik. ;)

Nem utolsósorban azt is nyereségként számolhatjuk el, hogy másoknak is könnyebb lesz a kódjainkat értelmezni, hiszen egy már látott és ismert mintára épülő kódokat kell megismernie, így gyorsabban haladhat és kevesebb kérdés merül fel. Ez jól jöhet az eredeti fejlesztőnek is.

Oké, meggyőződtünk róla hogy ez az MVC dolog jó, de egész pontosan mit jelent? Hogyan dolgozzunk MVC-ben hogy valóban könnyítsen a munkánkon és ne akadályozzon. Biztosan van mindenki ismeretségi körében olyan fejlesztő aki csak azért "MVC-zik" mert divatos vagy ezt várják el tőle. Próbálja használni ám több gondot okoz neki, mint amennyit nyer az egésszel. A kulcsszavak szerintem a tagolás, a KISS (Keep It Simple Stupid) és a DRY(Don't Repeat Yourself).

A legnagyobb hiba, amit látni szoktam hogy a Controllert túlterhelik felelősséggel a felhasználók. Bevallom sokáig én is így csináltam ameddig bele nem ütköztem bizonyos problémákba. Addig minden szép és jó volt, amíg csak magam dolgoztam az adott projekten, ám eljött az a pillanat, amikor ez megváltozott. Az egyik ilyen igény volt a unit tesztelés és a teszt alapú fejlesztés. Hamarosan rádöbbentem hogy az üzleti logikát a controllerre bízva bizony nem tudom tesztelni azt. A controller többek között feldolgozza a beérkező paramétereket, validál, adatokat olvas be a modellből ésatöbbi. Az üzleti logika csak egy kis szelete volt a munkájának. A megoldás az lett, hogy a Model rétegben bevezetésre került a rétegezés. Készítettem két réteget a Modellen belül is. Az egyik a business vagy domain logic réteg, a másik a data retrieval réteg. A data retrieval réteg lehet például valamilyen ORM, Active Record komponens, Table Gateway vagy Data Mapper+DAO Repository, a lényeg hogy semmi más feladata ne legyen, csak az adatok adatbázisba mentése és azok betöltése. Ezzel a réteggel kommunikál majd a controller réteg un. Value Objecteken vagy másnéven DAO-kon keresztül. Ezeknek a DAO-knak semmi más feladatunk nincs mint hogy adatokat szállítsanak a két réteg között. Ők a szoftverünk vörösvérsejtjei.

A logic pedig, bár a model része, nem kommunikál közvetlenül a data retrieval réteggel. Az egyetlen feladata hogy az üzleti logikánkat megvalósítja. Pl. hogy egy banki szoftverben az átutalás business logic metódus két számlát és egy összeget paraméterül kapva azt átvezesse az egyik számláról a másikra majd visszatérjen a módosított számlákkal. És itt lép működésbe a Controller réteg és látja el a feladatát. Összeállítja a különböző komponensekből a működő alkalmazást. Tehát betölteti a két számlát a data retrieval layerrel, validáltatja a böngészőből érkezett átutalási összeget, majd meghívja az üzleti logikát a két már betöltött számlával, valamint a kapott összeggel. Ennek végeztével lekezeli az esetleges hibákat és visszatéréskor a két számlát átadja a data retrieval rétegnek hogy a módosításokat az kiírhassa adatbázisba. A harmadik lépésben pedig megjeleníthet egy view-t és tájékoztathatja a felhasználót hogy a tranzakció sikeresen vagy sikertelenül lezajlott.

Miért van erre a bontásra szükség? Nagyon egyszerű. Az üzleti logikánk semmit nem tud a külvilágról, semmilyen külső komponenshez nem kötődik, bármikor kivehető, kicserélhető körülötte a környezete. Ezzel egyrészt könnyűvé válik a unit tesztelés és hibakeresés (már tudod a szlogent: kevesebb stressz), de ami még fontosabb: újrafelhasználható lesz!

Azt persze be kell látni hogy erre nem minden pontján van szüksége az alkalmazásnak. Vannak olyan lekérdezések, amelyek indokolják a külön logic bevezetését és olyanok is amelyek nem. Példának okáért ha egy blogot fejlesztünk, akkor a világon semmi értelme logicot írni arra hogy az utolsó 10 bejegyzést megjelenítsük a böngészőben. De lássuk be: ezt elszúrni nehéz is :)

Hogyan lehet feloldani azt az

Hogyan lehet feloldani azt az ellentmondást, hogy a Controllerben lévő validálási műveleteket - melyek lényegében elágazási lehetőségek - NE az üzleti logika részének tekintsük? Úgy érzem, hogy az üzleti logikát sajnos nem lehet teljesen átpakolni a Model-be - még ha azt helyesen több rétegre is tagoljuk -, hanem a Controllerben is marad belőle... Mi a véleményed?

Válasz egy bejegyzésben

Írtam egy blogbejegyzést erről.

"Az MVC (és a vele

"Az MVC (és a vele kéz-a-kézben járó objektumorientált programozás) véleményem szerint azért ennyire népszerű és elterjedt, mert lehetővé teszi a specializációt a különböző rétegekben. Ugye az MVC-t a Model-View-Controller szavakból képezzük, tehát ezekre specializálódnak a fejlesztők. Például a View réteg elkészítését rábízhatjuk egy kliens oldali programozóra aki HTML-ben és JavaScript-ben jártas, de a szerver oldali nyelvben nem jellemzően."
Thanks for the information