diff --git a/spring-5/pom.xml b/spring-5/pom.xml
index c2c565aef6..b77d89b532 100644
--- a/spring-5/pom.xml
+++ b/spring-5/pom.xml
@@ -1,188 +1,196 @@
- 4.0.0
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ 4.0.0
- com.baeldung
- spring-5
- 0.0.1-SNAPSHOT
- jar
+ com.baeldung
+ spring-5
+ 0.0.1-SNAPSHOT
+ jar
- spring-5
- spring 5 sample project about new features
+ spring-5
+ spring 5 sample project about new features
-
- org.springframework.boot
- spring-boot-starter-parent
- 2.0.0.M1
-
-
+
+ org.springframework.boot
+ spring-boot-starter-parent
+ 2.0.0.M1
+
+
-
-
- org.springframework.boot
- spring-boot-starter-data-jpa
-
-
- org.springframework.boot
- spring-boot-starter-security
-
-
- org.springframework.boot
- spring-boot-starter-validation
-
-
- org.springframework.boot
- spring-boot-starter-web
-
-
- org.springframework.boot
- spring-boot-starter-webflux
-
-
- org.projectreactor
- reactor-spring
- 1.0.1.RELEASE
-
+
+
+ org.springframework.boot
+ spring-boot-starter-data-jpa
+
+
+ org.springframework.boot
+ spring-boot-starter-security
+
+
+ org.springframework.boot
+ spring-boot-starter-validation
+
+
+ org.springframework.boot
+ spring-boot-starter-web
+
+
+ org.springframework.boot
+ spring-boot-starter-webflux
+
+
+ org.projectreactor
+ reactor-spring
+ ${reactor-spring.version}
+
+
+ javax.json.bind
+ javax.json.bind-api
+ ${jsonb-api.version}
+
+
+ org.apache.geronimo.specs
+ geronimo-json_1.1_spec
+ ${geronimo-json_1.1_spec.version}
+
+
+ org.apache.johnzon
+ johnzon-jsonb
+ ${johnzon.version}
+
+
+
+ org.apache.commons
+ commons-lang3
+
-
-
- org.apache.commons
- commons-lang3
-
+
-
+
+ org.springframework.boot
+ spring-boot-devtools
+ runtime
+
+
+ com.h2database
+ h2
+ runtime
+
-
- org.springframework.boot
- spring-boot-devtools
- runtime
-
-
- com.h2database
- h2
- runtime
-
+
+ org.springframework
+ spring-test
+
+
+ org.springframework.boot
+ spring-boot-starter-test
+ test
+
-
- org.springframework
- spring-test
-
-
- org.springframework.boot
- spring-boot-starter-test
- test
-
+
+ org.junit.jupiter
+ junit-jupiter-api
+ ${junit.jupiter.version}
+
+
+ org.junit.jupiter
+ junit-jupiter-engine
+ ${junit.jupiter.version}
+ test
+
+
+ org.junit.platform
+ junit-platform-surefire-provider
+ ${junit.platform.version}
+ test
+
+
+ org.junit.platform
+ junit-platform-runner
+ ${junit.platform.version}
+ test
+
-
- org.junit.jupiter
- junit-jupiter-api
- ${junit.jupiter.version}
-
-
- org.junit.jupiter
- junit-jupiter-engine
- ${junit.jupiter.version}
- test
-
-
- org.junit.platform
- junit-platform-surefire-provider
- ${junit.platform.version}
- test
-
-
- org.junit.platform
- junit-platform-runner
- ${junit.platform.version}
- test
-
+
-
+
+
+
+ org.springframework.boot
+ spring-boot-maven-plugin
+
+ com.baeldung.Spring5Application
+ JAR
+
+
-
-
-
- org.springframework.boot
- spring-boot-maven-plugin
-
- com.baeldung.Spring5Application
- JAR
-
-
+
+ org.apache.maven.plugins
+ maven-surefire-plugin
+
+ 3
+ true
+ methods
+ true
+
+ **/*IntegrationTest.java
+ **/*LiveTest.java
+
+
+
+
+
-
- org.apache.maven.plugins
- maven-surefire-plugin
- ${maven-surefire-plugin.version}
-
- 3
- true
-
- **/*IntegrationTest.java
- **/*LiveTest.java
-
-
-
+
+
+ spring-snapshots
+ Spring Snapshots
+ https://repo.spring.io/snapshot
+
+ true
+
+
+
+ spring-milestones
+ Spring Milestones
+ https://repo.spring.io/milestone
+
+ false
+
+
+
+
+
+ spring-snapshots
+ Spring Snapshots
+ https://repo.spring.io/snapshot
+
+ true
+
+
+
+ spring-milestones
+ Spring Milestones
+ https://repo.spring.io/milestone
+
+ false
+
+
+
-
- org.apache.maven.plugins
- maven-surefire-plugin
- ${maven-surefire-plugin.version}
-
- methods
- true
-
-
-
-
-
-
-
-
- spring-snapshots
- Spring Snapshots
- https://repo.spring.io/snapshot
-
- true
-
-
-
- spring-milestones
- Spring Milestones
- https://repo.spring.io/milestone
-
- false
-
-
-
-
-
- spring-snapshots
- Spring Snapshots
- https://repo.spring.io/snapshot
-
- true
-
-
-
- spring-milestones
- Spring Milestones
- https://repo.spring.io/milestone
-
- false
-
-
-
-
-
- UTF-8
- UTF-8
- 1.8
- 1.0.0-M4
- 5.0.0-M4
- 2.20
- 5.0.0.RC2
-
+
+ UTF-8
+ UTF-8
+ 1.8
+ 1.0.0-M4
+ 5.0.0-M4
+ 2.20
+ 5.0.0.RC2
+ 1.0.1.RELEASE
+ 1.1.3
+ 1.0
+ 1.0
+
diff --git a/spring-5/src/main/java/com/baeldung/jsonb/Person.java b/spring-5/src/main/java/com/baeldung/jsonb/Person.java
new file mode 100644
index 0000000000..99ebd54f0b
--- /dev/null
+++ b/spring-5/src/main/java/com/baeldung/jsonb/Person.java
@@ -0,0 +1,139 @@
+package com.baeldung.jsonb;
+
+import java.math.BigDecimal;
+import java.time.LocalDate;
+
+import javax.json.bind.annotation.JsonbDateFormat;
+import javax.json.bind.annotation.JsonbNumberFormat;
+import javax.json.bind.annotation.JsonbProperty;
+import javax.json.bind.annotation.JsonbTransient;
+
+public class Person {
+
+ @JsonbProperty("person-name")
+ private String name;
+ @JsonbProperty(nillable = true)
+ private String email;
+ @JsonbTransient
+ private int age;
+ @JsonbDateFormat("dd-MM-yyyy")
+ private LocalDate registeredDate;
+ private BigDecimal salary;
+
+ public Person() {
+ }
+
+ public Person(String name, String email, int age, LocalDate registeredDate, BigDecimal salary) {
+ super();
+ this.name = name;
+ this.email = email;
+ this.age = age;
+ this.registeredDate = registeredDate;
+ this.salary = salary;
+ }
+
+ public int getAge() {
+ return age;
+ }
+
+ public void setAge(int age) {
+ this.age = age;
+ }
+
+ public String getEmail() {
+ return email;
+ }
+
+ public void setEmail(String email) {
+ this.email = email;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public void setName(String name) {
+ this.name = name;
+ }
+
+ @JsonbNumberFormat(locale = "en_US", value = "#0.0")
+ public BigDecimal getSalary() {
+ return salary;
+ }
+
+ public void setSalary(BigDecimal salary) {
+ this.salary = salary;
+ }
+
+ public LocalDate getRegisteredDate() {
+ return registeredDate;
+ }
+
+ public void setRegisteredDate(LocalDate registeredDate) {
+ this.registeredDate = registeredDate;
+ }
+
+ @Override
+ public String toString() {
+ StringBuilder builder = new StringBuilder();
+ builder.append("Person [name=");
+ builder.append(name);
+ builder.append(", email=");
+ builder.append(email);
+ builder.append(", age=");
+ builder.append(age);
+ builder.append(", registeredDate=");
+ builder.append(registeredDate);
+ builder.append(", salary=");
+ builder.append(salary);
+ builder.append("]");
+ return builder.toString();
+ }
+
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = 1;
+ result = prime * result + age;
+ result = prime * result + ((email == null) ? 0 : email.hashCode());
+ result = prime * result + ((name == null) ? 0 : name.hashCode());
+ result = prime * result + ((registeredDate == null) ? 0 : registeredDate.hashCode());
+ result = prime * result + ((salary == null) ? 0 : salary.hashCode());
+ return result;
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj)
+ return true;
+ if (obj == null)
+ return false;
+ if (getClass() != obj.getClass())
+ return false;
+ Person other = (Person) obj;
+ if (age != other.age)
+ return false;
+ if (email == null) {
+ if (other.email != null)
+ return false;
+ } else if (!email.equals(other.email))
+ return false;
+ if (name == null) {
+ if (other.name != null)
+ return false;
+ } else if (!name.equals(other.name))
+ return false;
+ if (registeredDate == null) {
+ if (other.registeredDate != null)
+ return false;
+ } else if (!registeredDate.equals(other.registeredDate))
+ return false;
+ if (salary == null) {
+ if (other.salary != null)
+ return false;
+ } else if (!salary.equals(other.salary))
+ return false;
+ return true;
+ }
+
+}
diff --git a/spring-5/src/main/java/com/baeldung/jsonb/PersonController.java b/spring-5/src/main/java/com/baeldung/jsonb/PersonController.java
new file mode 100644
index 0000000000..75fcd1e2cc
--- /dev/null
+++ b/spring-5/src/main/java/com/baeldung/jsonb/PersonController.java
@@ -0,0 +1,58 @@
+package com.baeldung.jsonb;
+
+import java.math.BigDecimal;
+import java.time.LocalDate;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import javax.annotation.PostConstruct;
+
+import org.springframework.http.HttpStatus;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.PathVariable;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.ResponseBody;
+import org.springframework.web.bind.annotation.ResponseStatus;
+import org.springframework.web.bind.annotation.RestController;
+
+@RestController("/person")
+public class PersonController {
+
+ List personRepository;
+
+ @PostConstruct
+ public void init() {
+ // @formatter:off
+ personRepository = new ArrayList<>(Arrays.asList(
+ new Person("Jhon", "jhon@test.com", 20, LocalDate.of(2019, 9, 9), BigDecimal.valueOf(1000)),
+ new Person("Jhon", "jhon1@test.com", 20, LocalDate.of(2019, 9, 9), BigDecimal.valueOf(1500)),
+ new Person("Jhon", null, 20, LocalDate.of(2019, 9, 9), BigDecimal.valueOf(1000)),
+ new Person("Tom", "tom@test.com", 21, LocalDate.of(2019, 9, 9), BigDecimal.valueOf(1500)),
+ new Person("Mark", "mark@test.com", 21, LocalDate.of(2019, 9, 9), BigDecimal.valueOf(1200)),
+ new Person("Julia", "jhon@test.com", 20, LocalDate.of(2019, 9, 9), BigDecimal.valueOf(1000))));
+ // @formatter:on
+
+ }
+
+ @GetMapping("/person/{id}")
+ @ResponseBody
+ public Person findById(@PathVariable final int id) {
+ return personRepository.get(id);
+ }
+
+ @PostMapping("/person")
+ @ResponseStatus(HttpStatus.OK)
+ @ResponseBody
+ public boolean insertPerson(@RequestBody final Person person) {
+ return personRepository.add(person);
+ }
+
+ @GetMapping("/person")
+ @ResponseBody
+ public List findAll() {
+ return personRepository;
+ }
+
+}
diff --git a/spring-5/src/main/java/com/baeldung/jsonb/Spring5Application.java b/spring-5/src/main/java/com/baeldung/jsonb/Spring5Application.java
new file mode 100644
index 0000000000..00fce06834
--- /dev/null
+++ b/spring-5/src/main/java/com/baeldung/jsonb/Spring5Application.java
@@ -0,0 +1,30 @@
+package com.baeldung.jsonb;
+
+import java.util.ArrayList;
+import java.util.Collection;
+
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.autoconfigure.SpringBootApplication;
+import org.springframework.boot.autoconfigure.http.HttpMessageConverters;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.ComponentScan;
+import org.springframework.http.converter.HttpMessageConverter;
+import org.springframework.http.converter.json.JsonbHttpMessageConverter;
+
+@SpringBootApplication
+@ComponentScan(basePackages = { "com.baeldung.jsonb" })
+public class Spring5Application {
+
+ public static void main(String[] args) {
+ SpringApplication.run(Spring5Application.class, args);
+ }
+
+ @Bean
+ public HttpMessageConverters customConverters() {
+ Collection> messageConverters = new ArrayList<>();
+ JsonbHttpMessageConverter jsonbHttpMessageConverter = new JsonbHttpMessageConverter();
+ messageConverters.add(jsonbHttpMessageConverter);
+ return new HttpMessageConverters(true, messageConverters);
+ }
+
+}
diff --git a/spring-5/src/test/java/com/baeldung/jsonb/JsonbIntegrationTest.java b/spring-5/src/test/java/com/baeldung/jsonb/JsonbIntegrationTest.java
new file mode 100644
index 0000000000..a31a16d610
--- /dev/null
+++ b/spring-5/src/test/java/com/baeldung/jsonb/JsonbIntegrationTest.java
@@ -0,0 +1,44 @@
+package com.baeldung.jsonb;
+
+import static org.junit.Assert.assertTrue;
+
+import java.math.BigDecimal;
+import java.time.LocalDate;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.boot.test.context.SpringBootTest;
+import org.springframework.boot.test.web.client.TestRestTemplate;
+import org.springframework.http.ResponseEntity;
+import org.springframework.test.context.junit4.SpringRunner;
+
+@RunWith(SpringRunner.class)
+@SpringBootTest(classes = Spring5Application.class, webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
+public class JsonbIntegrationTest {
+ @Value("${security.user.name}")
+ private String username;
+ @Value("${security.user.password}")
+ private String password;
+
+ @Autowired
+ private TestRestTemplate template;
+
+ @Test
+ public void givenId_whenUriIsPerson_thenGetPerson() {
+ ResponseEntity response = template.withBasicAuth(username, password)
+ .getForEntity("/person/1", Person.class);
+ Person person = response.getBody();
+ assertTrue(person.equals(new Person("Jhon", "jhon1@test.com", 0, LocalDate.of(2019, 9, 9), BigDecimal.valueOf(1500.0))));
+ }
+
+ @Test
+ public void whenSendPostAPerson_thenGetOkStatus() {
+ ResponseEntity response = template.withBasicAuth(username, password)
+ .postForEntity("/person", "{\"birthDate\":\"07-09-2017\",\"email\":\"jhon1@test.com\",\"person-name\":\"Jhon\"}", Boolean.class);
+ boolean value = response.getBody();
+ assertTrue(true == value);
+ }
+
+}
diff --git a/spring-5/src/test/java/com/baeldung/jsonb/JsonbTest.java b/spring-5/src/test/java/com/baeldung/jsonb/JsonbTest.java
new file mode 100644
index 0000000000..7133999551
--- /dev/null
+++ b/spring-5/src/test/java/com/baeldung/jsonb/JsonbTest.java
@@ -0,0 +1,38 @@
+package com.baeldung.jsonb;
+
+import static org.junit.Assert.assertTrue;
+
+import java.math.BigDecimal;
+import java.time.LocalDate;
+
+import javax.json.bind.Jsonb;
+import javax.json.bind.JsonbBuilder;
+
+import org.junit.Before;
+import org.junit.Test;
+
+public class JsonbTest {
+
+ private Jsonb jsonb;
+
+ @Before
+ public void setup() {
+ jsonb = JsonbBuilder.create();
+ }
+
+ @Test
+ public void givenPersonObject_whenSerializeWithJsonb_thenGetPersonJson() {
+ Person person = new Person("Jhon", "jhon@test.com", 20, LocalDate.of(2019, 9, 7), BigDecimal.valueOf(1000));
+ String jsonPerson = jsonb.toJson(person);
+ assertTrue("{\"email\":\"jhon@test.com\",\"person-name\":\"Jhon\",\"registeredDate\":\"07-09-2019\",\"salary\":\"1000.0\"}".equals(jsonPerson));
+ }
+
+ @Test
+ public void givenPersonJson_whenDeserializeWithJsonb_thenGetPersonObject() {
+ Person person = new Person("Jhon", "jhon@test.com", 0, LocalDate.of(2019, 9, 7), BigDecimal.valueOf(1000.0));
+ String jsonPerson = "{\"email\":\"jhon@test.com\",\"person-name\":\"Jhon\",\"registeredDate\":\"07-09-2019\",\"salary\":\"1000.0\"}";
+ assertTrue(jsonb.fromJson(jsonPerson, Person.class)
+ .equals(person));
+ }
+
+}