0

I am using springboot and rabbitmq to queue requests which will then be processed later by the receiver. The MQ sender works perfectly when we send any object, however it is throwing the below exception when a HTTP request is being tried to get queued.

org.springframework.amqp.support.converter.MessageConversionException: Failed to convert Message content
    at org.springframework.amqp.support.converter.AbstractJackson2MessageConverter.createMessage(AbstractJackson2MessageConverter.java:463)
    at org.springframework.amqp.support.converter.AbstractMessageConverter.toMessage(AbstractMessageConverter.java:70)
    at org.springframework.amqp.support.converter.AbstractMessageConverter.toMessage(AbstractMessageConverter.java:58)
    at org.springframework.amqp.rabbit.core.RabbitTemplate.convertMessageIfNecessary(RabbitTemplate.java:1831)
    at org.springframework.amqp.rabbit.core.RabbitTemplate.convertAndSend(RabbitTemplate.java:1137)
    at org.springframework.amqp.rabbit.core.RabbitTemplate.convertAndSend(RabbitTemplate.java:1130)

Conversion exception occurs while writing HTTP request as JSON to the MQ.

How can we push a HTTP request as such to the MQ, so that I can use it to identify tenant/security/headers while processing the request from the queue.

The MQ Config, exchange, queue and binding are fine for normal objects. It is having this conversion exceptions for the HttpServletRequest type alone.

Controller and send method as follows:

@PostMapping("/createRequestQueue")
public ResponseEntity<String> pushRequesttoQueue(HttpServletRequest request) {
    try {
        rabbitMQSender.send(request);
    }catch (Exception ex){
        ex.printStackTrace();
    }
    return ResponseEntity.ok("Request received successfully");
}
public void send(HttpServletRequest request) {
    try {
        rabbitTemplate.convertAndSend(exchange, engRoutingkey, request);
    }catch(Exception ex) {
        ex.printStackTrace();
    }
}

Below is the code of the receiver service trying to make a Rest Template POST call to another service in our application. The called service runs in a seperate docker container. However, it is currently being tried locally.

@RabbitListener(queues = "${spring.rabbitmq.requestqueue}")
public void receivedMessage(RequestDTO requestDto) {
    logger.info("Request Received is.. " + requestDto.getFileName());
    logger.debug("baseUrl to access file-service: " + baseUrl);

    HttpHeaders headers = new HttpHeaders();
    headers.setAccept(Arrays.asList(MediaType.APPLICATION_JSON));
    headers.setContentType(MediaType.APPLICATION_JSON);
    headers.add("X-Tenant-Identifier",requestDto.getTenantId());
    String accessToken = requestDto.getAccessToken();
    headers.set("Authorization", "Bearer " + accessToken);

    if (logic) {
        String url = baseUrl+"/processFile";
        HttpEntity<RequestDTO> requestEntity = new HttpEntity<>(requestDto, headers);
        ResponseEntity<ResponseDTO> resp = restTemplate.postForEntity(baseUrl, requestEntity, ResponseDTO.class);
        logger.debug("Response:"+resp);
        if (resp.getStatusCode() != HttpStatus.OK) {
            logger.debug("Error occurred processing request:" + requestDto.getFileName());
        }
    }
}

1 Answers1

1

That's not correct. The HttpServletRequest is a servlet container entity and really very tied with that container and it ends its life cycle when you return control back to the container with that ResponseEntity.

You have to look into a way to convert this request to some data object carrying on body and headers from that HTTP request.

Artem Bilan
  • 113,505
  • 11
  • 91
  • 118
  • Thanks for the info. Actually tried carrying that data to an object from MQ sender and then used it to do a RestTemplate POST call to the actual service/methods to be executed as needed - from the receiver. However I am getting 302 redirect error, though the same POST call works fine when done outside a MQ receiver service. Can't we make RestTemplate calls inside a MQ receiver method? – Jaighanesh S Nov 17 '22 at 14:46
  • Sure we can! But that's fully different story and deserves its own SO thread. With more details how you perform that `RestTemplate` call and what you provide as arguments. – Artem Bilan Nov 17 '22 at 14:54
  • Have edited the original question with the snippet of how the rest call is being tried. I am getting a 302 response as below: 2022-11-17 16:41:09 - i.b.a.e.service.RabbitMQReceiver - Response:<302,[Location:"http://localhost:9100/file-services/", Transfer-Encoding:"chunked", Date:"Thu, 17 Nov 2022 11:11:06 GMT", Keep-Alive:"timeout=60", Connection:"keep-alive"]> – Jaighanesh S Nov 17 '22 at 15:04
  • As I said: this has nothing to do with RabbitMQ: https://stackoverflow.com/questions/973098/what-does-http-1-1-302-mean-exactly. See if you are missing some header for your service or so. – Artem Bilan Nov 17 '22 at 15:31