
本文详解如何用 Bash 脚本解析视频文件名(格式为 yyyy-mm-dd-hh-mm-ss.mp4),按日期分组生成每日独立 HTML 页面,并构建带视频数量统计的首页,同时修复因误用命令替换导致的 command not found 错误。
本文详解如何用 bash 脚本解析视频文件名(格式为 `yyyy-mm-dd-hh-mm-ss.mp4`),按日期分组生成每日独立 html 页面,并构建带视频数量统计的首页,同时修复因误用命令替换导致的 `command not found` 错误。
在嵌入式环境(如树莓派 + lighttpd)中自动化管理监控视频时,轻量、无依赖的 Bash 脚本是理想选择。核心需求有二:
-
按日聚合:将形如
2024-04-01-14-22-05.mp4的文件按yyyy-mm-dd归类; -
双层页面生成:
✅index.html:列出所有日期及当日视频总数(如01/04/2024 - 10 videos);
✅2024-04-01.html:展示该日全部视频缩略图、时间戳、下载链接等。
你原脚本的关键错误出现在输出重定向行:
" > "$("${day}.html")" # ❌ 错误:$() 是命令替换,不是变量扩展!
当 day=2024-04-01 时,此行实际执行 $(2024-04-01.html) —— Shell 试图运行一个名为 2024-04-01.html 的命令,自然报错 command not found。正确写法应为直接变量扩展:
" > "${day}.html" # ✅ 正确:${day} 展开为字符串,.html 拼接为文件名
此外,原逻辑存在几个关键优化点,以下是完整、健壮、可直接部署的改进版核心流程:
✅ 步骤一:安全提取日期并去重
# 清空临时数组
dates=()
videos_by_date=()
# 遍历视频(仅处理 .mp4/.avi 等常见格式)
for video in "$videos_dir"/*.mp4 "$videos_dir"/*.avi; do
[[ ! -f "$video" ]] && continue # 跳过无匹配文件的通配符
basename=$(basename "$video")
# 提取 yyyy-mm-dd(前10字符),忽略后缀和时间部分
date_part=${basename:0:10}
if [[ $date_part =~ ^[0-9]{4}-[0-9]{2}-[0-9]{2}$ ]]; then
dates+=("$date_part")
videos_by_date+=("$date_part|$video|$thumbs_dir/${basename%.*}.jpg")
fi
done
# 获取唯一日期列表(保持顺序)
readarray -t unique_dates <h3>✅ 步骤二:为每个日期生成专属 HTML 页</h3><pre class="brush:php;toolbar:false;">for day in "${unique_dates[@]}"; do
# 过滤出该日所有视频项(支持多视频同日)
day_items=()
for item in "${videos_by_date[@]}"; do
IFS='|' read -r d v t "${day}.html"
<title>Video Archive — $day</title><h2>$day (${#day_items[@]} videos)</h2>
<div style="display:grid; grid-template-columns:repeat(auto-fill, minmax(300px,1fr)))); gap:1rem;">
$(for item in "${day_items[@]}"; do
IFS='|' read -r video thumb
@@##@@
<p><strong>$base</strong></p>
<a href="%24video" download>⬇ Download</a>
</div>"
done)
EOF
done✅ 步骤三:生成首页 index.html(含日期跳转与计数)
# 构建首页导航列表
index_links=""
for day in "${unique_dates[@]}"; do
count=$(grep -c "^$day|" /dev/null || echo "$day")
index_links+="
? Video Archive
- $index_links
Generated on $(date)
EOF⚠️ 注意事项与最佳实践
-
Shell 兼容性:使用
#!/bin/bash替代#!/bin/sh,因readarray和[[等特性在 POSIX sh 中不可用; -
路径安全:始终用
"$var"引用变量,避免空格或特殊字符导致路径断裂; -
ffmpeg 缩略图:建议添加
-ss 00:00:03跳转到第3秒再截图,避开黑帧; -
性能优化:对数千文件,改用
find ... -printf+awk替代循环,但当前方案对树莓派已足够轻量; -
cron 部署示例:
# 每日凌晨 4:30 执行(确保录像已停止) 30 4 * * * /home/pi/video-indexer/generate.sh >> /var/log/video-index.log 2>&1
通过以上重构,脚本不再触发命令替换错误,逻辑清晰、容错性强,且完全满足低资源设备的静态站点生成需求。最终产物是零 JS 依赖的纯 HTML 站点,可直接由 lighttpd 托管,访问高效稳定。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











