mirror of https://github.com/containers/podman.git
move image filters under libpod/images
to make things more effecient for the api work we are doing, we should process image filters internally (as opposed to in main). this allows for better api responses and more closely affiliated functions. Signed-off-by: baude <bbaude@redhat.com>
This commit is contained in:
parent
c2dab75f0e
commit
8be7b466d8
9
API.md
9
API.md
|
@ -123,6 +123,8 @@ in the [API.md](https://github.com/containers/libpod/blob/master/API.md) file in
|
||||||
|
|
||||||
[func ListImages() Image](#ListImages)
|
[func ListImages() Image](#ListImages)
|
||||||
|
|
||||||
|
[func ListImagesWithFilters(filters: []string) Image](#ListImagesWithFilters)
|
||||||
|
|
||||||
[func ListPods() ListPodData](#ListPods)
|
[func ListPods() ListPodData](#ListPods)
|
||||||
|
|
||||||
[func LoadImage(name: string, inputFile: string, quiet: bool, deleteFile: bool) MoreResponse](#LoadImage)
|
[func LoadImage(name: string, inputFile: string, quiet: bool, deleteFile: bool) MoreResponse](#LoadImage)
|
||||||
|
@ -892,6 +894,13 @@ See also [GetContainer](#GetContainer).
|
||||||
method ListImages() [Image](#Image)</div>
|
method ListImages() [Image](#Image)</div>
|
||||||
ListImages returns information about the images that are currently in storage.
|
ListImages returns information about the images that are currently in storage.
|
||||||
See also [InspectImage](#InspectImage).
|
See also [InspectImage](#InspectImage).
|
||||||
|
### <a name="ListImagesWithFilters"></a>func ListImagesWithFilters
|
||||||
|
<div style="background-color: #E8E8E8; padding: 15px; margin: 10px; border-radius: 10px;">
|
||||||
|
|
||||||
|
method ListImagesWithFilters(filters: [[]string](#[]string)) [Image](#Image)</div>
|
||||||
|
ListImagesWithFilters returns information about the images that are currently in storage
|
||||||
|
after one or more filters has been applied.
|
||||||
|
See also [InspectImage](#InspectImage).
|
||||||
### <a name="ListPods"></a>func ListPods
|
### <a name="ListPods"></a>func ListPods
|
||||||
<div style="background-color: #E8E8E8; padding: 15px; margin: 10px; border-radius: 10px;">
|
<div style="background-color: #E8E8E8; padding: 15px; margin: 10px; border-radius: 10px;">
|
||||||
|
|
||||||
|
|
|
@ -5,14 +5,12 @@ import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"reflect"
|
"reflect"
|
||||||
"sort"
|
"sort"
|
||||||
"strconv"
|
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
"unicode"
|
"unicode"
|
||||||
|
|
||||||
"github.com/containers/buildah/pkg/formats"
|
"github.com/containers/buildah/pkg/formats"
|
||||||
"github.com/containers/libpod/cmd/podman/cliconfig"
|
"github.com/containers/libpod/cmd/podman/cliconfig"
|
||||||
"github.com/containers/libpod/cmd/podman/imagefilters"
|
|
||||||
"github.com/containers/libpod/libpod/image"
|
"github.com/containers/libpod/libpod/image"
|
||||||
"github.com/containers/libpod/pkg/adapter"
|
"github.com/containers/libpod/pkg/adapter"
|
||||||
"github.com/docker/go-units"
|
"github.com/docker/go-units"
|
||||||
|
@ -138,10 +136,10 @@ func init() {
|
||||||
|
|
||||||
func imagesCmd(c *cliconfig.ImagesValues) error {
|
func imagesCmd(c *cliconfig.ImagesValues) error {
|
||||||
var (
|
var (
|
||||||
filterFuncs []imagefilters.ResultFilter
|
image string
|
||||||
image string
|
|
||||||
)
|
)
|
||||||
|
|
||||||
|
ctx := getContext()
|
||||||
runtime, err := adapter.GetRuntime(getContext(), &c.PodmanCommand)
|
runtime, err := adapter.GetRuntime(getContext(), &c.PodmanCommand)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.Wrapf(err, "Could not get runtime")
|
return errors.Wrapf(err, "Could not get runtime")
|
||||||
|
@ -156,15 +154,9 @@ func imagesCmd(c *cliconfig.ImagesValues) error {
|
||||||
if len(c.Filter) > 0 && image != "" {
|
if len(c.Filter) > 0 && image != "" {
|
||||||
return errors.New("can not specify an image and a filter")
|
return errors.New("can not specify an image and a filter")
|
||||||
}
|
}
|
||||||
ctx := getContext()
|
filters := c.Filter
|
||||||
|
if len(filters) < 1 {
|
||||||
if len(c.Filter) > 0 {
|
filters = append(filters, fmt.Sprintf("reference=%s", image))
|
||||||
filterFuncs, err = CreateFilterFuncs(ctx, runtime, c.Filter, nil)
|
|
||||||
} else {
|
|
||||||
filterFuncs, err = CreateFilterFuncs(ctx, runtime, []string{fmt.Sprintf("reference=%s", image)}, nil)
|
|
||||||
}
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
opts := imagesOptions{
|
opts := imagesOptions{
|
||||||
|
@ -179,26 +171,17 @@ func imagesCmd(c *cliconfig.ImagesValues) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
opts.outputformat = opts.setOutputFormat()
|
opts.outputformat = opts.setOutputFormat()
|
||||||
images, err := runtime.GetImages()
|
filteredImages, err := runtime.GetFilteredImages(filters, false)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.Wrapf(err, "unable to get images")
|
return errors.Wrapf(err, "unable to get images")
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, image := range images {
|
for _, image := range filteredImages {
|
||||||
if image.IsReadOnly() {
|
if image.IsReadOnly() {
|
||||||
opts.outputformat += "{{.ReadOnly}}\t"
|
opts.outputformat += "{{.ReadOnly}}\t"
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var filteredImages []*adapter.ContainerImage
|
|
||||||
//filter the images
|
|
||||||
if len(c.Filter) > 0 || len(c.InputArgs) == 1 {
|
|
||||||
filteredImages = imagefilters.FilterImages(images, filterFuncs)
|
|
||||||
} else {
|
|
||||||
filteredImages = images
|
|
||||||
}
|
|
||||||
|
|
||||||
return generateImagesOutput(ctx, filteredImages, opts)
|
return generateImagesOutput(ctx, filteredImages, opts)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -392,53 +375,3 @@ func GenImageOutputMap() map[string]string {
|
||||||
}
|
}
|
||||||
return values
|
return values
|
||||||
}
|
}
|
||||||
|
|
||||||
// CreateFilterFuncs returns an array of filter functions based on the user inputs
|
|
||||||
// and is later used to filter images for output
|
|
||||||
func CreateFilterFuncs(ctx context.Context, r *adapter.LocalRuntime, filters []string, img *adapter.ContainerImage) ([]imagefilters.ResultFilter, error) {
|
|
||||||
var filterFuncs []imagefilters.ResultFilter
|
|
||||||
for _, filter := range filters {
|
|
||||||
splitFilter := strings.Split(filter, "=")
|
|
||||||
if len(splitFilter) < 2 {
|
|
||||||
return nil, errors.Errorf("invalid filter syntax %s", filter)
|
|
||||||
}
|
|
||||||
switch splitFilter[0] {
|
|
||||||
case "before":
|
|
||||||
before, err := r.NewImageFromLocal(splitFilter[1])
|
|
||||||
if err != nil {
|
|
||||||
return nil, errors.Wrapf(err, "unable to find image %s in local stores", splitFilter[1])
|
|
||||||
}
|
|
||||||
filterFuncs = append(filterFuncs, imagefilters.CreatedBeforeFilter(before.Created()))
|
|
||||||
case "after":
|
|
||||||
after, err := r.NewImageFromLocal(splitFilter[1])
|
|
||||||
if err != nil {
|
|
||||||
return nil, errors.Wrapf(err, "unable to find image %s in local stores", splitFilter[1])
|
|
||||||
}
|
|
||||||
filterFuncs = append(filterFuncs, imagefilters.CreatedAfterFilter(after.Created()))
|
|
||||||
case "readonly":
|
|
||||||
readonly, err := strconv.ParseBool(splitFilter[1])
|
|
||||||
if err != nil {
|
|
||||||
return nil, errors.Wrapf(err, "invalid filter readonly=%s", splitFilter[1])
|
|
||||||
}
|
|
||||||
filterFuncs = append(filterFuncs, imagefilters.ReadOnlyFilter(readonly))
|
|
||||||
case "dangling":
|
|
||||||
danglingImages, err := strconv.ParseBool(splitFilter[1])
|
|
||||||
if err != nil {
|
|
||||||
return nil, errors.Wrapf(err, "invalid filter dangling=%s", splitFilter[1])
|
|
||||||
}
|
|
||||||
filterFuncs = append(filterFuncs, imagefilters.DanglingFilter(danglingImages))
|
|
||||||
case "label":
|
|
||||||
labelFilter := strings.Join(splitFilter[1:], "=")
|
|
||||||
filterFuncs = append(filterFuncs, imagefilters.LabelFilter(ctx, labelFilter))
|
|
||||||
case "reference":
|
|
||||||
referenceFilter := strings.Join(splitFilter[1:], "=")
|
|
||||||
filterFuncs = append(filterFuncs, imagefilters.ReferenceFilter(ctx, referenceFilter))
|
|
||||||
default:
|
|
||||||
return nil, errors.Errorf("invalid filter %s ", splitFilter[0])
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if img != nil {
|
|
||||||
filterFuncs = append(filterFuncs, imagefilters.OutputImageFilter(img))
|
|
||||||
}
|
|
||||||
return filterFuncs, nil
|
|
||||||
}
|
|
||||||
|
|
|
@ -784,6 +784,11 @@ method DeleteStoppedContainers() -> (containers: []string)
|
||||||
# See also [InspectImage](#InspectImage).
|
# See also [InspectImage](#InspectImage).
|
||||||
method ListImages() -> (images: []Image)
|
method ListImages() -> (images: []Image)
|
||||||
|
|
||||||
|
# ListImagesWithFilters returns information about the images that are currently in storage
|
||||||
|
# after one or more filters has been applied.
|
||||||
|
# See also [InspectImage](#InspectImage).
|
||||||
|
method ListImagesWithFilters(filters: []string) -> (images: []Image)
|
||||||
|
|
||||||
# GetImage returns information about a single image in storage.
|
# GetImage returns information about a single image in storage.
|
||||||
# If the image caGetImage returns be found, [ImageNotFound](#ImageNotFound) will be returned.
|
# If the image caGetImage returns be found, [ImageNotFound](#ImageNotFound) will be returned.
|
||||||
method GetImage(id: string) -> (image: Image)
|
method GetImage(id: string) -> (image: Image)
|
||||||
|
|
|
@ -1,29 +1,30 @@
|
||||||
package imagefilters
|
package image
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"github.com/pkg/errors"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/containers/libpod/pkg/adapter"
|
|
||||||
"github.com/containers/libpod/pkg/inspect"
|
"github.com/containers/libpod/pkg/inspect"
|
||||||
"github.com/sirupsen/logrus"
|
"github.com/sirupsen/logrus"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ResultFilter is a mock function for image filtering
|
// ResultFilter is a mock function for image filtering
|
||||||
type ResultFilter func(*adapter.ContainerImage) bool
|
type ResultFilter func(*Image) bool
|
||||||
|
|
||||||
// Filter is a function to determine whether an image is included in
|
// Filter is a function to determine whether an image is included in
|
||||||
// command output. Images to be outputted are tested using the function. A true
|
// command output. Images to be outputted are tested using the function. A true
|
||||||
// return will include the image, a false return will exclude it.
|
// return will include the image, a false return will exclude it.
|
||||||
type Filter func(*adapter.ContainerImage, *inspect.ImageData) bool
|
type Filter func(*Image, *inspect.ImageData) bool
|
||||||
|
|
||||||
// CreatedBeforeFilter allows you to filter on images created before
|
// CreatedBeforeFilter allows you to filter on images created before
|
||||||
// the given time.Time
|
// the given time.Time
|
||||||
func CreatedBeforeFilter(createTime time.Time) ResultFilter {
|
func CreatedBeforeFilter(createTime time.Time) ResultFilter {
|
||||||
return func(i *adapter.ContainerImage) bool {
|
return func(i *Image) bool {
|
||||||
return i.Created().Before(createTime)
|
return i.Created().Before(createTime)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -31,14 +32,14 @@ func CreatedBeforeFilter(createTime time.Time) ResultFilter {
|
||||||
// CreatedAfterFilter allows you to filter on images created after
|
// CreatedAfterFilter allows you to filter on images created after
|
||||||
// the given time.Time
|
// the given time.Time
|
||||||
func CreatedAfterFilter(createTime time.Time) ResultFilter {
|
func CreatedAfterFilter(createTime time.Time) ResultFilter {
|
||||||
return func(i *adapter.ContainerImage) bool {
|
return func(i *Image) bool {
|
||||||
return i.Created().After(createTime)
|
return i.Created().After(createTime)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// DanglingFilter allows you to filter images for dangling images
|
// DanglingFilter allows you to filter images for dangling images
|
||||||
func DanglingFilter(danglingImages bool) ResultFilter {
|
func DanglingFilter(danglingImages bool) ResultFilter {
|
||||||
return func(i *adapter.ContainerImage) bool {
|
return func(i *Image) bool {
|
||||||
if danglingImages {
|
if danglingImages {
|
||||||
return i.Dangling()
|
return i.Dangling()
|
||||||
}
|
}
|
||||||
|
@ -48,7 +49,7 @@ func DanglingFilter(danglingImages bool) ResultFilter {
|
||||||
|
|
||||||
// ReadOnlyFilter allows you to filter images based on read/only and read/write
|
// ReadOnlyFilter allows you to filter images based on read/only and read/write
|
||||||
func ReadOnlyFilter(readOnly bool) ResultFilter {
|
func ReadOnlyFilter(readOnly bool) ResultFilter {
|
||||||
return func(i *adapter.ContainerImage) bool {
|
return func(i *Image) bool {
|
||||||
if readOnly {
|
if readOnly {
|
||||||
return i.IsReadOnly()
|
return i.IsReadOnly()
|
||||||
}
|
}
|
||||||
|
@ -59,7 +60,7 @@ func ReadOnlyFilter(readOnly bool) ResultFilter {
|
||||||
// LabelFilter allows you to filter by images labels key and/or value
|
// LabelFilter allows you to filter by images labels key and/or value
|
||||||
func LabelFilter(ctx context.Context, labelfilter string) ResultFilter {
|
func LabelFilter(ctx context.Context, labelfilter string) ResultFilter {
|
||||||
// We need to handle both label=key and label=key=value
|
// We need to handle both label=key and label=key=value
|
||||||
return func(i *adapter.ContainerImage) bool {
|
return func(i *Image) bool {
|
||||||
var value string
|
var value string
|
||||||
splitFilter := strings.Split(labelfilter, "=")
|
splitFilter := strings.Split(labelfilter, "=")
|
||||||
key := splitFilter[0]
|
key := splitFilter[0]
|
||||||
|
@ -83,7 +84,10 @@ func LabelFilter(ctx context.Context, labelfilter string) ResultFilter {
|
||||||
func ReferenceFilter(ctx context.Context, referenceFilter string) ResultFilter {
|
func ReferenceFilter(ctx context.Context, referenceFilter string) ResultFilter {
|
||||||
filter := fmt.Sprintf("*%s*", referenceFilter)
|
filter := fmt.Sprintf("*%s*", referenceFilter)
|
||||||
filter = strings.Replace(filter, "/", "|", -1)
|
filter = strings.Replace(filter, "/", "|", -1)
|
||||||
return func(i *adapter.ContainerImage) bool {
|
return func(i *Image) bool {
|
||||||
|
if len(referenceFilter) < 1 {
|
||||||
|
return true
|
||||||
|
}
|
||||||
for _, name := range i.Names() {
|
for _, name := range i.Names() {
|
||||||
newName := strings.Replace(name, "/", "|", -1)
|
newName := strings.Replace(name, "/", "|", -1)
|
||||||
match, err := filepath.Match(filter, newName)
|
match, err := filepath.Match(filter, newName)
|
||||||
|
@ -99,15 +103,15 @@ func ReferenceFilter(ctx context.Context, referenceFilter string) ResultFilter {
|
||||||
}
|
}
|
||||||
|
|
||||||
// OutputImageFilter allows you to filter by an a specific image name
|
// OutputImageFilter allows you to filter by an a specific image name
|
||||||
func OutputImageFilter(userImage *adapter.ContainerImage) ResultFilter {
|
func OutputImageFilter(userImage *Image) ResultFilter {
|
||||||
return func(i *adapter.ContainerImage) bool {
|
return func(i *Image) bool {
|
||||||
return userImage.ID() == i.ID()
|
return userImage.ID() == i.ID()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// FilterImages filters images using a set of predefined filter funcs
|
// FilterImages filters images using a set of predefined filter funcs
|
||||||
func FilterImages(images []*adapter.ContainerImage, filters []ResultFilter) []*adapter.ContainerImage {
|
func FilterImages(images []*Image, filters []ResultFilter) []*Image {
|
||||||
var filteredImages []*adapter.ContainerImage
|
var filteredImages []*Image
|
||||||
for _, image := range images {
|
for _, image := range images {
|
||||||
include := true
|
include := true
|
||||||
for _, filter := range filters {
|
for _, filter := range filters {
|
||||||
|
@ -119,3 +123,54 @@ func FilterImages(images []*adapter.ContainerImage, filters []ResultFilter) []*a
|
||||||
}
|
}
|
||||||
return filteredImages
|
return filteredImages
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// createFilterFuncs returns an array of filter functions based on the user inputs
|
||||||
|
// and is later used to filter images for output
|
||||||
|
func (ir *Runtime) createFilterFuncs(filters []string, img *Image) ([]ResultFilter, error) {
|
||||||
|
var filterFuncs []ResultFilter
|
||||||
|
ctx := context.Background()
|
||||||
|
for _, filter := range filters {
|
||||||
|
splitFilter := strings.Split(filter, "=")
|
||||||
|
if len(splitFilter) < 2 {
|
||||||
|
return nil, errors.Errorf("invalid filter syntax %s", filter)
|
||||||
|
}
|
||||||
|
switch splitFilter[0] {
|
||||||
|
case "before":
|
||||||
|
before, err := ir.NewFromLocal(splitFilter[1])
|
||||||
|
if err != nil {
|
||||||
|
return nil, errors.Wrapf(err, "unable to find image %s in local stores", splitFilter[1])
|
||||||
|
}
|
||||||
|
filterFuncs = append(filterFuncs, CreatedBeforeFilter(before.Created()))
|
||||||
|
case "after":
|
||||||
|
after, err := ir.NewFromLocal(splitFilter[1])
|
||||||
|
if err != nil {
|
||||||
|
return nil, errors.Wrapf(err, "unable to find image %s in local stores", splitFilter[1])
|
||||||
|
}
|
||||||
|
filterFuncs = append(filterFuncs, CreatedAfterFilter(after.Created()))
|
||||||
|
case "readonly":
|
||||||
|
readonly, err := strconv.ParseBool(splitFilter[1])
|
||||||
|
if err != nil {
|
||||||
|
return nil, errors.Wrapf(err, "invalid filter readonly=%s", splitFilter[1])
|
||||||
|
}
|
||||||
|
filterFuncs = append(filterFuncs, ReadOnlyFilter(readonly))
|
||||||
|
case "dangling":
|
||||||
|
danglingImages, err := strconv.ParseBool(splitFilter[1])
|
||||||
|
if err != nil {
|
||||||
|
return nil, errors.Wrapf(err, "invalid filter dangling=%s", splitFilter[1])
|
||||||
|
}
|
||||||
|
filterFuncs = append(filterFuncs, DanglingFilter(danglingImages))
|
||||||
|
case "label":
|
||||||
|
labelFilter := strings.Join(splitFilter[1:], "=")
|
||||||
|
filterFuncs = append(filterFuncs, LabelFilter(ctx, labelFilter))
|
||||||
|
case "reference":
|
||||||
|
referenceFilter := strings.Join(splitFilter[1:], "=")
|
||||||
|
filterFuncs = append(filterFuncs, ReferenceFilter(ctx, referenceFilter))
|
||||||
|
default:
|
||||||
|
return nil, errors.Errorf("invalid filter %s ", splitFilter[0])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if img != nil {
|
||||||
|
filterFuncs = append(filterFuncs, OutputImageFilter(img))
|
||||||
|
}
|
||||||
|
return filterFuncs, nil
|
||||||
|
}
|
|
@ -216,6 +216,19 @@ func (ir *Runtime) Shutdown(force bool) error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetImagesWithFilters gets images with a series of filters applied
|
||||||
|
func (ir *Runtime) GetImagesWithFilters(filters []string) ([]*Image, error) {
|
||||||
|
filterFuncs, err := ir.createFilterFuncs(filters, nil)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
images, err := ir.GetImages()
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return FilterImages(images, filterFuncs), nil
|
||||||
|
}
|
||||||
|
|
||||||
func (i *Image) reloadImage() error {
|
func (i *Image) reloadImage() error {
|
||||||
newImage, err := i.imageruntime.getImage(i.ID())
|
newImage, err := i.imageruntime.getImage(i.ID())
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
|
@ -84,6 +84,15 @@ func getRuntime(runtime *libpod.Runtime) (*LocalRuntime, error) {
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetFilterImages returns a slice of images in containerimages that are "filtered"
|
||||||
|
func (r *LocalRuntime) GetFilteredImages(filters []string, rwOnly bool) ([]*ContainerImage, error) {
|
||||||
|
images, err := r.ImageRuntime().GetImagesWithFilters(filters)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return r.ImagestoContainerImages(images, rwOnly)
|
||||||
|
}
|
||||||
|
|
||||||
// GetImages returns a slice of images in containerimages
|
// GetImages returns a slice of images in containerimages
|
||||||
func (r *LocalRuntime) GetImages() ([]*ContainerImage, error) {
|
func (r *LocalRuntime) GetImages() ([]*ContainerImage, error) {
|
||||||
return r.getImages(false)
|
return r.getImages(false)
|
||||||
|
@ -95,11 +104,15 @@ func (r *LocalRuntime) GetRWImages() ([]*ContainerImage, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *LocalRuntime) getImages(rwOnly bool) ([]*ContainerImage, error) {
|
func (r *LocalRuntime) getImages(rwOnly bool) ([]*ContainerImage, error) {
|
||||||
var containerImages []*ContainerImage
|
|
||||||
images, err := r.Runtime.ImageRuntime().GetImages()
|
images, err := r.Runtime.ImageRuntime().GetImages()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
return r.ImagestoContainerImages(images, rwOnly)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *LocalRuntime) ImagestoContainerImages(images []*image.Image, rwOnly bool) ([]*ContainerImage, error) {
|
||||||
|
var containerImages []*ContainerImage
|
||||||
for _, i := range images {
|
for _, i := range images {
|
||||||
if rwOnly && i.IsReadOnly() {
|
if rwOnly && i.IsReadOnly() {
|
||||||
continue
|
continue
|
||||||
|
|
|
@ -200,6 +200,28 @@ func (r *LocalRuntime) GetRWImages() ([]*ContainerImage, error) {
|
||||||
return r.getImages(true)
|
return r.getImages(true)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (r *LocalRuntime) GetFilteredImages(filters []string, rwOnly bool) ([]*ContainerImage, error) {
|
||||||
|
var newImages []*ContainerImage
|
||||||
|
images, err := iopodman.ListImagesWithFilters().Call(r.Conn, filters)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
for _, i := range images {
|
||||||
|
if rwOnly && i.ReadOnly {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
name := i.Id
|
||||||
|
if len(i.RepoTags) > 1 {
|
||||||
|
name = i.RepoTags[0]
|
||||||
|
}
|
||||||
|
newImage, err := imageInListToContainerImage(i, name, r)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
newImages = append(newImages, newImage)
|
||||||
|
}
|
||||||
|
return newImages, nil
|
||||||
|
}
|
||||||
func (r *LocalRuntime) getImages(rwOnly bool) ([]*ContainerImage, error) {
|
func (r *LocalRuntime) getImages(rwOnly bool) ([]*ContainerImage, error) {
|
||||||
var newImages []*ContainerImage
|
var newImages []*ContainerImage
|
||||||
images, err := iopodman.ListImages().Call(r.Conn)
|
images, err := iopodman.ListImages().Call(r.Conn)
|
||||||
|
|
|
@ -35,26 +35,34 @@ import (
|
||||||
"github.com/sirupsen/logrus"
|
"github.com/sirupsen/logrus"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ListImages lists all the images in the store
|
// ListImagesWithFilters returns a list of images that have been filtered
|
||||||
// It requires no inputs.
|
func (i *LibpodAPI) ListImagesWithFilters(call iopodman.VarlinkCall, filters []string) error {
|
||||||
func (i *LibpodAPI) ListImages(call iopodman.VarlinkCall) error {
|
images, err := i.Runtime.ImageRuntime().GetImagesWithFilters(filters)
|
||||||
images, err := i.Runtime.ImageRuntime().GetImages()
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return call.ReplyErrorOccurred(fmt.Sprintf("unable to get list of images %q", err))
|
return call.ReplyErrorOccurred(fmt.Sprintf("unable to get list of images %q", err))
|
||||||
}
|
}
|
||||||
|
imageList, err := imagesToImageList(images)
|
||||||
|
if err != nil {
|
||||||
|
return call.ReplyErrorOccurred(fmt.Sprintf("unable to parse response", err))
|
||||||
|
}
|
||||||
|
return call.ReplyListImagesWithFilters(imageList)
|
||||||
|
}
|
||||||
|
|
||||||
|
// imagesToImageList converts a slice of Images to an imagelist for varlink responses
|
||||||
|
func imagesToImageList(images []*image.Image) ([]iopodman.Image, error) {
|
||||||
var imageList []iopodman.Image
|
var imageList []iopodman.Image
|
||||||
for _, image := range images {
|
for _, image := range images {
|
||||||
labels, _ := image.Labels(getContext())
|
labels, _ := image.Labels(getContext())
|
||||||
containers, _ := image.Containers()
|
containers, _ := image.Containers()
|
||||||
repoDigests, err := image.RepoDigests()
|
repoDigests, err := image.RepoDigests()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
size, _ := image.Size(getContext())
|
size, _ := image.Size(getContext())
|
||||||
isParent, err := image.IsParent(context.TODO())
|
isParent, err := image.IsParent(context.TODO())
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return call.ReplyErrorOccurred(err.Error())
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
i := iopodman.Image{
|
i := iopodman.Image{
|
||||||
|
@ -74,6 +82,20 @@ func (i *LibpodAPI) ListImages(call iopodman.VarlinkCall) error {
|
||||||
}
|
}
|
||||||
imageList = append(imageList, i)
|
imageList = append(imageList, i)
|
||||||
}
|
}
|
||||||
|
return imageList, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// ListImages lists all the images in the store
|
||||||
|
// It requires no inputs.
|
||||||
|
func (i *LibpodAPI) ListImages(call iopodman.VarlinkCall) error {
|
||||||
|
images, err := i.Runtime.ImageRuntime().GetImages()
|
||||||
|
if err != nil {
|
||||||
|
return call.ReplyErrorOccurred(fmt.Sprintf("unable to get list of images %q", err))
|
||||||
|
}
|
||||||
|
imageList, err := imagesToImageList(images)
|
||||||
|
if err != nil {
|
||||||
|
return call.ReplyErrorOccurred(fmt.Sprintf("unable to parse response", err))
|
||||||
|
}
|
||||||
return call.ReplyListImages(imageList)
|
return call.ReplyListImages(imageList)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue