Menyelesaikan 406 NOT_ACCEPTABLE - Menguji WebLayer di SpringBoot

Dec 07 2020

Saya memiliki metode ini di aplikasi Spring Boot v2.1.0.RELEASE.

@GetMapping(value = "/wildProject", produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<List<WildProject>> getList(HttpServletRequest request,
        HttpServletResponse response)
        throws Exception {

    List<WildProject> list = authorisationService.getList();

    System.out.println("-----------------");
    System.out.println(list);
    System.out.println("-----------------");

    return ok().body(list);


} 

dan tes ini:

 this.mockMvc.perform(get("/wildProject")
  //.accept(MediaType.APPLICATION_JSON_UTF8_VALUE))
  // .andDo(print())
  .andExpect(content().contentType(MediaType.APPLICATION_JSON_VALUE))
  .andExpect(status().isOk());

dan inilah hasil tesnya:

20:03:38.253 [main] DEBUG o.s.w.s.m.m.a.HttpEntityMethodProcessor - Using 'application/json', given [*/*] and supported [application/json]
20:03:38.255 [main] WARN  o.s.w.s.m.s.DefaultHandlerExceptionResolver - Resolved [org.springframework.web.HttpMediaTypeNotAcceptableException: Could not find acceptable representation]
20:03:38.256 [main] DEBUG o.s.t.w.s.TestDispatcherServlet - Completed 406 NOT_ACCEPTABLE

MockHttpServletRequest:
      HTTP Method = GET
      Request URI = /wildProject
       Parameters = {}
          Headers = {Content-Type=[application/json;charset=UTF-8]}
             Body = null
    Session Attrs = {}

Handler:
             Type = com.bonansa.controller.AuthorisationController
           Method = public org.springframework.http.ResponseEntity<java.util.List<com.bonansa.WildProject>> com.bonansa.controller.AuthorisationController.getList() throws java.lang.Exception

Async:
    Async started = false
     Async result = null

Resolved Exception:
             Type = org.springframework.web.HttpMediaTypeNotAcceptableException

ModelAndView:
        View name = null
             View = null
            Model = null

FlashMap:
       Attributes = null

MockHttpServletResponse:
           Status = 406
    Error message = null
          Headers = {}
     Content type = null
             Body = 
    Forwarded URL = null
   Redirected URL = null
          Cookies = []

dan

@JsonSerialize(as = IWildProject.class)
public interface IWildProject {
..
}

Jawaban

s7vr Dec 19 2020 at 04:59

Masalah Anda muncul dua kali lipat.

Masalah yang mendasari Anda tidak mendaftarkan konverter pesan yang benar untuk dapat menulis respons json. Ini tersembunyi karena bug di mana server harus mengembalikan 500 bukan 406 karena kesalahan konfigurasi karena pengontrol telah menentukan anotasi yang dihasilkan dan klien telah menerima header dari semua.

Keterangan lebih lanjut - https://github.com/spring-projects/spring-framework/issues/23287

Ini tidak lagi menjadi masalah di rilis terbaru hanya masalah dengan versi boot musim semi 2.1.x.

2 x80486 Dec 08 2020 at 00:48

Anda tidak perlu menyetel Content-Typeheader untuk GETpermintaan karena Anda tidak mengirim apa pun kecuali meminta sesuatu. The Acceptheader apa cari dalam kasus ini.

Apalagi MediaType.APPLICATION_JSON_VALUEtidak akan cocok MediaType.APPLICATION_JSON_UTF8_VALUE.

Saya akan merekomendasikan untuk merefaktor kode itu menjadi:

this.mockMvc.perform(get("/wildProject")
  .accept(MediaType.APPLICATION_JSON_VALUE))
  // .andDo(print())
  .andExpect(content().contentType(MediaType.APPLICATION_JSON_VALUE))
  .andExpect(status().isOk());