summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--libpod/boltdb_state.go36
1 files changed, 34 insertions, 2 deletions
diff --git a/libpod/boltdb_state.go b/libpod/boltdb_state.go
index 9745121c7..c3db6152a 100644
--- a/libpod/boltdb_state.go
+++ b/libpod/boltdb_state.go
@@ -162,6 +162,11 @@ func (s *BoltState) Refresh() error {
return err
}
+ namesBucket, err := getNamesBucket(tx)
+ if err != nil {
+ return err
+ }
+
ctrsBucket, err := getCtrBucket(tx)
if err != nil {
return err
@@ -192,6 +197,7 @@ func (s *BoltState) Refresh() error {
// PID, mountpoint, and state for all of them
// Then save the modified state
// Also clear all network namespaces
+ toRemoveIDs := []string{}
err = idBucket.ForEach(func(id, name []byte) error {
ctrBkt := ctrsBucket.Bucket(id)
if ctrBkt == nil {
@@ -199,8 +205,16 @@ func (s *BoltState) Refresh() error {
podBkt := podsBucket.Bucket(id)
if podBkt == nil {
// This is neither a pod nor a container
- // Error out on the dangling ID
- return errors.Wrapf(define.ErrInternal, "id %s is not a pod or a container", string(id))
+ // Something is seriously wrong, but
+ // continue on and try to clean up the
+ // state and become consistent.
+ // Just note what needs to be removed
+ // for now - ForEach says you shouldn't
+ // remove things from the table during
+ // it.
+ logrus.Errorf("Database issue: dangling ID %s found (not a pod or container) - removing", string(id))
+ toRemoveIDs = append(toRemoveIDs, string(id))
+ return nil
}
// Get the state
@@ -285,6 +299,24 @@ func (s *BoltState) Refresh() error {
return err
}
+ // Remove dangling IDs.
+ for _, id := range toRemoveIDs {
+ // Look up the ID to see if we also have a dangling name
+ // in the DB.
+ name := idBucket.Get([]byte(id))
+ if name != nil {
+ if testID := namesBucket.Get(name); testID != nil {
+ logrus.Infof("Found dangling name %s (ID %s) in database", string(name), id)
+ if err := namesBucket.Delete(name); err != nil {
+ return errors.Wrapf(err, "error removing dangling name %s (ID %s) from database", string(name), id)
+ }
+ }
+ }
+ if err := idBucket.Delete([]byte(id)); err != nil {
+ return errors.Wrapf(err, "error removing dangling ID %s from database", id)
+ }
+ }
+
// Now refresh volumes
err = allVolsBucket.ForEach(func(id, name []byte) error {
dbVol := volBucket.Bucket(id)