HAVIT Knowledge Base

Vývoj webových aplikací, .NET, SQL, návrh
Welcome to HAVIT Knowledge Base Sign in | Join | Help
-
Home Články Forums Obrázky Soubory

ASP.NET

Vývoj webových aplikací ASP.NET

Co by měl každý vědět o ViewState

1) ViewState není odpovědný za zachování vlastních hodnot controlů mezi postbacky

ViewState není odpovědný za zachování hodnot (Value) TextBoxů, CheckBoxů, DropDownListů a jiných Web controlů mezi postbacky. Tyto hodnoty jsou uloženy normálně ve formulářových postback datech (POST/GET) a ASP.NET je nastaví v metodě LoadPostData() pro všechny prvky, které implementují rozhraní IPostBackDataHandler. Na to, aby nám mezi roundtripy zůstal text v TextBoxu tedy nepotřebujeme ViewState!!!

2) Na co tedy ViewState?

ViewState je vlastnost každého controlu zděděná od System.Web.UI.Control (má ji tedy i Page) a jeho základní funkčnost je založena ná následující implementaci vlastností:

public string NavigateUrl
{
   get
   {
      string text = (string) ViewState["NavigateUrl"];
      if (text != null)
         return text;
      else
         return string.Empty;
   }
   set
   {
      ViewState["NavigateUrl"] = value;
   }
}
Hodnoty vlastností (property) se tedy ukládají do a čtou z ViewState, veškeré jejich změny se promítají do ViewState.

3) ViewState je typu StateBag

ViewState je typu System.Web.UI.StateBag, která implementuje mj. IDictionary (slouží k ukládání párů klíč-hodnota) a interně používá HybridDictionary.
Důležitou metodou StateBagu je SaveViewState(), která odpovídá za uložení ViewState.
Celý fígl je v tom, že metoda SaveViewState() uloží jenom ty vlastnosti, které se změnily po zavolání metody TrackViewState().

4) Co se tedy ukládá při uložení ViewState?

Funkčnost ViewState je úzce spojena s life-cyclem stránky a okamžikem volání metody TrackViewState(). Ta je volána na konci události Init každého controlu, a tedy i stránky (pro zjištění, zda-li již byla volána, lze použít property IsTrackingViewState.
Změny properties provedené před koncem události Init každého controlu se tedy s ViewState neukládají, veškeré další změny až do volání metody SaveViewState() (v události SaveViewState) ano.

5) Jak tedy stránka/control s ViewState funguje?

Vezměme si krátký příklad:
<script runat="server">
   private void btnSubmit_Click(object sender, EventArgs e)
   {
      lblMessage.Text = "Goodbye, Everyone!";
   }
</script>
<asp:Label runat="server" ID="lblMessage" Font-Name="Verdana" Text="Hello, World!"></asp:Label><br />
<asp:Button runat="server" Text="Change Message" ID="btnSubmit"></asp:Button><br />
<asp:Button runat="server" Text="Empty Postback"></asp:Button>

Co se stane při první návštěvě stránky:

  1. "Instantiation stage": Nastaví se lblMessage.Text="Hello, World!"
  2. "Load ViewState stage": nic se nestane, není postback
  3. "Save ViewState stage": nic se nestane, nejsou změny ViewState
  4. "Render Stage": Label je renderován s "Hello, World!"

Co se stane při kliku na Change Message tlačítko:

  1. "Instantiation stage": Nastaví se lblMessage.Text="Hello, World!"
  2. "Load ViewState stage": nic se nestane, ViewState stránky je prázdný
  3. "Raise Postback Event": btnSubmit_Click nastaví
  4. lbl.Message="Goodbye, Everyone!"
  5. "Save ViewState stage": property Text od Labelu je uložena do ViewState, protože se změnila (po volání TrackViewState())
  6. "Render Stage": Label je renderován s "Goodbye, everyone!"

Co se stane při kliku na Empty postback tlačítko:

  1. "Instantiation stage": Nastaví se lblMessage.Text="Hello, World!"
  2. "Load ViewState stage": nastaví se lblMessage.Text="Goodbyw, Everyone!" z ViewState
  3. "Save ViewState stage": property Text od Labelu je uložena do ViewState, protože se změnila (po volání TrackViewState())
    "Render Stage": Label je renderován s "Goodbye, everyone!"

Shrnutí & spol.

  1. Do ViewState se ukládají všechny změny v properties controlů provedené po ukončení události Init.
  2. Protože ViewState ukládá pouze vlastnosti controlů a ne controly samotné, musíme dynamicky přidávané controly přidávat při každém postbacku stránky znovu a znovu - nejlépe během události Init (uděláme-li to však i později, metoda .Add() zajistí nahrání ViewState do přidávaných controlů).
  3. U editovatelných DataGridů je vypnutí ViewState docela dřina.
  4. ViewState se ukládá rekurzivně včetně ViewState child-controlů a to v serializované podobě pomocí LOSFormateru.
  5. ViewState lze ukládat i na serveru na disk nebo do databáze pomocí překrytí metod SavePageStateToPersistenceMedium() a LoadViewStateFromPersistenceMedium(), které standardně právě používají hidden-field ___VIEWSTATE. V některém z dalších článků si ukážeme ukládání do Session.
  6. Další možností na zmenšení ViewState je jeho komprese a dekomprese.
  7. ViewState je chráněn před změnami pomocí machine authentication check (MAC), který však pouze kontroluje, je-li ViewState od stejné verze stránky.
  8. ViewState lze i šifrovat, rozhodně se však nedoporučuje pro ukládání citlivých informací

Viz též článek ViewState vs. fáze Init, aneb jak jsem se chytil.

Published 23. dubna 2006 8:26 by Robert Haken

Comment Notification

If you would like to receive an email when updates are made to this post, please register here

Subscribe to this post's comments using RSS

Comments

No Comments

What do you think?

(required) 
(optional)
(required) 
Enter the code you see below

Submit