github.com/docker/app@v0.9.1-beta3.0.20210611140623-a48f773ab002/internal/commands/update.go (about)

     1  package commands
     2  
     3  import (
     4  	"fmt"
     5  	"os"
     6  
     7  	"github.com/deislabs/cnab-go/driver"
     8  
     9  	"github.com/deislabs/cnab-go/action"
    10  	"github.com/deislabs/cnab-go/credentials"
    11  	"github.com/docker/app/internal/bundle"
    12  	"github.com/docker/app/internal/cliopts"
    13  	"github.com/docker/app/internal/cnab"
    14  	"github.com/docker/app/internal/packager"
    15  	"github.com/docker/cli/cli/command"
    16  	"github.com/spf13/cobra"
    17  )
    18  
    19  type updateOptions struct {
    20  	cliopts.ParametersOptions
    21  	credentialOptions
    22  	bundleOrDockerApp string
    23  }
    24  
    25  func updateCmd(dockerCli command.Cli, installerContext *cliopts.InstallerContextOptions) *cobra.Command {
    26  	var opts updateOptions
    27  	cmd := &cobra.Command{
    28  		Use:     "update [OPTIONS] RUNNING_APP",
    29  		Short:   "Update a running App",
    30  		Example: `$ docker app update myrunningapp --set key=value`,
    31  		Args:    cobra.ExactArgs(1),
    32  		RunE: func(cmd *cobra.Command, args []string) error {
    33  			return runUpdate(dockerCli, args[0], opts, installerContext)
    34  		},
    35  	}
    36  	opts.ParametersOptions.AddFlags(cmd.Flags())
    37  	opts.credentialOptions.addFlags(cmd.Flags())
    38  	cmd.Flags().StringVar(&opts.bundleOrDockerApp, "image", "", "Override the running App with another App image")
    39  
    40  	return cmd
    41  }
    42  
    43  func runUpdate(dockerCli command.Cli, installationName string, opts updateOptions, installerContext *cliopts.InstallerContextOptions) error {
    44  	imageStore, installationStore, credentialStore, err := prepareStores(dockerCli.CurrentContext())
    45  	if err != nil {
    46  		return err
    47  	}
    48  
    49  	installation, err := installationStore.Read(installationName)
    50  	if err != nil {
    51  		return err
    52  	}
    53  
    54  	if IsInstallationFailed(installation) {
    55  		return fmt.Errorf("Running App %q cannot be updated, please use 'docker app run' instead", installationName)
    56  	}
    57  
    58  	if opts.bundleOrDockerApp != "" {
    59  		b, _, err := cnab.ResolveBundle(dockerCli, imageStore, opts.bundleOrDockerApp)
    60  		if err != nil {
    61  			return err
    62  		}
    63  		installation.Bundle = b.Bundle
    64  	}
    65  	if err := packager.CheckAppVersion(dockerCli.Err(), installation.Bundle); err != nil {
    66  		return err
    67  	}
    68  
    69  	if err := bundle.MergeBundleParameters(installation,
    70  		bundle.WithFileParameters(opts.ParametersFiles),
    71  		bundle.WithCommandLineParameters(opts.Overrides),
    72  		bundle.WithSendRegistryAuth(opts.sendRegistryAuth),
    73  	); err != nil {
    74  		return err
    75  	}
    76  
    77  	defer muteDockerCli(dockerCli)()
    78  	driverImpl, errBuf, err := cnab.SetupDriver(installation, dockerCli, installerContext, os.Stdout)
    79  	if err != nil {
    80  		return err
    81  	}
    82  	creds, err := prepareCredentialSet(installation.Bundle, opts.CredentialSetOpts(dockerCli, credentialStore)...)
    83  	if err != nil {
    84  		return err
    85  	}
    86  	if err := credentials.Validate(creds, installation.Bundle.Credentials); err != nil {
    87  		return err
    88  	}
    89  	u := &action.Upgrade{
    90  		Driver: driverImpl,
    91  	}
    92  	cfgFunc := func(op *driver.Operation) error {
    93  		op.Out = dockerCli.Out()
    94  		return nil
    95  	}
    96  	err = u.Run(&installation.Claim, creds, cfgFunc, cnab.WithRelocationMap(installation))
    97  	err2 := installationStore.Store(installation)
    98  	if err != nil {
    99  		return fmt.Errorf("Update failed: %s\n%s", err, errBuf)
   100  	}
   101  	if err2 != nil {
   102  		return err2
   103  	}
   104  	fmt.Fprintf(dockerCli.Out(), "Running App %q updated on context %q\n", installationName, dockerCli.CurrentContext())
   105  	return nil
   106  }