RestTemplate Spring boot 400 error Servlet.service() for servlet [dispatcherServlet] in context with path [] threw excepti. One method works rest dont

Issue

I am building spring boot microservices and using REST template to communicate between microservices (via eureka API Gateway). Oddly, a simple request from one service to another returning a String works but any other request and I get the following error:

26 --- [nio-9010-exec-1] o.a.c.c.C.[.[.[/].[dispatcherServlet]    : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.springframework.web.client.HttpClientErrorException$BadRequest: 400 : [{"timestamp":"2021-08-17T14:15:18.209+00:00","status":400,"error":"Bad Request","path":"/accounts/findbycustomernumber"}]] with root cause
org.springframework.web.client.HttpClientErrorException$BadRequest: 400 : [{"timestamp":"2021-08-17T14:15:18.209+00:00","status":400,"error":"Bad Request","path":"/accounts/findbycustomernumber"}]
    at org.springframework.web.cl

I have a CustomerProfile microservice which should fetch an "Account" entity from the BankAccount microservice. In my BankAccountService.controller I have 2 methods (which both work correctly:

@GetMapping("/test")
public String test() {
    return "Hello World";
}

 @GetMapping("/findbycustomernumber")
public ResponseEntity<List<Account>> findbycustomernumber(@RequestParam String customernumber) {
    log.info("Inside AccountController::findByCustomerID()");
    System.out.println("Customer number: " + customernumber);
    List<Account> findByCustomerNumberAccounts =
            accountService.findbycustomernumber (customernumber);
    return new ResponseEntity<List<Account>>(
            accountService.findbycustomernumber(customernumber),
            HttpStatus.OK
    );
}

And in my CustomerProfile controller I have 2 methods:

@GetMapping("/test")
public ResponseEntity<String> test() {
    return customerProfileService.test();
}

@GetMapping("findbycustomernumber")
public ResponseEntity<Account> findByCustomerNumber(@RequestParam String customernumber) {
    log.info("Inside: /CustomerProfileController/findbycustomernumber");
    return customerProfileService.findByCustomerNumber(customernumber);
}

and their respective methods in the service package using rest template is:

public ResponseEntity<String> test() {
    ResponseEntity<String> response = restTemplate.getForEntity(
            "http://BANK-ACCOUNT-SERVICE/accounts/test",
            String.class);

    return response;
}

public ResponseEntity<Account> findByCustomerNumber(String customernumber) {
    log.info("Inside CustomerProfileService::findByCustomerNumber()");
    String url = "http://BANK-ACCOUNT-SERVICE/accounts/findbycustomernumber";
    HttpHeaders requestHeaders = new HttpHeaders();
    requestHeaders.setContentType(MediaType.APPLICATION_JSON);
    HttpEntity<String> request = new HttpEntity<>(customernumber, requestHeaders);



    ResponseEntity<Account> response = restTemplate.exchange(url, HttpMethod.GET, request, Account.class);
    return response;
}

Using postman, if i send a request to localhost:9191/customerprofile/test (9191 because I am using netflix eureka API gateway), the method works fine. The request journey is client->API-Gateway->CustomerProfileService.controller->CustomerProfileService.service->BankAccouunttService.controller->client.

But the second method, findbycustomernumber, which is implemented the same way returns a 400 error code with failure to find path. Why is one working and the other isn’t when everything is implemented the same?

I have somewhat edited the code for privacy so you may notice minor errors that may be irrelevant to this issue. But as one RestTemplate request in customer profile services service class is working and the other isnt, I am sure the issue is with how I am calling the restTemplate methods. I have tried all the methods getForEntity, getForObject and Exchange but I always get the same error.

I have searched for quite sometime. I know there are similar questions online but i have still not got anywhere.
Thanks

Solution

400 bad request is due to the missing query parameter of that API.

try to provide url as below in rest template

UriComponentsBuilder builder = UriComponentsBuilder.fromUriString(url)
        // Add query parameter
        .queryParam("customernumber", customernumber);
HttpEntity<?> request = new HttpEntity<>(requestHeaders);

ResponseEntity<Account> response = restTemplate.exchange(builder.toUriString(), HttpMethod.GET, request, Account.class);
return response;

Answered By – Midhun Mohan

This Answer collected from stackoverflow, is licensed under cc by-sa 2.5 , cc by-sa 3.0 and cc by-sa 4.0

Leave a Reply

(*) Required, Your email will not be published