django-video-encoding帮助将您的视频转换为不同的格式和分辨率。
项目描述
django-video-encoding
django-video-encoding帮助将您的视频转换为不同的格式和分辨率。
要求
- Python 3.6.1或更高版本
- ffmpeg和ffprobe
安装
-
安装django-video-encoding
pip install django-video-encoding
-
将
video_encoding
添加到您的INSTALLED_APPS
。
集成
将VideoField
和GenericRelation(Format)
添加到您的模型中。您可以可选地通过向VideoField
提供相应的字段名来存储视频的width
、height
和duration
。
from django.contrib.contenttypes.fields import GenericRelation
from django.db import models
from video_encoding.fields import VideoField
from video_encoding.models import Format
class Video(models.Model):
width = models.PositiveIntegerField(editable=False, null=True)
height = models.PositiveIntegerField(editable=False, null=True)
duration = models.FloatField(editable=False, null=True)
file = VideoField(width_field='width', height_field='height',
duration_field='duration')
format_set = GenericRelation(Format)
要显示所有转换后的视频在管理员中,您应该将FormatInline
添加到您的ModelAdmin
from django.contrib import admin
from video_encoding.admin import FormatInline
from .models import Video
@admin.register(Video)
class VideoAdmin(admin.ModelAdmin):
inlines = (FormatInline,)
list_dispaly = ('get_filename', 'width', 'height', 'duration')
fields = ('file', 'width', 'height', 'duration')
readonly_fields = fields
视频的转换应在单独的进程中完成。典型选项是django-rq或celery。以下示例将使用django-rq
。celery
的配置类似。django-video-encoding
已提供任务(convert_all_videos
)用于转换模型上的所有视频。当上传视频时应触发此任务。因此,我们监听post-save
信号并将保存的实例排队进行处理。
# signals.py
from django.db.models.signals import post_save
from django.dispatch import receiver
from django_rq import enqueue
from video_encoding import tasks
from .models import Video
@receiver(post_save, sender=Video)
def convert_video(sender, instance, **kwargs):
enqueue(tasks.convert_all_videos,
instance._meta.app_label,
instance._meta.model_name,
instance.pk)
一段时间后,您可以使用以下方式访问转换后的视频:
video = Video.objects.get(...)
for format in video.format_set.complete().all():
# do something
生成视频缩略图
后端提供了一个 get_thumbnail()
方法,用于从视频中提取缩略图。以下是一个如何生成缩略图并将其存储在模型中的基本示例。
# models.py
from django.db import models
class Video(models.Model):
width = models.PositiveIntegerField(editable=False, null=True)
height = models.PositiveIntegerField(editable=False, null=True)
duration = models.FloatField(editable=False, null=True)
thumbnail = ImageField(blank=True)
file = VideoField(width_field='width', height_field='height',
duration_field='duration')
format_set = GenericRelation(Format)
# tasks.py
from django.core.files import File
from video_encoding.backends import get_backend
from .models import Video
def create_thumbnail(video_pk):
video = Video.objects.get(pk=video_pk)
if not video.file:
# no video file attached
return
if video.thumbnail:
# thumbnail has already been generated
return
encoding_backend = get_backend()
thumbnail_path = encoding_backend.get_thumbnail(video.file.path)
filename = os.path.basename(self.url),
try:
with open(thumbnail_path, 'rb') as file_handler:
django_file = File(file_handler)
video.thumbnail.save(filename, django_file)
video.save()
finally:
os.unlink(thumbnail_path)
您应该通过使用 django-rq
、celery
或类似工具,在单独的进程中运行此方法,并从 post_save
信号中排队执行。
# signals.py
from django.db.models.signals import post_save
from django.dispatch import receiver
from django_rq import enqueue
from . import tasks
from .models import Video
@receiver(post_save, sender=Video)
def create_thumbnail(sender, instance, **kwargs):
enqueue(tasks.create_thumbnail, instance.pk)
信号
在编码过程中,会发出多个信号以报告进度。您可以根据 Django 文档 中的说明注册到信号。
此简单示例演示了如何在转换完成后更新“视频模型”。
# apps.py
from django.apps import AppConfig
class MyAppConfig(AppConfig):
# ...
def ready(self) -> None:
from . import signals # register signals
# signals.py
from typing import Type
from django.dispatch import receiver
from video_encoding import signals
from myapp.models import Video
@receiver(signals.encoding_finished, sender=Video)
def mark_as_finished(sender: Type[Video], instance: Video) -> None:
"""
Mark video as "convertion has been finished".
"""
video.processed = True
video.save(update_fields=['processed'])
signals.encoding_started
在编码开始之前发出。
参数
sender: Type[models.Model]
:包含 VideoField
的模型。
instance: models.Model
:包含 VideoField
的模型的实例。
signals.encoding_finished
与 encoding_started()
类似,但在文件被转换为所有格式之后发出。
参数
sender: Type[models.Model]
:包含 VideoField
的模型。
instance: models.Model
:包含 VideoField
的模型的实例。
signals.format_started
在视频被转换为配置的格式之一之前发出。
参数
sender: Type[models.Model]
:包含 VideoField
的模型。
instance: models.Model
:包含 VideoField
的模型的实例。
format: Format
:格式实例,将引用编码后的视频文件。
signals.format_finished
与 format_finished
类似,但在视频编码过程之后发出,并包括编码是否成功。
参数
sender: Type[models.Model]
:包含 VideoField
的模型。
instance: models.Model
:包含 VideoField
的模型的实例。
format: Format
:格式实例,将引用编码后的视频文件。
result: ConversionResult
:video_encoding.signals.ConversionResult
的实例,指示转换是否 FAILED
、SUCCEEDED
或被 SKIPPED
。
配置
VIDEO_ENCODING_THREADS(默认:1
)
定义应使用多少个线程进行编码。这可能不是每个后端都支持的。
VIDEO_ENCODING_BACKEND(默认:'video_encoding.backends.ffmpeg.FFmpegBackend'
)
选择编码的后端。 django-video-encoding
仅支持 ffmpeg
,但您可以实现自己的后端。您可以自由发布您的插件并提交拉取请求。
VIDEO_ENCODING_BACKEND_PARAMS(默认:{}
)
如果您的后端需要一些特殊配置,您可以在这里将其指定为 dict
。
VIDEO_ENCODING_FORMATS(默认值请参阅 video_encoding/config.py
)
此字典定义了所有必需的编码,并有一些合理的默认值。如果您想自定义格式,您必须为每个格式指定 name
、extension
和 params
。例如
VIDEO_ENCODING_FORMATS = {
'FFmpeg': [
{
'name': 'webm_sd',
'extension': 'webm',
'params': [
'-b:v', '1000k', '-maxrate', '1000k', '-bufsize', '2000k',
'-codec:v', 'libvpx', '-r', '30',
'-vf', 'scale=-1:480', '-qmin', '10', '-qmax', '42',
'-codec:a', 'libvorbis', '-b:a', '128k', '-f', 'webm',
],
},
]
编码后端
video_encoding.backends.ffmpeg.FFmpegBackend(默认)
使用 ffmpeg
和 ffprobe
转换您的视频的后端。
选项
VIDEO_ENCODING_FFMPEG_PATHffmpeg
的路径。如果没有提供路径,后端使用 which
来定位它。 VIDEO_ENCODING_FFPROBE_PATHffprobe
的路径。如果没有提供路径,后端使用 which
来定位它。
自定义后端
您可以实现自定义编码后端。创建一个继承自 video_encoding.backends.base.BaseEncodingBackend
的新类。您必须设置属性 name
并实现方法 encode
、get_media_info
和 get_thumbnail
。有关更多详细信息,请参阅参考实现:video_encoding.backends.ffmpeg.FFmpegBackend
。
如果您想开源您的后端,请按照以下步骤操作。
-
创建一个名为 django-video-encoding-BACKENDNAME 的包
-
将您的包发布到 pypi
-
提交包含以下更改的拉取请求
- 将包添加到
extra_requires
- 为
VIDEO_ENCODING_FORMATS
提供合理的默认值
- 将包添加到
开发
本项目使用 poetry 进行打包和管理所有依赖,并使用 pre-commit 运行 flake8、isort、mypy 和 black。
克隆此仓库并运行
poetry install
poetry run pre-commit install
以创建包含所有依赖项的虚拟环境。之后,您可以使用以下命令运行测试套件
poetry run pytest
此仓库遵循 Conventional Commits 风格。
Cookiecutter 模板
本项目使用 cruft 和 cookiecutter-pyproject 模板创建。要更新此仓库到最新模板版本,请在仓库根目录下运行
cruft update
。
项目详情
下载文件
下载适用于您平台上的文件。如果您不确定选择哪个,请了解有关 安装包 的更多信息。
源分布
构建分布
django-video-encoding-1.0.0.tar.gz 的哈希值
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 933901782f127200ae63b03b95c846eecec98a5d75cc2db27decbc862692ed49 |
|
MD5 | b60469c4e7e9b07b4efd92a9dc535e45 |
|
BLAKE2b-256 | fce514861849efd731b5d6320306bce835c2e831efbe795cc1afa6c92a297cc6 |
django_video_encoding-1.0.0-py3-none-any.whl 的哈希值
算法 | 哈希摘要 | |
---|---|---|
SHA256 | a30fd6e48389d379963965102dc1ae9090394a1ad85e6d0b98091ada2dece658 |
|
MD5 | 035132d950db2111eb770779b72502b9 |
|
BLAKE2b-256 | 5e1e14ea39842be5f77dbefefd22a36ce2fc82fe0b772df2d9ed32d81091dbb7 |