組織キャッシュとセッションキャッシュの使用
学習の目的
パーティションを作成する
プラットフォームキャッシュを使用するには、最初に少なくとも 1 つのパーティションを設定します。パーティションを設定したら、プラットフォームキャッシュ Apex API を使用してパーティションに対するデータの追加、アクセス、削除ができます。
各パーティションには、1 つのセッションキャッシュと 1 つの組織キャッシュ区分があります。各セグメントに異なる容量を割り当てることができます。通常、パーティションに 5 MB 以上を割り当てます。この例では、空間を割り当てず、コードがキャッシュの欠落を正しく処理するかどうかを確認しています。空間が割り当てられないと、キャッシュ欠落率が 100% になります。これは、キャッシュ値がキャッシュ内に見つからず、get() メソッドが null を返すということです。この手法を使用してキャッシュの欠落をテストすることを検討します。キャッシュの欠落の処理方法については、後のセクションで取り上げます。
使用を開始するために、[プラットフォームキャッシュ] ページからパーティションを 1 つ作成しましょう (Salesforce Classic でのみ使用可能)。
- [設定] から、[クイック検索] ボックスに「プラットフォームキャッシュ」と入力し、[プラットフォームキャッシュ] を選択します。
- [新規プラットフォームキャッシュ区分] をクリックします。
- パーティションに名前を付けます (アプリケーションの名前など)。
- [デフォルトパーティション] をオンにします。
- セッションキャッシュに「0」、組織キャッシュに「0」と入力し、[保存] をクリックします。
キャッシュキー名の形式
各キャッシュキーでは次の形式が使用されます。
Namespace.Partition.Key
「Namespace」は、アプリケーションが実行されている組織の名前空間名であり、特殊な名前「local」に設定することもできます。「local」という名前は、名前空間が組織に定義されているかどうかに関係なく、組織の名前空間を示します。
「Partition」は、作成したパーティションの名前です。この例では CurrencyCache です。
「Key」は、値を保存するのに使用したキーの名前です。キー名はキャッシュ値を一意に表します。
たとえば、米国ドルからユーロへの通貨換算レートを保存するとします。DollarToEuroRate という名前のキーを作成できます。直前に作成したパーティションの場合、キーの完全名は次のようになります。
local.CurrencyCache.DollarToEuroRate
たとえば、次のスニペットは DollarToEuroRate キーで値を組織キャッシュに保存します。
Cache.Org.put('local.CurrencyCache.DollarToEuroRate', '0.91');
作成したパーティションはデフォルトパーティションであるため、名前空間およびパーティション名を省略して、キー名のみを指定できます。
DollarToEuroRate
デフォルトパーティションを使用する場合、put() コールを次のように短縮できます。
Cache.Org.put('DollarToEuroRate', '0.91');
組織キャッシュにデータを保存して取得する
ユーザーインターフェースで実行する唯一のステップである、パーティションの設定が完了しました。次は Apex に切り替えてキャッシュを管理します。組織キャッシュを使用して、組織の誰もが使用できるデータを保存します。Cache.Org クラスメソッドを使用するか、特定のパーティションを参照するには Cache.OrgPartition クラスを使用します。次にそのパーティションに対してキャッシュメソッドをコールします。
次の Apex スニペットは、Cache.OrgPartition クラスを使用してパーティションにアクセスし、通貨換算アプリケーションのキャッシュ値を保存および取得する方法を示します。ローカル名前空間の CurrencyCache というパーティションを取得します。新しい値はキー DollarToEuroRate と今日の通貨換算レートで追加されます。次に、キー DollarToEuroRate の値がキャッシュから取得されます。
// Get partition Cache.OrgPartition orgPart = Cache.Org.getPartition('local.CurrencyCache'); // Add cache value to the partition. Usually, the value is obtained from a // callout, but hardcoding it in this example for simplicity. orgPart.put('DollarToEuroRate', '0.91'); // Retrieve cache value from the partition String cachedRate = (String)orgPart.get('DollarToEuroRate');
キャッシュ値を 1 つのパーティションだけで管理している場合は、Cache.OrgPartition メソッドを使用します。Cache.OrgPartition メソッドは、名前空間とパーティションのプレフィックスをパーティションオブジェクトの作成時に 1 回だけ指定すればよいため、Cache.Org メソッドよりも容易に使用できます。
キャッシュ値の存続期間
前の例では、すべてが正しく機能し、次の状態であることを前提としています。
- プラットフォームキャッシュが有効化されていて、使用可能な空間を持つパーティションがある
- キャッシュ値がキャッシュで見つかる
- 値がキャッシュに正常に保存される
ただし現実には、キャッシュ値が常に保証されるとは限りません。プラットフォームキャッシュは一時的な空間として使用するものです。たとえば、キャッシュが期限切れになっていることもあります。キャッシュがまだ存続していても、キャッシュデータがキャッシュから削除されているかもしれません。シマリスが頬袋を空にして他のドングリ用の空間を作るのとまったく同じように、プラットフォームキャッシュも他のデータを保持できるように一部の空間をクリアします。パーティション制限を超えると、Salesforce はキャッシュデータを、LRU (Least Recently Used: 最近最も使用されなかったもの) アルゴリズムに基づいて削除します。キャッシュの削除は、使用量が 100% 以下の容量に減るまで行われます。また、ローカルキャッシュ制限を超えた場合、要求がコミットされる前に項目がローカルキャッシュから削除されることがあります。
キャッシュデータの存続期間と有効期限
キャッシュ内にデータが保持される期間は Time to Live 値 (ttlsecs) と呼ばれます。Time to Live 値は、Apex メソッドを使用してキー - 値ペアを保存するときに指定します。セッションキャッシュの場合、データは最大 8 時間キャッシュ内に存続します。組織キャッシュの場合、データは最大 48 時間キャッシュ内に存続します。デフォルトでは、組織キャッシュの Time to Live 値は 24 時間です。
セッションキャッシュの有効期限は、指定した Time to Live に達するか、ユーザーセッションが期限切れになるかのいずれか早い時点で終了します。組織キャッシュは、指定した Time to Live に達すると有効期限が終了します。
キャッシュの欠落を処理するためのベストプラクティス
ベストプラクティスとして、コードでは障害点を予測して対処する必要があります。つまり、キャッシュの欠落が発生し得ることを常に想定します。キャッシュの欠落とは、キャッシュにキーの値を要求し、その値が見つからない場合のことです。get() コールの戻り値は null になります。get() コールの結果が null かどうかを確認し、適宜処理します。たとえば、結果が null の場合、データベースまたは API コールから値を取得します。
次の Apex スニペットは、キャッシュから返された値が null でないかどうか (if (cachedRate != null)) をチェックしてキャッシュの欠落を処理する方法を示しています。たとえば、値が null でない場合は、その値を使用してページに表示できます。それ以外の場合は、この値を別のソース (API コールや Salesforce など) から取得します。
Cache.OrgPartition orgPart = Cache.Org.getPartition('local.CurrencyCache'); String cachedRate = (String)orgPart.get('DollarToEuroRate'); // Check the cache value that the get() call returned. if (cachedRate != null) { // Display this exchange rate } else { // We have a cache miss, so fetch the value from the source. // Call an API to get the exchange rate. }
セッションキャッシュにデータを保存して取得する
セッションキャッシュが何をするものか覚えていますか? そうです。個々のユーザーセッションに結び付けられたデータが保存されます。たとえば、アプリケーションでセッションキャッシュを使用してユーザーのお気に入りの通貨やカスタムナビゲーションタブの順序を保存できます。セッションキャッシュでは、Apex でキャッシュ値を管理し、Visualforce グローバル変数でキャッシュ値を読み取ることができます。
Apex を使用する場合、セッションキャッシュの管理は、組織キャッシュの管理方法と似ていますが、クラス名が異なります。セッションキャッシュに保存されている値にアクセスするには、Cache.Session クラスと Cache.SessionPartition クラスを使用します。パーティション内の値を管理するには、Cache.Session クラスのメソッドを使用します。1 つのパーティション内のみのキャッシュ値を管理する場合は、代わりに Cache.SessionPartition メソッドを使用します。Cache.SessionPartition メソッドは、名前空間とパーティションのプレフィックスをパーティションオブジェクトの作成時に 1 回だけ指定すればよいため、Cache.Session メソッドよりも容易に使用できます。
次の Apex コードのスニペットは、パーティションにアクセスしてキャッシュ値の保存と取得を行う方法を示します。ローカル名前空間の CurrencyCache というパーティションを取得します。新しい値がキー FavoriteCurrency で追加されます。FavoriteCurrency キーの値が取得されます。FavoriteCurrency キーで、ユーザーのお気に入りの通貨が保存されます。この値はユーザーごとに異なるため、セッションキャッシュに適しています。
// Get partition Cache.SessionPartition sessionPart = Cache.Session.getPartition('local.CurrencyCache'); // Add cache value to the partition sessionPart.put('FavoriteCurrency', 'JPY'); // Retrieve cache value from the partition String cachedRate = (String)sessionPart.get('FavoriteCurrency');
Visualforce グローバル変数を使用してプラットフォームキャッシュにアクセスする
$Cache.Session または $Cache.Org グローバル変数を使用して、Visualforce ページからプラットフォームキャッシュに保存されているキャッシュ値にアクセスできます。これらのグローバル変数を使用することで、Apex で保存されたキャッシュ値を Visualforce ページから直接読み取ることができます。
$Cache.Session グローバル変数を使用する場合、キー名を名前空間とパーティション名で完全修飾します。次の例は、名前空間 ExPro、パーティション CurrencyCache、およびキー FavoriteCurrencyRate からキャッシュ値を取得する出力テキストコンポーネントです。
<apex:outputText value="{!$Cache.Session.ExPro.CurrencyCache.FavoriteCurrencyRate}"/>
Apex メソッドとは異なり、組織のデフォルトパーティションを参照する場合に namespace.partition プレフィックスは省略できません。組織で名前空間が定義されていない場合、local を使用して、コードが実行されている現在の組織の名前空間を参照できます。
<apex:outputText value="{!$Cache.Session.local.MyPartition.Key}"/>
キャッシュ値が Apex リストやカスタムクラスのように、プロパティやメソッドのあるデータ構造の場合、そのプロパティにはドット表記を使用して $Cache.Session 式でアクセスします。たとえば、次のマークアップでは、numbersList の値が List と宣言されている場合に、List.size() Apex メソッドが呼び出されます。
<apex:outputText value="{!$Cache.Session.local.MyPartition.numbersList.size}"/>
次の例では、カスタムクラスとして宣言された myData キャッシュ値の value プロパティにアクセスします。
<apex:outputText value="{!$Cache.Session.local.MyPartition.myData.value}"/>
ISV アプリケーションへのキャッシュ割り当ての保護
プラットフォームキャッシュを使用して、ISV アプリケーションの高速化とパフォーマンス向上を実現できます。ISV の開発者は、独自の名前空間用のキャッシュ空間を購入することでアプリケーションのキャッシュ空間を保証できます。これにより、アプリケーションが登録者組織にインストールされたとき、アプリケーションのキャッシュ空間が登録者組織のキャッシュ使用状況の影響を受けずにすみます。アプリケーションの名前空間から実行されている Apex コードのみが名前空間のキャッシュにアクセスして使用できます。登録者組織の他のコードはこのキャッシュを使用できません。名前空間のキャッシュに対してアプリケーションをテストし、キャッシュ割り当てがすべての登録者組織で保護されることを確認できます。
キャッシュパーティションは、アプリケーションのパッケージの一部として登録者に分配されます。他のコンポーネントを追加するのと同様に、名前空間の 1 つ以上のキャッシュパーティションをコンポーネントとしてパッケージに追加します。キャッシュパーティションが連動コンポーネントとして自動的に追加されることはありません。
次の図は、パッケージがパッケージ済みキャッシュと一緒にインストールされた Enterprise Edition 登録者組織のキャッシュ容量の例を示します。登録者の合計キャッシュ容量 30 MB は、セッションキャッシュと組織キャッシュの組み合わせで構成される 3 つのパーティションに分割されています。パッケージ済みキャッシュ容量は、登録者組織のインストール済みパッケージに付属しており、2 つのパーティションが含まれています。このパッケージ済みキャッシュは、ISV が購入した 20 MB のキャッシュで構成されます(パッケージ済みキャッシュにアクセスできるのはパッケージの Apex コードのみで、登録者組織のコードはこのキャッシュを使用できません)。
名前空間キャッシュは、チャネル注文アプリケーションから購入してください。キャッシュは 10 MB ブロック単位で購入できます。アプリケーションで必要なキャッシュ空間の量を判別するには、キャッシュパーティションを使用してアプリケーションをテストします。トライアルキャッシュを使用して組織のキャッシュ容量を増やします。最初の単元で説明したとおり、特定のエディションの登録者組織にはデフォルトでキャッシュが割り当てられます。アプリケーションの開発に使用する Developer Edition 組織の場合、10 MB のトライアルキャッシュを要求できます。組織に提供されるトライアルキャッシュ量を増やすことができます。増加要求については、Salesforce にお問い合わせください。さまざまなキャッシュサイズを試すことで、独自の名前空間に対して購入するキャッシュ量をより的確に把握できます。
プラットフォームキャッシュの値を取得および保存する方法を理解できたので、自分で試してみてください! 次の Challenge を実行して知識をテストしましょう。