くろねこ日記

ソフトウェアに関する技術メモが多いです.

MongoDBつかってみた

はじめに

Flaskやsinatraを使ってウェブアプリケーションを作成する際に,どのDBを採用するかというのは仕様決定上重要になります.

僕はこれまでDBというとMySQLSQLiteのようなRDBMSを使っていたのですが,sinatra札幌さんのほうでflask上でNoSQLであるMongoDBを使用する機会を頂き,ここにMongoDBの概要と使い方,Pythonからどう制御するのかについて簡単にまとめました.

MongoDBとは

RDBMSを使用していた方にとってはMongoDBはちょっと異質に見えるかもしれません. RDBMSではデータ構造を明確化し,数学的な堅牢性を持っているイメージですね.SQLとよばれる言語を使用することでデータのソーティングなどを行ないます.

MongoDBではデータ構造はRDBほど明確化しなくても使用することができ,SQLのような言語を使う必要がありません.ドキュメント指向データベースと呼ばれており,データのやりとりはドキュメントとよばれる構造データにJSON形式で記述して使います.そのためプログラミング言語からSELECT * FROM テーブル名のようにコード中にSQLを書くこと必要がなく,使用言語がJSONフォーマットを扱えさえすれば配列やリストのような形でDBを操作できます.

MongoDBの用語

RDBMSを使用しているとデータベースの選択やレコードの選択などを考えてしまいますが,MongoDBは独特のドキュメント指向データベースと呼ばれている通りRDBMSとは異なる概念を持っています. ここではその概念と用語についてまとめてみました.

  • データベース:一つのアプリケーションで使用するコレクションを格納しておくもの.コレクションは複数持つことができる.

  • コレクション:ドキュメントを格納しておくもの.複数のドキュメントを持つことができる.

  • ドキュメント:商品ID,品名,価格などのデータそのものを格納できる.商品ID,品名のみなど可変長に扱える.入力形式はハッシュのようにKeyとValueの関係で保持される.

つまり包含関係で言えば「ドキュメント⊆コレクション⊆データベース」となります.

とりあえず動かしてみる

MongoDBを起動した状態で「mongodb」とシェル上からタイプするとMongoDBにアクセスできます.ここでは次のようなものを満すデータベースを作ってみましょう.

  • データベース名:examDBという学校の試験を

*コレクション:Math, Englishの2教科を現わすコレクション

*ドキュメント:Name,Gradeの2項目.ただしGradeはテストを受けていない場合はつけない場合がある.

*要素:NameはTaro,Jiro, Saburoの3人.Taroは「Math40点,Englishは受けていない」. JIroは「Math100点,Englishは80点」.Saburoは「Mathは90点Englishは70点」.

データベースの生成や選択は

 use examDB

としEnterを叩くだけです.簡単ですね 次にコレクション名とドキュメントを生成します.コレクションはMathとEnglishの2項目,ドキュメントはNameとGradeの2項目ですね.MongoDBではそれらを直接指定できます. まずはMathにそれぞれ項目を入力していきましょう.

db.Math.insert({Name : "Taro", Grade: "40"})
db.Math.insert({Name : "Jiro", Grade: "100"})
db.Math.insert({Name : "Saburo", Grade: "90"})

です. dbは上記のuseコマンドでexamDBをすでに選択しています.db.Mathとすることでコレクション名Mathを生成し操作できます.次にドキュメントを挿入したいのでdb.Math.insertのように指定できます.insertについては中身はJSONフォーマットで入力するだけなのでdb.Math.insert({ドキュメント項目名(Key) : ドキュメント項目値(Value), ・・・})です. 上記では3項目あるので3行分記述してます.

次にEnglishについても同様に打ちましょう.

db.English.insert({Name : "Taro"})
db.English.insert({Name : "Jiro", Grade: "80"})
db.English.insert({Name : "Saburo", Grade:"70"})

ですね.Taroは受けていないのでGradeの項目は入力してません.

では次は挿入されたデータを呼び出してみましょう. たとえば,Mathを呼び出したいときには MongoDBでは

db.Math.find()

だけです.これで入力した3項目が返ってきます.

MathのうちTaroのデータだけ呼びたいときには

db.Math.find(Name:"Taro")

だけです.

ここでは触れてませんが,コレクションの中にも子コレクションを生成することもできます. その場合もコレクション名が増えるだけで操作は,findやinsertを使用することができます.

PythonからMongoDBを操作する

PythonからMongoDBを操作してみましょう. PythonからMongoDBを扱えるライブラリにpymongoというのがあります. 「pip install pymongo」とタイプすることでインストールができると思います.

では先程の操作をpymongoからやってみましょう

from pymongo import MongoClient

client = MongoClient()#接続先を指定Localhostの場合はvoidで良い
db = client['examDB']#データベースを選択
#Mathの項目追加
db.Math.insert({'Name' : 'Taro', 'Grade':'40'})
db.Math.insert({'Name' : 'Jiro', 'Grade': '100'})
db.Math.insert({'Name' : 'Saburo', 'Grade': '90'})
#Englishの項目追加
db.English.insert({'Name' : 'Taro'})
db.English.insert({'Name' : 'Jiro', 'Grade': '80'})
db.English.insert({'Name' : 'Saburo', 'Grade':'70'})
#Mathのfind
for data in db.Math.find():
     print(data)
#MathのTaroだけ呼びだす
for data in db.Math.find({'Name':'Taro'}):
     print(data)

これらの形であればリストに格納したりイテレータのような形で扱うことができますね.

まとめ

MongoDBはRDBMSとは違ったSQLを使用しないデータベースであり,Jsonフォーマットでデータを扱えます.

概念用語としてデータベース,コレクション,ドキュメントがあります. ここでは学校のテストデータを例にmongoDBとPython上で試してみました.