【问题标题】:Is Django middleware thread safe?Django 中间件线程安全吗?
【发布时间】:2011-06-02 12:29:26
【问题描述】:

Django 中间件线程安全吗?我可以这样做吗,

class ThreadsafeTestMiddleware(object):

    def process_request(self, request):
        self.thread_safe_variable = some_dynamic_value_from_request

    def process_response(self, request, response):
        # will self.thread_safe_variable always equal to some_dynamic_value_from_request?

【问题讨论】:

    标签: python django thread-safety middleware


    【解决方案1】:

    为什么不将你的变量绑定到请求对象,像这样:

    class ThreadsafeTestMiddleware(object):
    
        def process_request(self, request):
            request.thread_safe_variable = some_dynamic_value_from_request
    
        def process_response(self, request, response):
            #... do something with request.thread_safe_variable here ...
    

    【讨论】:

    【解决方案2】:

    不,绝对不是。我写了关于这个问题here - 结果是在中间件类中存储状态是一个非常糟糕的主意。

    正如史蒂夫指出的那样,解决方案是将其添加到请求中。

    【讨论】:

    【解决方案3】:

    如果您在多线程的守护模式下使用 mod_wsgi,这些选项都不起作用。

    WSGIDaemonProcess domain.com user=www-data group=www-data threads=2

    这很棘手,因为它将与 django 开发服务器(单个本地线程)一起使用,并根据线程的生命周期在生产中产生不可预测的结果。

    在 mod_wsgi 下设置请求属性和操作会话都不是线程安全的。由于 process_response 将请求作为参数,因此您应该在该函数中执行所有逻辑。

    class ThreadsafeTestMiddleware(object):
    
        def process_response(self, request, response):
            thread_safe_variable = request.some_dynamic_value_from_request
    

    【讨论】:

    • 这是不正确的。您的请求/响应对象不在线程和/或请求之间共享,因此可以安全使用。
    • 对我不起作用。我遇到过第一个用户的请求数据被设置为线程生命周期并导致问题的情况。
    • 请求对象是在请求开始时创建的,直到请求通过所有中间件类、被处理并再次通过中间件返回时才被释放。这与线程无关 - 整个过程都是同一个非共享对象。
    • 完全有道理,但这被破坏了并且总是粘贴第一个用户的数据。 pastebin.com/zJ5wct3Z
    • 这里不正确的是你使用了self.refcode = refcode。将其更改为request.refcode = refcode,然后在process_response 方法中从request.refcode 读回。我希望这会有所帮助。
    猜你喜欢
    • 2012-06-01
    • 1970-01-01
    • 2013-11-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-09-03
    相关资源
    最近更新 更多