这是我参与「第三届青训营 -后端场」笔记创作活动的的第 3 篇笔记
本篇文章讲讲我作为一个项目经历基本为零的小白,在完成抖音项目最基本的功能实现部分踩过哪些坑,不包括高级的部分(什么高并发、微服务、SQL 安全之类的,问就是不会)
Gorm 连接数据库
可以参考我的上一篇笔记:抖音项目 Gorm 连接 MySQL | 青训营笔记
Gorm 外键使用
在使用 Gorm 时,要搞清楚其最主要的功能就是省时省力地将 Go 中的 struct 结构和 SQL 中的 table 对应起来。通过 demo 我们可以知道在结构体内变量旁边加入形如`gorm:"foreignKey:xxx"`的 tag 来告诉 Gorm 应当如何处理。那么对于以下结构体
type Video struct {
Author User `gorm:"foreignKey:UserId"`
UserId int64
}
Author 对应的外键是 UserId,我们在读取 Video 的时候就可以一步到位的提取出对应的 Author 信息,尽管它是一个 User 型结构。如何实现呢,只需要调用一个非常简单的函数,这个函数藏在了官方文档的很不明显的角落,找了很久才找到——Preload,可以像这样实现(以下为 feed.go 中部分代码)
var videoList []Video
DB.Preload("Author").Order("id desc").Limit(30).Find(&videoList)
如此,我们就能在推送的视频列表中包含作者信息,非常方便
视频封面截取
前端抖声 app 并没有为我们传入封面信息,因此需要后端自行提取,参考程序员快乐网 StackOverflow 的回答:go - First frame of video,可以得知最方便的做法是通过 os 包调用环境中的 ffmpeg 程序,这需要我们本地或服务器环境中已经安装好了 ffmpeg,我比较喜欢用 scoop(Windows 环境),一行代码搞定
scoop install ffmpeg
服务器是 Ubuntu 系统,使用 apt-get
sudo apt-get install ffmpeg
Go 代码也很简单,照着回答抄就可以了。值得注意的是封面选取的时机,一开始选择的是视频第一帧,然而很多视频会有渐入的效果,即从黑屏慢慢进入,第一帧往往都是黑屏,因此选取了第 300 帧,按照 24fps 来看,大概是十多秒的位置,那么这里显然留下了一个问题:万一视频没那么长怎么办?因此最佳的实践应当是统计视频总帧数,选取中间的某一帧(当然甚至还能更进一步,分析整体视频画面变化的地方,选取典型结果供用户选择,感觉像 YouTube 或者 B 站应该都是这么做的),这里考虑到封面选取不是本项目的重点,因此就图省事了
cmd := exec.Command(
"ffmpeg", "-i", "./public/videos/"+finalName,
"-vf", "select=eq(n\, 300)", "-frames", "1",
"./public/covers/"+finalName+".jpg",
)
//cmd.Stderr = os.Stderr // 输出错误信息
if err := cmd.Run(); err != nil {
log.Fatalln("Video cover generation failed")
}
服务器部署
最简单的方法:
git clone
go build
然而一 build 发现失败,这是由于众所周知的原因,我们无法访问 proxy.golang.org,可以使用国内的镜像站 goproxy.cn,两行代码搞定(Linux 环境)
go env -w GO111MODULE=on
go env -w GOPROXY=https://goproxy.cn,direct
目前想到的就是这些了,相关代码可以参考我们的项目地址:GitHub - mini-douyin)