【问题标题】:Safe to modify settings.SITE_ID from middleware in Django?从 Django 的中间件修改 settings.SITE_ID 是否安全?
【发布时间】:2010-08-12 01:56:58
【问题描述】:

我已经修改了我在http://effbot.org/zone/django-multihost.htm 找到的 multihost.py 中间件,以动态设置 settings.SITE_ID,但有些担心我可能刚刚离开预订。

我发现的多域托管的大多数示例都是使用硬编码到各自 SITE_ID 的多个 settings.py 文件设置的。

我是否在这里创建了具有致命缺陷的修复程序?会动态改变这个值吗?

from django.conf import settings
from django.contrib.sites.models import Site

class MultiHostMiddleware:

    def process_request(self, request):
        try:
            host_raw = request.META["HTTP_HOST"]
            colon = host_raw.find(':')
            if colon > -1:
                host = host_raw[0:colon]
            else:
                host = host_raw

            s = Site.objects.get(domain=host)
            if s:
                settings.SITE_ID = s.id

        except KeyError:
            pass # use default urlconf (settings.ROOT_URLCONF)

对于好奇的人来说,到目前为止它已经启动并运行,但还没有经受住实际流量。

【问题讨论】:

  • 不知道这是否可行,但我想知道使用urlparse 是否会更好地获取主机名(docs.python.org/library/urlparse.html)。
  • 附加信息,此代码已经在一个 2 域站点上使用了大约一周,没有明显的故障。流量相当低,但我认为这个概念成立。

标签: django django-middleware django-sites


【解决方案1】:

简短的官方回答是you're not supposed to do this,尽管文档并没有真正解释为什么不这样做。

如果您使用的是线程服务器,我会担心竞争条件。这应该很容易测试;只需在一个视图中调用sleep(),然后返回带有当前站点名称的HttpResponse。当第一个视图处于休眠状态时,点击不同域上的不同视图。

如果您使用 prefork,我认为这不会导致任何问题。我在 matplotlib 中使用了这种方法,因为通过使用 matplotlib.rcParams.update() 更改全局配置来设置图形属性是最简单的。我使用 prefork fcgi,所以我可以放心地假设每个请求都有自己的整个过程(伙计们,如果我错了,请纠正我)。

编辑:我认为你可以通过禁用sites 应用程序来使用RequestSite 做你想做的事。例如,James Bennett 的 django-registration 在这种情况下实例化了一个 RequestSite 对象,该对象从请求对象中提取主机名。

【讨论】:

    猜你喜欢
    • 2011-08-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-12-01
    • 1970-01-01
    • 2012-06-01
    • 2018-12-10
    相关资源
    最近更新 更多