前言
服务器中目前堆积了一部分无效文件,这些无效文件来自下面的一些操作:
- 已删除信息对应的附件。
- 过期的聊天消息:单聊和群聊消息缓存时间都是
120
天,超过120
天后,消息缓存会被移除,但是消息对应的附件还会保留。 - [上传文件] 和 [提交表单] 分成两个请求处理的功能,用户上传文件成功后,没有提交表单,这类文件就会成为垃圾文件。
- 修改头像、车图片等信息后,旧的文件仍然保留在服务器上未被移除。
除这些无效文件外,还有一部分重复的文件也会浪费服务器的存储空间,比如A给B连续发送多张相同的图片。
这些垃圾/无效文件,对 App
的功能并不会造成影响,唯一的影响就是会占用服务器的存储空间。就目前的用户数而言,这些垃圾文件其实并不会占用太大的存储空间,因此不作处理也是可以的。但我们针对文件的处理还包含了文件机审操作,每次文件上传都需要将文件提交机审。而 采用合适方案后,是可以减少提交文件机审的次数的,并且可以减少文件 I/O
的次数,这些都能够提高文件上传的效率。因此综合来看,还是有必要进行优化的。
方案选择
通过临时文件夹处理无效文件
- 文件上传后,先保存到临时文件夹,之后提交表单时,再将其移动到指定的文件夹中,临时文件夹中的文件定期清理
- 对于删除朋友圈信息这样的操作,将对应的文件移动到指定的文件夹,这个文件夹中的文件定期清理(注:这样操作后,原信息中保存的文件的
URL
将会失效) - 对于过期的聊天文件,定期将存储聊天文件的文件夹中超出期限(
120
天)的文件删除即可。
这是一种较为简单的方案,改动小,但仅仅只是解决了服务器中无效文件的问题,重复文件的问题并没有处理,并且对于文件上传的效率是没有提升的。
增加文件上传记录
这里先将大概的逻辑梳理出来,后面再对一些问题进行额外说明:
- 增加一个 文件上传记录表,表中记录对应文件的
Hash
值,服务端收到上传的文件后,计算其Hash
值,然后去已有的文件记录中找是否存在相同Hash
值的文件上传记录。(文件Hash
值计算方法后面再讲) - 如果表中无记录,那么表示是第一次上传,将文件保存到服务器,如果需要机审则提交机审,需要压缩则进行压缩。之后增加一条记录,文件引用数设置为0,文件名设置为文件
hash
值,记录文件的审核结果,保存原图和缩略图路径,最后给App
端返回对应的文件url
。 - 如果表中有记录,那么就直接根据现有记录来处理即可,无需再重复进行 [文件存储]、[生成缩略图]、[文件审核] 的操作,直接给
App
端返回对应的文件url
即可。(注:如果文件缩略图没有生成过,或者没有进行过审核,那么相关操作还是要执行的;并且文件记录如果isDelete = 1
,那么表示被清理了,上面这三个操作也要执行 ) App
端提交表单后,根据url
拿到hash
值,找对应的文件上传记录,将 文件记录的引用计数加1;文件对应的数据被删除后,比如删除朋友圈,那么 文件引用数减1;如果用户上传文件后没有提交表单,那么 文件引用计数不会变更。- 增加定时任务,定期清理 引用数为0,并且更新时间超过1年 的垃圾文件。
具体实施
目前使用的是 [增加文件上传记录] 的方式来对文件上传逻辑进行的改造,下面记录一下相关的问题和解决办法。
文件 Hash
计算
上面提到通过文件 Hash
值来处理重复图片的问题,具体处理是:文件上传记录表主键设置为文件 Hash
值;文件通过文件 Hash
值来命名。
然而哈希算法存在一个问题,存在哈希碰撞的问题,任何哈希算法都无法避免,但不同的哈希算法碰撞概率不同,就 文件哈希 而言, MD5
算法已被验证出会出现碰撞的情况(两张不同的图片 MD5
值一样)。如果出现哈希碰撞的话,会导致 两种不同的图片共用一个链接 的情况,这在 App
内的表现是 文件展示错乱。不过这种碰撞概率极小,对于我们目前的场景来说,MD5
算法就够用了。如果想要减少这种情况的发生,可以考虑使用 SHA-256
算法,MD5
算法对应的 hash
值是 32
位字符,而 SHA-256
算法对应的 hash
值是 64
位字符,字符位数越多,那么字符组合就更多,碰撞概率就更小。
另外,关于文件的 hash
值,即使原始内容只改动一个字节,哈希码也会完全不同。也就是说,图片的样式尺寸等信息发生变更后,它的 hash
值就会变更。
重复
Hash
值的概率虽然小,但是还是存在的,服务端后面可以考虑在逻辑上对这种情况进行处理。
文件记录表结构
关于文件上传记录表,有两种表结构:
- 单表结构。字段包括:文件哈希值、文件URL、文件存储路径、文件缩略图、文件审核状态、文件被引用次数,使用 文件哈希值 作为主键。
- 双表结构。如果想看 文件具体是被什么数据引用的,那么就需要在第1种设计的基础上 移除文件被引用次数,额外增加一个文件被引用记录表,专门记录文件被哪条数据引用了。
目前并没有要看 文件具体是被什么数据引用 的需求,因此目前使用的是第1种表结构,具体的表结构如下:
1 | thumbnail_chatcreate table t_app_file_upload_record |
file_hash
使用 64
位存储,这样之后如果需要将 MD5
算法替换为 SHA-256
算法可以直接进行替换。
audit_status
包含如下几种审核状态:0->未审核,1->审核通过,2->审核不通过,3->审核失败,4->已提交异步审核。
注意其中缩略图分成了两个字段来存储,分别是 thumbnail_logo
和 thumbnail_chat
,因为目前服务端对图片的压缩处理有两种:
- **
logo
类缩略图(width<=200 && heigh<=225
)**。通过POST /fileUpload/image - 普通图片上传
接口上传的图片,如果需要压缩,那么缩略图就是这种 - **聊天/朋友圈信息缩略图(
width<=720
)**。通过POST /fileUpload/upload/{type} - 朋友圈、聊天文件的上传
接口上传的图片,如果需要压缩,那么缩略图就是这种
缩略图为何要单独使用一个字段存储
上面说过,图片被调整后,对应的 Hash
值会变更,缩略图和原图的哈希值就是不一样的,那么这里 为什么不将缩略图单独作为一条记录存储呢?
这是考虑到目前 App
的场景,原图和缩略图可以通过 [Hash
值 + 指定后缀] 的方式获取,通过原图可以拿到缩略图,通过缩略图也可以获取到原图,缩略图和原图是强耦合关系,它们是一起存在一起被删除。额外通过一条记录存储的话,会增加表格复杂度和代码复杂度。
然而这么处理的话,有一个缺陷,就是 服务器上会出现重复 Hash
值的图片。比如现在上传一张图片 p1
,它的缩略图为 t1
,增加了一条文件上传记录,文件 Hash
值记录的是 p1
的哈希值。之后将缩略图 t1
作为原图上传,就会出现找不到 t1
对应的文件哈希值的情况,因此就会重新存储,并新增一条上传记录。但这种情况 最多也只是会存在两张相同的图片,t1
的哈希值被记录之后,之后就不会重新上传了,因此是可以接受的。
文件审核逻辑说明
audit_status
包含如下几种审核状态:0->未审核,1->审核通过,2->审核不通过,3->审核失败,4->已提交异步审核。
- 在上传文件时,如果需要审核,但文件状态是 [未审核] 或 [审核失败],那么重新提交机审;
- 如果文件状态是 [审核不通过],那么后续逻辑无需执行,直接返回提示给
App
端; - 如果文件状态是 [已提交异步审核],那么在
redis
缓存队列中增加缓存,异步审核结束直接处理后续逻辑。(这种情况在下面 [音视频文件异步审核带来的问题] 中有详细说明) - 审核不通过的文件,即使文件被移除了,文件记录
isDelete
被置为了1
,后面在接收到相同的文件时,仍然按 直接返回审核不通过的提示,不执行后续逻辑 来处理。 - 如果提交的音视频在文件记录中存在并且已经完成了审核,那么文件上传接口会直接返回文件审核结果,
App
端无需再等待异步回调。
除了上面的调整外,在对图片审核进行测试时发现会出现下面的问题:聊天文件上传较大的原图时,会出现审核失败的情况,原因是图片机审接口返回了审核失败的信息。针对这种情况,进行如下优化:提交的审核的图片,统一使用缩略图。
文件审核包含不同场景带来的问题
文件记录表中记录文件的审核状态,这存在一个问题:同一张图片,在不同场景下使用时,需要提交审核的参数是不同的,比如 [群聊]、[单聊] 图片的审核使用的就是不同的审核参数。
之前对图片审核进行过一次改造,目前图像审核使用的华为云自定义策略模式,所有场景的图片审核使用的都是同一策略,也就是说,目前图像审核的结果是可以在多个场景下复用的。
音视频文件异步审核带来的问题
目前服务端中进行的图片机审是同步请求,提交机审后接口立刻返回审核结果;而音视频审核是异步审核,提交机审后,需要等待回调。
异步审核就代表 [提交审核] 到 [审核完成] 中间会有一个时间,如果用户在这个时间内上传了相同的音视频文件,不做处理的话会重复提交审核。最好是能够按照如下的方式进行处理:用户1上传了音视频,文件还在审核中,这时用户2上传音视频,无需重复审核,只要在用户1上传的音视频审核完毕后直接通知用户2即可。
具体处理办法:
- 文件审核状态
auditStatus
增加一种状态:4 -> 已提交异步审核。 - 视频提交异步审核后,将 [待通知用户/带审核流程的任务] 缓存起来,缓存结构调整为
list
结构。异步审核还没结束时,别的用户又提交了相同的视频审核,那么再在缓存中添加一条即可。 - 当音视频任务审核完毕后,给所有缓存的 [待通知用户] 推送通知,而所有 [带审核流程的任务] 继续执行后续的审核流程。
朋友圈文件审核包含审核流程带来的问题
常规的文件上传,如果文件需要审核,审核操作和上传操作是一起进行的。而朋友圈中的文件审核操作和上传操作是分开的,审核操作是在后续的审核流程中进行的。因此针对朋友圈文件的审核操作,需要单独进行处理。处理后的朋友圈文件上传审核流程如下:
- 上传文件,服务端新增文件上传记录
- App端提交表单,服务端更新引用计数
- 开始进行文件的审核,服务端更新文件审核状态
- 如果是音视频,等待音视频异步审核结束,拿到审核结果后,再次更新文件的审核状态。
后续可以进行的优化。由于朋友圈文件的审核操作与上传文件的逻辑是分开的,因此与其他场景下的文件上传逻辑相比,朋友圈的文件上传对 FileUploadRecord
的更新操作多了一次。如果性能太差,后续可以考虑按如下逻辑进行:第1步上传操作中直接进行审核,在第3步进行文件审核时,就可以无需审核直接拿到文件审核结果,并且无需再进行一次 FileUploadRecord
更新操作。但这种处理的劣势是:朋友圈信息中所有的 [图片/视频/音频] 都会触发审核,而原先是只要有一个附件审核不通过,后续其他附件就不会再进行审核操作了。
存在的问题。在上面的第2和第3步中,正常情况下都是能够拿到文件对应的上传记录的,因为第1步已经确保了上传记录的存在。但是存在一种特殊情况:第2第3步提交的文件链接,没有经过第1步处理,比如提交的文件链接是第三方的,这种情况下找不到对应的文件记录,并且文件在服务器也不存在。这种情况在使用接口测试工具进行测试时可能会出现,而正常通过 App
端操作时应该不会出现。
针对这种情况,服务端进行了补偿措施:如果朋友圈文件提交审核时,根据文件 url
没有找到对应的文件记录,那么直接将这个文件 url
提交审核。
另外,这种问题后续服务端也需要统一进行一下限制,即 **提交表单时上传的文件 url
必须是我们服务的,禁止第三方文件 url
*。因为按照目前的文件上传逻辑,提交第三方文件url
是不会经过机审的,这容易出现问题。(后续可以考虑 App
端提交表单时,统一提交文件 Hash
值,由服务端去数据库找对应的文件 url
,再进行后续操作*)
文件引用计数变更逻辑
关于文件引用计数变更的处理,最先考虑的是通过切面处理,因为切面处理更易维护。但是尝试之后发现这种处理不太适合目前的场景,切面更适合 新增文件(引用计数增加)、删除文件(引用计数减少) 的场景,比如 朋友圈信息新增、朋友圈信息删除。而 文件修改 场景就不太适合,因为这种场景涉及 旧文件引用计数减少,新文件引用计数增加,比如 用户头像变更、名片图片变更。
因此目前按如下方式处理:在每个引用计数发生变化的位置,分别增加代码。
此外,关于文件引用计数的计算,存在一些疑问:App
端存在一些场景,没有触发文件上传操作,但是最终会涉及文件的引用变更。比如添加商友、保存名片,这些操作没有进行文件上传操作,但是最后会将其他数据中的文件冗余到自己的信息中,比如加商友时会从 t_app_user
表中拿到 [商友头像] 填充到 t_app_user_friend
中,那这类文件的引用计数是否需要计算呢?
目前考虑是:如果保存有文件的数据,后续用户可以对该数据中的文件重新上传,那么就进行引用计数的变更;否则就无需进行引用计数的变更。两个例子:
- 无需计算引用计数。B是A的商友,A修改商友头像,头像信息同步至B与A的商友关系中,用户之后是无法主动修改商友关系中的头像的,只能通过修改商友头像才会同步过来,因此这时商友关系中头像的变更是无需进行引用计数的修改的。
- 需要计算引用计数。A有名片并设置了名片正反面图像,B保存A的网络名片,会增加一条
UserCardTemp
(本地名片)记录,UserCardTemp
中的名片正反面图像来自网络名片,用户之后是可以对UserCardTemp
中的图像进行修改的,因此这时UserCardTemp
中的图像是需要进行文件引用计数变更的。
聊天文件引用计数的处理
目前的逻辑中,聊天消息的过期时间是 120
天,消息过期被移除后,附件还存在在服务器中。常规的文件上传逻辑包含两步:①. 文件上传(服务端新增 FileUploadRecord
) ②. 提交表单(服务端增加 FileUploadRecord
的引用计数)。对于聊天中发送的文件,第②步提交表单操作是没有的,因此引用计数的计算需要单独处理,目前有如下三种方案:
- 文件上传后,立刻增加引用计数;聊天消息过期后,将引用计数减少。使用这个方案的话,需要额外增加一个聊天消息过期监听事件。并且还存在一个问题:如果文件上传引用计数增加后,聊天消息发送失败,那么聊天消息不会缓存到服务端,这条文件的引用计数就有问题,定时清理文件时这个文件就不会被清理掉。
如果可以接受后面存在的这个问题,那么可以使用这种方案。
- 聊天消息发送后,增加引用计数;聊天消息过期后,引用计数减少。相比上一种方案,这种方案在 [服务端收到消息并成功缓存后] 才会增加引用计数,可以避免上面提到的问题。
- 聊天中上传的文件不记录引用计数的变更,对定时清理文件的逻辑进行调整,清理 [修改时间大于1年,且引用计数为0] 的文件。每一次文件引用计数的变更,都需要修改数据库。真实场景中,聊天文件的数量应该是比其他所有场景中文件数量之和还要多的,如果按照上面两种方式处理,即发送一个文件引用计数加1,那么数据库修改操作会非常频繁。而这种方案不需要记录聊天文件引用计数的变更,过期的文件也能正常被清理。
目前使用的是第三种方案,这种方案存在一个问题:发送聊天文件时,如果文件记录存在并且无需压缩和审核,那么服务端会直接返回这个文件,不进行其他处理。这时文件记录的 updateDate
是不会变化的,也就是说如果这个文件在 1
天后 updateDate
就满一年了,那么 1
天后它就被清理掉。因此,对文件上传记录进行了如下改造:**文件上传时,如果文件上传记录已存在,那么更新其 updateDate
**。这个新增的逻辑只对聊天文件上传的场景进行了处理,因为其他场景下的文件上传都需要进行文件引用计数的变更。
这样改造后还存在一个问题:发送收藏文件 或 转发图片 时,是不会走 上传文件 接口的,这时文件记录的 updateDate
也不会变更,这可能会导致 文件无法按照正常的逻辑被清理:
- 这两个操作中,发送收藏文件 不会影响文件的清理逻辑,因为只有聊天中只能发送未被删除的收藏文件,这表示这个收藏文件的引用计数肯定大于0,也就不会被异常清除;
- 但是文件转发操作就会受到影响了,
App
端目前处理的的文件转发逻辑是直接转发文件url
,不经过文件上传接口。看如下案例:文件url
在1
天后会被清除,用户在聊天中转发这个文件,文件上传记录不会更新,1天后文件会被清除,正常的应该是这个文件在1年后才被清除。
因此需要 App
端进行如下调整:聊天中转发文件也走上传文件接口,由于服务端目前已对文件进行 Hash
去重,因此这个转发操作不会导致服务端重复存储文件,最终返回的文件 Url
与被转发的图片也是一样的。 修改为这一步是为了服务端能够更新文件上传记录的 updateDate
,以便文件清理逻辑能够正常执行。
额外补充:目前文件清理逻辑是 [定期清理修改时间大于1年,且引用计数为0的文件]。由于聊天文件未接入引用计数的变更逻辑,因此后续如果需要调整文件清理的逻辑,要保证清理的文件的修改时间至少大于 120
天,也就是不能小于聊天消息缓存的过期时间。
文件命名规则
上传的文件统一按照 Hash
值命名,针对图片,还需要拼接尺寸后缀以及考虑缩略图。原先的图片命名规则是根据场景划分的,不同场景下命名规则不同:
POST /fileUpload/image - 普通图片上传
接口上传的图片。原图:通过uuid
命名,不携带后缀缩略图:原图url
后增加_t
后缀POST /fileUpload/upload/{type} - 朋友圈、聊天文件的上传
接口上传的图片。原图:分两种情况
①. 聊天中选择原图、朋友圈图片,这种图片通过 uuid
命名,并增加 _o
后缀:http://7vw31jdn.dongtaiyuming.net/images/app/63a10c4bc01aa17f36335d2b4197ff08_o.jpg
②. 聊天中未选择原图,这种图片通过 uuid
命名,并增加 _width*height
后缀:http://7vw31jdn.dongtaiyuming.net/images/app/63a10c4bc01aa17f36335d2b4197ff08_500*450.jpg
缩略图:也分两种情况
①. 视频缩略图,视频 url
基础上增加 _t
后缀,图片是 png
格式
②. 聊天中选择原图、朋友圈图片,这种会生成缩略图,在原图 url
的基础上去除 _o
后缀。
而新的图片命名规则不再根据场景进行划分,统一按如下方式命名:
- 原图:通过
hash
值命名,不增加后缀:http://7vw31jdn.dongtaiyuming.net/images/app/63a10c4bc01aa17f36335d2b4197ff08.jpg?size=width*height
logo
类缩略图:在原图基础上增加_s
后缀:http://7vw31jdn.dongtaiyuming.net/images/app/63a10c4bc01aa17f36335d2b4197ff08_s.jpg?size=width*height
- 朋友圈、聊天缩略图:在原图基础上增加
_t
后缀:http://7vw31jdn.dongtaiyuming.net/images/app/63a10c4bc01aa17f36335d2b4197ff08_t.jpg?size=width*height
除了上面的命名规则外,原先还会在图片 url
后拼接图片尺寸信息,原先的规则如下:
- 视频:视频
url
后拼接缩略图尺寸,视频缩略图url
后拼接自己的尺寸 - 图片:有缩略图的图片,原图后面拼接缩略图尺寸,缩略图后面拼接缩略图尺寸;
无缩略图的图片,图片后面拼接当前图片的尺寸信息
目前统一按照下面的规则拼接尺寸:
- 视频:仍然保持原先的规则。
- 图片:原图和缩略图后面统一拼接自己的尺寸信息。
图片命名规则变更后对 App
端的影响
在图片命名规则变更后,会对 App
端现有功能造成影响。因此针对 App
端中所有涉及图片上传的功能进行了测试,测试下来发现下面几个功能受到了影响:
- 朋友圈图片中,如果图片被压缩了,点击查看大图时,显示的仍然是缩略图(比较模糊);点击下载图片时,会提示下载失败;收藏该图片后,收藏列表中加载不出,无法查看。
- [本地名片的正反面图片]、[商友/好友头像]、[车名片图片] 、[群统计/群投票图片],如果这些图片有缩略图,查看大图时显示的仍然是缩略图(比较模糊),没有展示原图。
对 App
端代码进行 Review
,目前 App
端处理的图片加载逻辑如下:
- 朋友圈图片加载逻辑。在 [查看大图、下载图片、收藏图片] 操作时,会去获取原图
url
:首先判断图片url
是否携带_o
后缀,如果携带,说明是原图,那么直接 [下载/收藏/ 展示] 即可;如果没有携带,说明是缩略图,那么加上_o
后缀,拿到原图url
,再进行 [下载/收藏/展示]。 - 普通图片加载逻辑。在 [查看大图] 时,会去获取原图
url
:首先判断图片url
是否携带_t
后缀,如果携带,说明是缩略图,那么名片详情中展示的正反面图片就去除_t
后缀,拿到原图url
,再进行 [展示];如果未携带,说明是原图,直接展示。
这两个个问题都是由于 原图缩略图命名规则发生变化 导致的问题,旧的 [获取原图 url
] 逻辑还按 [朋友圈图片] 和 [普通图片] 进行了区分。服务端采用新的命名规则后,App
端针对 [获取原图 url
] 逻辑,可以对所有场景的图片统一按照如下方式处理:
- 如果图片
Url
后缀携带_t
、_s
后缀,表示图片是缩略图,那么将_t
、_s
后缀去除,拿到原图Url
,进行 [下载/收藏/展示]; - 如果图片
Url
没有携带后缀,那么表示是原图,直接进行 [下载/收藏/展示] 即可。
另外,图片 url
后拼接尺寸的逻辑也发生了变更,目前测试下来调整后对 App
没有影响,但是没有对相关代码进行 review
,因此可能部分被影响的场景未被测试到,如果之后发现问题再做调整。
文件存储路径优化
目前是各个模块的文件分开存放,如果同一层级的文件过多,会影响检索效率,比如聊天文件。由于现在统一使用文件 Hash
来去重,后面会出现 不同模块的数据引用同一张图片 的情况,比如聊天、朋友圈、头像使用的都是同一图片,这种情况下,分模块存储已经意义不大了,因此目前对存储路径进行改造,统一按照日期对存储路径进行命名,不再区分模块,比如在 2024-04-17
上传的文件,统一存储到 [20240417] 文件夹下面。
同一个视频 Hash
值不一样
在朋友圈和聊天中发送视频时(聊天中不勾选原图),存在一个问题,多次发送同一个视频,服务端接收到之后计算其 Hash
值,每次都不一样,Hash
值不一样,服务端就会认为它们是不同的文件,就会分别对它们执行文件保存、新增上传记录的操作。
Hash
值不一样的问题上面提到过,这里的问题应该是 App
端对视频进行压缩后导致的。但是同样是 App
端进行压缩,同一张图片在 App
端多次压缩,上传到服务端时计算得到的 Hash
值却是相同的,因此猜测视频压缩后 Hash
值不一样是因为压缩算法的问题。
注:这个问题仍然需要调查,如果视频压缩后每次
Hash
值都不一样的情况的无法避免,那么就需要寻找其他的解决方案,比如通过原视频的Hash
值来确定是否重复。
后续可以进行的一些优化
- 目前文件上传接口中,耗时较长的操作是获取文件的
Hash
值,该操作后续可以考虑放在App
端处理。文件Hash
放在App
端做还有一个好处,App
端计算完文件Hash
值后,直接请求服务端查询是否存在相同Hash
值的文件,如果存在,服务端直接返回;如果不存在,再按照常规的流程进行。相比之前的流程,如果文件Hash
存在的话,那么就能省去文件上传到服务器的操作,如果是视频,还可以额外省去压缩视频的操作。不过通过这种方式拿到的文件Hash
值是原文件的Hash
值,如果视频/图片需要在App
端压缩后再发送,那么还是需要先压缩才能拿到对应文件的Hash
值 App
端提交表单时,统一提交文件Hash
值,由服务端去数据库找对应的文件url
,如果未找到,则表示文件不存在,返回提示信息,这样可以避免用户通过非常规手段提交第三方Url
。- 二维码、群头像,这类由服务端生成的文件,也接入新的文件上传逻辑:增加对应的文件上传记录。
- 目前文件引用计数变更是嵌套在主逻辑之内的,与主逻辑耦合度过高,后期可以考虑针对这一块进行优化,将其从主逻辑解耦出来。
- 目前音视频文件在提交审核后,对应文件记录的
auditStatus
会被置为4
。而存在一种情况,阿里云音视频审核任务提交后,由于一些原因,服务端一直没有收到回调,这时音视频的审核状态将不会改变。服务端需要对这种特殊情况进行处理,可以在提交审核任务后,超过指定时间就将审核状态修改为审核失败状态。 - 文件记录中审核过的文件,超过一定时间后可以重新提交审核。因为审核规则和尺度可能在各个时间都是不同的,原先审核未通过的信息过1年后就能审核通过,反之亦然。
参考链接
IM开发基础知识补课(二):如何设计大量图片文件的服务端存储架构?
文件储存用 md5 做标识可行吗,要考虑会出现相同 md5 的文件的情况吗?