From 1b7c6c7abe5ac50d32b5f5330b819b2fff2792ad Mon Sep 17 00:00:00 2001 From: Michael Hoennig Date: Thu, 20 Jun 2024 09:26:49 +0200 Subject: [PATCH] fix failed deletion of test-data with reverse references --- .../HsManagedServerHostingAssetValidator.java | 2 +- ...HsHostingAssetControllerAcceptanceTest.java | 11 ++++++++++- .../rbac/test/ContextBasedTestWithCleanup.java | 18 ++++++++++++++++-- 3 files changed, 27 insertions(+), 4 deletions(-) diff --git a/src/main/java/net/hostsharing/hsadminng/hs/hosting/asset/validators/HsManagedServerHostingAssetValidator.java b/src/main/java/net/hostsharing/hsadminng/hs/hosting/asset/validators/HsManagedServerHostingAssetValidator.java index 839309a0..00050010 100644 --- a/src/main/java/net/hostsharing/hsadminng/hs/hosting/asset/validators/HsManagedServerHostingAssetValidator.java +++ b/src/main/java/net/hostsharing/hsadminng/hs/hosting/asset/validators/HsManagedServerHostingAssetValidator.java @@ -15,7 +15,7 @@ class HsManagedServerHostingAssetValidator extends HsHostingAssetEntityValidator integerProperty("monit_min_free_ssd").min(1).max(1000).withDefault(5), integerProperty("monit_max_hdd_usage").unit("%").min(10).max(100).withDefault(95), integerProperty("monit_min_free_hdd").min(1).max(4000).withDefault(10), - // stringProperty("monit_alarm_email").unit("GB").optional() FIXME: via Contact? + // stringProperty("monit_alarm_email").unit("GB").optional() TODO.impl: via Contact? // other settings // booleanProperty("fastcgi_small").withDefault(false), TODO.spec: clarify Salt-Grains diff --git a/src/test/java/net/hostsharing/hsadminng/hs/hosting/asset/HsHostingAssetControllerAcceptanceTest.java b/src/test/java/net/hostsharing/hsadminng/hs/hosting/asset/HsHostingAssetControllerAcceptanceTest.java index 20122736..84fe1627 100644 --- a/src/test/java/net/hostsharing/hsadminng/hs/hosting/asset/HsHostingAssetControllerAcceptanceTest.java +++ b/src/test/java/net/hostsharing/hsadminng/hs/hosting/asset/HsHostingAssetControllerAcceptanceTest.java @@ -10,8 +10,11 @@ import net.hostsharing.hsadminng.hs.booking.project.HsBookingProjectRepository; import net.hostsharing.hsadminng.hs.office.debitor.HsOfficeDebitorRepository; import net.hostsharing.hsadminng.rbac.test.ContextBasedTestWithCleanup; import net.hostsharing.hsadminng.rbac.test.JpaAttempt; +import org.junit.jupiter.api.ClassOrderer; import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Order; import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.TestClassOrder; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.boot.test.web.server.LocalServerPort; @@ -28,11 +31,12 @@ import static net.hostsharing.hsadminng.rbac.test.JsonMatcher.lenientlyEquals; import static org.assertj.core.api.Assertions.assertThat; import static org.hamcrest.Matchers.matchesRegex; +@Transactional @SpringBootTest( webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT, classes = { HsadminNgApplication.class, JpaAttempt.class } ) -@Transactional +@TestClassOrder(ClassOrderer.OrderAnnotation.class) // fail early on fetching problems class HsHostingAssetControllerAcceptanceTest extends ContextBasedTestWithCleanup { @LocalServerPort @@ -54,6 +58,7 @@ class HsHostingAssetControllerAcceptanceTest extends ContextBasedTestWithCleanup JpaAttempt jpaAttempt; @Nested + @Order(2) class ListAssets { @Test @@ -152,6 +157,7 @@ class HsHostingAssetControllerAcceptanceTest extends ContextBasedTestWithCleanup } @Nested + @Order(3) class AddAsset { @Test @@ -339,6 +345,7 @@ class HsHostingAssetControllerAcceptanceTest extends ContextBasedTestWithCleanup } @Nested + @Order(1) class GetAsset { @Test @@ -410,6 +417,7 @@ class HsHostingAssetControllerAcceptanceTest extends ContextBasedTestWithCleanup } @Nested + @Order(4) class PatchAsset { @Test @@ -463,6 +471,7 @@ class HsHostingAssetControllerAcceptanceTest extends ContextBasedTestWithCleanup } @Nested + @Order(5) class DeleteAsset { @Test diff --git a/src/test/java/net/hostsharing/hsadminng/rbac/test/ContextBasedTestWithCleanup.java b/src/test/java/net/hostsharing/hsadminng/rbac/test/ContextBasedTestWithCleanup.java index c2de3959..5e9d8347 100644 --- a/src/test/java/net/hostsharing/hsadminng/rbac/test/ContextBasedTestWithCleanup.java +++ b/src/test/java/net/hostsharing/hsadminng/rbac/test/ContextBasedTestWithCleanup.java @@ -18,6 +18,8 @@ import org.springframework.transaction.PlatformTransactionManager; import jakarta.persistence.*; import java.util.*; +import java.util.concurrent.atomic.AtomicBoolean; +import java.util.function.Supplier; import static java.lang.System.out; import static java.util.Comparator.comparing; @@ -176,7 +178,7 @@ public abstract class ContextBasedTestWithCleanup extends ContextBasedTest { if (!tm.getTransaction(null).isRollbackOnly()) { out.println(ContextBasedTestWithCleanup.class.getSimpleName() + ".cleanupAndCheckCleanup"); cleanupTemporaryTestData(); - deleteLeakedRbacObjects(); + repeatUntilTrue(3, this::deleteLeakedRbacObjects); long rbacObjectCount = assertNoNewRbacObjectsRolesAndGrantsLeaked(); out.println("TOTAL OBJECT COUNT (after): " + rbacObjectCount); @@ -227,7 +229,8 @@ public abstract class ContextBasedTestWithCleanup extends ContextBasedTest { }).assertSuccessful().returnedValue(); } - private void deleteLeakedRbacObjects() { + private boolean deleteLeakedRbacObjects() { + final var deletionSuccessful = new AtomicBoolean(true); rbacObjectRepo.findAll().stream() .filter(o -> o.serialId > latestIntialTestDataSerialId) .sorted(comparing(o -> o.serialId)) @@ -244,8 +247,10 @@ public abstract class ContextBasedTestWithCleanup extends ContextBasedTest { if (exception != null) { out.println("DELETING leaked " + o.objectTable + "#" + o.uuid + " FAILED " + exception); + deletionSuccessful.set(false); } }); + return deletionSuccessful.get(); } private void assertEqual(final Set before, final Set after) { @@ -306,6 +311,15 @@ public abstract class ContextBasedTestWithCleanup extends ContextBasedTest { "doc/temp/" + name + ".md" ); } + + public static boolean repeatUntilTrue(int maxAttempts, Supplier method) { + for (int attempts = 0; attempts < maxAttempts; attempts++) { + if (method.get()) { + return true; + } + } + return false; + } } interface RbacObjectRepository extends Repository {