My learning diary

File Upload to Spring Boot

Implementing file uploads through GraphQL was something I never managed to succeed in. Got embroiled in type incompatibilities. And eventually, I gave up and implemented a separate but simple API endpoint just for file uploads.

So here’s the design: The user clicks “Submit”. The files get uploaded first. Upon upload, the server returns IDs. And the rest of the form data plus the returned IDs are sent to the GraphQL endpoint.

This is how the backend controller looks like:

@RestController
@RequestMapping("/")
public class MyFileController {
    ...

    @PostMapping("/upload")
    public MyResponse upload(@RequestParam("files") final MultipartFile[] files) {
        // TODO: Create an empty list to house file IDs.
        for (final MultipartFile file : files) {
            try {
                // Get file content with file.getBytes(). This may throw an exception.
                // Get filename with file.getOriginalFilename().
                // TODO: Add file data to db.
            } catch (final IOException e) {
                // TODO: Log the error
            }
        }
        return MyResponse.builder().build(); // TODO: Populate this with file IDs
    }
}

And this is how you send files over from the frontend:

const upload = async (files: File[]) => {
    const formData = new FormData();
    for (let i = 0; i < files.length; i++) {
        formData.append('files', files[i]);
    }
    return await axios.post<MyResponseDefinedInTS>('/upload', formData);
};

File is defined by TypeScript and it is equivalent to File in JavaScript (Stack Overflow).

Relevant posts