简体   繁体   中英

org.springframework.web.client.RestClientException: Error while extracting response for type and content type [application/json;charset=utf-8]

I can't figure out what the problem is. I am using postgre DB. When I run a test for the GET method, an error occurs, for the second day I can not solve it.

Here is my Entity class

import lombok.*;
import lombok.experimental.FieldDefaults;

import javax.persistence.*;

@Entity
@Table(name = "cities_catalog")
@FieldDefaults(level = AccessLevel.PRIVATE)
@Data
@NoArgsConstructor
public class PostgreCity {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    Integer id;

    @Column(name = "name")
    String name;

    public PostgreCity(String name) {
        this.name = name;
    }
}

here is my Repository class

import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Repository;
    
    @Repository
    public interface CityRepository extends JpaRepository<PostgreCity, Integer> {
    }

here is my Controller class

import lombok.AccessLevel;
import lombok.AllArgsConstructor;
import lombok.experimental.FieldDefaults;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@RestController
@AllArgsConstructor
@FieldDefaults(makeFinal = true, level = AccessLevel.PRIVATE)
public class CityPostController {

    @Autowired
    CityRepository cityRepository;

    @GetMapping(value = "/get")
    public List<PostgreCity> get(){
        List<PostgreCity> list = this.cityRepository.findAll();
        return list;
    }
}

here is my Junit test class

import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;

import java.util.HashMap;

import static org.junit.jupiter.api.Assertions.*;

class CityPostControllerTest extends RequestService {

    @Autowired
    CityRepository cityRepositoryp;
    Integer id;

    @BeforeEach
    void setUp() {
    }

    @AfterEach
    void tearDown() {
    }

    @Test
    void get() {
        ResponseEntity<PostgreCity> responseEntity = this.get(PostgreCity.class);
        assertNotNull(responseEntity);
        assertEquals(HttpStatus.OK.value(), responseEntity.getStatusCodeValue());
    }

    @Override
    public String getPath() {
        return "/get";
    }
}

here is my RequestService class

import io.egrow.eugene.insurance.InsuranceApplicationTests;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.web.client.TestRestTemplate;
import org.springframework.http.*;


public abstract class RequestService extends InsuranceApplicationTests {

    @Autowired
    TestRestTemplate testRestTemplate;


    public <T> ResponseEntity<T> patchNoAuth(String payload, Class<T> tClass) {

        HttpHeaders headers = getHeaderWithoutAuthentication();
        HttpEntity<String> entity = new HttpEntity<>(payload, headers);

        return testRestTemplate.exchange(this.getPath(), HttpMethod.PATCH, entity, tClass);
    }

    public <T> ResponseEntity<T> get(Class<T> tClass) {

        return testRestTemplate.getForEntity(this.getPath(), tClass);
    }

    private HttpHeaders getHeaderWithoutAuthentication() {

        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);

        return headers;
    }

    public abstract String getPath();
}

here is error message when I run test.

org.springframework.web.client.RestClientException: Error while extracting response for type [class io.egrow.eugene.insurance.boundary.databases.postgre.models.cities.PostgreCity] and content type [application/json;charset=utf-8]; nested exception is org.springframework.http.converter.HttpMessageNotReadableException: JSON parse error: Cannot deserialize value of type `io.egrow.eugene.insurance.boundary.databases.postgre.models.cities.PostgreCity` from Array value (token `JsonToken.START_ARRAY`); nested exception is com.fasterxml.jackson.databind.exc.MismatchedInputException: Cannot deserialize value of type `io.egrow.eugene.insurance.boundary.databases.postgre.models.cities.PostgreCity` from Array value (token `JsonToken.START_ARRAY`)
 at [Source: (PushbackInputStream); line: 1, column: 1]

The problem is here:

ResponseEntity<PostgreCity> responseEntity = this.get(PostgreCity.class);

You are expecting a single entity but in the RestController you have a List:

@GetMapping(value = "/get")
public List<PostgreCity> get(){
    List<PostgreCity> list = this.cityRepository.findAll();
    return list;
}

For getting the list you can use the ParameterizedTypeReference, like so:

ResponseEntity<List<PostgreCity>> responseEntity = 
  restTemplate.exchange(
    "/get",
    HttpMethod.GET,
    null,
    new ParameterizedTypeReference<List<PostgreCity>>() {}
  );
List<PostgreCity> postgreCities = responseEntity.getBody();

For more details and reference can have a look at this tutorial:

https://www.baeldung.com/spring-resttemplate-json-list

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM