倍数の同時を許可するPHP用のドキュメントストア。これは、新しいサービスをインストールするオーバーヘッドなしで、MongoDBまたはCouchDBに代わるミニマリストの代替品です。
また、小さなフットプリントデータベースとしても機能します。
平均して、SMBは月に100個の請求書を生成します。したがって、SMBが10年あたり12000件の請求書を生成するとしましょう。
顧客を使用した12000の請求書の生成、詳細(詳細あたり約1〜5行)、およびI7/SSD/16GB/Windows 64bitsの日付をテストします。

100の同時テスト(書き込みと読み取り)を含むテスト、10回。
| n° | 読みます | (MS) | 読みます | エラー |
|---|---|---|---|---|
| 1 | 100 | 7471 | 100 | 0 |
| 2 | 100 | 7751 | 100 | 0 |
| 3 | 100 | 7490 | 100 | 0 |
| 4 | 100 | 7480 | 100 | 0 |
| 5 | 100 | 8199 | 100 | 0 |
| 6 | 100 | 7451 | 100 | 0 |
| 7 | 100 | 7476 | 100 | 0 |
| 8 | 100 | 7244 | 100 | 0 |
| 9 | 100 | 7573 | 100 | 0 |
| 10 | 100 | 7818 | 100 | 0 |
include " lib/DocumentStoreOne.php " ;
use eftec DocumentStoreOne DocumentStoreOne ;
try {
$ flatcon = new DocumentStoreOne ( " base " , ' tmp ' );
// or you could use:
// $flatcon = new DocumentStoreOne(__DIR__ . "/base", 'tmp');
} catch ( Exception $ e ) {
die ( " Unable to create document store. Please, check the folder " );
}
$ flatcon -> insertOrUpdate ( " somekey1 " , json_encode ( array ( " a1 " => ' hello ' , " a2 " => ' world ' ))); // or you could use serialize/igbinary_serialize
$ doc = $ flatcon -> get ( " somekey1 " );
$ listKeys = $ flatcon -> select ();
$ flatcon -> delete ( " somekey1 " ); include " lib/DocumentStoreOne.php " ;
use eftec DocumentStoreOne DocumentStoreOne ;
$ doc = new DocumentStoreOne ( " base " , " task " , ' folder ' );
//also: $doc=new DocumentStoreOne(__DIR__."/base","task",'folder');
$ doc -> serializeStrategy = ' php ' ; // it sets the strategy of serialization to php
$ doc -> autoSerialize ( true ); // autoserialize
$ flatcon -> insertOrUpdate ( " somekey1 " , array ( " a1 " => ' hello ' , " a2 " => ' world ' )); DocumentStoreOneインスタンスを作成します。
| 戦略 | タイプ | サーバ | ベンチマーク |
|---|---|---|---|
| dso_auto | 利用可能な最良の戦略を設定します(デフォルト) | 依存します | - |
| dso_folder | ドキュメントのロック/ロックを解除するためにフォルダーを使用します | - | 0.3247 |
| DSO_APCU | ドキュメントのロック/ロックを解除するためにAPCUを使用します | - | 0.1480 |
| dso_redis | ドキュメントのロック/ロックを解除するためにRedisを使用します | LocalHost:6379 | 2.5403(最悪) |
| dso_none | ドキュメントをロック/ロック解除するために何も使用しません。それは最速の方法ですが、複数のユーザーにとっては安全ではありません | 0 |
| 戦略 | タイプ |
|---|---|
| Php | serialize()関数を使用してシリアル化します |
| php_array | include()/var_export()関数を使用してシリアル化します。結果がPHPコードファイルであるため、結果はOpcacheでキャッシュされる可能性があります。 |
| json_object | JSONを使用して(オブジェクトとして)シリアル化されています |
| json_array | JSON(アレイとして)を使用してシリアル化されています |
| CSV | CSVファイルを使用してシリアル化します。 |
| igbinary | Igbinaryファイルを使用してシリアル化します。 |
| なし(デフォルト値) | シリアル化されていません。情報は、手動でシリアル化/シリアル化する必要があります |
例:
$ flatcon = new DocumentStoreOne ( __DIR__ . " /base " ); // new instance, using the folder /base, without serialization and with the default data
$ flatcon = new DocumentStoreOne ( __DIR__ . " /base " , '' , ' auto ' , '' , ' php_array ' ); // new instance and serializing using php_arrayベンチマーク100のインサートを追加するのにかかる時間(秒単位)。
use eftec DocumentStoreOne DocumentStoreOne ;
include " lib/DocumentStoreOne.php " ;
try {
$ flatcon = new DocumentStoreOne ( __DIR__ . " /base " , ' tmp ' );
} catch ( Exception $ e ) {
die ( " Unable to create document store. " . $ e -> getMessage ());
} use eftec DocumentStoreOne DocumentStoreOne ;
include " lib/DocumentStoreOne.php " ;
try {
$ flatcon = new DocumentStoreOne ( " /base " , ' tmp ' ,DocumentStoreOne:: DSO_APCU );
} catch ( Exception $ e ) {
die ( " Unable to create document store. " . $ e -> getMessage ());
}コレクションが有効な場合はtrueを返します(サブフォルダー)。
$ ok = $ flatcon -> isCollection ( ' tmp ' );現在のコレクションを設定します
$ flatcon -> collection ( ' newcollection ' ); // it sets a collection.このコマンドはネストできます。
$ flatcon -> collection ( ' newcollection ' )-> select (); // it sets and return a queryコレクションが正しいか存在するかは検証されていないか、注意していません。 ISCollection()を使用して、それが正しいかどうかを確認する必要があります。
情報を自動化するかどうかを設定し、それがどのようにシリアル化されているかを設定します。コンストラクターを使用して設定することもできます。
| 戦略 | タイプ |
|---|---|
| Php | serialize()関数を使用してシリアル化します。 |
| php_array | include()/var_export()関数を使用してシリアル化します。結果がPHPファイルになるため、結果はopcacheでキャッシュされる可能性があります |
| json_object | JSONを使用して(オブジェクトとして)シリアル化されています |
| json_array | JSON(アレイとして)を使用してシリアル化されています |
| CSV | CSVファイルを使用してシリアル化します。 |
| igbinary | Igbinaryファイルを使用してシリアル化します。 |
| なし(デフォルト値) | シリアル化されていません。情報は、手動でシリアル化/シリアル化する必要があります |
コレクション(ベースフォルダー内の新しいフォルダー)を作成します。操作が故障した場合にfalseを返します。それ以外の場合、それは真実に戻ります
$ flatcon -> createCollection ( ' newcollection ' );
$ flatcon -> createCollection ( ' /folder1/folder2 ' ); 示されている$ IDに新しいドキュメント(文字列)を挿入します。ドキュメントが存在する場合、更新されます。
$ triesは、試行回数を示します。デフォルト値は-1(デフォルトの試行回数)です。
// if we are not using auto serialization
$ doc = json_encode ([ " a1 " => ' hello ' , " a2 " => ' world ' ]);
$ flatcon -> insertOrUpdate ( " 1 " , $ doc ); // it will create a document called 1.dson in the base folder.
// if we are using auto serialization
$ flatcon -> insertOrUpdate ( " 1 " ,[ " a1 " => ' hello ' , " a2 " => ' world ' ]);ドキュメントがロックされている場合、それが利用可能になるまでまたは「NTH」数のトライの後に取得します(デフォルトでは10秒に相当する100トライです)
挿入や更新よりも速いです。
示されている$ IDに新しいドキュメント(文字列)を挿入します。ドキュメントが存在する場合、falseを返します。
$ triesは、試行回数を示します。デフォルト値は-1(デフォルトの試行回数)です。
// if we are not using auto serialization
$ doc = json_encode ( array ( " a1 " => ' hello ' , " a2 " => ' world ' ));
$ flatcon -> insert ( " 1 " , $ doc );
// if we are using auto serialization
$ flatcon -> insert ( " 1 " ,[ " a1 " => ' hello ' , " a2 " => ' world ' ]);ドキュメントがロックされている場合、それが利用可能になるまでまたは「NTH」数のトライの後に取得します(デフォルトでは10秒に相当する100トライです)
表示されている$ IDでドキュメント(文字列)を更新します。ドキュメントが存在しない場合、falseを返します
$ triesは、試行回数を示します。デフォルト値は-1(デフォルトの試行回数)です。
// if we are not using auto serialization
$ doc = json_encode ([ " a1 " => ' hello ' , " a2 " => ' world ' ]);
$ flatcon -> update ( " 1 " , $ doc );
// if we are using auto serialization
$ flatcon -> update ( " 1 " ,[ " a1 " => ' hello ' , " a2 " => ' world ' ]);ドキュメントがロックされている場合、それが利用可能になるまで、または「n番目の」数のトライの後に取得します(デフォルトでは100回の試行です10秒に相当します)
ドキュメント$ IDを読み取ります。ドキュメントが存在しない場合、または読み取れない場合、falseを返します。
$ triesは、試行回数を示します。デフォルト値は-1(デフォルトの試行回数)です。
$ doc = $ flatcon -> get ( " 1 " ); // the default value is false
$ doc = $ flatcon -> get ( " 1 " ,- 1 , ' empty ' );ドキュメントがロックされている場合、それが利用可能になるまでまたは「NTH」数のトライの後に取得します(デフォルトでは10秒に相当する100トライです)
ドキュメント$ IDフィルタリングを読み取ります。ドキュメントが存在しない場合、または読み取れない場合、falseを返します。
$ triesは、試行回数を示します。デフォルト値は-1(デフォルトの試行回数)です。
// data in rows [['id'=>1,'cat'=>'vip'],['id'=>2,'cat'=>'vip'],['id'=>3,'cat'=>'normal']];
$ data = $ this -> getFiltered ( ' rows ' ,- 1 , false ,[ ' cat ' => ' normal ' ]); // [['id'=>3,'cat'=>'normal']]
$ data = $ this -> getFiltered ( ' rows ' ,- 1 , false ,[ ' type ' => ' busy ' ], false ); // [2=>['id'=>3,'cat'=>'normal']]ドキュメントがロックされている場合、それが利用可能になるまでまたは「NTH」数のトライの後に取得します(デフォルトでは10秒に相当する100トライです)
$ nameという名前のドキュメントに値を追加します。新しい値が追加されるため、ドキュメント全体を作成することは避けてください。たとえば、ログファイルに役立ちます。
a)値が存在しない場合、$ addvalueで作成されます。それ以外の場合は、trueを返します
b)値が存在する場合、 $ addvalueが追加され、trueが返されます
c)それ以外の場合、falseを返します
$ seq = $ flatcon -> appendValue ( " log " , date ( ' c ' ). " new log " );新しいシーケンスを読み取りまたは生成します。
a)シーケンスが存在する場合、 $間隔で増加し、この値が返されます。
b)シーケンスが存在しない場合、 $ initで作成され、この値は返されます。 c)ライブラリがシーケンスを作成できない場合、ロックできない、またはシーケンスが存在するが、読み取れない場合、falseを返します
$ seq = $ flatcon -> getNextSequence ();$ id = get( 'genseq_')でシーケンスを覗くことはできますが、推奨されません。
シーケンスが破損している場合、$ initにリセットされます
シーケンスのリストを予約する必要がある場合は、 $ ReserveAdditionalを使用できます
$ seq = $ flatcon -> getNextSequence ( " seq " ,- 1 , 1 , 1 , 100 ); // if $seq=1, then it's reserved up to the 101. The next value will be 102.時間、ランダム値、サーバーIDに基づいて、一意のシーケンス(64bit整数)を返します。
衝突の可能性(同じ値の世代)は1/4095(0.0001秒ごとに実行される2つの操作ごと)です。
$ this -> nodeId = 1 ; // if it is not set then it uses a random value each time.
$ unique = $ flatcon -> getSequencePHP (); ドキュメント$ IDが存在するかどうかを確認します。ドキュメントが存在する場合はtrueを返します。それ以外の場合、それはfalseを返します。
$ triesは、試行回数を示します。デフォルト値は-1(デフォルトの試行数)です。
検証は、ドキュメントが完全にロック解除されている場合にのみ発生します。
$ found = $ flatcon -> ifExist ( " 1 " );ドキュメントがロックされている場合、それが利用可能になるまで、または「n番目の」数のトライの後に取得します(デフォルトでは100回の試行です10秒に相当します)
ドキュメント$ IDを削除します。ドキュメントが存在しない場合、または削除できない場合、falseを返します。
$ triesは、試行回数を示します。デフォルト値は-1(デフォルトの試行数)です。
$ doc = $ flatcon -> delete ( " 1 " );ドキュメントがロックされている場合、それが利用可能になるまで、または「n番目の」数のトライの後に取得します(デフォルトでは100回の試行です10秒に相当します)
コレクションに保存されているすべてのIDを返します。
$ listKeys = $ flatcon -> select ();
$ listKeys = $ flatcon -> select ( " invoice_* " );ロックされたドキュメントが含まれています。
$ iddestinationでドキュメント$ idoriginをコピーします
$ bool = $ flatcon -> copy ( 20 , 30 );ドキュメントの宛先が存在する場合、その交換が行われます
ドキュメント$ idoriginの名前を$ iddestinationに変更します
$ bool = $ flatcon -> rename ( 20 , 30 );ドキュメントの宛先が存在する場合、操作に失敗します。
STDCLASSを特定のクラスに変換します。
$ inv = new Invoice ();
$ invTmp = $ doc -> get ( ' someid ' ); //$invTmp is a stdClass();
DocumentStoreOne:: fixCast ( $ inv , $ invTmp ); オブジェクトの配列であるメンバーでは機能しません。配列はstdclassとして保持されます。
次のフィールドは公開されており、ランタイム中に変更される可能性があります
| 分野 | タイプ |
|---|---|
| $データベース | データベースの文字列ルートフォルダー |
| $コレクション | データベースの文字列電流コレクション(サブフォルダー) |
| $ maxlocktime = 120 | ロックのint maximium持続時間(秒単位)。デフォルトでは2分です |
| $ DefaultNumretry = 100 | intデフォルトのretriries数。デフォルトでは、100x0.1sec = 10秒を試みます |
| $ intervalbetweenretry = 100000 | retiries間のint間隔(マイクロ秒単位)。 100000は0.1秒を意味します |
| $ docext = "。dson" | 文書の文字列デフォルト拡張子(DOTを使用) |
| $ keyEncryption = "" | 文字列は、キーが保存されているときに暗号化されているかどうかを示します(ファイル名)。空の意味、暗号化なし。 MD5、SHA1、SHA256を使用できます。 |
例:
$ ds = new DocumentStoreOne ();
$ ds -> maxLockTime = 300 ; $ ds = new DocumentStoreOne ();
$ ds -> insert ( ' 1 ' , ' hello ' ); // it stores the document 1.dson
$ ds -> keyEncryption = ' SHA256 ' ;
$ ds -> insert ( ' 1 ' , ' hello ' ); // it stores the document 6b86b273ff34fce19d6b804eff5a3f5747ada4eaa22f1d49c01e52ddb7875b4b.dson 手動で行うことができます。このシステムにより、(すべての値を読み取る代わりに)簡単にアクセスできる事前に計算された値を保存できます。
次の演習では、購入のリストがあります
| id | お客様 | 年 | セックス | 製品購入 | 額 |
|---|---|---|---|---|---|
| 14 | ジョン | 33 | m | 33 | 3 |
| 25 | アンナ | 22 | f | 32 | 1 |
| 製品コード | 単価 |
|---|---|
| 32 | 23.3 |
| 33 | 30 |
ジョンはコード33で3つの製品を購入しました。製品33はユニットあたり23.3ドルです。
質問、すべての顧客がいくら支払ったのですか?
これは簡単なエクササイズであり、リレーショナルデータベース(Select * From Purchases Inner Joing製品)により適しています。ただし、ドキュメントがデータベースに保存するのに長いか複雑な場合は、ドキュメントストアが輝く場所です。
// 1) open the store
$ ds = new DocumentStoreOne ( ' base ' , ' purchases ' ); // we open the document store and selected the collection purchase.
$ ds -> autoSerialize ( true , ' auto ' );
// 2) reading all products
// if the list of products holds in memory then, we could store the whole list in a single document (listproducts key)
$ products = $ ds -> collection ( ' products ' )-> get ( ' listproducts ' );
// 3) we read the keys of every purchases. It could be slow and it should be a limited set (<100k rows)
$ purchases = $ ds -> collection ( ' purchases ' )-> select (); // they are keys such as 14,15...
$ customerXPurchase =[];
// 4) We read every purchase. It is also slow. Then we merge the result and obtained the final result
foreach ( $ purchases as $ k ) {
$ purchase = $ ds -> get ( $ k );
@ $ customerXPurchase [ $ purchase -> customer ]+=( $ purchase -> amount * @ $ products [ $ purchase -> productpurchase ]); // we add the amount
}
// 5) Finally, we store the result.
$ ds -> collection ( ' total ' )-> insertOrUpdate ( $ customerXPurchase , ' customerXPurchase ' ); // we store the result.| お客様 | 価値 |
|---|---|
| ジョン | 69.9 |
| アンナ | 30 |
コードで行われているので、ハイブリッドシステム(リレーショナルデータベース+ストア+メモリキャッシュ)を作成することが可能です
次の情報をシリアル化したいとしましょう。
$ input =[[ ' a1 ' => 1 , ' a2 ' => ' a ' ],[ ' a1 ' => 2 , ' a2 ' => ' b ' ]];値はシリアル化されていないため、オブジェクト、配列、またはその他の構造をシリアル化することはできません。文字列でのみ動作します。
値の保存方法
helloworld
値がどのように返されるか
" helloworld " PHPのシリアル化は、シリアル化とシリアル化のより速い方法の1つであり、常に同じ構造(クラス、配列、フィールド)で同じ値を返します。
ただし、保存された値は長い場合があります。
値の保存方法:
a:2:{i:0;a:2:{s:2:"a1";i:1;s:2:"a2";s:1:"a";}i:1;a:2:{s:2:"a1";i:2;s:2:"a2";s:1:"b";}}
値がどのように返されるか:
[['a1'=>1,'a2'=>'a'],['a1'=>2,'a2'=>'b']]
このシリアル化により、PHPコードが生成されます。このコードは冗長ですが、いくつかの素晴らしい機能があります。
値の保存方法:
<?php /** @generated */
return array (
0 =>
array (
' a1 ' => 1 ,
' a2 ' => ' a ' ,
),
1 =>
array (
' a1 ' => 2 ,
' a2 ' => ' b ' ,
),
);値がどのように返されるか:
[['a1'=>1,'a2'=>'a'],['a1'=>2,'a2'=>'b']]
両方の方法は、シリアル化とシリアル化のためにJSONと連携しますが、最初のリターンは常に連想配列でしたが、もう一方はオブジェクト(stdclass)を返すことができます
プロ:
短所:
値の保存方法:
[{"a1":1,"a2":"a"},{"a1":2,"a2":"b"}]
値がどのように返されるか:
[[ ' a1 ' => 1 , ' a2 ' => ' a ' ],[ ' a1 ' => 2 , ' a2 ' => ' b ' ]] // array
[stdClass{ ' a1 ' => 1 ,'a2'=>'a'},stdClass{ ' a1 ' => 2 ,'a2'=>'b'}] // objectデフォルトでは、このライブラリはエラーまたは例外が発生したときにエラーをスローします。いくつかの方法では、エラーのスローを避けることができますが、それらのほとんどはエラーを投げる可能性があります。
エラーは、キャッチアブルを試す/キャッチすることです。
// throw an error:
$ this -> throwable = true ; // (default value is true) If false, then the errors are stored in $this->latestError
try {
$ this -> insert ( ' id1 ' , ' values ' );
} catch ( $ ex ) {
var_dump ( $ ex );
} // not throw an error:
$ this -> throwable = false ;
$ this -> insert ( ' id1 ' , ' values ' );
if ( $ this -> latestError ) {
var_dump ( $ this -> latestError );
}
$ this -> resetError ();または、例外のスローを避けるためにも使用することもできます。
// not throw an error:
$ this ->-> noThrowOnError ()-> insert ( ' id1 ' , ' values ' );
// but you can still see the latest error:
if ( $ this -> latestError ) {
var_dump ( $ this -> latestError );
}次のようにCSVを使用できます。
$ doc = new DocumentStoreOne ( __DIR__ . " /base " , '' , ' none ' , '' , ' csv ' ); // set your strategy to csv.
$ doc -> docExt = ' .csv ' ; // (optional), you can set the extension of the document
$ doc -> csvPrefixColumn = ' col_ ' ; // (optional), you can set the name of the columns (if the csv doesn't have columns)
$ doc -> csvStyle (); // (optional) not needing, but you can use to set your own specifications of csv, for example tab-separated, etc.
$ doc -> regionalStyle (); // (optional) not needing, but you can use to set your own regional settings.
$ values =[
[ ' name ' => ' john1 ' , ' age ' => 22 ],
[ ' name ' => ' john2 ' , ' age ' => 22 ],
[ ' name ' => ' john3 ' , ' age ' => 22 ],
];
$ doc -> delete ( ' csv1 ' );
$ doc -> insert ( ' csv1 ' , $ values );[runtimeexception]は、repo.packagist.orgにパッケージをパッケージにロードできませんでした。 :無効なバージョン文字列「^5.6」。