Repository: netty/netty (Java)

Issue:
MixedFileUpload does not always create DiskFileUpload under the specified baseDir
### Expected behavior

`MixedFileUpload` should always used the specified `baseDir` to create `DiskFileUpload`.

### Actual behavior

If the `DiskFileUpload` is created in the `MixedFileUpload` constructor then `basedDire` & `deleteOnExit` parameters are not taken into account and so created the default ones, i.e `DiskFileUpload.baseDirectory` & `DiskFileUpload.deleteOnExitTemporaryFile`:

```java
    public MixedFileUpload(String name, String filename, String contentType,
            String contentTransferEncoding, Charset charset, long size,
            long limitSize, String baseDir, boolean deleteOnExit) {
        this.limitSize = limitSize;
        if (size > this.limitSize) {
            fileUpload = new DiskFileUpload(name, filename, contentType,
                    contentTransferEncoding, charset, size);
        } else {
            fileUpload = new MemoryFileUpload(name, filename, contentType,
                    contentTransferEncoding, charset, size);
        }
        definedSize = size;
        this.baseDir = baseDir;
        this.deleteOnExit = deleteOnExit;
    }
```

However if the `DiskFileUpload` is created later through `addContent` method then these parameters are correctly passed to the `DiskFileUpload` constructor:

```java
    @Override
    public void addContent(ByteBuf buffer, boolean last)
            throws IOException {
        if (fileUpload instanceof MemoryFileUpload) {
            try {
                checkSize(fileUpload.length() + buffer.readableBytes());
                if (fileUpload.length() + buffer.readableBytes() > limitSize) {
                    DiskFileUpload diskFileUpload = new DiskFileUpload(fileUpload
                            .getName(), fileUpload.getFilename(), fileUpload
                            .getContentType(), fileUpload
                            .getContentTransferEncoding(), fileUpload.getCharset(),
                            definedSize, baseDir, deleteOnExit);
                    diskFileUpload.setMaxSize(maxSize);
                    ByteBuf data = fileUpload.getByteBuf();
                    if (data != null && data.isReadable()) {
                        diskFileUpload.addContent(data.retain(), false);
                    }
                    // release old upload
                    fileUpload.release();

                    fileUpload = diskFileUpload;
                }
            } catch (IOException e) {
                buffer.release();
                throw e;
            }
        }
        fileUpload.addContent(buffer, last);
    }
```

### Steps to reproduce

Create a `MixedFileUpload` with `size > limitSize` while specifying a `baseDir`.

### Minimal yet complete reproducer code (or URL to code)

```java
import static java.nio.charset.StandardCharsets.UTF_8;

import io.netty.buffer.Unpooled;
import io.netty.handler.codec.http.multipart.DiskFileUpload;
import io.netty.handler.codec.http.multipart.MixedFileUpload;
import java.io.IOException;
import java.nio.file.Files;
import java.util.Arrays;

class MixedFileUploadBug {
  public static void main(String[] args) throws IOException {
    var defaultDirectory = Files.createTempDirectory(null);
    DiskFileUpload.baseDirectory = defaultDirectory.toString();

    var specifiedDirectory = Files.createTempDirectory(null);
    var mixedFileUpload =
        new MixedFileUpload(
            "name",
            "filename",
            "contentType",
            "contentTransferEncoding",
            UTF_8,
            100,
            10,
            specifiedDirectory.toString(),
            true);
    mixedFileUpload.addContent(Unpooled.wrappedBuffer(new byte[100]), true);

    System.out.printf("defaultDirectory: %s%n", Arrays.toString(defaultDirectory.toFile().list()));
    System.out.printf(
        "specifiedDirectory: %s%n", Arrays.toString(specifiedDirectory.toFile().list()));
  }
}
```

Ouput:

```
defaultDirectory: [FUp_9153067335013617885_upload]
specifiedDirectory: []
```


### Netty version

`4.1.77.Final`

### JVM version (e.g. `java -version`)

```
❯ java -version
openjdk version "17.0.5" 2022-10-18 LTS
OpenJDK Runtime Environment Zulu17.38+21-CA (build 17.0.5+8-LTS)
OpenJDK 64-Bit Server VM Zulu17.38+21-CA (build 17.0.5+8-LTS, mixed mode, sharing)
```

### OS version (e.g. `uname -a`)

```
❯ uname -a
Darwin COMP-RTYGPQ9CDC 21.6.0 Darwin Kernel Version 21.6.0: Sun Nov  6 23:31:13 PST 2022; root:xnu-8020.240.14~1/RELEASE_ARM64_T6000 arm64 arm Darwin
```



Hints:
Interested in doing a PR?
Yes definitely, I should be able to push a PR in the following days

Patch:
diff --git a/codec-http/src/main/java/io/netty/handler/codec/http/multipart/MixedFileUpload.java b/codec-http/src/main/java/io/netty/handler/codec/http/multipart/MixedFileUpload.java
--- a/codec-http/src/main/java/io/netty/handler/codec/http/multipart/MixedFileUpload.java
+++ b/codec-http/src/main/java/io/netty/handler/codec/http/multipart/MixedFileUpload.java
@@ -25,20 +25,21 @@
 public class MixedFileUpload extends AbstractMixedHttpData<FileUpload> implements FileUpload {
 
     public MixedFileUpload(String name, String filename, String contentType,
-            String contentTransferEncoding, Charset charset, long size,
-            long limitSize) {
+                           String contentTransferEncoding, Charset charset, long size,
+                           long limitSize) {
         this(name, filename, contentType, contentTransferEncoding,
-                charset, size, limitSize, DiskFileUpload.baseDirectory, DiskFileUpload.deleteOnExitTemporaryFile);
+             charset, size, limitSize, DiskFileUpload.baseDirectory, DiskFileUpload.deleteOnExitTemporaryFile);
     }
 
     public MixedFileUpload(String name, String filename, String contentType,
-            String contentTransferEncoding, Charset charset, long size,
-            long limitSize, String baseDir, boolean deleteOnExit) {
+                           String contentTransferEncoding, Charset charset, long size,
+                           long limitSize, String baseDir, boolean deleteOnExit) {
         super(limitSize, baseDir, deleteOnExit,
-                size > limitSize ?
-                        new DiskFileUpload(name, filename, contentType, contentTransferEncoding, charset, size) :
-                        new MemoryFileUpload(name, filename, contentType, contentTransferEncoding, charset, size)
-                );
+              size > limitSize?
+                      new DiskFileUpload(name, filename, contentType, contentTransferEncoding, charset, size, baseDir,
+                                         deleteOnExit) :
+                      new MemoryFileUpload(name, filename, contentType, contentTransferEncoding, charset, size)
+        );
     }
 
     @Override


Test patch:
diff --git a/codec-http/src/test/java/io/netty/handler/codec/http/multipart/MixedTest.java b/codec-http/src/test/java/io/netty/handler/codec/http/multipart/MixedTest.java
--- a/codec-http/src/test/java/io/netty/handler/codec/http/multipart/MixedTest.java
+++ b/codec-http/src/test/java/io/netty/handler/codec/http/multipart/MixedTest.java
@@ -20,8 +20,12 @@
 import org.junit.jupiter.api.Assertions;
 import org.junit.jupiter.api.Test;
 
+import java.io.File;
 import java.io.IOException;
 
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
 public class MixedTest {
     @Test
     public void mixedAttributeRefCnt() throws IOException {
@@ -54,4 +58,19 @@ public void mixedFileUploadRefCnt() throws IOException {
 
         upload.release(2);
     }
+
+    @Test
+    public void testSpecificCustomBaseDir() throws IOException {
+        File baseDir = new File("target/MixedTest/testSpecificCustomBaseDir");
+        baseDir.mkdirs(); // we don't need to clean it since it is in volatile files anyway
+        MixedFileUpload upload = new MixedFileUpload("foo", "foo", "foo", "UTF-8", CharsetUtil.UTF_8, 1000, 100,
+                                                     baseDir.getAbsolutePath(), true);
+
+        upload.addContent(Unpooled.wrappedBuffer(new byte[1000]), true);
+
+        assertTrue(upload.getFile().getAbsolutePath().startsWith(baseDir.getAbsolutePath()));
+        assertTrue(upload.getFile().exists());
+        assertEquals(1000, upload.getFile().length());
+        upload.delete();
+    }
 }