diff --git a/Makefile b/Makefile index 4bdb0f6a86..8d5ddabee5 100644 --- a/Makefile +++ b/Makefile @@ -34,5 +34,3 @@ vendor: vendor.conf echo; git status --porcelain -- vendor 2>/dev/nul; \ echo; exit 1; \ fi; - -ci: cross test diff --git a/circle.yml b/circle.yml index 93dc842e3d..f8032a6aab 100644 --- a/circle.yml +++ b/circle.yml @@ -1,27 +1,41 @@ version: 2 jobs: build: - working_directory: ~/cli + working_directory: /work docker: - image: docker:17.05 + parallelism: 4 steps: - run: name: "Install Git and SSH" - command: | - apk add -U git openssh + command: apk add -U git openssh - checkout - setup_remote_docker - run: name: "Lint" command: | + if [ "$CIRCLE_NODE_INDEX" != "0" ]; then exit; fi docker build -f dockerfiles/Dockerfile.lint --tag cli-linter . docker run cli-linter - run: - name: "Build and Unit Test" + name: "Cross" command: | + if [ "$CIRCLE_NODE_INDEX" != "1" ]; then exit; fi docker build -f dockerfiles/Dockerfile.ci --tag cli-builder . - docker run cli-builder + docker run --name cross cli-builder make cross + docker cp cross:/go/src/github.com/docker/cli/build /work/build + - run: + name: "Unit Test" + command: | + if [ "$CIRCLE_NODE_INDEX" != "2" ]; then exit; fi + docker build -f dockerfiles/Dockerfile.ci --tag cli-builder . + docker run cli-builder make test - run: name: "Vendor" command: | - docker run cli-builder make vendor + if [ "$CIRCLE_NODE_INDEX" != "3" ]; then exit; fi + docker build -f dockerfiles/Dockerfile.ci --tag cli-builder . + docker run cli-builder make -B vendor + + - store_artifacts: + path: /work/build diff --git a/cli/command/checkpoint/cmd.go b/cli/command/checkpoint/cmd.go index f748dd72f1..30e9ce364c 100644 --- a/cli/command/checkpoint/cmd.go +++ b/cli/command/checkpoint/cmd.go @@ -7,12 +7,12 @@ import ( ) // NewCheckpointCommand returns the `checkpoint` subcommand (only in experimental) -func NewCheckpointCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewCheckpointCommand(dockerCli command.Cli) *cobra.Command { cmd := &cobra.Command{ Use: "checkpoint", Short: "Manage checkpoints", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), Tags: map[string]string{"experimental": "", "version": "1.25"}, } cmd.AddCommand( diff --git a/cli/command/checkpoint/create.go b/cli/command/checkpoint/create.go index cdcd3220bc..974b44ab83 100644 --- a/cli/command/checkpoint/create.go +++ b/cli/command/checkpoint/create.go @@ -18,7 +18,7 @@ type createOptions struct { leaveRunning bool } -func newCreateCommand(dockerCli *command.DockerCli) *cobra.Command { +func newCreateCommand(dockerCli command.Cli) *cobra.Command { var opts createOptions cmd := &cobra.Command{ @@ -39,7 +39,7 @@ func newCreateCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runCreate(dockerCli *command.DockerCli, opts createOptions) error { +func runCreate(dockerCli command.Cli, opts createOptions) error { client := dockerCli.Client() checkpointOpts := types.CheckpointCreateOptions{ diff --git a/cli/command/checkpoint/list.go b/cli/command/checkpoint/list.go index 6c560a9a1b..758aa69936 100644 --- a/cli/command/checkpoint/list.go +++ b/cli/command/checkpoint/list.go @@ -14,7 +14,7 @@ type listOptions struct { checkpointDir string } -func newListCommand(dockerCli *command.DockerCli) *cobra.Command { +func newListCommand(dockerCli command.Cli) *cobra.Command { var opts listOptions cmd := &cobra.Command{ @@ -34,7 +34,7 @@ func newListCommand(dockerCli *command.DockerCli) *cobra.Command { } -func runList(dockerCli *command.DockerCli, container string, opts listOptions) error { +func runList(dockerCli command.Cli, container string, opts listOptions) error { client := dockerCli.Client() listOpts := types.CheckpointListOptions{ diff --git a/cli/command/checkpoint/remove.go b/cli/command/checkpoint/remove.go index 4fbf763c8b..298adbaef7 100644 --- a/cli/command/checkpoint/remove.go +++ b/cli/command/checkpoint/remove.go @@ -13,7 +13,7 @@ type removeOptions struct { checkpointDir string } -func newRemoveCommand(dockerCli *command.DockerCli) *cobra.Command { +func newRemoveCommand(dockerCli command.Cli) *cobra.Command { var opts removeOptions cmd := &cobra.Command{ @@ -32,7 +32,7 @@ func newRemoveCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runRemove(dockerCli *command.DockerCli, container string, checkpoint string, opts removeOptions) error { +func runRemove(dockerCli command.Cli, container string, checkpoint string, opts removeOptions) error { client := dockerCli.Client() removeOpts := types.CheckpointDeleteOptions{ diff --git a/cli/command/cli.go b/cli/command/cli.go index e9c3af2232..eea823f4c5 100644 --- a/cli/command/cli.go +++ b/cli/command/cli.go @@ -86,10 +86,12 @@ func (cli *DockerCli) In() *InStream { } // ShowHelp shows the command help. -func (cli *DockerCli) ShowHelp(cmd *cobra.Command, args []string) error { - cmd.SetOutput(cli.err) - cmd.HelpFunc()(cmd, args) - return nil +func ShowHelp(err io.Writer) func(*cobra.Command, []string) error { + return func(cmd *cobra.Command, args []string) error { + cmd.SetOutput(err) + cmd.HelpFunc()(cmd, args) + return nil + } } // ConfigFile returns the ConfigFile diff --git a/cli/command/container/cmd.go b/cli/command/container/cmd.go index ebcb2d504c..82500be02e 100644 --- a/cli/command/container/cmd.go +++ b/cli/command/container/cmd.go @@ -7,12 +7,13 @@ import ( ) // NewContainerCommand returns a cobra command for `container` subcommands +// nolint: interfacer func NewContainerCommand(dockerCli *command.DockerCli) *cobra.Command { cmd := &cobra.Command{ Use: "container", Short: "Manage containers", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), } cmd.AddCommand( NewAttachCommand(dockerCli), diff --git a/cli/command/container/create.go b/cli/command/container/create.go index a73fadf9db..2795e4fed7 100644 --- a/cli/command/container/create.go +++ b/cli/command/container/create.go @@ -25,7 +25,7 @@ type createOptions struct { } // NewCreateCommand creates a new cobra.Command for `docker create` -func NewCreateCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewCreateCommand(dockerCli command.Cli) *cobra.Command { var opts createOptions var copts *containerOptions @@ -56,7 +56,7 @@ func NewCreateCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runCreate(dockerCli *command.DockerCli, flags *pflag.FlagSet, opts *createOptions, copts *containerOptions) error { +func runCreate(dockerCli command.Cli, flags *pflag.FlagSet, opts *createOptions, copts *containerOptions) error { containerConfig, err := parse(flags, copts) if err != nil { reportError(dockerCli.Err(), "create", err.Error(), true) @@ -70,7 +70,7 @@ func runCreate(dockerCli *command.DockerCli, flags *pflag.FlagSet, opts *createO return nil } -func pullImage(ctx context.Context, dockerCli *command.DockerCli, image string, out io.Writer) error { +func pullImage(ctx context.Context, dockerCli command.Cli, image string, out io.Writer) error { ref, err := reference.ParseNormalizedNamed(image) if err != nil { return err @@ -146,7 +146,7 @@ func newCIDFile(path string) (*cidFile, error) { return &cidFile{path: path, file: f}, nil } -func createContainer(ctx context.Context, dockerCli *command.DockerCli, containerConfig *containerConfig, name string) (*container.ContainerCreateCreatedBody, error) { +func createContainer(ctx context.Context, dockerCli command.Cli, containerConfig *containerConfig, name string) (*container.ContainerCreateCreatedBody, error) { config := containerConfig.Config hostConfig := containerConfig.HostConfig networkingConfig := containerConfig.NetworkingConfig diff --git a/cli/command/container/opts_test.go b/cli/command/container/opts_test.go index 429fee7c51..e10754f31b 100644 --- a/cli/command/container/opts_test.go +++ b/cli/command/container/opts_test.go @@ -165,7 +165,9 @@ func TestParseRunVolumes(t *testing.T) { // Two bind-mounts, first read-only, second read-write. // TODO Windows: The Windows version uses read-write as that's the only mode it supports. Can change this post TP4 - arr, tryit = setupPlatformVolume([]string{`/hostTmp:/containerTmp:ro`, `/hostVar:/containerVar:rw`}, []string{os.Getenv("TEMP") + `:c:\containerTmp:rw`, os.Getenv("ProgramData") + `:c:\ContainerPD:rw`}) + arr, tryit = setupPlatformVolume( + []string{`/hostTmp:/containerTmp:ro`, `/hostVar:/containerVar:rw`}, + []string{os.Getenv("TEMP") + `:c:\containerTmp:rw`, os.Getenv("ProgramData") + `:c:\ContainerPD:rw`}) if _, hostConfig := mustParse(t, tryit); hostConfig.Binds == nil || compareRandomizedStrings(hostConfig.Binds[0], hostConfig.Binds[1], arr[0], arr[1]) != nil { t.Fatalf("Error parsing volume flags, `%s and %s` did not mount-bind correctly. Received %v", arr[0], arr[1], hostConfig.Binds) } diff --git a/cli/command/container/prune.go b/cli/command/container/prune.go index 8cc81929e1..676a6a8f3e 100644 --- a/cli/command/container/prune.go +++ b/cli/command/container/prune.go @@ -17,7 +17,7 @@ type pruneOptions struct { } // NewPruneCommand returns a new cobra prune command for containers -func NewPruneCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewPruneCommand(dockerCli command.Cli) *cobra.Command { opts := pruneOptions{filter: opts.NewFilterOpt()} cmd := &cobra.Command{ @@ -48,7 +48,7 @@ func NewPruneCommand(dockerCli *command.DockerCli) *cobra.Command { const warning = `WARNING! This will remove all stopped containers. Are you sure you want to continue?` -func runPrune(dockerCli *command.DockerCli, opts pruneOptions) (spaceReclaimed uint64, output string, err error) { +func runPrune(dockerCli command.Cli, opts pruneOptions) (spaceReclaimed uint64, output string, err error) { pruneFilters := command.PruneFilters(dockerCli, opts.filter.Value()) if !opts.force && !command.PromptForConfirmation(dockerCli.In(), dockerCli.Out(), warning) { @@ -73,6 +73,6 @@ func runPrune(dockerCli *command.DockerCli, opts pruneOptions) (spaceReclaimed u // RunPrune calls the Container Prune API // This returns the amount of space reclaimed and a detailed output string -func RunPrune(dockerCli *command.DockerCli, filter opts.FilterOpt) (uint64, string, error) { +func RunPrune(dockerCli command.Cli, filter opts.FilterOpt) (uint64, string, error) { return runPrune(dockerCli, pruneOptions{force: true, filter: filter}) } diff --git a/cli/command/container/run.go b/cli/command/container/run.go index 9cd0b1d812..c1f5541899 100644 --- a/cli/command/container/run.go +++ b/cli/command/container/run.go @@ -220,7 +220,7 @@ func runContainer(dockerCli *command.DockerCli, opts *runOptions, copts *contain func attachContainer( ctx context.Context, - dockerCli *command.DockerCli, + dockerCli command.Cli, errCh *chan error, config *container.Config, containerID string, diff --git a/cli/command/container/stats_unit_test.go b/cli/command/container/stats_unit_test.go index 612914c9cd..21e650e285 100644 --- a/cli/command/container/stats_unit_test.go +++ b/cli/command/container/stats_unit_test.go @@ -8,7 +8,12 @@ import ( func TestCalculateBlockIO(t *testing.T) { blkio := types.BlkioStats{ - IoServiceBytesRecursive: []types.BlkioStatEntry{{Major: 8, Minor: 0, Op: "read", Value: 1234}, {Major: 8, Minor: 1, Op: "read", Value: 4567}, {Major: 8, Minor: 0, Op: "write", Value: 123}, {Major: 8, Minor: 1, Op: "write", Value: 456}}, + IoServiceBytesRecursive: []types.BlkioStatEntry{ + {Major: 8, Minor: 0, Op: "read", Value: 1234}, + {Major: 8, Minor: 1, Op: "read", Value: 4567}, + {Major: 8, Minor: 0, Op: "write", Value: 123}, + {Major: 8, Minor: 1, Op: "write", Value: 456}, + }, } blkRead, blkWrite := calculateBlockIO(blkio) if blkRead != 5801 { diff --git a/cli/command/formatter/container_test.go b/cli/command/formatter/container_test.go index 8d23cc781c..5b1451c29e 100644 --- a/cli/command/formatter/container_test.go +++ b/cli/command/formatter/container_test.go @@ -320,8 +320,36 @@ func TestContainerContextWriteJSON(t *testing.T) { } expectedCreated := time.Unix(unix, 0).String() expectedJSONs := []map[string]interface{}{ - {"Command": "\"\"", "CreatedAt": expectedCreated, "ID": "containerID1", "Image": "ubuntu", "Labels": "", "LocalVolumes": "0", "Mounts": "", "Names": "foobar_baz", "Networks": "", "Ports": "", "RunningFor": "About a minute ago", "Size": "0B", "Status": ""}, - {"Command": "\"\"", "CreatedAt": expectedCreated, "ID": "containerID2", "Image": "ubuntu", "Labels": "", "LocalVolumes": "0", "Mounts": "", "Names": "foobar_bar", "Networks": "", "Ports": "", "RunningFor": "About a minute ago", "Size": "0B", "Status": ""}, + { + "Command": "\"\"", + "CreatedAt": expectedCreated, + "ID": "containerID1", + "Image": "ubuntu", + "Labels": "", + "LocalVolumes": "0", + "Mounts": "", + "Names": "foobar_baz", + "Networks": "", + "Ports": "", + "RunningFor": "About a minute ago", + "Size": "0B", + "Status": "", + }, + { + "Command": "\"\"", + "CreatedAt": expectedCreated, + "ID": "containerID2", + "Image": "ubuntu", + "Labels": "", + "LocalVolumes": "0", + "Mounts": "", + "Names": "foobar_bar", + "Networks": "", + "Ports": "", + "RunningFor": "About a minute ago", + "Size": "0B", + "Status": "", + }, } out := bytes.NewBufferString("") err := ContainerWrite(Context{Format: "{{json .}}", Output: out}, containers) diff --git a/cli/command/formatter/history_test.go b/cli/command/formatter/history_test.go index 97ebcfdde1..a1ee205b03 100644 --- a/cli/command/formatter/history_test.go +++ b/cli/command/formatter/history_test.go @@ -77,8 +77,8 @@ func TestHistoryContext_CreatedSince(t *testing.T) { } func TestHistoryContext_CreatedBy(t *testing.T) { - withTabs := `/bin/sh -c apt-key adv --keyserver hkp://pgp.mit.edu:80 --recv-keys 573BFD6B3D8FBC641079A6ABABF5BD827BD9BF62 && echo "deb http://nginx.org/packages/mainline/debian/ jessie nginx" >> /etc/apt/sources.list && apt-get update && apt-get install --no-install-recommends --no-install-suggests -y ca-certificates nginx=${NGINX_VERSION} nginx-module-xslt nginx-module-geoip nginx-module-image-filter nginx-module-perl nginx-module-njs gettext-base && rm -rf /var/lib/apt/lists/*` - expected := `/bin/sh -c apt-key adv --keyserver hkp://pgp.mit.edu:80 --recv-keys 573BFD6B3D8FBC641079A6ABABF5BD827BD9BF62 && echo "deb http://nginx.org/packages/mainline/debian/ jessie nginx" >> /etc/apt/sources.list && apt-get update && apt-get install --no-install-recommends --no-install-suggests -y ca-certificates nginx=${NGINX_VERSION} nginx-module-xslt nginx-module-geoip nginx-module-image-filter nginx-module-perl nginx-module-njs gettext-base && rm -rf /var/lib/apt/lists/*` + withTabs := `/bin/sh -c apt-key adv --keyserver hkp://pgp.mit.edu:80 --recv-keys 573BFD6B3D8FBC641079A6ABABF5BD827BD9BF62 && echo "deb http://nginx.org/packages/mainline/debian/ jessie nginx" >> /etc/apt/sources.list && apt-get update && apt-get install --no-install-recommends --no-install-suggests -y ca-certificates nginx=${NGINX_VERSION} nginx-module-xslt nginx-module-geoip nginx-module-image-filter nginx-module-perl nginx-module-njs gettext-base && rm -rf /var/lib/apt/lists/*` // nolint: lll + expected := `/bin/sh -c apt-key adv --keyserver hkp://pgp.mit.edu:80 --recv-keys 573BFD6B3D8FBC641079A6ABABF5BD827BD9BF62 && echo "deb http://nginx.org/packages/mainline/debian/ jessie nginx" >> /etc/apt/sources.list && apt-get update && apt-get install --no-install-recommends --no-install-suggests -y ca-certificates nginx=${NGINX_VERSION} nginx-module-xslt nginx-module-geoip nginx-module-image-filter nginx-module-perl nginx-module-njs gettext-base && rm -rf /var/lib/apt/lists/*` // nolint: lll var ctx historyContext cases := []historyCase{ @@ -167,11 +167,19 @@ func TestHistoryContext_Table(t *testing.T) { out := bytes.NewBufferString("") unixTime := time.Now().AddDate(0, 0, -1).Unix() histories := []image.HistoryResponseItem{ - {ID: "imageID1", Created: unixTime, CreatedBy: "/bin/bash ls && npm i && npm run test && karma -c karma.conf.js start && npm start && more commands here && the list goes on", Size: int64(182964289), Comment: "Hi", Tags: []string{"image:tag2"}}, + { + ID: "imageID1", + Created: unixTime, + CreatedBy: "/bin/bash ls && npm i && npm run test && karma -c karma.conf.js start && npm start && more commands here && the list goes on", + Size: int64(182964289), + Comment: "Hi", + Tags: []string{"image:tag2"}, + }, {ID: "imageID2", Created: unixTime, CreatedBy: "/bin/bash echo", Size: int64(182964289), Comment: "Hi", Tags: []string{"image:tag2"}}, {ID: "imageID3", Created: unixTime, CreatedBy: "/bin/bash ls", Size: int64(182964289), Comment: "Hi", Tags: []string{"image:tag2"}}, {ID: "imageID4", Created: unixTime, CreatedBy: "/bin/bash grep", Size: int64(182964289), Comment: "Hi", Tags: []string{"image:tag2"}}, } + // nolint: lll expectedNoTrunc := `IMAGE CREATED CREATED BY SIZE COMMENT imageID1 24 hours ago /bin/bash ls && npm i && npm run test && karma -c karma.conf.js start && npm start && more commands here && the list goes on 183MB Hi imageID2 24 hours ago /bin/bash echo 183MB Hi diff --git a/cli/command/formatter/node_test.go b/cli/command/formatter/node_test.go index ea2f4ce4d5..8326e93cde 100644 --- a/cli/command/formatter/node_test.go +++ b/cli/command/formatter/node_test.go @@ -128,8 +128,23 @@ foobar_bar for _, testcase := range cases { nodes := []swarm.Node{ - {ID: "nodeID1", Description: swarm.NodeDescription{Hostname: "foobar_baz"}, Status: swarm.NodeStatus{State: swarm.NodeState("foo")}, Spec: swarm.NodeSpec{Availability: swarm.NodeAvailability("drain")}, ManagerStatus: &swarm.ManagerStatus{Leader: true}}, - {ID: "nodeID2", Description: swarm.NodeDescription{Hostname: "foobar_bar"}, Status: swarm.NodeStatus{State: swarm.NodeState("bar")}, Spec: swarm.NodeSpec{Availability: swarm.NodeAvailability("active")}, ManagerStatus: &swarm.ManagerStatus{Leader: false, Reachability: swarm.Reachability("Reachable")}}, + { + ID: "nodeID1", + Description: swarm.NodeDescription{Hostname: "foobar_baz"}, + Status: swarm.NodeStatus{State: swarm.NodeState("foo")}, + Spec: swarm.NodeSpec{Availability: swarm.NodeAvailability("drain")}, + ManagerStatus: &swarm.ManagerStatus{Leader: true}, + }, + { + ID: "nodeID2", + Description: swarm.NodeDescription{Hostname: "foobar_bar"}, + Status: swarm.NodeStatus{State: swarm.NodeState("bar")}, + Spec: swarm.NodeSpec{Availability: swarm.NodeAvailability("active")}, + ManagerStatus: &swarm.ManagerStatus{ + Leader: false, + Reachability: swarm.Reachability("Reachable"), + }, + }, } out := bytes.NewBufferString("") testcase.context.Output = out diff --git a/cli/command/image/cmd.go b/cli/command/image/cmd.go index cb079174d1..10357fcfd8 100644 --- a/cli/command/image/cmd.go +++ b/cli/command/image/cmd.go @@ -8,12 +8,13 @@ import ( ) // NewImageCommand returns a cobra command for `image` subcommands +// nolint: interfacer func NewImageCommand(dockerCli *command.DockerCli) *cobra.Command { cmd := &cobra.Command{ Use: "image", Short: "Manage images", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), } cmd.AddCommand( NewBuildCommand(dockerCli), diff --git a/cli/command/image/trust.go b/cli/command/image/trust.go index c5b50ba460..dd0d12c4c5 100644 --- a/cli/command/image/trust.go +++ b/cli/command/image/trust.go @@ -42,7 +42,7 @@ func trustedPush(ctx context.Context, cli command.Cli, repoInfo *registry.Reposi // PushTrustedReference pushes a canonical reference to the trust server. // nolint: gocyclo -func PushTrustedReference(cli command.Cli, repoInfo *registry.RepositoryInfo, ref reference.Named, authConfig types.AuthConfig, in io.Reader) error { +func PushTrustedReference(streams command.Streams, repoInfo *registry.RepositoryInfo, ref reference.Named, authConfig types.AuthConfig, in io.Reader) error { // If it is a trusted push we would like to find the target entry which match the // tag provided in the function and then do an AddTarget later. target := &client.Target{} @@ -81,14 +81,14 @@ func PushTrustedReference(cli command.Cli, repoInfo *registry.RepositoryInfo, re default: // We want trust signatures to always take an explicit tag, // otherwise it will act as an untrusted push. - if err := jsonmessage.DisplayJSONMessagesToStream(in, cli.Out(), nil); err != nil { + if err := jsonmessage.DisplayJSONMessagesToStream(in, streams.Out(), nil); err != nil { return err } - fmt.Fprintln(cli.Out(), "No tag specified, skipping trust metadata push") + fmt.Fprintln(streams.Out(), "No tag specified, skipping trust metadata push") return nil } - if err := jsonmessage.DisplayJSONMessagesToStream(in, cli.Out(), handleTarget); err != nil { + if err := jsonmessage.DisplayJSONMessagesToStream(in, streams.Out(), handleTarget); err != nil { return err } @@ -97,15 +97,15 @@ func PushTrustedReference(cli command.Cli, repoInfo *registry.RepositoryInfo, re } if target == nil { - fmt.Fprintln(cli.Out(), "No targets found, please provide a specific tag in order to sign it") + fmt.Fprintln(streams.Out(), "No targets found, please provide a specific tag in order to sign it") return nil } - fmt.Fprintln(cli.Out(), "Signing and pushing trust metadata") + fmt.Fprintln(streams.Out(), "Signing and pushing trust metadata") - repo, err := trust.GetNotaryRepository(cli, repoInfo, authConfig, "push", "pull") + repo, err := trust.GetNotaryRepository(streams, repoInfo, authConfig, "push", "pull") if err != nil { - fmt.Fprintf(cli.Out(), "Error establishing connection to notary repository: %s\n", err) + fmt.Fprintf(streams.Out(), "Error establishing connection to notary repository: %s\n", err) return err } @@ -132,7 +132,7 @@ func PushTrustedReference(cli command.Cli, repoInfo *registry.RepositoryInfo, re if err := repo.Initialize([]string{rootKeyID}, data.CanonicalSnapshotRole); err != nil { return trust.NotaryError(repoInfo.Name.Name(), err) } - fmt.Fprintf(cli.Out(), "Finished initializing %q\n", repoInfo.Name.Name()) + fmt.Fprintf(streams.Out(), "Finished initializing %q\n", repoInfo.Name.Name()) err = repo.AddTarget(target, data.CanonicalTargetsRole) case nil: // already initialized and we have successfully downloaded the latest metadata @@ -146,11 +146,11 @@ func PushTrustedReference(cli command.Cli, repoInfo *registry.RepositoryInfo, re } if err != nil { - fmt.Fprintf(cli.Out(), "Failed to sign %q:%s - %s\n", repoInfo.Name.Name(), tag, err.Error()) + fmt.Fprintf(streams.Out(), "Failed to sign %q:%s - %s\n", repoInfo.Name.Name(), tag, err.Error()) return trust.NotaryError(repoInfo.Name.Name(), err) } - fmt.Fprintf(cli.Out(), "Successfully signed %q:%s\n", repoInfo.Name.Name(), tag) + fmt.Fprintf(streams.Out(), "Successfully signed %q:%s\n", repoInfo.Name.Name(), tag) return nil } @@ -203,7 +203,7 @@ func addTargetToAllSignableRoles(repo *client.NotaryRepository, target *client.T } // imagePushPrivileged push the image -func imagePushPrivileged(ctx context.Context, cli command.Cli, authConfig types.AuthConfig, ref reference.Named, requestPrivilege types.RequestPrivilegeFunc) (io.ReadCloser, error) { +func imagePushPrivileged(ctx context.Context, cli command.Cli, authConfig types.AuthConfig, ref reference.Reference, requestPrivilege types.RequestPrivilegeFunc) (io.ReadCloser, error) { encodedAuth, err := command.EncodeAuthToBase64(authConfig) if err != nil { return nil, err @@ -372,6 +372,7 @@ func convertTarget(t client.Target) (target, error) { } // TagTrusted tags a trusted ref +// nolint: interfacer func TagTrusted(ctx context.Context, cli command.Cli, trustedRef reference.Canonical, ref reference.NamedTagged) error { // Use familiar references when interacting with client and output familiarRef := reference.FamiliarString(ref) diff --git a/cli/command/network/cmd.go b/cli/command/network/cmd.go index da695f8a5c..97bcca2a8d 100644 --- a/cli/command/network/cmd.go +++ b/cli/command/network/cmd.go @@ -8,12 +8,13 @@ import ( ) // NewNetworkCommand returns a cobra command for `network` subcommands +// nolint: interfacer func NewNetworkCommand(dockerCli *command.DockerCli) *cobra.Command { cmd := &cobra.Command{ Use: "network", Short: "Manage networks", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), } cmd.AddCommand( newConnectCommand(dockerCli), diff --git a/cli/command/network/prune.go b/cli/command/network/prune.go index 6a0f639e9f..dde573eeab 100644 --- a/cli/command/network/prune.go +++ b/cli/command/network/prune.go @@ -17,7 +17,7 @@ type pruneOptions struct { } // NewPruneCommand returns a new cobra prune command for networks -func NewPruneCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewPruneCommand(dockerCli command.Cli) *cobra.Command { opts := pruneOptions{filter: opts.NewFilterOpt()} cmd := &cobra.Command{ @@ -47,7 +47,7 @@ func NewPruneCommand(dockerCli *command.DockerCli) *cobra.Command { const warning = `WARNING! This will remove all networks not used by at least one container. Are you sure you want to continue?` -func runPrune(dockerCli *command.DockerCli, opts pruneOptions) (output string, err error) { +func runPrune(dockerCli command.Cli, opts pruneOptions) (output string, err error) { pruneFilters := command.PruneFilters(dockerCli, opts.filter.Value()) if !opts.force && !command.PromptForConfirmation(dockerCli.In(), dockerCli.Out(), warning) { @@ -71,7 +71,7 @@ func runPrune(dockerCli *command.DockerCli, opts pruneOptions) (output string, e // RunPrune calls the Network Prune API // This returns the amount of space reclaimed and a detailed output string -func RunPrune(dockerCli *command.DockerCli, filter opts.FilterOpt) (uint64, string, error) { +func RunPrune(dockerCli command.Cli, filter opts.FilterOpt) (uint64, string, error) { output, err := runPrune(dockerCli, pruneOptions{force: true, filter: filter}) return 0, output, err } diff --git a/cli/command/node/cmd.go b/cli/command/node/cmd.go index ec7a9e395c..b3090d5d71 100644 --- a/cli/command/node/cmd.go +++ b/cli/command/node/cmd.go @@ -12,12 +12,12 @@ import ( ) // NewNodeCommand returns a cobra command for `node` subcommands -func NewNodeCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewNodeCommand(dockerCli command.Cli) *cobra.Command { cmd := &cobra.Command{ Use: "node", Short: "Manage Swarm nodes", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), Tags: map[string]string{"version": "1.24"}, } cmd.AddCommand( diff --git a/cli/command/plugin/cmd.go b/cli/command/plugin/cmd.go index a70f8705ca..c298934937 100644 --- a/cli/command/plugin/cmd.go +++ b/cli/command/plugin/cmd.go @@ -7,12 +7,13 @@ import ( ) // NewPluginCommand returns a cobra command for `plugin` subcommands +// nolint: interfacer func NewPluginCommand(dockerCli *command.DockerCli) *cobra.Command { cmd := &cobra.Command{ Use: "plugin", Short: "Manage plugins", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), Tags: map[string]string{"version": "1.25"}, } diff --git a/cli/command/plugin/push.go b/cli/command/plugin/push.go index 50ba3d610d..68d25157c6 100644 --- a/cli/command/plugin/push.go +++ b/cli/command/plugin/push.go @@ -13,7 +13,7 @@ import ( "github.com/spf13/cobra" ) -func newPushCommand(dockerCli *command.DockerCli) *cobra.Command { +func newPushCommand(dockerCli command.Cli) *cobra.Command { cmd := &cobra.Command{ Use: "push [OPTIONS] PLUGIN[:TAG]", Short: "Push a plugin to a registry", @@ -30,7 +30,7 @@ func newPushCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runPush(dockerCli *command.DockerCli, name string) error { +func runPush(dockerCli command.Cli, name string) error { named, err := reference.ParseNormalizedNamed(name) if err != nil { return err diff --git a/cli/command/prune/prune.go b/cli/command/prune/prune.go index 37852e6dee..b6cb16a5cb 100644 --- a/cli/command/prune/prune.go +++ b/cli/command/prune/prune.go @@ -11,41 +11,41 @@ import ( ) // NewContainerPruneCommand returns a cobra prune command for containers -func NewContainerPruneCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewContainerPruneCommand(dockerCli command.Cli) *cobra.Command { return container.NewPruneCommand(dockerCli) } // NewVolumePruneCommand returns a cobra prune command for volumes -func NewVolumePruneCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewVolumePruneCommand(dockerCli command.Cli) *cobra.Command { return volume.NewPruneCommand(dockerCli) } // NewImagePruneCommand returns a cobra prune command for images -func NewImagePruneCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewImagePruneCommand(dockerCli command.Cli) *cobra.Command { return image.NewPruneCommand(dockerCli) } // NewNetworkPruneCommand returns a cobra prune command for Networks -func NewNetworkPruneCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewNetworkPruneCommand(dockerCli command.Cli) *cobra.Command { return network.NewPruneCommand(dockerCli) } // RunContainerPrune executes a prune command for containers -func RunContainerPrune(dockerCli *command.DockerCli, filter opts.FilterOpt) (uint64, string, error) { +func RunContainerPrune(dockerCli command.Cli, filter opts.FilterOpt) (uint64, string, error) { return container.RunPrune(dockerCli, filter) } // RunVolumePrune executes a prune command for volumes -func RunVolumePrune(dockerCli *command.DockerCli, filter opts.FilterOpt) (uint64, string, error) { +func RunVolumePrune(dockerCli command.Cli, filter opts.FilterOpt) (uint64, string, error) { return volume.RunPrune(dockerCli, filter) } // RunImagePrune executes a prune command for images -func RunImagePrune(dockerCli *command.DockerCli, all bool, filter opts.FilterOpt) (uint64, string, error) { +func RunImagePrune(dockerCli command.Cli, all bool, filter opts.FilterOpt) (uint64, string, error) { return image.RunPrune(dockerCli, all, filter) } // RunNetworkPrune executes a prune command for networks -func RunNetworkPrune(dockerCli *command.DockerCli, filter opts.FilterOpt) (uint64, string, error) { +func RunNetworkPrune(dockerCli command.Cli, filter opts.FilterOpt) (uint64, string, error) { return network.RunPrune(dockerCli, filter) } diff --git a/cli/command/registry/login.go b/cli/command/registry/login.go index e7799ae746..aa508a6a8d 100644 --- a/cli/command/registry/login.go +++ b/cli/command/registry/login.go @@ -20,7 +20,7 @@ type loginOptions struct { } // NewLoginCommand creates a new `docker login` command -func NewLoginCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewLoginCommand(dockerCli command.Cli) *cobra.Command { var opts loginOptions cmd := &cobra.Command{ @@ -48,7 +48,7 @@ func NewLoginCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runLogin(dockerCli *command.DockerCli, opts loginOptions) error { +func runLogin(dockerCli command.Cli, opts loginOptions) error { ctx := context.Background() clnt := dockerCli.Client() diff --git a/cli/command/registry/logout.go b/cli/command/registry/logout.go index eba303acf0..d241df4cf0 100644 --- a/cli/command/registry/logout.go +++ b/cli/command/registry/logout.go @@ -12,7 +12,7 @@ import ( ) // NewLogoutCommand creates a new `docker logout` command -func NewLogoutCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewLogoutCommand(dockerCli command.Cli) *cobra.Command { cmd := &cobra.Command{ Use: "logout [SERVER]", Short: "Log out from a Docker registry", @@ -30,7 +30,7 @@ func NewLogoutCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runLogout(dockerCli *command.DockerCli, serverAddress string) error { +func runLogout(dockerCli command.Cli, serverAddress string) error { ctx := context.Background() var isDefaultRegistry bool diff --git a/cli/command/registry/search.go b/cli/command/registry/search.go index 131e4f73f1..fa0d75ab2c 100644 --- a/cli/command/registry/search.go +++ b/cli/command/registry/search.go @@ -30,7 +30,7 @@ type searchOptions struct { } // NewSearchCommand creates a new `docker search` command -func NewSearchCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewSearchCommand(dockerCli command.Cli) *cobra.Command { opts := searchOptions{filter: opts.NewFilterOpt()} cmd := &cobra.Command{ @@ -58,7 +58,7 @@ func NewSearchCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runSearch(dockerCli *command.DockerCli, opts searchOptions) error { +func runSearch(dockerCli command.Cli, opts searchOptions) error { indexInfo, err := registry.ParseSearchIndexInfo(opts.term) if err != nil { return err diff --git a/cli/command/secret/cmd.go b/cli/command/secret/cmd.go index a8f85e03cf..9f8e84345e 100644 --- a/cli/command/secret/cmd.go +++ b/cli/command/secret/cmd.go @@ -8,12 +8,13 @@ import ( ) // NewSecretCommand returns a cobra command for `secret` subcommands +// nolint: interfacer func NewSecretCommand(dockerCli *command.DockerCli) *cobra.Command { cmd := &cobra.Command{ Use: "secret", Short: "Manage Docker secrets", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), Tags: map[string]string{"version": "1.25"}, } cmd.AddCommand( diff --git a/cli/command/service/cmd.go b/cli/command/service/cmd.go index 1c2bc85803..94e3a97d4e 100644 --- a/cli/command/service/cmd.go +++ b/cli/command/service/cmd.go @@ -8,12 +8,13 @@ import ( ) // NewServiceCommand returns a cobra command for `service` subcommands +// nolint: interfacer func NewServiceCommand(dockerCli *command.DockerCli) *cobra.Command { cmd := &cobra.Command{ Use: "service", Short: "Manage services", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), Tags: map[string]string{"version": "1.24"}, } cmd.AddCommand( diff --git a/cli/command/service/opts.go b/cli/command/service/opts.go index ecc37d7b00..027c2081f6 100644 --- a/cli/command/service/opts.go +++ b/cli/command/service/opts.go @@ -593,7 +593,7 @@ func (opts *serviceOptions) ToStopGracePeriod(flags *pflag.FlagSet) *time.Durati return nil } -func (opts *serviceOptions) ToService(ctx context.Context, apiClient client.APIClient, flags *pflag.FlagSet) (swarm.ServiceSpec, error) { +func (opts *serviceOptions) ToService(ctx context.Context, apiClient client.NetworkAPIClient, flags *pflag.FlagSet) (swarm.ServiceSpec, error) { var service swarm.ServiceSpec envVariables, err := runconfigopts.ReadKVStrings(opts.envFile.GetAll(), opts.env.GetAll()) @@ -780,7 +780,8 @@ func addServiceFlags(flags *pflag.FlagSet, opts *serviceOptions, defaultFlagValu flags.StringVar(&opts.update.order, flagUpdateOrder, "", flagDesc(flagUpdateOrder, `Update order ("start-first"|"stop-first")`)) flags.SetAnnotation(flagUpdateOrder, "version", []string{"1.29"}) - flags.Uint64Var(&opts.rollback.parallelism, flagRollbackParallelism, defaultFlagValues.getUint64(flagRollbackParallelism), "Maximum number of tasks rolled back simultaneously (0 to roll back all at once)") + flags.Uint64Var(&opts.rollback.parallelism, flagRollbackParallelism, defaultFlagValues.getUint64(flagRollbackParallelism), + "Maximum number of tasks rolled back simultaneously (0 to roll back all at once)") flags.SetAnnotation(flagRollbackParallelism, "version", []string{"1.28"}) flags.DurationVar(&opts.rollback.delay, flagRollbackDelay, 0, flagDesc(flagRollbackDelay, "Delay between task rollbacks (ns|us|ms|s|m|h)")) flags.SetAnnotation(flagRollbackDelay, "version", []string{"1.28"}) diff --git a/cli/command/service/ps.go b/cli/command/service/ps.go index 624873815a..070f1db8ae 100644 --- a/cli/command/service/ps.go +++ b/cli/command/service/ps.go @@ -27,7 +27,7 @@ type psOptions struct { filter opts.FilterOpt } -func newPsCommand(dockerCli *command.DockerCli) *cobra.Command { +func newPsCommand(dockerCli command.Cli) *cobra.Command { opts := psOptions{filter: opts.NewFilterOpt()} cmd := &cobra.Command{ @@ -49,7 +49,7 @@ func newPsCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runPS(dockerCli *command.DockerCli, opts psOptions) error { +func runPS(dockerCli command.Cli, opts psOptions) error { client := dockerCli.Client() ctx := context.Background() diff --git a/cli/command/service/trust.go b/cli/command/service/trust.go index 8afe809049..650f0d95c0 100644 --- a/cli/command/service/trust.go +++ b/cli/command/service/trust.go @@ -15,7 +15,7 @@ import ( "golang.org/x/net/context" ) -func resolveServiceImageDigest(dockerCli *command.DockerCli, service *swarm.ServiceSpec) error { +func resolveServiceImageDigest(dockerCli command.Cli, service *swarm.ServiceSpec) error { if !command.IsTrusted() { // Digests are resolved by the daemon when not using content // trust. @@ -51,7 +51,7 @@ func resolveServiceImageDigest(dockerCli *command.DockerCli, service *swarm.Serv return nil } -func trustedResolveDigest(ctx context.Context, cli *command.DockerCli, ref reference.NamedTagged) (reference.Canonical, error) { +func trustedResolveDigest(ctx context.Context, cli command.Cli, ref reference.NamedTagged) (reference.Canonical, error) { repoInfo, err := registry.ParseRepositoryInfo(ref) if err != nil { return nil, err diff --git a/cli/command/service/update.go b/cli/command/service/update.go index bac8c29d2e..cb12d04262 100644 --- a/cli/command/service/update.go +++ b/cli/command/service/update.go @@ -213,7 +213,7 @@ func runUpdate(dockerCli *command.DockerCli, flags *pflag.FlagSet, opts *service } // nolint: gocyclo -func updateService(ctx context.Context, apiClient client.APIClient, flags *pflag.FlagSet, spec *swarm.ServiceSpec) error { +func updateService(ctx context.Context, apiClient client.NetworkAPIClient, flags *pflag.FlagSet, spec *swarm.ServiceSpec) error { updateString := func(flag string, field *string) { if flags.Changed(flag) { *field, _ = flags.GetString(flag) diff --git a/cli/command/stack/cmd.go b/cli/command/stack/cmd.go index 1a03be8f85..8d4281cfc6 100644 --- a/cli/command/stack/cmd.go +++ b/cli/command/stack/cmd.go @@ -7,12 +7,13 @@ import ( ) // NewStackCommand returns a cobra command for `stack` subcommands +// nolint: interfacer func NewStackCommand(dockerCli *command.DockerCli) *cobra.Command { cmd := &cobra.Command{ Use: "stack", Short: "Manage Docker stacks", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), Tags: map[string]string{"version": "1.25"}, } cmd.AddCommand( @@ -26,7 +27,7 @@ func NewStackCommand(dockerCli *command.DockerCli) *cobra.Command { } // NewTopLevelDeployCommand returns a command for `docker deploy` -func NewTopLevelDeployCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewTopLevelDeployCommand(dockerCli command.Cli) *cobra.Command { cmd := newDeployCommand(dockerCli) // Remove the aliases at the top level cmd.Aliases = []string{} diff --git a/cli/command/stack/deploy.go b/cli/command/stack/deploy.go index 5817e35c51..d18a43484d 100644 --- a/cli/command/stack/deploy.go +++ b/cli/command/stack/deploy.go @@ -24,7 +24,7 @@ type deployOptions struct { prune bool } -func newDeployCommand(dockerCli *command.DockerCli) *cobra.Command { +func newDeployCommand(dockerCli command.Cli) *cobra.Command { var opts deployOptions cmd := &cobra.Command{ @@ -47,7 +47,7 @@ func newDeployCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runDeploy(dockerCli *command.DockerCli, opts deployOptions) error { +func runDeploy(dockerCli command.Cli, opts deployOptions) error { ctx := context.Background() switch { @@ -66,7 +66,7 @@ func runDeploy(dockerCli *command.DockerCli, opts deployOptions) error { // a swarm manager. This is necessary because we must create networks before we // create services, but the API call for creating a network does not return a // proper status code when it can't create a network in the "global" scope. -func checkDaemonIsSwarmManager(ctx context.Context, dockerCli *command.DockerCli) error { +func checkDaemonIsSwarmManager(ctx context.Context, dockerCli command.Cli) error { info, err := dockerCli.Client().Info(ctx) if err != nil { return err diff --git a/cli/command/stack/deploy_bundlefile.go b/cli/command/stack/deploy_bundlefile.go index daf6ae5aeb..2f2a9aa042 100644 --- a/cli/command/stack/deploy_bundlefile.go +++ b/cli/command/stack/deploy_bundlefile.go @@ -9,7 +9,7 @@ import ( "github.com/docker/docker/api/types/swarm" ) -func deployBundle(ctx context.Context, dockerCli *command.DockerCli, opts deployOptions) error { +func deployBundle(ctx context.Context, dockerCli command.Cli, opts deployOptions) error { bundle, err := loadBundlefile(dockerCli.Err(), opts.namespace, opts.bundlefile) if err != nil { return err diff --git a/cli/command/stack/deploy_composefile.go b/cli/command/stack/deploy_composefile.go index 2aa5fe15d9..f574332646 100644 --- a/cli/command/stack/deploy_composefile.go +++ b/cli/command/stack/deploy_composefile.go @@ -20,7 +20,7 @@ import ( "golang.org/x/net/context" ) -func deployCompose(ctx context.Context, dockerCli *command.DockerCli, opts deployOptions) error { +func deployCompose(ctx context.Context, dockerCli command.Cli, opts deployOptions) error { configDetails, err := getConfigDetails(opts.composefile) if err != nil { return err @@ -161,7 +161,7 @@ func getConfigFile(filename string) (*composetypes.ConfigFile, error) { func validateExternalNetworks( ctx context.Context, - dockerCli *command.DockerCli, + dockerCli command.Cli, externalNetworks []string) error { client := dockerCli.Client() @@ -183,7 +183,7 @@ func validateExternalNetworks( func createSecrets( ctx context.Context, - dockerCli *command.DockerCli, + dockerCli command.Cli, namespace convert.Namespace, secrets []swarm.SecretSpec, ) error { @@ -210,7 +210,7 @@ func createSecrets( func createNetworks( ctx context.Context, - dockerCli *command.DockerCli, + dockerCli command.Cli, namespace convert.Namespace, networks map[string]types.NetworkCreate, ) error { @@ -247,7 +247,7 @@ func createNetworks( func deployServices( ctx context.Context, - dockerCli *command.DockerCli, + dockerCli command.Cli, services map[string]swarm.ServiceSpec, namespace convert.Namespace, sendAuth bool, diff --git a/cli/command/stack/ps.go b/cli/command/stack/ps.go index 45df793e80..c5a73d7c9d 100644 --- a/cli/command/stack/ps.go +++ b/cli/command/stack/ps.go @@ -24,7 +24,7 @@ type psOptions struct { format string } -func newPsCommand(dockerCli *command.DockerCli) *cobra.Command { +func newPsCommand(dockerCli command.Cli) *cobra.Command { opts := psOptions{filter: opts.NewFilterOpt()} cmd := &cobra.Command{ @@ -46,7 +46,7 @@ func newPsCommand(dockerCli *command.DockerCli) *cobra.Command { return cmd } -func runPS(dockerCli *command.DockerCli, opts psOptions) error { +func runPS(dockerCli command.Cli, opts psOptions) error { namespace := opts.namespace client := dockerCli.Client() ctx := context.Background() diff --git a/cli/command/swarm/cmd.go b/cli/command/swarm/cmd.go index 7943a8323a..07cb302c62 100644 --- a/cli/command/swarm/cmd.go +++ b/cli/command/swarm/cmd.go @@ -8,12 +8,13 @@ import ( ) // NewSwarmCommand returns a cobra command for `swarm` subcommands -func NewSwarmCommand(dockerCli *command.DockerCli) *cobra.Command { +// nolint: interfacer +func NewSwarmCommand(dockerCli command.Cli) *cobra.Command { cmd := &cobra.Command{ Use: "swarm", Short: "Manage Swarm", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), Tags: map[string]string{"version": "1.24"}, } cmd.AddCommand( diff --git a/cli/command/swarm/unlock_key.go b/cli/command/swarm/unlock_key.go index 3fd9d26f7f..870f8e4435 100644 --- a/cli/command/swarm/unlock_key.go +++ b/cli/command/swarm/unlock_key.go @@ -80,7 +80,10 @@ func runUnlockKey(dockerCli command.Cli, opts unlockKeyOptions) error { func printUnlockCommand(ctx context.Context, dockerCli command.Cli, unlockKey string) { if len(unlockKey) > 0 { - fmt.Fprintf(dockerCli.Out(), "To unlock a swarm manager after it restarts, run the `docker swarm unlock`\ncommand and provide the following key:\n\n %s\n\nPlease remember to store this key in a password manager, since without it you\nwill not be able to restart the manager.\n", unlockKey) + fmt.Fprintf(dockerCli.Out(), "To unlock a swarm manager after it restarts, "+ + "run the `docker swarm unlock`\ncommand and provide the following key:\n\n %s\n\n"+ + "Please remember to store this key in a password manager, since without it you\n"+ + "will not be able to restart the manager.\n", unlockKey) } return } diff --git a/cli/command/system/cmd.go b/cli/command/system/cmd.go index d7a47a8ee5..455387cd46 100644 --- a/cli/command/system/cmd.go +++ b/cli/command/system/cmd.go @@ -1,19 +1,19 @@ package system import ( - "github.com/spf13/cobra" - "github.com/docker/cli/cli" "github.com/docker/cli/cli/command" + "github.com/spf13/cobra" ) // NewSystemCommand returns a cobra command for `system` subcommands +// nolint: interfacer func NewSystemCommand(dockerCli *command.DockerCli) *cobra.Command { cmd := &cobra.Command{ Use: "system", Short: "Manage Docker", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), } cmd.AddCommand( NewEventsCommand(dockerCli), diff --git a/cli/command/system/info.go b/cli/command/system/info.go index c951e42eb7..a466ac92af 100644 --- a/cli/command/system/info.go +++ b/cli/command/system/info.go @@ -330,7 +330,9 @@ func printStorageDriverWarnings(dockerCli *command.DockerCli, info types.Info) { for _, pair := range info.DriverStatus { if pair[0] == "Data loop file" { - fmt.Fprintf(dockerCli.Err(), "WARNING: %s: usage of loopback devices is strongly discouraged for production use.\n Use `--storage-opt dm.thinpooldev` to specify a custom block storage device.\n", info.Driver) + fmt.Fprintf(dockerCli.Err(), "WARNING: %s: usage of loopback devices is "+ + "strongly discouraged for production use.\n "+ + "Use `--storage-opt dm.thinpooldev` to specify a custom block storage device.\n", info.Driver) } if pair[0] == "Supports d_type" && pair[1] == "false" { backingFs := getBackingFs(info) diff --git a/cli/command/system/prune.go b/cli/command/system/prune.go index 1a7898f4bf..dcc5d72217 100644 --- a/cli/command/system/prune.go +++ b/cli/command/system/prune.go @@ -18,7 +18,7 @@ type pruneOptions struct { } // NewPruneCommand creates a new cobra.Command for `docker prune` -func NewPruneCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewPruneCommand(dockerCli command.Cli) *cobra.Command { opts := pruneOptions{filter: opts.NewFilterOpt()} cmd := &cobra.Command{ @@ -51,7 +51,7 @@ Are you sure you want to continue?` allImageDesc = `- all images without at least one container associated to them` ) -func runPrune(dockerCli *command.DockerCli, options pruneOptions) error { +func runPrune(dockerCli command.Cli, options pruneOptions) error { var message string if options.all { @@ -66,7 +66,7 @@ func runPrune(dockerCli *command.DockerCli, options pruneOptions) error { var spaceReclaimed uint64 - for _, pruneFn := range []func(dockerCli *command.DockerCli, filter opts.FilterOpt) (uint64, string, error){ + for _, pruneFn := range []func(dockerCli command.Cli, filter opts.FilterOpt) (uint64, string, error){ prune.RunContainerPrune, prune.RunVolumePrune, prune.RunNetworkPrune, diff --git a/cli/command/utils.go b/cli/command/utils.go index 853fe11c78..3f4acaa2e9 100644 --- a/cli/command/utils.go +++ b/cli/command/utils.go @@ -69,7 +69,7 @@ func PrettyPrint(i interface{}) string { // the user input 'y' or 'Y' it returns true other false. If no // message is provided "Are you sure you want to proceed? [y/N] " // will be used instead. -func PromptForConfirmation(ins *InStream, outs *OutStream, message string) bool { +func PromptForConfirmation(ins io.Reader, outs io.Writer, message string) bool { if message == "" { message = "Are you sure you want to proceed?" } diff --git a/cli/command/volume/cmd.go b/cli/command/volume/cmd.go index 00e1a925b4..cf6e61dfb7 100644 --- a/cli/command/volume/cmd.go +++ b/cli/command/volume/cmd.go @@ -7,12 +7,12 @@ import ( ) // NewVolumeCommand returns a cobra command for `volume` subcommands -func NewVolumeCommand(dockerCli *command.DockerCli) *cobra.Command { +func NewVolumeCommand(dockerCli command.Cli) *cobra.Command { cmd := &cobra.Command{ Use: "volume COMMAND", Short: "Manage volumes", Args: cli.NoArgs, - RunE: dockerCli.ShowHelp, + RunE: command.ShowHelp(dockerCli.Err()), Tags: map[string]string{"version": "1.21"}, } cmd.AddCommand( diff --git a/cli/command/volume/prune.go b/cli/command/volume/prune.go index 7e33ef91dd..77a81b9284 100644 --- a/cli/command/volume/prune.go +++ b/cli/command/volume/prune.go @@ -73,6 +73,6 @@ func runPrune(dockerCli command.Cli, opts pruneOptions) (spaceReclaimed uint64, // RunPrune calls the Volume Prune API // This returns the amount of space reclaimed and a detailed output string -func RunPrune(dockerCli *command.DockerCli, filter opts.FilterOpt) (uint64, string, error) { +func RunPrune(dockerCli command.Cli, filter opts.FilterOpt) (uint64, string, error) { return runPrune(dockerCli, pruneOptions{force: true, filter: filter}) } diff --git a/cmd/docker/docker.go b/cmd/docker/docker.go index 0066137c0c..abc262e357 100644 --- a/cmd/docker/docker.go +++ b/cmd/docker/docker.go @@ -37,7 +37,7 @@ func newDockerCommand(dockerCli *command.DockerCli) *cobra.Command { showVersion() return nil } - return dockerCli.ShowHelp(cmd, args) + return command.ShowHelp(dockerCli.Err())(cmd, args) }, PersistentPreRunE: func(cmd *cobra.Command, args []string) error { // daemon command is special, we redirect directly to another binary diff --git a/dockerfiles/Dockerfile.ci b/dockerfiles/Dockerfile.ci index 0dd14ee192..d4185c9b22 100644 --- a/dockerfiles/Dockerfile.ci +++ b/dockerfiles/Dockerfile.ci @@ -23,5 +23,3 @@ COPY . /go/src/github.com/docker/cli ENV CGO_ENABLED=0 WORKDIR /go/src/github.com/docker/cli - -CMD ["make", "ci"] diff --git a/gometalinter.json b/gometalinter.json index 80d60b063f..f7c6a88a5d 100644 --- a/gometalinter.json +++ b/gometalinter.json @@ -1,5 +1,6 @@ { "Vendor": true, + "Deadline": "2m", "Sort": ["linter", "severity", "path"], "Exclude": ["cli/compose/schema/bindata.go"], @@ -11,8 +12,11 @@ "goimports", "golint", "ineffassign", + "interfacer", + "lll", "vet" ], - "Cyclo": 19 + "Cyclo": 19, + "LineLength": 200 }