パートI. InterSystems GlobalsDB .Net-内部でのピアリングとの戦闘における偵察

画像

最後に、「Microsoft .NetにはInterSystems GlobalsDB /CachéExtremeがありますか?」という質問を説得するのではなく、もう少し待ちます。 Caché2012.2(フィールドテスト)の新しいバージョンとGlobalsDB v2012.296は、このプラットフォームのサポートを導入しました。

6分の1の寿司スタイルで、多くの開発者に人気のスタイル、つまり、 インストールノートなどを読むことなく、実際にWindowsのGlobalsDBディストリビューションを表すものを探ります。



Windowsおよび.Netのディストリビューションをダウンロードします。 globals_setup_2012.296.exeのサイズは25メガバイトです。 InstallShieldインストーラーが起動します。 Windows 7x64では管理者モードで起動せず、Mac OS XではVMWare Fusionで動作しました。



インストールは予測可能でした。ホームディレクトリとしてC:\ usr \ isc \ globalsを指定しました。 実験の純度を高めるために、このOSにはすでにCachéがあると言わなければなりません。



私は何が設定されたかを勉強します。 \ usr \ isc \ globalsには、bin、dev、mgr-標準のCaché構造の3つのフォルダがあります。 バイナリとDBMS自体はbin、mgrにあります-構成ファイルとデータベースファイル、さらに重要なことにシステムログ、この場合はglobalsdb.log



\ Dev-開発者向けのさまざまなツールを含むフォルダー。 興味があるのは、ビン、ヘルプ、サンプルで構成される\ Dev \ dotnetです。 In。\ Binには、InterSystems.GlobalsDBのアセンブリがあります。サンプルでは、​​javadocsのchm類似物に気づくのに役立ちます-使用例が少ないVisual Studioプロジェクト。



プロジェクトを押します。 Visual Studio 10が起動し、プロジェクトを2008から独自の形式に変換し始めます-インターシステムズの開発者は、8のままです。Cachéの新しいリリースには、.Net 4のアセンブリが既にあります。稼いだ!



驚いたことに、GlobalsDB for Javaの場合、データベースを起動する必要がありました\ Bin \ globalsdb startおよびデータベースにアクセスするには、環境変数GLOBALS_HOMEおよびPATHを設定する必要がありました。



Sysinternals Process Explorerを使用して問題を調査しています。 Cから始まる6つのcache.exeプロセスが見つかりました:\ usr \ isc \ globalsdb(ところで、これはGLOBALS_HOMEの値です)。 起動したVisual Studioの環境を確認します。既にGLOBALS_HOMEとPATHに目的のパスがあります-%GLOBALS_HOME%\ bin。 Windowsサービスのリストを見ると、GlobalsDBサービスが見つかります。 一般的に、インストーラーはささいなことを処理しました-良い傾向です。 ちなみに、%GLOBALS_HOME%\ bin \ globalsdb start / stopコマンドを使用した開始/停止は、サービスの開始または停止と同等であり、その逆も同様です。



コンソールアプリケーションは動作しますが、この例はGlobalsDB開発者のテストセットである可能性が高く、.NetでのGlobalsDB APIメソッドのすべてのオーバーロードが動作することを系統的に検証しました。 したがって、APIを扱うために、独自の新しいプロジェクトを作成します。 同時に、GlobalsDBを取得するためにVSで何をする必要があるかを見てみましょう。



コンソールアプリケーション用の新しいプロジェクトを作成します。 %GLOBALS_HOME%\ dev \ dotnet \ binにあるInterSystems.GlobalsDBへの参照を追加します。 私の場合、これはアセンブリC:\ usr \ isc \ globals \ dev \ dotnet \ bin \ InterSystems.GlobalsDB.dllです。



using System; using System.Diagnostics; using InterSystems.Globals; namespace globals { class Program { static void Main(string[] args) { } } }
      
      







System.Diagnosticsを使用して速度を測定します。



次に、接続がどのように行われるかの例を見て、それをコードに転送します。



 static void Main(string[] args) { Connection connection = ConnectionContext.GetConnection() connection.Close(); Console.ReadLine(); }
      
      







始めます。 例外を取得する不正な形式のプログラムをロードしようとしました。 すべてが明確で、私のプロジェクトはデフォルトでx32でビルドされます。 プロジェクトの[プロパティ]-> [ビルド]に移動し、プラットフォームターゲットをx64に設定します。 立ち上げ-すべて順調です。



さあ、データベースに何かを書いてみてください。 これは、GlobalsDBグローバルと呼ばれるもの、またはフルネーム-グローバル変数、つまりグローバルCaché変数です。特定のデータベースプロセスのメモリにあるローカル変数とは異なり、ディスク上にあるため、すべてのデータベース接続にアクセスできます。 GlobalsDbでは、グローバルのみで作業できます。



誰もがそのpr落性のためにグローバルを認識しています-多次元変数と呼ばれる人もいれば、ツリーまたはキー値ストアと見なす人もいます。連想配列またはMultiMapとして表す方が私に近いです。 空想にふけっていない場合、グローバルはCachéのデータストレージのアトミック構造(たとえば、リレーショナルテーブルのアトミック構造はテーブル)であり、名前はノードと呼ばれる要素で構成されます。 各ノードは、添え字(インデックスまたはキーと呼ばれることが多い)と呼ばれる左側と、実際に格納されるデータ(単純型(数値、文字列)、または要素が再び単純型またはリストであるリスト)で構成されます。

グローバルの例(擬似コード)。



a。 これがキー値またはキーアクセスを持つコレクションだと思う人のために:



test(1) = “some text or number limited to 3641144 bytes”

test(“any string limited to 500 bytes”) = 3.14









b。 このツリーは次のとおりだと思う人のために:



test(1,”post”) = “root”

test(1,2,”post”) = “branch A”

test(1,3,”post”) = “branch B”








c。 空の添え字も添え字です。



test = 2







d。 リストを使用した表形式のデータストレージと同様:



orders(1)=list(1001,”20.12.2012”,3,,999.99)

orders(2)=list(1002,”04.12.2012”,4,,249.99)







次に、データをグローバルに保存してみましょう。 これを行うには、グローバル名を指定し、新しいグローバルノードを作成し、ノードの添え字(例からわかるようにキーまたはインデックス)とこのノードに格納されているデータを指定します。 グローバルノードを操作するために、GlobalsDB APIはNodeReferenceクラスのオブジェクトを使用します。 実際、これはグローバル内のあるノードへのポインターです。 ノードは下付き文字で識別されるため、NodeReferenceは下付き文字へのリンクであると想定できます。 最初はヘッドノードを指すグローバルへのリンクは、接続を介して取得します。



NodeReference testArray = connection.CreateNodeReference( "test"); //グローバル名はtest



最初に、単純なNodeReference.Set()メソッドを使用します。 一般化された形式では、NodeReference.Set(データ、添え字)として取得できます。したがって、実行後、この種類のデータベースにグローバルノードがあります。



globalName(添字)=データ



したがって、コードは次のようになります。



  static void Main(string[] args) { Connection connection = ConnectionContext.GetConnection(); NodeReference node = connection.CreateNodeReference("test"); node.Set("some text or number limited to 3641144 bytes",1); node.Set(3.14, "any string or primitive type or several values limited to 500 bytes"); connection.Close(); Console.ReadLine(); }
      
      





実施します。 例外が発生します:Connection.CreateNodeReference()を呼び出す前に接続する必要があります。 そうです、サンプルコードを見てください。ファクトリーではなく、自分で接続を確立する責任があります。 なぜそう 知りません ここで、接続に関するマルチスレッド作業に関連する問題があることに気付くことができます。今後、必要に応じてこれを覚えておくことが重要です。 接続確立を追加します。



if(!connection.IsConnected())connection.Connect();



今ではすべてが順調です。 GlobalsDB APIのヒントが機能することがわかります。 右に、多次元添え字と添え字とデータの制限値を操作する例を追加します。



  static void Main(string[] args) { Connection connection = ConnectionContext.GetConnection(); if (!connection.IsConnected()) connection.Connect(); NodeReference node = connection.CreateNodeReference("test"); node.Set("some text or number limited to 3641144 bytes",1); node.Set(3.14, "any string limited to 500 bytes"); node.Set("root",new object[2] {1,"post"}) ; node.Set("branch A",new object[3] {1,1,"post"}) ; node.Set("branch B",new object[3] {1,2,"post"}) ; node.Set(2); node.Close(); node = connection.CreateNodeReference("limit"); String longestKey = new String('k', 500); String longestValue = new String('v', 3641144); node.Set(longestValue, longestKey); connection.Close(); Console.ReadLine(); }
      
      







グローバルノードがデータベースに挿入されたことを確認する方法 NodeReference読み取りメソッドのいずれかを使用できます。 ただし、デバッグには、GlobalsDBには記載されていないが、Cachéを使用した人に馴染みのあるこの手法を使用できます(特にGlobalsDB配信には管理ユーティリティがないため)。 したがって、%GLOBALS_HOME%に移動し、コマンドラインで次の操作を行います。



 C:\usr\isc\globals\bin>cache -s ..\mgr -U Data DATA>_
      
      





その結果、データベースへのターミナルセッションを取得します。 これは何ですか これは、ターミナルモードで起動される標準のデータベースプロセスであり、 CachéObject Script言語でコマンドを実行できます データベースで動作する独立したプロセスは、アプリケーションサーバーとして使用できるようにするCachéの機能の1つです。たとえば、アプリケーションのユーザーコードが機能するプロセスを開始します。 GlobalsDBの場合、このプロセスは.Netコードが実行されるCLRプロセスになります。



作成されたノードを表示する方法は? これを行うために、write(省略形w)およびzwrite(zw)コマンドがあります。 例:



 DATA>zw ^test ^test=2 ^test(1)="some text or number limited to 3641144 bytes" ^test(1,1,"post")="branch A" ^test(1,2,"post")="branch B" ^test(1,"post")="root" ^test("any string limited to 500 bytes")=3.1400000000000001243
      
      





ノードまたはグローバル全体の削除-killコマンド(略称k):

 DATA>kill ^test
      
      





データ記録:



 DATA>s ^test(1,"name") = "Athens"
      
      





ループに挿入:

 DATA>for i=1:1:100 { s ^test(i) = i }
      
      







端末を終了するのは、haltコマンド(略称h)です。

 DATA>h C:\usr\isc\globals\bin>
      
      





時間測定:

 DATA>s st=$zh for i=1:1:100000 { s ^test(i)=i} w $zh-st,! .064444
      
      





次に、.Netおよびタイムスタンプから100,000エントリを挿入してみましょう。

  static public void testInserts(int loop) { Connection connection = ConnectionContext.GetConnection(); if (!connection.IsConnected()) connection.Connect(); NodeReference node = connection.CreateNodeReference("test"); node.Kill(); Stopwatch dbTimer = Stopwatch.StartNew(); for (int i = 0; i < loop; i++) { node.Set(i+" item", i); } dbTimer.Stop(); Console.WriteLine(dbTimer.ElapsedMilliseconds + " milliseconds to save " + loop + " items"); Console.WriteLine("It is " + dbTimer.Elapsed.Seconds + " seconds"); node.Close(); connection.Close(); }
      
      







一連のテストの結果:

 for (int i = 100000; i <= 1100000; i += 200000) testInserts(i); ConnectionContext.GetConnection().Close();
      
      







 C:\src\globals\globals\bin\Release>.\globals.exe 430 ms to save 100000 items. 232558 records/second 1223 ms to save 300000 items. 245298 records/second 1958 ms to save 500000 items. 255362 records/second 2754 ms to save 700000 items. 254175 records/second 3559 ms to save 900000 items. 252880 records/second 4436 ms to save 1100000 items. 247971 records/second
      
      





1秒あたり200,000件を超えるレコード。 これはすべて、ロギングを有効にしてトランザクション内で発生します。 一方、データは非常に模擬的です。 3番目の方法では、これは5メートルの空きディスク容量がある仮想マシンの下で発生します。 4番目の場合、このような速度では、すべてがレコードのサイズとキーのランダム性、トランザクションフローの強度、バッチでの処理能力、トランザクションの必要性など、詳細に大きく依存します。



開始するのに十分-GlobalsDBがインストールされ、プロジェクトが機能しており、速度に関する一般的な結論が出ています。

将来的には、グローバルノードを介したナビゲーションやノードトラバーサル操作などの重要なトピックを分析し、リスト、トランザクション、カウンター、ロックを操作します。 それとは別に、複数のスレッドを操作する場合のGlobalsDBの動作に関する興味深い質問を検討します。



All Articles