RestTemplate Posting Permintaan dengan JSON

REST Top

Saya baru saja mengumumkan kursus Learn Spring baru , yang berfokus pada dasar-dasar Spring 5 dan Spring Boot 2:

>> LIHAT KURSUSnya

1. Perkenalan

Dalam tutorial singkat ini, kami mengilustrasikan cara menggunakan Spring's RestTemplate untuk membuat permintaan POST mengirimkan konten JSON.

2. Menyiapkan Contoh

Mari kita mulai dengan menambahkan kelas model Person sederhana untuk merepresentasikan data yang akan dikirim:

public class Person { private Integer id; private String name; // standard constructor, getters, setters }

Untuk bekerja dengan objek Person , kita akan menambahkan antarmuka dan implementasi PersonService dengan dua metode:

public interface PersonService { public Person saveUpdatePerson(Person person); public Person findPersonById(Integer id); }

Penerapan metode ini hanya akan mengembalikan objek. Kami menggunakan implementasi tiruan dari lapisan ini di sini sehingga kami dapat fokus pada lapisan web.

3. Penyiapan REST API

Mari tentukan REST API sederhana untuk kelas Person kita :

@PostMapping( value = "/createPerson", consumes = "application/json", produces = "application/json") public Person createPerson(@RequestBody Person person) { return personService.saveUpdatePerson(person); } @PostMapping( value = "/updatePerson", consumes = "application/json", produces = "application/json") public Person updatePerson(@RequestBody Person person, HttpServletResponse response) { response.setHeader("Location", ServletUriComponentsBuilder.fromCurrentContextPath() .path("/findPerson/" + person.getId()).toUriString()); return personService.saveUpdatePerson(person); }

Ingat, kami ingin memposting data dalam format JSON. Untuk itu, kami menambahkan atribut konsumsi dalam anotasi @PostMapping dengan nilai "application / json" untuk kedua metode.

Demikian pula, kami menyetel atribut produksi ke "application / json" untuk memberi tahu Spring bahwa kami menginginkan isi respons dalam format JSON.

Kami menganotasi parameter person dengan anotasi @RequestBody untuk kedua metode. Ini akan memberi tahu Spring bahwa objek person akan terikat ke badan permintaan HTTP .

Terakhir, kedua metode mengembalikan objek Person yang akan terikat ke isi respons. Perhatikan bahwa kami akan membuat anotasi kelas API kami dengan @RestController untuk menganotasi semua metode API dengan anotasi @ResponseBody tersembunyi .

4. Menggunakan RestTemplate

Sekarang kita bisa menulis beberapa unit test untuk menguji Person REST API kita. Di sini, kami akan mencoba mengirim permintaan POST ke Person API dengan menggunakan metode POST yang disediakan oleh RestTemplate : postForObject , postForEntity , dan postForLocation .

Sebelum kita mulai menerapkan pengujian unit kita, mari tentukan metode pengaturan untuk menginisialisasi objek yang akan kita gunakan di semua metode pengujian unit kita:

@BeforeClass public static void runBeforeAllTestMethods() { createPersonUrl = "//localhost:8082/spring-rest/createPerson"; updatePersonUrl = "//localhost:8082/spring-rest/updatePerson"; restTemplate = new RestTemplate(); headers = new HttpHeaders(); headers.setContentType(MediaType.APPLICATION_JSON); personJsonObject = new JSONObject(); personJsonObject.put("id", 1); personJsonObject.put("name", "John"); }

Selain metode penyiapan ini, perhatikan bahwa kami akan merujuk ke mapper berikut untuk mengonversi String JSON menjadi objek JSONNode dalam pengujian unit kami:

private final ObjectMapper objectMapper = new ObjectMapper();

Seperti yang disebutkan sebelumnya, kami ingin memposting data dalam format JSON. Untuk mencapai ini, kami akan menambahkan header Content-Type ke permintaan kami dengan jenis media APPLICATION_JSON .

Kelas HttpHeaders Spring menyediakan metode berbeda untuk mengakses header. Di sini, kami menyetel header Content-Type ke application / json dengan memanggil metode setContentType . Kami akan melampirkan objek header ke permintaan kami.

4.1. Memposting JSON Dengan postForObject

RestTemplate 's postForObject metode menciptakan sumber daya baru dengan posting obyek ke template URI yang diberikan. Ini mengembalikan hasil sebagai secara otomatis dikonversi ke tipe yang ditentukan dalam parameter responseType .

Katakanlah kita ingin membuat permintaan POST ke Person API kita untuk membuat objek Person baru dan mengembalikan objek yang baru dibuat ini sebagai tanggapan.

Pertama, kita akan membangun objek permintaan tipe HttpEntity berdasarkan personJsonObject dan header yang berisi Tipe-Konten . Ini memungkinkan metode postForObject mengirim isi permintaan JSON:

@Test public void givenDataIsJson_whenDataIsPostedByPostForObject_thenResponseBodyIsNotNull() throws IOException { HttpEntity request = new HttpEntity(personJsonObject.toString(), headers); String personResultAsJsonStr = restTemplate.postForObject(createPersonUrl, request, String.class); JsonNode root = objectMapper.readTree(personResultAsJsonStr); assertNotNull(personResultAsJsonStr); assertNotNull(root); assertNotNull(root.path("name").asText()); }

Metode postForObject () mengembalikan isi respons sebagai tipe String .

Kita juga bisa mengembalikan respons sebagai objek Person dengan menyetel parameter responseType :

Person person = restTemplate.postForObject(createPersonUrl, request, Person.class); assertNotNull(person); assertNotNull(person.getName());

Sebenarnya, metode penangan permintaan kami yang cocok dengan URI createPersonUrl menghasilkan isi respons dalam format JSON.

Tetapi ini bukan batasan bagi kami - postForObject dapat secara otomatis mengubah isi respons menjadi tipe Java yang diminta (mis. String , Person ) yang ditentukan dalam parameter responseType .

4.2. Memposting JSON Dengan postForEntity

Dibandingkan dengan postForObject () , postForEntity () mengembalikan respons sebagai objek ResponseEntity . Selain itu, kedua metode melakukan pekerjaan yang sama.

Katakanlah kita ingin membuat permintaan POST ke Person API kita untuk membuat objek Person baru dan mengembalikan respons sebagai ResponseEntity .

Kita dapat menggunakan metode postForEntity untuk mengimplementasikan ini:

@Test public void givenDataIsJson_whenDataIsPostedByPostForEntity_thenResponseBodyIsNotNull() throws IOException { HttpEntity request = new HttpEntity(personJsonObject.toString(), headers); ResponseEntity responseEntityStr = restTemplate. postForEntity(createPersonUrl, request, String.class); JsonNode root = objectMapper.readTree(responseEntityStr.getBody()); assertNotNull(responseEntityStr.getBody()); assertNotNull(root.path("name").asText()); }

Mirip dengan postForObject , postForEntity memiliki parameter responseType untuk mengubah isi respons menjadi jenis Java yang diminta.

Di sini, kami dapat mengembalikan isi respons sebagai ResponseEntity .

We can also return the response as a ResponseEntity object by setting the responseType parameter to Person.class:

ResponseEntity responseEntityPerson = restTemplate. postForEntity(createPersonUrl, request, Person.class); assertNotNull(responseEntityPerson.getBody()); assertNotNull(responseEntityPerson.getBody().getName());

4.3. Posting JSON With postForLocation

Similar to the postForObject and postForEntity methods, postForLocation also creates a new resource by posting the given object to the given URI. The only difference is that it returns the value of the Location header.

Remember, we already saw how to set the Location header of a response in our updatePerson REST API method above:

response.setHeader("Location", ServletUriComponentsBuilder.fromCurrentContextPath() .path("/findPerson/" + person.getId()).toUriString());

Sekarang mari kita bayangkan bahwa kita ingin mengembalikan header Location dari respon setelah memperbarui objek person yang kita posting.

Kita bisa mengimplementasikan ini dengan menggunakan metode postForLocation :

@Test public void givenDataIsJson_whenDataIsPostedByPostForLocation_thenResponseBodyIsTheLocationHeader() throws JsonProcessingException { HttpEntity request = new HttpEntity(personJsonObject.toString(), headers); URI locationHeader = restTemplate.postForLocation(updatePersonUrl, request); assertNotNull(locationHeader); }

5. Kesimpulan

Pada artikel ini, kami membahas cara menggunakan RestTemplate untuk membuat permintaan POST dengan JSON.

Seperti biasa, semua contoh dan cuplikan kode dapat ditemukan di GitHub.

REST bawah

Saya baru saja mengumumkan kursus Learn Spring baru , yang berfokus pada dasar-dasar Spring 5 dan Spring Boot 2:

>> LIHAT KURSUSnya