書籍転載
独習ASP.NET 第3版

ASP.NETの状態管理:アプリケーション変数/キャッシュ機能
― 第7章 状態管理 7.4/7.5 ―

WINGSプロジェクト 山田 祥寛
2011/08/03
Page1 Page2

7.5 キャッシュ機能

 データソース(データベースなど)の内容がほとんど変更されないのに、ページ自体はリクエストのたびに動的に処理しなければならないのは無駄なことです。そのようなページでは、動的に生成されるデータ、場合によっては、ページそのものをキャッシュすることで、2回目以降の処理を高速化できます。

 キャッシュとは、いわゆる処理過程(もしくは結果)で生成されたコンテンツ(またはコンテンツのもととなるデータソース)を特定の媒体にプールしておくことで、次回以降のアクセスを高速化する仕組みのことです。

 一口に「キャッシュ」と言ってもその形式はさまざまです。まずは、ASP.NETで用意されている3種類のキャッシュ技術についてまとめます。

出力キャッシュ

 古くから採用されてきた手法で、ページ全体の結果をそのまま保存します。ページキャッシュとも呼びます。

 インターネットブラウザーでも、一度アクセスしたページをローカルのディスクに保存する仕組みが備わっていますが、これこそ代表的なページキャッシュ機能の1つです。ネットワークの構成、設定によっては、クライアントではなく、途中のプロキシ(代理)サーバーやアプリケーションサーバーでページキャッシュを有効にすることもできるでしょう。

 ただし、かつてのページキャッシュは、動的なページを保持する技術としては、あまり有用なものではありませんでした。ページキャッシュは、リクエストの内容にかかわらず返されるレスポンスが同一でなければ、意味がありません。ところが、一般的な動的サイトでは、ポストデータやクエリ情報によって、レスポンスが書き換えられる場合がほとんどです。これでは、ページキャッシュを使っても無意味であるばかりか、本来出力させたいページがクライアントに返されない可能性が出てきてしまいます。

 この点、ASP.NETのキャッシュ技術は賢くできています(図7.13)。

図7.13 ページキャッシュ

 リクエストパラメーターやヘッダー情報、ブラウザーの種類などによって異なる出力を、それぞれ別のキャッシュデータとして保存できるのです。これをDynamic Output Cachingと呼びます。

 これによって、たとえばラジオボタンの選択によって異なる結果を返すようなページでも、安心してページキャッシュを利用できます。

フラグメントキャッシュ

 動的なページといっても、実は、毎回動的に生成しなければならない(頻繁に更新が行われる)コンテンツは、その中のごく一部にすぎません。裏を返せば、ページの大部分は、毎回同じ内容を返しても差し支えないコンテンツなのです。

 そこで登場するのが、フラグメントキャッシュです。フラグメントキャッシュとは、ページの一部(フラグメント)ごとに異なるキャッシュ定義を設定する技術です。フラグメントキャッシュを利用することで、頻繁に更新されるコンテンツには短いキャッシュ時間を、固定的なコンテンツについては長時間持続されるキャッシュを設定できます。

データキャッシュ

 フラグメントキャッシュがページの断片をキャッシュするのに対し、データキャッシュは、ページを生成するために利用する元データをキャッシュします(図7.14)。

図7.14 データキャッシュ

 たとえば、メニュー情報がXMLデータとして管理されているとしましょう。メニュー情報は、あるページでは選択ボックスで表示したり、リストとして表示したり、あるいは、もっと別な形で加工されたものを表示するかもしれません。このため、フラグメントキャッシュには適していません。出力形式に整形する前のデータそのものをキャッシュする必要があるのです。

 データキャッシュを利用することで、データを(ファイルやデータベースではなく)メモリから直接に読み込めるようになりますので、パフォーマンスを改善できます。

 これらキャッシュのうち、本節では、ページキャッシュ、データキャッシュについて解説します。

7.5.1 ページキャッシュの基本

 まずは、ページキャッシュからです。ページキャッシュを有効にするには、@OutputCacheディレクティブを利用します。

 @OutputCacheディレクティブの基本的な例を、自作のSqlParam.aspxで確認してみましょう。ラジオボタン(list)の選択値に応じてページをキャッシュします。

1.ページキャッシュを有効にする

 SqlParam.aspxをソースビューで開いて、リスト7.10のように編集します。

<%@ Page Language="vb" AutoEventWireup="false" CodeBehind="SqlParam.aspx.vb"
         Inherits="SelfAspNet.SqlParam" %>
<%@ OutputCache Duration="120" VaryByParam="list" %>
リスト7.10 SqlParam.aspx

 ポストデータやクエリ情報によってキャッシュを振り分けたいという場合、そのキーをVar yByParam属性で指定します。ここでは、ラジオボタンlistでキャッシュを振り分けるので、VaryByParam属性にlistを指定しています。

 VaryByParam属性には、その他にも表7.8のような形式でキーを指定できます。

記述 概要
VaryByParam="list;id" 振り分けのキーが複数ある場合(セミコロン区切りで指定)
VaryByParam="*" すべてのキーでキャッシュを識別したい場合
VaryByParam="none" キーによる振り分けが不要な場合
表7.8 VaryByParam属性の記述(例)

 リクエスト情報によって振り分けの必要がない場合も、VaryByParam属性を省略することはできない点に注意してください。

 もう1つ、Duration属性はキャッシュの有効期間を表します。ここでは、120秒にしていますが、データの性質に応じて適宜変更してください。

* フォーム要素の値をキーにキャッシュを振り分ける場合には、要注意です。というのも、VaryByParam属性で指定するキー名は、ユニークIDであるためです。ユニークIDは、ページの階層構造によって変動します(たとえばコンテンツページ配下のテキストボックスではctl00$cph$txtNameのようになるかもしれません)。ユニークIDを指定するのが現実的でない場合には、キャッシュの数は多くなってしまいますが、「*」(すべてのキー)を指定しても良いでしょう。

2.現在時刻を表示する

 キャッシュが有効になっていることを確認するために、ページの先頭に現在時刻を表示します(リスト7.11)。本来、文字列の出力にはLabelコントロールなどを利用すべきですが、ここでは簡単化のためにWriteメソッドを使用しています。

Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
  Response.Write(DateTime.Now.ToString())
End Sub
リスト7.11 SqlParam.aspx.vb

 以上の手順を終えたら、サンプルを実行してみましょう。ラジオボタンの選択に応じて正しくデータが表示されること、120秒以内に同じオプションが選択された場合には同一の時刻が表示されること(キャッシュが有効になっていること)を確認してください。

7.5.2 リクエストヘッダーでキャッシュを振り分ける ― VaryByHeader属性

 VaryByHeader属性を使用することで、リクエストヘッダーによってキャッシュを切り替えることができます。たとえば、以下はブラウザーから送信されたAccept-Languageヘッダー(使用している言語)に応じて表示言語を切り替える例です(図7.15)。この場合、キャッシュもAccept-Languageヘッダーの単位に切り替える必要があります。

図7.15 リクエストヘッダーでキャッシュを振り分ける

1.リソースファイルを作成する

 国際化対応ページを作成するには、まずリソースファイルを用意する必要があります。リソースファイルとは、言語/地域に依存する文字列などの情報をまとめたファイルです。ASP.NETでは、ブラウザーから送信された言語情報(Accept-Languageヘッダー)を利用して適切なリソースファイルを選択し、その中の情報をページに埋め込むことで国際化対応を実現しているのです。これによって、ページそのものを多重化することなく、さまざまな言語に対応できます(図7.16)。

図7.16 国際化対応ページの実装

 リソースファイルを作成するには、[新しい項目の追加]ダイアログで、[リソースファイル]テンプレートを選択してください。保存先はApp_GlobalResourcesフォルダー、名前はMyRes.resx、MyRes.ja-JP.resxとします。

 App_GlobalResourcesフォルダーは、グローバルリソースフォルダーとも呼ばれ、ASP.NETの予約フォルダーの1つです。アプリケーション共通で利用するリソースファイルは、原則として、アプリケーションルート直下のApp_GlobalResourcesフォルダーに保存します。

 リソースファイルの名前にも決まりがあります。

ベース名[.カルチャ名].resx

 ベース名とは、アプリケーションからリソースファイルを識別するための名前、カルチャ名は言語/地域を識別するためのキーです。たとえば、「ja-JP」であれば日本語(日本)の意味ですし、「en-US」であれば英語(アメリカ合衆国)を意味します。ASP.NETでは、カルチャ名とブラウザーの言語設定(Accept-Languageヘッダー)を比較するのです。

 カルチャ名が省略された場合には、デフォルトのリソースファイルであることを意味します。デフォルトのリソースファイルとは、合致するカルチャが存在しない場合に、最終的に適用されるリソースのことです。

 リソースファイルを開くと、図7.17のようなデータシートが表示されます。

図7.17 リソースファイル編集用のデータシート

 ここでは、それぞれ表7.9のようにリソースを定義しておきましょう。

ファイル名 キー名
MyRes.resx Greeting Hello
Update Last Updated
MyRes.ja.resx Greeting こんにちは
Update 最終更新日
表7.9 リソースの設定(例)

2.ページをレイアウトする

 新規にHeaderCache.aspxを作成し、図7.18のようにレイアウトします。

図7.18 HeaderCache.aspxのレイアウト

 LabelコントロールlblMessageのTextプロパティにリソースファイルを割り当てるには、プロパティウィンドウから(Expressions)プロパティ右端のボタンをクリックします。

 [<ID値>式]ダイアログが起動しますので、図7.19のように入力してください。ClassKeyプロパティにはリソースファイルのベース名、ResourceKeyプロパティにはリソースのキー名を、それぞれ指定します。これでLabelコントロールlblMessageのTextプロパティにMyResリソースのGreetingキーが割り当てられました。

図7.19 [<ID値> 式]ダイアログ

 同じ要領で、LabelコントロールlblTimeTitleには、MyResリソースのUpdateキーを割り当てます。

3.ページのカルチャを設定する

 ソースビューからHeaderCache.aspxの@Page/@OutputCacheディレクティブを編集します(リスト7.12)。

<%@ Page Language="vb" AutoEventWireup="false" CodeBehind="HeaderCache.aspx.vb"
         Inherits="SelfAspNet.HeaderCache" Culture="auto" UICulture="auto" %>
<%@ OutputCache VaryByParam="none" VaryByHeader="Accept-Language" Duration="120" %>
リスト7.12 HeaderCache.aspx

 Culture/UICulture属性は、それぞれアプリケーション、ユーザーインターフェイスで利用するカルチャを表します。ブラウザーの言語設定(Accept-Language属性)を利用する場合には、いずれもautoとしておきましょう。

 また、@OutputCacheディレクティブのVaryByHeader属性は、キャッシュの識別に利用するヘッダー名を表します。ここでは、ページの内容がAccept-Languageヘッダーによって切り替わりますので、Accept-Languageと指定しておきます。

 VaryByParam属性は必須ですので、ここではnone(パラメーターでキャッシュを識別しない)としておきます。

4.現在時刻を表示する

 キャッシュが有効になっていることを確認するために、LabelコントロールlblCurrentに現在時刻を表示します(リスト7.13)。

Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
  lblCurrent.Text = DateTime.Now.ToString()
End Sub
リスト7.13 HeaderCache.aspx.vb

 以上の手順を終えたら、サンプルを実行してみましょう。動作を確認するには、Internet Explorerであれば、メニューバーの[ツール]→[インターネットオプション]から[全般]タブの[言語]ボタンをクリックします。[言語の優先順位]ダイアログ(図7.20)で、先頭の言語を「日本語(日本)[ja-JP]」「英語(米国)[en-US]」とで切り替えて、表示の変化を確認してください。また、同じ言語設定では時刻表示が変化しない(キャッシュが働いている)ことも確認しておきましょう。

図7.20 [言語の優先順位]ダイアログ(Internet Explorer)

* @OutputCacheディレクティブでは、VaryByParam/VaryByHeader属性の他にも、VaryByCustom属性を利用できます。設定次第でさまざまなキーでキャッシュを識別することのできる属性ですが、よく利用するのは「VaryBy Custom="Browser"」という設定です。これによって、ブラウザーごとにキャッシュを識別できます。

7.5.3 ページキャッシュの共通ルールを定義する ― <outputCacheSettings>要素

 @OutputCacheディレクティブは、ページ個別のキャッシュルール(キャッシュポリシー)を指定するものでした。しかし、一般的にはキャッシュルールは、ページ単位で決まるものではありません。アプリケーション一律、とは言わないまでも、更新/参照の頻度、データの種類によって、ポリシーは数種類に決まるのが一般的でしょう。

 そのような場合、個々の@OutputCacheディレクティブにパラメーターをハードコーディングするのは面倒ですし、そもそもキャッシュポリシーに変更があった場合に、すべてのページを修正しなければならないのは、望ましいことではありません。

 そこで、ASP.NETではキャッシュポリシーをアプリケーション構成ファイル(Web.config)で管理できるようになっています。たとえば、MyCacheというキャッシュポリシーを定義するには、<caching>→<outputCacheSettings>→<outputCacheProfiles>要素配下に<add>要素を記述します(リスト7.14)。

<caching>
  <outputCacheSettings>
    <outputCacheProfiles>
      <add name="MyCache" enabled="true" duration="120" varyByParam="*" />
    </outputCacheProfiles>
  </outputCacheSettings>
</caching>
リスト7.14 Web.config

 <add>要素に記述できる属性は、@OutputCacheディレクティブのそれに準じます。これによって、個々のページでは、以下のように記述すれば良いようになります。

<%@ OutputCache CacheProfile="MyCache" %>

7.5.4 データキャッシュの基本

 SqlDataSourceのようなデータソースコントロールを利用しているならば、データキャッシュを行うのは簡単なことです。表7.10のプロパティを設定することで、データソースから取得した情報をキャッシュできます。

プロパティ 概要
EnableCaching データキャッシュ機能を有効にするか
CacheDuration キャッシュの有効期限(秒)
CacheExpirationPolicy 有効期限の基点(Absolute|Sliding)
SqlCacheDependency データベースキャッシングのキー
表7.10 SqlDataSourceコントロールのキャッシュ関連プロパティ(主要)

 CacheExpirationPolicyプロパティがAbsolute(絶対基点。デフォルト)である場合、キャッシュデータの有効期限は「最初に作成」された時点からカウントします(図7.21)。一方、Sliding(相対基点)を指定した場合には、キャッシュの有効期限は「最後にアクセス」された時点からカウントされます。つまり、Absolute指定の場合、データへのアクセスの有無にかかわらず有効期限が決まりますが、Sliding指定の場合は、データへのアクセスの有無によって有効期限が変動するということです。

図7.21 CacheExpirationPolicyプロパティ

 なお、データソースコントロールでキャッシュ機能を利用する場合には、DataSourceプロパティをDataSet(デフォルト)としておく必要があります。DataReaderの設定では、キャッシュは正しく動作しませんので要注意です。

 自作したサンプルのEnableCaching属性をTrueとし、データベースの内容を書き換えても、ページに反映されないことも確認してみましょう。

7.5.5 データベースキャッシングを利用する

 データベースキャッシングとは、キャッシュの作成元となっているテーブル(データベース)に変更があったタイミングでキャッシュデータをリフレッシュする機能のことを言います。データベースキャッシングを利用することで、データソースは更新されたのにキャッシュは古い情報のまま残ってしまう、といったようなデータの不整合を解消することができます。以下に、具体的な手順を見ていきましょう。

1.データベースファイルをアタッチする

 データベースキャッシングを利用するには、あらかじめデータベースファイル(.mdfファイル)をSQL Serverにアタッチしておく必要があります。データベースをアタッチするには、.mdfファイルをアプリケーション配下から別のフォルダー(たとえば、「C:\Data」)に移動したうえで、データベースエクスプローラーのコンテキストメニューから[接続の追加]を選択します。[接続の追加]ダイアログが起動しますので、図7.22のように必要な情報を入力してください。

図7.22 [接続の追加]ダイアログ

2.データベース上でキャッシュ機能を有効にする

 続いて、.NET Framework標準で用意されているaspnet_regsql.exeを使ってデータベースのキャッシュ機能を有効化します。aspnet_regsql.exeは「<システムルート>\Microsoft.NET\Framework\<バージョン番号>」フォルダーに含まれています。

 コマンドプロンプトから以下のようにコマンドを入力してください。

> aspnet_regsql.exe -S .\SQLEXPRESS -E -d SelfAsp -ed
> aspnet_regsql.exe -S .\SQLEXPRESS -E -d SelfAsp -t Album -et

 なお、ここではデータベース名がSelfAsp、キャッシュ機能を有効にしたいテーブル名がAlbumであると仮定しています。

3.Web.configの設定を変更する

 次に、キャッシュ対象となるデータベースをアプリケーションに登録します。たとえば、接続名「MyDBCache」で定義されたデータベースを登録するには、リスト7.15のように記述してください。MyDBCacheは、データベースSelfAspに接続するための定義情報です。

<?xml version="1.0" ?>
<configuration>
  ……中略……

  <connectionStrings>
    ……中略……
    <add name="MyDBCache" connectionString="Data Source=.\SQLEXPRESS;Initial Catalog=SelfAsp;Integrated Security=True" providerName="System.Data.SqlClient" />
  </connectionStrings>

  <system.web>
    ……中略……

    <caching>
      <sqlCacheDependency enabled="true" pollTime="5000">
        <databases>
          <add name="MyCache" connectionStringName="MyDBCache" />
        </databases>
      </sqlCacheDependency>
    </caching>

    ……中略……
  </system.web>

</configuration>
リスト7.15 Web.config

 データベースキャッシング機能を有効にするのは、<sqlCacheDependency>要素のenabled属性の役割です。pollTime属性は、キャッシュ対象のテーブルに対して変更を確認する時間間隔をミリ秒単位で指定します。デフォルトは1分で、500ミリ秒未満の設定はできません。

 具体的な対象データベースの登録は、<databases>→<add>要素に記述します。name属性にはキャッシュの定義名として任意の文字列を、connectionStringName属性には対象データベースへの接続名をそれぞれ指定します。connectionStringName属性の値は、<connectionStrings>→<add>要素のname属性であらかじめ定義された値に対応している必要があります。

4.@OutputCacheディレクティブを指定する

 最後に、キャッシュ対象の.aspxファイルに対して@OutputCacheディレクティブを追加します。SqlDependency属性には、Web.configに設定した内容に基づいて、「キャッシュ名:テーブル名」の形式で指定します。

 ここでは、自作のGridView.aspxに対して、リスト7.16のようにコードを追加/修正しておきます。

<%@ OutputCache Duration="120" VaryByParam="None" SqlDependency="MyCache:Album" %>
  ……中略……
  <asp:SqlDataSource ID="sds" runat="server" ConnectionString="<%$ ConnectionStrings:MyDBCache %>"
リスト7.16 GridView.aspx

 以上で、データベースキャッシングを利用する準備は完了です。キャッシュが有効になったこと、Albumテーブル更新時にページも更新されることを確認してください。

7.5.6 Cacheオブジェクトでキャッシュを操作する

 データキャッシュは、プログラム側から操作することもできます。以下では、XML文書で管理された書籍データをキャッシュし、2回目以降のアクセスではキャッシュの内容を表示することにします(図7.23)。

図7.23 Books.xmlの内容をグリッド表示

1.Books.xmlをコピーする

 Books.xmlは、配布サンプルのApp_Dataフォルダーに含まれています。あらかじめプロジェクト配下のApp_Dataフォルダーにインポートしてください。

2.ページをレイアウトする

 新規にDataCache.aspxを作成したら、図7.24のようにレイアウトします。また、タスクメニューの[列の編集...]をクリックして、[フィールド]ダイアログから、GridViewコントロールにBoundFieldフィールドを追加してください(表7.11)。

図7.24 DataCache.aspxのレイアウト

プロパティ 1 2 3 4 5
HeaderText ISBNコード 書名 価格 出版社 刊行日
DataField isbn title price publish published
表7.11 GridViewコントロールのフィールド設定(BoundFieldフィールドを5つ追加)

3.イベントハンドラーを定義する

 GridViewコントロールにデータをバインドするコードを追加します(リスト7.17)。

リスト7.17 DataCache.aspx.vb

 Cache.GetメソッドでBooksキャッシュの内容を取得し、キャッシュが存在しない(Nothingである)場合には、オリジナルのBooks.xmlを、そうでない場合にはキャッシュの内容を読み込み、データセット(DataSetオブジェクト)にセットします()。

 ReadXmlメソッドはXML文書をテーブルの形式に変換したうえで、データセットに流し込むためのメソッドです。引数には物理パスを要求しますので、MapPathメソッドでパスを変換しておきましょう()。

 また、新規にXML文書の読み込みを行った場合は、Insertメソッドでその内容をキャッシュに保存しておきます()。

Get(key As String) As Object
Insert(key As String, value As Object[, dep As CacheDependency]
構文 Get/Insertメソッド
key:キー
value:キャッシュオブジェクト
dep:依存関係

 これによって、2回目以降のアクセスではファイルの読み込みをスキップし、キャッシュ(メモリ)へのアクセスのみでページを表示できるというわけです。

 実際のサンプルを実行してみましょう。2回目以降のアクセスで、オリジナルのBooks.xmlを変更しても、ページには反映されないことを確認してください。

7.5.7 有効期限や依存関係を持つキャッシュを生成する

 しかし、ここでちょっと疑問に思うことはありませんか。ただアプリケーション共通で使えるデータをメモリに保存しておくだけでは、すでに登場したアプリケーション変数となんら変わるところはありません。アプリケーション変数とキャッシュデータとは、どのような使い分けをしたら良いのでしょうか。

 Cacheオブジェクトでは、キャッシュデータに有効期限や依存関係、優先順位を持たせることができます。アプリケーション変数は基本的にアプリケーションが起動している中で維持されますが、キャッシュデータはさまざまな条件下で破棄されるされる可能性があるという点が異なります(こうした特性を考えれば、Applicationオブジェクトにはリフレッシュのオーバーヘッドが大きい=破棄されたくないデータを格納するのが望ましいでしょう)。

 具体的な例も見ていきましょう。

依存関係を設定する

 前項の例では、キャッシュデータのもととなったBooks.xmlが更新されても、キャッシュに反映されないことを確認しました。しかし、一般的にはキャッシュを利用しつつも、キャッシュの元データが更新されたら、それに応じてキャッシュも更新したいのが普通です。

 そこでCacheオブジェクトでは、キャッシュのオリジナルデータを監視し、その変更に応じてキャッシュをリフレッシュする仕組みを提供しています。この場合であれば、Books.xmlが更新されたタイミングでキャッシュBooksも置き換えるわけです。これをキャッシュBooksはBooks.xmlに依存する、と言います。先ほどの例に依存性の設定を加えてみたのが、リスト7.18です(修正した結果は、配布サンプルではDataCache2.aspxという名前で収録しています)。

Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
  Dim ds As New DataSet()
  If IsDBNull(Cache.Get("Books")) Or IsNothing(Cache.Get("Books")) Then
    ds.ReadXml(Server.MapPath("/App_Data/Books.xml"))
    Dim cd As New CacheDependency(Server.MapPath("/App_Data/Books.xml"))
    Cache.Insert("Books", ds, cd)
  Else
    ds = Cache.Get("Books")
  End If
  grid.DataSource = ds
  Page.DataBind()
End Sub
リスト7.18 DataCache2.aspx.vb

 この状態で、Books.xmlを更新してみると、今度はページの内容が即座に更新され、キャッシュがリフレッシュされたことがわかるはずです。

 キャッシュの依存関係を設定するには、Insertメソッドの第3引数にCacheDependencyオブジェクトを指定するだけです(太字部分)。CacheDependencyクラスは、キャッシュの依存関係に関わる情報を表すクラスです。

New CacheDependency(path As String[, key As String][, dep As CacheDependency][, start As DateTime])
構文 CacheDependencyクラス(コンストラクター)
path:監視対象のフォルダー/ファイル(配列も可)
key:監視対象のキャッシュキー(配列も可)
dep:依存している依存関係
start:何時以降の変更を検知するか

 必須の引数はpathだけです。指定されたファイルやフォルダーを監視し、対象のコンテンツが変更された場合に現在のキャッシュを破棄(再生成)します。もしもキャッシュを生成する際に指定されたパスが見つからず、あとから該当のパスが生成された場合にも、パスの内容が変更されたものと見なし、キャッシュは破棄されます。

 引数key/depを指定することで、別のキャッシュ、または依存関係に対して、依存関係を設定することもできます(図7.25)。相互に強く関係するキャッシュ(たとえば、部門データと社員データのように)を定義している場合、キャッシュ同士の階層関係を明確に表現できます。

図7.25 キャッシュ依存の継承

 引数startは、ファイルが変更されたと見なす時刻を表します。キャッシュ生成以前にさかのぼって変更を検知したい場合に指定します。

有効期限を設定する

 キャッシュを登録する際に、有効期限を設定します。依存関係を監視するまでもないが、適宜、新しい情報にリフレッシュしたいという場合に指定します。

Insert(key As String, value As Object, dep As CacheDependency, absolute As DateTime, sliding As TimeSpan)
構文 Insertメソッド
key:キー名
value:データ
dep:キャッシュの依存関係
absolute:有効期限(絶対時間)
sliding:有効期限(相対時間)

 有効期限を設定する場合、

  • 依存関係(引数dep)は省略できない(不要な場合はNothingを指定)
  • 有効期限には、絶対指定、相対指定の2種類がある

という点に注目です。以下は、絶対/相対指定それぞれの例です。

Cache.Insert("Hoge", value, Nothing, DateTime.Now.AddMinutes(30), Cache.NoSlidingExpiration) ……絶対指定

Cache.Insert("Hoge", value, Nothing, Cache.NoAbsoluteExpiration, TimeSpan.FromSeconds(15)) ……相対指定

 絶対指定/相対指定はいずれも省略できない点に注意してください。片方を指定した場合には、もう片方にはそれぞれ、Cache.NoSlidingExpiration(相対指定は無効)、Cache.NoAbsoluteExpiration(絶対指定は無効)を指定する必要があります。

優先順位を設定する

 キャッシュは依存性、有効期限によって破棄されるほか、メモリが不足するなどの状況に応じて破棄される可能性もあります。その際に、どのキャッシュを先に削除するかを決めるのが優先順位の意味です。

Insert(key As String, value As Object, dep As CacheDependency, absolute As DateTime, sliding As TimeSpan, priority As CacheItemPriority priority, callback As CacheItemRemovedCallback)
構文 Insertメソッド
key:キー名
value:データ
dep:キャッシュの依存関係
absolute:有効期限(絶対時間)
sliding:有効期限(相対時間)
priority:優先順位
callback:キャッシュ削除時に呼び出されるデリゲート

 優先順位は低い順に、Low→BelowLow→Normal→AboveNormal→High→NotRemovableのような値を指定できます。NotRemovableを指定した場合には、キャッシュは有効期限や依存性によってしか削除されません。

 また、優先順位を指定した場合には、引数callbackは省略できません。不要な場合にも、必ずNothingを指定するようにしてください(削除デリゲートについては、本書では割愛します)。

Cache.Insert("Hoge", value, Nothing, DateTime.Now.AddMinutes(30), Cache.NoSlidingExpiration, CacheItemPriority.High, Nothing)

* 有効期限や使用メモリの割合は、アプリケーション構成ファイルの<caching> → <cache>要素で指定できます。具体的には、以下のような属性を指定できます。

属性 概要 デフォルト値
disableMemoryCollection メモリ逼迫時のメモリ収集機能を無効にするか false
disableExpiration キャッシュの有効期限を無効にするか false
privateBytesLimit 有効期限切れキャッシュのクリアを行うための、アプリケーションにおけるプライベートメモリの上限 0(自動判定)
percentagePhysical MemoryUsedLimit 有効期限切れキャッシュのクリアを行うための、マシンの物理メモリの上限割合 0(自動判定)
privateBytesPollTime メモリ使用状況をポーリングする時間間隔 00:02:00
<cache>要素の主な属性

この章の理解度チェック

  1. 以下は、ASP.NETの組み込みオブジェクトについてまとめたものです。カッコ内を適切な語句で補い、表を完成させてください。
組み込みオブジェクト 概要
[  ] アプリケーション共通の情報を管理
Cache [  ]を実現するための方法を提供
Request クライアントからの[  ]情報にアクセスするための方法を提供
Response クライアントへの[  ]を制御するための方法を提供
Server [  ]の一連のプロパティ、メソッドにアクセスするための手段を提供
Session [  ]共通の情報を管理
Trace [  ]の制御
[  ] ページ要求を行っているユーザーに関する情報を管理
[  ] ビューステートにアクセスする手段を提供
ASP.NETの主な組み込みオブジェクト
  1. 次の文章は、状態維持について述べたものです。正しいものには○を、間違っているものには×を記入してください。

( )HTTPはステートフルなプロトコルなので、HTTPの機能を利用することで状態を維持することができる。
( )クッキーはクライアントで管理されるので、サーバーで管理されるセッションよりも安全である。
( )アプリケーション変数は、設定を変更することでデータベースに保存することもできる。
( )セッション変数はAbandonメソッドで破棄されなかった場合、ゴミとしてサーバーを再起動するまで残ってしまうので要注意である。
( )ビューステートは、リダイレクトしたページ間で保持できる。

  1. 以下は、ASP.NETで利用できる状態維持の技術についてまとめたものです。カッコ内を適切な語句で補い、表を完成させてください。
機能 保存場所 有効範囲 データ型
クエリ情報 クライアント 現在/次のページ 文字列
隠しフィールド [  ] 現在/次のページ [  ]
ビューステート [  ] ページ内 文字列
クッキー [  ] [  ] 文字列
セッション サーバー 現在のユーザー [  ]
[  ] サーバー すべてのユーザー オブジェクト
ASP.NETの状態管理
  1. 以下は、ASP.NETで利用可能なセッションモードに関する記述です。カッコ内を適切な語句で埋めて、表を完成させましょう。
モード 概要
[  ] ASP.NETと同一プロセス上でセッションを管理。最も高速な動作を望めますが、Webサーバー再起動などの前後でセッションを維持できないという難点があります。また、大量のセッション情報を保存するには[  ]です。
StateServer ASP.NETと[  ]プロセス上でセッションを管理。[  ]モードよりも若干オーバーヘッドが[  ]ですが、 Webサーバーの状態にかかわらず、セッション情報を維持できます。
[  ] セッションの保存先として SQL Serverを使用。最もオーバーヘッドの[  ]方式で、使用に際しては相応の準備も必要です。しかし、サーバーの状態にかかわらず、セッションを維持でき、ある程度の容量のセッション管理にも対応が可能です。
ASP.NETで利用可能なセッションモード
  1. 以下は、構成ファイル上で、キャッシュポリシー"MyCache"を定義するための構成設定と、そのポリシーを引用するための.aspxファイルでの記述です。空欄を適切な語句で埋めて、コードを完成させてみましょう。
<[  ] >
  <outputCacheSettings>
    <[ 
 ] >
      <add name="MyCache" enabled="true"[ 
 ] ="120" varyByParam="*" />
    </[ 
 ] >
  </outputCacheSettings>
</[  ]>
Web.config

<%@[  ][  ] ="MyCache" %>
キャッシュポリシーを引用する.aspxファイル

 『書籍転載:独習ASP.NET 第3版』からの転載は今回で終了です。end of article

 

 INDEX
  [書籍転載]独習ASP.NET 第3版
  ASP.NETの状態管理:アプリケーション変数/キャッシュ機能
    1.アプリケーション変数
  2.キャッシュ機能

インデックス・ページヘ  「独習ASP.NET 第3版」


Insider.NET フォーラム 新着記事
  • 第2回 簡潔なコーディングのために (2017/7/26)
     ラムダ式で記述できるメンバの増加、throw式、out変数、タプルなど、C# 7には以前よりもコードを簡潔に記述できるような機能が導入されている
  • 第1回 Visual Studio Codeデバッグの基礎知識 (2017/7/21)
     Node.jsプログラムをデバッグしながら、Visual Studio Codeに統合されているデバッグ機能の基本の「キ」をマスターしよう
  • 第1回 明瞭なコーディングのために (2017/7/19)
     C# 7で追加された新機能の中から、「数値リテラル構文の改善」と「ローカル関数」を紹介する。これらは分かりやすいコードを記述するのに使える
  • Presentation Translator (2017/7/18)
     Presentation TranslatorはPowerPoint用のアドイン。プレゼンテーション時の字幕の付加や、多言語での質疑応答、スライドの翻訳を行える
@ITメールマガジン 新着情報やスタッフのコラムがメールで届きます(無料)

注目のテーマ

Insider.NET 記事ランキング

本日 月間