【问题标题】:How to correctly connect to mongodb in Celery worker?如何在 Celery worker 中正确连接到 mongodb?
【发布时间】:2018-06-01 14:34:54
【问题描述】:

学习 Celery,阅读 Celery Best Practices,并有一个关于 Celery 数据库使用的非常简单的问题。

德尼·贝托维奇 说:

您不应将数据库对象(例如您的用户模型)传递给 后台任务,因为序列化的对象可能包含陈旧的 数据。

那么,如果我想在worker中连接数据库,什么是正确的选择:

@app.task
def add(x, y, collection):
    client = MongoClient('mongodb://localhost:27017/')
    db = client.wakawaka
    db[collection].insert_one({'sum':x+y})
    return True

或:

client = MongoClient('mongodb://localhost:27017/')
db = client.wakawaka

@app.task
def add(x, y, collection):
    db[collection].insert_one({'sum':x+y})
    return True

?

UPD:我可以在每个任务结束时close()我的mongodb连接,所以每次我需要一些东西时,任务都会连接到新的数据库,不会浪费资源。不过,我是否需要多次打开/关闭数据库连接?或者我可以连接一次并以某种方式刷新连接以检索新版本的数据库?

【问题讨论】:

    标签: python mongodb celery pymongo celery-task


    【解决方案1】:

    打开/关闭每个事务的数据库连接可以避免因数据过时或不正确而导致的错误,因为事务是独立执行的。还简化了数据库事务的生命周期管理。

    您可以在连接上下文管理器块中编写您的事务。这处理关闭连接,因此无需显式关闭连接。它也是线程安全的。您还可以利用内置的连接池在出现异常时重试。

    @app.task
    def add(x, y, collection):
        with MongoClient('mongodb://localhost:27017') as connection:
            db = connection.db
            db.collection.insert_one({'sum':x+y})
        return True
    

    请注意,如果您要更新多个文档,这不会维护数据更新的事务完整性。

    从 Mongodb 4.0.0 和 pymongo 3.7 开始,它们开始支持多文档 ACID 事务。

    【讨论】:

    • 不确定使用gevent时是否是这种情况
    猜你喜欢
    • 2017-11-26
    • 2013-01-09
    • 2021-06-15
    • 2019-10-15
    • 2023-04-04
    • 1970-01-01
    • 2023-04-09
    • 2021-06-23
    • 1970-01-01
    相关资源
    最近更新 更多