将 byte[] 转换为 MultipartFile

1、概览

MutlipartFile 是 Spring 提供的一个接口,用于接收 multipart 请求中的文件参数。Spring 没有为其提供任何默认实现,但提供了一个用于测试的实现。

在本教程中,我们将学习如何将字节数组转换为 MultipartFile

2、实现 MultipartFile 接口

让我们创建自己的 MultipartFile 接口实现,并封装传入的字节数组:

public class CustomMultipartFile implements MultipartFile {

    private byte[] input;

    @Override
    public String getName() {
        return null;
    }

    @Override
    public String getOriginalFilename() {
        return null;
    }

    @Override
    public String getContentType() {
        return null;
    }

    // 下一个代码段中定义了接口的其他方法
}

我们在类中定义了一个 byte[] 属性,存储传入的字节数组。接口中定义的其他几个描述性方法,可以根据需求来实现。这里默认返回 null

剩余的几个接口方法是必须要实现的,如下:

public class CustomMultipartFile implements MultipartFile {

    // 前一段儿代码省略...

    @Override
    public boolean isEmpty() {
        return input == null || input.length == 0;
    }

    @Override
    public long getSize() {
        return input.length;
    }

    @Override
    public byte[] getBytes() throws IOException {
        return input;
    }

    @Override
    public InputStream getInputStream() throws IOException {
        return new ByteArrayInputStream(input);
    }

    @Override
    public void transferTo(File destination) throws IOException, IllegalStateException {
        try(FileOutputStream fos = new FileOutputStream(destination)) {
            fos.write(input);
        }
    }
}

这些方法除了 transferTo 外可能不需要任何自定义逻辑。有几种不同的方法可以实现 transferTo(File destination) 方法。下面我们就来看看其中几种:

使用 Java NIO:

@Override
public void transferTo(File destination) throws IOException, IllegalStateException {
    Path path = Paths.get(destination.getPath());
    Files.write(path, input);
}

另一种方法是在 POM 中添加 Apache commons IO 依赖,并使用 FileUtils 类:

@Override
public void transferTo(File destination) throws IOException, IllegalStateException {
    FileUtils.writeByteArrayToFile(destination, input);
}

transferTo(File destination) 方法可以非常方便地可以把 MultipartFile 写入到本地文件(File)。

现在我们已经定义了我们的类,让我们用一个小测试用例来测试一下这个实现:

@Test
void whenProvidingByteArray_thenMultipartFileCreated() throws IOException {
    byte[] inputArray = "Test String".getBytes();
    CustomMultipartFile customMultipartFile = new CustomMultipartFile(inputArray);
    Assertions.assertFalse(customMultipartFile.isEmpty());
    Assertions.assertArrayEquals(inputArray, customMultipartFile.getBytes());
    Assertions.assertEquals(inputArray.length,customMultipartFile.getSize());
}

在上面的测试用例中,我们已经成功地将字节数组转换为 MultipartFile 实例。

2.1、完整实现

import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;

import org.springframework.web.multipart.MultipartFile;

public class CustomMultipartFile implements MultipartFile {

    private byte[] input;

    public CustomMultipartFile(byte[] input) {
        super();
        this.input = input;
    }

    @Override
    public String getName() {
        return null;
    }

    @Override
    public String getOriginalFilename() {
        return null;
    }

    @Override
    public String getContentType() {
        return null;
    }

    @Override
    public boolean isEmpty() {
        return input == null || input.length == 0;
    }

    @Override
    public long getSize() {
        return input.length;
    }

    @Override
    public byte[] getBytes() throws IOException {
        return input;
    }

    @Override
    public InputStream getInputStream() throws IOException {
        return new ByteArrayInputStream(input);
    }

    @Override
    public void transferTo(File destination) throws IOException, IllegalStateException {
        try (FileOutputStream fos = new FileOutputStream(destination)) {
            fos.write(input);
        }
    }
}

3、MockMultipartFile

Spring 提供了开箱即用的 MockMultipartFile,用于测试 Multipart 请求。

让我们创建一个测试,了解如何使用:

@Test
void whenProvidingByteArray_thenMockMultipartFileCreated() throws IOException {
    byte[] inputArray = "Test String".getBytes();
    MockMultipartFile mockMultipartFile = new MockMultipartFile("tempFileName",inputArray);
    Assertions.assertFalse(mockMultipartFile.isEmpty());
    Assertions.assertArrayEquals(inputArray, mockMultipartFile.getBytes());
    Assertions.assertEquals(inputArray.length,mockMultipartFile.getSize());
}

成功使用 Spring 提供的 MockMultipartFile 将字节数组转换为 MultipartFile 对象。

4、总结

在本教程中,我们介绍了如何将字节数组转换为 MultipartFile 对象。


参考:https://www.baeldung.com/java-convert-byte-array-to-multipartfile