[Java] AssertJ equivalent voor Hamcrest patroon

Pagina: 1
Acties:

Vraag


Acties:
  • 0 Henk 'm!

  • ari3
  • Registratie: Augustus 2002
  • Niet online
Ik ben bezig de unit tests van mijn project te migreren van Hamcrest matchers naar AssertJ. De fluenency van AssertJ spreekt mij zeer aan. Echter, heb ik een specifieke use-case waarbij ik voor een Hamcrest one-liner geen AssertJ equivalent kan vinden. Het gaat daarbij om geneste collecties in POJO's.

Gegeven deze assertie met gebruik van Hamcrest matchers:
Java:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
        assertThat(allDecks, containsInAnyOrder(
            allOf(
                hasProperty("name", is("Test Deck 1")),
                hasProperty("account", hasProperty("id", is(10L))),
                hasProperty("cards", hasSize(2)),
                hasProperty("cards", containsInAnyOrder(hasProperty("id", is(100L)), hasProperty("id", is(200L))))
            ),
            allOf(
                hasProperty("name", is("Test Deck 2")),
                hasProperty("account", hasProperty("id", is(10L))),
                hasProperty("cards", hasSize(1)),
                hasProperty("cards", containsInAnyOrder(hasProperty("id", is(300L))))
            )
        ));


Bovenstaande kan ik deels herschrijven met AssertJ-asserties als:
Java:
1
2
3
4
5
6
        assertThat(allDecks)
            .extracting("name", "account.id")
            .containsExactlyInAnyOrder(
                tuple("Test Deck 1", 10L),
                tuple("Test Deck 2", 10L))
        );


Hierbij mist voor de eerste tuple nog de vertaling nog van:
Java:
1
hasProperty("cards", containsInAnyOrder(hasProperty("id", is(100L)), hasProperty("id", is(200L))))

En voor de tweede tuple mist de vertaling van:
Java:
1
hasProperty("cards", containsInAnyOrder(hasProperty("id", is(300L))))


Wat is het AssertJ-equivalent hiervan? Natuurlijk is dit te testen met AssertJ, maar alle mogelijkheden die ik bedenk vereisen een veelvoud aan regels code of zelfs een extra assertThat-blok om de geneste collecties apart te testen. Dit komt de leesbaarheid niet ten goede. Ik leg daarom de volgende beperking op aan de oplossing:
- Het moet leesbaar zijn, liefst een one-liner.
- Geen gebruik van custom assertions.

Iemand een idee?

"Kill one man, and you are a murderer. Kill millions of men, and you are a conqueror. Kill them all, and you are a god." -- Jean Rostand

Alle reacties


Acties:
  • 0 Henk 'm!

  • Hydra
  • Registratie: September 2000
  • Laatst online: 21-08 17:09
Ik wou zeggen "custom assertions" maar dat wil je niet, maareh. Ik vind persoonlijk die diepe nesting best wel onleesbaar. Zelf heb ik er een voorkeur voor om als ik 'dieper' moet, gewoon wat ik aan het testen ben in een aparte variable zet.

Zelf werk ik overigens in Kotlin waar je dat met with() mooi kan scopen, maar daar heb je natuurlijk niet zo veel aan.

Hoe dan ook denk ik dat je, als je geen custom assertions wil, vooral aangewezen bent op het vooral iets anders te doen.

https://niels.nu