Deploying static files

See also

For an introduction to the use of django.contrib.staticfiles, see Managing static files (e.g. images, JavaScript, CSS).

Serving static files in production

将静态文件投入生产的基本概述很简单:在静态文件更改时运行collectstatic命令,然后将收集的静态文件目录(STATIC_ROOT)移动到静态文件服务器和服务。 根据STATICFILES_STORAGE,可能需要手动将文件移动到新位置,或者Storage类的post_process方法会处理。

当然,就像所有部署任务一样,麻烦会出现在许多细节上。 每个生产设置都会有所不同,因此您需要调整基本轮廓以适应您的需求。 以下是一些可能有所帮助的常见模式。

Serving the site and your static files from the same server

如果您想从已为您的网站提供服务的同一台服务器提供静态文件,则此过程可能如下所示:

您可能希望自动执行此过程,特别是如果您拥有多个Web服务器。 有许多方法可以实现这种自动化,但许多Django开发人员喜欢的一种选择是Fabric

在下面和下面的部分中,我们将展示一些示例fabfiles(即 Fabric脚本)来自动执行这些文件部署选项。 fabfile的语法非常简单,但不会在这里介绍;请参阅Fabric的文档,以获取语法的完整说明。

因此,将静态文件部署到几个Web服务器的fabfile可能如下所示:

from fabric.api import *

# Hosts to deploy onto
env.hosts = ['www1.example.com', 'www2.example.com']

# Where your project code lives on the server
env.project_root = '/home/www/myproject'

def deploy_static():
    with cd(env.project_root):
        run('./manage.py collectstatic -v0 --noinput')

Serving static files from a dedicated server

Most larger Django sites use a separate Web server – i.e., one that’s not also running Django – for serving static files. This server often runs a different type of web server – faster but less full-featured. Some common choices are:

Configuring these servers is out of scope of this document; check each server’s respective documentation for instructions.

Since your static file server won’t be running Django, you’ll need to modify the deployment strategy to look something like:

  • When your static files change, run collectstatic locally.
  • Push your local STATIC_ROOT up to the static file server into the directory that’s being served. rsync is a common choice for this step since it only needs to transfer the bits of static files that have changed.

Here’s how this might look in a fabfile:

from fabric.api import *
from fabric.contrib import project

# Where the static files get collected locally. Your STATIC_ROOT setting.
env.local_static_root = '/path/to/static'

# Where the static files should go remotely
env.remote_static_root = '/home/www/static.example.com'

@roles('static')
def deploy_static():
    local('./manage.py collectstatic')
    project.rsync_project(
        remote_dir=env.remote_static_root,
        local_dir=env.local_static_root,
        delete=True,
    )

Serving static files from a cloud service or CDN

Another common tactic is to serve static files from a cloud storage provider like Amazon’s S3 and/or a CDN (content delivery network). This lets you ignore the problems of serving static files and can often make for faster-loading Web pages (especially when using a CDN).

When using these services, the basic workflow would look a bit like the above, except that instead of using rsync to transfer your static files to the server you’d need to transfer the static files to the storage provider or CDN.

There’s any number of ways you might do this, but if the provider has an API a custom file storage backend will make the process incredibly simple. If you’ve written or are using a 3rd party custom storage backend, you can tell collectstatic to use it by setting STATICFILES_STORAGE to the storage engine.

For example, if you’ve written an S3 storage backend in myproject.storage.S3Storage you could use it with:

STATICFILES_STORAGE = 'myproject.storage.S3Storage'

Once that’s done, all you have to do is run collectstatic and your static files would be pushed through your storage package up to S3. If you later needed to switch to a different storage provider, it could be as simple as changing your STATICFILES_STORAGE setting.

For details on how you’d write one of these backends, see Writing a custom storage system. There are 3rd party apps available that provide storage backends for many common file storage APIs. A good starting point is the overview at djangopackages.org.

Learn more

For complete details on all the settings, commands, template tags, and other pieces included in django.contrib.staticfiles, see the staticfiles reference.