Repository: minio/minio (language: go)

Issue:
Number of empty folders inside .minio.sys/multipart is growing up constantly 
Number of empty folders inside .minio.sys/multipart is growing up constantly 

## Context

I'm using minio to store files with a very short life-time  (~1 minute )

Files are uploaded using the multipart API  and removed after a short time (~1 minute )

I'm using rusoto_s3 as S3 client (https://github.com/rusoto/rusoto)
```
S3Client::create_multipart_upload()
S3Client::upload_part()
S3Client::complete_multipart_upload()
...
S3Client::delete_object()
```

All files are uploaded correctly

However the number of folders in .minio.sys/multipart is growing up and up. 
All the folders are empty.
After running it for few days, millions of folders are created and the system is slowing down.

## Your Environment

Minio RELEASE.2023-05-18T00-05-36Z with the following docker compose
Docker version 23.0.3,

```
  minio:
    image: quay.io/minio/minio:RELEASE.2023-05-18T00-05-36Z 
    restart: always
    command: server --console-address ":9001" /data
    ports:
      - 9002:9000
      - 9001:9001
    healthcheck:
      test:
        [
          "CMD",
          "curl",
          "-f",
          "http://localhost:9002/minio/health/live"
        ]
      interval: 30s
      timeout: 20s
      retries: 3
    volumes:
      - minio-data:/data
```




Discussion / hints:
> However the number of folders in .minio.sys/multipart is growing up and up.
> All the folders are empty.
> After running it for few days, millions of folders are created and the system is slowing down.

This should have been fixed, let me check locally. 

Fix patch:
diff --git a/cmd/erasure-multipart.go b/cmd/erasure-multipart.go
index 8cca0dc6ebd77..b940673a38183 100644
--- a/cmd/erasure-multipart.go
+++ b/cmd/erasure-multipart.go
@@ -198,7 +198,7 @@ func (er erasureObjects) cleanupStaleUploadsOnDisk(ctx context.Context, disk Sto
 	diskPath := disk.Endpoint().Path
 
 	readDirFn(pathJoin(diskPath, minioMetaMultipartBucket), func(shaDir string, typ os.FileMode) error {
-		return readDirFn(pathJoin(diskPath, minioMetaMultipartBucket, shaDir), func(uploadIDDir string, typ os.FileMode) error {
+		readDirFn(pathJoin(diskPath, minioMetaMultipartBucket, shaDir), func(uploadIDDir string, typ os.FileMode) error {
 			uploadIDPath := pathJoin(shaDir, uploadIDDir)
 			fi, err := disk.ReadVersion(ctx, minioMetaMultipartBucket, uploadIDPath, "", false)
 			if err != nil {
@@ -209,19 +209,20 @@ func (er erasureObjects) cleanupStaleUploadsOnDisk(ctx context.Context, disk Sto
 				removeAll(pathJoin(diskPath, minioMetaMultipartBucket, uploadIDPath))
 			}
 			wait()
-			vi, err := disk.StatVol(ctx, pathJoin(minioMetaMultipartBucket, shaDir))
-			if err != nil {
-				return nil
-			}
-			wait = deletedCleanupSleeper.Timer(ctx)
-			if now.Sub(vi.Created) > expiry {
-				// We are not deleting shaDir recursively here, if shaDir is empty
-				// and its older then we can happily delete it.
-				Remove(pathJoin(diskPath, minioMetaMultipartBucket, shaDir))
-			}
-			wait()
 			return nil
 		})
+		vi, err := disk.StatVol(ctx, pathJoin(minioMetaMultipartBucket, shaDir))
+		if err != nil {
+			return nil
+		}
+		wait := deletedCleanupSleeper.Timer(ctx)
+		if now.Sub(vi.Created) > expiry {
+			// We are not deleting shaDir recursively here, if shaDir is empty
+			// and its older then we can happily delete it.
+			Remove(pathJoin(diskPath, minioMetaMultipartBucket, shaDir))
+		}
+		wait()
+		return nil
 	})
 
 	readDirFn(pathJoin(diskPath, minioMetaTmpBucket), func(tmpDir string, typ os.FileMode) error {


Test patch: