introduce pull --missing flag to only pull images not present in cache

Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>
This commit is contained in:
Nicolas De Loof 2023-09-07 16:36:22 +02:00 committed by Nicolas De loof
parent 8af49ff369
commit a697a0690a
10 changed files with 147 additions and 60 deletions

View File

@ -72,8 +72,8 @@ func createCommand(p *ProjectOptions, dockerCli command.Cli, backend api.Service
}
flags := cmd.Flags()
flags.BoolVar(&opts.Build, "build", false, "Build images before starting containers.")
flags.BoolVar(&opts.noBuild, "no-build", false, "Don't build an image, even if it's missing.")
flags.StringVar(&opts.Pull, "pull", "missing", `Pull image before running ("always"|"missing"|"never")`)
flags.BoolVar(&opts.noBuild, "no-build", false, "Don't build an image, even if it's policy.")
flags.StringVar(&opts.Pull, "pull", "policy", `Pull image before running ("always"|"policy"|"never")`)
flags.BoolVar(&opts.forceRecreate, "force-recreate", false, "Recreate containers even if their configuration and image haven't changed.")
flags.BoolVar(&opts.noRecreate, "no-recreate", false, "If containers already exist, don't recreate them. Incompatible with --force-recreate.")
flags.BoolVar(&opts.removeOrphans, "remove-orphans", false, "Remove containers for services not defined in the Compose file.")
@ -145,7 +145,7 @@ func (opts createOptions) Apply(project *types.Project) error {
}
// N.B. opts.Build means "force build all", but images can still be built
// when this is false
// e.g. if a service has pull_policy: build or its local image is missing
// e.g. if a service has pull_policy: build or its local image is policy
if opts.Build {
for i, service := range project.Services {
if service.Build == nil {

View File

@ -38,6 +38,7 @@ type pullOptions struct {
includeDeps bool
ignorePullFailures bool
noBuildable bool
policy string
}
func pullCommand(p *ProjectOptions, dockerCli command.Cli, backend api.Service) *cobra.Command {
@ -67,20 +68,39 @@ func pullCommand(p *ProjectOptions, dockerCli command.Cli, backend api.Service)
flags.MarkHidden("no-parallel") //nolint:errcheck
cmd.Flags().BoolVar(&opts.ignorePullFailures, "ignore-pull-failures", false, "Pull what it can and ignores images with pull failures.")
cmd.Flags().BoolVar(&opts.noBuildable, "ignore-buildable", false, "Ignore images that can be built.")
cmd.Flags().StringVar(&opts.policy, "policy", "", `Apply pull policy ("missing"|"always").`)
return cmd
}
func (opts pullOptions) apply(project *types.Project, services []string) error {
if !opts.includeDeps {
err := project.ForServices(services, types.IgnoreDependencies)
if err != nil {
return err
}
}
if opts.policy != "" {
for i, service := range project.Services {
if service.Image == "" {
continue
}
service.PullPolicy = opts.policy
project.Services[i] = service
}
}
return nil
}
func runPull(ctx context.Context, dockerCli command.Cli, backend api.Service, opts pullOptions, services []string) error {
project, err := opts.ToProject(dockerCli, services)
if err != nil {
return err
}
if !opts.includeDeps {
err := project.ForServices(services, types.IgnoreDependencies)
if err != nil {
return err
}
err = opts.apply(project, services)
if err != nil {
return err
}
return backend.Pull(ctx, project, api.PullOptions{

View File

@ -0,0 +1,57 @@
/*
Copyright 2023 Docker Compose CLI authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package compose
import (
"testing"
"github.com/compose-spec/compose-go/types"
"gotest.tools/v3/assert"
)
func TestApplyPullOptions(t *testing.T) {
project := &types.Project{
Services: []types.ServiceConfig{
{
Name: "must-build",
// No image, local build only
Build: &types.BuildConfig{
Context: ".",
},
},
{
Name: "has-build",
Image: "registry.example.com/myservice",
Build: &types.BuildConfig{
Context: ".",
},
},
{
Name: "must-pull",
Image: "registry.example.com/another-service",
},
},
}
err := pullOptions{
policy: types.PullPolicyMissing,
}.apply(project, nil)
assert.NilError(t, err)
assert.Equal(t, project.Services[0].PullPolicy, "") // still default
assert.Equal(t, project.Services[1].PullPolicy, types.PullPolicyMissing)
assert.Equal(t, project.Services[2].PullPolicy, types.PullPolicyMissing)
}

View File

@ -101,8 +101,8 @@ func upCommand(p *ProjectOptions, dockerCli command.Cli, backend api.Service) *c
flags := upCmd.Flags()
flags.BoolVarP(&up.Detach, "detach", "d", false, "Detached mode: Run containers in the background")
flags.BoolVar(&create.Build, "build", false, "Build images before starting containers.")
flags.BoolVar(&create.noBuild, "no-build", false, "Don't build an image, even if it's missing.")
flags.StringVar(&create.Pull, "pull", "missing", `Pull image before running ("always"|"missing"|"never")`)
flags.BoolVar(&create.noBuild, "no-build", false, "Don't build an image, even if it's policy.")
flags.StringVar(&create.Pull, "pull", "policy", `Pull image before running ("always"|"policy"|"never")`)
flags.BoolVar(&create.removeOrphans, "remove-orphans", false, "Remove containers for services not defined in the Compose file.")
flags.StringArrayVar(&create.scale, "scale", []string{}, "Scale SERVICE to NUM instances. Overrides the `scale` setting in the Compose file if present.")
flags.BoolVar(&up.noColor, "no-color", false, "Produce monochrome output.")

View File

@ -5,16 +5,16 @@ Creates containers for a service.
### Options
| Name | Type | Default | Description |
|:-------------------|:--------------|:----------|:----------------------------------------------------------------------------------------------|
| `--build` | | | Build images before starting containers. |
| `--dry-run` | | | Execute command in dry run mode |
| `--force-recreate` | | | Recreate containers even if their configuration and image haven't changed. |
| `--no-build` | | | Don't build an image, even if it's missing. |
| `--no-recreate` | | | If containers already exist, don't recreate them. Incompatible with --force-recreate. |
| `--pull` | `string` | `missing` | Pull image before running ("always"\|"missing"\|"never") |
| `--remove-orphans` | | | Remove containers for services not defined in the Compose file. |
| `--scale` | `stringArray` | | Scale SERVICE to NUM instances. Overrides the `scale` setting in the Compose file if present. |
| Name | Type | Default | Description |
|:-------------------|:--------------|:---------|:----------------------------------------------------------------------------------------------|
| `--build` | | | Build images before starting containers. |
| `--dry-run` | | | Execute command in dry run mode |
| `--force-recreate` | | | Recreate containers even if their configuration and image haven't changed. |
| `--no-build` | | | Don't build an image, even if it's policy. |
| `--no-recreate` | | | If containers already exist, don't recreate them. Incompatible with --force-recreate. |
| `--pull` | `string` | `policy` | Pull image before running ("always"\|"policy"\|"never") |
| `--remove-orphans` | | | Remove containers for services not defined in the Compose file. |
| `--scale` | `stringArray` | | Scale SERVICE to NUM instances. Overrides the `scale` setting in the Compose file if present. |
<!---MARKER_GEN_END-->

View File

@ -5,13 +5,14 @@ Pull service images
### Options
| Name | Type | Default | Description |
|:-------------------------|:-----|:--------|:--------------------------------------------------------|
| `--dry-run` | | | Execute command in dry run mode |
| `--ignore-buildable` | | | Ignore images that can be built. |
| `--ignore-pull-failures` | | | Pull what it can and ignores images with pull failures. |
| `--include-deps` | | | Also pull services declared as dependencies. |
| `-q`, `--quiet` | | | Pull without printing progress information. |
| Name | Type | Default | Description |
|:-------------------------|:---------|:--------|:--------------------------------------------------------|
| `--dry-run` | | | Execute command in dry run mode |
| `--ignore-buildable` | | | Ignore images that can be built. |
| `--ignore-pull-failures` | | | Pull what it can and ignores images with pull failures. |
| `--include-deps` | | | Also pull services declared as dependencies. |
| `--policy` | `string` | | Apply pull policy ("missing"\|"always"). |
| `-q`, `--quiet` | | | Pull without printing progress information. |
<!---MARKER_GEN_END-->

View File

@ -5,33 +5,33 @@ Create and start containers
### Options
| Name | Type | Default | Description |
|:-----------------------------|:--------------|:----------|:---------------------------------------------------------------------------------------------------------|
| `--abort-on-container-exit` | | | Stops all containers if any container was stopped. Incompatible with -d |
| `--always-recreate-deps` | | | Recreate dependent containers. Incompatible with --no-recreate. |
| `--attach` | `stringArray` | | Restrict attaching to the specified services. Incompatible with --attach-dependencies. |
| `--attach-dependencies` | | | Automatically attach to log output of dependent services. |
| `--build` | | | Build images before starting containers. |
| `-d`, `--detach` | | | Detached mode: Run containers in the background |
| `--dry-run` | | | Execute command in dry run mode |
| `--exit-code-from` | `string` | | Return the exit code of the selected service container. Implies --abort-on-container-exit |
| `--force-recreate` | | | Recreate containers even if their configuration and image haven't changed. |
| `--no-attach` | `stringArray` | | Do not attach (stream logs) to the specified services. |
| `--no-build` | | | Don't build an image, even if it's missing. |
| `--no-color` | | | Produce monochrome output. |
| `--no-deps` | | | Don't start linked services. |
| `--no-log-prefix` | | | Don't print prefix in logs. |
| `--no-recreate` | | | If containers already exist, don't recreate them. Incompatible with --force-recreate. |
| `--no-start` | | | Don't start the services after creating them. |
| `--pull` | `string` | `missing` | Pull image before running ("always"\|"missing"\|"never") |
| `--quiet-pull` | | | Pull without printing progress information. |
| `--remove-orphans` | | | Remove containers for services not defined in the Compose file. |
| `-V`, `--renew-anon-volumes` | | | Recreate anonymous volumes instead of retrieving data from the previous containers. |
| `--scale` | `stringArray` | | Scale SERVICE to NUM instances. Overrides the `scale` setting in the Compose file if present. |
| `-t`, `--timeout` | `int` | `0` | Use this timeout in seconds for container shutdown when attached or when containers are already running. |
| `--timestamps` | | | Show timestamps. |
| `--wait` | | | Wait for services to be running\|healthy. Implies detached mode. |
| `--wait-timeout` | `int` | `0` | Maximum duration to wait for the project to be running\|healthy. |
| Name | Type | Default | Description |
|:-----------------------------|:--------------|:---------|:---------------------------------------------------------------------------------------------------------|
| `--abort-on-container-exit` | | | Stops all containers if any container was stopped. Incompatible with -d |
| `--always-recreate-deps` | | | Recreate dependent containers. Incompatible with --no-recreate. |
| `--attach` | `stringArray` | | Restrict attaching to the specified services. Incompatible with --attach-dependencies. |
| `--attach-dependencies` | | | Automatically attach to log output of dependent services. |
| `--build` | | | Build images before starting containers. |
| `-d`, `--detach` | | | Detached mode: Run containers in the background |
| `--dry-run` | | | Execute command in dry run mode |
| `--exit-code-from` | `string` | | Return the exit code of the selected service container. Implies --abort-on-container-exit |
| `--force-recreate` | | | Recreate containers even if their configuration and image haven't changed. |
| `--no-attach` | `stringArray` | | Do not attach (stream logs) to the specified services. |
| `--no-build` | | | Don't build an image, even if it's policy. |
| `--no-color` | | | Produce monochrome output. |
| `--no-deps` | | | Don't start linked services. |
| `--no-log-prefix` | | | Don't print prefix in logs. |
| `--no-recreate` | | | If containers already exist, don't recreate them. Incompatible with --force-recreate. |
| `--no-start` | | | Don't start the services after creating them. |
| `--pull` | `string` | `policy` | Pull image before running ("always"\|"policy"\|"never") |
| `--quiet-pull` | | | Pull without printing progress information. |
| `--remove-orphans` | | | Remove containers for services not defined in the Compose file. |
| `-V`, `--renew-anon-volumes` | | | Recreate anonymous volumes instead of retrieving data from the previous containers. |
| `--scale` | `stringArray` | | Scale SERVICE to NUM instances. Overrides the `scale` setting in the Compose file if present. |
| `-t`, `--timeout` | `int` | `0` | Use this timeout in seconds for container shutdown when attached or when containers are already running. |
| `--timestamps` | | | Show timestamps. |
| `--wait` | | | Wait for services to be running\|healthy. Implies detached mode. |
| `--wait-timeout` | `int` | `0` | Maximum duration to wait for the project to be running\|healthy. |
<!---MARKER_GEN_END-->

View File

@ -29,7 +29,7 @@ options:
- option: no-build
value_type: bool
default_value: "false"
description: Don't build an image, even if it's missing.
description: Don't build an image, even if it's policy.
deprecated: false
hidden: false
experimental: false
@ -49,8 +49,8 @@ options:
swarm: false
- option: pull
value_type: string
default_value: missing
description: Pull image before running ("always"|"missing"|"never")
default_value: policy
description: Pull image before running ("always"|"policy"|"never")
deprecated: false
hidden: false
experimental: false

View File

@ -57,6 +57,15 @@ options:
experimentalcli: false
kubernetes: false
swarm: false
- option: policy
value_type: string
description: Apply pull policy ("missing"|"always").
deprecated: false
hidden: false
experimental: false
experimentalcli: false
kubernetes: false
swarm: false
- option: quiet
shorthand: q
value_type: bool

View File

@ -121,7 +121,7 @@ options:
- option: no-build
value_type: bool
default_value: "false"
description: Don't build an image, even if it's missing.
description: Don't build an image, even if it's policy.
deprecated: false
hidden: false
experimental: false
@ -181,8 +181,8 @@ options:
swarm: false
- option: pull
value_type: string
default_value: missing
description: Pull image before running ("always"|"missing"|"never")
default_value: policy
description: Pull image before running ("always"|"policy"|"never")
deprecated: false
hidden: false
experimental: false