- 目录
- 前言
- 现状
- 需求
- 实现方案
- 结论与思考
前言
对于多媒体存储服务,点播视频文件生成封面应该是非常基础的功能之一,目前自己正在开发的多媒体存储服务就面临这样的需求。因为这个多媒体存储服务是从零开始的,缺少部分基础功能的情况,各位大佬别见笑。
但是,正是因为从零开始开发,因此很多之前被忽略的问题也渐渐浮出水面,映入了我们的眼帘。这个经历过程是非常可贵的,自己从中也学到了很多东西。
现状
首先,我们来看一下当前多媒体存储服务的现状。
目前,多媒体存储服务已经具备了上传、下载、观看预览、转码、查询、删除等基础功能。
文件结构体定义如下:
type File struct { // DefaultModel adds _id, created_at and updated_at fields to the Model mgm.DefaultModel `bson:",inline"` Name string `json:"name" bson:"name"` Md5 string `json:"md5" bson:"md5"` Type string `json:"type" bson:"type"` Url string `json:"url" bson:"url"` Path string `json:"path" bson:"path"` Duration float64 `json:"duration" bson:"duration"` CloudUrl string `json:"cloudurl" bson:"cloudurl"` Filekey string `json:"filekey" bson:"filekey"` Size int64 `json:"size" bson:"size"` } type FileArray []File
上述所有功能都是基于该结构体进行展开的。
需求
现在出现了一个新需求,就是为视频文件生成封面。我们应该怎样设计实现方案呢?
其实,大体的方案可以分为两类。一种方案是在原有文件结构体的基础上扩展封面相关字段,另一种方案是将封面作为一个单独的文件进行管理并与原文件做关联处理。下面会详细分析二者的区别及优缺点。
实现方案
方案一、在原有文件结构体的基础上扩展封面相关字段
这种方案,是继续扩展当前已经定义好的文件结构体,增加封面的关联地址,因此增加一个CoverURL
字段就搞定了。乍一看,感觉没有毛病,但是深入分析一下就会发现问题。如果后续我们需要删除该点播视频文件,理论上应该把对应的封面文件也删除。这个时候,你会发现如果只增加上面的一个字段是不够的,缺少了操作句柄。因此,我们还需要增加一个字段CoverKey
。
按照上述方案,修改后的文件结构体:
type File struct { // DefaultModel adds _id, created_at and updated_at fields to the Model mgm.DefaultModel `bson:",inline"` Name string `json:"name" bson:"name"` Md5 string `json:"md5" bson:"md5"` Type string `json:"type" bson:"type"` Url string `json:"url" bson:"url"` Path string `json:"path" bson:"path"` Duration float64 `json:"duration" bson:"duration"` CloudUrl string `json:"cloudurl" bson:"cloudurl"` Filekey string `json:"filekey" bson:"filekey"` Size int64 `json:"size" bson:"size"` CoverURL string `json:"coverurl" bson:"coverurl"` // 新增项 CoverKey string `json:"coverkey" bson:"coverkey"` // 新增项 // 后续可能还要继续增加。。。 } type FileArray []File
目前,上述结构体就已经满足当前需求了。但是,我们难道就仅仅满足当前的单一需求吗?我们是不是应该思考的更加长远一些?是的,作为一名资深的研发工程师,除了需要设计出满足当前需求的最佳实现方案,还需要具备后期的高可扩展性。
那么问题来了,如果我们后期想要查询或者修改封面的名字和大小,我们是不是还要增加新的 CoverName
和CoverSize
字段?如果想要下载封面,是不是还要增加新的 CoverDownloadURL
字段......这次时候,你就会发现我们其实是复制了一遍文件结构体的所有字段,这样显然是不合理的。
如果是这样,那么有没有更好的可扩展方案呢?答案是有的,请参看方案二。
方案二、将封面作为一个单独的文件进行管理并与原文件做关联
这种方案,将封面作为一个单独的文件进行管理并与原视频文件做关联,能够解决方案一遇到的各种问题,同时,具备一定能力的可扩展性。如果想要满足当前需求,我们仅需要增加一个Cover
字段,存储封面文件的ID,用来关联该视频文件的封面文件。后期对视频文件封面的所有操作都可以通过转换成封面文件的操作,因此简化了对封面文件管理逻辑。还有很多别的优点,大家可以自己思考补充,欢迎在评论区留言。
按照上述方案,修改后的文件结构体:
type File struct { // DefaultModel adds _id, created_at and updated_at fields to the Model mgm.DefaultModel `bson:",inline"` Name string `json:"name" bson:"name"` Md5 string `json:"md5" bson:"md5"` Type string `json:"type" bson:"type"` Url string `json:"url" bson:"url"` Path string `json:"path" bson:"path"` Duration float64 `json:"duration" bson:"duration"` CloudUrl string `json:"cloudurl" bson:"cloudurl"` Filekey string `json:"filekey" bson:"filekey"` Size int64 `json:"size" bson:"size"` Cover string `json:"cover" bson:"cover"` // 新增项 } type FileArray []File
大家会发现,方案二对原有文件结构体的修改程度最小,保证了文件结构体的简洁性和抽象性。同时,还满足了当前需求,又具备了一定的可扩展能力。
结论与思考
其实,日常开发过程中,我们经常会遇到各种各样的需求,解决方案也各式各样,我们想要成为一名资深的研发工程师,就要在统筹全局的前提下,寻找更加符合我们系统架构的实现方案。因为每个系统架构和业务线的设计和需求都不一样,很难找到一个大一统的方案,因此,我坚持的原则就是“设计开发实现方案时,没有最好只有更好”。上面就是本人分享的关于一次点播视频文件生成封面的需求设计和开发的思考过程,欢迎大家评论留言交流经验。
作者简介:????大家好,我是 Data-Mining(liuzhen007),是一位音视频技术爱好者,前后就职于传统广电巨头和音视频互联网公司,具有丰富的音视频直播和点播相关经验,对 WebRTC、FFmpeg 和 Electron 有非常深入的了解,????公众号:玩转音视频。同时也是 CSDN 博客专家、华为云社区云享专家、签约作者,欢迎关注我分享更多干货!????