From 42c4ce1b0f7c782e58c03e0e2ba80ae33b958ea0 Mon Sep 17 00:00:00 2001 From: raoulvdberge Date: Sat, 25 May 2024 15:20:34 +0200 Subject: [PATCH] refactor: use neoforge framework Stop using Guava RateLimiter as the gametests run ticks faster, and the RateLimiter uses the system clock so RS wouldn't keep up with the faster tick rate. --- config/checkstyle/checkstyle-suppressions.xml | 1 + .../ConstructorBlockEntity.java | 2 +- .../common/exporter/ExporterBlockEntity.java | 2 +- .../support/AbstractDirectionalBlock.java | 4 + ...dulingNetworkNodeContainerBlockEntity.java | 2 +- ...deableNetworkNodeContainerBlockEntity.java | 12 +-- refinedstorage2-platform-forge/build.gradle | 14 +++ .../platform/forge/ConstructorTest.java | 49 +++++++++ .../platform/forge/ExporterGameTest.java | 21 ---- .../platform/forge/TestMod.java | 98 ++++++++++++++++++ .../src/test/resources/META-INF/mods.toml | 7 ++ .../structures/empty_15x15.nbt | Bin 8456 -> 0 bytes 12 files changed, 180 insertions(+), 32 deletions(-) create mode 100644 refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/ConstructorTest.java delete mode 100644 refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/ExporterGameTest.java create mode 100644 refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/TestMod.java create mode 100644 refinedstorage2-platform-forge/src/test/resources/META-INF/mods.toml delete mode 100644 refinedstorage2-platform-forge/src/test/resources/data/refinedstorage2/structures/empty_15x15.nbt diff --git a/config/checkstyle/checkstyle-suppressions.xml b/config/checkstyle/checkstyle-suppressions.xml index b0d870283..8b6e49245 100644 --- a/config/checkstyle/checkstyle-suppressions.xml +++ b/config/checkstyle/checkstyle-suppressions.xml @@ -10,4 +10,5 @@ + diff --git a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/constructordestructor/ConstructorBlockEntity.java b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/constructordestructor/ConstructorBlockEntity.java index 4c870f75e..45cf2e459 100644 --- a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/constructordestructor/ConstructorBlockEntity.java +++ b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/constructordestructor/ConstructorBlockEntity.java @@ -57,7 +57,7 @@ public ConstructorBlockEntity(final BlockPos pos, final BlockState state) { } @Override - protected void setFilters(final List filters) { + public void setFilters(final List filters) { this.tasks.clear(); this.tasks.addAll(filters.stream().map(TaskImpl::new).toList()); } diff --git a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/exporter/ExporterBlockEntity.java b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/exporter/ExporterBlockEntity.java index 5ea3d2f31..2b911edb6 100644 --- a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/exporter/ExporterBlockEntity.java +++ b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/exporter/ExporterBlockEntity.java @@ -95,7 +95,7 @@ protected void setTaskExecutor(final TaskExecutor filters) { + public void setFilters(final List filters) { mainNode.setFilters(filters); } diff --git a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/AbstractDirectionalBlock.java b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/AbstractDirectionalBlock.java index b8f86a1c7..b61083c3c 100644 --- a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/AbstractDirectionalBlock.java +++ b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/AbstractDirectionalBlock.java @@ -70,6 +70,10 @@ public Direction extractDirection(@Nullable final BlockState state) { return getDirectionType().extractDirection(direction); } + public BlockState rotated(final T direction) { + return defaultBlockState().setValue(getDirectionType().getProperty(), direction); + } + public static boolean doesBlockStateChangeWarrantNetworkNodeUpdate(final BlockState oldBlockState, final BlockState newBlockState) { if (!(newBlockState.getBlock() instanceof AbstractDirectionalBlock newDirectionalBlock)) { diff --git a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/network/AbstractSchedulingNetworkNodeContainerBlockEntity.java b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/network/AbstractSchedulingNetworkNodeContainerBlockEntity.java index df09b565f..dac1392be 100644 --- a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/network/AbstractSchedulingNetworkNodeContainerBlockEntity.java +++ b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/network/AbstractSchedulingNetworkNodeContainerBlockEntity.java @@ -82,5 +82,5 @@ public void writeScreenOpeningData(final ServerPlayer player, final FriendlyByte protected abstract void setTaskExecutor(TaskExecutor taskExecutor); - protected abstract void setFilters(List filters); + public abstract void setFilters(List filters); } diff --git a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/network/AbstractUpgradeableNetworkNodeContainerBlockEntity.java b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/network/AbstractUpgradeableNetworkNodeContainerBlockEntity.java index 6939537ae..27f36f9ed 100644 --- a/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/network/AbstractUpgradeableNetworkNodeContainerBlockEntity.java +++ b/refinedstorage2-platform-common/src/main/java/com/refinedmods/refinedstorage2/platform/common/support/network/AbstractUpgradeableNetworkNodeContainerBlockEntity.java @@ -10,7 +10,6 @@ import java.util.ArrayList; import java.util.List; -import com.google.common.util.concurrent.RateLimiter; import net.minecraft.core.BlockPos; import net.minecraft.core.NonNullList; import net.minecraft.nbt.CompoundTag; @@ -33,7 +32,8 @@ public abstract class AbstractUpgradeableNetworkNodeContainerBlockEntity type, @@ -52,7 +52,7 @@ protected AbstractUpgradeableNetworkNodeContainerBlockEntity( @Override public final void doWork() { - if (rateLimiter.tryAcquire()) { + if (workTicks++ % workTickRate == 0) { super.doWork(); postDoWork(); } @@ -105,16 +105,12 @@ public void load(final CompoundTag tag) { private void configureAccordingToUpgrades() { LOGGER.debug("Reconfiguring {} for upgrades", getBlockPos()); final int amountOfSpeedUpgrades = upgradeContainer.getAmount(Items.INSTANCE.getSpeedUpgrade()); - this.rateLimiter = createRateLimiter(amountOfSpeedUpgrades); + this.workTickRate = (amountOfSpeedUpgrades + 1) * 20; this.setEnergyUsage(upgradeContainer.getEnergyUsage()); } protected abstract void setEnergyUsage(long upgradeEnergyUsage); - private static RateLimiter createRateLimiter(final int amountOfSpeedUpgrades) { - return RateLimiter.create((double) amountOfSpeedUpgrades + 1); - } - @Override public NonNullList getDrops() { final NonNullList drops = NonNullList.create(); diff --git a/refinedstorage2-platform-forge/build.gradle b/refinedstorage2-platform-forge/build.gradle index 3e5fc0444..e238e0037 100644 --- a/refinedstorage2-platform-forge/build.gradle +++ b/refinedstorage2-platform-forge/build.gradle @@ -32,4 +32,18 @@ dependencies { compileOnly "top.theillusivec4.curios:curios-neoforge:7.1.0+1.20.4:api" } +sourceSets { + test { + minecraft { + modIdentifier = 'rstest' + } + } +} + +runs { + gameTestServer { + systemProperty 'neoforge.enabledGameTestNamespaces', 'refinedstorage2_tests' + } +} + enablePublishing() diff --git a/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/ConstructorTest.java b/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/ConstructorTest.java new file mode 100644 index 000000000..076dbd5ae --- /dev/null +++ b/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/ConstructorTest.java @@ -0,0 +1,49 @@ +package com.refinedmods.refinedstorage2.platform.forge; + +import com.refinedmods.refinedstorage2.api.resource.ResourceAmount; +import com.refinedmods.refinedstorage2.platform.common.constructordestructor.ConstructorBlockEntity; +import com.refinedmods.refinedstorage2.platform.common.storage.ItemStorageType; + +import java.util.List; + +import net.minecraft.core.Direction; +import net.minecraft.gametest.framework.GameTest; +import net.minecraft.world.level.block.Blocks; +import net.neoforged.testframework.annotation.TestHolder; +import net.neoforged.testframework.gametest.EmptyTemplate; +import net.neoforged.testframework.gametest.ExtendedGameTestHelper; + +import static com.refinedmods.refinedstorage2.platform.forge.TestMod.DIRT; +import static com.refinedmods.refinedstorage2.platform.forge.TestMod.RSBLOCKS; +import static com.refinedmods.refinedstorage2.platform.forge.TestMod.itemIsInserted; +import static com.refinedmods.refinedstorage2.platform.forge.TestMod.storageMustContainExactly; +import static net.minecraft.core.BlockPos.ZERO; + +public final class ConstructorTest { + private ConstructorTest() { + } + + @GameTest + @EmptyTemplate(value = "5x5x5", floor = true) + @TestHolder(description = "Tests whether the Constructor can place a block") + public static void shouldPlaceBlock(final ExtendedGameTestHelper helper) { + // Arrange + helper.setBlock(ZERO.above(), RSBLOCKS.getCreativeController().getDefault()); + helper.setBlock(ZERO.above().above(), RSBLOCKS.getConstructor().getDefault().rotated(Direction.EAST)); + helper.setBlock( + ZERO.above().above().above(), + RSBLOCKS.getItemStorageBlock(ItemStorageType.Variant.ONE_K) + ); + + final var seq = helper.startSequence(); + seq.thenWaitUntil(itemIsInserted(helper, ZERO.above().above(), DIRT, 10)); + + // Act + helper.requireBlockEntity(ZERO.above().above(), ConstructorBlockEntity.class).setFilters(List.of(DIRT)); + + // Assert + seq.thenWaitUntil(() -> helper.assertBlockPresent(Blocks.DIRT, ZERO.above().above().east())) + .thenWaitUntil(storageMustContainExactly(helper, ZERO.above().above(), new ResourceAmount(DIRT, 9))) + .thenSucceed(); + } +} diff --git a/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/ExporterGameTest.java b/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/ExporterGameTest.java deleted file mode 100644 index b05f0b472..000000000 --- a/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/ExporterGameTest.java +++ /dev/null @@ -1,21 +0,0 @@ -package com.refinedmods.refinedstorage2.platform.forge; - -import com.refinedmods.refinedstorage2.platform.common.util.IdentifierUtil; - -import net.minecraft.gametest.framework.GameTest; -import net.minecraft.gametest.framework.GameTestHelper; -import net.neoforged.neoforge.gametest.GameTestHolder; -import net.neoforged.neoforge.gametest.PrefixGameTestTemplate; - -@GameTestHolder(IdentifierUtil.MOD_ID) -@PrefixGameTestTemplate(false) -public final class ExporterGameTest { - private ExporterGameTest() { - } - - @GameTest(template = "empty_15x15") - public static void shouldExport(final GameTestHelper test) { - System.out.println("Hello World"); - test.succeed(); - } -} diff --git a/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/TestMod.java b/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/TestMod.java new file mode 100644 index 000000000..2fdf4d06a --- /dev/null +++ b/refinedstorage2-platform-forge/src/test/java/com/refinedmods/refinedstorage2/platform/forge/TestMod.java @@ -0,0 +1,98 @@ +package com.refinedmods.refinedstorage2.platform.forge; + +import com.refinedmods.refinedstorage2.api.core.Action; +import com.refinedmods.refinedstorage2.api.network.Network; +import com.refinedmods.refinedstorage2.api.network.node.NetworkNode; +import com.refinedmods.refinedstorage2.api.network.storage.StorageNetworkComponent; +import com.refinedmods.refinedstorage2.api.resource.ResourceAmount; +import com.refinedmods.refinedstorage2.api.storage.EmptyActor; +import com.refinedmods.refinedstorage2.platform.api.support.network.AbstractNetworkNodeContainerBlockEntity; +import com.refinedmods.refinedstorage2.platform.common.content.Blocks; +import com.refinedmods.refinedstorage2.platform.common.support.resource.ItemResource; +import com.refinedmods.refinedstorage2.platform.common.util.IdentifierUtil; + +import java.util.Arrays; +import javax.annotation.Nullable; + +import net.minecraft.core.BlockPos; +import net.minecraft.gametest.framework.GameTestAssertException; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.world.item.ItemStack; +import net.minecraft.world.item.Items; +import net.neoforged.bus.api.IEventBus; +import net.neoforged.fml.ModLoadingContext; +import net.neoforged.fml.common.Mod; +import net.neoforged.testframework.conf.FrameworkConfiguration; +import net.neoforged.testframework.gametest.ExtendedGameTestHelper; + +@Mod(TestMod.ID) +public class TestMod { + public static final String ID = IdentifierUtil.MOD_ID + "_tests"; + + public static final ItemResource DIRT = ItemResource.ofItemStack(new ItemStack(Items.DIRT)); + public static final Blocks RSBLOCKS = Blocks.INSTANCE; + + public TestMod(final IEventBus eventBus) { + final var framework = FrameworkConfiguration.builder(new ResourceLocation(ID, "tests")) + .build() + .create(); + framework.init(eventBus, ModLoadingContext.get().getActiveContainer()); + } + + @Nullable + public static Network getNetwork(final ExtendedGameTestHelper helper, final BlockPos pos) { + try { + final var be = helper.requireBlockEntity(pos, AbstractNetworkNodeContainerBlockEntity.class); + final var field = AbstractNetworkNodeContainerBlockEntity.class.getDeclaredField("mainNode"); + field.setAccessible(true); + final NetworkNode mainNode = (NetworkNode) field.get(be); + return mainNode.getNetwork(); + } catch (IllegalAccessException | IllegalArgumentException | NoSuchFieldException | SecurityException e) { + throw new RuntimeException(e); + } + } + + public static Runnable itemIsInserted(final ExtendedGameTestHelper helper, + final BlockPos networkPos, + final ItemResource resource, + final long amount) { + return () -> { + final Network network = getNetwork(helper, networkPos); + helper.assertTrue(network != null && network.getComponent(StorageNetworkComponent.class) + .insert(resource, amount, Action.EXECUTE, EmptyActor.INSTANCE) == amount, + "Item couldn't be inserted" + ); + }; + } + + public static Runnable storageMustContainExactly(final ExtendedGameTestHelper helper, + final BlockPos networkPos, + final ResourceAmount... expected) { + return () -> { + final Network network = getNetwork(helper, networkPos); + helper.assertTrue(network != null, "Network is not found"); + if (network == null) { + return; + } + final StorageNetworkComponent storage = network.getComponent(StorageNetworkComponent.class); + for (final ResourceAmount expectedItem : expected) { + final boolean contains = storage.getAll() + .stream() + .anyMatch(inStorage -> inStorage.getResource().equals(expectedItem.getResource()) + && inStorage.getAmount() == expectedItem.getAmount()); + if (!contains) { + throw new GameTestAssertException("Missing from storage: " + expectedItem); + } + } + for (final ResourceAmount inStorage : storage.getAll()) { + final boolean wasExpected = Arrays.stream(expected).anyMatch( + expectedItem -> expectedItem.getResource().equals(inStorage.getResource()) + && expectedItem.getAmount() == inStorage.getAmount() + ); + if (!wasExpected) { + throw new GameTestAssertException("Unexpected in storage: " + inStorage); + } + } + }; + } +} diff --git a/refinedstorage2-platform-forge/src/test/resources/META-INF/mods.toml b/refinedstorage2-platform-forge/src/test/resources/META-INF/mods.toml new file mode 100644 index 000000000..a7c44f750 --- /dev/null +++ b/refinedstorage2-platform-forge/src/test/resources/META-INF/mods.toml @@ -0,0 +1,7 @@ +modLoader = "javafml" +loaderVersion = "[2,)" +license = "MIT" +[[mods]] +modId = "refinedstorage2" +[[mods]] +modId = "refinedstorage2_tests" \ No newline at end of file diff --git a/refinedstorage2-platform-forge/src/test/resources/data/refinedstorage2/structures/empty_15x15.nbt b/refinedstorage2-platform-forge/src/test/resources/data/refinedstorage2/structures/empty_15x15.nbt deleted file mode 100644 index bec09916859500fc9ffe7cf2c71f422e5a60cc17..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 8456 zcmeHMZ)jRq6wla3yKZY>jFe4?9|jv^Z5(TA7`1Uw;ux$AfsMBLqjPDBElI?#P!kg0 zzHEbugi%=f4+C+K(m~U?P)%xLHlbZ7Rcs43(ME<%6r__E<6bpB-`>3rThpiK3J$iS zU!GjfyXT(Y{oUU=_dKz2a}EA+rhD#he^?k${1KHY?te7;xh#3NyLOMn_};7E&$Jvc zok-r=&s_ZOp;_x{{lNOlmcRBMnHPOB*V$lmyBICS4N}vcp2UPXu$)f%#UaDcdYV1% zd9b=Br&15R9K$XjAK+|(<*e2@96x6;ue-yHSY;Su!@IMeCfwuG9gU1}MeUO{oSkS% zI5d}xD_1nix|^}_fsV$waiv>hc)Pvvl`l?Gjl;pN znRlBu4i>S^WKvd*z#Ky6dix1=KdG&w4BMG9Z0E>r?MiYSf(>1#&yj%31EVa*Rzg1S zQW^6ul`(H~8S{El!TWV4Y5KOtA}4-~nqKc)v$k1GO6jpFpIc#)4lZ2qDI}s@i_sp7 zLNwbO+|heSV<~C(#@VXB843Qv2bJD^m)~M)6WZhWXZ%a-(J9}U&_jq1 z`OxtEf5H&7HEm#2;S7j&*IY2z_1j>ur{Hakz+iX6o^%}u!pBaDKum5pCME2Nz5>U@ zz%dPNhY!WA*f>v%T1*SXC3X*bM?Se2_5LVLCoY<@iP?GHgiHOb_5qTBsYoCl;fVKi z3sN6Lvk|Gy8k)DBmn0t=97K{dLLe*G!Z6ron5wh`20I3O>VNT(d_GAGEGzm$Fo6g> zEfK^t2gfu56X<-R1_dR?dhskG2K6P9;t8HILXVPX14CdZI72K9c0B{SC})SpzJMN8#M+g%7=*z!QPokHRrI2t4({F~#AS z9v*~+?EO}>QP~#|3FWu~c?-QHs2gaoWIc)n^(qWOkf3Bz!w`(X5a`=s2okW6U4lK? z;aWW01IIK8d(sn#^Ew<;Gc3+J&rY08zDC)^i;40YB8p%^$`8)Mr?nr3fFXc@fZ5fu zqgZWESE%gx0-y8)ST7#?D^zk+rK7~@cp9aH=2U0;_WQ0pC{LWuFvyF?<)`CZ_--YXoB1OnaIBVEd za4}Hrb`;GT1m$mqx*g|nPT{to%ZdsW4D35dK)8&&A9Yc^A-YgPs@fsYP()qgFu|Vv z|E?@rtQ{|7?ZD}!DW@Ga1!jl0eMdnFQf+tOo{m6M^l9v)kIG-#hne9*S>+^V##SUG zD4`^@`?vGl7#o{D^eDwtB)3F|Zyd&r)lxaC7S2)nPB=&1hA($!xO=VZf;|!RAtVGb z5qKh?;u0Ja{S%UgqBRiS8@Ko#+9`GuPARxiD#n8H48ys!~lE`_rsooa1VjD!Z8teauCEc496sf*qWw#!YQpP zyPCW{G8tiilla{(YB&}1yVq4tHl6f3sZ>bJ(aV82m&y9M%xc(8Q7pS|3mMpmlL<+< On&)DZ`?dz2sregqsUKGW