Ubuntu20.04でMongoDBレプリカセットのキーファイル認証を構成する方法
序章
MongoDB は、 Mongo とも呼ばれ、多くの最新のWebアプリケーションで使用されているオープンソースのドキュメントデータベースです。 リレーショナルデータベースモデルに依存しないため、NoSQLデータベースに分類されます。 代わりに、動的スキーマを持つJSONのようなドキュメントを使用します。 つまり、リレーショナルデータベースとは異なり、MongoDBでは、データベースにデータを追加する前に事前定義されたスキーマは必要ありません。
レプリカセットまたはシャードデータベースアーキテクチャの場合のように、複数の分散MongoDBインスタンスを操作する場合は、それらの間の通信が安全であることを確認することが重要です。 これを行う1つの方法は、キーファイル認証を使用することです。 これには、基本的にクラスター内の各メンバーの共有パスワードとして機能する特別なファイルの作成が含まれます。
このチュートリアルでは、キーファイル認証を使用するように既存のレプリカセットを更新する方法の概要を説明します。 このガイドに含まれる手順により、レプリカセットにダウンタイムが発生しないようにすることもできるため、レプリカセット内のデータは、それにアクセスする必要のあるすべてのクライアントまたはアプリケーションで引き続き利用できます。
前提条件
このチュートリアルを完了するには、次のものが必要です。
- それぞれがUbuntu20.04を実行している3台のサーバー。 これら3つのサーバーすべてに、管理者の非rootユーザーとUFWで構成されたファイアウォールが必要です。 これを設定するには、Ubuntu20.04の初期サーバー設定ガイドに従ってください。
- 各UbuntuサーバーにインストールされたMongoDB。 Ubuntu 20.04 にMongoDBをインストールする方法に関するチュートリアルに従い、各サーバーで各手順を完了してください。
- レプリカセットとして構成された3つのMongoDBインストールすべて。 Ubuntu 20.04 でMongoDBレプリカセットを構成する方法に関するこのチュートリアルに従って、これを設定してください。
- サーバーごとに生成されたSSHキー。 さらに、各サーバーの
authorized_keys
ファイルに他の2つのサーバーの公開鍵が追加されていることを確認する必要があります。 これは、各マシンがSSHを介して相互に通信できるようにするためです。これにより、ステップ2で各マシンにキーファイルを簡単に配布できるようになります。 これらを設定するには、 Ubuntu20.04でSSHキーを設定する方法に関するガイドに従ってください。
わかりやすくするために、このガイドでは、前提条件のレプリカセットのチュートリアルで確立された規則に従い、3つのサーバーを mongo0 、 mongo1 、およびmongo2と呼びます。 ]。 また、そのガイドのステップ1 を完了し、次のホスト名が特定のサーバーのIPアドレスに解決されるように各サーバーのhosts
ファイルを構成したことも前提としています。
ホスト名 | に解決します |
---|---|
mongo0.replset.member | mongo0 |
mongo1.replset.member | mongo1 |
mongo2.replset.member | mongo2 |
このガイドには、これらのサーバーの1つだけでコマンドを実行したり、ファイルを更新したりする必要があるインスタンスがいくつかあります。 このような場合、このガイドではデフォルトで例で mongo0 を使用し、次のようにコマンドまたはファイルの変更を青色の背景で表示することでこれを示します。
-
複数サーバーで実行する必要のあるコマンドまたはファイルの変更は、次のような標準の灰色の背景になります。
-
キーファイル認証について
MongoDBでは、キーファイル認証は、データベースシステムのデフォルトの認証メカニズムである Salted Challenge Response Authentication Mechanism(SCRAM)に依存しています。 SCRAMには、MongoDBがユーザー名、パスワード、および認証データベースの組み合わせに対してユーザーによって提示されたクレデンシャルを読み取り、検証することが含まれます。これらはすべて、特定のMongoDBインスタンスによって認識されます。 これは、データベースに接続するときにパスワードを提供するユーザーを認証するために使用されるのと同じメカニズムです。
キーファイル認証では、キーファイルはクラスター内の各メンバーの共有パスワードとして機能します。 キーファイルには、6〜1024文字が含まれている必要があります。 キーファイルにはbase64セットの文字のみを含めることができ、MongoDBはキーを読み取るときに空白文字を削除することに注意してください。 Mongoのバージョン4.2以降、キーファイルはYAML形式を使用しており、1つのキーファイルで複数のキーを共有できます。
警告:コミュニティバージョンのMongoDBには、データベースを安全に保つのに役立つ2つの認証方法、キーファイル認証とx.509認証が付属しています。 レプリケーションを使用する本番環境のデプロイメントでは、 MongoDBドキュメントはx.509認証の使用を推奨し、キーファイルを「テストまたは開発環境に最適な」「最低限のセキュリティ形式」として説明しています。
x.509証明書を取得して構成するプロセスには、ケースバイケースで行う必要のあるいくつかの警告と決定が伴います。つまり、この手順はDigitalOceanチュートリアルの範囲を超えています。 実稼働環境でレプリカセットを使用することを計画している場合は、x.509認証に関する公式MongoDBドキュメントを確認することを強くお勧めします。
レプリカセットをテストまたは開発に使用することを計画している場合は、このチュートリアルに従って、クラスターにセキュリティのレイヤーを追加できます。
ステップ1—ユーザー管理者を作成する
MongoDBで認証を有効にすると、レプリカセットのロールベースのアクセス制御も有効になります。 MongoDBのドキュメントによると:
MongoDBは、役割ベースのアクセス制御(RBAC)を使用して、MongoDBシステムへのアクセスを管理します。 ユーザーには、データベースのリソースと操作へのユーザーのアクセスを決定する1つ以上のロールが付与されます。
MongoDBインスタンスでアクセス制御が有効になっている場合、有効なMongoDBユーザーとして認証されていない限り、システム上のどのリソースにもアクセスできないことを意味します。 それでも、特定のリソースにアクセスするには、適切な権限を持つユーザーとして認証する必要があります。
キーファイル認証(およびその結果としてアクセス制御)を有効にする前にMongoDBシステムのユーザーを作成しない場合、レプリカセットからロックアウトされることはありません。 セットへの認証に使用できるMongoDBユーザーを作成し、必要に応じて、Mongoのlocalhost例外を介して他のユーザーを作成できます。 これは、MongoDBがアクセス制御を有効にしているが、ユーザーが不足している構成に対して行う特別な例外です。 この例外では、 localhost のデータベースに接続してから、admin
データベースにユーザーを作成することしかできません。
ただし、認証を有効にした後でローカルホストの例外に依存してMongoDBユーザーを作成すると、レプリカはユーザーを作成するまで接続を認証できないため、レプリカセットにダウンタイムが発生します。 この手順では、前にユーザーを作成して認証を有効にし、レプリカセットが引き続き使用可能であることを確認する方法の概要を説明します。 このユーザーには、データベース上に他のユーザーを作成するためのアクセス許可があり、将来必要なアクセス許可を持つ他のユーザーを自由に作成できます。 MongoDBでは、このような権限を持つユーザーはユーザー管理者と呼ばれます。
まず、レプリカセットのプライマリメンバーに接続します。 どのメンバーがプライマリであるかわからない場合は、rs.status()
メソッドを実行してそれを識別できます。
レプリカセットでMongoDBインスタンスをホストしているUbuntuサーバーのいずれかのbashプロンプトから次のmongo
コマンドを実行します。 このコマンドの--eval
オプションは、mongo
操作に、mongo
を単独で実行したときに表示されるシェルインターフェイス環境を開かず、代わりに単一のコマンドまたはメソッドを実行するように指示します。 --eval
引数に続く引用符:
- mongo --eval 'rs.status()'
rs.status()
は多くの情報を返しますが、出力の関連部分は"members" :
配列です。 MongoDBのコンテキストでは、配列は、角かっこ([
と]
)の間に保持されたドキュメントのコレクションです。
"members":
配列には、レプリカセットのメンバーの1つに関する情報が含まれている多数のドキュメントがあります。 これらの各メンバードキュメント内で、"stateStr"
フィールドを見つけます。 "stateStr"
の値が"PRIMARY"
であるメンバーは、レプリカセットのプライマリメンバーです。 次の例は、mongo0がプライマリである状況を示しています。
Output. . .
"members" : [
{
"_id" : 0,
"name" : "mongo0.replset.member:27017",
"health" : 1,
"state" : 1,
"stateStr" : "PRIMARY",
. . .
},
. . .
どのレプリカセットメンバーがプライマリであるかがわかったら、そのインスタンスをホストしているサーバーにSSHで接続します。 デモンストレーションの目的で、このガイドでは、mongo0がプライマリである例を引き続き使用します。
- ssh sammy@mongo0_ip_address
サーバーにログインした後、mongo
シェル環境を開いてMongoDBに接続します。
- mongo
MongoDBでユーザーを作成するときは、認証データベースとして使用される特定のデータベース内にユーザーを作成する必要があります。 ユーザーの名前とその認証データベースの組み合わせは、そのユーザーの一意の識別子として機能します。
特定の管理アクションは、認証データベースがadmin
データベース(すべてのMongoDBインストールに含まれる特別な特権データベース)であるユーザーのみが使用できます。これには、新しいユーザーを作成する機能も含まれます。 この手順の目的は、レプリカセットに他のユーザーを作成できるユーザー管理者を作成することであるため、admin
データベースに接続して、このユーザーに適切な権限を付与できるようにします。
- use admin
Outputswitched to db admin
MongoDBには、データベースの管理に使用できるJavaScriptベースのシェルメソッドが多数インストールされています。 これらの1つであるdb.createUser
メソッドは、メソッドが実行されるデータベースに新しいユーザーを作成するために使用されます。
db.createUser
メソッドを開始します。
- db.createUser(
注:Mongoは、閉じ括弧を入力するまで、db.createUser
メソッドを完了として登録しません。 そうするまで、プロンプトは大なり記号(>
)から省略記号(...
)に変わります。
この方法では、ユーザーのユーザー名とパスワード、およびユーザーに付与する役割を指定する必要があります。 MongoDBはデータをJSONのようなドキュメントに保存することを思い出してください。 新しいユーザーを作成するときは、適切なユーザーデータを個々のフィールドとして保持するドキュメントを作成するだけです。
JSONのオブジェクトと同様に、MongoDBのドキュメントは中括弧({
および}
)で開始および終了します。 冒頭の中括弧を入力して、ユーザードキュメントを開始します。
- {
次に、user:
フィールドに、希望するユーザー名を二重引用符で囲んだ値にコンマを付けて入力します。 次の例では、ユーザー名 UserAdminSammy を指定していますが、任意のユーザー名を入力できます。
- user: "UserAdminSammy",
次に、passwordPrompt()
メソッドを値としてpwd
フィールドに入力します。 db.createUser
メソッドを実行すると、passwordPrompt()
メソッドはパスワードの入力を求めるプロンプトを表示します。 これは、ユーザー名の場合と同じようにパスワードをクリアテキストで入力するという代替手段よりも安全です。
注:passwordPrompt()
メソッドは、MongoDBバージョン4.2以降とのみ互換性があります。 古いバージョンのMongoを使用している場合は、ユーザー名を書き出すのと同じように、パスワードをクリアテキストで書き出す必要があります。
- pwd: "password",
このフィールドの後には、必ずコンマを付けてください。
- pwd: passwordPrompt(),
次に、roles
フィールドに続けて、管理ユーザーに付与する役割の詳細を示す配列を入力します。 MongoDBでは、 roles は、ユーザーがアクセスできるリソースに対して実行できるアクションを定義します。 カスタムロールは自分で定義できますが、Mongoには、一般的に必要な権限を付与する多数の組み込みロールも付属しています。
ユーザー管理者を作成しているため、少なくとも、admin
データベースに対する組み込みのuserAdminAnyDatabase
ロールをユーザーに付与する必要があります。 これにより、ユーザー管理者は新しいユーザーとロールを作成および変更できます。 管理ユーザーはadmin
データベースでこの役割を持っているため、クラスター全体へのスーパーユーザーアクセスも許可されます。
- roles: [ { role: "userAdminAnyDatabase", db: "admin" } ]
続いて、ドキュメントの終わりを示すために閉じ中括弧を入力します。
- }
次に、閉じ括弧を入力して、db.createUser
メソッドを閉じて実行します。
- )
まとめると、db.createUser
メソッドは次のようになります。
> db.createUser(
... {
... user: "UserAdminSammy",
... pwd: passwordPrompt(),
... roles: [ { role: "userAdminAnyDatabase", db: "admin" } ]
... }
... )
各行の構文が正しい場合、メソッドは正しく実行され、パスワードの入力を求められます。
OutputEnter password:
選択した強力なパスワードを入力します。 次に、ユーザーが追加されたという確認を受け取ります。
OutputSuccessfully added user: {
"user" : "UserAdminSammy",
"roles" : [
{
"role" : "userAdminAnyDatabase",
"db" : "admin"
},
"readWriteAnyDatabase"
]
}
これで、システム上の他のユーザーとロールを管理するために使用できるMongoDBユーザープロファイルを追加しました。 このステップの残りの部分で概説するように、別のユーザーを作成することでこれをテストできます。
作成したユーザー管理者として認証することから始めます。
- db.auth( "UserAdminSammy", passwordPrompt() )
認証が成功した場合、db.auth()
は1
を返します。
Output1
注:将来、クラスターに接続するときにユーザー管理者として認証する場合は、次のようなコマンドを使用して、サーバープロンプトから直接認証できます。
- mongo -u "UserAdminSammy" -p --authenticationDatabase "admin"
このコマンドで、-u
オプションは、次の引数が認証するユーザー名であることをシェルに通知します。 -p
フラグは、パスワードの入力を求めるプロンプトを表示し、--authenticationDatabase
オプションはユーザーの認証データベースの名前の前にあります。 間違ったパスワードを入力した場合、またはユーザー名と認証データベースが一致しない場合、認証できなくなり、接続を再試行する必要があります。
また、レプリカセットにユーザー管理者として新しいユーザーを作成するには、セットのプライマリメンバーに接続する必要があることに注意してください。
別のユーザーを追加する手順は、ユーザー管理者の場合と同じです。 次の例では、clusterAdmin
ロールを持つ新しいユーザーを作成します。これは、ユーザーがレプリケーションとシャーディングに関連する多くの操作を実行できることを意味します。 MongoDBのコンテキスト内では、これらの特権を持つユーザーはクラスター管理者と呼ばれます。
このような特定の機能を実行するための専用ユーザーを用意することは、システム上にいる特権ユーザーの数を制限するため、優れたセキュリティ慣行です。 このチュートリアルの後半でキーファイル認証を有効にした後、clusterAdmin
ロールで許可されている操作(rs.status()
などのrs.
メソッドなど)を実行するクライアント。 ]またはrs.conf()
—最初にクラスター管理者として認証する必要があります。
そうは言っても、このユーザーに好きな役割を提供することができ、同様に別の名前と認証データベースをユーザーに提供することができます。 ただし、新しいユーザーをクラスター管理者として機能させる場合は、mustでadmin
データベース内のclusterAdmin
ロールを付与する必要があります。
クラスタ管理者として機能するユーザーを作成することに加えて、次のメソッドはユーザーに ClusterAdminSammy という名前を付け、passwordPrompt()
メソッドを使用してパスワードの入力を求めます。
- db.createUser(
- {
- user: "ClusterAdminSammy",
- pwd: passwordPrompt(),
- roles: [ { role: "clusterAdmin", db: "admin" } ]
- }
- )
繰り返しになりますが、バージョン 4.2 より前のバージョンのMongoDBを使用している場合は、passwordPrompt()
メソッドを使用する代わりに、パスワードをクリアテキストで書き出す必要があります。
各行の構文が正しい場合、メソッドは正しく実行され、パスワードの入力を求められます。
OutputEnter password:
選択した強力なパスワードを入力します。 次に、ユーザーが追加されたという確認を受け取ります。
OutputSuccessfully added user: {
"user" : "ClusterAdminSammy",
"roles" : [
{
"role" : "clusterAdmin",
"db" : "admin"
}
]
}
この出力は、ユーザー管理者が新しいユーザーを作成してそれらに役割を付与できることを確認します。 これで、MongoDBシェルを閉じることができます。
- exit
または、CTRL + C
を押してシェルを閉じることもできます。
この時点で、MongoDBクラスターに接続されているクライアントまたはアプリケーションがある場合は、データベースへの認証に使用できる適切なロールを持つ1人以上の専用ユーザーを作成することをお勧めします。 それ以外の場合は、キーファイルを生成する方法を学び、レプリカセットのメンバーに配布してから、レプリカセットのメンバーにキーファイルでの認証を要求するように各メンバーを構成します。
ステップ2—認証キーファイルの作成と配布
キーファイルを作成する前に、整理しておくために、キーファイルを保存するディレクトリを各サーバーに作成すると便利な場合があります。 次のコマンドを実行します。これにより、管理用Ubuntuユーザーのホームディレクトリにmongo-security
という名前のディレクトリが3台のサーバーのそれぞれに作成されます。
- mkdir ~/mongo-security
次に、サーバーの1つでキーファイルを生成します。 これはどのサーバーでも実行できますが、説明のために、このガイドではmongo0にキーファイルを生成します。
作成したmongo-security
ディレクトリに移動します。
- cd ~/mongo-security/
そのディレクトリ内に、次のopenssl
コマンドを使用してキーファイルを作成します。
- openssl rand -base64 768 > keyfile.txt
このコマンドの引数に注意してください。
rand
:疑似ランダムバイトのデータを生成するようにOpenSSLに指示します-base64
:コマンドがbase64エンコーディングを使用して、疑似ランダムデータを印刷可能なテキストとして表す必要があることを指定します。 前述のように、MongoDBキーファイルにはbase64セットの文字しか含めることができないため、これは重要です。768
:コマンドが生成する必要のあるバイト数。 base64エンコーディングでは、3バイトのデータが4文字で表されます。 MongoDBキーファイルには最大1024文字を使用できるため、有効なキーファイルに対して生成できる最大バイト数は768です。
このコマンドの768
引数の後には、大なり記号(>
)が続きます。 これにより、コマンドの出力がkeyfile.txt
という名前の新しいファイルにリダイレクトされます。このファイルはキーファイルとして機能します。 必要に応じて、キーファイルにkeyfile.txt
以外の名前を付けてください。ただし、後のコマンドに表示される場合は、必ずファイル名を変更してください。
次に、所有者のみが読み取りアクセス権を持つように、キーファイルの権限を変更します。
- chmod 400 keyfile.txt
これに続いて、レプリカセット内のMongoDBインスタンスをホストしている他の2つのサーバーにキーファイルを配布します。 SSHキーの設定方法の前提条件ガイドに従っていると仮定すると、scp
コマンドを使用してこれを行うことができます。
- scp keyfile.txt sammy@mongo1.replset.member:/home/sammy/mongo-security
- scp keyfile.txt sammy@mongo2.replset.member:/home/sammy/mongo-security
これらの各コマンドは、mongo1およびmongo2で以前に作成した~/mongo-security/
ディレクトリにキーファイルを直接コピーすることに注意してください。 必ずsammy
を各サーバーで作成した管理用Ubuntuユーザープロファイルの名前に変更してください。
次に、ファイルの所有者をmongodbユーザープロファイルに変更します。 これは、MongoDBをインストールしたときに作成された特別なユーザーであり、mongod
サービスを実行するために使用されます。 このユーザーは、MongoDBがキーファイルを認証に使用するために、キーファイルにアクセスできる必要があります。
各サーバーで次のコマンドを実行して、キーファイルの所有者をmongodbユーザーアカウントに変更します。
- sudo chown mongodb:mongodb ~/mongo-security/keyfile.txt
各サーバーでキーファイルの所有者を変更したら、各MongoDBインスタンスを再構成して、キーファイル認証を実施する準備が整います。
ステップ3—キーファイル認証を有効にする
キーファイルを生成し、レプリカセット内の各サーバーに配布したので、各サーバーのMongoDB構成ファイルを更新して、キーファイル認証を適用できます。
認証を要求するようにレプリカセットのメンバーを構成する際のダウンタイムを回避するために、このステップでは、最初にセットのセカンダリメンバーを再構成する必要があります。 次に、プライマリメンバーにステップダウンしてセカンダリメンバーになるように指示します。 これにより、セカンダリメンバーは、新しいプライマリを選択するための選択を行い、クラスターにアクセスする必要のあるクライアントまたはアプリケーションがクラスターを利用できるようにします。 次に、認証を有効にするために以前のプライマリノードを再構成します。
レプリカセットのセカンダリメンバーをホストしている各サーバーで、お好みのテキストエディターを使用してMongoDBの構成ファイルを開きます。
- sudo nano /etc/mongod.conf
ファイル内で、security
セクションを見つけます。 デフォルトでは次のようになります。
. . .
#security:
. . .
ポンド記号(#
)を削除して、この行のコメントを解除します。 次に、次の行で、keyFile:
ディレクティブを追加し、その後に前の手順で作成したキーファイルへのフルパスを追加します。
. . .
security:
keyFile: /home/sammy/mongo-security/keyfile.txt
. . .
この新しい行の先頭には2つのスペースがあることに注意してください。 これらは、構成ファイルを正しく読み取るために必要です。 独自の構成ファイルにこの行を入力するときは、指定するパスが各サーバー上のキーファイルの実際のパスを反映していることを確認してください。
keyFile
ディレクティブの下に、true
の値を持つtransitionToAuth
ディレクティブを追加します。 true
に設定すると、この構成オプションにより、MongoDBインスタンスは認証された接続と認証されていない接続の両方を受け入れることができます。 これは、レプリカセットを再構成して認証を実施する場合に役立ちます。これにより、セットの各メンバーを再起動してもデータを引き続き使用できるようになります。
. . .
security:
keyFile: /home/sammy/mongo-security/keyfile.txt
transitionToAuth: true
. . .
繰り返しになりますが、transitionToAuth
ディレクティブの前に2つの空白スペースが含まれていることを確認してください。
これらの変更を行った後、ファイルを保存して閉じます。 nano
を使用して編集した場合は、CTRL + X
、Y
、ENTER
の順に押すと編集できます。
次に、両方のセカンダリインスタンスのサーバーでmongod
サービスを再起動して、これらの変更をすぐに有効にします。
- sudo systemctl restart mongod
これで、レプリカセットのセカンダリメンバーのキーファイル認証を構成しました。 この時点で、認証されたユーザーと認証されていないユーザーの両方が、これらのメンバーに制限なくアクセスできます。
次に、プライマリメンバーでこの手順を繰り返します。 ただし、そうする前に、メンバーをステップダウンして、プライマリではなくなるようにする必要があります。 これを行うには、プライマリメンバーをホストしているサーバーでMongoDBシェルを開きます。 説明のために、このガイドでは、これがmongo0であると再び想定しています。
- mongo
プロンプトから、rs.stepDown()
メソッドを実行します。 これにより、プライマリーがセカンダリーメンバーになるように指示され、現在のセカンダリーメンバーが新しいプライマリーとして機能するかどうかを決定するための選挙を実施します。
- rs.stepDown()
メソッドが出力に"ok" : 1
を返す場合、プライマリメンバーが正常にステップダウンしてセカンダリになることを意味します。
Output{
"ok" : 1,
"$clusterTime" : {
"clusterTime" : Timestamp(1614795467, 1),
"signature" : {
"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
"keyId" : NumberLong(0)
}
},
"operationTime" : Timestamp(1614795467, 1)
}
プライマリをステップダウンした後、Mongoシェルを閉じることができます。
- exit
次に、このサーバーでMongoDB構成ファイルを開きます。
- sudo nano /etc/mongod.conf
セキュリティセクションを見つけ、ポンド記号を削除してsecurity
ヘッダーのコメントを解除します。 次に、他のMongoDBインスタンスに追加したものと同じkeyFile
およびtransitionToAuth
ディレクティブを追加します。 これらの変更を行うと、security
セクションは次のようになります。
. . .
security:
keyFile: /home/sammy/mongo-security/keyfile.txt
transitionToAuth: true
. . .
ここでも、keyFile
ディレクティブの後のファイルパスが、このサーバー上のキーファイルの実際の場所を反映していることを確認してください。
終了したら、ファイルを保存して閉じます。 次に、mongod
プロセスを再開します。
- sudo systemctl restart mongod
その後、すべてのMongoDBインスタンスは、認証された接続と認証されていない接続の両方を受け入れることができます。 このガイドの最後のステップでは、特権アクションを実行する前にユーザーに認証を要求するようにインスタンスを構成します。
ステップ4—認証を実施するためにtransitionToAuth
なしで各メンバーを再起動する
この時点で、各MongoDBインスタンスは、transitionToAuth
がtrue
に設定された状態で構成されています。 つまり、各サーバーが作成したキーファイルを使用して内部で接続を認証できるようにした場合でも、認証されていない接続を受け入れることができます。
これを変更し、各メンバーに認証を強制するように要求するには、各サーバーでmongod.conf
ファイルを再度開きます。
- sudo nano /etc/mongod.conf
security
セクションを見つけて、transitionToAuth
ディレクティブを無効にします。 これを行うには、行の前にポンド記号を付けてコメントアウトします。
. . .
security:
keyFile: /home/sammy/mongo-security/keyfile.txt
#transitionToAuth: true
. . .
各インスタンスの構成ファイルでtransitionToAuth
ディレクティブを無効にした後、各ファイルを保存して閉じます。
次に、各サーバーでmongod
サービスを再起動します。
- sudo systemctl restart mongod
その後、レプリカセット内の各MongoDBインスタンスは、特権アクションを実行するために認証する必要があります。
これをテストするには、適切な権限を持つ認証済みユーザーによって呼び出されたときに機能するMongoDBメソッドを実行してみてください。 Ubuntuサーバーのプロンプトから次のコマンドを実行してみてください。
- mongo --eval 'rs.status()'
手順1でこのメソッドを正常に実行した場合でも、rs.status()
メソッドは、clusterAdmin
またはclusterManager
の役割を付与されたユーザーのみが実行できるようになりました。キーファイル認証を有効にしました。 このコマンドをプライマリメンバーまたはセカンダリメンバーの1つをホストしているサーバーで実行するかどうかに関係なく、認証されていないため、このコマンドは機能しません。
Output. . .
MongoDB server version: 4.4.4
{
"operationTime" : Timestamp(1616184183, 1),
"ok" : 0,
"errmsg" : "command replSetGetStatus requires authentication",
"code" : 13,
"codeName" : "Unauthorized",
"$clusterTime" : {
"clusterTime" : Timestamp(1616184183, 1),
"signature" : {
"hash" : BinData(0,"huJUmB/lrrxpx9YfnONM4mayJwo="),
"keyId" : NumberLong("6941116945081040899")
}
}
}
アクセス制御を有効にした後、すべてのクラスター管理メソッド(rs.
メソッド(rs.status()
など)は、適切なクラスター管理ロールが付与された認証済みユーザーによって呼び出された場合にのみ機能する)を思い出してください。 手順1で概説したように、クラスター管理者を作成し、そのユーザーとして認証した場合、この方法は期待どおりに機能します。
- mongo -u "ClusterAdminSammy" -p --authenticationDatabase "admin" --eval 'rs.status()'
プロンプトが表示されたらユーザーのパスワードを入力すると、rs.status()
メソッドの出力が表示されます。
Output. . .
MongoDB server version: 4.4.4
{
"set" : "shard2",
"date" : ISODate("2021-03-19T20:21:45.528Z"),
"myState" : 2,
"term" : NumberLong(4),
"syncSourceHost" : "mongo1.replset.member:27017",
"syncSourceId" : 2,
"heartbeatIntervalMillis" : NumberLong(2000),
"majorityVoteCount" : 2,
. . .
これにより、レプリカセットが認証を実施していること、および正常に認証できることが確認されます。
結論
このチュートリアルを完了することで、OpenSSLを使用してキーファイルを作成し、MongoDBレプリカセットを構成して、メンバーが内部認証に使用するように要求しました。 また、将来的にユーザーと役割を管理できるようにするユーザー管理者を作成しました。 このすべてを通して、レプリカセットはダウンタイムを経ることはなく、データはクライアントとアプリケーションで引き続き利用できます。
MongoDBの詳細については、MongoDBコンテンツのライブラリ全体を確認することをお勧めします。