Overview
このガイドでは、 Kotlinドライバーがレプリカセットに対して読み取りおよび書込み (write) 操作を実行する方法を変更するために、書込み保証 (write concern)、読み取り保証 (read concern)、 読み込み設定 (read preference) オプションを構成する方法を学習します。
読み取り設定と書込み設定の優先順位
次のレベルで、書込み保証、読み取り保証、読み込み設定(read preference)のオプションを設定できます。
クライアント(オーバーライドされない限り、すべての操作実行にデフォルトを設定します)
トランザクション
Database
コレクション
このリストは、オプション設定の優先順位の増加順も示しています。例、トランザクションに読み取り保証 (read concern)を設定すると、クライアントから継承された読み取り保証 (read concern)設定が上書きされます。
書込み保証 (write concern) 、読み取り保証 (read concern)、読み込み設定 (read preference)オプションを使用すると、レプリカセット内のデータの因果整合性と可用性をカスタマイズできます。これらのオプションの完全なリストについては、 MongoDBサーバーマニュアルの次のガイドを参照してください。
読み取り操作と書込み操作の設定
読み込み設定(読み込み設定 (read preference)を設定することで、ドライバーがレプリカセットメンバー間で読み取り操作をルーティングする方法を制御できます。 また、読み取りおよび書込み保証を設定して、ドライバーがレプリカセットに対する読み取りおよび書込み操作の確認を待機する方法も制御できます。
次のセクションでは、さまざまなレベルでこれらの読み取りと書込み設定を構成する方法を示します。
クライアント構成
この例では、MongoClientSettingsインスタンスを MongoClient.create() メソッドに渡すことで、MongoClientインスタンスの読み込み設定 (read preference)、読み取り保証 (read concern)) 、書込み保証 (write concern)を設定する方法を示しています。このコードは、次の設定を構成します。
secondary読み込み設定 (read preference): 読み取り操作は、 セカンダリレプリカセットメンバーからデータを取得します。LOCAL読み取り保証 (read concern) : 読み取り操作は、インスタンスの最新データを返しますが、そのデータがレプリカセットのノードの過半数に書き込まれたことを保証します。W2書込み保証 (write concern)) : プライマリレプリカセットノードと 1 つのセカンダリ ノードは、書込み (write)操作を確認する必要があります。
val settings = MongoClientSettings.builder() .applyConnectionString(ConnectionString("mongodb://localhost:27017/")) .readPreference(ReadPreference.secondary()) .readConcern(ReadConcern.LOCAL) .writeConcern(WriteConcern.W2) .build() val mongoClient = MongoClient.create(settings)
あるいは、接続 URI で読み取り設定と書込み設定を指定することもできます。これは MongoClient.create() メソッドのパラメーターとして渡されます。
val uri = "mongodb://localhost:27017/?readPreference=secondary&w=2&readConcernLevel=local" val uriClient = MongoClient.create(uri)
トランザクション構成
この例では、 TransactionOptionsインスタンスをstartTransaction() メソッドに渡すことで、トランザクションの 読み込み設定(読み込み設定 (read preference)、読み取り保証 (read concern)、書込み保証 (write concern)を設定する方法を示しています。トランザクションは セッション 内で実行されます。これは、順番に実行されるよう関連付けられた読み取り操作または書込み操作のグループです。
Tip
セッションの詳細については、 MongoDBサーバーマニュアルのサーバー セッションを参照してください。
この例では、次の設定を構成しています。
primary読み込み設定 (read preference): 読み取り操作は、 プライマリレプリカセットメンバーからデータを取得します。MAJORITY読み取り保証 (read concern) : 読み取り操作は、レプリカセットノードの過半数に書き込まれたインスタンスの最新データを返します。W1書込み保証 (write concern)) : プライマリレプリカセットノードは書込み (write)操作を確認する必要があります。
mongoClient.startSession().use { session -> try { // Sets transaction read and write settings val txnOptions = TransactionOptions.builder() .readPreference(ReadPreference.primary()) .readConcern(ReadConcern.MAJORITY) .writeConcern(WriteConcern.W1) .build() runBlocking { session.startTransaction(txnOptions) // Specify transaction operations here session.commitTransaction() } } catch (e: Exception) { println("Transaction failed: ${e.message}") } }
データベース構成
この例では、セッター メソッドを getDatabase() メソッドに連鎖させることで、test_database というデータベースの読み込み設定(読み込み設定 (read preference)、読み取り保証 (read concern)、書込み保証 (write concern)を設定する方法を示しています。 このコードは、次の設定を構成します。
primaryPreferred読み込み設定 (read preference): 読み取り操作は、プライマリレプリカセットメンバーからデータを取得します。プライマリが使用できない場合は セカンダリ メンバーからデータが取得されます。AVAILABLE読み取り保証 (read concern) : 読み取り操作は、インスタンスの最新データを返しますが、そのデータがレプリカセットのノードの過半数に書き込まれたことを保証します。MAJORITY書込み保証 (write concern) ) : すべてのレプリカセットのノードの過半数が書込み (write)操作を確認する必要があります。
val database = mongoClient.getDatabase("test_database") .withReadPreference(ReadPreference.primaryPreferred()) .withReadConcern(ReadConcern.AVAILABLE) .withWriteConcern(WriteConcern.MAJORITY)
コレクション構成
この例では、セッター メソッドを getCollection() メソッドに連鎖させることで、test_collection というコレクションの読み込み設定(読み込み設定 (read preference)、読み取り保証 (read concern)、書込み保証 (write concern)を設定する方法を示しています。 このコードは、次の設定を構成します。
secondaryPreferred読み込み設定 (read preference): 読み取り操作は、セカンダリレプリカセットメンバーからデータを取得します。セカンダリ メンバーが使用できない場合は、プライマリ メンバーからデータが取得されます。AVAILABLE読み取り保証 (read concern) : 読み取り操作は、インスタンスの最新データを返しますが、そのデータがレプリカセットのノードの過半数に書き込まれたことを保証します。UNACKNOWLEDGED書込み保証 (write concern)) : レプリカセット ノードは書込み (write)操作を確認する必要はありません。
val collection = database.getCollection<Document>("test_collection") .withReadPreference(ReadPreference.secondaryPreferred()) .withReadConcern(ReadConcern.AVAILABLE) .withWriteConcern(WriteConcern.UNACKNOWLEDGED)
高度な読み取り構成
次のセクションでは、 Kotlinドライバーが読み取り操作をルーティングする方法をさらにカスタマイズする方法について説明します。
シャーディングされたクラスター
シャーディングされたクラスターに接続する 際に、読み込み設定 (read preference)を指定できます。MongoDB はシャーディングを使用して、データセットをキー範囲ごとに分割し、複数のデータベースインスタンスにデータを分散します。シャーディングされたクラスター、またはシャーディングされた配置内のノードのセットには、次のコンポーネントが含まれます。
シャード : シャーディングされたデータのサブセットを含むレプリカセット。
Mongos :アプリケーションとシャーディングされたクラスター間のインターフェースを提供するクエリ ルーター。
コンフィギュレーションサーバー : クラスターの構成設定とメタデータを保存するサーバー。
Tip
シャーディングされたクラスターの詳細については、 MongoDBサーバーマニュアルの「 シャーディング 」を参照してください。
レプリカセットシャードから読み取る場合、mongos は指定された読み込み設定 (read preference)を適用します。読み込み設定 (read preference)は、操作ごとに再評価されます。
次の例は、シャーディングされたクラスターに接続し、接続文字列で secondary読み込み設定 (read preference)を指定する方法を示しています。
val shardedClient = MongoClient.create( "mongodb://user:password@mongos1.example.com,mongos2.example.com/?readPreference=secondary" )
タグセット
MongoDBサーバーでは、選択した任意の基準に従ってレプリカセットメンバーにキーと値のタグを適用できます。次に、それらのタグを使用して、1 つ以上のノードを 読み取り操作の対象にすることができます。
デフォルトでは 、 Kotlinドライバーは 、読み取り元のノードを選択するときに タグ付けを無視します。Kotlinドライバーに特定のタグを優先するように指示するには、タグをリストとして読み込み設定 (read preference) セッター メソッドに渡します。
米国の複数のデータセンターでホストされているノードを含むレプリカセットに接続しているとします。 ドライバーが次の順序でセカンダリレプリカセットメンバーからの読み取りを優先するようにします。
タグ付けされた ニューヨークデータセンターのメンバー
("dc", "ny")サンフランシスコデータセンターのメンバー( でタグ付け)
("dc", "sf")セカンダリ ノード
このコード例では、前述のレプリカセットメンバーを表すタグのリストを ReadPreference.secondary() セッター メソッドに渡します。 次に、コードは読み込み設定 (read preference)情報を withReadPreference() メソッドに渡して、データベースに読み取り順序を設定します。
val tag1 = TagSet(Tag("dc", "ny")) val tag2 = TagSet(Tag("dc", "sf")) val tag3 = TagSet() // Empty tag set as fallback val readPref = ReadPreference.secondary(listOf(tag1, tag2, tag3)) val taggedDb = mongoClient.getDatabase("test_database") .withReadPreference(readPref)
ロード バランシング
シャーディングされたクラスターまたはレプリカセットに接続すると、 Kotlinドライバーは負荷分散を使用して読み取りおよび書込みリクエストを処理します。負荷分散により、ドライバーはこれらのリクエストを複数のサーバーに分散できるため、1 つのサーバーが過負荷になるのを回避し、最適なパフォーマンスを確保します。
When connecting to a sharded cluster, the Kotlin driver determines the closest mongos instance by calculating which one has the lowest network round-trip time. Then, the driver determines the latency window by adding this mongos's average round-trip time to the localThresholdMS value. The driver load balances requests across up to two random mongos instances that fall within the latency window. For each request, the driver chooses the server with the lower operation load by determining its operationCount value.
レプリカセットに接続すると、 Kotlinドライバーはまず読み込み設定 (read preference)に従ってレプリカセットメンバーを選択します。その後、ドライバーは前のセクションで説明したのと同じプロセスに従います。レイテンシウィンドウを計算した後、ドライバーはウィンドウ内にあるランダムなレプリカセットノードを最大 2 つ選択し、operationCount 値が低いノードを選択してリクエストを受信します。
Tip
負荷分散の詳細については、 MongoDBサーバーマニュアルのクラスターのバランサーを参照してください。
LocalThreshold
Kotlinドライバーはローカルしきい値を使用して、サーバー選択のレイテンシウィンドウを計算します。この値により、読み取りリクエストと書き込みリクエストを受信する資格のあるサーバーが決まります。
When connecting to a replica set with a non-primary read preference, the driver reads from the nearest eligible replica set member within the latency window. When connecting to a sharded cluster, the driver selects from all reachable mongos instances within the latency window. To learn about read preference modes, see Read Preference.
デフォルトで、ドライバーは最も近い適格なサーバーの ping 時間が 15 ミリ秒以内であるサーバーのみを使用します。
例えば、レプリカセットに 5 つのノードがあり、最も近いノードの ping 時間が 5 ミリ秒であるとします。デフォルトの localThresholdMS が 15 ミリ秒の場合、次の表に示すように、ping 時間が 20 ミリ秒以下のノードのみがレイテンシ ウィンドウ内にあります。
Host | タイプ | ping 時間 | レイテンシ ウィンドウ内 |
|---|---|---|---|
| 原発 | 5ミリ秒 | はい |
| セカンダリ | 9ミリ秒 | はい |
| セカンダリ | 13ミリ秒 | はい |
| セカンダリ | 24ミリ秒 | No |
| セカンダリ | 42ミリ秒 | No |
レイテンシ ウィンドウを調整するには、MongoClientSettings インスタンスで localThreshold オプションを設定するか、接続 URI で localThresholdMS オプションを設定します。
注意
単一の mongosインスタンスからレプリカセットメンバーを選択する場合、 Kotlinドライバーは localThresholdMS オプションを無視します。この場合は、localThreshold コマンドライン オプション を使用します。
次の例ではレプリカセットに接続し、35 ミリ秒のローカルしきい値を指定しています。各アプローチに対応するコードを確認するには、MongoClientSettings タブまたは Connection URIタブを選択します。
val latencySettings = MongoClientSettings.builder() .applyConnectionString(ConnectionString("mongodb://localhost:27017/")) .applyToClusterSettings { builder -> builder.localThreshold(35, TimeUnit.MILLISECONDS) } .build() val latencyClient2 = MongoClient.create(latencySettings)
val latencyClient1 = MongoClient.create( "mongodb://localhost:27017/?replicaSet=repl0&localThresholdMS=35" )
前の例では、 Kotlinドライバーは、最も近いノードのping時間の 35 ミリ秒以内に、一致するノードに読み取りを分散します。
再試行可能な読み取りと書込み
Kotlinドライバーは、ネットワークまたはサーバーエラーにより失敗した場合、特定の読み取りおよび書き込み操作を 1 回自動的に再試行します。
MongoClientSettingsインスタンスで retryReads または retryWrites オプションを false に設定することで、再試行可能な読み取りまたは再試行可能な書込みを明示的に無効にすることができます。接続 URI で retryReads または retryWrites オプションを設定することもできます。
次の例では、再試行可能な読み取りと再試行可能な書込みの両方を false に設定しています。各アプローチに対応するコードを確認するには、MongoClientSettings タブまたは Connection URIタブを選択します。
val retrySettings = MongoClientSettings.builder() .applyConnectionString(ConnectionString("mongodb://localhost:27017/")) .retryReads(false) // Disables automatic retries of read operations .retryWrites(false) // Disables automatic retries of write operations .build() val retryClient = MongoClient.create(retrySettings)
val retryUri = "mongodb://localhost:27017/?retryReads=false&retryWrites=false" val retryUriClient = MongoClient.create(retryUri)
サポートされている再試行可能な読み取り操作の詳細については、 MongoDBサーバーマニュアルの「 再試行可能な読み取り 」を参照してください。サポートされている再試行可能な書き込み操作の詳細については、 MongoDBサーバーマニュアルの「再試行可能な書き込み」を参照してください。
API ドキュメント
このガイドで説明したメソッドや型の詳細については、次の API ドキュメントを参照してください。