web-dev-qa-db-fra.com

Spring Controller @RequestBody avec téléchargement de fichier est-ce possible?

J'ai un contrôleur comme celui-ci et je souhaite soumettre un formulaire avec téléchargement de fichier, ainsi que des données de formulaire telles que label, comme indiqué ci-dessous. De plus, je souhaite utiliser @RequestBody pour pouvoir utiliser l'annotation @Valid sur le wrapper, car davantage de variables seront ajoutées.

public @ResponseBody WebResponse<Boolean> updateEUSettings(
    final Locale locale,
    @Validated @ModelAttribute final EUPSettingsWrapper endUserPortalSettingsWrapper) {
}

Et mon emballage est:

public class EUPSettingsWrapper {

    private String label;
    private MultipartFile logo;
// getter , setters..etc...
}

Mais je voudrais le convertir en @RequestBody à partir de ModelAttributes. 

J'essaie de le faire en séparant le téléchargement du fichier en tant que paramètre de requête comme ceci:

public @ResponseBody WebResponse<Boolean> updateEUSettings(
    final Locale locale,
    @Validated @RequestBody final EUPSettingsWrapper endUserPortalSettingsWrapper, 
    @RequestParam(value = "file1", required = true) final MultipartFile logo) {

    endUserPortalSettingsWrapper.setLogo(logo);

    // ...
}

Dans mon simulacre de MVC, je pose:

getMockMvc().perform(fileUpload(uri).file(logo)
                        .accept(MediaType.APPLICATION_JSON)
                        .content(JSONUtils.toJSON(wrapper))
                        .contentType(MediaType.MULTIPART_FORM_DATA))
                        .andExpect(status().isOk());

Mais je reçois une erreur comme celle-ci qui dit:

org.springframework.web.HttpMediaTypeNotSupportedException: Content type 'multipart/form-data' not supported

Quelqu'un at-il une bonne idée de la manière dont le téléchargement de fichiers multipart peut être utilisé avec @RequestBody? Quelque chose que je fais mal ci-dessus?

27
Yatin

Veuillez ajouter le bean suivant dans votre spring-servlet.xml pour ajouter le support pour la demande multipart.

<bean id="multipartResolver"
    class="org.springframework.web.multipart.commons.CommonsMultipartResolver" />

N'oubliez pas non plus d'ajouter la dépendance pour jar commons-fileupload

11
Ankur Jain

Je ne pouvais pas trouver un moyen d'utiliser @RequestBody.

Cependant, vous pouvez faire quelque chose comme ça:

@RequestMapping(value = "/uploadStuff", method = RequestMethod.POST)
public MyViewDto doStuff(@RequestPart("json") @Valid MyDto dto,
                         @RequestPart("file") MultipartFile file) { ... }

Vous pouvez le tester comme ceci:

MockMultipartFile jsonFile = new MockMultipartFile("json", "",
            "application/json", "{}".getBytes());
MockMultipartFile dataFile = new MockMultipartFile("file", "foo.Zip", "application/octet-stream", bytes);

mockMvc.perform(fileUpload("/uploadStuff")
            .file(dataFile)
            .file(jsonFile))
            .andExpect(status().isOk());
4
hookumsnivy

Pour le printemps 4 et les versions ultérieures, vous pouvez procéder comme suit pour obtenir l'objet complet:

public ResponseEntity<Object> upload(@Payload EUPSettingsWrapper wrapper) {

}

Remarque: devrait également fonctionner sans la balise

public ResponseEntity<Object> upload(EUPSettingsWrapper wrapper) {

}
0
Jason Glez