Introdução ao JaVers
1. Visão geral
Neste artigo, examinaremos a bibliotecaJaVers.
Essa biblioteca ajuda os programadores a examinar e detectar alterações nos estados de objetos Java simples. Quando usamos objetos mutáveis em nosso código, cada objeto pode ser potencialmente modificado em vários locais do aplicativo; JaVers would help us discover and audit these changes.
2. Dependência do Maven
Para começar, vamos adicionar a dependênciajavers-core Maven ao nossopom.xml:
org.javers
javers-core
3.1.0
Podemos encontrar a versão mais recente emMaven Central.
3. Detectando mudanças de estado de POJO
Vamos começar com uma classePerson simples:
public class Person {
private Integer id;
private String name;
// standard getters/constructors
}
Suponha que criamos um objetoPerson em uma parte de nosso aplicativo e em alguma outra parte da base de código, o nome do campothe person with the same id foi alterado. Queremos compará-los para descobrir que tipo de mudanças aconteceu no objeto pessoa.
Podemos comparar esses dois objetos usando o métodocompare() da classeJaVers:
@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");
}
4. Detectando Mudança de Estado da Lista de Objetos
Se estivermos trabalhando com coleções de objetos, da mesma forma precisamos examinar as mudanças de estado observando cada elemento na coleção. Às vezes, queremos adicionar ou remover o objeto específico da lista, alterando seu estado.
Let’s have a look at an example; digamos que temos uma lista de objetos e removemos um objeto dessa lista.
Essa alteração pode ser indesejável por algum motivo, e queremos auditar as alterações que ocorreram nesta lista. JaVers nos permite fazer isso usando um métodocompareCollections():
@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);
}
5. Comparando Gráficos de Objetos
Em aplicativos de palavras reais, geralmente lidamos com os gráficos de objetos. Digamos que temos uma classePersonWithAddress que tem uma lista dos objetosAddress e estamos adicionando um novo endereço para a pessoa dada.
Podemos encontrar facilmente o tipo de alteração que ocorreu:
@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")));
}
Da mesma forma, a remoção de um endereço será detectada:
@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")));
}
6. Conclusão
Neste artigo rápido, usamos a biblioteca JaVers, uma biblioteca útil que nos fornece APIs para detectar alterações de estado em nossos objetos. Não apenas ele pode detectar a alteração em um objeto POJO simples, mas também pode detectar mudanças mais complexas nas coleções de objetos ou mesmo nos gráficos de objetos.
Como sempre, o código está disponívelover on GitHub.