MongoDBの最近のブログ記事

[続報]MongoDBをext3で使ったら死んだ

| カテゴリ:
MongoDBをext3で使ったら死んだ」の続報です。

(なお、「死んだ」との表現はオーバーではないかとのご指摘がありました。「病んだ」にしてもよかったのですが、私と同じ不幸を減らすためにはより多くの人にこの記事を見てもらった方がよいと考え、この表記にさせていただきました。)

ext4の導入に挑戦!

このまま本番サーバをext3で運用し続けるわけにはいかないので、ニフティクラウドでDisk200を100GB追加しようと決心。
(月額1万円もするんですのよ)

ディスクを作成して、ext4にフォーマットしてみる。

Javascriptが世界を支配する日

| カテゴリ:
JavaScript。
javascript-console.png
2005年ごろまでそれは、
「ホームページ」にアラートボックスを表示してうざがられたり、
マウスポインタの形を変えてユーザビリティを下げたり、
そういう存在でした。

インタラクティブなサイトといえばJavaアプレットかFlashでした。
Yahooオークションの残り時間表示、Yahooゲームのチャット機能などはJavaアプレットでした。
おしゃれなサイトはたいていFlashでした。

「JS冬の時代」「失われた10年」ということが言われました。
前回の記事 、 の続報です。

上記内容について、各方面から疑問の声がつぎつぎとよせられました。

↓  ↓ 


たったしかに。。
バージョン1.6.4で実験した私がアフォでした。

↓  ↓ 


ひえぇえ

↓  ↓ 


うわわぁぁあわわ

あの@yukihiro_matz様からもツイートが!!

MongoDBで、バッチ処理でテストデータを流し込みたいときはどうすればよいでしょうか?

実はとても簡単です。

任意のJavascriptファイルをmongoクライアントに渡してやるだけです。
$ bin/mongo hostname/dbname  --quite file.js

例:ダミーのユーザデータを1万件流し込む方法

下記のようなJavascriptをファイルを作成します。
LinuxのMongoDBはインストールがあっけないほど簡単です。
これは意外と知らていない事実です。

apt-getもyumもmakeも使いません。
root権限いりません。

3分と書きましたが実際のインストール作業は1分でできます。
なにせダウンロードして解凍するだけなのですから。

遊んだあとは作業ディレクトリをrmすることできれいさっぱり消せますので、気軽にやってみましょう!

MongoDBをインストールして起動するまで

インストールコマンドです。
前回の記事「MongoDBをext3で使ったら死んだ」の続きです。

ファイルアロケーションについてはext3よりext4の方が高速であることは既に触れました。
では具体的に何倍速度差があるのでしょうか?
気になったので実験してみました。

他の条件を全く同じにしてext3とext4でファイルアロケーションに要する時間を計測しました。

実験環境

MongoDBをext3で使ったら死んだ

| カテゴリ:
MongoDBをext3で使ってはいけません!
やったら死にます。

公式サイトには「ext3は非推奨」と書かれてますが、「非推奨」というか「禁じ手」です。
マジで死にます。

なぜext3でMongoDBを使ってはいけないのか

MongoDBにはpreallocateという仕組みがあり、保存に必要なデータ領域を前もってファイルシステム上に確保します。
わかりやすく言うと、「中身がゼロで埋められた巨大なファイルを前もって作成する」という振る舞いをします。

ところがext3は「巨大なファイルを作る」という処理が非常に苦手なのです。
shellにログインした状態でクエリ結果をファイルに保存しかったのですが、やり方が見つかりませんでした。

クエリをjsファイルとしてあらかじめ用意して、mongoクライアントに渡してやるとうまくいきました。

query.js
var query = {action:"hoge"};
db.userlog.find(query).forEach(function(x){ print(x.user_id); });
上記query.jsファイルをmongoクライアントに食わせると、結果を標準出力に吐いてくれます。
$ mongo  host/dbname query.js
MongoDB shell version: 2.0.1
connecting to: mem1/jp8122renshu
205368
206859
196658
152520
156449
156449
234470

MySQLやPostgreSQLでSQLファイル実行するような感覚で使えますね。

Enjoy!
追記
--quietオプションをつけると、余分な出力(バージョン表示とか)を抑制することができます。
$ mongo --quiet host/dbname query.js
205368
206859
196658
参考:MongoDBのshellを使い倒す

MongoDBのベストプラクティス10箇条

| カテゴリ:
MongoDB Best Practicesという面白い記事があったので意訳してみます。
書いた人はEngine Yardという会社のひとです。
(Amazon EC2でMongoDBを運用する場合を主に想定しているようです。)

1.必ずレプリカセット(replica sets)を使いましょう

MapReduceの処理は、はじめのうちはインタラクティブシェルで試行錯誤することになると思います。

しかしシェル上でコードを書く場合、繰り返し実行するのが不便だったり、コードをバージョン管理(Git/Subversion)システムにコミットできないとういデメリットがあります。
いろいろ試してみて手法が固まってきたら、JSコードをファイルとして保存した方がよいでしょう。

例えば、アクセスログの時間帯別集計をするMapRedcue処理を、下記のようにJSファイルとして保存します。
MapReduceでは、scopeオプションというのがあります。
これを使うと、あらかじめ作った自作関数をmap,reduce内から使うことができます。

利点は、
  • map関数本体がすっきりする
  • 単体テストがやりやすくなる

以前紹介した「MongoDB : サルでもわかるMapReduceその2:ログの時間別集計を行う」のアクセスログ集計を、scopeを使って実行してみます。

MongoDBにはJavaScriptで動くインタラクティブシェルがあります。

このシェルには、組み込みの変数やオブジェクトやメソッドがいろいろあるのですが、ヘルプやマニュアルにも書いてない便利なメソッドがたくさんあります。

例えば、Array.sumというメソッドがあって、配列の合計を求めたりできます。

Mongo shellでは、ログアウト時に変数が破棄される

MongoDBのshell上でグローバル関数を定義しても、いちどshellから抜けてしまうと関数は破棄されます。

$ ~/bin/mongo
> var wa = function (a,b){return a+b ;} 
> wa(2,3)
5
> exit
bye
(この時点で関数waは消滅する)

$ ~/bin/mongo

> wa(2,3)
Fri Dec 23 18:41:59 ReferenceError: wa is not defined (shell):1
(関数waはもう存在しない)

サーバ側に関数を保存する方法

前回の記事「MongoDB : サルでもわかるMapReduce」では、MapReduceを使った簡単な集計を行いました。
今回はもう少し実用的なことをしてみましょう。

アクセスログを時間帯別に集計する

accesslogというコレクションに、下記のようにユーザのアクセスログがたまっているとします。
> db.accesslog.find();
{ "_id" : ObjectId("4eed6c60ee5b36a552000000"), "user_id" : 141637, "timestamp" : ISODate("2011-11-01T15:00:00.223Z") }
{ "_id" : ObjectId("4eed6c60ee5b36a552000001"), "user_id" : 141637, "timestamp" : ISODate("2011-11-01T15:00:00.432Z") }
{ "_id" : ObjectId("4eed6c60ee5b36a552000002"), "user_id" : 115383, "timestamp" : ISODate("2011-11-01T15:00:02.994Z") }
{ "_id" : ObjectId("4eed6c60ee5b36a552000003"), "user_id" : 190968, "timestamp" : ISODate("2011-11-01T15:00:03.871Z") }
{ "_id" : ObjectId("4eed6c60ee5b36a552000004"), "user_id" : 160751, "timestamp" : ISODate("2011-11-01T15:00:05.071Z") }
{ "_id" : ObjectId("4eed6c60ee5b36a552000005"), "user_id" : 121768, "timestamp" : ISODate("2011-11-01T15:00:05.163Z") }
 

これを時間帯別に件数カウントしてみましょう。
MongoDBで日付情報を保存するときは、MongoDB標準のISODateで保存することが多いと思います。

ISODateで日付期間指定して検索する方法を紹介します。

例:2011-11-01から2011-11-02の期間を指定して検索する

MongoDBのデフォルトの日時オブジェクトはISODateというものです。

これの実装がどうなっているか調べてみました。

ISODateとは、関数であります。
ということは、ISODate関数のコードを可視化できれば、実装がわかるはずです。

Mongo Shell で"ISODate"とタイプしてみたら、コードの中身を表示することができました。

ISODateの実装

MongoDB : サルでもわかるMapReduce

| カテゴリ:
MongoDBにデータを入れたものの、何をどうしていいかわからないプログラマのみなさんこんにちわ。
今日はそんなあなたのために、MapReduceの超わかりやすい入門を書いてみました。

MapReduceで何ができるのか?

MapReduceについて勉強していたら、"emit"という見慣れない英単語が出てきたので調べてみました。

emit : 〈液体・光・熱・においなどを〉出す,放つ

電気自動車のことをよくゼロエミッションカー(Zero Emission Car)と言いますが、"emission"の動詞形が"emit"なんですね。

MongoDB速すぎワロタw

いま巷で話題のMongoDB。
どれくらい速いのかと、insertのパフォーマンスをPostgreSQLと測定してみました。

結果はMongoDBの方が10倍以上速かったです。
まさに爆速!!

人気記事

このアーカイブについて

このページには、過去に書かれたブログ記事のうちMongoDBカテゴリに属しているものが含まれています。

前のカテゴリはJScriptです。

次のカテゴリはPostgreSQLです。

最近のコンテンツはインデックスページで見られます。過去に書かれたものはアーカイブのページで見られます。

最近の人気記事