diff --git a/pkg/backup/download.go b/pkg/backup/download.go index c469e488..b091f2b4 100644 --- a/pkg/backup/download.go +++ b/pkg/backup/download.go @@ -40,6 +40,16 @@ var ( ErrBackupIsAlreadyExists = errors.New("backup is already exists") ) +func (b *Backuper) resumeExistingBackup(backupName string) bool { + _, checkDownloadErr := os.Stat(path.Join(b.DefaultDataPath, "backup", backupName, "download.state2")) + if errors.Is(checkDownloadErr, os.ErrNotExist) { + log.Warn().Msgf("%s already exists but no download.state2 found, will resume download from scratch", backupName) + } else { + log.Warn().Msgf("%s already exists will try to resume download", backupName) + } + return true +} + func (b *Backuper) Download(backupName string, tablePattern string, partitions []string, schemaOnly, rbacOnly, configsOnly, namedCollectionsOnly, resume bool, hardlinkExistsFiles bool, backupVersion string, commandId int) error { if pidCheckErr := pidlock.CheckAndCreatePidFile(backupName, "download"); pidCheckErr != nil { return errors.WithMessage(pidCheckErr, "CheckAndCreatePidFile") @@ -87,14 +97,8 @@ func (b *Backuper) Download(backupName string, tablePattern string, partitions [ } if !b.resume { return ErrBackupIsAlreadyExists - } else { - _, checkDownloadErr := os.Stat(path.Join(b.DefaultDataPath, "backup", backupName, "download.state2")) - if errors.Is(checkDownloadErr, os.ErrNotExist) { - return ErrBackupIsAlreadyExists - } - isResumeExists = true - log.Warn().Msgf("%s already exists will try to resume download", backupName) } + isResumeExists = b.resumeExistingBackup(backupName) } } startDownload := time.Now() diff --git a/pkg/backup/download_test.go b/pkg/backup/download_test.go index 27ea7434..ac7c5f7e 100644 --- a/pkg/backup/download_test.go +++ b/pkg/backup/download_test.go @@ -1,6 +1,8 @@ package backup import ( + "os" + "path" "regexp" "testing" "time" @@ -91,6 +93,16 @@ var remoteBackup = storage.Backup{ UploadDate: time.Now(), } +func TestResumeExistingBackupAllowsMissingStateFile(t *testing.T) { + backupName := "test_resume_crash" + defaultDataPath := t.TempDir() + assert.NoError(t, os.MkdirAll(path.Join(defaultDataPath, "backup", backupName), 0o750)) + + backuper := &Backuper{DefaultDataPath: defaultDataPath} + + assert.True(t, backuper.resumeExistingBackup(backupName)) +} + func TestReBalanceTablesMetadataIfDiskNotExists_Files_NoErrors(t *testing.T) { remoteBackup.DataFormat = "tar" baseTable := metadata.TableMetadata{