diff --git a/pkg/storage/s3/checker.go b/pkg/storage/s3/checker.go index 2851baee..6fee5a03 100644 --- a/pkg/storage/s3/checker.go +++ b/pkg/storage/s3/checker.go @@ -8,6 +8,7 @@ import ( "github.com/aws/aws-sdk-go/service/s3" "github.com/gomods/athens/pkg/config" "github.com/gomods/athens/pkg/errors" + "github.com/gomods/athens/pkg/log" "github.com/gomods/athens/pkg/observ" ) @@ -22,25 +23,24 @@ func (s *Storage) Exists(ctx context.Context, module, version string) (bool, err Bucket: aws.String(s.bucket), Prefix: aws.String(fmt.Sprintf("%s/@v", module)), } - var count int + found := make(map[string]struct{}, 3) err := s.s3API.ListObjectsPagesWithContext(ctx, lsParams, func(loo *s3.ListObjectsOutput, lastPage bool) bool { for _, o := range loo.Contents { - // sane assumption: no duplicate keys. - switch *o.Key { - case config.PackageVersionedName(module, version, "info"): - count++ - case config.PackageVersionedName(module, version, "mod"): - count++ - case config.PackageVersionedName(module, version, "zip"): - count++ + if _, exists := found[*o.Key]; exists { + log.EntryFromContext(ctx).Warnf("duplicate key in prefix %q: %q", *lsParams.Prefix, *o.Key) + continue + } + if *o.Key == config.PackageVersionedName(module, version, "info") || + *o.Key == config.PackageVersionedName(module, version, "mod") || + *o.Key == config.PackageVersionedName(module, version, "zip") { + found[*o.Key] = struct{}{} } } - return count != 3 + return len(found) < 3 }) if err != nil { return false, errors.E(op, err, errors.M(module), errors.V(version)) } - - return count == 3, nil + return len(found) == 3, nil }