帮助解决Django RemoteUserMiddleware与新数据库的RemoteUserBackend问题

3 投票
2 回答
3554 浏览
提问于 2025-04-16 16:57

Django 1.3版本新增了RemoteUserMiddlewareRemoteUserBackend这两个类,目的是让Apache可以进行用户身份验证。详细信息可以查看这个链接

我有一个叫做initial_data.json的文件,它在执行syncdb时会创建一个超级用户。通过dumpdata可以确认这一点。

但是我发现,使用新创建的数据库登录似乎不太正常。我收到了一个叫做ImproperlyConfigured的异常,内容是:Django的远程用户身份验证中间件需要安装身份验证中间件。

Edit your MIDDLEWARE_CLASSES setting to insert django.contrib.auth.middleware.AuthenticationMiddleware' before the RemoteUserMiddleware class.

错误追踪信息指向了RemoteMiddleware.process_request()

def process_request(self, request):
    # AuthenticationMiddleware is required so that request.user exists.
    if not hasattr(request, 'user'):
        raise ImproperlyConfigured(...

Apache的DEBUG输出显示,设置中确实按要求包含了AuthenticationMiddlewareRemoteUserMiddleware

MIDDLEWARE_CLASSES  
('django.middleware.common.CommonMiddleware',
 'django.contrib.sessions.middleware.SessionMiddleware',
 'django.middleware.csrf.CsrfViewMiddleware',
 'django.contrib.auth.middleware.AuthenticationMiddleware',
 'django.contrib.auth.middleware.RemoteUserMiddleware',
 'django.contrib.messages.middleware.MessageMiddleware')

但是,request.user属性没有被设置,这就导致了异常的产生。

如果我仔细查看django.contrib.auth.backends和中间件的源代码,我发现AuthenticationMiddleware为请求类注册了LazyUser。但是RemoteUserBackend似乎没有调用authenticate()方法,而这个方法是用来在用户表中查找remote_user的。

我应该做些什么才能让authenticate()被调用,从而创建request.user呢?

如果需要,我可以提供更多信息。顺便提一下,我正在使用SSL,这会不会有我没有预料到的影响?

我还应该提到,我使用的是Apache2.2.14和mod_wsgi

2 个回答

0

这真是个不太优雅的解决办法。

我创建了一个单元测试,结果在正常的开发环境中运行得很好。基于这个测试,我去修改了上面提到的 RemoteMilddleware.process_request() 函数,在Apache服务器上禁用了对 user 属性的测试。这样就正常工作了……

我并不打算把这个当作答案,但我觉得有必要把这个解决办法记录下来,方便其他遇到同样问题的人。我会考虑提交一个bug报告。

有没有人知道在Apache2中有什么合适的解决方案或者该怎么处理这个问题?所有的错误追踪信息和变量信息都表明Apache正确设置了REMOTE_USER,但Django1.3似乎没有正确使用它来进行身份验证。

2

我也遇到过同样的问题,经过一点调试后发现我忘了为认证和其他应用创建mysql(我觉得sqlite也是一样)表格。所以如果你还没创建的话,你需要运行命令 python manage.py syncdb,或者用其他方法来创建它们。

撰写回答