Článek obsahuje popis řešení efektivní správy ASP.NET PageState. Zabývá se problémy, jako je např. uložení PageState na serveru a šifrování. Pro lepší pochopení uveřejňuji okomentované zdrojové soubory ke stažení.
V rámci svého webu jsem vytvořil nestandardní, ale velmi efektivní systém, který se stará o ukládání a načítání pagestate. Předně bych rád zmínil, že se nejedná o návod, ale spíš o popis řešení. V projektu jsou řešeny tyto problémy: ukládání identifikátoru do původního skrytého pole, automatické mazání starších záznamů, šifrování pagestate a samozřejmě jeho ukládání různými způsoby na server. V závěru vám nabídnu celý projekt s podrobně okomentovanými zdroji ke stažení a na případné dotazy rád odpovím.
Základ
Základem celého systému jsou třídy HiddenFieldPageStatePersister a PageStateManager. Obě třídy v rozporu s vaším očekáváním dědí ze standardní třídy System.Web.UI.HiddenFieldPageStatePersister, ale první z nich ke standardnímu způsobu ukládání přidává pouze šifrování s pomocí šifry Rijndael, a proto se jí nebudu věnovat. Šifrování zajišťuje statická třída, kterou používám už dlouhou dobu a funguje velice spolehlivě – nejsem jejím autorem a bohužel si nevzpomínám na její původ. Druhá třída se stará o kompletní správu pagestate, jeho serverové ukládání, načítání i odstranění. Nejdůležitější jsou přepsané metody Load a Save, ve kterých se používá tzv. fiktivní pagestate. Celé to spočívá v tom, že pagestate uložíte na server a základní třídě podstrčíte identifikátor, ta ho uloží do skrytého pole. Třída také obsahuje metodu, která v případě potřeby odstraní přebytečný záznam s pagestate.
Uchovávání na serveru
O samotné uchovávání na serveru se stará nějaký persister, který implementuje rozhraní IPageStatePersister, které definuje metody pro uložení, načtení a odstranění pagestate na serveru. K dispozici jsou persistery pro souborový systém, SQL databázi a session. Další persistery je možné poměrně snadno začlenit do projektu, a nebo ho můžete přiřadit přes konfigurační soubor – jako hodnotu atributu Persister uveďte zápis typ,assembly.
Cache
Poslední podstatnou částí je třída PageStateCahe, která implementuje timeout pro záznamy uložené na serveru. Dvanáct hodin po vytvoření záznamu dojde k vyvolání události, při které dojde k zavolání metody persisteru, která odstraní pagestate. Ke kontrole dochází každou minutu.
Konfigurace
O deklarativní konfiguraci se stará třída SectionHandler, která, jak už z názvu vyplývá, implementuje handler pro vlastní sekci v konfiguračním souboru web.config. Handler musíte připojit v části configSections.
<?xml version="1.0"?>
<configuration>
<!-- nastavení aplikace -->
<configSections>
<!-- konfigurace sekcí -->
<sectionGroup name="Programujte">
<!-- přiřazení handleru k sekci -->
<section name="PageStateSettings" type="Programujte.PageState.SectionHandler, PageState" />
</sectionGroup>
</configSections>
<!-- řetězce pro připojení k DB -->
<connectionStrings>
<add name="ConnectionString" connectionString="řetězec pro připojení"/>
</connectionStrings>
<!-- skupina sekci Programujte -->
<Programujte>
<!-- nastavení page adaptéru, který se stará o alternativní ukládání pagestate -->
<PageStateSettings CacheTimeOut="720" ConnectionStringName="ConnectionString" Enabled="true" Encryption="true" FolderPath="~\pagestate" Persister="SQL" IDColumnName="pagestateID" StateColumnName="pagestate" TableName="pagestate">
<!-- soubory, ve kterých bude uplatněn standardní postup uložení pagestate -->
<ExcludedFiles>
<!-- není defaultní -->
<add path="~\*.aspx" />
<remove path="~\*.aspx" />
</ExcludedFiles>
</PageStateSettings>
</Programujte>
</configuration>
Následující tabulka popisuje význam atributů a podsekcí sekce PageStateSettings. Výchozí hodnoty jsou zvýrazněné tučně.
Atribut / podsekce | Možné hodnoty | Význam |
CacheTimeOut | Libovolné číslo (720). | Životnost záznamů v minutách. |
ConnectionStringName | Libovolný řetězec (ConnectionString). | Název jednoho z řetězců v sekci connectionStrings. |
Enabled | True nebo false. | Rychlé vypnutí nebo zapnutí správy pagestate. |
Encryption | True nebo false. | Rychlé vypnutí nebo zapnutí šifrování pagestate. |
FolderPatch | Libovolná cesta ~\* (~\pagestate). | Cesta, kam mohou být uloženy soubory s pagestate. |
Persister | SQL, File, Session, HiddenField nebo zápis typ,assembly. | Udává, jaký persister se má použít. |
IDColumnName | Libovolný řetězec (pagestateID). | Název sloupce, kam se ukládá identifikátor. |
StateColumnName | Libovolný řetězec (pagestate). | Název sloupce, kam se ukládá pagestate. |
TableName | Libovolný řetězec (pagestate). | Název databázové tabulky, která obsahuje výše zmíněné sloupce. |
ExcludedFiles | <add path="~\*.aspx" /> <remove path="~\*.aspx" /> |
Kolekce souborů, kde bude uplatněn standardní postup uložení pagestate. |
Použití na webu
Pro použití na webu slouží třída PageAdapter, kterou ke svému projektu přiřadíte s pomocí souboru .browser. Soubor s následujícím obsahem uložte do složky App_Browsers ve vašem webovém projektu.
<browsers>
<browser refID="Default" >
<controlAdapters>
<adapter controlType="System.Web.UI.Page" adapterType="Programujte.PageState.PageAdapter" />
</controlAdapters>
</browser>
</browsers>
Závěr
Článek je určen pro pokročilé vývojaře, ale doufám, že jsem všem dostatečně vysvětlil, o co vlastně jde. Další podrobnosti se dovíte v kompletních a okomentovaných zdrojových souborech, které si můžete stáhnout, libovolně upravit a šířit dál. K provozu potřebujete ASP.NET server s podporou .NET 2.0+, pro .NET 1.x nebo MONO je nutné provést drobné úpravy. Na projektu je určitě hodně co zlepšovat, ale to už nechám na vás.