MongoDB插入引发重复键错误

时间:2013-07-08 14:28:54

标签: python mongodb pymongo database

尝试在 mongodb集合中进行批量插入时出现以下错误。

  

pymongo.errors.DuplicateKeyError:E11000重复键错误索引:   cmdDistros.locDistro。$ id dup key:{:   ObjectId('51dac9d0c74cd81acd85c0fd')}

我在创建任何文档时都没有指定_id,所以mongodb应该创建唯一的索引吗?这是我使用的代码:

#Populate database with uniform distribution
            entries = []
            for coor in freeIndices:
                for theta in range(360):
                    entry = {"x" : coor[0], "y" : coor[1], "heading" : theta}
                    for i in range(numData):
                            entry["data" + str(i)] = 1./numData
                    entries.append(entry)
            print "Entries created, loading into database..."

            locDistro.insert(entries)

从mongoDB手中夺走命运,我尝试使用以下方法创建自己的索引:

#Populate database with uniform distribution
            entries = []
            idNum = 0
            for coor in freeIndices:
                for theta in range(360):
                    print idNum
                    entry = {"_id" : idNum, "x" : coor[0], "y" : coor[1], "heading" : theta}
                    idNum += 1
                    for i in range(numData):
                            entry["data" + str(i)] = 1./numData
                    entries.append(entry)
            print "Entries created, loading into database..."

            locDistro.insert(entries, manipulate = False)

print语句显示了每个idnum,因为文档已经创建,并且它们都是唯一的,并且正如预期的那样递增。但是在插入时,我收到了错误:

  

pymongo.errors.DuplicateKeyError:E11000重复键错误索引:   cmdDistros.locDistro。$ id dup key:{:0}

并且只有一个文档被插入到我的数据库中。

我完全被难过,任何人都可以回答为什么会发生这种情况?

5 个答案:

答案 0 :(得分:17)

您需要了解您的条目列表中包含一系列对一个条目dict的引用。因此,当PyMongo设置条目[0] ['_ id']时,所有其他条目都获得相同的_id。 (实际上,PyMongo会遍历列表设置每个条目的_id,因此所有条目最后都会有 final _id。)快速解决方法是:

entries.append(entry.copy())

这只是一个浅层副本,但在您分享的代码中我相信这足以解决您的问题。

答案 1 :(得分:4)

删除密钥"_id"

for i in xrange(2): 
    doc['i'] = i 
    if '_id' in doc: 
        del doc['_id'] 
    collection.insert(doc)

或手动创建一个新的:

from bson.objectid import ObjectId

for i in xrange(2): 
    doc['i'] = i 
    doc['_id'] = ObjectId() 
    collection.insert(doc)

Getting "err" : "E11000 duplicate key error when inserting into mongo using the Java driver

答案 2 :(得分:2)

使用insert_one()insert_many()时也遇到相同的错误

我的解决方案是将update_one()upsert=True一起使用

  doc = {a: 1, b:2, x:{xx:"hello",yy:"world"}}
  db.collection.update_one(doc,{'$set':doc},upsert=True)

这对我有用:-)

答案 3 :(得分:0)

确保每次插入后清除变量“ entries”。

问题是,如果 _id 字段不存在,PyMongo会在文档中注入一个 _id 字段( _id 总是在客户端生成)。这意味着插入方法会首次添加循环 _id 。由于'entries'是在外部定义的,因此每次循环遍历后,对 _id 使用相同的值。

在循环语句顶部清除dict变量。

OR

从dict中删除_id。例如:

del my_dict['_id'] 

答案 4 :(得分:0)

解决方案:在循环中声明dict()项目,然后填充并插入它。 使用 pymongo 中的 insert_one()时,我遇到了类似的问题。我通过在循环内声明 dict()项目解决了我的问题。 这是您的代码的工作版本:

#Populate database with uniform distribution
            entries = []
            for coor in freeIndices:
                for theta in range(360):
                    entry = dict()
                    entry['x'] = coor[0]
                    entry['y'] = coor[1]
                    entry['heading'] = theta
             
                    for i in range(numData):
                            entry['data' + str(i)] = 1./numData
                    entries.append(entry)
            print "Entries created, loading into database..."

            locDistro.insert(entries)