From 1f9b90cdbe62d32d8f1f6b4e7bd9dbd35d4d474c Mon Sep 17 00:00:00 2001 From: Vijay Kesanakurthi Date: Tue, 8 Oct 2024 12:03:08 +0530 Subject: [PATCH] fix: Copy with trailing slash at destination. --- internal/action/copy.go | 31 +++++++++++++++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/internal/action/copy.go b/internal/action/copy.go index 6af584715e..c50c40439c 100644 --- a/internal/action/copy.go +++ b/internal/action/copy.go @@ -3,6 +3,8 @@ package action import ( "context" "fmt" + "path/filepath" + "strings" "github.com/gopasspw/gopass/internal/action/exit" "github.com/gopasspw/gopass/pkg/ctxutil" @@ -30,6 +32,35 @@ func (s *Action) copy(ctx context.Context, from, to string, force bool) error { return exit.Error(exit.NotFound, nil, "%s does not exist", from) } + isSourceDir := s.Store.IsDir(ctx, from) + hasTrailingSlash := strings.HasSuffix(to, "/") + + if isSourceDir && hasTrailingSlash { + return s.copyFlattenDir(ctx, from, to, force) + } + + return s.copyRegular(ctx, from, to, force) +} + +func (s *Action) copyFlattenDir(ctx context.Context, from, to string, force bool) error { + entries, err := s.Store.List(ctx, 0) + if err != nil { + return exit.Error(exit.List, err, "failed to list entries in %q", from) + } + + for _, entry := range entries { + fromPath := filepath.Join(from, entry) + toPath := filepath.Join(to, filepath.Base(entry)) + + if err := s.copyRegular(ctx, fromPath, toPath, force); err != nil { + return err + } + } + + return nil +} + +func (s *Action) copyRegular(ctx context.Context, from, to string, force bool) error { if !force { if s.Store.Exists(ctx, to) && !termio.AskForConfirmation(ctx, fmt.Sprintf("%s already exists. Overwrite it?", to)) { return exit.Error(exit.Aborted, nil, "not overwriting your current secret")