Current request is not a multipart request Spring Boot and Postman (Uploading json file plus extra field)

喜夏-厌秋 提交于 2021-02-11 17:58:39

问题


I'm getting this Current request is not a multipart request error when trying to upload a json file and an extra id or dto object for my request, since this is also required to populate my database.

When I am sending only the json file, everything is being uploaded fine, but now I've added the id field to the related methods and Postman, I'm getting this message and struggling to debug and fix it, if I can get any help please.

These are the pieces involved:

@Controller
@RequestMapping("/api/gatling-tool/json")
public class StatsJsonController {

@Autowired
StatsJsonService fileService;

@PostMapping(value = "/import")
public ResponseEntity<ResponseMessage> uploadFile(@RequestParam("file") MultipartFile file, @RequestBody CategoryQueryDto categoryQueryDto) {
    String message = "";

    UUID id = categoryQueryDto.getId();

    if (StatsJsonHelper.hasJsonFormat(file)) {
        try {
            fileService.save(file, id);

            message = "Uploaded the file successfully: " + file.getOriginalFilename();
            return ResponseEntity.status(HttpStatus.OK).body(new ResponseMessage(message));
        } catch (Exception e) {
            message = "Could not upload the file: " + file.getOriginalFilename() + "!";
            return ResponseEntity.status(HttpStatus.EXPECTATION_FAILED).body(new ResponseMessage(message));
        }
    }

    message = "Please upload a json file!";
    return ResponseEntity.status(HttpStatus.BAD_REQUEST).body(new ResponseMessage(message));
}

}




@Service
public class StatsJsonService {

@Autowired
StatsJsonRepository repository;

public void save(MultipartFile file, UUID id) {
    StatsEntity statsEntity = StatsJsonHelper.jsonToStats(file, id);
    repository.save(statsEntity);
}

}


public class StatsJsonHelper {

public static String TYPE = "application/json";

public static boolean hasJsonFormat(MultipartFile file) {

    if (!TYPE.equals(file.getContentType())) {
        return false;
    }

    return true;
}

public static StatsEntity jsonToStats(MultipartFile file, UUID id) {

    try {
        Gson gson = new Gson();

        File myFile = convertMultiPartToFile(file);

        BufferedReader br = new BufferedReader(new FileReader(myFile));

        Stats stats = gson.fromJson(br, Stats.class);
         StatsEntity statsEntity = new StatsEntity();
        
        statsEntity.setGroup1Count(stats.stats.group1.count);
        statsEntity.setGroup1Name(stats.stats.group1.name);
        statsEntity.setGroup1Percentage(stats.stats.group1.percentage);


        statsEntity.setId(id);

        return statsEntity;

    } catch (IOException e) {
        throw new RuntimeException("fail to parse json file: " + e.getMessage());
    }
}

Thank you very much.

https://github.com/francislainy/gatling_tool_backend/pull/3/files

UPDATE

Added changes as per @dextertron's answers (getting a 415 unsupported media type error)

@PostMapping(value = "/import")
public ResponseEntity<ResponseMessage> uploadFile(@RequestParam("file") MultipartFile file, @RequestBody CategoryQueryDto categoryQueryDto) {

The same error persists even if I change this part from application/json to multiform/data as well.

public static String TYPE = "multiform/data";

回答1:


I tried with couple of combinations in controller.

The one Worked for me looks something like this. Basically we will have to pass both arguments as @RequestParam.

    @PostMapping("/import")
    public ResponseEntity<Object> uploadFile(@RequestParam("file") MultipartFile file, @RequestParam String id) {
        return null;
    }

I know you wanted to pass CategoryQueryDto as @RequestBody But it seems in multipart request @RequestParam and @RequestBody doesn't seem to work together.

So you IMO you can do 2 things here :-

  1. Design the controller as above and just send the id as string in request and use that in fileService.save(file, id); directly.

  2. If you still want to use CategoryQueryDto you can send this {"id":"adbshdb"} and then convert it to CategoryQueryDto using object mapper.

This is how your controller will look like -

    @PostMapping("/import")
    public ResponseEntity<Object> uploadFile(@RequestParam("file") MultipartFile file, @RequestParam String categoryQueryDtoString) throws JsonProcessingException {
        ObjectMapper objectMapper = new ObjectMapper();
        CategoryQueryDto categoryQueryDto = objectMapper.readValue(categoryQueryDtoString, CategoryQueryDto.class);
// Do your file related stuff
        return ResponseEntity.ok().body(file.getOriginalFilename());
    }

And this is how you can send request using postman/ARC -

PS: Dont forget to set Content-Type header like so -




回答2:


First, you need to set the Content-Type headers to be "multipart/form-data", then as the second parameter in form-data use "categoryQueryDto" as key and add json as value ({'id': 'whatever'}).

After that change annotation for parameters from @RequestPart/@RequestBody to @RequestParam in your controller.




回答3:


Posting another solution that I experimented with which was to append the id to the path for the call.

@PostMapping(value = "/import/{id}", produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<ResponseMessage> uploadFile(@RequestParam("file") MultipartFile file, @PathVariable(value = "id") UUID id) {
    String message = "";

    if (StatsJsonHelper.hasJsonFormat(file)) {
        try {
            fileService.save(file, id);

            message = "Uploaded the file successfully: " + file.getOriginalFilename();
            return ResponseEntity.status(HttpStatus.OK).body(new ResponseMessage(message));
        } catch (Exception e) {
            message = "Could not upload the file: " + file.getOriginalFilename() + "!";
            return ResponseEntity.status(HttpStatus.EXPECTATION_FAILED).body(new ResponseMessage(message));
        }
    }

    message = "Please upload a json file!";
    return ResponseEntity.status(HttpStatus.BAD_REQUEST).body(new ResponseMessage(message));
}


来源:https://stackoverflow.com/questions/64158746/current-request-is-not-a-multipart-request-spring-boot-and-postman-uploading-js

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!