Docker公式MongoDBにパスワードを設定する方法

現在、あるウェブサービスを開発中です。このウェブサービスは、Docker上で運用する予定でして、DBとして採用したMongoDBもやはりDocker上で走らせています。

Docker HubからMongoDBの公式イメージをPULLして、コンテナを立ち上げれば、手間なくMongoDBを走らせることができて便利なのですが、パスワードの設定を後回しにしていました。

このままうっかり本番運用を開始してまったらさすがにやばいので、パスワードを設定してみました。

Docker公式MongoDBにパスワードを設定する方法

公式サイトの説明を見ますと、Docker stackを使う場合は、以下のような設定ファイルで立ち上げれば良いようです。

version: '3.1'

services:

  mongo:
    image: mongo
    restart: always
    environment:
      MONGO_INITDB_ROOT_USERNAME: root
      MONGO_INITDB_ROOT_PASSWORD: example

定番の環境変数で読み込ませるパターンですね。

問題は、すでにパスワード設定なしで走らせているmongoDBに、どのようにユーザー認証の設定を追加すればいいのかということです。

おそらく、初回起動時に上記の設定で運用を始めていれば、認証情報が自動的に登録されたのだと思いますが、すでに運用を始めているmongoDBのcomposeファイルを書き換えても、ユーザーの登録は行われませんので、手動でユーザーを追加してやる必要があります。

以降は、mongoDBのコンテナに入って作業をします。
ちなみに、僕はportainerを使用して、スタックやコンテナの管理をしています。ターミナルを使って、コンテナに入ってコマンド入力するのはなかなか面倒なんですけど、portainerならブラウザ上で簡単手間なしでコマンド入力出来るので、すっかり手放せなくなりました。

まずは、mongo shellに入ります。

mongo

adminテーブルに切り替えます。adminテーブルはインストール時に自動的に追加されています。

use admin

管理ユーザーを登録します。

db.createUser({
    user:"admin", # 任意のユーザ名
    pwd:"xxxxxx", # 任意のパスワード
    roles:[{ role:"userAdminAnyDatabase", db:"admin" }]
})

これで管理用ユーザの登録が完了しました。

次に、このユーザを使って、個々のテーブルにアクセスできるユーザーを追加していきます。

先程のユーザ―名とパスワードで認証します。

db.auth("admin", "パスワード")

認証が通ると、「1」と表示されます。

続いて、今回のウェブサービスで使用するテーブル(仮にhogehogeテーブルとします)にアクセスするユーザー(仮にユーザー名をaaaとします)を登録します。

まずは、カレントテーブルを切り替えます。

use hogehoge

以下のコマンドでユーザーを追加します。

db.createUser({
    user:"aaa", # 任意のユーザ名
    pwd:"xxxxxx", # 任意のパスワード
    roles:[{ role: "readWrite", db: "hogehoge" }]
})

これで、hogehogeテーブルに読み書きできる権限を持つユーザーaaaの登録が完了しました。

ところが、これだけでは、パスワード認証なしでデータにアクセス出来てしまいます。mongoDBを「認証あり」の設定で再起動する必要があります。

「認証ありで起動する」というところがポイントでして、たとえユーザーとパスワードを設定していても、認証ありで起動しないと、認証しなくてもデータにアクセス出来てしまいます。なんでこんな仕様なのか分からないのですが、結構やらかしているサーバがありそうで怖いですね。

では、どのように「認証あり」で起動するのかといいますと、Docker公式mongoDBイメージの場合、環境変数にMONGO_INITDB_ROOT_USERNAMEとMONGO_INITDB_ROOT_PASSWORDを設定してやれば、自動的に認証ありで起動するようです。

なので、コンテナを一旦落として、composeファイルに環境変数を追加して起動し直せばOKです。コンテナのログを見ると、認証なしで起動した場合はその旨のアラートが出ますので、起動後は念のためにログを確認することをお勧めします。

このテーブルへのアクセス方法は、使用するインターフェイスによって違うと思いますが、概ね以下のように修正すれば良いのではないかと思います。

認証なし
mongodb://mongo:27017

認証あり
mongodb://{ユーザー}:{パスワード}@mongo:27017/{テーブル名}

認証の際は、ユーザー名とパスワードだけでなく、対象となるテーブル名も指定してやるところがポイントでしょうか。
というか僕はそこでつまずいて、何でアクセス出来んのじゃーっ!!!となりました。

シェアする

  • このエントリーをはてなブックマークに追加

フォローする