mirror of
https://github.com/containers/podman.git
synced 2025-08-06 19:44:14 +08:00
Add pod, volume, network to inspect package
podman inspect only had the capabilities to inspect containers and images. if a user wanted to inspect a pod, volume, or network, they would have to use `podman network inspect`, `podman pod inspect` etc. Docker's cli allowed users to inspect both volumes and networks using regular inspect, so this commit gives the user the functionality If the inspect type is not specified using --type, the order of inspection is: containers images volumes networks pods meaning if container that has the same name as an image, podman inspect would return the container inspect. To avoid duplicate code, podman network inspect and podman volume inspect now use the inspect package as well. Podman pod inspect does not because podman pod inspect returns a single json object while podman inspect can return multiple) Signed-off-by: Ashley Cui <acui@redhat.com>
This commit is contained in:
@ -12,6 +12,7 @@ import (
|
|||||||
"github.com/containers/common/pkg/report"
|
"github.com/containers/common/pkg/report"
|
||||||
"github.com/containers/podman/v2/cmd/podman/registry"
|
"github.com/containers/podman/v2/cmd/podman/registry"
|
||||||
"github.com/containers/podman/v2/cmd/podman/validate"
|
"github.com/containers/podman/v2/cmd/podman/validate"
|
||||||
|
"github.com/containers/podman/v2/libpod/define"
|
||||||
"github.com/containers/podman/v2/pkg/domain/entities"
|
"github.com/containers/podman/v2/pkg/domain/entities"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
"github.com/sirupsen/logrus"
|
"github.com/sirupsen/logrus"
|
||||||
@ -19,12 +20,18 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
// ImageType is the image type.
|
|
||||||
ImageType = "image"
|
|
||||||
// ContainerType is the container type.
|
|
||||||
ContainerType = "container"
|
|
||||||
// AllType can be of type ImageType or ContainerType.
|
// AllType can be of type ImageType or ContainerType.
|
||||||
AllType = "all"
|
AllType = "all"
|
||||||
|
// ContainerType is the container type.
|
||||||
|
ContainerType = "container"
|
||||||
|
// ImageType is the image type.
|
||||||
|
ImageType = "image"
|
||||||
|
//NetworkType is the network type
|
||||||
|
NetworkType = "network"
|
||||||
|
//PodType is the pod type.
|
||||||
|
PodType = "pod"
|
||||||
|
//VolumeType is the volume type
|
||||||
|
VolumeType = "volume"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Pull in configured json library
|
// Pull in configured json library
|
||||||
@ -58,15 +65,16 @@ type inspector struct {
|
|||||||
containerEngine entities.ContainerEngine
|
containerEngine entities.ContainerEngine
|
||||||
imageEngine entities.ImageEngine
|
imageEngine entities.ImageEngine
|
||||||
options entities.InspectOptions
|
options entities.InspectOptions
|
||||||
|
podOptions entities.PodInspectOptions
|
||||||
}
|
}
|
||||||
|
|
||||||
// newInspector creates a new inspector based on the specified options.
|
// newInspector creates a new inspector based on the specified options.
|
||||||
func newInspector(options entities.InspectOptions) (*inspector, error) {
|
func newInspector(options entities.InspectOptions) (*inspector, error) {
|
||||||
switch options.Type {
|
switch options.Type {
|
||||||
case ImageType, ContainerType, AllType:
|
case ImageType, ContainerType, AllType, PodType, NetworkType, VolumeType:
|
||||||
// Valid types.
|
// Valid types.
|
||||||
default:
|
default:
|
||||||
return nil, errors.Errorf("invalid type %q: must be %q, %q or %q", options.Type, ImageType, ContainerType, AllType)
|
return nil, errors.Errorf("invalid type %q: must be %q, %q, %q, %q, %q, or %q", options.Type, ImageType, ContainerType, PodType, NetworkType, VolumeType, AllType)
|
||||||
}
|
}
|
||||||
if options.Type == ImageType {
|
if options.Type == ImageType {
|
||||||
if options.Latest {
|
if options.Latest {
|
||||||
@ -76,10 +84,18 @@ func newInspector(options entities.InspectOptions) (*inspector, error) {
|
|||||||
return nil, errors.Errorf("size is not supported for type %q", ImageType)
|
return nil, errors.Errorf("size is not supported for type %q", ImageType)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if options.Type == PodType && options.Size {
|
||||||
|
return nil, errors.Errorf("size is not supported for type %q", PodType)
|
||||||
|
}
|
||||||
|
podOpts := entities.PodInspectOptions{
|
||||||
|
Latest: options.Latest,
|
||||||
|
Format: options.Format,
|
||||||
|
}
|
||||||
return &inspector{
|
return &inspector{
|
||||||
containerEngine: registry.ContainerEngine(),
|
containerEngine: registry.ContainerEngine(),
|
||||||
imageEngine: registry.ImageEngine(),
|
imageEngine: registry.ImageEngine(),
|
||||||
options: options,
|
options: options,
|
||||||
|
podOptions: podOpts,
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -91,17 +107,19 @@ func (i *inspector) inspect(namesOrIDs []string) error {
|
|||||||
ctx := context.Background()
|
ctx := context.Background()
|
||||||
|
|
||||||
if len(namesOrIDs) == 0 {
|
if len(namesOrIDs) == 0 {
|
||||||
if !i.options.Latest {
|
if !i.options.Latest && !i.options.All {
|
||||||
return errors.New("no containers or images specified")
|
return errors.New("no names or ids specified")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpType := i.options.Type
|
tmpType := i.options.Type
|
||||||
if i.options.Latest {
|
if i.options.Latest {
|
||||||
if len(namesOrIDs) > 0 {
|
if len(namesOrIDs) > 0 {
|
||||||
return errors.New("--latest and containers cannot be used together")
|
return errors.New("--latest and arguments cannot be used together")
|
||||||
|
}
|
||||||
|
if i.options.Type == AllType {
|
||||||
|
tmpType = ContainerType // -l works with --type=all, defaults to containertype
|
||||||
}
|
}
|
||||||
tmpType = ContainerType // -l works with --type=all
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Inspect - note that AllType requires us to expensively query one-by-one.
|
// Inspect - note that AllType requires us to expensively query one-by-one.
|
||||||
@ -131,10 +149,57 @@ func (i *inspector) inspect(namesOrIDs []string) error {
|
|||||||
for i := range ctrData {
|
for i := range ctrData {
|
||||||
data = append(data, ctrData[i])
|
data = append(data, ctrData[i])
|
||||||
}
|
}
|
||||||
default:
|
case PodType:
|
||||||
return errors.Errorf("invalid type %q: must be %q, %q or %q", i.options.Type, ImageType, ContainerType, AllType)
|
for _, pod := range namesOrIDs {
|
||||||
|
i.podOptions.NameOrID = pod
|
||||||
|
podData, err := i.containerEngine.PodInspect(ctx, i.podOptions)
|
||||||
|
if err != nil {
|
||||||
|
cause := errors.Cause(err)
|
||||||
|
if !strings.Contains(cause.Error(), define.ErrNoSuchPod.Error()) {
|
||||||
|
errs = []error{err}
|
||||||
|
} else {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
errs = nil
|
||||||
|
data = append(data, podData)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if i.podOptions.Latest { //latest means there are no names in the namesOrID array
|
||||||
|
podData, err := i.containerEngine.PodInspect(ctx, i.podOptions)
|
||||||
|
if err != nil {
|
||||||
|
cause := errors.Cause(err)
|
||||||
|
if !strings.Contains(cause.Error(), define.ErrNoSuchPod.Error()) {
|
||||||
|
errs = []error{err}
|
||||||
|
} else {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
errs = nil
|
||||||
|
data = append(data, podData)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case NetworkType:
|
||||||
|
networkData, allErrs, err := registry.ContainerEngine().NetworkInspect(ctx, namesOrIDs, i.options)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
errs = allErrs
|
||||||
|
for i := range networkData {
|
||||||
|
data = append(data, networkData[i])
|
||||||
|
}
|
||||||
|
case VolumeType:
|
||||||
|
volumeData, allErrs, err := i.containerEngine.VolumeInspect(ctx, namesOrIDs, i.options)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
errs = allErrs
|
||||||
|
for i := range volumeData {
|
||||||
|
data = append(data, volumeData[i])
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
return errors.Errorf("invalid type %q: must be %q, %q, %q, %q, %q, or %q", i.options.Type, ImageType, ContainerType, PodType, NetworkType, VolumeType, AllType)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Always print an empty array
|
// Always print an empty array
|
||||||
if data == nil {
|
if data == nil {
|
||||||
data = []interface{}{}
|
data = []interface{}{}
|
||||||
@ -195,11 +260,41 @@ func (i *inspector) inspectAll(ctx context.Context, namesOrIDs []string) ([]inte
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
|
if len(errs) == 0 {
|
||||||
|
data = append(data, imgData[0])
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
volumeData, errs, err := i.containerEngine.VolumeInspect(ctx, []string{name}, i.options)
|
||||||
|
if err != nil {
|
||||||
|
return nil, nil, err
|
||||||
|
}
|
||||||
|
if len(errs) == 0 {
|
||||||
|
data = append(data, volumeData[0])
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
networkData, errs, err := registry.ContainerEngine().NetworkInspect(ctx, namesOrIDs, i.options)
|
||||||
|
if err != nil {
|
||||||
|
return nil, nil, err
|
||||||
|
}
|
||||||
|
if len(errs) == 0 {
|
||||||
|
data = append(data, networkData[0])
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
i.podOptions.NameOrID = name
|
||||||
|
podData, err := i.containerEngine.PodInspect(ctx, i.podOptions)
|
||||||
|
if err != nil {
|
||||||
|
cause := errors.Cause(err)
|
||||||
|
if !strings.Contains(cause.Error(), define.ErrNoSuchPod.Error()) {
|
||||||
|
return nil, nil, err
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
data = append(data, podData)
|
||||||
|
continue
|
||||||
|
}
|
||||||
if len(errs) > 0 {
|
if len(errs) > 0 {
|
||||||
allErrs = append(allErrs, errors.Errorf("no such object: %q", name))
|
allErrs = append(allErrs, errors.Errorf("no such object: %q", name))
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
data = append(data, imgData[0])
|
|
||||||
}
|
}
|
||||||
return data, allErrs, nil
|
return data, allErrs, nil
|
||||||
}
|
}
|
||||||
|
@ -1,13 +1,7 @@
|
|||||||
package network
|
package network
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"encoding/json"
|
"github.com/containers/podman/v2/cmd/podman/inspect"
|
||||||
"fmt"
|
|
||||||
"os"
|
|
||||||
"text/tabwriter"
|
|
||||||
"text/template"
|
|
||||||
|
|
||||||
"github.com/containers/common/pkg/report"
|
|
||||||
"github.com/containers/podman/v2/cmd/podman/registry"
|
"github.com/containers/podman/v2/cmd/podman/registry"
|
||||||
"github.com/containers/podman/v2/pkg/domain/entities"
|
"github.com/containers/podman/v2/pkg/domain/entities"
|
||||||
"github.com/spf13/cobra"
|
"github.com/spf13/cobra"
|
||||||
@ -23,10 +17,7 @@ var (
|
|||||||
Example: `podman network inspect podman`,
|
Example: `podman network inspect podman`,
|
||||||
Args: cobra.MinimumNArgs(1),
|
Args: cobra.MinimumNArgs(1),
|
||||||
}
|
}
|
||||||
)
|
inspectOpts *entities.InspectOptions
|
||||||
|
|
||||||
var (
|
|
||||||
networkInspectOptions entities.NetworkInspectOptions
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
@ -35,36 +26,13 @@ func init() {
|
|||||||
Command: networkinspectCommand,
|
Command: networkinspectCommand,
|
||||||
Parent: networkCmd,
|
Parent: networkCmd,
|
||||||
})
|
})
|
||||||
|
inspectOpts = new(entities.InspectOptions)
|
||||||
flags := networkinspectCommand.Flags()
|
flags := networkinspectCommand.Flags()
|
||||||
flags.StringVarP(&networkInspectOptions.Format, "format", "f", "", "Pretty-print network to JSON or using a Go template")
|
flags.StringVarP(&inspectOpts.Format, "format", "f", "", "Pretty-print network to JSON or using a Go template")
|
||||||
}
|
}
|
||||||
|
|
||||||
func networkInspect(_ *cobra.Command, args []string) error {
|
func networkInspect(_ *cobra.Command, args []string) error {
|
||||||
responses, err := registry.ContainerEngine().NetworkInspect(registry.Context(), args, entities.NetworkInspectOptions{})
|
inspectOpts.Type = inspect.NetworkType
|
||||||
if err != nil {
|
return inspect.Inspect(args, *inspectOpts)
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
switch {
|
|
||||||
case report.IsJSON(networkInspectOptions.Format) || networkInspectOptions.Format == "":
|
|
||||||
b, err := json.MarshalIndent(responses, "", " ")
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
fmt.Println(string(b))
|
|
||||||
default:
|
|
||||||
row := report.NormalizeFormat(networkInspectOptions.Format)
|
|
||||||
// There can be more than 1 in the inspect output.
|
|
||||||
row = "{{range . }}" + row + "{{end}}"
|
|
||||||
tmpl, err := template.New("inspectNetworks").Parse(row)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
w := tabwriter.NewWriter(os.Stdout, 8, 2, 0, ' ', 0)
|
|
||||||
defer w.Flush()
|
|
||||||
|
|
||||||
return tmpl.Execute(w, responses)
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
@ -1,16 +1,11 @@
|
|||||||
package volumes
|
package volumes
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"github.com/containers/podman/v2/cmd/podman/inspect"
|
||||||
"os"
|
|
||||||
"text/template"
|
|
||||||
|
|
||||||
"github.com/containers/common/pkg/report"
|
|
||||||
"github.com/containers/podman/v2/cmd/podman/registry"
|
"github.com/containers/podman/v2/cmd/podman/registry"
|
||||||
"github.com/containers/podman/v2/pkg/domain/entities"
|
"github.com/containers/podman/v2/pkg/domain/entities"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
"github.com/spf13/cobra"
|
"github.com/spf13/cobra"
|
||||||
"golang.org/x/net/context"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
@ -21,7 +16,7 @@ var (
|
|||||||
Use: "inspect [options] VOLUME [VOLUME...]",
|
Use: "inspect [options] VOLUME [VOLUME...]",
|
||||||
Short: "Display detailed information on one or more volumes",
|
Short: "Display detailed information on one or more volumes",
|
||||||
Long: volumeInspectDescription,
|
Long: volumeInspectDescription,
|
||||||
RunE: inspect,
|
RunE: volumeInspect,
|
||||||
Example: `podman volume inspect myvol
|
Example: `podman volume inspect myvol
|
||||||
podman volume inspect --all
|
podman volume inspect --all
|
||||||
podman volume inspect --format "{{.Driver}} {{.Scope}}" myvol`,
|
podman volume inspect --format "{{.Driver}} {{.Scope}}" myvol`,
|
||||||
@ -29,8 +24,7 @@ var (
|
|||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
inspectOpts = entities.VolumeInspectOptions{}
|
inspectOpts *entities.InspectOptions
|
||||||
inspectFormat string
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
@ -39,34 +33,16 @@ func init() {
|
|||||||
Command: inspectCommand,
|
Command: inspectCommand,
|
||||||
Parent: volumeCmd,
|
Parent: volumeCmd,
|
||||||
})
|
})
|
||||||
|
inspectOpts = new(entities.InspectOptions)
|
||||||
flags := inspectCommand.Flags()
|
flags := inspectCommand.Flags()
|
||||||
flags.BoolVarP(&inspectOpts.All, "all", "a", false, "Inspect all volumes")
|
flags.BoolVarP(&inspectOpts.All, "all", "a", false, "Inspect all volumes")
|
||||||
flags.StringVarP(&inspectFormat, "format", "f", "json", "Format volume output using Go template")
|
flags.StringVarP(&inspectOpts.Format, "format", "f", "json", "Format volume output using Go template")
|
||||||
}
|
}
|
||||||
|
|
||||||
func inspect(cmd *cobra.Command, args []string) error {
|
func volumeInspect(cmd *cobra.Command, args []string) error {
|
||||||
if (inspectOpts.All && len(args) > 0) || (!inspectOpts.All && len(args) < 1) {
|
if (inspectOpts.All && len(args) > 0) || (!inspectOpts.All && len(args) < 1) {
|
||||||
return errors.New("provide one or more volume names or use --all")
|
return errors.New("provide one or more volume names or use --all")
|
||||||
}
|
}
|
||||||
responses, err := registry.ContainerEngine().VolumeInspect(context.Background(), args, inspectOpts)
|
inspectOpts.Type = inspect.VolumeType
|
||||||
if err != nil {
|
return inspect.Inspect(args, *inspectOpts)
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
switch {
|
|
||||||
case report.IsJSON(inspectFormat), inspectFormat == "":
|
|
||||||
jsonOut, err := json.MarshalIndent(responses, "", " ")
|
|
||||||
if err != nil {
|
|
||||||
return errors.Wrapf(err, "error marshalling inspect JSON")
|
|
||||||
}
|
|
||||||
fmt.Println(string(jsonOut))
|
|
||||||
default:
|
|
||||||
row := "{{range . }}" + report.NormalizeFormat(inspectFormat) + "{{end}}"
|
|
||||||
tmpl, err := template.New("volumeInspect").Parse(row)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
return tmpl.Execute(os.Stdout, responses)
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
% podman-inspect(1)
|
% podman-inspect(1)
|
||||||
|
|
||||||
## NAME
|
## NAME
|
||||||
podman\-inspect - Display a container or image's configuration
|
podman\-inspect - Display a container, image, volume, network, or pod's configuration
|
||||||
|
|
||||||
## SYNOPSIS
|
## SYNOPSIS
|
||||||
**podman inspect** [*options*] *name* [...]
|
**podman inspect** [*options*] *name* [...]
|
||||||
@ -9,8 +9,9 @@ podman\-inspect - Display a container or image's configuration
|
|||||||
## DESCRIPTION
|
## DESCRIPTION
|
||||||
|
|
||||||
This displays the low-level information on containers and images identified by name or ID. By default, this will render
|
This displays the low-level information on containers and images identified by name or ID. By default, this will render
|
||||||
all results in a JSON array. If the container and image have the same name, this will return container JSON for
|
all results in a JSON array. If the inspect type is all, the order of inspection is: containers, images, volumes, network, pods.
|
||||||
unspecified type. If a format is specified, the given template will be executed for each result.
|
So, if a container has the same name as an image, then the container JSON will be returned, and so on.
|
||||||
|
If a format is specified, the given template will be executed for each result.
|
||||||
|
|
||||||
For more inspection options, see:
|
For more inspection options, see:
|
||||||
|
|
||||||
@ -25,7 +26,7 @@ For more inspection options, see:
|
|||||||
|
|
||||||
**--type**, **-t**=*type*
|
**--type**, **-t**=*type*
|
||||||
|
|
||||||
Return JSON for the specified type. Type can be 'container', 'image' or 'all' (default: all)
|
Return JSON for the specified type. Type can be 'container', 'image', 'volume', 'network', 'pod', or 'all' (default: all)
|
||||||
(Only meaningful when invoked as *podman inspect*)
|
(Only meaningful when invoked as *podman inspect*)
|
||||||
|
|
||||||
**--format**, **-f**=*format*
|
**--format**, **-f**=*format*
|
||||||
@ -38,6 +39,8 @@ The keys of the returned JSON can be used as the values for the --format flag (s
|
|||||||
Instead of providing the container name or ID, use the last created container. If you use methods other than Podman
|
Instead of providing the container name or ID, use the last created container. If you use methods other than Podman
|
||||||
to run containers such as CRI-O, the last started container could be from either of those methods.
|
to run containers such as CRI-O, the last started container could be from either of those methods.
|
||||||
|
|
||||||
|
This option can be used to inspect the latest pod created when used with --type pod
|
||||||
|
|
||||||
The latest option is not supported on the remote client or when invoked as *podman image inspect*.
|
The latest option is not supported on the remote client or when invoked as *podman image inspect*.
|
||||||
|
|
||||||
**--size**, **-s**
|
**--size**, **-s**
|
||||||
@ -148,6 +151,20 @@ podman container inspect --latest --format {{.EffectiveCaps}}
|
|||||||
[CAP_CHOWN CAP_DAC_OVERRIDE CAP_FSETID CAP_FOWNER CAP_MKNOD CAP_NET_RAW CAP_SETGID CAP_SETUID CAP_SETFCAP CAP_SETPCAP CAP_NET_BIND_SERVICE CAP_SYS_CHROOT CAP_KILL CAP_AUDIT_WRITE]
|
[CAP_CHOWN CAP_DAC_OVERRIDE CAP_FSETID CAP_FOWNER CAP_MKNOD CAP_NET_RAW CAP_SETGID CAP_SETUID CAP_SETFCAP CAP_SETPCAP CAP_NET_BIND_SERVICE CAP_SYS_CHROOT CAP_KILL CAP_AUDIT_WRITE]
|
||||||
```
|
```
|
||||||
|
|
||||||
|
```
|
||||||
|
# podman inspect myPod --type pod --format "{{.Name}}"
|
||||||
|
myPod
|
||||||
|
```
|
||||||
|
```
|
||||||
|
# podman inspect myVolume --type volume --format "{{.Name}}"
|
||||||
|
myVolume
|
||||||
|
```
|
||||||
|
|
||||||
|
```
|
||||||
|
# podman inspect nyNetwork --type network --format "{{.name}}"
|
||||||
|
myNetwork
|
||||||
|
```
|
||||||
|
|
||||||
## SEE ALSO
|
## SEE ALSO
|
||||||
podman(1)
|
podman(1)
|
||||||
|
|
||||||
|
@ -220,7 +220,7 @@ the exit codes follow the `chroot` standard, see below:
|
|||||||
| [podman-import(1)](podman-import.1.md) | Import a tarball and save it as a filesystem image. |
|
| [podman-import(1)](podman-import.1.md) | Import a tarball and save it as a filesystem image. |
|
||||||
| [podman-info(1)](podman-info.1.md) | Displays Podman related system information. |
|
| [podman-info(1)](podman-info.1.md) | Displays Podman related system information. |
|
||||||
| [podman-init(1)](podman-init.1.md) | Initialize one or more containers |
|
| [podman-init(1)](podman-init.1.md) | Initialize one or more containers |
|
||||||
| [podman-inspect(1)](podman-inspect.1.md) | Display a container or image's configuration. |
|
| [podman-inspect(1)](podman-inspect.1.md) | Display a container, image, volume, network, or pod's configuration. |
|
||||||
| [podman-kill(1)](podman-kill.1.md) | Kill the main process in one or more containers. |
|
| [podman-kill(1)](podman-kill.1.md) | Kill the main process in one or more containers. |
|
||||||
| [podman-load(1)](podman-load.1.md) | Load an image from a container image archive into container storage. |
|
| [podman-load(1)](podman-load.1.md) | Load an image from a container image archive into container storage. |
|
||||||
| [podman-login(1)](podman-login.1.md) | Login to a container registry. |
|
| [podman-login(1)](podman-login.1.md) | Login to a container registry. |
|
||||||
|
1
go.mod
1
go.mod
@ -63,7 +63,6 @@ require (
|
|||||||
github.com/vishvananda/netlink v1.1.0
|
github.com/vishvananda/netlink v1.1.0
|
||||||
go.etcd.io/bbolt v1.3.5
|
go.etcd.io/bbolt v1.3.5
|
||||||
golang.org/x/crypto v0.0.0-20200709230013-948cd5f35899
|
golang.org/x/crypto v0.0.0-20200709230013-948cd5f35899
|
||||||
golang.org/x/net v0.0.0-20201006153459-a7d1128ccaa0
|
|
||||||
golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d // indirect
|
golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d // indirect
|
||||||
golang.org/x/sync v0.0.0-20200625203802-6e8e738ad208
|
golang.org/x/sync v0.0.0-20200625203802-6e8e738ad208
|
||||||
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f
|
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f
|
||||||
|
@ -113,15 +113,15 @@ func InspectNetwork(w http.ResponseWriter, r *http.Request) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
name := utils.GetName(r)
|
name := utils.GetName(r)
|
||||||
options := entities.NetworkInspectOptions{}
|
options := entities.InspectOptions{}
|
||||||
ic := abi.ContainerEngine{Libpod: runtime}
|
ic := abi.ContainerEngine{Libpod: runtime}
|
||||||
reports, err := ic.NetworkInspect(r.Context(), []string{name}, options)
|
reports, errs, err := ic.NetworkInspect(r.Context(), []string{name}, options)
|
||||||
if err != nil {
|
|
||||||
// If the network cannot be found, we return a 404.
|
// If the network cannot be found, we return a 404.
|
||||||
if errors.Cause(err) == define.ErrNoSuchNetwork {
|
if len(errs) > 0 {
|
||||||
utils.Error(w, "Something went wrong", http.StatusNotFound, err)
|
utils.Error(w, "Something went wrong", http.StatusNotFound, define.ErrNoSuchNetwork)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
if err != nil {
|
||||||
utils.InternalServerError(w, err)
|
utils.InternalServerError(w, err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -51,7 +51,7 @@ type ContainerEngine interface {
|
|||||||
HealthCheckRun(ctx context.Context, nameOrID string, options HealthCheckOptions) (*define.HealthCheckResults, error)
|
HealthCheckRun(ctx context.Context, nameOrID string, options HealthCheckOptions) (*define.HealthCheckResults, error)
|
||||||
Info(ctx context.Context) (*define.Info, error)
|
Info(ctx context.Context) (*define.Info, error)
|
||||||
NetworkCreate(ctx context.Context, name string, options NetworkCreateOptions) (*NetworkCreateReport, error)
|
NetworkCreate(ctx context.Context, name string, options NetworkCreateOptions) (*NetworkCreateReport, error)
|
||||||
NetworkInspect(ctx context.Context, namesOrIds []string, options NetworkInspectOptions) ([]NetworkInspectReport, error)
|
NetworkInspect(ctx context.Context, namesOrIds []string, options InspectOptions) ([]NetworkInspectReport, []error, error)
|
||||||
NetworkList(ctx context.Context, options NetworkListOptions) ([]*NetworkListReport, error)
|
NetworkList(ctx context.Context, options NetworkListOptions) ([]*NetworkListReport, error)
|
||||||
NetworkRm(ctx context.Context, namesOrIds []string, options NetworkRmOptions) ([]*NetworkRmReport, error)
|
NetworkRm(ctx context.Context, namesOrIds []string, options NetworkRmOptions) ([]*NetworkRmReport, error)
|
||||||
PlayKube(ctx context.Context, path string, opts PlayKubeOptions) (*PlayKubeReport, error)
|
PlayKube(ctx context.Context, path string, opts PlayKubeOptions) (*PlayKubeReport, error)
|
||||||
@ -76,7 +76,7 @@ type ContainerEngine interface {
|
|||||||
VarlinkService(ctx context.Context, opts ServiceOptions) error
|
VarlinkService(ctx context.Context, opts ServiceOptions) error
|
||||||
Version(ctx context.Context) (*SystemVersionReport, error)
|
Version(ctx context.Context) (*SystemVersionReport, error)
|
||||||
VolumeCreate(ctx context.Context, opts VolumeCreateOptions) (*IDOrNameResponse, error)
|
VolumeCreate(ctx context.Context, opts VolumeCreateOptions) (*IDOrNameResponse, error)
|
||||||
VolumeInspect(ctx context.Context, namesOrIds []string, opts VolumeInspectOptions) ([]*VolumeInspectReport, error)
|
VolumeInspect(ctx context.Context, namesOrIds []string, opts InspectOptions) ([]*VolumeInspectReport, []error, error)
|
||||||
VolumeList(ctx context.Context, opts VolumeListOptions) ([]*VolumeListReport, error)
|
VolumeList(ctx context.Context, opts VolumeListOptions) ([]*VolumeListReport, error)
|
||||||
VolumePrune(ctx context.Context) ([]*VolumePruneReport, error)
|
VolumePrune(ctx context.Context) ([]*VolumePruneReport, error)
|
||||||
VolumeRm(ctx context.Context, namesOrIds []string, opts VolumeRmOptions) ([]*VolumeRmReport, error)
|
VolumeRm(ctx context.Context, namesOrIds []string, opts VolumeRmOptions) ([]*VolumeRmReport, error)
|
||||||
|
@ -18,11 +18,6 @@ type NetworkListReport struct {
|
|||||||
*libcni.NetworkConfigList
|
*libcni.NetworkConfigList
|
||||||
}
|
}
|
||||||
|
|
||||||
// NetworkInspectOptions describes options for inspect networks
|
|
||||||
type NetworkInspectOptions struct {
|
|
||||||
Format string
|
|
||||||
}
|
|
||||||
|
|
||||||
// NetworkInspectReport describes the results from inspect networks
|
// NetworkInspectReport describes the results from inspect networks
|
||||||
type NetworkInspectReport map[string]interface{}
|
type NetworkInspectReport map[string]interface{}
|
||||||
|
|
||||||
|
@ -56,6 +56,8 @@ type InspectOptions struct {
|
|||||||
Size bool `json:",omitempty"`
|
Size bool `json:",omitempty"`
|
||||||
// Type -- return JSON for specified type.
|
// Type -- return JSON for specified type.
|
||||||
Type string `json:",omitempty"`
|
Type string `json:",omitempty"`
|
||||||
|
// All -- inspect all
|
||||||
|
All bool `json:",omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// All API and CLI diff commands and diff sub-commands use the same options
|
// All API and CLI diff commands and diff sub-commands use the same options
|
||||||
|
@ -105,10 +105,6 @@ type VolumeRmReport struct {
|
|||||||
Id string //nolint
|
Id string //nolint
|
||||||
}
|
}
|
||||||
|
|
||||||
type VolumeInspectOptions struct {
|
|
||||||
All bool
|
|
||||||
}
|
|
||||||
|
|
||||||
type VolumeInspectReport struct {
|
type VolumeInspectReport struct {
|
||||||
*VolumeConfigResponse
|
*VolumeConfigResponse
|
||||||
}
|
}
|
||||||
|
@ -43,21 +43,26 @@ func (ic *ContainerEngine) NetworkList(ctx context.Context, options entities.Net
|
|||||||
return reports, nil
|
return reports, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ic *ContainerEngine) NetworkInspect(ctx context.Context, namesOrIds []string, options entities.NetworkInspectOptions) ([]entities.NetworkInspectReport, error) {
|
func (ic *ContainerEngine) NetworkInspect(ctx context.Context, namesOrIds []string, options entities.InspectOptions) ([]entities.NetworkInspectReport, []error, error) {
|
||||||
config, err := ic.Libpod.GetConfig()
|
config, err := ic.Libpod.GetConfig()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
|
var errs []error
|
||||||
rawCNINetworks := make([]entities.NetworkInspectReport, 0, len(namesOrIds))
|
rawCNINetworks := make([]entities.NetworkInspectReport, 0, len(namesOrIds))
|
||||||
for _, name := range namesOrIds {
|
for _, name := range namesOrIds {
|
||||||
rawList, err := network.InspectNetwork(config, name)
|
rawList, err := network.InspectNetwork(config, name)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
if errors.Cause(err) == define.ErrNoSuchNetwork {
|
||||||
|
errs = append(errs, errors.Errorf("no such network %s", name))
|
||||||
|
continue
|
||||||
|
} else {
|
||||||
|
return nil, nil, errors.Wrapf(err, "error inspecting network %s", name)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
rawCNINetworks = append(rawCNINetworks, rawList)
|
rawCNINetworks = append(rawCNINetworks, rawList)
|
||||||
}
|
}
|
||||||
return rawCNINetworks, nil
|
return rawCNINetworks, errs, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ic *ContainerEngine) NetworkRm(ctx context.Context, namesOrIds []string, options entities.NetworkRmOptions) ([]*entities.NetworkRmReport, error) {
|
func (ic *ContainerEngine) NetworkRm(ctx context.Context, namesOrIds []string, options entities.NetworkRmOptions) ([]*entities.NetworkRmReport, error) {
|
||||||
|
@ -4,6 +4,7 @@ import (
|
|||||||
"context"
|
"context"
|
||||||
|
|
||||||
"github.com/containers/podman/v2/libpod"
|
"github.com/containers/podman/v2/libpod"
|
||||||
|
"github.com/containers/podman/v2/libpod/define"
|
||||||
"github.com/containers/podman/v2/pkg/domain/entities"
|
"github.com/containers/podman/v2/pkg/domain/entities"
|
||||||
"github.com/containers/podman/v2/pkg/domain/filters"
|
"github.com/containers/podman/v2/pkg/domain/filters"
|
||||||
"github.com/containers/podman/v2/pkg/domain/infra/abi/parse"
|
"github.com/containers/podman/v2/pkg/domain/infra/abi/parse"
|
||||||
@ -71,9 +72,10 @@ func (ic *ContainerEngine) VolumeRm(ctx context.Context, namesOrIds []string, op
|
|||||||
return reports, nil
|
return reports, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ic *ContainerEngine) VolumeInspect(ctx context.Context, namesOrIds []string, opts entities.VolumeInspectOptions) ([]*entities.VolumeInspectReport, error) {
|
func (ic *ContainerEngine) VolumeInspect(ctx context.Context, namesOrIds []string, opts entities.InspectOptions) ([]*entities.VolumeInspectReport, []error, error) {
|
||||||
var (
|
var (
|
||||||
err error
|
err error
|
||||||
|
errs []error
|
||||||
vols []*libpod.Volume
|
vols []*libpod.Volume
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -82,13 +84,18 @@ func (ic *ContainerEngine) VolumeInspect(ctx context.Context, namesOrIds []strin
|
|||||||
if opts.All {
|
if opts.All {
|
||||||
vols, err = ic.Libpod.GetAllVolumes()
|
vols, err = ic.Libpod.GetAllVolumes()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
for _, v := range namesOrIds {
|
for _, v := range namesOrIds {
|
||||||
vol, err := ic.Libpod.LookupVolume(v)
|
vol, err := ic.Libpod.LookupVolume(v)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, errors.Wrapf(err, "error inspecting volume %s", v)
|
if errors.Cause(err) == define.ErrNoSuchVolume {
|
||||||
|
errs = append(errs, errors.Errorf("no such volume %s", v))
|
||||||
|
continue
|
||||||
|
} else {
|
||||||
|
return nil, nil, errors.Wrapf(err, "error inspecting volume %s", v)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
vols = append(vols, vol)
|
vols = append(vols, vol)
|
||||||
}
|
}
|
||||||
@ -98,11 +105,11 @@ func (ic *ContainerEngine) VolumeInspect(ctx context.Context, namesOrIds []strin
|
|||||||
var uid, gid int
|
var uid, gid int
|
||||||
uid, err = v.UID()
|
uid, err = v.UID()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
gid, err = v.GID()
|
gid, err = v.GID()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
config := entities.VolumeConfigResponse{
|
config := entities.VolumeConfigResponse{
|
||||||
Name: v.Name(),
|
Name: v.Name(),
|
||||||
@ -117,7 +124,7 @@ func (ic *ContainerEngine) VolumeInspect(ctx context.Context, namesOrIds []strin
|
|||||||
}
|
}
|
||||||
reports = append(reports, &entities.VolumeInspectReport{VolumeConfigResponse: &config})
|
reports = append(reports, &entities.VolumeInspectReport{VolumeConfigResponse: &config})
|
||||||
}
|
}
|
||||||
return reports, nil
|
return reports, errs, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ic *ContainerEngine) VolumePrune(ctx context.Context) ([]*entities.VolumePruneReport, error) {
|
func (ic *ContainerEngine) VolumePrune(ctx context.Context) ([]*entities.VolumePruneReport, error) {
|
||||||
|
@ -5,22 +5,34 @@ import (
|
|||||||
|
|
||||||
"github.com/containers/podman/v2/pkg/bindings/network"
|
"github.com/containers/podman/v2/pkg/bindings/network"
|
||||||
"github.com/containers/podman/v2/pkg/domain/entities"
|
"github.com/containers/podman/v2/pkg/domain/entities"
|
||||||
|
"github.com/pkg/errors"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (ic *ContainerEngine) NetworkList(ctx context.Context, options entities.NetworkListOptions) ([]*entities.NetworkListReport, error) {
|
func (ic *ContainerEngine) NetworkList(ctx context.Context, options entities.NetworkListOptions) ([]*entities.NetworkListReport, error) {
|
||||||
return network.List(ic.ClientCxt, options)
|
return network.List(ic.ClientCxt, options)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ic *ContainerEngine) NetworkInspect(ctx context.Context, namesOrIds []string, options entities.NetworkInspectOptions) ([]entities.NetworkInspectReport, error) {
|
func (ic *ContainerEngine) NetworkInspect(ctx context.Context, namesOrIds []string, options entities.InspectOptions) ([]entities.NetworkInspectReport, []error, error) {
|
||||||
reports := make([]entities.NetworkInspectReport, 0, len(namesOrIds))
|
var (
|
||||||
|
reports = make([]entities.NetworkInspectReport, 0, len(namesOrIds))
|
||||||
|
errs = []error{}
|
||||||
|
)
|
||||||
for _, name := range namesOrIds {
|
for _, name := range namesOrIds {
|
||||||
report, err := network.Inspect(ic.ClientCxt, name)
|
report, err := network.Inspect(ic.ClientCxt, name)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
errModel, ok := err.(entities.ErrorModel)
|
||||||
|
if !ok {
|
||||||
|
return nil, nil, err
|
||||||
|
}
|
||||||
|
if errModel.ResponseCode == 404 {
|
||||||
|
errs = append(errs, errors.Errorf("no such network %q", name))
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
reports = append(reports, report...)
|
reports = append(reports, report...)
|
||||||
}
|
}
|
||||||
return reports, nil
|
return reports, errs, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ic *ContainerEngine) NetworkRm(ctx context.Context, namesOrIds []string, options entities.NetworkRmOptions) ([]*entities.NetworkRmReport, error) {
|
func (ic *ContainerEngine) NetworkRm(ctx context.Context, namesOrIds []string, options entities.NetworkRmOptions) ([]*entities.NetworkRmReport, error) {
|
||||||
|
@ -5,6 +5,7 @@ import (
|
|||||||
|
|
||||||
"github.com/containers/podman/v2/pkg/bindings/volumes"
|
"github.com/containers/podman/v2/pkg/bindings/volumes"
|
||||||
"github.com/containers/podman/v2/pkg/domain/entities"
|
"github.com/containers/podman/v2/pkg/domain/entities"
|
||||||
|
"github.com/pkg/errors"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (ic *ContainerEngine) VolumeCreate(ctx context.Context, opts entities.VolumeCreateOptions) (*entities.IDOrNameResponse, error) {
|
func (ic *ContainerEngine) VolumeCreate(ctx context.Context, opts entities.VolumeCreateOptions) (*entities.IDOrNameResponse, error) {
|
||||||
@ -35,25 +36,36 @@ func (ic *ContainerEngine) VolumeRm(ctx context.Context, namesOrIds []string, op
|
|||||||
return reports, nil
|
return reports, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ic *ContainerEngine) VolumeInspect(ctx context.Context, namesOrIds []string, opts entities.VolumeInspectOptions) ([]*entities.VolumeInspectReport, error) {
|
func (ic *ContainerEngine) VolumeInspect(ctx context.Context, namesOrIds []string, opts entities.InspectOptions) ([]*entities.VolumeInspectReport, []error, error) {
|
||||||
|
var (
|
||||||
|
reports = make([]*entities.VolumeInspectReport, 0, len(namesOrIds))
|
||||||
|
errs = []error{}
|
||||||
|
)
|
||||||
if opts.All {
|
if opts.All {
|
||||||
vols, err := volumes.List(ic.ClientCxt, nil)
|
vols, err := volumes.List(ic.ClientCxt, nil)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
for _, v := range vols {
|
for _, v := range vols {
|
||||||
namesOrIds = append(namesOrIds, v.Name)
|
namesOrIds = append(namesOrIds, v.Name)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
reports := make([]*entities.VolumeInspectReport, 0, len(namesOrIds))
|
|
||||||
for _, id := range namesOrIds {
|
for _, id := range namesOrIds {
|
||||||
data, err := volumes.Inspect(ic.ClientCxt, id)
|
data, err := volumes.Inspect(ic.ClientCxt, id)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
errModel, ok := err.(entities.ErrorModel)
|
||||||
|
if !ok {
|
||||||
|
return nil, nil, err
|
||||||
|
}
|
||||||
|
if errModel.ResponseCode == 404 {
|
||||||
|
errs = append(errs, errors.Errorf("no such volume %q", id))
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
reports = append(reports, &entities.VolumeInspectReport{VolumeConfigResponse: data})
|
reports = append(reports, &entities.VolumeInspectReport{VolumeConfigResponse: data})
|
||||||
}
|
}
|
||||||
return reports, nil
|
return reports, errs, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ic *ContainerEngine) VolumePrune(ctx context.Context) ([]*entities.VolumePruneReport, error) {
|
func (ic *ContainerEngine) VolumePrune(ctx context.Context) ([]*entities.VolumePruneReport, error) {
|
||||||
|
@ -515,6 +515,14 @@ func (s *PodmanSessionIntegration) InspectPodToJSON() define.InspectPodData {
|
|||||||
return i
|
return i
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// InspectPodToJSON takes the sessions output from an inspect and returns json
|
||||||
|
func (s *PodmanSessionIntegration) InspectPodArrToJSON() []define.InspectPodData {
|
||||||
|
var i []define.InspectPodData
|
||||||
|
err := jsoniter.Unmarshal(s.Out.Contents(), &i)
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
|
||||||
// CreatePod creates a pod with no infra container
|
// CreatePod creates a pod with no infra container
|
||||||
// it optionally takes a pod name
|
// it optionally takes a pod name
|
||||||
func (p *PodmanTestIntegration) CreatePod(name string) (*PodmanSessionIntegration, int, string) {
|
func (p *PodmanTestIntegration) CreatePod(name string) (*PodmanSessionIntegration, int, string) {
|
||||||
|
@ -289,4 +289,145 @@ var _ = Describe("Podman inspect", func() {
|
|||||||
Expect(baseJSON[0].HostConfig.SecurityOpt).To(Equal([]string{"label=type:spc_t,label=level:s0", "seccomp=unconfined"}))
|
Expect(baseJSON[0].HostConfig.SecurityOpt).To(Equal([]string{"label=type:spc_t,label=level:s0", "seccomp=unconfined"}))
|
||||||
})
|
})
|
||||||
|
|
||||||
|
It("podman inspect pod", func() {
|
||||||
|
podName := "testpod"
|
||||||
|
create := podmanTest.PodmanNoCache([]string{"pod", "create", "--name", podName})
|
||||||
|
create.WaitWithDefaultTimeout()
|
||||||
|
Expect(create.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"inspect", podName})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect.ExitCode()).To(Equal(0))
|
||||||
|
Expect(inspect.IsJSONOutputValid()).To(BeTrue())
|
||||||
|
podData := inspect.InspectPodArrToJSON()
|
||||||
|
Expect(podData[0].Name).To(Equal(podName))
|
||||||
|
})
|
||||||
|
|
||||||
|
It("podman inspect pod with type", func() {
|
||||||
|
podName := "testpod"
|
||||||
|
create := podmanTest.PodmanNoCache([]string{"pod", "create", "--name", podName})
|
||||||
|
create.WaitWithDefaultTimeout()
|
||||||
|
Expect(create.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"inspect", "--type", "pod", podName})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect.ExitCode()).To(Equal(0))
|
||||||
|
Expect(inspect.IsJSONOutputValid()).To(BeTrue())
|
||||||
|
podData := inspect.InspectPodArrToJSON()
|
||||||
|
Expect(podData[0].Name).To(Equal(podName))
|
||||||
|
})
|
||||||
|
|
||||||
|
It("podman inspect latest pod", func() {
|
||||||
|
SkipIfRemote("--latest flag n/a")
|
||||||
|
podName := "testpod"
|
||||||
|
create := podmanTest.PodmanNoCache([]string{"pod", "create", "--name", podName})
|
||||||
|
create.WaitWithDefaultTimeout()
|
||||||
|
Expect(create.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"inspect", "--type", "pod", "--latest"})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect.ExitCode()).To(Equal(0))
|
||||||
|
Expect(inspect.IsJSONOutputValid()).To(BeTrue())
|
||||||
|
podData := inspect.InspectPodArrToJSON()
|
||||||
|
Expect(podData[0].Name).To(Equal(podName))
|
||||||
|
})
|
||||||
|
It("podman inspect latest defaults to latest container", func() {
|
||||||
|
SkipIfRemote("--latest flag n/a")
|
||||||
|
podName := "testpod"
|
||||||
|
pod := podmanTest.PodmanNoCache([]string{"pod", "create", "--name", podName})
|
||||||
|
pod.WaitWithDefaultTimeout()
|
||||||
|
Expect(pod.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
inspect1 := podmanTest.Podman([]string{"inspect", "--type", "pod", podName})
|
||||||
|
inspect1.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect1.ExitCode()).To(Equal(0))
|
||||||
|
Expect(inspect1.IsJSONOutputValid()).To(BeTrue())
|
||||||
|
podData := inspect1.InspectPodArrToJSON()
|
||||||
|
infra := podData[0].Containers[0].Name
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"inspect", "--latest"})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect.ExitCode()).To(Equal(0))
|
||||||
|
Expect(inspect.IsJSONOutputValid()).To(BeTrue())
|
||||||
|
containerData := inspect.InspectContainerToJSON()
|
||||||
|
Expect(containerData[0].Name).To(Equal(infra))
|
||||||
|
})
|
||||||
|
|
||||||
|
It("podman inspect network", func() {
|
||||||
|
name, path := generateNetworkConfig(podmanTest)
|
||||||
|
defer removeConf(path)
|
||||||
|
|
||||||
|
session := podmanTest.Podman([]string{"inspect", name, "--format", "{{.cniVersion}}"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session.ExitCode()).To(Equal(0))
|
||||||
|
Expect(session.LineInOutputContains("0.3.0")).To(BeTrue())
|
||||||
|
})
|
||||||
|
|
||||||
|
It("podman inspect a volume", func() {
|
||||||
|
session := podmanTest.Podman([]string{"volume", "create", "myvol"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
volName := session.OutputToString()
|
||||||
|
Expect(session.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
session = podmanTest.Podman([]string{"inspect", volName})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session.ExitCode()).To(Equal(0))
|
||||||
|
Expect(session.IsJSONOutputValid()).To(BeTrue())
|
||||||
|
})
|
||||||
|
|
||||||
|
It("podman inspect a volume with --format", func() {
|
||||||
|
session := podmanTest.Podman([]string{"volume", "create", "myvol"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
volName := session.OutputToString()
|
||||||
|
Expect(session.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
session = podmanTest.Podman([]string{"inspect", "--format", "{{.Name}}", volName})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session.ExitCode()).To(Equal(0))
|
||||||
|
Expect(session.OutputToString()).To(Equal(volName))
|
||||||
|
})
|
||||||
|
It("podman inspect --type container on a pod should fail", func() {
|
||||||
|
podName := "testpod"
|
||||||
|
create := podmanTest.PodmanNoCache([]string{"pod", "create", "--name", podName})
|
||||||
|
create.WaitWithDefaultTimeout()
|
||||||
|
Expect(create.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"inspect", "--type", "container", podName})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect).To(ExitWithError())
|
||||||
|
})
|
||||||
|
|
||||||
|
It("podman inspect --type network on a container should fail", func() {
|
||||||
|
ctrName := "testctr"
|
||||||
|
create := podmanTest.PodmanNoCache([]string{"create", "--name", ctrName, ALPINE})
|
||||||
|
create.WaitWithDefaultTimeout()
|
||||||
|
Expect(create.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"inspect", "--type", "network", ctrName})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect).To(ExitWithError())
|
||||||
|
})
|
||||||
|
|
||||||
|
It("podman inspect --type pod on a container should fail", func() {
|
||||||
|
ctrName := "testctr"
|
||||||
|
create := podmanTest.PodmanNoCache([]string{"create", "--name", ctrName, ALPINE})
|
||||||
|
create.WaitWithDefaultTimeout()
|
||||||
|
Expect(create.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"inspect", "--type", "pod", ctrName})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect).To(ExitWithError())
|
||||||
|
})
|
||||||
|
|
||||||
|
It("podman inspect --type volume on a container should fail", func() {
|
||||||
|
ctrName := "testctr"
|
||||||
|
create := podmanTest.PodmanNoCache([]string{"create", "--name", ctrName, ALPINE})
|
||||||
|
create.WaitWithDefaultTimeout()
|
||||||
|
Expect(create.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"inspect", "--type", "volume", ctrName})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect).To(ExitWithError())
|
||||||
|
})
|
||||||
|
|
||||||
})
|
})
|
||||||
|
Reference in New Issue
Block a user