sdafasdf
sdafasdf

Reputation: 561

Content type 'multipart/form-data;boundary=----...;charset=UTF-8' not supported

I want to send an object to the controller that has several lists with files and several fields with plain text.

public class ContributionNew<T extends MovieInfoDTO> {
    private List<T> elementsToAdd;
    private Map<Long, T> elementsToUpdate;
    private Set<Long> idsToDelete;
    private Set<String> sources;
    private String comment;
}

public class Photo extends MovieInfoDTO {
    private MultipartFile photo;
}

@PostMapping(value = "/{id}/contributions/photos")
@ResponseStatus(HttpStatus.CREATED)
public
ResponseEntity<Void> createPhotoContribution(
        @ApiParam(value = "The movie ID", required = true)
        @PathVariable("id") final Long id,
        @ApiParam(value = "The contribution", required = true)
        @RequestBody @Valid final ContributionNew<Photo> contribution
) {

I am sending data using postman. However, he throws me away

org.springframework.web.HttpMediaTypeNotSupportedException: Content type 'multipart/form-data;boundary=----WebKitFormBoundarywY7ByvgonAjDoaCT;charset=UTF-8' not supported

What should I set the Content-type for this controller so that I can send an object that has fields of plain text and lists with files?

If I set the header in the header

Content-type: multipart/form-data; charset=utf-8

it throws me in the console

org.apache.tomcat.util.http.fileupload.FileUploadException: the request was rejected because no multipart boundary was found

Upvotes: 56

Views: 164418

Answers (9)

soufiane ELAMMARI
soufiane ELAMMARI

Reputation: 1029

Hi Folks simply change : @RequestBody to @ModelAttribute

public ResponseEntity<DTO> exemple(@ModelAttribute DTO dto) throws TechnicalException

Happy coding.

Upvotes: 10

user16046173
user16046173

Reputation: 21

produces = { "application/json" } has to written in the controller instead of consumes = { "application/json" }

Upvotes: 2

Jack
Jack

Reputation: 121

Here's a full code sample written in Kotlin using Spring Boot 2.1.7

Example uses a ProfileRepository that would be something you implement of course.

Kotlin is nice, because the data class implements serializable already.

Take note, that you have to use var not val for the model objects properties otherwise the field values will be null in the log message.

import org.springframework.web.bind.annotation.ModelAttribute
import org.springframework.web.bind.annotation.PostMapping
import org.springframework.web.bind.annotation.RestController
import org.springframework.web.multipart.MultipartFile

@RestController
class ExampleController(private val myProfileRepository: ProfileRepository) {
    
    @PostMapping("/api/uploadFile")
    fun createProvider(@ModelAttribute request: CreateProfileRequest): Provider {
        println("received create request with photo: ${request.photo} for the following person ${request.name}")
        return myProfileRepository.save(Provider(name = request.name!!))
    }
}

data class CreateProfileRequest(
    var name: String? = null,
    var photo: MultipartFile? = null
)

Upvotes: 1

Shadab Reza
Shadab Reza

Reputation: 105

Instead of @RequestBody, use @RequestParam!

Upvotes: 9

Mukund Lalge
Mukund Lalge

Reputation: 51

import org.springframework.web.bind.annotation.ModelAttribute;

Use @ModelAttribute instead of @RequestBody. It worked for me.

Upvotes: 5

plue
plue

Reputation: 517

In Postman, you need to set the body to be of type raw, and from the drop down you can select JSON, I had a similar issue, this fixed my issue.

view screen here

Upvotes: 36

tushar
tushar

Reputation: 69

use @ModelAttribute instead of @ResponseBody as this takes up data in key value pairs and the later is used for an object like, json. While hitting the api simply pass the multipart type and json key value pairs of the object. It works fine!

stack overflow question on this

Upvotes: 4

Chirag Shah
Chirag Shah

Reputation: 373

Instead of @RequestBody, use @ModelAttribute like,

@PostMapping(value = "/{id}/contributions/photos")
@ResponseStatus(HttpStatus.CREATED)
public
ResponseEntity<Void> createPhotoContribution(
        @ApiParam(value = "The movie ID", required = true)
        @PathVariable("id") final Long id,
        @ApiParam(value = "The contribution", required = true)
        @ModelAttribute @Valid final ContributionNew<Photo> contribution
) {

Upvotes: 3

uncleBounty
uncleBounty

Reputation: 773

As said dknight @RequestBody means use of JSON or XML data with maps your DTO bean. In case of MultipartFile you can't use JSON data so you can't use @RequestBody. Try with @ModelAttribute annotation.

Working sample :

@PostMapping("/promoters")
@Timed
public ResponseEntity<PromoterDTO> createPromoter(@ModelAttribute PromoterDTO promoterDTO) throws URISyntaxException { ... }

With PromoterDTO like this :

    public class PromoterDTO implements Serializable {

        private Long id; 

        private String name;

        private String address;

        private MultipartFile logo;
    }

Upvotes: 67

Related Questions