MongoCollection::update
(PECL mongo >=0.9.0)
MongoCollection::update — 指定した条件にもとづいてレコードを更新する
説明
public bool|array MongoCollection::update
( array $criteria
, array $new_object
[, array $options
= array()
] )
パラメータ
-
criteria
-
更新したいオブジェクトの条件。
-
new_object
-
マッチするレコードを更新するオブジェクト。
更新演算子を含めたり (特定のフィールドだけの更新用)、
ドキュメント全体を上書きしたりできます。
-
options
-
更新時のオプションの配列。
現在利用可能なオプションは、以下のとおりです。
-
"upsert"
$criteria
にマッチするレコードが見つからない場合に
新しいドキュメントを追加します。
新しいドキュメントを追加するときに
$new_object
にアトミックな修正子
($ 演算子) が含まれていれば、この操作を
$criteria
パラメータに適用して新しいドキュメントを作ります。
$new_object
がアトミックな修正子を含まない場合は、
そのままの形式で新しいドキュメントに使います。
詳細は、以下の upsert の例を参照ください。
-
"multiple"
$criteria にマッチするすべてのドキュメントを更新します。
MongoCollection::update() は
MongoCollection::remove() と正反対の動きをします。
デフォルトでは、マッチするすべてのドキュメントではなく
ひとつのドキュメントだけを更新するのです。
複数ドキュメントを更新したいのかそうでないのかは、
常に指定しておくことを推奨します。
将来、データベースのデフォルトの挙動が変わる可能性があるからです。
"fsync"
Boolean 型で、デフォルトは FALSE
です。
ジャーナリングが有効な場合、これは "j" とまったく同じ動きをします。
ジャーナリングが有効でない場合は、追加をディスク上のデータベースファイルに同期させるまで成功したと見なさないようになります。
TRUE
にすると確認つき書き込みが暗黙のうちに設定され、"w" の値を 0 にします。
注意: ジャーナリングが有効な場合は、"fsync" のかわりに "j" を使いましょう。
"fsync" と "j" を同時に指定すると、エラーになります。
"j"
デフォルトは FALSE
です。これを指定すると、追加をジャーナルに同期させるまで成功したと見なさないようになります。TRUE
にすると確認付き書き込みと見なされ、"w" の設定を 0 に上書きします。
注意: このオプションを使っているときにジャーナリングを無効にすると、MongoDB 2.6 以降ではエラーが発生して書き込みに失敗します。古いバージョンのサーバーでは、単純にオプションの指定を無視します。
"socketTimeoutMS"
このオプションは、ソケット通信の制限時間を、ミリ秒単位で指定します。この時間内にサーバーからの反応がなければ、MongoCursorTimeoutException をスローします。この場合、サーバー側で書き込み処理が行われたのかどうかを判断できなくなります。-1 を指定すると、永遠にブロックします。MongoClient のデフォルト値は 30000 (30 秒) です。
-
"w"
WriteConcerns を参照ください。MongoClient でのデフォルト値は 1 です。
"wTimeoutMS"
このオプションは、書き込み確認を待つ制限時間をミリ秒単位で指定します。これが書き込み操作に適用されるのは、"w" が 1 より大きい場合のみです。というのも、タイムアウトはレプリケーションに関する機能だからです。この時間内に書き込み確認ができなかった場合は MongoCursorException をスローします。0 を指定すると、永遠にブロックし続けます。MongoClient でのデフォルトは 10000 ミリ秒 (10 秒) です。
以下のオプションは廃止予定です。使ってはいけません。
"safe"
非推奨。write concern の w オプションを使いましょう。
"timeout"
非推奨。"socketTimeoutMS" のエイリアス。
"wtimeout"
廃止予定。"wTimeoutMS" のエイリアスです。
エラー / 例外
"w" オプションが設定されていて書き込みが失敗した場合に MongoCursorException をスローします。
"w" オプションの値が 1 より大きく設定されていて、操作の完了までの時間が MongoCursor::$timeout ミリ秒をこえた場合に MongoCursorTimeoutException をスローします。サーバー上での操作は止めません。これはクライアント側でのタイムアウトです。MongoCollection::$wtimeout はミリ秒です。
例
例1 MongoCollection::update()
address フィールドをドキュメントに追加します。
<?php
$c->insert(array("firstname" => "Bob", "lastname" => "Jones" ));
$newdata = array('$set' => array("address" => "1 Smith Lane"));
$c->update(array("firstname" => "Bob"), $newdata);
var_dump($c->findOne(array("firstname" => "Bob")));
?>
array(4) {
["_id"]=>
object(MongoId)#6 (0) {
}
["firstname"]=>
string(3) "Bob"
["lastname"]=>
string(5) "Jones"
["address"]=>
string(12) "1 Smith Lane"
}
例2 MongoCollection::update() での upsert
upsert を使うとコードを簡潔にすることができます。
オブジェクトが存在しない ($criteria
に基づく) 場合は新たに作成し、
存在する場合はそれを更新するという操作を一行で書けるからです。
次の例では、$new_object
にアトミックな修正子が含まれています。
コレクションは空なので upsert は新たなドキュメントを追加することになり、
これらの操作を
$criteria
パラメータに適用してドキュメントを作ります。
<?php
$c->drop();
$c->update(
array("uri" => "/summer_pics"),
array('$inc' => array("page hits" => 1)),
array("upsert" => true)
);
var_dump($c->findOne());
?>
array(3) {
["_id"]=>
object(MongoId)#9 (0) {
}
["uri"]=>
string(12) "/summer_pics"
["page hits"]=>
int(1)
}
$new_object
がアトミックな修正子
($ 演算子) を含まない場合、upsert は
$new_object
をそのままの形式で新しいドキュメントに使います。
これは通常の update の挙動と同じです。
アトミックな修正子を使わなければ、ドキュメント全体が上書きされます。
<?php
$c->drop();
$c->update(
array("name" => "joe"),
array("username" => "joe312", "createdAt" => new MongoDate()),
array("upsert" => true)
);
var_dump($c->findOne());
?>
array(3) {
["_id"]=>
object(MongoId)#10 (0) {
}
["username"]=>
string(6) "joe312"
["createdAt"]=>
object(MongoDate)#4 (0) {
}
}
例3 MongoCollection::update() での複数更新
デフォルトでは MongoCollection::update() は、
$criteria
にマッチするドキュメントが複数見つかっても最初のものだけを更新します。
必要なら、"multiple" オプションでその挙動を変えることができます。
この例は、翌日が誕生日である全員に "gift" フィールドを追加します。
<?php
$today = array('$gt' => new MongoDate(), '$lt' => new MongoDate(strtotime("+1 day")));
$people->update(
array("birthday" => $today),
array('$set' => array('gift' => $surprise)),
array("multiple" => true)
);
?>