- MongoDB ログイン
- MongoDB操作
- Mongo DBの障害調査
MongoDB ログイン
ローカルホストへのMongoDBへのログイン
# mongo [DB名] -u 「UserのDB名」 -p
I.E
# mongo mango_db_name -u username -p MongoDB shell version v3.6.10 Enter password: connecting to: mongodb://127.0.0.1:27017/mango_db_nameb?gssapiServiceName=mongodb Implicit session: session { "id" : UUID("a384d33f-ec64-4c87-b6f6-77503e6ad3df") } MongoDB server version: 3.6.10
リモートホストのMongoDBへのログイン
$ mongo --host「ホスト名」 -u 「ユーザー名」 -p [password] [DB名]
I.E $ mongo --host 192.167.8.29:27000 -u mongo -p password_name database_name MongoDB shell version v3.6.18 connecting to: mongodb://xxxxxxxxx Implicit session: session { "id" : UUID("3b058d16-2e6a-4fab-bbac-35abb5a785c9") } MongoDB server version: 4.4.3 WARNING: shell and server versions do not match > show dbs database_name 0.024GB
もしくは、
$ mongo mongodb://「ユーザー名」:「パスワード」@「IP」:「ポート」/「DB名」
I.E
$ mongo mongodb://Username:MongoPassword@192.168.1.5:27017/database_mongo_name MongoDB shell version v4.4.
*ただし、デフォルトでは、リモートからのアクセスは、禁止されているため許可する必要がある。
/etc/monod.conf`のbindIpに、接続元のIPを入力する。
# network interfaces net: port: 27017 bindIp: 127.0.0.1,10.192.168.1.1,10.165.8.100
その後、サービスを再起動する。
systemctl restart mongod.service
*認証をDisabledにする方法もある。 /etc/monod.conf のsecurity configをコメントアウトして、再起動すると、認証が不要になる。 どうしても、アクセスできないようであれば、一時的にこちらの方法を利用してもよいだろう。
認証を有効にしている場合、データベースごとにユーザー・passが必要になる。 そのため、ログイン時に以下のように、データベースを指定したうえで、ログインする必要がある。 指定しないと、ログインできたように見えるが、show dbsの結果が出ないなどの問題にあたるかも
$ mongo --host 192.167.8.29:27000 -u mongo -p passwork_name database_name
# security config # BEGIN ANSIBLE MANAGED BLOCK security: keyFile: /etc/mongo_key authorization: enabled
また、データベースごとに、アクセス可能なユーザーが定義されています。 特定のデータベースにアクセスするためには、アクセス権を持っているアカウントでのアクセスが必要となります。 ユーザの作成には、”ユーザー作成”を参照ください。
MongoDB操作
DB作成 or DBの切り替え
use 「DB名」;
I.E mongo_db_nameという名称のmongoDBを作成する or DBを切り替える場合
> use mongo_db_name switched to db mongo_db_name
DB一覧参照
show dbs;
I.E DBの一覧参照
> show dbs; admin 0.000GB config 0.000GB local 0.000GB alert_db 37.617GB compabt_db 0.075GB
Collection 操作
Collectoin一覧参照
> show collections collection1 collecton2
ドキュメント操作
ドキュメント一覧参照
db.<ドキュメント名>.find() I.E db.collection1.find()
ドキュメント検索 find()を利用
ドキュメントのKey,Valueで検索
db.<コレクション名>.find( { key: value} )
例えば、コレクション名がcollection1, 検索したいkeyがType, valueがcatの場合
db.collecton1.find( { Type: "cat"} )
なお、And検索は、以下の通り。
db.<コレクション名>.find( { key: value, key2: value2 } )
ワイルドカードで検索。
ワイルドカードの検索は、$regexを利用する。 KeyがType、Valueにcatが含まれているドキュメントを検索する。
db.collection1.find({Type : {$regex : "cat" } })
最新のドキュメントから5件を出力(idが最新のドキュメントを検索)
db.<コレクション名>.find().sort({_id: -1}).limit(5)
ドキュメント名がcollection1から最新の5件を検索。
db.collection1.find().sort({_id: -1}).limit(5)
ドキュメントの検索結果を見やすくする(成形された結果を出力)
検索コマンドの最後に.pretty()を追加することで、成形された結果が出てくる。
db.<コレクション名>.find().sort({_id: -1}).limit(5).pretty()
*注意点として、外部からmongoにアクセスする場合、以下のように、find内の検索クエリの”をエスケープする必要がある。 mongo --host 192.168.10.25:27010 --eval "db.collection1.find({Type : \"cat\"})" database_name -u mongo_user -p mongo_pass
特定のフィールドのみを出力する
例えば、出力結果がJson形式でいかのようになっていたとします。
{ "id" :{ "date": { "name": "A-san } } }
nameフィールドのみを取り出したい場合は、以下のようにします。
db.alerts.find({} , {'id.date.name':1})
日付で検索(特定の日時より新しい日付で検索)
TimeStampが、2021-01-05T10:50:19より新しい場合。
db.<コレクション名>.find({ timestamp : { "$gt": ISODate('2021-01-05T10:50:19')}})
xx以上の場合は$gte xxより大きい場合は、$gt xx以下の場合は、$lte xx寄居小さい場合は、$lt
ドキュメントのデータを集計(加算する) aggregate()を利用
aggregateの基本的な使い方
db.コレクション名.aggregate([{$match: {検索条件}, {$group: {集計条件}}}] $matchは検索条件、$groupは集計の条件 $matchに関しては省略が可能
例えば、以下のようにtype、 timestamp , countからなるデータが保存されていたとします。
{ "type" : "Atype", "timestamp" : ISODate("2022-01-01T07:02:29Z"), "count" : 4}, { "type" : "Btype", "timestamp" : ISODate("2022-01-14T02:42:33Z"), "count" : 13), { "type" : "Btype", "timestamp" : ISODate("2022-01-12T12:32:29Z"), "count" : 34}、 { "type" : "Ctype", "timestamp" : ISODate("2022-01-12T12:32:29Z"), "count" : 34}
ここから、typeがBtypeのもので、かつ、timestampが2022-01-12T00:00:00+09:00以降のものだけ検索し、そのcountを加算するような操作は、以下のようなqueryになります。
db.alerts.aggregate( {$match: {Type: "Btype", timestamp: {$gt: ISODate("2022-01-12T00:00:00+09:00") } } } , { $group: { _id: "$Type", total: { $sum: "$count" } } } )
まず、$matchで検索条件を指定します。 次に、Typeのフィールドでグルーピングします。$groupの_id で指定されてる値がグルーピングする対象です。 そして、$sumで、countフィールドの値を加算します。 結果は以下のようになるはずです。
{ "_id" : "Btype", "total" : 47 }
ドキュメントの任意のデータを出力する $projectを利用
projectの基本的な使い方
aggregate()内で利用して、任意のデータフィールドを表示させます。SQLのselect col1, col2, col3 from DB; のようなイメージです。
例えば、以下のようなデータがあったとします。
{ "Type": "ABCDtype", "timestamp" : ISODate("2022-01-24T01:46:01Z"), "total" : 1 , "count" : 12 } { "Type": "ABCDtype", "timestamp" : ISODate("2022-05-22T11:36:02Z"), "total" : 1 , "count" : 12 } { "Type": "CDtype", "timestamp" : ISODate("2022-09-12T09:49:02Z"), "total" : 1 , "count" : 12 } { "Type": "Dtype", "timestamp" : ISODate("2022-12-24T03:41:141Z"), "total" : 1 , "count" : 12 }
以下のQueryは次のように動きます。
db.data.aggregate( {$match: {Type: "ABCDtype" } {$project: { "timestamp": 1, total: "$total" , count: "$count" , result : {"$divide" : ["$total", "$count"]} } } )
- $matchでTypeがABCDtypeのデータを選択します。
- そのなかから、$projectで出力したい、データを選択します。この場合は、timestamp, total, count, resultが出力されます。 timestamp:1とすることで、データが出力され、表示したくないときは、timestamp:0とします。 また、resultのフィールドは、新規に追加しています。resultの中身は、各データの$totalを$countで割った(divide)値を表示します。
このように任意の結果を$projectで加工して、表示できます。
mongodb外部からの操作
以下のように、 --evalコマンドを利用して、Mongo外から操作ができる。 ただし、外部から、コマンドを実行できるように設定を事前に実施する必要がある。 ”リモートホストのMongoDBへのログイン”を参照のこと。
mongo --host 192.168.10.2:27012 --eval "db.collection1.find().sort({_id: 1}).limit(1)" mongo_db_name-u mongo_user -p mongo_password
*注意点として、Queryで(とくにfind()で)ダブルクウォテーション”やシングルクウォテーションが利用されるが、escapeしないと、うまく検索できない場合がある。
コレクションデータの全件削除
db.コレクション名.remove({});
表示するコレクションの上限の設定を変更する
find()などで検索した結果の出力上限は20に設定されています。 これを変更するには、以下のようにします。出力上限が40になります。
DBQuery.shellBatchSize = 40
Mongo DBの障害調査
Mongoの設定ファイル
Mongの設定ファイルは通常以下に保存される。
/etc/mongod.conf
また、Mongのデータ保存バスは設定ファイル(mongod.conf)の”Strage:”で設定される。
#cat /etc/mongod.conf # Where and how to store data. storage: dbPath: /var/lib/mongodb journal: enabled: true
mongodが起動しない場合、上記のdbPath先がなく、デーモンが起動しない場合があるので、パスの確認が必要。
データ容量を調べる db.status()
db.status()でデータサイズを調べることができます。。 dataサイズあたりを見ればよいです。
> db.stats() { "db" : "pulse_database_alerts_alert", "collections" : 2, "views" : 0, "objects" : 477256, "avgObjSize" : 363.51303074241076, "dataSize" : 173488775, "storageSize" : 164175302656, "indexes" : 5, "indexSize" : 41529344, "totalSize" : 164216832000, "scaleFactor" : 1, "fsUsedSize" : 380248883200, "fsTotalSize" : 386358312960, "ok" : 1 }
ユーザー関連
ユーザー一覧表示
db.system.users.find()
ユーザ作成
ユーザは基本的に、データベースごとに作成します。データベースごとに作成されたユーザがそのデータベースへのアクセス権が付与されます。 ただし、adminデータベースで作成したユーザは、管理者となれます。
//データベースへの切り替え # use ”データベース名” // 特定のデータベースのみ管理者権限をもつユーザの作成 > db.createUser( { user: "ユーザ名", pwd: "パスワード", roles: [ { role: "userAdmin", db: "データベース名" } ] } )