Re: [mongoose] getting "duplicate key error: dup key" error, with an empty array of embedded documents

736 views
Skip to first unread message

Aaron Heckmann

unread,
Jul 13, 2012, 2:08:41 PM7/13/12
to mongoo...@googlegroups.com
Make the foo_id index unique and sparse:

FooSchema = new Schema({
   foo_id: {type: Number, required: true, unique: true, sparse: true},
   foo_desc: String
});


On Fri, Jul 13, 2012 at 8:03 AM, getify <get...@gmail.com> wrote:
I have node 0.8.1 and mongoose 2.7.1 (with mongo 2.0.6). I have a structure like this:


FooSchema = new Schema({
   foo_id: {type: Number, required: true, unique: true},
   foo_desc: String
});

BarSchema = new Schema({
   bar_id: {type: Number, required: true, unique: true},
   foos: [FooSchema]
});


When I create a model out of `BarSchema`, everything is fine. When I create the first record in the `BarSchema` model, everything is fine. I do that something like this:


BarModel = mongoose.model("Bar",BarSchema,"Bar");

bar = new BarModel();
bar.bar_id = 1234;
bar.foos = []; // i want to have an empty array of `BarSchema`s for now.
bar.save();

That works fine, and indeed it creates an entry like:

{_id: ..., bar_id: 1234, foos: []}

But then later, I try to add another document to the BarModel, again like this:

bar2 = new BarModel();
bar2.bar_id = 5678;
bar2.foos = []; // again, want another empty array for now
bar2.save(function(err,result){
   console.log(err);
});

On that second document save, it complains that there's a duplicate key on `FooSchema.foo_id`, even though neither `BarModel` entry had any `FooSchema` instances, but were instead only empty arrays.

I tried also setting the `default` for the `foo_id` field to be `null`, but I get the same behavior.

What can I do?


--Kyle

--
http://mongoosejs.com
http://github.com/learnboost/mongoose
You received this message because you are subscribed to the Google
Groups "Mongoose Node.JS ORM" group.
To post to this group, send email to mongoo...@googlegroups.com
To unsubscribe from this group, send email to
mongoose-orm...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/mongoose-orm?hl=en



--
Aaron



getify

unread,
Jul 16, 2012, 11:22:26 AM7/16/12
to mongoo...@googlegroups.com
Thanks Aaron. That seems to have fixed my immediate problem.

However, it brings up something else I don't understand well. To which root is the "unique" index of Foo relative to? The database, the collection, or the parent document?

I would have expected to be able to do something like this:

Bar[0] {
   bar_id: 12345
   foos: [
      { foo_id: 5678, description: "yeah, baby!" }
      { foo_id: 5555, description: "oh wow" }
   ]
}

Bar[1] {
   bar_id: 67890
   foos: [
      { foo_id: 5555, description: "hello world" }  // is this a dup key or not?
   ]
}

But it would seem that this is not true? I'm confused where the `foo_id` unique index is relative to, if not to the containing `Bar` document?

If the above is indeed a violation of the unique index, then how does one enumerate all the current `Foo` id's, without doing a nested loop first over all the `Bar`s, and then over each of their `Foo` child records? That seems very inefficient.


--Kyle

Aaron Heckmann

unread,
Jul 16, 2012, 2:34:37 PM7/16/12
to mongoo...@googlegroups.com
On Mon, Jul 16, 2012 at 8:22 AM, getify <get...@gmail.com> wrote:
To which root is the "unique" index of Foo relative to? The database, the collection, or the parent document?

Mongo indexes are all collection level.

Bar[0] {
   bar_id: 12345
   foos: [
      { foo_id: 5678, description: "yeah, baby!" }
      { foo_id: 5555, description: "oh wow" }
   ]
}

Bar[1] {
   bar_id: 67890
   foos: [
      { foo_id: 5555, description: "hello world" }  // is this a dup key or not?
   ]
}

Yes that is a dup `foo_id` key.
 
If the above is indeed a violation of the unique index, then how does one enumerate all the current `Foo` id's, without doing a nested loop first over all the `Bar`s, and then over each of their `Foo` child records? That seems very inefficient.


Looping over every array of every doc in the collection is indeed inefficient. A different option is to use the ObjectId you get for free as the unique id in the FooSchema. Otherwise another guid generator will work.



--
Aaron



Reply all
Reply to author
Forward
0 new messages