我的365天完整短视频,用Go语言记录生活的一年
- 汽车
- 2026-08-02 20:27:54
- 102
你有没有想过,如果每天用短视频记录生活,一年后回头看会是什么样子?我在2023年就这么干了,而且是用Go语言写了个小工具来管理整个过程,说实话,一开始以为就是拍365个15秒的片段,结果事儿比我想象的多得多——从视频采集、时间戳管理、元数据存储,到最后的合成输出,每一步都有坑,这篇东西不是教程,就是把我踩过的坑和趟出来的路,用大白话跟你唠唠。
为什么用Go语言来处理短视频?
你可能觉得奇怪,剪视频不是用Python或者专门的软件吗?我一开始也这么想,直到我拍了大概两个月,发现文件散落得到处都是,文件名混乱,想找某一天的片段得翻半天,我寻思着写个脚本管理,Python是挺好,但我这台老笔记本跑Python经常卡得风扇狂转,后来试了下Go,好家伙,编译出来是个单文件,跑起来内存占用小,处理视频文件这种IO密集型任务,并发模型真是舒服。
Go语言处理视频的优势其实很直接:
- 底层调用ffmpeg做转码,Go负责调度和流程控制,分工明确
- goroutine并发处理多个视频片段,比Python快不少,特别是批量重命名和格式统一的时候
- 部署简单,交叉编译后扔到任何机器都能跑,不用装依赖环境
我的365天短视频完整流程
整个项目其实分四块:拍摄、存储管理、元数据索引、后期合成,我的流程用了个简单的表格来表示:
| 阶段 | 工具/方法 | Go语言负责的部分 |
|---|---|---|
| 拍摄 | 手机+相机 | 无(纯手工活) |
| 文件整理 | 自动脚本 | 批量重命名、按日期归类 |
| 元数据记录 | JSON+SQLite | 每天的场景标签、心情、天气 |
| 剪辑合成 | ffmpeg | 拼接、转码、生成时间水印 |
第一步:拍摄逻辑
其实真没那么多讲究,我就是每天固定拍3个片段:早上起床(或者窗外)、中午吃的饭、晚上干的事,固定机位+固定时长(15秒),省得后期难搞,这里有个小心得:一定要在拍完当天就导入电脑,隔几天再弄,手机里几百个视频,光找素材就能把人逼疯。
第二步:用Go写批量处理脚本
这就是我第一个Go程序,逻辑很简单:读取指定目录下的所有视频文件,按拍摄日期重命名,然后移动到对应的月份文件夹里。
func processFile(path string, info os.FileInfo, err error) error {
// 提取拍摄时间(从EXIF或者文件名)
date := extractDate(path)
// 生成新文件名:2024-01-15_0730.mov
newName := fmt.Sprintf("%s_%s%s", date.Format("2006-01-02"), time.Now().Format("1504"), ext)
// 移动到对应月份目录
os.Rename(path, filepath.Join("videos", date.Month().String(), newName))
return nil
}
func main() {
filepath.Walk("./raw", processFile)
fmt.Println("整理完成,共处理", count, "个文件")
}
说实话,这个代码写得很粗糙,错误处理都没做,但能用,要什么自行车啊?能用就行。
第三步:每天一条记录的数据库
光有视频文件还不够,每天拍了啥内容,当时的感受是什么,这些文字信息才是有温度的,我建了个SQLite数据库,表结构长这样:
| 字段 | 类型 | 说明 |
|---|---|---|
| id | INTEGER | 主键 |
| day | TEXT | 日期,格式YYYY-MM-DD |
| video_path | TEXT | 视频文件路径 |
| mood | TEXT | 当天心情标签 |
| weather | TEXT | 天气 |
| note | TEXT | 自由文本记录 |
然后写了个小服务,启动后监听本地端口,我每天用手机浏览器打开个网页,填点内容,POST上去就完事了,这个没用任何框架,就标准库的net/http,别提多爽了,编译完就一个二进制文件,哪台电脑都能跑。
第四步:365天的完整短视频合成
所有素材和记录都齐了之后,最激动人心的时刻来了——合成一个完整的年度视频,我用Go调用ffmpeg命令行,把365个片段按顺序拼接起来。
这里有个教训:ffmpeg的concat协议对编码格式要求很严格,我头几次合成出来的视频要么卡顿,要么音画不同步,后来学乖了,先用ffmpeg把每个片段统一转成H.264编码、相同分辨率和帧率,然后再拼接。
cmd := exec.Command("ffmpeg",
"-f", "concat",
"-safe", "0",
"-i", listFile,
"-c", "copy",
"final_video.mp4")
这是简单版,实际上我还加了时间水印(用drawtext滤镜),把日期实时叠加到视频上,这个水印太重要了,不然看回放的时候根本分不清哪天是哪天。
那些没预料到的坑
- 存储空间:365个15秒视频,约合6GB左右,加上转码后的中间文件,峰值占了20GB,建议准备个外接硬盘。
- 编码格式不统一:手机拍的H.265,相机拍的H.264,还有几个是竖屏,建议统一转换后再入库,不然后期全是麻烦事。
- Go调ffmpeg的坑:不能用
cmd.Run(),要用cmd.StdoutPipe()和cmd.StderrPipe()同时读,不然缓冲区满了会死锁,这个我调试了一个下午才想明白。 - 文件名千万别带中文:虽然Windows和Linux都支持,但ffmpeg有时会抽风,尤其涉及特殊符号的时候,老老实实用数字和横线。
感受和收获
说实话,这个项目做完之后,我最大的感受不是技术上的提升,而是对时间有了更具体的感知,365天,每天15秒,最后合在一起就是一个多小时的视频,看着里面自己的样子一点点变化,从长头发到秃头,从穿短袖到穿羽绒服,那种感觉很难形容,Go语言本身没帮我看懂人生,但它的并发模型倒是让我明白一个道理——所有的事都是串行的,但可以并发地准备,就像拍视频,拍的时候专心拍,整理的时候批量处理,这样才能坚持下来。
最后你要问我值不值得搞?我觉得值,就算你不想写代码,纯手工整理也行,关键是坚持的记录本身,哦对了,那个Go程序和完整的文档我都扔在GitHub上了,你要是感兴趣可以去搜"yearly-video-manager"这个项目,觉得实用就点个star,不实用就当看个乐呵,反正代码写得也就那样,能用就行。
