Django项目私有媒体文件存储
项目描述
django-private-storage
此模块提供私有媒体文件存储,因此用户上传可以受到登录保护。
它使用Django存储API的内部功能,因此所有表单渲染和管理员集成都无需额外操作。
安装
pip install django-private-storage
配置
添加到设置中
INSTALLED_APPS += (
'private_storage',
)
PRIVATE_STORAGE_ROOT = '/path/to/private-media/'
PRIVATE_STORAGE_AUTH_FUNCTION = 'private_storage.permissions.allow_staff'
添加到 urls.py
import private_storage.urls
urlpatterns += [
path('private-media/', include(private_storage.urls)),
]
使用方法
在Django模型中添加 PrivateFileField
from django.db import models
from private_storage.fields import PrivateFileField
class MyModel(models.Model):
title = models.CharField("Title", max_length=200)
file = PrivateFileField("File")
PrivateFileField 还接受以下关键字参数
upload_to:在 PRIVATE_STORAGE_ROOT 中的可选子文件夹。
upload_subfolder:一个定义文件夹的函数,它接收当前的模型实例。
content_types:允许的内容类型
max_file_size:字节数的最大文件大小。(1MB是1024 * 1024)
storage:要使用的存储对象,默认为private_storage.storage.private_storage
图片
您还可以使用PrivateImageField,它只允许您上传图片
from django.db import models
from private_storage.fields import PrivateImageField
class MyModel(models.Model):
title = models.CharField("Title", max_length=200)
width = models.PositiveSmallIntegerField(default=0)
height = models.PositiveSmallIntegerField(default=0)
image = PrivateFileField("Image", width_field='width', height_field='height')
PrivateImageField还接受以下kwargs,除了PrivateFileField
width_field:可选字段,用于存储图片的宽度
height_field:可选字段,用于存储图片的高度
其他主题
在Amazon S3上存储文件
PRIVATE_STORAGE_CLASS设置可以被重新定义,以指向不同的存储类。默认是private_storage.storage.files.PrivateFileSystemStorage,它使用PRIVATE_STORAGE_ROOT指向的私有媒体文件夹。
定义以下设置之一
PRIVATE_STORAGE_CLASS = 'private_storage.storage.s3boto3.PrivateS3BotoStorage'
AWS_PRIVATE_STORAGE_BUCKET_NAME = 'private-files' # bucket name
这使用django-storages设置。将前缀AWS_替换为AWS_PRIVATE_。以下设置在没有相应的AWS_PRIVATE_...设置时被重用
AWS_ACCESS_KEY_ID
AWS_SECRET_ACCESS_KEY
AWS_S3_URL_PROTOCOL
AWS_S3_REGION_NAME
AWS_IS_GZIPPED
所有其他设置应使用AWS_PRIVATE_...设置明确定义。
默认情况下,所有管理中的URL都返回直接S3桶URL,启用查询参数认证。当AWS_PRIVATE_QUERYSTRING_AUTH = False时,所有文件下载都通过我们的PrivateFileView URL进行代理。此行为可以通过使用PRIVATE_STORAGE_S3_REVERSE_PROXY = True明确启用。
要启用加密,请配置AWS_PRIVATE_S3_ENCRYPTION和AWS_PRIVATE_S3_SIGNATURE_VERSION或使用
PRIVATE_STORAGE_CLASS = 'private_storage.storage.s3boto3.PrivateEncryptedS3BotoStorage'
确保在Amazon上生成加密密钥。
MinIO存储
定义以下设置之一
PRIVATE_STORAGE_CLASS = 'private_storage.storage.minio.PrivateMinioStorage'
MINIO_PRIVATE_STORAGE_MEDIA_BUCKET_NAME = 'private-files'
MINIO_PRIVATE_STORAGE_MEDIA_URL= '/private-files'
这使用django-minio-storage设置。将前缀MINIO_替换为MINIO_PRIVATE_。所有设置在没有相应的MINIO_PRIVATE_...设置时被重用。
MINIO_STORAGE_ENDPOINT
MINIO_STORAGE_ACCESS_KEY
MINIO_STORAGE_SECRET_KEY
MINIO_STORAGE_USE_HTTPS
MINIO_STORAGE_MEDIA_BUCKET_NAME
MINIO_STORAGE_MEDIA_URL
MINIO_STORAGE_AUTO_CREATE_MEDIA_BUCKET
MINIO_STORAGE_AUTO_CREATE_MEDIA_POLICY
MINIO_STORAGE_MEDIA_USE_PRESIGNED
MINIO_STORAGE_MEDIA_BACKUP_FORMAT
MINIO_STORAGE_ASSUME_MEDIA_BUCKET_EXISTS
MINIO_STORAGE_MEDIA_OBJECT_METADATA
与S3一样,您可以通过我们的PrivateFileView URL启用代理。只需指定PRIVATE_STORAGE_MINO_REVERSE_PROXY = True。
定义访问规则
PRIVATE_STORAGE_AUTH_FUNCTION定义了哪些用户可以访问文件。默认情况下,这仅包括超级用户。
以下是一些可用的选项
private_storage.permissions.allow_authenticated
private_storage.permissions.allow_staff
private_storage.permissions.allow_superuser
您可以创建一个自定义函数,并使用它代替。该函数接收一个private_storage.models.PrivateFile对象,它有以下字段
request:Django请求。
storage:用于检索文件的存储引擎。
relative_name:存储中的文件名。
full_path:完整的文件系统路径。
exists():文件是否存在。
content_type:HTTP内容类型。
parent_object:仅在使用了PrivateStorageDetailView时设置。
通过对象ID检索文件
为实现更多基于对象的访问权限,创建一个提供下载的自定义视图。
from private_storage.views import PrivateStorageDetailView
class MyDocumentDownloadView(PrivateStorageDetailView):
model = MyModel
model_file_field = 'file'
def get_queryset(self):
# Make sure only certain objects can be accessed.
return super().get_queryset().filter(...)
def can_access_file(self, private_file):
# When the object can be accessed, the file may be downloaded.
# This overrides PRIVATE_STORAGE_AUTH_FUNCTION
return True
以下类级别属性可以被重写
model:要获取的模型(包括SingleObjectMixin的所有其他属性)。
model_file_field:这应该指向用于存储文件的字段。
storage / get_storage():从其中读取文件的存储类。
server_class:用于生成HttpResponse / FileResponse的Python类。
content_disposition:可以是“inline”(在浏览器内显示)或“attachment”(保存为下载)。
content_disposition_filename / get_content_disposition_filename():覆盖下载的文件名。
优化大文件传输
在某些配置中,发送大文件可能效率不高。
在最坏的情况下,整个文件需要分块读取,并通过整个WSGI缓冲区、OS内核、Web服务器和代理服务器传输。实际上,整个文件在内存缓冲区中复制了几次。
有更有效的方法来传输文件,例如UNIX上的sendfile()系统调用。当WSGI服务器提供wsgi.file_handler支持时,Django会使用此功能。
在某些情况下,这种效果会被抵消,例如通过位于WSGI容器前面的本地HTTP服务器。一个典型的例子是在Nginx或Apache Web服务器后面运行Gunicorn。
对于这种情况,可以通过以下设置启用Web服务器的本地支持
对于Apache
PRIVATE_STORAGE_SERVER = 'apache'
这还需要安装并激活mod_xsendfile Apache模块。将以下XSendFile配置添加到您的conf.d配置文件中。
<virtualhost ...>
...
WSGIScriptAlias / ...
XSendFile On
XSendFilePath ... [path to where the files are, same as PRIVATE_STORAGE_ROOT]
...
</virtualhost>
对于Nginx
PRIVATE_STORAGE_SERVER = 'nginx'
PRIVATE_STORAGE_INTERNAL_URL = '/private-x-accel-redirect/'
在服务器配置中添加以下location块
location /private-x-accel-redirect/ {
internal;
alias /path/to/private-media/;
}
对于非常旧的Nginx版本,您将不得不配置PRIVATE_STORAGE_NGINX_VERSION,因为Nginx版本在1.5.9之前(2014年发布)处理非ASCII文件名的方式不同。
其他Web服务器
PRIVATE_STORAGE_SERVER也可以指向一个点分隔的Python类路径。实现一个具有静态serve(private_file)方法的类。
使用多个存储
PrivateFileField接受一个storage关键字参数,因此您可以初始化多个private_storage.storage.PrivateStorage对象,每个对象从不同的location和base_url提供文件。
例如
from django.db import models
from private_storage.fields import PrivateFileField
from private_storage.storage.files import PrivateFileSystemStorage
my_storage = PrivateFileSystemStorage(
location='/path/to/storage2/',
base_url='/private-documents2/'
)
class MyModel(models.Model):
file = PrivateFileField(storage=my_storage)
然后创建一个视图来提供这些文件
from private_storage.views import PrivateStorageView
from .models import my_storage
class MyStorageView(PrivateStorageView):
storage = my_storage
def can_access_file(self, private_file):
# This overrides PRIVATE_STORAGE_AUTH_FUNCTION
return self.request.is_superuser
然后公开该URL
urlpatterns += [
url('^private-documents2/(?P<path>.*)$', views.MyStorageView.as_view()),
]
贡献
此模块旨在通用。如果您对它有任何不满,或者认为它不够灵活,请告诉我们。我们很乐意改进它!
运行测试
我们使用tox在本地运行测试套件的不同版本(并使用travis-ci自动检查PR)。
要本地运行测试套件,请确保您的Python环境已安装tox和django
python3.6 -m pip install tox django
然后只需执行tox即可运行整个测试矩阵
tox
项目详情
下载文件
下载适合您平台的文件。如果您不确定选择哪个,请了解有关 安装包 的更多信息。
源分发
构建分发
哈希值 for django_private_storage-3.1.1-py3-none-any.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | fcb14c0f56e1fb5e1984afe689e6a92d79c1347dd5329aa50b53ecec4e517a52 |
|
MD5 | a96ff287d3bbc0c054e1c254c6fcf9fc |
|
BLAKE2b-256 | 79da1997c3e440e437af0fd42f3a71565511aaf43ed7c51f1742c090d1248af6 |