Skip to content

Commit d09bbc7

Browse files
authored
fix(dr): use Status.CompletionTimestamp for sorting backups (#1679)
1 parent 736ecc9 commit d09bbc7

File tree

3 files changed

+190
-63
lines changed

3 files changed

+190
-63
lines changed

cmd/installer/cli/restore.go

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -192,8 +192,8 @@ func RestoreCmd(ctx context.Context, name string) *cobra.Command {
192192
return fmt.Errorf("unable to resume: %w", err)
193193
}
194194
if backupToRestore != nil {
195-
creationTimestamp := backupToRestore.GetCreationTimestamp().Format("2006-01-02 15:04:05 UTC")
196-
logrus.Infof("Resuming restore from backup %q (%s)\n", backupToRestore.GetName(), creationTimestamp)
195+
completionTimestamp := backupToRestore.GetCompletionTimestamp().Format("2006-01-02 15:04:05 UTC")
196+
logrus.Infof("Resuming restore from backup %q (%s)\n", backupToRestore.GetName(), completionTimestamp)
197197

198198
if err := overrideRuntimeConfigFromBackup(localArtifactMirrorPort, *backupToRestore); err != nil {
199199
return fmt.Errorf("unable to override runtime config from backup: %w", err)
@@ -339,10 +339,11 @@ func RestoreCmd(ctx context.Context, name string) *cobra.Command {
339339

340340
logrus.Debugf("picking backup to restore")
341341
backupToRestore = pickBackupToRestore(backups)
342+
logrus.Debugf("backup to restore: %s", backupToRestore.GetName())
342343

343344
logrus.Info("")
344-
creationTimestamp := backupToRestore.GetCreationTimestamp().Time.Format("2006-01-02 15:04:05 UTC")
345-
shouldRestore := prompts.New().Confirm(fmt.Sprintf("Restore from backup %q (%s)?", backupToRestore.GetName(), creationTimestamp), true)
345+
completionTimestamp := backupToRestore.GetCompletionTimestamp().Format("2006-01-02 15:04:05 UTC")
346+
shouldRestore := prompts.New().Confirm(fmt.Sprintf("Restore from backup %q (%s)?", backupToRestore.GetName(), completionTimestamp), true)
346347
logrus.Info("")
347348
if !shouldRestore {
348349
logrus.Infof("Aborting restore...")
@@ -1015,6 +1016,7 @@ func waitForBackups(ctx context.Context, out io.Writer, kcli client.Client, k0sC
10151016
}
10161017
}
10171018

1019+
logrus.Debugf("Found %d restorable backup(s)", len(validBackups))
10181020
if len(validBackups) == 1 {
10191021
loading.Infof("Found 1 restorable backup!")
10201022
} else {
@@ -1053,7 +1055,8 @@ func pickBackupToRestore(backups []disasterrecovery.ReplicatedBackup) *disasterr
10531055
latestBackup = &b
10541056
continue
10551057
}
1056-
if b.GetCreationTimestamp().After(latestBackup.GetCreationTimestamp().Time) {
1058+
// Should this use Status.StartTimestamp instead of Status.CompletionTimestamp?
1059+
if b.GetCompletionTimestamp().After(latestBackup.GetCompletionTimestamp().Time) {
10571060
latestBackup = &b
10581061
}
10591062
}

pkg/disasterrecovery/backup.go

Lines changed: 32 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -63,22 +63,32 @@ var (
6363
)
6464

6565
// ReplicatedBackups implements sort.Interface for []ReplicatedBackup based on the
66-
// CreationTimestamp of the infrastructure backup.
66+
// Status.StartTimestamp of the infrastructure backup.
6767
type ReplicatedBackups []ReplicatedBackup
6868

6969
func (a ReplicatedBackups) Len() int { return len(a) }
7070
func (a ReplicatedBackups) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
7171
func (a ReplicatedBackups) Less(i, j int) bool {
7272
var iTime, jTime time.Time
73-
if a[i].GetInfraBackup() != nil {
74-
iTime = a[i].GetInfraBackup().GetCreationTimestamp().Time
75-
} else if len(a[i]) > 0 {
76-
iTime = a[i][0].GetCreationTimestamp().Time
73+
if a[i].GetInfraBackup() != nil && a[i].GetInfraBackup().Status.StartTimestamp != nil {
74+
iTime = a[i].GetInfraBackup().Status.StartTimestamp.Time
75+
} else {
76+
for _, backup := range a[i] {
77+
if backup.Status.StartTimestamp != nil {
78+
iTime = backup.Status.StartTimestamp.Time
79+
break
80+
}
81+
}
7782
}
78-
if a[j].GetInfraBackup() != nil {
79-
jTime = a[j].GetInfraBackup().GetCreationTimestamp().Time
80-
} else if len(a[j]) > 0 {
81-
jTime = a[j][0].GetCreationTimestamp().Time
83+
if a[j].GetInfraBackup() != nil && a[j].GetInfraBackup().Status.StartTimestamp != nil {
84+
jTime = a[j].GetInfraBackup().Status.StartTimestamp.Time
85+
} else {
86+
for _, backup := range a[j] {
87+
if backup.Status.StartTimestamp != nil {
88+
jTime = backup.Status.StartTimestamp.Time
89+
break
90+
}
91+
}
8292
}
8393
return iTime.Before(jTime)
8494
}
@@ -181,18 +191,22 @@ func (b ReplicatedBackup) GetRestore() (*velerov1.Restore, error) {
181191
return nil, fmt.Errorf("missing restore spec annotation")
182192
}
183193

184-
// GetCreationTimestamp returns the creation timestamp of the velero infra backup object or the
185-
// first backup in the slice if the infra backup is not found.
186-
func (b ReplicatedBackup) GetCreationTimestamp() metav1.Time {
187-
backup := b.GetInfraBackup()
188-
if backup != nil {
189-
return backup.GetCreationTimestamp()
194+
// GetCompletionTimestamp returns the completion timestamp of the last velero backup to be
195+
// completed or zero if the expected backup count is not met or any of the backups in the slice is
196+
// not completed.
197+
func (b ReplicatedBackup) GetCompletionTimestamp() metav1.Time {
198+
if b.GetExpectedBackupCount() != len(b) {
199+
return metav1.Time{}
190200
}
191-
// if the infra backup is not found, we return the creation timestamp of the first backup
201+
var completionTimestamp metav1.Time
192202
for _, backup := range b {
193-
return backup.GetCreationTimestamp()
203+
if backup.Status.CompletionTimestamp == nil {
204+
return metav1.Time{}
205+
} else if backup.Status.CompletionTimestamp.Time.After(completionTimestamp.Time) {
206+
completionTimestamp = *backup.Status.CompletionTimestamp
207+
}
194208
}
195-
return metav1.Time{}
209+
return completionTimestamp
196210
}
197211

198212
// GetAnnotation returns the value of the specified annotation key from the velero infra backup

0 commit comments

Comments
 (0)