mirror of
https://github.com/rcourtman/Pulse.git
synced 2026-05-07 00:37:36 +00:00
74 lines
2.3 KiB
Go
74 lines
2.3 KiB
Go
package dockeragent
|
|
|
|
import (
|
|
"context"
|
|
"strings"
|
|
"time"
|
|
|
|
"github.com/docker/docker/api/types/container"
|
|
)
|
|
|
|
// cleanupOrphanedBackups searches for and removes any Pulse backup containers
|
|
// (created during updates) that are older than 15 minutes.
|
|
func (a *Agent) cleanupOrphanedBackups(ctx context.Context) {
|
|
if !a.tryStartCleanupTask() {
|
|
a.logger.Debug().Msg("Skipping orphaned backup cleanup - previous cleanup still running")
|
|
return
|
|
}
|
|
defer a.finishCleanupTask()
|
|
|
|
a.logger.Debug().Msg("Checking for orphaned backup containers")
|
|
|
|
// List all containers (including stopped ones)
|
|
list, err := dockerCallWithRetry(ctx, dockerCleanupCallTimeout, func(callCtx context.Context) ([]container.Summary, error) {
|
|
return a.docker.ContainerList(callCtx, container.ListOptions{
|
|
All: true,
|
|
})
|
|
})
|
|
if err != nil {
|
|
a.logger.Warn().Err(annotateDockerConnectionError(err)).Msg("Failed to list containers for cleanup")
|
|
return
|
|
}
|
|
|
|
for _, c := range list {
|
|
if !isBackupContainer(c.Names) {
|
|
continue
|
|
}
|
|
|
|
// Check age based on the timestamp in the name, not the container's creation date
|
|
// (Renaming a container does not change its creation date)
|
|
parts := strings.Split(c.Names[0], backupContainerMarker)
|
|
if len(parts) < 2 {
|
|
continue
|
|
}
|
|
|
|
timestampStr := parts[len(parts)-1]
|
|
// Backup names are currently stamped with the agent host's local wall
|
|
// clock, so cleanup must parse in the local location to avoid treating
|
|
// valid stale backups as fresh on non-UTC systems.
|
|
backupTime, err := time.ParseInLocation("20060102_150405", timestampStr, time.Local)
|
|
if err != nil {
|
|
// If we can't parse the timestamp, fall back to creation date as a safety
|
|
created := time.Unix(c.Created, 0)
|
|
if time.Since(created) < 15*time.Minute {
|
|
continue
|
|
}
|
|
backupTime = created
|
|
}
|
|
|
|
if time.Since(backupTime) > 15*time.Minute {
|
|
a.logger.Info().
|
|
Str("container", c.Names[0]).
|
|
Time("backupTime", backupTime).
|
|
Msg("removing orphaned backup container")
|
|
|
|
_, err := dockerCallWithRetry(ctx, dockerCleanupCallTimeout, func(callCtx context.Context) (struct{}, error) {
|
|
err := a.docker.ContainerRemove(callCtx, c.ID, container.RemoveOptions{Force: true})
|
|
return struct{}{}, err
|
|
})
|
|
if err != nil {
|
|
a.logger.Warn().Err(annotateDockerConnectionError(err)).Str("id", c.ID).Msg("Failed to remove orphaned backup container")
|
|
}
|
|
}
|
|
}
|
|
}
|