SDK のキャッシュ機構
GS2 の Game Engine 向け SDK (GS2 SDK for Unity, GS2 SDK for Unreal Engine など) には、サーバーから取得したデータを SDK 内部にキャッシュする機構が組み込まれています。 このキャッシュ機構を理解することで、API 呼び出し回数を削減し、ゲームのレスポンス性とコストの両方を改善できます。
キャッシュの基本動作
Domain オブジェクト(gs2.Inventory.Namespace(...).Me(...).Inventory(...) のようなアクセス)を介してデータを取得すると、取得したデータは SDK 内部のキャッシュに保持されます。
同一のリソースに対する再取得は、サーバーに問い合わせを行わず、キャッシュから返されます。
そのため、UI の各所で必要となる値を都度サーバーから取得しなくても、Domain オブジェクトを通して何度でも安心して値を参照できます。
キャッシュの自動更新
サーバー側でデータが更新された場合は、SDK 側のキャッシュも自動的に最新の状態に追随します。 具体的には以下のタイミングで反映されます。
- API 呼び出しの応答内に含まれるリソース情報を受け取ったとき
- WebSocket 接続を介してリソースの更新通知を受け取ったとき
- スタンプシートの実行結果として返却されたリソース情報を受け取ったとき
例えば、Gs2-Showcase で商品を購入すると、その購入処理によって増加した Gs2-Inventory のアイテム所持数も、購入 API の応答に含まれる結果から自動的に SDK 内のキャッシュへ反映されます。
UI 側でわざわざ「アイテム一覧を取り直す」必要はありません。
設計指針
取得 API は躊躇なく呼ぶ
Domain オブジェクト経由の ModelAsync / Model / Fetch といった取得処理は、初回はサーバーへリクエストを発行し、以降はキャッシュから値を返します。
そのため、UI を更新するたびに値を読みに行く実装にしても、過剰なリクエスト料金が発生することはありません。
// UI 描画のたびに呼んでも、初回以降は SDK 内のキャッシュから返る
var item = await gs2.Inventory.Namespace("namespace-0001")
.Me(GameSession)
.Inventory("inventory-0001")
.ItemSet("item-0001")
.ModelAsync();キャッシュの更新を能動的に受け取る
Domain オブジェクトは、SDK 内のキャッシュが更新されたタイミングを購読するためのイベント機構を持っています。 UI 側でイベントを購読しておくと、所持数の変動などをポーリングなしで反映できます。
詳細は各 Game Engine SDK のリファレンスを参照してください。
サーバーの最新状態を保証したい場合
低レベル API(Gs2*RestClient / Gs2*WebSocketClient を直接呼び出す形式)はキャッシュを介さずに必ずサーバーへリクエストを送ります。
チート対策のサーバー再検証など、確実にサーバー側の最新状態を取得したい場合は低レベル API を利用してください。
ゾーン切り替え時の挙動
GS2 は 1 つのリージョン内に複数のゾーンを Active / Active で構成しています (リージョン を参照)。 ゾーン間ではデータベースの同期にわずかな遅延が発生するため、ゾーンが切り替わった瞬間に「書き込んだはずの値が読み込めない」現象が起こり得ます。
SDK のキャッシュ機構は、こうした瞬間的な不整合があっても UI が古い値で固まり続けないよう、ベストエフォートで最新状態に追随するよう設計されています。 ゲーム開発者が特別な追加実装を行わなくても、新しいゾーンの最新値にキャッシュが寄っていきます。