跳转到主要内容

存储和视图以发送X-Accel-Redirect(或X-Sendfile)头部到nginx(或apache)反向代理

项目描述

Bitbucket Pipelines license status version pyversion

django-reverse-proxy-send-file

摘要

此包有助于编写使用X-Accel-Redirect头部,由nginx提供文件,但同时在django的侧允许权限检查的视图。

简介

storage.ReverseProxySendFileFileSystemStorage类是django的FileSystemStorage的替代品,它使FileField(或ImageField)url使用REVERSE_PROXY_SENDFILE_MEDIA_URL设置的基本url,而不是MEDIA_URL。

storage.ReverseProxySendFileStorageMixin允许您在任何存储类上应用覆盖的base_url

ReverseProxySendFileView 类处理 GET 请求,并返回一个包含 nginx 的 X-Accel-Redirect 头的空响应,指示 nginx 从给定路径返回文件。必须在 nginx 上下文中定义 REVERSE_PROXY_SENDFILE_MEDIA_ROOT 设置,以便它可以找到文件。

ReverseProxySendFileView 可以被重写以实现自定义的 check_permission 方法,该方法验证当前用户是否有权下载资源。

安装

安装 django-reverse-proxy-send-file pypi 包。例如:

  • poetry add django-reverse-proxy-send-file
  • pip install django-reverse-proxy-send-file

用法

请参阅下面的示例部分

设置

名称 默认值 描述
REVERSE_PROXY_SENDFILE_MEDIA_ROOT MEDIA_ROOT 在 django 上下文中存储上传媒体文件的基路径(由 Storage 类使用)
REVERSE_PROXY_SENDFILE_MEDIA_URL "smedia/" 处理应通过反向代理提供资源的 URL。
REVERSE_PROXY_SENDFILE_REVERSE_PROXY_ROOT "smedia/" 在反向代理上下文中的基路径,通过头将其发送回反向代理以找到文件
REVERSE_PROXY_SENDFILE_MODE "nginx" 可能的值:"nginx""apache"
nginx 模式下将使用 X-Accel-Redirect 头。
apache 模式下将使用 X-Sendfile
REVERSE_PROXY_SENDFILE_HEADER_NAME None 自定义头名称。如果设置,则使用此头,而不管 REVERSE_PROXY_SENDFILE_MODE 设置如何。
REVERSE_PROXY_SENDFILE_DEBUG_SERVE_RESOURCE True 在 django 的 DEBUG 模式下,资源将由开发服务器直接提供。

示例

settings.py

...
REVERSE_PROXY_SENDFILE_MEDIA_URL = "smedia/"
REVERSE_PROXY_SENDFILE_MEDIA_ROOT = "/django_path/to/smedia/"
REVERSE_PROXY_SENDFILE_REVERSE_PROXY_ROOT = "/nginx_path/to/smedia/"
...

models.py

from django.contrib.auth.models import User

from reverse_proxy_send_file.storage import ReverseProxySendFileFileSystemStorage

class MyModel(models.Model):
    ...
    user = models.ForeignKey(User, on_delete=models.CASCADE)
    my_file = models.FileField(
        "My file",
        upload_to="my_files/",
        storage=ReverseProxySendFileFileSystemStorage(),
    )
    ...

views.py

from django.http import Http404

from reverse_proxy_send_file.views import ReverseProxySendFileView

class ReverseProxySendFileMyFileView(ReverseProxySendFileView):
    def check_permission(self, request, resource_url, *args, **kwargs):
        obj_qs = MyModel.objects.filter(my_file=resource_url)
        if not obj_qs.exists():
            raise Http404()
        return obj_qs.filter(user=request.user).exists()

urls.py

from django.conf import settings
from views import ReverseProxySendFileMyFileView

urlpatterns = [
    ...
    re_path(
        settings.REVERSE_PROXY_SENDFILE_MEDIA_URL + "(?P<resource_url>my_files/.*)$",
        views.ReverseProxySendFileMyFileView.as_view(),
        name="reverse_proxy_send_file",
    ),
    ...
]
  1. 用户上传文件。文件存储在 /django_path/to/smedia/my_files/blop.pdf
  2. 用户访问 /smedia/my_files/blop.pdf
  3. 执行 django 请求并检查文件访问权限(在 check_permission 中)。
    • 如果用户允许,则返回包含头 X-Accel-Redirect=/nginx_path/to/smedia/my_files/blop.pdf 的 HTTP 响应(Nginx 将使用它向客户端发送文件)。
    • 如果文件未找到,则返回 404 文件未找到
    • 如果用户被禁止,则返回 403 禁止访问

设置开发环境

# install dev dependencies
poetry install --no-root
# install git pre-commit
pre-commit install

运行测试

使用 tox 命令在所有支持的 Python 版本上运行所有测试。示例

tox
tox -e py38-django40
tox -f py39

构建包并在 PyPI 上发布

pyproject.toml 中更改版本号

poetry build
poetry publish

项目详情


下载文件

为您的平台下载文件。如果您不确定选择哪个,请了解更多关于 安装包 的信息。

源分布

django_reverse_proxy_send_file-1.0.2.tar.gz (5.0 kB 查看散列)

上传时间

构建分布

django_reverse_proxy_send_file-1.0.2-py3-none-any.whl (4.9 kB 查看散列)

上传时间 Python 3

由...