Web ページとそのコントロールの状態情報を維持する必要があります。ただし、Web アプリケーションはステートレス プロトコルである HTTP プロトコル上に構築されるため、状態情報を維持することが非常に困難になります。この問題を解決するために、ASP.NET 2.0 テクノロジは、セッション、Cookie、ビュー ステート、コントロール ステート、隠しフィールド、クエリ文字列、個人用ユーザー構成 (プロファイル) などの使用など、さまざまなソリューションを提供します。 ASP.NET 2.0 テクノロジを使用してサーバー コントロールを作成する場合、主な解決策はビュー ステートとコントロール ステートを使用することです。この記事では、ビューステート(ViewState)の基礎知識を詳しく解説し、代表的なアプリケーションを通してビューステートの応用方法を紹介します。
ビュー ステートの概要
ビュー ステートは、サーバーからクライアントへの往復、およびクライアントからの戻りの往復中に、ページとページ内のコントロールが状態情報を維持できるようにする非常に重要なテクノロジです。このようにして、ステートフルで継続的に実行されるページ効果を、Web のようなステートレス環境上に作成できます。このセクションでは、主に操作メカニズム、アプリケーション メソッド、格納されるデータ型、パフォーマンスとセキュリティ、ビュー ステートのブロック (これは ASP.NET 2.0 の新機能)、ビュー ステートの長所と短所について紹介します。
(1)
実行メカニズムのビュー ステートの具体的な実行プロセスは次のとおりです。ユーザーが .aspx ページを要求すると、.NET フレームワークはまず関連するコントロールの状態データを文字列にシリアル化し、それを次の名前のファイルにします。 __VIEWSTATE 隠しフィールドの Value 値がクライアントに送信されます。ページが初めて要求された場合、サーバー コントロールも初めて実行されます。__VIEWSTATE という名前の隠しフィールドには、コントロールのデフォルト情報 (通常は空または null) のみが含まれます。後続のポストバック イベントでは、前のポストバックで使用可能なサーバー コントロールのプロパティの状態が ViewState に保存されます。これにより、サーバー コントロールは、現在処理されているポストバック イベントが発生する前に状態を監視できるようになります。これらのプロセスは .NET Framework によって処理され、ユーザーにとって .aspx ページを実行すると継続的な実行の効果が得られます。
(2) 格納されるデータ型
ビューステートには複数の型のデータを格納できますが、操作効率を向上させるために、ビューステート自体にも共通の型に最適化されたシリアル化メソッドのセットが含まれています。ビューステートのシリアル化メソッドでデフォルトでサポートされるデータ型には、String、Int32、Unit、Color、Array、ArrayList、HashTable、およびカスタム型コンバータ TypeConverter が含まれます。
ビュー ステートは、上記のタイプを含む Array、ArrayList、および HashTable オブジェクト用に最適化されています。したがって、コントロールでビュー ステートを使用する場合は、最適化された型だけでなく、上記の単純なデータ型にも使用を制限するようにしてください。ここでは、値の型を他の型に変換し、標準値とサブプロパティにアクセスするための統合メソッドを提供するカスタム型コンバーター TypeConverter に焦点を当てる必要があります。たとえば、TypeConverter を使用して、文字列を数値に変換したり、数値を文字列に変換したりできます。型コンバーターがない場合、ページ フレームワークは .NET フレームワークが提供するバイナリ シリアル化関数を使用してオブジェクトをシリアル化します。このプロセスは非常にリソースを消費します。
(3) パフォーマンスとセキュリティ
ビューステートを使用する場合、オブジェクトは最初にシリアル化され、その後ポストバックによって逆シリアル化される必要があります。したがって、ViewState のパフォーマンスについて知っておく必要があります。デフォルトでは、コントロールの ViewState は有効になります。ViewState を使用する必要がない場合は、オフにすることをお勧めします。 ViewState は、次の状況では必要なくなります。(1) コントロールはサーバー側イベントを定義しません (現時点でのコントロール イベントはすべてクライアント側イベントであり、ポストバックには参加しません)。動的またはデータバインドされたプロパティ値はありません。ビューステートをオフにするには、コントロールの EnableViewState 値を「false」、つまり EnableViewState="false" に設定します。
デフォルトでは、ビューステートに関連するコンテンツがコンパイルされてクライアントに送信されると、読者にはページの HTML コード内の __VIEWSTATE 隠しフィールドのコンテンツが表示されます。これらは意味のない文字列であり、.NET Framework が関連するコンテンツを Base64 エンコードを通じてエンコードした結果です。これらはクライアントとサーバーの間でクリア テキストで送受信されます。パスワード、アカウント、接続文字列などの機密コンテンツが関係する場合など、場合によっては、デフォルトの方法を使用するのは非常に安全ではありません。この目的を達成するために、.NET Framework は ViewState に対して 2 つのセキュリティ メカニズムを提供します。
検証メカニズム:
EnableViewStateMAC="true" 属性を設定することで、ViewState データにハッシュ コードを追加するように .NET Framework に指示できます (ハッシュ コードは A SHA1 タイプの長さは 160 ビットなので、実行パフォーマンスに重大な影響を与えます)。ポストバック イベントが発生すると、ハッシュ コードが再確立され、元のハッシュ コードと一致する必要があります。このようにして、送信プロセス中に ViewState が改ざんされる可能性があるかどうかを効果的にチェックできます。デフォルトでは、.NET Framework は SHA1 アルゴリズムを使用して ViewState ハッシュ コードを生成します。さらに、以下に示すように、machine.config ファイルで
· 暗号化メカニズムでは、
暗号化を使用して ViewState フィールドの実際のデータ値を保護します。まず、上記のように EnableViewStatMAC="true" を設定する必要があります。次に、machineKey 検証の種類を 3DES、つまり
(4) ビューステートのブロック
上記の内容では、ビューステートの基礎知識を紹介します。ただし、一部の読者は混乱するかもしれません。場合によっては、ビューステート データが非常に大きくなったらどうなるでしょうか?これは明らかに、意図しない結果をもたらすでしょう。この目的を達成するために、ASP.NET 2.0 には、「ビュー ステート ブロッキング」と呼ばれる新しい機能が追加されています。ビューステート内のデータの量が大きすぎる場合、ビューステートのチャンク化によりデータが自動的に複数のチャンクに分割され、データが複数の非表示のフォーム フィールドに配置されます。
ビュー ステートのチャンク化を有効にするには、MaxPageStateFieldLength プロパティを 1 つのビュー ステート フィールドで許可される最大サイズ (バイト単位) に設定します。ページがサーバーにポストバックされると、ページはページの初期化フェーズ中にビュー ステート文字列を解析し、ページ内のプロパティ情報を復元します。デフォルト設定は -1 です。これは、最大サイズがなく、ビューステートがチャンクに分割されないことを意味します。
(5) メリットとデメリット
ビューステートを使用すると、以下の 3 つのメリットがあります。 1. サーバーリソースの消費が少なくなります (アプリケーションやセッションと比較して)。ビューステート データがクライアント コンピューターに書き込まれるためです。 2. メンテナンスが簡単。デフォルトでは、.NET システムは制御状態データのメンテナンスを自動的に有効にします。 3. 強化されたセキュリティ機能。ビューステートの値は、Unicode 実装に対してハッシュ、圧縮、エンコードされるため、隠しフィールドを使用するよりも安全です。
ビューステートの使用には、次の 3 つの欠点があります。 1. パフォーマンスに関する考慮事項。ビュー ステートはページ自体に保存されるため、大きな値が保存されると、ビュー ステートがチャンク化されていても、ユーザーがページを表示および送信するときに速度が低下する可能性があります。 2. 機器の制限。モバイル デバイスには、大量のビュー ステート データを保存するのに十分なメモリ容量がない場合があります。したがって、デバイス上でサーバー コントロールを移動する場合は、別の実装方法が使用されます。 3. 潜在的なセキュリティリスク。ビューステートは、ページ上の 1 つ以上の非表示フィールドに保存されます。ビューステートはデータをハッシュ形式で保存しますが、改ざんされる可能性があります。ページの出力ソースを直接表示すると、非表示フィールドの情報が表示され、セキュリティ上の問題が発生する可能性があります。
代表的な用途
ASP.NET 2.0 テクノロジを使用してサーバー コントロールを開発するプロセスでは、ビュー ステートを使用できる側面が数多くあります。サーバー コントロール プロパティを実装するには、ViewState ディクショナリを使用するのが一般的です。 ViewState のタイプは System.Web.UI.StateBag で、サーバー コントロールのプロパティ値を格納できるキーと値のペアの辞書です。以下に代表的な例を用いて ViewState の適用方法を説明します。
カスタム サーバー コントロール LabelInViewState では、Text と TextInViewState の 2 つのプロパティが実装されています。前者はプライベート変数を使用して作成され、後者は ViewState を使用して実装されます。これらはすべて、テキスト コンテンツを取得または設定するために使用されます。カスタムコントロール実装ファイルLabelInViewState.csのソースコードは以下のとおりです。
System を使用する;System.Collections.Generic を使用する; System.ComponentModel を使用する;System.Text を使用する; System.Web を使用します。 System.Web.UI を使用します。 System.Web.UI.WebControls を使用;名前空間 WebControlLibrary{ [DefaultProperty("テキスト")] [ToolboxData("<{0}:LabelInViewState runat=server></{0}:LabelInViewState>")] パブリック クラス LabelInViewState : WebControl { private string _text; //Text 属性を実装します public string Text { 得る { return (_text == null) ? string.Empty : _text; } セット { _text = 値 } } //ViewState を使用して TextInViewState プロパティを実装します public string TextInViewState { 得る { String s = (String)ViewState["TextInViewState"]; return ((s == null) ? String.Empty : s); } set { ViewState["TextInViewState"] = 値 } } // RenderContents メソッドをオーバーライドします protected override void RenderContents(HtmlTextWriter Output) { 出力.Write("テキスト = "); 出力.書き込み(テキスト); Output.Write(" "); Output.Write("TextInViewState = "); 出力.Write(TextInViewState); } } } |
<%@ ページ言語="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %> <%@ 登録名空間="WebControlLibrary" Assembly="WebControlLibrary" TagPrefix="sample" %> <スクリプト runat="サーバー"> void Button1_Click(オブジェクト送信者, EventArgs e) { デモラベル.テキスト = TextBox1.Text; デモラベル.TextInViewState = TextBox2.Text; } </スクリプト> <head runat="サーバー"> </頭> <body style="font-size: small;"> <form id="form1" runat="server"> <div> 名前: |
ページに表示される上記のコードには、2 つのテキスト ボックス、2 つのボタン、およびカスタム サーバー コントロール LabelInViewState が含まれています。イベント ハンドラー Button1_Click に示されているように、「送信」ボタンがクリックされると、LabelInViewState コントロールはテキスト ボックス内のテキストを取得して表示します。アプリケーションのレンダリングを図 1 と 2 に示します。
図 1 [送信] ボタンをクリックします | 図 2 [リロード] ボタンをクリックします |