如何在循环中使用批量upsert?

时间:2017-06-02 06:29:12

标签: python mongodb mongodb-query pymongo

我在Mongoldb的领域是; id,website_url,status。

我需要找到website_url并将其状态更新为3并添加一个名为err_desc的新字段。

我有一个website_urls列表,它的状态和err_desc。

以下是我的代码。

client = MongoClient('localhost', 9000)
db1 = client['Company_Website_Crawl']
collection1 = db1['All']
posts1 = collection1.posts
bulk = posts1.initialize_ordered_bulk_op()
website_url = ["http://www.example.com","http://example2.com/"]
err_desc = ["error1","error2"]
for i in website_url:
    parsed_uri = urlparse(i)
    domain = '{uri.scheme}://{uri.netloc}/'.format(uri=parsed_uri)
    final_url = domain
    final_url_strip = domain.rstrip("/")
    print i,final_url,final_url_strip,"\n"
    try:
        k = bulk.find({'website_url':i}).upsert().update({'$push':{'err_desc':err_desc,'status':3}})
        k = bulk.execute()
        print k
    except Exception as e:
        print "fail"
        print e

错误

  

发生了错误的批处理操作错误

     

fail批量操作只能执行一次。

最初我用过

k =  posts1.update({'website_url':final_url_strip},{'$set':{'err_desc':err_desc,'status':3}},multi=True)

5M记录太慢了。所以我想使用批量更新选项。请帮助我在这种情况下使用批量upsert。

1 个答案:

答案 0 :(得分:0)

错误消息告诉您在调用execute()后需要重新初始化批量写入操作。但问题是,你做错了。在这种情况下,您需要在for循环结束时调用execute,如下所示:

from itertools import count


ct = count()

for url in website_url:
    ...
    try:
        bulk.find({'website_url':i}).upsert().update({'$push':{'err_desc':err_desc,'status':3}})
        val = next(ct)
    except Exception as e:
        ...
if val > 0:
    bulk.execute()     

另请注意,Bulk()现已弃用,已替换为bulkwrite