使用 Gunicorn 运行 Django - 最佳实践

Posted

技术标签:

【中文标题】使用 Gunicorn 运行 Django - 最佳实践【英文标题】:Running Django with Gunicorn - Best Practice 【发布时间】:2013-05-27 07:32:58 【问题描述】:

使用 gunicorn 运行 django 应用程序有 3 种方法:

    标准gunicorn + wsgi (ref django doc)

    gunicorn project.wsgi:application

    使用 gunicorn django 集成(参考 gunicorn doc 和 django doc):

    python manage.py run_gunicorn

    使用gunicorn_django 命令(参考gunicorn doc)

    gunicorn_django [OPTIONS] [SETTINGS_PATH]

Django 的文档建议使用 1.,这在 Gunicorn 文档中甚至没有列为选项。

关于使用 gunicorn 运行 django 应用程序的最佳方式是否有任何最佳实践,这些不同解决方案的可预见的优点/缺点是什么?

看一眼gunicorn's code,看起来他们几乎都在做同样的事情:2. 似乎正在使用 django 的内部创建一个 wsgi 应用程序,3. 使用 2.

如果是这样的话,我什至不明白为什么不简单地使用“1”。一直以来,特别是因为自 django 1.4 以来为您自动创建了一个 wsgi.py 文件;如果这是真的,也许应该建议对文档进行改进......

此外,使用 django 进行 gunicorn 设置的最佳实践也很棒。使用1.,在wsgi文件中设置一些默认值,避免额外设置是否有意义?

参考资料:

    Should I use django-gunicorn integration or wsgi? 仅涉及选项 1. 和 3.,没有设置提示,答案也没有给出任何理由 Deploying Django with gunicorn and nginx 提供一些更广泛的信息,但不严格相关也不回答这个问题 Django Gunicorn wsgi 关于版本“4”,正在启动 gunicorn -c configfile 和 configfile 将指向 django_settings 到 django Django WSGI and Gunicorn 只是有点令人困惑 :) 混淆了 1. 和 3。当然wsgi.py 仅与 1 一起使用。

【问题讨论】:

我已经发布了 70 多个 django 最佳实践,以将 django 扩展到数百万用户。它还包括 gunicorn 和 wsgi 调优见解。 digiqt.com/blog/django-best-practices-for-scalable-apps.html 【参考方案1】:

退房后我会说最好的方法是使用gunicorn + wsgi

$ gunicorn project.wsgi:application

现在都在 gunicorn 文档中得到确认:if you run Django 1.4 or newer, it’s highly recommended to simply run your application with the WSGI interface using the gunicorn command 和 django as linked above。

它还避免将 gunicorn 添加为已安装的应用程序,这意味着不需要安装 gunicorn 来测试您的应用程序,这可能不时有用。

关于设置

要使用的 Django 设置文件可以通过 ENV 变量传递,或者在 wsgi.py 文件中自定义。如果我有多个必须从同一个项目运行的设置(例如多个网站),我有时会创建多个 wsgi.py 文件 - See Django Doc 了解更多信息。

不需要来自Carl's comment 的任何新文件的单行解决方案:

DJANGO_SETTINGS_MODULE=project.settings.prod gunicorn project.wsgi:application

听起来是一种更好的方式(尽管我可能最终会在一些 shell 命令中编写它以便于“记住”)。

Gunicorn 设置可以作为-c settings_file 传递,但我正在探索其他方法,如果我发现任何方法,我会尝试更新这个答案。使用环境变量似乎是一种解决方法,但仅限于有限的情况

特别是在 django 和 gunicorn 之间获取/共享一些设置会很好; gunicorn 文档说:

目前,只有 Paster 应用程序可以访问框架 具体设置。如果您有为 WSGI 提供设置的想法 应用程序或从 Django 的 settings.py 中提取信息 免费打开一个问题让我们知道。

更新:还没有找到更聪明的方法,但毕竟 env 变量对于我最常见的情况来说已经足够了)。

【讨论】:

是的,这是最好的方法。存在其他模式的原因是 gunicorn 是在 Django 默认项目模板包含正确的 WSGI 入口点之前创建的,因此 gunicorn 开发人员无法假设他们的 Django 用户会有一个。 我并不完全清楚您对设置的要求是什么——我认为您最好单独提出一个问题,并附上一些明确的示例来说明您正在考虑的设置类型。 @CarlMeyer 我说的是 django 设置和 gunicorn 设置(尽管我承认它不是很清楚,我尝试更明确)。如果不能重现可定制的./manage.py run_gunicorn --settings=SETTINGS,就很难说启动 django 实例。特别是,当我有一个运行多个实例的项目(例如,django-cms 上的多个网站)时,我会使用不同的设置。我目前对 django 设置的解决方案是乘以 WSGI 文件(或设置 ENV 变量)。 只需设置环境变量DJANGO_SETTINGS_MODULE,这是迄今为止最简单的方法。我一生中从未使用过--settingsmanage.py 的参数,我什至不确定它是否应该存在。如果需要,您甚至可以在单个命令行中设置 env var,例如DJANGO_SETTINGS_MODULE=project.settings.prod gunicorn project.wsgi:application【参考方案2】:

我想使用run_gunicorn 是可行的方法,也是最简单的使用方法。

它与usign gunicorn project.wsgi:application基本相同,但需要将gunicorn添加到INSTALLED_APPS,以便django识别run_gunicorn命令,因此它可能不是默认方式...

或多或少不推荐使用gunicorn_django,因为文档还指出here...

【讨论】:

好吧,根据那个文档gunicorn djangoapp.wsgi:application 是要走的路,甚至不是run_gunicorn;我仍然试图理解为什么 3 种模式,文档中关于 /suggested/ 方式的奇怪注释,以及配置的最佳实践是什么(我可以想象将它的一部分放入 wsgi.py 文件中)...谢谢! run_gunicorn 命令现在包含一条关于已弃用并在 R21 中删除的警告。 这已不再可行,但我很高兴这个答案存在,它帮助我理解了为什么在 2014 年将 gunicorn 条目添加到 INSTALLED_APPS,并确认我可以现在摆脱它。【参考方案3】:

找到了一个适用于 manage.py(在本地机器上)和 gunicorn 的解决方案

创建一个包含所有环境内容的文件

# mysite/settings/set_env.py

import os

_environment = os.getenv('environment', None)
if _environment == "production":
    os.environ.setdefault("DJANGO_SETTINGS_MODULE", "mysite.settings.production")
elif _environment == "development":
    os.environ.setdefault("DJANGO_SETTINGS_MODULE", "mysite.settings.development")
else:
    os.environ.setdefault("DJANGO_SETTINGS_MODULE", "mysite.settings.local")

并在你的 manage.py 和 wsgi.py 文件中导入这个文件,不需要在 gunicorn 执行中更改任何其他内容

【讨论】:

以上是关于使用 Gunicorn 运行 Django - 最佳实践的主要内容,如果未能解决你的问题,请参考以下文章

使用 nginx 和 gunicorn 运行多个 django 项目

尝试使用 Foreman 在 Gunicorn 上本地运行 Django 应用程序

通过 Gunicorn/Nginx 使用 Django 的站点框架运行多个站点

如何运行多个Django App Gunicorn systemd?

如何运行与 gunicorn 绑定的 django 应用程序?

关闭 django 站点进行维护?