1

開くのに非常に時間がかかるデータセット (ストアド プロシージャ) の場合、Datasnap サーバーに何らかのキャッシュを実装したいと考えています。

したがって、このデータセットが最初にロードされ、クライアント (TClientDataSet) に転送された場合、サーバーが再起動するか、サーバーで「リロード」プロシージャが呼び出されない限り、次の要求のためにデータセットを閉じてから再度開くべきではありません。

そのため、最初に開いた後、すべての新しいクライアントは、サーバー側のデータセットを更新/再ロードすることなく、データセットのコピー (クローン) のみを受け取ります。

このデータセット「キャッシュ」を簡単に実装するには、Datasnap サーバー データモジュールをセッションごとに作成しないでください (新しいセッションごとに、クライアントが DatasetProvider を開く要求を送信するまでサーバー側のデータセットが閉じられるため)。セッションデータモジュール用にもデータセットを複製する解決策を見つけることができるかもしれませんが、私の基本的な質問は次のとおりです。

クライアントがサーバー側のデータセットを開くことはできますが、閉じることはできないように、DatasetProvider のメソッドをオーバーライドする方法はありますか?

4

1 に答える 1

0

数年前、私が働いていたいくつかの DataSnap サーバーは、非常に遅い SQL Server 7 サーバーからデータを取得する必要がありました。次に、ファイル キャッシュまたはデータベースからデータを読み取る「サーバー ClientDataSets」に「キャッシュされたプロバイダー」が接続されている TClientDataSets に基づいて、サーバー キャッシュ「おもちゃ」を作成しました。

キャッシュは、データセットごとに特定のハードコードされた一連のルールに基づいて更新されました。キャッシュを更新する必要がある場合、server-ClientDataSet はプロバイダを使用して ADOQuery を介してデータベースからデータを取得し、TClientDataSet のバイナリ形式を使用してデータをアプリケーション サーバー ディスクに保存します。(サーバー インスタンス間のキャッシュ共有を有効にします)。

キャッシュを更新する時期であると判断したときに、異なるインスタンスが同時にデータベースから情報をプルするのを防ぐために、非常に基本的な同期方法が開発されました。「制御ファイル」は、データ検索操作中にディスク上に作成され、完了または失敗時に削除されます。データのプル操作が開始される前に、サーバー インスタンスはファイルの存在を確認します。存在する場合は、ファイルが存在しなくなるまで待機ループに入り、.cds 関連ファイル内の有効なデータを確認し、それに応じて動作します。ファイルが存在しない場合は、まったく同じミリ秒のケースをカバーして作成を試みます。

これは24 時間年中無休のアプリケーションではなく、12 時間 6 日のアプリケーションのようなものでした:D. この方法は非常に優れていることが証明されました。私はそのコードを維持していたほぼ 3 年間、この失礼な同期で 1 回も失敗したことを覚えていません..しかし、より堅牢なメカニズムを作成する必要があるかもしれません。

キャッシュを更新する必要がない場合、データはディスクから読み込まれます。

すべてのキャッシュ作業は、プロバイダー メソッドを使用して行われました。

したがって、関係は次のようになりました。

//
//     Client                    Server
//---------------    -----------------------------------------------------------------
//                                               Cache refresh?
//
//                                                   Yes
//                                                  ----- Provider --- ADOQuery - DB
// ClientDataSet ---- Provider --- ClientDataSet --|
//                                                  ----- LoadFromFile
//                                                   No
//
//

更新が必要かどうかのチェックと OpenDataSet の疑似コードは次のようになります。

function CacheRequiresRefresh: Boolean
begin
  if not IsPresentLocalData then
    Result := True
  else if ControlRecordIsMoreRecent then
    Result := True
  else if SomeOtherCondition then
    Result := True
  else
    Result := False;
end;

function OpenDataSet;
begin
  repeat
    if CacheRequiresRefresh then
    begin
      if not ControlFilePresent then
        if CreateControlFile then
        begin
          ConnectCDSToProvider;
          CDS.Open;
        end
      else
        if ControlFilePresent then
          WaitUntilControlFileIsNotPresent
    end
    else
      CDS.LoadFromFile('filename.cds');
  until CDS.Active;
end;

私はもうコードにアクセスできません。確かにすべての詳細を思い出すことはできません。幸いなことに、現在のサーバーは非常に優れており、今これについて考える必要がないほど十分に高速です...メカニズムがどのように機能するかを説明したいと思います. 明確化またはさらに支援が必要な場合は、コメントしてください。

于 2010-10-26T19:29:44.857 に答える