Skip to content

Commit bcd8bba

Browse files
committed
fix(upload): 优化分片函数
2 parents 34c2b7d + bfdf98f commit bcd8bba

File tree

2 files changed

+33
-55
lines changed

2 files changed

+33
-55
lines changed

internal/fs/sliceup.go

Lines changed: 27 additions & 51 deletions
Original file line numberDiff line numberDiff line change
@@ -42,8 +42,8 @@ type SliceUploadSession struct {
4242
// NewSliceUploadManager 创建分片上传管理器
4343
func NewSliceUploadManager() *SliceUploadManager {
4444
manager := &SliceUploadManager{}
45-
// 启动时恢复未完成的上传任务
46-
go manager.recoverIncompleteUploads()
45+
// 系统重启后清理未完成的上传任务,因为前端session会失效
46+
go manager.cleanupIncompleteUploads()
4747
return manager
4848
}
4949

@@ -532,18 +532,18 @@ func (sw *sliceWriter) Write(p []byte) (int, error) {
532532
return n, err
533533
}
534534

535-
// recoverIncompleteUploads 恢复重启后未完成的上传任务
536-
func (m *SliceUploadManager) recoverIncompleteUploads() {
535+
// cleanupIncompleteUploads 清理重启后未完成的上传任务和临时文件
536+
func (m *SliceUploadManager) cleanupIncompleteUploads() {
537537
defer func() {
538538
if r := recover(); r != nil {
539-
log.Errorf("Panic in recoverIncompleteUploads: %v", r)
539+
log.Errorf("Panic in cleanupIncompleteUploads: %v", r)
540540
}
541541
}()
542542

543543
// 等待一段时间,确保系统完全启动
544544
time.Sleep(10 * time.Second)
545545

546-
log.Info("Starting recovery of incomplete slice uploads...")
546+
log.Info("Starting cleanup of incomplete slice uploads after restart...")
547547

548548
// 查询所有未完成的上传任务
549549
incompleteUploads, err := db.GetIncompleteSliceUploads()
@@ -557,67 +557,43 @@ func (m *SliceUploadManager) recoverIncompleteUploads() {
557557
return
558558
}
559559

560-
log.Infof("Found %d incomplete slice uploads, starting recovery...", len(incompleteUploads))
560+
log.Infof("Found %d incomplete slice uploads, starting cleanup...", len(incompleteUploads))
561561

562+
cleanedCount := 0
562563
for _, upload := range incompleteUploads {
563-
m.recoverSingleUpload(upload)
564+
if m.cleanupSingleUpload(upload) {
565+
cleanedCount++
566+
}
564567
}
565568

566-
log.Info("Slice upload recovery completed")
569+
log.Infof("Slice upload cleanup completed, cleaned up %d tasks", cleanedCount)
567570
}
568571

569-
// recoverSingleUpload 恢复单个上传任务
570-
func (m *SliceUploadManager) recoverSingleUpload(upload *tables.SliceUpload) {
572+
// cleanupSingleUpload 清理单个上传任务
573+
func (m *SliceUploadManager) cleanupSingleUpload(upload *tables.SliceUpload) bool {
571574
defer func() {
572575
if r := recover(); r != nil {
573-
log.Errorf("Panic in recoverSingleUpload for task %s: %v", upload.TaskID, r)
576+
log.Errorf("Panic in cleanupSingleUpload for task %s: %v", upload.TaskID, r)
574577
}
575578
}()
576579

577-
log.Infof("Recovering upload task: %s, status: %s", upload.TaskID, upload.Status)
578-
579-
// 检查是否所有切片都已上传完成
580-
if tables.IsAllSliceUploaded(upload.SliceUploadStatus, upload.SliceCnt) {
581-
// 所有切片都已完成,尝试完成上传
582-
log.Infof("All slices completed for task %s, attempting to complete upload", upload.TaskID)
583-
m.attemptCompleteUpload(upload)
584-
return
585-
}
586-
587-
// 部分切片未完成的情况
588-
completedSlices := tables.CountUploadedSlices(upload.SliceUploadStatus)
589-
log.Infof("Task %s: %d/%d slices completed, marking as available for resume",
590-
upload.TaskID, completedSlices, upload.SliceCnt)
591-
592-
// 更新状态为等待用户继续上传
593-
upload.Status = tables.SliceUploadStatusWaiting
594-
upload.Message = "Ready for resume after server restart"
595-
if err := db.UpdateSliceUpload(upload); err != nil {
596-
log.Errorf("Failed to update slice upload status for task %s: %v", upload.TaskID, err)
597-
}
580+
log.Infof("Cleaning up upload task: %s, status: %s", upload.TaskID, upload.Status)
598581

599-
// 如果有临时文件但文件不存在,清理记录
582+
// 清理临时文件
600583
if upload.TmpFile != "" {
601-
if _, err := os.Stat(upload.TmpFile); os.IsNotExist(err) {
602-
log.Warnf("Temporary file lost for task %s, cleaning up", upload.TaskID)
603-
if err := db.DeleteSliceUploadByTaskID(upload.TaskID); err != nil {
604-
log.Errorf("Failed to clean up lost task %s: %v", upload.TaskID, err)
605-
}
584+
if err := os.Remove(upload.TmpFile); err != nil && !os.IsNotExist(err) {
585+
log.Warnf("Failed to remove temp file %s for task %s: %v", upload.TmpFile, upload.TaskID, err)
586+
} else {
587+
log.Debugf("Removed temp file: %s", upload.TmpFile)
606588
}
607589
}
608-
}
609-
610-
// attemptCompleteUpload 尝试完成上传(用于恢复已完成切片的任务)
611-
func (m *SliceUploadManager) attemptCompleteUpload(upload *tables.SliceUpload) {
612-
// 这里需要获取存储驱动,但在恢复阶段我们无法直接获取 storage driver
613-
// 所以我们将状态标记为待完成,等用户下次操作时自动完成
614-
upload.Status = tables.SliceUploadStatusPendingComplete
615-
upload.Message = "All slices completed, waiting for final completion"
616590

617-
if err := db.UpdateSliceUpload(upload); err != nil {
618-
log.Errorf("Failed to update slice upload to pending complete for task %s: %v", upload.TaskID, err)
619-
return
591+
// 从数据库中删除任务记录
592+
if err := db.DeleteSliceUploadByTaskID(upload.TaskID); err != nil {
593+
log.Errorf("Failed to delete slice upload task %s: %v", upload.TaskID, err)
594+
return false
620595
}
621596

622-
log.Infof("Task %s marked as pending completion", upload.TaskID)
597+
log.Infof("Successfully cleaned up task: %s", upload.TaskID)
598+
return true
623599
}

server/handles/fsup.go

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -250,10 +250,12 @@ func FsPreup(c *gin.Context) {
250250

251251
storage := c.Request.Context().Value(conf.StorageKey).(driver.Driver)
252252
path := c.Request.Context().Value(conf.PathKey).(string)
253-
fullPath := utils.FixAndCleanPath(stdpath.Join(path, req.Name))
254-
if res, _ := fs.Get(c.Request.Context(), fullPath, &fs.GetArgs{NoLog: true}); res != nil && !req.Overwrite {
255-
common.ErrorStrResp(c, "file exists", 403)
256-
return
253+
if !req.Overwrite {
254+
fullPath := utils.FixAndCleanPath(stdpath.Join(path, req.Name))
255+
if res, _ := fs.Get(c.Request.Context(), fullPath, &fs.GetArgs{NoLog: true}); res != nil {
256+
common.ErrorStrResp(c, "file exists", 403)
257+
return
258+
}
257259
}
258260

259261
res, err := fs.Preup(c.Request.Context(), storage, path, req)

0 commit comments

Comments
 (0)