This is a follow-up to7609dde8d0and3f5b1bdd32, which removed support for DCT for build and plugin commands. As these flags are just stubs, hidden by default and no longer functional, they don't have to reflect the current state of DCT. Signed-off-by: Sebastiaan van Stijn <github@gone.nl>
101 lines
3.1 KiB
Go
101 lines
3.1 KiB
Go
package plugin
|
|
|
|
import (
|
|
"context"
|
|
"errors"
|
|
"fmt"
|
|
|
|
"github.com/distribution/reference"
|
|
"github.com/docker/cli/cli"
|
|
"github.com/docker/cli/cli/command"
|
|
"github.com/docker/cli/internal/jsonstream"
|
|
"github.com/docker/cli/internal/prompt"
|
|
"github.com/spf13/cobra"
|
|
)
|
|
|
|
func newUpgradeCommand(dockerCLI command.Cli) *cobra.Command {
|
|
var options pluginOptions
|
|
cmd := &cobra.Command{
|
|
Use: "upgrade [OPTIONS] PLUGIN [REMOTE]",
|
|
Short: "Upgrade an existing plugin",
|
|
Args: cli.RequiresRangeArgs(1, 2),
|
|
RunE: func(cmd *cobra.Command, args []string) error {
|
|
options.localName = args[0]
|
|
if len(args) == 2 {
|
|
options.remote = args[1]
|
|
}
|
|
return runUpgrade(cmd.Context(), dockerCLI, options)
|
|
},
|
|
Annotations: map[string]string{"version": "1.26"},
|
|
ValidArgsFunction: completeNames(dockerCLI, stateAny), // TODO(thaJeztah): should only complete for the first arg
|
|
DisableFlagsInUseLine: true,
|
|
}
|
|
|
|
flags := cmd.Flags()
|
|
flags.BoolVar(&options.grantPerms, "grant-all-permissions", false, "Grant all permissions necessary to run the plugin")
|
|
flags.Bool("disable-content-trust", true, "Skip image verification (deprecated)")
|
|
_ = flags.MarkHidden("disable-content-trust")
|
|
flags.BoolVar(&options.skipRemoteCheck, "skip-remote-check", false, "Do not check if specified remote plugin matches existing plugin image")
|
|
return cmd
|
|
}
|
|
|
|
func runUpgrade(ctx context.Context, dockerCLI command.Cli, opts pluginOptions) error {
|
|
p, _, err := dockerCLI.Client().PluginInspectWithRaw(ctx, opts.localName)
|
|
if err != nil {
|
|
return fmt.Errorf("error reading plugin data: %w", err)
|
|
}
|
|
|
|
if p.Enabled {
|
|
return errors.New("the plugin must be disabled before upgrading")
|
|
}
|
|
|
|
opts.localName = p.Name
|
|
if opts.remote == "" {
|
|
opts.remote = p.PluginReference
|
|
}
|
|
remote, err := reference.ParseNormalizedNamed(opts.remote)
|
|
if err != nil {
|
|
return fmt.Errorf("error parsing remote upgrade image reference: %w", err)
|
|
}
|
|
remote = reference.TagNameOnly(remote)
|
|
|
|
old, err := reference.ParseNormalizedNamed(p.PluginReference)
|
|
if err != nil {
|
|
return fmt.Errorf("error parsing current image reference: %w", err)
|
|
}
|
|
old = reference.TagNameOnly(old)
|
|
|
|
_, _ = fmt.Fprintf(dockerCLI.Out(), "Upgrading plugin %s from %s to %s\n", p.Name, reference.FamiliarString(old), reference.FamiliarString(remote))
|
|
if !opts.skipRemoteCheck && remote.String() != old.String() {
|
|
r, err := prompt.Confirm(ctx, dockerCLI.In(), dockerCLI.Out(), "Plugin images do not match, are you sure?")
|
|
if err != nil {
|
|
return err
|
|
}
|
|
if !r {
|
|
return cancelledErr{errors.New("plugin upgrade has been cancelled")}
|
|
}
|
|
}
|
|
|
|
options, err := buildPullConfig(dockerCLI, opts)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
responseBody, err := dockerCLI.Client().PluginUpgrade(ctx, opts.localName, options)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
defer func() {
|
|
_ = responseBody.Close()
|
|
}()
|
|
if err := jsonstream.Display(ctx, responseBody, dockerCLI.Out()); err != nil {
|
|
return err
|
|
}
|
|
_, _ = fmt.Fprintf(dockerCLI.Out(), "Upgraded plugin %s to %s\n", opts.localName, opts.remote) // todo: return proper values from the API for this result
|
|
return nil
|
|
}
|
|
|
|
type cancelledErr struct{ error }
|
|
|
|
func (cancelledErr) Cancelled() {}
|