ドキュメントを検索する

コレクション内のドキュメントを検索/表示してみます。
* ドキュメントを検索・表示する
* 特定のドキュメントを検索・表示する
* 特定のオブジェクトを含むドキュメントを検索・表示する


ドキュメントを検索・表示する

ドキュメントを検索・表示するにはfind()メソッドを使用します。

> db.foods.find()

引数を指定しない場合、もしくは空のオブジェクト({})を指定した場合は、すべてのドキュメントを対象とします。SQLでいうとselect * from foods;という構文に相当します。

では、事前に下記4件のデータをfoodsコレクションに登録します。

{ "name" : "栄太楼", product : [ { name : "五色羽二重餅", price : 702 }, { name : "羽二重きなこ餅", price : 756 } ] }
{ "name" : "天たつ", product : [ { name : "越前仕立て汐うに", price : 5400 }, { name : "小鯛ささ漬け", price : 1296 } ] }
{ "name" : "はや川", product : [ { name : "羽二重くるみ", price : 660 }, { name : "おやき", price : 120 } ] }
{ "name" : "松岡軒", product : [ { name : "羽二重餅", price : 735 }, { name : "羽二重どら焼", price : 1085 } ] }

nameに店の名前が入っています。また、productという配列の中に、name(商品名)とprice(値段)というオブジェクトが複数格納されています。

で、find()メソッドを実行すると、下記のようにすべてのドキュメントが返ってきます。

> db.foods.find()
{ "_id" : ObjectId("570b6877501ef26c7925cd72"), "name" : "栄太楼", "product" : [ { "name" : "五色羽二重餅", "price" : 702 }, { "name" : "羽二重きなこ餅", "price" : 756 } ] }
{ "_id" : ObjectId("570b6877501ef26c7925cd73"), "name" : "天たつ", "product" : [ { "name" : "越前仕立て汐うに", "price" : 5400 }, { "name" : "小鯛ささ漬け", "price" : 1296 } ] }
{ "_id" : ObjectId("570b6877501ef26c7925cd74"), "name" : "はや川", "product" : [ { "name" : "羽二重くるみ", "price" : 660 }, { "name" : "おやき", "price" : 120 } ] }
{ "_id" : ObjectId("570b6877501ef26c7925cd75"), "name" : "松岡軒", "product" : [ { "name" : "羽二重餅", "price" : 735 }, { "name" : "羽二重どら焼", "price" : 1085 } ] }

このうち、"_id" : ObjectId("xxxx")の部分は、ドキュメント追加時にMongoDBが自動で付け足してくれるIDです。非表示にしたい場合は、第2引数に{"_id":0}というオブジェクトを指定します。

> db.foods.find({}, {"_id":0})
{ "name" : "栄太楼", "product" : [ { "name" : "五色羽二重餅", "price" : 702 }, { "name" : "羽二重きなこ餅", "price" : 756 } ] }
{ "name" : "天たつ", "product" : [ { "name" : "越前仕立て汐うに", "price" : 5400 }, { "name" : "小鯛ささ漬け", "price" : 1296 } ] }
{ "name" : "はや川", "product" : [ { "name" : "羽二重くるみ", "price" : 660 }, { "name" : "おやき", "price" : 120 } ] }
{ "name" : "松岡軒", "product" : [ { "name" : "羽二重餅", "price" : 735 }, { "name" : "羽二重どら焼", "price" : 1085 } ] }

特定のドキュメントを検索・表示する

では、find()メソッドの引数にオブジェクトを指定し、検索条件を追加してみます。
{ キー:値 }というオブジェクトを指定した場合、そのキーと値のペアを持つドキュメントのみを取得します。SQLでいうとselect * from foods where name="文字列";という構文に相当します。

> db.foods.find({name:"はや川"}, {"_id":0})
{ "name" : "はや川", "product" : [ { "name" : "羽二重くるみ", "price" : 660 }, { "name" : "おやき", "price" : 120 } ] }

部分一致で検索を行うには、正規表現を用います。SQLでいうとselect * from foods where name like "%文字列%";などの構文に相当します。

> db.foods.find({name:/栄/}, {"_id":0})
{ "name" : "栄太楼", "product" : [ { "name" : "五色羽二重餅", "price" : 702 }, { "name" : "羽二重きなこ餅", "price" : 756 } ] }

特定のオブジェクトを含むドキュメントを検索・表示する

ここからがMongoDBの真骨頂ですよ。

では、「羽二重餅」という文字列を含む商品名があるドキュメントを検索してみます。商品名にアクセスするためのキーは"product.name"になります。

> db.foods.find({"product.name":/羽二重餅/}, {"_id":0})
{ "name" : "栄太楼", "product" : [ { "name" : "五色羽二重餅", "price" : 702 }, { "name" : "羽二重きなこ餅", "price" : 756 } ] }
{ "name" : "松岡軒", "product" : [ { "name" : "羽二重餅", "price" : 735 }, { "name" : "羽二重どら焼", "price" : 1085 } ] }

ではでは、値段が1,000円以上の商品があるドキュメントを検索してみます。キーを"product.price"とし、また「1000以上」を指定するには$gte演算子を用いて{$gte:1000}と指定します。

> db.foods.find({"product.price":{$gte:1000}}, {"_id":0})
{ "name" : "天たつ", "product" : [ { "name" : "越前仕立て汐うに", "price" : 5400 }, { "name" : "小鯛ささ漬け", "price" : 1296 } ] }
{ "name" : "松岡軒", "product" : [ { "name" : "羽二重餅", "price" : 735 }, { "name" : "羽二重どら焼", "price" : 1085 } ] }

続いて、値段が600円以上、700円未満の商品があるドキュメントを検索してみます。$and演算子を使用し、配列内に$gte演算子と$lt演算子を使用して条件を指定します。

> db.foods.find({$and: [ {"product.price": {$gte: 600}}, {"product.price": {$lt: 700}} ]}, {"_id":0})
{ "name" : "はや川", "product" : [ { "name" : "羽二重くるみ", "price" : 660 }, { "name" : "おやき", "price" : 120 } ] }

続いて、「羽二重くるみ」または「羽二重どら焼」という商品があるドキュメントを検索してみます。$or演算子でも検索できますが…

> db.foods.find({$or: [ {"product.name": "羽二重くるみ"}, {"product.name": "羽二重どら焼"} ]}, {"_id":0})
{ "name" : "はや川", "product" : [ { "name" : "羽二重くるみ", "price" : 660 }, { "name" : "おやき", "price" : 120 } ] }
{ "name" : "松岡軒", "product" : [ { "name" : "羽二重餅", "price" : 735 }, { "name" : "羽二重どら焼", "price" : 1085 } ] }

$in演算子を使用すると、表記をより簡略化できます。

> db.foods.find({"product.name": {$in: [ "羽二重くるみ", "羽二重どら焼" ]}}, {"_id":0})
{ "name" : "はや川", "product" : [ { "name" : "羽二重くるみ", "price" : 660 }, { "name" : "おやき", "price" : 120 } ] }
{ "name" : "松岡軒", "product" : [ { "name" : "羽二重餅", "price" : 735 }, { "name" : "羽二重どら焼", "price" : 1085 } ] }