github.com/panekj/cli@v0.0.0-20230304125325-467dd2f3797e/cli/command/service/inspect.go (about)

     1  package service
     2  
     3  import (
     4  	"context"
     5  	"strings"
     6  
     7  	"github.com/docker/cli/cli"
     8  	"github.com/docker/cli/cli/command"
     9  	"github.com/docker/cli/cli/command/formatter"
    10  	flagsHelper "github.com/docker/cli/cli/flags"
    11  	"github.com/docker/docker/api/types"
    12  	apiclient "github.com/docker/docker/client"
    13  	"github.com/pkg/errors"
    14  	"github.com/spf13/cobra"
    15  )
    16  
    17  type inspectOptions struct {
    18  	refs   []string
    19  	format string
    20  	pretty bool
    21  }
    22  
    23  func newInspectCommand(dockerCli command.Cli) *cobra.Command {
    24  	var opts inspectOptions
    25  
    26  	cmd := &cobra.Command{
    27  		Use:   "inspect [OPTIONS] SERVICE [SERVICE...]",
    28  		Short: "Display detailed information on one or more services",
    29  		Args:  cli.RequiresMinArgs(1),
    30  		RunE: func(cmd *cobra.Command, args []string) error {
    31  			opts.refs = args
    32  
    33  			if opts.pretty && len(opts.format) > 0 {
    34  				return errors.Errorf("--format is incompatible with human friendly format")
    35  			}
    36  			return runInspect(dockerCli, opts)
    37  		},
    38  		ValidArgsFunction: func(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) {
    39  			return CompletionFn(dockerCli)(cmd, args, toComplete)
    40  		},
    41  	}
    42  
    43  	flags := cmd.Flags()
    44  	flags.StringVarP(&opts.format, "format", "f", "", flagsHelper.InspectFormatHelp)
    45  	flags.BoolVar(&opts.pretty, "pretty", false, "Print the information in a human friendly format")
    46  	return cmd
    47  }
    48  
    49  func runInspect(dockerCli command.Cli, opts inspectOptions) error {
    50  	client := dockerCli.Client()
    51  	ctx := context.Background()
    52  
    53  	if opts.pretty {
    54  		opts.format = "pretty"
    55  	}
    56  
    57  	getRef := func(ref string) (interface{}, []byte, error) {
    58  		// Service inspect shows defaults values in empty fields.
    59  		service, _, err := client.ServiceInspectWithRaw(ctx, ref, types.ServiceInspectOptions{InsertDefaults: true})
    60  		if err == nil || !apiclient.IsErrNotFound(err) {
    61  			return service, nil, err
    62  		}
    63  		return nil, nil, errors.Errorf("Error: no such service: %s", ref)
    64  	}
    65  
    66  	getNetwork := func(ref string) (interface{}, []byte, error) {
    67  		network, _, err := client.NetworkInspectWithRaw(ctx, ref, types.NetworkInspectOptions{Scope: "swarm"})
    68  		if err == nil || !apiclient.IsErrNotFound(err) {
    69  			return network, nil, err
    70  		}
    71  		return nil, nil, errors.Errorf("Error: no such network: %s", ref)
    72  	}
    73  
    74  	f := opts.format
    75  	if len(f) == 0 {
    76  		f = "raw"
    77  		if len(dockerCli.ConfigFile().ServiceInspectFormat) > 0 {
    78  			f = dockerCli.ConfigFile().ServiceInspectFormat
    79  		}
    80  	}
    81  
    82  	// check if the user is trying to apply a template to the pretty format, which
    83  	// is not supported
    84  	if strings.HasPrefix(f, "pretty") && f != "pretty" {
    85  		return errors.Errorf("Cannot supply extra formatting options to the pretty template")
    86  	}
    87  
    88  	serviceCtx := formatter.Context{
    89  		Output: dockerCli.Out(),
    90  		Format: NewFormat(f),
    91  	}
    92  
    93  	if err := InspectFormatWrite(serviceCtx, opts.refs, getRef, getNetwork); err != nil {
    94  		return cli.StatusError{StatusCode: 1, Status: err.Error()}
    95  	}
    96  	return nil
    97  }