【问题标题】:What is the purpose of Django's request._cached_user?Django 的 request._cached_user 的目的是什么?
【发布时间】:2015-06-23 03:29:54
【问题描述】:

刚接触 Django 并真正尝试建立对其内置身份验证和会话机制的扎实掌握。查看当前(v1.8)源代码,我看到了:

django/contrib/auth/middleware.py

def get_user(request):
    if not hasattr(request, '_cached_user'):
        request._cached_user = auth.get_user(request)
    return request._cached_user

class AuthenticationMiddleware(object):
    def process_request(self, request):
        assert hasattr(request, 'session'), (
            "The Django authentication middleware requires session middleware "
            "to be installed. Edit your MIDDLEWARE_CLASSES setting to insert "
            "'django.contrib.sessions.middleware.SessionMiddleware' before "
            "'django.contrib.auth.middleware.AuthenticationMiddleware'."
        )
        request.user = SimpleLazyObject(lambda: get_user(request))

当我通过 Django 代码 grep 时,我看不到任何其他地方引用了 request._cached_user,并且除了身份验证中间件中的 lambda 之外,没有其他地方调用这个特定的 get_user()。除非我不懂中间件,否则 process_request() 每个请求只会调用一次。

我是否错过了一个明显的原因,为什么 Django 将 _cached_user 存储在 request 中,不再引用它?

【问题讨论】:

  • 你能弄明白吗?看不懂下面的答案!太奇怪了,其他任何地方都没有提到_cached_user

标签: django django-authentication django-sessions


【解决方案1】:

只是解释德怀特的回答:

我猜get_user() 函数在一个请求-响应周期中在不同的地方被多次调用。鉴于 request 是“全局”(技术上不是全局范围)变量,因此将用户对象设置为请求属性是有意义的。

【讨论】:

    【解决方案2】:

    作为一般 Django MVC 模式的一部分,视图通过请求(未登录的用户)。

    但是,在任何使用登录/身份验证的 Django 应用程序中,访问经过身份验证的用户模型是一项常见操作。

    框架(尤其是 AuthenticationMiddleware)假定与请求关联的经过身份验证的用户在处理每个 Web 请求期间不会更改。

    出于性能原因,get_user 函数保留关联用户的引用,从而避免对关联用户的重复数据库查询。

    【讨论】:

    • 知道request._cached_userrequest.user 有何不同吗?我能想到的唯一可能性是 Django 试图减轻在查看代码中重新分配 request.user 的情况。
    • _cached_user 属性的存在不会停止/避免在请求处理期间设置“用户”属性。我很确定它归结为使用 SimpleLazyObject 反过来要求始终返回相同的对象(在复制的情况下)。
    猜你喜欢
    • 2011-08-22
    • 2016-09-08
    • 2014-05-14
    • 1970-01-01
    • 2020-06-15
    • 2011-11-14
    • 1970-01-01
    • 2019-01-06
    • 1970-01-01
    相关资源
    最近更新 更多