Django-从URL中删除www



我已经将其添加到我的.htacces:中

RewriteEngine on
RewriteCond %{HTTP_HOST} ^www.
RewriteRule ^(.*)$ http://example.com/$1 [R=301,L]

但尝试联系www.example.com会将我重定向到:

http://example.com/example/wsgi.py/

因为我的httpd.conf中有WSGIScriptAlias / home/www/example.com/example/wsgi.py指令,当然我会得到404错误。

最终,我通过在urls.py:中添加下一行,成功地修复了

url(r'^example/wsgi.py/$', index),(因此重定向到主页)

但我不太确定这是否是正确的方法(因为当我尝试访问example.com时,我看到网络浏览器很快将地址更改为www.example.com,然后再次更改为example.com

如果有人会问,是的,我看到过这个,但这对我也没有帮助,因为浏览器会遇到url递归问题(example.com/example.com/example.com/sample.com/example.com…)

编辑:文件夹结构

这是我的文件夹结构:

mysite static media .htaccess manage.py mysite templates templatetags tinymce static urls.py settigs.py views.py wsgi.py models.py forms.py __init__.py

我知道这个问题已经回答了一段时间,但要添加到上面给出的答案中,请使用

host.startswith('www.')

它更具可读性,而且您应该使用永久重定向来为浏览器提供正确的响应标头。

from django import http
class NoWWWRedirectMiddleware(object):
    def process_request(self, request):
        host = request.get_host()
        if host.startswith('www.'):
            if request.method == 'GET':  # if wanna be a prefect REST citizen, consider HEAD and OPTIONS here as well
                no_www_host = host[4:]
                url = request.build_absolute_uri().replace(host, no_www_host, 1)
                return http.HttpResponsePermanentRedirect(url)

我发现使用中间件实现无www重定向要比使用Apache mod_rewrite config简单得多。

您链接到的中间件看起来像是完成了任务。我猜你的问题来自Apache配置-确保删除所有mod_rewrite命令(Rewrite*的东西),然后重新启动Apache服务器(参考Apache文档,但检查你的操作系统,可能是特定的)。

你只需要做一个额外的调整:确保你不会重定向任何POST请求,因为这可能会导致数据丢失(切线参考:为什么HTTP没有POST重定向?)。

无论如何,这就是我使用的,对我来说效果很好:

from django.http import HttpResponseRedirect
class NoWWWRedirectMiddleware(object):
    def process_request(self, request):
    if request.method == 'GET':  # if wanna be a prefect REST citizen, consider HEAD and OPTIONS here as well
        host = request.get_host()
        if host.lower().find('www.') == 0:
            no_www_host = host[4:]
            url = request.build_absolute_uri().replace(host, no_www_host, 1)
            return HttpResponseRedirect(url)

要使用它,请将它放在某个文件中,可能是mysite/mysite/middleware.py。然后确保它在您的settings.py:中运行

MIDDLEWARE_CLASSES = (
    'mysite.middleware.NoWWWRedirectMiddleware',
    # ... other middleware ...

如果你的settings.py中没有MIDDLEWARE_CLASSES,那么从Django文档中复制默认值,但让你看到的是Django的正确版本,1.7中有一些更改!

适用于Django 1.11+风格中间件的修改版本:

from django.http import HttpResponsePermanentRedirect
class NoWWWRedirectMiddleware:
    def __init__(self, get_response=None):
        self.get_response = get_response
    def __call__(self, request):
        response = self.process_request(request)
        return response or self.get_response(request)
    def process_request(self, request):
        host = request.get_host()
        if host.startswith('www.'):
            if request.method == 'GET':
                no_www = host[4:]
                url = request.build_absolute_uri().replace(host, no_www, 1)
                    return HttpResponsePermanentRedirect(url)

此Apache配置适用于我:

RewriteEngine On
RewriteCond %{HTTP_HOST} ^www.example.com$ [NC]
RewriteRule ^(.*)$ http://example.com$1 [R=301,L]
WSGIScriptAlias / /home/www/example.com/example/wsgi.py
WSGIPythonPath /home/www/example.com/example
<Directory /home/www/example.com/example>
  <Files wsgi.py>
    Require all granted
  </Files>
</Directory>

最新更新