影视素材库是管理视频、音频、字幕等影视相关资源的重要工具,通过Python开发可以实现自定义的分类规则和灵活的检索能力,适配不同场景的素材管理需求。本文将从数据库设计到功能实现逐步讲解完整流程。
一、前期准备与数据库设计
首先需要安装必要的依赖库,主要使用SQLite作为存储数据库,通过Python内置的sqlite3模块操作,同时用os模块处理文件路径。影视素材的核心信息包括素材ID、名称、类型、存储路径、时长、标签、上传时间等,我们先设计对应的数据表。
import sqlite3
import os
from datetime import datetime
# 初始化数据库连接
def init_db(db_path="movie_materials.db"):
conn = sqlite3.connect(db_path)
cursor = conn.cursor()
# 创建素材分类表
cursor.execute("""
CREATE TABLE IF NOT EXISTS material_category (
id INTEGER PRIMARY KEY AUTOINCREMENT,
category_name TEXT NOT NULL UNIQUE,
parent_id INTEGER DEFAULT 0,
create_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
""")
# 创建素材主表
cursor.execute("""
CREATE TABLE IF NOT EXISTS material_info (
id INTEGER PRIMARY KEY AUTOINCREMENT,
material_name TEXT NOT NULL,
category_id INTEGER NOT NULL,
file_path TEXT NOT NULL UNIQUE,
duration REAL DEFAULT 0,
tags TEXT DEFAULT "",
upload_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (category_id) REFERENCES material_category(id)
)
""")
conn.commit()
conn.close()
print("数据库初始化完成")
if __name__ == "__main__":
init_db()
二、分类功能实现
分类功能支持多级分类,用户可以创建一级分类如视频、音频、字幕,也可以在每个一级分类下创建子分类,比如视频分类下可以创建宣传片、正片、花絮等子分类。下面实现分类的增删改查功能。
1. 添加分类
def add_category(category_name, parent_id=0):
conn = sqlite3.connect("movie_materials.db")
cursor = conn.cursor()
try:
cursor.execute("INSERT INTO material_category (category_name, parent_id) VALUES (?,?)", (category_name, parent_id))
conn.commit()
print(f"分类 {category_name} 添加成功")
return cursor.lastrowid
except sqlite3.IntegrityError:
print(f"分类 {category_name} 已存在")
return None
finally:
conn.close()
2. 查询分类树
def get_category_tree():
conn = sqlite3.connect("movie_materials.db")
cursor = conn.cursor()
cursor.execute("SELECT id, category_name, parent_id FROM material_category ORDER BY parent_id, id")
all_categories = cursor.fetchall()
conn.close()
# 构建分类树结构
category_dict = {}
for cat_id, cat_name, parent_id in all_categories:
category_dict[cat_id] = {
"name": cat_name,
"parent_id": parent_id,
"children": []
}
tree = []
for cat_id, cat_info in category_dict.items():
if cat_info["parent_id"] == 0:
tree.append({"id": cat_id, "name": cat_info["name"], "children": cat_info["children"]})
else:
parent = category_dict.get(cat_info["parent_id"])
if parent:
parent["children"].append({"id": cat_id, "name": cat_info["name"]})
return tree
三、素材入库与检索功能
素材入库时需要关联对应的分类,同时支持添加自定义标签,方便后续检索。检索功能支持按分类、名称关键词、标签、时长范围等多维度查询。
1. 素材入库实现
def add_material(material_name, category_id, file_path, duration=0, tags=""):
# 校验文件是否存在
if not os.path.exists(file_path):
print(f"文件路径 {file_path} 不存在")
return False
conn = sqlite3.connect("movie_materials.db")
cursor = conn.cursor()
try:
cursor.execute("""
INSERT INTO material_info (material_name, category_id, file_path, duration, tags)
VALUES (?,?,?,?,?)
""", (material_name, category_id, file_path, duration, tags))
conn.commit()
print(f"素材 {material_name} 入库成功")
return cursor.lastrowid
except sqlite3.IntegrityError:
print(f"素材路径 {file_path} 已存在")
return False
finally:
conn.close()
2. 多条件检索功能
def search_materials(category_id=None, keyword=None, tag=None, min_duration=None, max_duration=None):
conn = sqlite3.connect("movie_materials.db")
cursor = conn.cursor()
# 构建动态查询语句
sql = """
SELECT m.id, m.material_name, c.category_name, m.file_path, m.duration, m.tags, m.upload_time
FROM material_info m
LEFT JOIN material_category c ON m.category_id = c.id
WHERE 1=1
"""
params = []
if category_id is not None:
sql += " AND m.category_id = ?"
params.append(category_id)
if keyword is not None:
sql += " AND m.material_name LIKE ?"
params.append(f"%{keyword}%")
if tag is not None:
sql += " AND m.tags LIKE ?"
params.append(f"%{tag}%")
if min_duration is not None:
sql += " AND m.duration >= ?"
params.append(min_duration)
if max_duration is not None:
sql += " AND m.duration <= ?"
params.append(max_duration)
sql += " ORDER BY m.upload_time DESC"
cursor.execute(sql, params)
results = cursor.fetchall()
conn.close()
# 格式化返回结果
material_list = []
for item in results:
material_list.append({
"id": item[0],
"name": item[1],
"category": item[2],
"path": item[3],
"duration": item[4],
"tags": item[5],
"upload_time": item[6]
})
return material_list
四、功能测试示例
下面的代码演示了完整的流程,从初始化数据库、添加分类、入库素材到检索素材的完整操作。
if __name__ == "__main__":
# 初始化数据库
init_db()
# 添加分类
video_cat_id = add_category("视频")
add_category("宣传片", parent_id=video_cat_id)
add_category("正片", parent_id=video_cat_id)
audio_cat_id = add_category("音频")
# 添加测试素材
add_material("产品宣传片1", video_cat_id, "/data/materials/video/ad1.mp4", duration=120, tags="宣传,产品")
add_material("正片第一集", video_cat_id, "/data/materials/video/ep1.mp4", duration=2400, tags="正片,剧集")
add_material("背景音乐1", audio_cat_id, "/data/materials/audio/bgm1.mp3", duration=180, tags="背景音乐")
# 测试检索功能
print("检索标签为宣传的素材:")
result1 = search_materials(tag="宣传")
for r in result1:
print(r)
print("n检索视频分类下的素材:")
result2 = search_materials(category_id=video_cat_id)
for r in result2:
print(r)
五、扩展优化方向
上述实现是基础的影视素材库功能,还可以根据实际需求扩展更多能力:比如添加素材预览功能,通过OpenCV读取视频首帧生成缩略图存储;增加用户权限管理,区分素材的上传、编辑、删除权限;实现素材的去重检测,通过文件哈希值判断重复上传的素材;添加批量导入功能,扫描指定文件夹自动识别素材并入库。整个系统的核心逻辑基于Python的数据库操作和文件处理能力,后续扩展也只需要在此基础上增加对应的功能模块即可。