mongodb - PHP 5.2.13 MongoCursorException 'duplicate key error index' -
i'm getting duplicate _ids when inserting documents our mongo database. intermittent problem happens under load (is reproducable test scripts).
here's test code don't think i'm trying double-insert same object (i know php mongo driver adds _id field):
// insert job $job = array( 'type' => 'cleanup', 'meta' => 'cleaning data', 'user_id' => new mongoid($user_id), 'created' => time(), 'status' => 'pending' ); $this->db->job->insert($job, array('safe' => true)); // <-- failz here
i went on frenzy , installed latest stable (1.1.4) mongo driver no avail. isn't under heavy load. we're doing maybe 5 req/s on 1 server, 16m rec/s limit inc value isn't issue.
any ideas appreciated. i'm hoping somewhere has used mongo php , inserted more 5 docs/s , had issue ;).
-edit-
on centos 5.4 x86_64, linux 2.6.18-164.el5xen, apache worker 2.2.15, php 5.2.13, mongodb 1.8.1
-edit2-
noted in comments, i'm using latest version of pecl driver of (1.2.0) , problem still happening.
-edit3-
forgot post exact error:
uncaught exception 'mongocursorexception' message 'e11000 duplicate key error index: hannibal.job.$_id_ dup key
there different solution (the preform/worker mpm didn't in case, running prefork default anyway).
the issue insert array passed reference, , modified php mongodb library include id. need clear id.
so imagine following code:
$atoinsert = array('field'=>$val1); $collection->insert($atoinsert); << have '_id' added $atoinsert['field'] = $val2 $collection->insert($atoinsert); << fail above error
why? happens library is:
$atoinsert = array('field'=>$val1); $collection->insert($atoinsert); // $atoinsert has '_id' added php mongodb library // therefore $atoinsert = array('field'=>$val1, '_id'=>mongoid() ); $atoinsert['field'] = $val2 // therefore $atoinsert = array('field'=>$val2, '_id'=>mongoid() ); $collection->insert($atoinsert); // not add '_id' exists. fail.
solution reinitialise array
$atoinsert = array('field'=>$val1); $collection->insert($atoinsert); $atoinsert = array('field'=>$val2); $collection->insert($atoinsert);
or unset id
$atoinsert = array('field'=>$val1); $collection->insert($atoinsert); unset($atoinsert['_id']); $atoinsert['field'] = $val2 $collection->insert($atoinsert); << work
Comments
Post a Comment