Skip to content

Commit

Permalink
NewFromLocal can return multiple images
Browse files Browse the repository at this point in the history
If you use additional stores and pull the same image into
writable stores, you can end up with the situation where
you have the same image twice. This causes image exists
to return the wrong error.  It should return true in this
situation rather then an error.

Signed-off-by: Daniel J Walsh <dwalsh@redhat.com>
  • Loading branch information
rhatdan committed Oct 28, 2020
1 parent e04e567 commit 99d3e2e
Show file tree
Hide file tree
Showing 4 changed files with 19 additions and 4 deletions.
3 changes: 3 additions & 0 deletions libpod/define/errors.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,9 @@ var (
// ErrNoSuchImage indicates the requested image does not exist
ErrNoSuchImage = errors.New("no such image")

// ErrMultipleImages found multiple name and tag matches
ErrMultipleImages = errors.New("found multiple name and tag matches")

// ErrNoSuchTag indicates the requested image tag does not exist
ErrNoSuchTag = errors.New("no such tag")

Expand Down
3 changes: 2 additions & 1 deletion libpod/image/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import (
"github.com/containers/image/v5/docker/reference"
"github.com/containers/image/v5/signature"
"github.com/containers/image/v5/types"
"github.com/containers/podman/v2/libpod/define"
"github.com/containers/storage"
"github.com/pkg/errors"
)
Expand Down Expand Up @@ -42,7 +43,7 @@ func findImageInRepotags(search imageParts, images []*Image) (*storage.Image, er
if len(results) == 0 {
return &storage.Image{}, errors.Errorf("unable to find a name and tag match for %s in repotags", searchName)
} else if len(results) > 1 {
return &storage.Image{}, errors.Errorf("found multiple name and tag matches for %s in repotags", searchName)
return &storage.Image{}, errors.Wrapf(define.ErrMultipleImages, searchName)
}
return results[0], nil
}
Expand Down
7 changes: 6 additions & 1 deletion pkg/api/handlers/libpod/images.go
Original file line number Diff line number Diff line change
Expand Up @@ -44,11 +44,16 @@ func ImageExists(w http.ResponseWriter, r *http.Request) {
runtime := r.Context().Value("runtime").(*libpod.Runtime)
name := utils.GetName(r)

_, err := runtime.ImageRuntime().NewFromLocal(name)
ir := abi.ImageEngine{Libpod: runtime}
report, err := ir.Exists(r.Context(), name)
if err != nil {
utils.Error(w, "Something went wrong.", http.StatusNotFound, errors.Wrapf(err, "failed to find image %s", name))
return
}
if !report.Value {
utils.Error(w, "Something went wrong.", http.StatusNotFound, errors.Wrapf(nil, "failed to find image %s", name))
return
}
utils.WriteResponse(w, http.StatusNoContent, "")
}

Expand Down
10 changes: 8 additions & 2 deletions pkg/domain/infra/abi/images.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,8 +39,14 @@ const SignatureStoreDir = "/var/lib/containers/sigstore"

func (ir *ImageEngine) Exists(_ context.Context, nameOrID string) (*entities.BoolReport, error) {
_, err := ir.Libpod.ImageRuntime().NewFromLocal(nameOrID)
if err != nil && errors.Cause(err) != define.ErrNoSuchImage {
return nil, err
if err != nil {
if errors.Cause(err) == define.ErrMultipleImages {
return &entities.BoolReport{Value: true}, nil
} else {
if errors.Cause(err) != define.ErrNoSuchImage {
return nil, err
}
}
}
return &entities.BoolReport{Value: err == nil}, nil
}
Expand Down

0 comments on commit 99d3e2e

Please sign in to comment.