refactor(backend): update file info handling to use pointers and enhance upload task validation with expiration checks

This commit is contained in:
keven1024
2025-04-30 15:08:26 +08:00
parent 1dc349ef31
commit f2c115b09c
2 changed files with 56 additions and 18 deletions

View File

@@ -27,7 +27,7 @@ func CreateUploadTask(c echo.Context) error {
fileId := utils.GetFileId(r.FileHash, r.FileSize)
fileInfo, _ := models.GetRedisFileInfo(fileId)
if fileInfo != (models.RedisFileInfo{}) {
if fileInfo != nil {
return utils.HTTPSuccessHandler(c, map[string]any{
"size": fileInfo.FileSize,
"mime_type": fileInfo.MimeType,
@@ -78,12 +78,20 @@ func UploadFileSlice(c echo.Context) error {
if r.FileId == "" || r.FileIndex == 0 || r.FileSlice == nil {
return utils.HTTPErrorHandler(c, errors.New("上传文件信息不完整"))
}
_, err := models.GetRedisFileInfo(r.FileId)
fileInfo, err := models.GetRedisFileInfo(r.FileId)
if err != nil {
return utils.HTTPErrorHandler(c, err)
}
now := time.Now().Unix()
if fileInfo.CreatedAt+fileInfo.Expire < now {
return utils.HTTPErrorHandler(c, errors.New("上传任务已过期"))
}
if fileInfo.FileType != models.FileTypeInit {
return utils.HTTPErrorHandler(c, errors.New("上传任务状态错误"))
}
// 打开文件
file, err := r.FileSlice.Open()
if err != nil {
@@ -123,6 +131,11 @@ func FinishUploadTask(c echo.Context) error {
return utils.HTTPErrorHandler(c, errors.New("上传任务状态错误"))
}
now := time.Now().Unix()
if fileInfo.CreatedAt+fileInfo.Expire < now {
return utils.HTTPErrorHandler(c, errors.New("上传任务已过期"))
}
// 合并文件切片
uploadPath, _ := services.GetUploadDirPath()
slicesPath := filepath.Join(uploadPath, fmt.Sprintf("%s_%s", r.FileId, "tmp"))
@@ -133,12 +146,33 @@ func FinishUploadTask(c echo.Context) error {
return utils.HTTPErrorHandler(c, err)
}
// 更新文件状态
// fileInfo.FileType = models.FileTypeComplete
if err := services.MergeFileSlices(r.FileId); err != nil {
// 计算文件MD5
file, err := os.Open(mergeFilePath)
if err != nil {
file.Close()
os.Remove(mergeFilePath)
return utils.HTTPErrorHandler(c, err)
}
file_hash, err := utils.GetFileMd5(file)
if err != nil {
file.Close()
os.Remove(mergeFilePath)
return utils.HTTPErrorHandler(c, err)
}
if file_hash != fileInfo.FileHash {
file.Close()
os.Remove(mergeFilePath)
return utils.HTTPErrorHandler(c, errors.New("文件MD5不一致"))
}
defer file.Close()
// 更新文件信息
models.SetRedisFileInfo(r.FileId, models.RedisFileInfo{
FileType: models.FileTypeUpload,
})
return utils.HTTPSuccessHandler(c, map[string]any{
"message": "文件上传完成并合并成功",
})

View File

@@ -3,9 +3,9 @@ package models
import (
"backend/internal/utils"
"encoding/json"
"errors"
"dario.cat/mergo"
"github.com/redis/go-redis/v9"
)
type FileInfo struct {
@@ -35,18 +35,20 @@ type RedisShareInfo struct {
CreatedAt int64 `json:"created_at"`
}
func GetRedisFileInfo(fileId string) (RedisFileInfo, error) {
func GetRedisFileInfo(fileId string) (*RedisFileInfo, error) {
rdb, ctx := utils.GetRedisClient()
fileInfoUnmarshalData, _ := rdb.HGet(ctx, "015:fileInfoMap", fileId).Result()
if fileInfoUnmarshalData != "" {
var fileInfoData RedisFileInfo
if err := json.Unmarshal([]byte(fileInfoUnmarshalData), &fileInfoData); err != nil {
return RedisFileInfo{}, err
}
return fileInfoData, nil
fileInfoUnmarshalData, err := rdb.HGet(ctx, "015:fileInfoMap", fileId).Result()
if err == redis.Nil {
return nil, nil
}
return RedisFileInfo{}, errors.New("db不存在该文件信息")
if err != nil {
return nil, err
}
var fileInfoData RedisFileInfo
if err := json.Unmarshal([]byte(fileInfoUnmarshalData), &fileInfoData); err != nil {
return nil, err
}
return &fileInfoData, nil
}
func SetRedisFileInfo(fileId string, fileInfo RedisFileInfo) error {
@@ -55,7 +57,9 @@ func SetRedisFileInfo(fileId string, fileInfo RedisFileInfo) error {
if err != nil {
return err
}
mergo.Merge(&fileInfo, old_fileInfo)
if old_fileInfo != nil {
mergo.Merge(&fileInfo, old_fileInfo)
}
jsonData, _ := json.Marshal(fileInfo)
_, err = rdb.HSet(ctx, "015:fileInfoMap", fileId, string(jsonData)).Result()
return err