diff --git a/libraries/pom.xml b/libraries/pom.xml
index 71d0e76c8a..11295230b4 100644
--- a/libraries/pom.xml
+++ b/libraries/pom.xml
@@ -67,6 +67,11 @@
jsonassert
${jsonassert.version}
+
+ org.javers
+ javers-core
+ ${javers.version}
+
@@ -78,6 +83,7 @@
3.21.0-GA
3.6.2
1.5.0
+ 3.1.0
\ No newline at end of file
diff --git a/libraries/src/main/java/com/baeldung/javers/Address.java b/libraries/src/main/java/com/baeldung/javers/Address.java
new file mode 100644
index 0000000000..14f5907ef6
--- /dev/null
+++ b/libraries/src/main/java/com/baeldung/javers/Address.java
@@ -0,0 +1,11 @@
+package com.baeldung.javers;
+
+
+public class Address {
+ private String country;
+
+ public Address(String country) {
+ this.country = country;
+ }
+
+}
diff --git a/libraries/src/main/java/com/baeldung/javers/Person.java b/libraries/src/main/java/com/baeldung/javers/Person.java
new file mode 100644
index 0000000000..c53a09358b
--- /dev/null
+++ b/libraries/src/main/java/com/baeldung/javers/Person.java
@@ -0,0 +1,27 @@
+package com.baeldung.javers;
+
+public class Person {
+ private Integer id;
+ private String name;
+
+ public Person(Integer id, String name) {
+ this.id = id;
+ this.name = name;
+ }
+
+ public Integer getId() {
+ return id;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public void setId(Integer id) {
+ this.id = id;
+ }
+
+ public void setName(String name) {
+ this.name = name;
+ }
+}
\ No newline at end of file
diff --git a/libraries/src/main/java/com/baeldung/javers/PersonWithAddress.java b/libraries/src/main/java/com/baeldung/javers/PersonWithAddress.java
new file mode 100644
index 0000000000..0b4e33fcb5
--- /dev/null
+++ b/libraries/src/main/java/com/baeldung/javers/PersonWithAddress.java
@@ -0,0 +1,40 @@
+package com.baeldung.javers;
+
+
+import java.util.List;
+
+public class PersonWithAddress {
+ private Integer id;
+ private String name;
+ private List
address;
+
+ public PersonWithAddress(Integer id, String name, List address) {
+ this.id = id;
+ this.name = name;
+ this.address = address;
+ }
+
+ public Integer getId() {
+ return id;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public void setId(Integer id) {
+ this.id = id;
+ }
+
+ public void setName(String name) {
+ this.name = name;
+ }
+
+ public List getAddress() {
+ return address;
+ }
+
+ public void setAddress(List address) {
+ this.address = address;
+ }
+}
diff --git a/libraries/src/test/java/com/baeldung/javers/JaversTest.java b/libraries/src/test/java/com/baeldung/javers/JaversTest.java
new file mode 100644
index 0000000000..e8e3e62e08
--- /dev/null
+++ b/libraries/src/test/java/com/baeldung/javers/JaversTest.java
@@ -0,0 +1,113 @@
+package com.baeldung.javers;
+
+
+import org.javers.common.collections.Lists;
+import org.javers.core.Javers;
+import org.javers.core.JaversBuilder;
+import org.javers.core.diff.Diff;
+import org.javers.core.diff.changetype.NewObject;
+import org.javers.core.diff.changetype.ObjectRemoved;
+import org.javers.core.diff.changetype.ValueChange;
+import org.javers.core.diff.changetype.container.ListChange;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+
+import static org.assertj.core.api.Assertions.assertThat;
+
+public class JaversTest {
+
+ @Test
+ public void givenPersonObject_whenApplyModificationOnIt_thenShouldDetectChange() {
+ //given
+ Javers javers = JaversBuilder.javers().build();
+
+ Person person = new Person(1, "Michael Program");
+ Person personAfterModification = new Person(1, "Michael Java");
+
+ //when
+ Diff diff = javers.compare(person, personAfterModification);
+
+ //then
+ ValueChange change = diff.getChangesByType(ValueChange.class).get(0);
+
+ assertThat(diff.getChanges()).hasSize(1);
+ assertThat(change.getPropertyName()).isEqualTo("name");
+ assertThat(change.getLeft()).isEqualTo("Michael Program");
+ assertThat(change.getRight()).isEqualTo("Michael Java");
+ }
+
+
+ @Test
+ public void givenListOfPersons_whenCompare_ThenShouldDetectChanges() {
+ //given
+ Javers javers = JaversBuilder.javers().build();
+ Person personThatWillBeRemoved = new Person(2, "Thomas Link");
+ List oldList = Lists.asList(new Person(1, "Michael Program"), personThatWillBeRemoved);
+ List newList = Lists.asList(new Person(1, "Michael Not Program"));
+
+ //when
+ Diff diff = javers.compareCollections(oldList, newList, Person.class);
+
+ //then
+ assertThat(diff.getChanges()).hasSize(3);
+
+
+ ValueChange valueChange = diff.getChangesByType(ValueChange.class).get(0);
+ assertThat(valueChange.getPropertyName()).isEqualTo("name");
+ assertThat(valueChange.getLeft()).isEqualTo("Michael Program");
+ assertThat(valueChange.getRight()).isEqualTo("Michael Not Program");
+
+ ObjectRemoved objectRemoved = diff.getChangesByType(ObjectRemoved.class).get(0);
+ assertThat(objectRemoved.getAffectedObject().get().equals(personThatWillBeRemoved)).isTrue();
+
+ ListChange listChange = diff.getChangesByType(ListChange.class).get(0);
+ assertThat(listChange.getValueRemovedChanges().size()).isEqualTo(1);
+
+ }
+
+ @Test
+ public void givenListOfPerson_whenPersonHasNewAddress_thenDetectThatChange() {
+ //given
+ Javers javers = JaversBuilder.javers().build();
+
+ PersonWithAddress person =
+ new PersonWithAddress(1, "Tom", Arrays.asList(new Address("England")));
+
+ PersonWithAddress personWithNewAddress =
+ new PersonWithAddress(1, "Tom",
+ Arrays.asList(new Address("England"), new Address("USA")));
+
+
+ //when
+ Diff diff = javers.compare(person, personWithNewAddress);
+ List objectsByChangeType = diff.getObjectsByChangeType(NewObject.class);
+
+ //then
+ assertThat(objectsByChangeType).hasSize(1);
+ assertThat(objectsByChangeType.get(0).equals(new Address("USA")));
+ }
+
+ @Test
+ public void givenListOfPerson_whenPersonRemovedAddress_thenDetectThatChange() {
+ //given
+ Javers javers = JaversBuilder.javers().build();
+
+ PersonWithAddress person =
+ new PersonWithAddress(1, "Tom", Arrays.asList(new Address("England")));
+
+ PersonWithAddress personWithNewAddress =
+ new PersonWithAddress(1, "Tom", Collections.emptyList());
+
+
+ //when
+ Diff diff = javers.compare(person, personWithNewAddress);
+ List objectsByChangeType = diff.getObjectsByChangeType(ObjectRemoved.class);
+
+ //then
+ assertThat(objectsByChangeType).hasSize(1);
+ assertThat(objectsByChangeType.get(0).equals(new Address("England")));
+ }
+}