Skip to content

Commit 9e52e9f

Browse files
author
Ulysses Souza
authored
Merge pull request docker#9004 from ndeloof/cp_stopped
compose cp doesn't need a full project and can copy from stopped containers
2 parents cf7319f + c5b7624 commit 9e52e9f

File tree

5 files changed

+21
-20
lines changed

5 files changed

+21
-20
lines changed

cmd/compose/cp.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -73,12 +73,12 @@ func copyCommand(p *projectOptions, backend api.Service) *cobra.Command {
7373
}
7474

7575
func runCopy(ctx context.Context, backend api.Service, opts copyOptions) error {
76-
projects, err := opts.toProject(nil)
76+
name, err := opts.toProjectName()
7777
if err != nil {
7878
return err
7979
}
8080

81-
return backend.Copy(ctx, projects, api.CopyOptions{
81+
return backend.Copy(ctx, name, api.CopyOptions{
8282
Source: opts.source,
8383
Destination: opts.destination,
8484
All: opts.all,

pkg/api/api.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ type Service interface {
6363
// Exec executes a command in a running service container
6464
Exec(ctx context.Context, project string, opts RunOptions) (int, error)
6565
// Copy copies a file/folder between a service container and the local filesystem
66-
Copy(ctx context.Context, project *types.Project, opts CopyOptions) error
66+
Copy(ctx context.Context, project string, options CopyOptions) error
6767
// Pause executes the equivalent to a `compose pause`
6868
Pause(ctx context.Context, project string, options PauseOptions) error
6969
// UnPause executes the equivalent to a `compose unpause`

pkg/api/proxy.go

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ type ServiceProxy struct {
4141
RunOneOffContainerFn func(ctx context.Context, project *types.Project, opts RunOptions) (int, error)
4242
RemoveFn func(ctx context.Context, project *types.Project, options RemoveOptions) error
4343
ExecFn func(ctx context.Context, project string, opts RunOptions) (int, error)
44-
CopyFn func(ctx context.Context, project *types.Project, opts CopyOptions) error
44+
CopyFn func(ctx context.Context, project string, options CopyOptions) error
4545
PauseFn func(ctx context.Context, project string, options PauseOptions) error
4646
UnPauseFn func(ctx context.Context, project string, options PauseOptions) error
4747
TopFn func(ctx context.Context, projectName string, services []string) ([]ContainerProcSummary, error)
@@ -269,13 +269,10 @@ func (s *ServiceProxy) Exec(ctx context.Context, project string, options RunOpti
269269
}
270270

271271
// Copy implements Service interface
272-
func (s *ServiceProxy) Copy(ctx context.Context, project *types.Project, options CopyOptions) error {
272+
func (s *ServiceProxy) Copy(ctx context.Context, project string, options CopyOptions) error {
273273
if s.CopyFn == nil {
274274
return ErrNotImplemented
275275
}
276-
for _, i := range s.interceptors {
277-
i(ctx, project)
278-
}
279276
return s.CopyFn(ctx, project, options)
280277
}
281278

pkg/compose/containers.go

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ package compose
1919
import (
2020
"context"
2121
"sort"
22+
"strconv"
2223

2324
moby "github.com/docker/docker/api/types"
2425
"github.com/docker/docker/api/types/filters"
@@ -86,6 +87,14 @@ func isNotOneOff(c moby.Container) bool {
8687
return !ok || v == "False"
8788
}
8889

90+
func indexed(index int) containerPredicate {
91+
return func(c moby.Container) bool {
92+
number := c.Labels[api.ContainerNumberLabel]
93+
idx, err := strconv.Atoi(number)
94+
return err == nil && index == idx
95+
}
96+
}
97+
8998
// filter return Containers with elements to match predicate
9099
func (containers Containers) filter(predicate containerPredicate) Containers {
91100
var filtered Containers

pkg/compose/cp.go

Lines changed: 7 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -26,11 +26,9 @@ import (
2626

2727
"golang.org/x/sync/errgroup"
2828

29-
"github.com/compose-spec/compose-go/types"
3029
"github.com/docker/cli/cli/command"
3130
"github.com/docker/compose/v2/pkg/api"
3231
moby "github.com/docker/docker/api/types"
33-
"github.com/docker/docker/api/types/filters"
3432
"github.com/docker/docker/pkg/archive"
3533
"github.com/docker/docker/pkg/system"
3634
"github.com/pkg/errors"
@@ -44,7 +42,7 @@ const (
4442
acrossServices = fromService | toService
4543
)
4644

47-
func (s *composeService) Copy(ctx context.Context, project *types.Project, opts api.CopyOptions) error {
45+
func (s *composeService) Copy(ctx context.Context, project string, opts api.CopyOptions) error {
4846
srcService, srcPath := splitCpArg(opts.Source)
4947
destService, dstPath := splitCpArg(opts.Destination)
5048

@@ -64,20 +62,17 @@ func (s *composeService) Copy(ctx context.Context, project *types.Project, opts
6462
serviceName = destService
6563
}
6664

67-
f := filters.NewArgs(
68-
projectFilter(project.Name),
69-
serviceFilter(serviceName),
70-
)
71-
if !opts.All {
72-
f.Add("label", fmt.Sprintf("%s=%d", api.ContainerNumberLabel, opts.Index))
73-
}
74-
containers, err := s.apiClient.ContainerList(ctx, moby.ContainerListOptions{Filters: f})
65+
containers, err := s.getContainers(ctx, project, oneOffExclude, true, serviceName)
7566
if err != nil {
7667
return err
7768
}
7869

7970
if len(containers) < 1 {
80-
return fmt.Errorf("service %s not running", serviceName)
71+
return fmt.Errorf("no container found for service %q", serviceName)
72+
}
73+
74+
if !opts.All {
75+
containers = containers.filter(indexed(opts.Index))
8176
}
8277

8378
g := errgroup.Group{}

0 commit comments

Comments
 (0)