MongoDB: レプリケーション:高可用性アーキテクチャ

最終更新:2026-08-26

レプリカセットはMongoDB高可用性の要—習得すれば99.99%の可用性を持つ本番クラスターを構築できます。

1. 学習内容



2. レプリカセットアーキテクチャ

概念概要: レプリカセットはMongoDB高可用性アーキテクチャの基盤です。複数のmongodプロセスで構成—1つのPrimaryノード + N個のSecondaryノード + オプションのArbiterノード。Primaryノードは全ての書き込み操作を受け付け、oplog経由でSecondaryノードに非同期で複製し、データ冗長性と自動フェイルオーバーを実現します。

動作原理: Primaryは全ての書き込み操作をoplog(固定サイズのcappedコレクション)に記録し、Secondaryはoplogを追跡(tail)して書き込み操作を継続的に取得・再生し、Primaryとのデータ整合性を維持します。Primaryが障害発生すると、残りのノードが選挙プロトコル(Raftベース)で新しいPrimaryを選出し、アプリケーションは自動的に再接続し、99.99%の可用性を実現します。

Raftプロトコルと選挙メカニズム: MongoDBの選挙プロセスはRaftプロトコルの派生版に基づいており、コアルールは「過半数ルール」です—過半数以上のノードから票を獲得した候補だけがPrimaryになれます。これにより、任意の時点で最大1つのPrimaryが存在すること(スプリットブレイン防止)と、新しいPrimaryが最も完全なデータを持つことが保証されます。

100%
graph TB
    App[アプリケーション] --> P[Primary<br/>マスターノード<br/>全書き込みを受け付け]
    P -.oplog複製.-> S1[Secondary 1<br/>スレーブノード<br/>読み取り可能+バックアップ]
    P -.oplog複製.-> S2[Secondary 2<br/>スレーブノード<br/>読み取り可能+バックアップ]
    A[Arbiter<br/>調停ノード<br/>投票のみ]

    subgraph "データフロー"
        W[書き込み] --> P
        P -->|oplog| S1
        P -->|oplog| S2
    end

    subgraph "選挙"
        P -->|ハートビート| S1
        P -->|ハートビート| S2
        P -->|ハートビート| A
    end

    style P fill:#d4edda
    style S1 fill:#cce5ff
    style S2 fill:#cce5ff
    style A fill:#fff3cd

ノード役割の比較:

ノード 責務 データ保存 読み取り可能 選挙参加 優先度
Primary 全書き込み操作を受け付け デフォルト1(増加可能)
Secondary Primaryデータを複製 ✅(設定必要) デフォルト1
Arbiter 選挙投票のみ参加 0(選出不可)

レプリカセット vs 単一ノード:

項目 単一ノード レプリカセット
可用性 単一障害点 99.99%(自動フェイルオーバー)
データ安全性 ディスク障害=データ消失 マルチコピー冗長性
読み取り拡張 なし Secondary読み取り負荷分散
トランザクション対応 ✅(レプリカセット必要)
運用複雑さ 低い 中程度


3. レプリカセットの起動

概念説明: レプリカセットの起動は2ステップ:1) --replSetパラメータでmongodプロセスを起動、2) mongoshrs.initiate()を実行してレプリカセット設定を初期化。初期化時に全メンバーのアドレスを指定し、MongoDBが自動的にPrimaryを選出します。

動作原理: rs.initiate()はレプリカセット設定を各ノードのローカルデータベースに書き込み、選挙プロトコルをトリガーします。最初に初期化されたノードが通常Primaryになり、他のノードは自動的に設定を同期しoplog追跡を開始します。

BASH
# === 最初のノードを起動(レプリカセットモード)===
mongod --replSet rs0 --port 27017 --dbpath /data/db1 --bind_ip localhost

# === mongoshで初期化 ===
mongosh
> rs.initiate({
    _id: 'rs0',
    members: [
      { _id: 0, host: 'localhost:27017' },
      { _id: 1, host: 'localhost:27018' },
      { _id: 2, host: 'localhost:27019' }
    ]
  });

初期化設定パラメータ:

パラメータ 説明
_id レプリカセット名、--replSetと一致させる 'rs0'
members メンバー一覧 [{_id: 0, host: '...'}]
members._id メンバーID(一意) 0, 1, 2
members.host メンバーアドレス 'localhost:27017'
members.priority 選挙優先度(0 = 選出不可) デフォルト1
settings.electionTimeoutMillis ハートビートタイムアウト デフォルト10000ms


4. ノードの追加・削除

概念説明: レプリカセットはオンラインでのノード追加・削除をサポートし、サービス停止は不要です。ノード追加後、新ノードは自動的にPrimaryから初期同期(フル同期)を実行し、その後oplog追跡(増分同期)に切り替わります。

データ同期プロセス:

100%
sequenceDiagram
    participant New as 新規ノード
    participant P as Primary
    participant Oplog as oplog

    New->>P: レプリカセットへの参加リクエスト
    P-->>New: 確認 + 現在の設定

    Note over New,P: フェーズ1: 初期同期(フル同期)
    New->>P: 全データをリクエスト
    P-->>New: 全コレクションデータ + インデックス

    Note over New,P: フェーズ2: Oplog追跡(増分同期)
    loop 継続
        New->>Oplog: 最新oplogエントリを取得
        Oplog-->>New: 増分操作
        New->>New: oplog操作を再生
    end

    Note over New: 同期完了後、選挙に参加可能
操作 コマンド 説明
データノード追加 rs.add('host:port') 自動初期同期
調停ノード追加 rs.addArb('host:port') 投票のみ、データ保存なし
ノード削除 rs.remove('host:port') 自動ノード降格
ステータス確認 rs.status() 全ノードステータス + 健康
設定確認 rs.conf() レプリカセット設定詳細
JAVASCRIPT
// === 新規ノード追加 ===
rs.add('localhost:27020');

// === Arbiter追加(データ保存なし)===
rs.addArb('localhost:27021');

// === ノード削除 ===
rs.remove('localhost:27020');

// === レプリカセットステータス確認 ===
rs.status();

ポイント解説:

  1. 初期同期中、新ノードは選挙や読み取りサービスに参加しません。同期完了後、自動的にSecondaryノードになります。
  2. 大規模データセットの初期同期は時間がかかる(100GBで数時間の可能性)、オフピーク時間帯の追加を推奨。
  3. Arbiterはデータを保存しません。奇数ノードでの投票参加を保証するためだけに使用し、優先度は0です。


5. 選挙メカニズム(Raftベース)

概念説明: 選挙メカニズムはレプリカセット高可用性の中核です—Primary障害時、Secondaryが自動的に選挙を開始して新しいPrimaryを選出します。MongoDBの選挙はRaftプロトコルの派生版に基づき、コア保証は「任意の時点で最大1つのPrimary」(スプリットブレイン防止)と「新しいPrimaryが最も完全なデータを持つ」ことです。

Raft選挙プロセス:

  1. 障害検出: SecondaryがelectionTimeout(デフォルト10秒)以内にPrimaryからハートビートを受信しない
  2. 選挙開始: 利用可能なSecondaryのうち優先度が最も高いものが候補になり、termをインクリメント
  3. 投票リクエスト: 候補は全ノードに投票リクエストを送信
  4. 投票ルール: 各ノードは1つのtermで1票のみ投票、最も最新のデータを持つ候補に投票
  5. 過半数選出: 過半数以上の票(> N/2)を獲得した候補が新しいPrimaryになる
  6. アプリ再接続: ドライバは自動的に新しいPrimaryを検出し、透過的に切り替え
100%
sequenceDiagram
    participant S1 as Secondary 1<br/>(候補)
    participant S2 as Secondary 2
    participant A as Arbiter

    Note over S1: Primaryハートビートタイムアウト10秒<br/>選挙を呼び出し

    S1->>S1: termをインクリメント = 2<br/>自分に投票
    S1->>S2: RequestVote(term=2, lastOplogTime)
    S1->>A: RequestVote(term=2, lastOplogTime)

    S2->>S1: GrantVote ✅<br/>(データが十分に最新)
    A->>S1: GrantVote ✅

    Note over S1: 過半数の票を獲得(2/3)<br/>新しいPrimaryになる

    S1->>S2: Heartbeat(term=2, role=PRIMARY)
    S1->>A: Heartbeat(term=2, role=PRIMARY)

    Note over S1,S2: 選挙終了、アプリは自動再接続

主要な選挙パラメータ:

選挙ルール 説明 デフォルト値
トリガー PrimaryがelectionTimeout以上到達不能 10秒
候補 全Secondary + Arbiter
投票 過半数以上の票(> 半数)を獲得でPrimaryに
優先度 高い優先度のノードが優先選出 1
データ完全性 投票者は最新のoplogを持つ候補にのみ投票
選挙クールダウン 頻繁な選挙を防止 30秒
100%
graph LR
    A[Primary障害] --> B[Secondary検出]
    B --> C{過半数の票を獲得?}
    C -->|はい| D[Primaryに昇格]
    C -->|いいえ| E[待機]
    D --> F[アプリ再接続]

    style D fill:#d4edda
選挙ルール 説明
トリガー PrimaryがelectionTimeout以上到達不能
候補 全Secondary + Arbiter
投票 過半数以上の票(> 半数)を獲得でPrimaryに
優先度 高い優先度のノードが優先選出

なぜ奇数ノードが必要か: 3ノードシステムは1つの障害を許容(2/3過半数投票)、4ノードシステムも1つの障害しか許容(3/4過半数投票)、5ノードシステムは2つの障害を許容(3/5過半数投票)。偶数ノードは耐障害性を増やさずコストが増えるため、奇数ノードを推奨。

▶ サンプル 1:選挙優先度設定

JAVASCRIPT
// TechCorp:より強力なサーバーを優先的にPrimaryに
rs.reconfig({
  _id: 'rs0',
  members: [
    { _id: 0, host: 'mongo1:27017', priority: 3 },   // 最強サーバー、圧倒的に選出
    { _id: 1, host: 'mongo2:27017', priority: 2 },   // 第2選択
    { _id: 2, host: 'mongo3:27017', priority: 1 },   // 最も低い優先度
    { _id: 3, host: 'mongo4:27017', priority: 0 }    // 選出不可(コールドスタンバイ)
  ]
});

出力:

TEXT 📖 参照専用
{ "ok" : 1 }


6. 読み書き分離

概念説明: レプリカセットは本質的に読み書き分離をサポート—書き込み操作はPrimaryにルーティングされ、読み取り操作はSecondaryに分散可能です。readPreferenceで読み取りルーティングポリシーを設定し、読み取り集中型シナリオでPrimaryの負荷を大幅に削減できます。

動作原理: Mongoose/MongoドライバはreadPreferenceパラメータを使用して、読み取り操作をどのノードに送信するかを決定します。primaryは強整合性を保証し、secondaryはPrimaryノードの負荷を削減しますが、レプリケーション遅延が発生します。

readPreference詳細:

モード 動作 整合性 遅延 使用シーン
primary プライマリノードのみ読み取り 最高 最低 トランザクション、重要データ
primaryPreferred プライマリ優先、不可ならセカンダリ 強い 低い 一般的なシーン
secondary セカンダリノードのみ読み取り 弱い 高い レポート/分析
secondaryPreferred セカンダリ優先、不可ならプライマリ より弱い より低い 読み取り多・書き込み少
nearest ネットワーク遅延最小 不定 最低 地理分散

整合性 vs パフォーマンスのトレードオフ:

100%
graph LR
    A[primary<br/>強整合性<br/>高遅延] --> B[primaryPreferred<br/>強整合性]
    B --> C[secondaryPreferred<br/>弱整合性]
    C --> D[secondary<br/>弱整合性<br/>低遅延]
    D --> E[nearest<br/>不定<br/>最低遅延]

    style A fill:#d4edda
    style D fill:#fff3cd
JAVASCRIPT
// === デフォルト:全読み書きがPrimaryで実行 ===
const user = await User.findById(userId);

// === セカンダリから読み取り(Primary負荷軽減)===
const products = await Product.find().read('secondary');

// === 読み取り設定オプション ===
await Product.find().read('primary');              // マスターノードのみ
await Product.find().read('primaryPreferred');     // プライマリ優先
await Product.find().read('secondary');            // スレーブノードのみ
await Product.find().read('secondaryPreferred');   // セカンダリ優先
await Product.find().read('nearest');              // 最も近いノード

ポイント解説:

  1. セカンダリからの読み取りはレプリケーション遅延が発生する可能性(通常< 1秒、ネットワーク問題時はより長く)。
  2. secondaryモードでは、全Secondaryノードが利用不可の場合、クエリはエラーを返します。
  3. レポートや検索インデックス構築など整合性がそれほど重要でないシナリオでは、secondaryまたはsecondaryPreferredを推奨。


7. Dockerでの3ノード構築

概念説明: Docker Composeはローカルでレプリカセットを開発・テストする最も便利な方法です。3ノード構成(1 Primary + 2 Secondary)は推奨される最小の本番構成で、高可用性と自動フェイルオーバーを提供します。

デプロイアーキテクチャ:

100%
graph TB
    subgraph "Docker Compose"
        M1[mongo1:27017<br/>Primary/Secondary]
        M2[mongo2:27017<br/>Primary/Secondary]
        M3[mongo3:27017<br/>Primary/Secondary]
    end

    App[アプリケーション] --> M1
    App --> M2
    App --> M3

    M1 <--> M2
    M2 <--> M3
    M1 <--> M3

    style M1 fill:#d4edda
    style M2 fill:#cce5ff
    style M3 fill:#cce5ff
YAML
# docker-compose.yml
version: '3.8'
services:
  mongo1:
    image: mongo:7.0
    command: mongod --replSet rs0 --port 27017
    ports:
      - "27017:27017"

  mongo2:
    image: mongo:7.0
    command: mongod --replSet rs0 --port 27017
    ports:
      - "27018:27017"

  mongo3:
    image: mongo:7.0
    command: mongod --replSet rs0 --port 27017
    ports:
      - "27019:27017"
JAVASCRIPT
// === レプリカセット初期化 ===
rs.initiate({
  _id: 'rs0',
  members: [
    { _id: 0, host: 'mongo1:27017' },
    { _id: 1, host: 'mongo2:27017' },
    { _id: 2, host: 'mongo3:27017' }
  ]
});

デプロイステップ:

ステップ コマンド 説明
1 docker-compose up -d 3コンテナを起動
2 mongosh --port 27017 最初のノードに接続
3 rs.initiate({...}) レプリカセット初期化
4 rs.status() ステータス確認
5 rs.conf() 設定確認


8. フェイルオーバー

概念説明: フェイルオーバーはレプリカセットの最も重要な機能です—Primaryノード障害時、残りのノードが自動的に新しいPrimaryを選出し、アプリケーションは透過的に再接続します。全プロセスは通常10–30秒で完了、この間書き込みは不可ですが、読み取りはSecondaryノードに縮退可能です。

フェイルオーバープロセス:

100%
sequenceDiagram
    participant App as アプリケーション
    participant P as Primary (mongo1)
    participant S1 as Secondary (mongo2)
    participant S2 as Secondary (mongo3)

    Note over P: mongo1障害

    P-xApp: ハートビート切断
    P-xS1: ハートビート切断
    P-xS2: ハートビート切断

    Note over S1,S2: 10秒間Primaryハートビート未受信

    S1->>S2: 選挙を呼び出し
    S2->>S1: 賛成票
    S1->>S1: 過半数の票獲得(2/3)

    Note over S1: mongo2が新しいPrimaryに

    App->>S1: 自動再接続 → 書き込み復旧
    App->>S2: 読み取り継続(secondaryPreferred)

    Note over App,S1: 合計ダウンタイム: 10-30秒
障害シナリオ 影響 復旧時間
Primary停止 書き込み中断10–30秒 自動選挙復旧
Secondary停止 影響なし 再起動後自動同期
過半数ノード停止 レプリカセット読み取り専用 過半数ノード復旧必要
ネットワーク分断 少数側は書き込み不可 ネットワーク復旧後自動統合
BASH
# === Primary停止をシミュレート ===
# mongo1コンテナをkill
docker stop mongo1

# === 自動選挙(30秒で完了)===
# mongo2またはmongo3が自動的にPrimaryに昇格

# === アプリ自動再接続(mongoose設定)===
mongoose.connect('mongodb://mongo1,mongo2,mongo3/shopdb?replicaSet=rs0');

アプリ層のトラブルシューティング:

設定 説明 推奨値
接続文字列 全ノードをリスト mongodb://m1,m2,m3/db?replicaSet=rs0
リトライ書き込み ネットワークエラーを自動リトライ retryWrites=true
読み取り設定 障害時の読み取り縮退 secondaryPreferred
接続タイムアウト 接続タイムアウト時間 connectTimeoutMS=5000
サーバー選択タイムアウト ノード選択タイムアウト serverSelectionTimeoutMS=30000


9. レプリカセットのベストプラクティス

概念概要: レプリカセットのベストプラクティスは、ノード数、セキュリティ設定、監視アラートなどを網羅します。これらの実践に従うことで、本番環境での一般的なレプリカセット障害を防止できます。

主要な実践:

実践 説明 理由
3ノード構成 1 Primary + 2 Secondary 最小耐障害構成、1ノード障害を許容
奇数ノード 選挙には過半数票が必要: 3/5/7 偶数ノードは耐障害性を増やさない
writeConcern: majority 過半数ノードで書き込み確認 データ消失なし(Primary障害でも)
readPreference primaryPreferred デフォルトでプライマリ読み取り 整合性保証、プライマリ不可ならセカンダリ
oplogウィンドウ監視 oplogロールオーバーはデータ消失の原因 ウィンドウ > 24時間を維持
適切な優先度設定 強力サーバーは高い優先度 障害復旧後、強力サーバーが再選出
Arbiterは慎重に使用 コスト重視時のみ使用 Arbiterはデータ保存せず、復旧不可

writeConcernの比較:

writeConcern データ安全性 書き込み遅延 使用シーン
w: 1 Primary確認のみ 最速 ログ、非重要データ
w: majority 過半数ノード確認 中程度 一般ビジネスデータ
w: majority, j: true 過半数確認 + journalディスク書き込み 最も遅い 金融、重要データ

監視チェックリスト:

監視項目 コマンド 健全値 アラート閾値
レプリカセットステータス rs.status() 1 PRIMARY + N SECONDARY PRIMARYなし
レプリケーション遅延 rs.status().members[n].optimeDate < 1秒 > 10秒
oplogウィンドウ rs.printReplicationInfo() > 72時間 < 24時間
接続数 db.serverStatus().connections < 1000 > 8000
選挙回数 rs.status().electionMetrics 少ない 頻繁な選挙

▶ サンプル:Dockerで3ノードレプリカセット構築 + フェイルオーバーテスト

BASH
# === 1. docker-compose.yml ===
# version: '3.8'
# services:
#   mongo1:
#     image: mongo:7.0
#     command: mongod --replSet rs0 --bind_ip_all --port 27017
#     ports: ["27017:27017"]
#     networks: [mongo-net]
#
#   mongo2:
#     image: mongo:7.0
#     command: mongod --replSet rs0 --bind_ip_all --port 27017
#     ports: ["27018:27017"]
#     networks: [mongo-net]
#
#   mongo3:
#     image: mongo:7.0
#     command: mongod --replSet rs0 --bind_ip_all --port 27017
#     ports: ["27019:27017"]
#     networks: [mongo-net]
#
# networks:
#   mongo-net:
#     driver: bridge

# 3ノード起動
docker-compose up -d

# === 2. レプリカセット初期化 ===
mongosh --port 27017 --eval '
  rs.initiate({
    _id: "rs0",
    members: [
      { _id: 0, host: "localhost:27017" },
      { _id: 1, host: "localhost:27018" },
      { _id: 2, host: "localhost:27019" }
    ]
  });
'

# === 3. レプリカセットステータス確認 ===
mongosh --port 27017 --eval 'rs.status();'
# 出力:
# {
#   set: 'rs0',
#   members: [
#     { name: 'localhost:27017', stateStr: 'PRIMARY' },
#     { name: 'localhost:27018', stateStr: 'SECONDARY' },
#     { name: 'localhost:27019', stateStr: 'SECONDARY' }
#   ]
# }

# === 4. テストデータ書き込み(自動的にSecondaryに複製)===
mongosh --port 27017 --eval '
  db.products.insertOne({ sku: "PHONE-001", title: "Smartphone X", price: 599 });
'

# === 5. データ複製を確認 ===
mongosh --port 27018 --eval '
  db.setSecondaryOk();  // Secondary読み取り許可
  db.products.findOne({ sku: "PHONE-001" });
'
# 同じドキュメントを返す、複製成功を証明

# === 6. フェイルオーバーテスト ===
# Primaryを停止
docker stop mongo1

# mongo2で確認
mongosh --port 27018 --eval 'rs.status();'
# 出力:mongo2が自動的にPRIMARYに昇格(30秒で完了)

# === 7. アプリ自動再接続(mongoose)===
JAVASCRIPT
// mongoose接続文字列は自動的に全ノードを発見
const mongoose = require('mongoose');
await mongoose.connect(
  'mongodb://localhost:27017,localhost:27018,localhost:27019/shopdb?replicaSet=rs0'
);

// Primary障害でも、アプリは自動的に新しいPrimaryに接続
const products = await Product.find();  // 自動リトライ、エラーなし

// === 8. 読み書き分離設定 ===
// 書き込み操作はPrimaryで完了
await Product.create({ sku: 'PHONE-002', title: 'Phone 2' });

// 読み取り操作はSecondaryで可能(Primary負荷軽減)
const products = await Product.find().read('secondaryPreferred');

// === 9. 障害ノード復旧 ===
docker start mongo1
# mongo1は自動的にSecondaryとしてレプリカセットに参加、Primaryからデータ同期開始

出力:

TEXT 📖 参照専用
3ノードレプリカセットが高可用性を提供;Primary障害時、30秒以内に自動フェイルオーバー、アプリへの影響なし。

▶ サンプル 3:読み取り設定とフェイルオーバーを備えたNode.jsアプリケーション(難易度 ⭐⭐)

JAVASCRIPT
// シーン:ShopHubアプリケーションがレプリカセットに接続、自動フェイルオーバー付き
const mongoose = require('mongoose');

// レプリカセットメンバーを含む接続文字列
const uri = 'mongodb://mongo1:27017,mongo2:27017,mongo3:27017/shophub?' +
  'replicaSet=rs0&' +
  'readPreference=primaryPreferred&' +
  'w=majority&' +
  'maxPoolSize=50';

// リトライロジック付きで接続
async function connectWithRetry() {
  try {
    await mongoose.connect(uri, {
      serverSelectionTimeoutMS: 5000,
      heartbeatFrequencyMS: 10000,
      retryWrites: true,
      retryReads: true
    });

    console.log('レプリカセットに接続完了');

    // レプリカセットステータスを監視
    const admin = mongoose.connection.db.admin();
    const status = await admin.command({ replSetGetStatus: 1 });

    console.log('レプリカセットステータス:');
    status.members.forEach(m => {
      console.log(`  ${m.name}: ${m.stateStr} (health: ${m.health})`);
    });

    // 現在のPrimary
    const primary = status.members.find(m => m.stateStr === 'PRIMARY');
    console.log(`現在のPrimary: ${primary?.name}`);

  } catch (err) {
    console.error('接続失敗:', err.message);
    console.log('5秒後にリトライ...');
    setTimeout(connectWithRetry, 5000);
  }
}

// 接続イベント処理
mongoose.connection.on('disconnected', () => {
  console.log('MongoDBから切断');
});

mongoose.connection.on('reconnected', () => {
  console.log('MongoDBに再接続');
});

mongoose.connection.on('error', (err) => {
  console.error('MongoDB接続エラー:', err);
});

connectWithRetry();

出力:

TEXT 📖 参照専用
レプリカセットに接続完了
レプリカセットステータス:
  mongo1:27017: PRIMARY (health: 1)
  mongo2:27017: SECONDARY (health: 1)
  mongo3:27017: SECONDARY (health: 1)
現在のPrimary: mongo1:27017

❓ よくある質問

Q レプリカセットの最小ノード数は?
A 1ノード(開発のみ)、本番では最小3ノード(1 primary + 2 secondary)。
Q Arbiterノードの目的は?
A 選挙投票のみ参加(データは保存しない)。データ冗長性を増やさずに奇数ノードを実現。
Q レプリカセットは水平スケールできる?
A レプリカセットは高可用性(HA)を提供、水平スケールはシャードクラスター(Sharding)で実現。
Q セカンダリノードに書き込みできる?
A 技術的には可能だが、データ競合を引き起こすため、本番環境では無効化されている。

📖 まとめ


📝 練習問題

  1. 基礎問題(⭐): Docker Composeで3ノードレプリカセットをデプロイ。
  2. 基礎問題(⭐): レプリカセットを初期化し、ステータスを確認(rs.status())。
  3. 応用問題(⭐⭐): 読み書き分離をテスト(readPreference: secondary)。
  4. 応用問題(⭐⭐): Primary障害をシミュレートし、自動選挙プロセスを観察。
  5. チャレンジ(⭐⭐⭐): 完全なレプリカセットをデプロイ(3ノード + レプリカセット監視 + 障害復旧テスト)。
Web-Tutorial.com

Web-Tutorial 技術チーム

複数の開発者によって共同維持されているプログラミングチュートリアルプラットフォーム。各チュートリアルは専門分野の開発者が執筆・レビューしています。正確で信頼性の高いコンテンツを目指しています — 問題を見つけた場合はお知らせください。

100%