MVC 5, a teljesítmény javítása vezérlőkkel

ASP.NET --- ASP.NET MVC 5 --- A teljesítmény javítása vezérlők segítségével

Az MVC Framework két speciális típusú vezérlőt kínál, amelyek javíthatják az MVC webes alkalmazások teljesítményét. Mint minden teljesítményoptimalizáláshoz, az ilyen vezérlőkkel való együttműködés feláldozza az egyszerű használatát, vagy korlátozott funkcionalitással foglalkozik. Az alábbi szakaszok bemutatják mindkét típusú vezérlők használatát, és megmagyarázzák a hozzájuk kapcsolódó előnyöket és hátrányokat.

Olyan vezérlők használata, amelyek nem támogatják a munkamenet állapotát

Alapértelmezés szerint a vezérlők olyan munkamenetállapotot tartanak fenn, amely az adatok közötti értékek tárolására használható a kérések között, megkönnyítve az MVC programozók számára a problémák megoldását. A munkamenet állapotának létrehozása és fenntartása összetett folyamat. Az adatokat tárolni és letölteni kell, és a munkameneteket maguknak kell kezelni, hogy biztosítsák az elavulás megfelelő szabályait. A munkamenet adatok memóriát használnak a kiszolgálón vagy egy másik tárolóban, és az adatszinkronizálás szükségessége több webszerver között megnehezíti az alkalmazás több kiszolgálón történő futtatását (nagy alkalmazások esetén).

A munkamenet állapotának egyszerűsítése érdekében az ASP.NET egyszerre csak egy kérést dolgoz fel egy adott munkamenethez. Ha az ügyfél sok átfedési kérelmet bocsát ki, akkor a kiszolgáló sorba állítja és feldolgozza azokat egymás után. Ennek a megközelítésnek az az előnye, hogy nem kell aggódnia, hogy ugyanazokat az adatokat egyszerre több kérelemmel módosítja. A hátrány az, hogy képtelenek elérni a lekérdezések szükséges átvitelt.

Nem mindegyik vezérlőnek szüksége van egy munkamenet-állapotra. Ilyen esetekben az alkalmazás teljesítménye javítható a munkamenet állapotának fenntartásával kapcsolatos munkák elkerülésével. Ez olyan vezérlőkön keresztül történik, amelyek nem támogatják a munkamenet állapotát. Ezek nagyon hasonlítanak a hagyományos vezérlőkhöz, de két kivételtől eltekintve: az MVC keretrendszer nem tölti be és nem tárolja a munkamenet állapotát, amikor az ilyen vezérlőket a kérés feldolgozására használják, és az átfedő kéréseket egyszerre lehet kezelni.

Az ülés állapotának kezelése egy speciális IControllerFactory gyárban

Amikor a vezérlő üzemét az előző cikkek egyikében vitattuk meg, megmutattuk, hogy az IControllerFactory interfész GetControllerSessionBehavior () nevű eljárást tartalmaz. amely visszaadja a SessionStateBehavior felsorolás értékét. Ez a felsorolás négy olyan értéket tartalmaz, amelyek szabályozzák a munkamenet állapotát a vezérlőben:

A SessionStateBehavior felsorolás értékei

A munkamenet állapota teljesen le van tiltva

Az IControllerFactory interfészet megvalósító vezérlőegység közvetlenül beállítja a vezérlők számára a munkamenet állapotát, visszatérve a SessionStateBehavior értékeket a GetControllerSessionBehavior () metódustól. Ez a módszer a RequestContext objektum paramétereit és a vezérlő nevét tartalmazó karakterláncot veszi figyelembe. A fenti táblázatban leírt négy érték bármelyikét visszaadhatja, és a különböző vezérlők különböző értékeket adhatnak vissza.

A következő példa a GetControllerSessionBehavior () módszer módosított végrehajtását mutatja be a korábban létrehozott CustomControllerFactory osztályból:

A munkamenet állapotának kezelése az DefaultControllerFactory segítségével

Ha a beépített vezérlő gyárat használja, a SessionState attribútumot az egyes vezérlőkategóriákra alkalmazva vezérelheti a szabályozó munkamenet állapotát, amint az az alábbi példában látható, ahol létrehozták a FastController nevű új vezérlőt:

A SessionState attribútum a vezérlõosztályra kerül alkalmazásra, és hatással van a vezérlõ összes cselekvési módjára. Az attribútum által elfogadott egyetlen paraméter a SessionStateBehavior felsorolás értéke. A fenti példában a munkamenet állapota teljesen le van tiltva. Ez azt jelenti, hogy ha megpróbálja beállítani a munkamenet értékét a vezérlőben, például:

vagy olvasd el a nézetet:

az MVC keretrendszer kivételt fog adni, amikor a műveletet hívják, vagy a nézet megjelenik. Ha a munkamenet állapota letiltva van, a HttpContext.Session tulajdonság null értéket ad vissza.

Aszinkron vezérlők használata

Az MVC keretrendszer alapjául az ASP.NET támogatja a .NET szálösszeget. amelyet az ügyfélkérések feldolgozására használnak. Ezt a csoportot a munkatársak csoportjának nevezzük, és mindegyik szál, vagyis a munkavállaló szál. Amikor egy kérés érkezik, a munkanevet beszedik a medencéből és megkezdi a kérés feldolgozását. A kérelem feldolgozása után a munkafolyamat visszatért a medencébe, így érkezéskor új kérések feldolgozására lesz elérhető.

Az ASP.NET alkalmazásokban egy szálösszeköttetés alkalmazása két előnyt jelent:

A munkafolyamatok újrafelhasználásával elkerülheti az új munkafolyamat létrehozásával járó általános költségeket minden egyes kérelem feldolgozásakor.

A rendelkezésre álló munkafolyamatok meghatározott számú jelenléte miatt elkerülhető, hogy az egyidejűleg feldolgozott kérelmek száma meghaladja a szerver képességeit.

A munkafolyamat-pool jobban működik, ha a kérések rövid időn belül feldolgozhatók. Ez a helyzet a legtöbb MVC alkalmazás esetében jellemző. Ha azonban vannak olyan műveletek, amelyek más szerverektől függenek, és hosszú idő telik el, akkor kiderülhet, hogy minden munkafolyamat elfoglalt, és más rendszerek miatt leáll.

A szerver képes több munkát elvégezni (elvégre nagyon kevés forrás szükséges a várakozás alatt), de mivel minden munkafolyamat csatlakoztatva van, a bejövő kérelmek várakoznak. Van egy meglehetősen furcsa helyzet, amikor az alkalmazás lebeg, míg a szerver többnyire üresjáratban van.

Ezen a ponton előfordulhat, hogy az adott alkalmazáshoz pontosan konfigurált munkafolyamat-pool saját megvalósításának ötlete áll. Ne tegye ezt semmilyen módon! A párhuzamos kód írása meglehetősen egyszerű. A működő párhuzamos kódok írása azonban nehéz, különösen a kezdő párhuzamos programozásnál. Javasoljuk, hogy ragaszkodjon a szabványos medencéhez. Ha párhuzamos programozással rendelkezik tapasztalatokkal, akkor tudnia kell, hogy az előnyök nagyon kicsiek lesznek, mint az új témacsoport kódolásához és teszteléséhez.

Tehát a probléma megoldása egy aszinkron vezérlő használata. Ez növeli az alkalmazás általános teljesítményét, de nem nyújt semmilyen előnyt az aszinkron műveletek végrehajtásához.

Az aszinkron vezérlők csak olyan műveletekhez használhatók, amelyek I / O vagy hálózatot tartalmaznak, de nem azok, amelyeket a CPU intenzíven használja. Az aszinkron vezérlők által megoldani kívánt probléma a medence modell és a feldolgozás alatt álló kérelmek típusának eltéréseivel függ össze. A pool célja annak biztosítása, hogy minden egyes kérelem megfelelő számú szerverforrást kapjon, de végül olyan munkafolyamatokból áll, amelyek nem tesznek semmit. Ha további háttéráramlást alkalmaz a CPU-val intenzív tevékenységek számára, a szerver erőforrásai túl sok egyidejű kérésre lesznek elfogyasztva.

Ez a szakasz feltételezi, hogy ismeri a feladat párhuzamos könyvtárat (TPL). A könyvtárat a Szálak és fájlok részben ismertetjük. Az aszinkron webes űrlap létrehozása az ASP.NET webes űrlapokon is látható.

Példaképzés

Mielőtt elkezdenénk magyarázni az aszinkron vezérlőket, bemutatunk egy példát egy olyan problémára, amelyre szánják őket. Az alábbi példa egy hagyományos RemoteData nevű szinkronvezérlő kódját mutatja, amelyet a mintaprojekthez adtunk:

Ez a vezérlő tartalmaz egy Data () nevű műveleti eljárást, amely létrehozza a RemoteService modell osztály egy példányát, és ráhívja a GetRemoteData () metódust. Ez a módszer példa egy olyan műveletre, amely sok időt igényel, de kevés CPU-t használ. Az alábbi példa bemutatja a RemoteService.cs fájlban a Models mappában meghatározott RemoteService osztályt:

Valójában a GetRemoteData () metódus itt szimulálódik. A valóságban ez a módszer lassú hálózati kapcsolaton keresztül képes összetett adatokat kivonni, de az egyszerűség kedvéért a Thread.Sleep () metódus két másodperces késleltetést emulált. Az utolsó kiegészítés az új nézet. Ehhez létrehozza a Views / RemoteData mappát, amelybe a Data.cshtml nézet fájlt a példában szereplő tartalommal látja el:

Miután elindította az alkalmazást, és a / RemoteData / Data nézet URL-jéhez navigált, a megfelelő műveletmódot hívják meg, létrehoz egy RemoteService objektumot, majd a GetRemoteData () metódust. Két másodperc elteltével (egy valós művelet végrehajtásának szimulálása után) a GetRemoteData () adatát visszaküldik, amelyet a megjelenítéshez továbbítanak:

MVC 5, a teljesítmény javítása vezérlőkkel

A probléma az, hogy a kérelem feldolgozását végző dolgozószál két másodpercig üresjáratban volt - nem tett semmi hasznosat, és nem állt rendelkezésre más kérések kezelésére, amíg várakozott.

Aszinkron vezérlő létrehozása

Az aszinkron vezérlő használatával a munkafolyamat szabaddá válik, és más kéréseket is képes kezelni. Ez nem akadályozza meg, hogy a felhasználó két másodperces interakcióba lépjen az alkalmazás felületével. A végén fiktív adatokat fognak kapni és feldolgozni. Vannak ügyféloldali technológiák (AJAX), amelyekkel ilyen kéréseket tehet a böngészőben, amely lehetővé teszi, hogy legalább tájékoztassa a felhasználót az adatgyűjtés folyamatáról, és lehetőséget biztosítson arra, hogy folytassa a munkát az alkalmazás egy másik részével.

Miután bemutatjuk a megoldandó problémát, lépjünk át egy aszinkron vezérlő létrehozásával. Az ilyen vezérlő kétféleképpen hozható létre. Az első a System.Web.Mvc.Async névtér IAsyncController felületének végrehajtása, ami az IController aszinkron egyenértékűje. Ezt a megközelítést nem bizonyítják, mert a .NET párhuzamos programozás fogalmainak részletes magyarázatára van szükség.

A figyelem továbbra is az MVC keretrendszerre fog összpontosítani, így a következő példa a második megközelítésre: az új kulcsszavak használata és az aszinkron egy hagyományos vezérlőben.

A .NET-keretrendszer korábbi verzióiban az aszinkron vezérlők létrehozása időigényes feladat volt, és megkövetelte, hogy a vezérlő egy különleges osztályból örököse, és minden műveletet két módszerre oszthasson. Az új kulcsszavak várják, és az async ezt a folyamatot sokkal könnyebbé teszi: létre kell hoznia egy új feladatobjektumot, és várnia kell az eredményre, amint az az alábbi példában látható:

Az aszinkron cselekvési módszerek létrehozásának régi módja továbbra is támogatott, bár az itt vizsgált megközelítés sokkal elegánsabb, ezért ajánlott használni. A régi megközelítés egyik eleme az, hogy lehetetlen alkalmazni a neveket az Async-vel (például IndexAsync ()) vagy befejezett (például IndexCompleted ()) nevű névtér-módszerekkel.

Tehát ebben a példában az akció módja refakturált, így most visszaadja a feladatot. az async és váró kulcsszavakat alkalmazzák, és a Feladat objektumot, amely felelős a GetRemoteData () módszer hívásáért.

Asynchronous módszerek használata a vezérlőben

Az aszinkron vezérlő az aszinkron módszerek alkalmazására is használható más alkalmazásokban. Tájékoztatási célból az aszinkron módszert hozzáadjuk a RemoteService osztályhoz, amint az az alábbi példában látható:

A GetRemoteDataAsync () metódus eredménye a Feladat-objektum, amely ugyanazt az üzenetet hozza létre, mint a szinkron módszert, amikor elkészült. Az alábbi példában láthatja, hogyan használják ezt az aszinkron módszert a RemoteData vezérlőhöz hozzáadott új akciómódszerben:

Amint láthatja, mindkét műveletmód ugyanazt az alapmintát követi, és a különbség csak akkor jelenik meg, ha a Feladat objektum létrejön. Bármely akciómód felhívása következtében a munkatábla nem lesz lekötve a GetRemoteData () hívás befejezéséig. Ez azt jelenti, hogy a szál elérhető más kérelmek kezelésére, ezáltal jelentősen javítva az MVC Framework alkalmazás teljesítménymutatóit.