674 lines
28 KiB
Java
674 lines
28 KiB
Java
package games.dmg.spigotbase;
|
|
|
|
import static org.junit.jupiter.api.Assertions.assertEquals;
|
|
import static org.junit.jupiter.api.Assertions.assertFalse;
|
|
import static org.junit.jupiter.api.Assertions.assertTrue;
|
|
import static org.mockito.ArgumentMatchers.any;
|
|
import static org.mockito.ArgumentMatchers.anyString;
|
|
import static org.mockito.Mockito.mock;
|
|
import static org.mockito.Mockito.never;
|
|
import static org.mockito.Mockito.times;
|
|
import static org.mockito.Mockito.verify;
|
|
import static org.mockito.Mockito.when;
|
|
|
|
import java.io.IOException;
|
|
import java.time.Instant;
|
|
import java.util.List;
|
|
import java.util.Map;
|
|
import java.util.Optional;
|
|
import java.util.UUID;
|
|
import java.util.concurrent.atomic.AtomicReference;
|
|
import java.util.function.UnaryOperator;
|
|
import org.bukkit.ChatColor;
|
|
import org.bukkit.Material;
|
|
import org.bukkit.command.CommandSender;
|
|
import org.bukkit.entity.Player;
|
|
import org.bukkit.inventory.ItemStack;
|
|
import org.bukkit.inventory.PlayerInventory;
|
|
import net.kyori.adventure.dialog.DialogLike;
|
|
import org.junit.jupiter.api.Test;
|
|
import org.mockito.ArgumentCaptor;
|
|
|
|
final class BaseSettingsCommandTest {
|
|
@Test
|
|
void rejectsNonPlayerExecution() {
|
|
CommandSender sender = mock(CommandSender.class);
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
mock(BaseStateManager.class),
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class)
|
|
);
|
|
|
|
command.onCommand(sender, null, "basesettings", new String[0]);
|
|
|
|
verify(sender).sendMessage("Only players have base progression.");
|
|
}
|
|
|
|
@Test
|
|
void spawnableEnableIsIdempotentAfterUnlock() {
|
|
UUID playerId = UUID.randomUUID();
|
|
PlayerState current = PlayerState.newPlayer(playerId, "Builder")
|
|
.withAdministrativeLevels(1, 0, 0, 0, 0, false, false, false)
|
|
.withBase(
|
|
new BaseLocation(UUID.randomUUID(), "world", 0, 64, 0, 0, 0),
|
|
Instant.EPOCH
|
|
)
|
|
.withTotalBlocksPlaced(250);
|
|
|
|
CommandResult result = execute(current, "spawnable", "enable");
|
|
|
|
assertTrue(result.updated().spawnableOverlayEnabled());
|
|
}
|
|
|
|
@Test
|
|
void borderEnableIsIdempotent() {
|
|
UUID playerId = UUID.randomUUID();
|
|
PlayerState current = PlayerState.newPlayer(playerId, "Builder")
|
|
.withAdministrativeLevels(1, 0, 0, 0, 0, false, false, false)
|
|
.withBase(
|
|
new BaseLocation(UUID.randomUUID(), "world", 0, 64, 0, 0, 0),
|
|
Instant.EPOCH
|
|
);
|
|
|
|
CommandResult result = execute(current, "border", "enable");
|
|
|
|
assertTrue(result.updated().borderEnabled());
|
|
}
|
|
|
|
@Test
|
|
void invalidArgumentsShowUsage() {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder"))
|
|
.thenReturn(PlayerState.newPlayer(playerId, "Builder"));
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class)
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {"unknown"});
|
|
|
|
verify(player).sendMessage(org.mockito.ArgumentMatchers.<String>argThat(
|
|
message -> message.contains("Usage: /basesettings")
|
|
));
|
|
}
|
|
|
|
@Test
|
|
void autocompletesValuesForEachSetting() {
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
mock(BaseStateManager.class),
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class)
|
|
);
|
|
|
|
assertEquals(
|
|
List.of("allowed"),
|
|
command.onTabComplete(null, null, "basesettings", new String[] {"visitors", "a"})
|
|
);
|
|
assertEquals(
|
|
List.of("upgrade"),
|
|
command.onTabComplete(null, null, "basesettings", new String[] {"pocket", "u"})
|
|
);
|
|
assertEquals(
|
|
List.of("flight"),
|
|
command.onTabComplete(null, null, "basesettings", new String[] {"pocket", "f"})
|
|
);
|
|
assertEquals(
|
|
List.of("disable"),
|
|
command.onTabComplete(
|
|
null, null, "basesettings", new String[] {"pocket", "flight", "d"}
|
|
)
|
|
);
|
|
assertEquals(
|
|
List.of("mobs"),
|
|
command.onTabComplete(null, null, "basesettings", new String[] {"pocket", "m"})
|
|
);
|
|
assertEquals(
|
|
List.of("type"),
|
|
command.onTabComplete(null, null, "basesettings", new String[] {"pocket", "t"})
|
|
);
|
|
assertEquals(
|
|
List.of("nether"),
|
|
command.onTabComplete(
|
|
null, null, "basesettings", new String[] {"pocket", "type", "n"}
|
|
)
|
|
);
|
|
assertEquals(
|
|
List.of("crimson_forest"),
|
|
command.onTabComplete(
|
|
null,
|
|
null,
|
|
"basesettings",
|
|
new String[] {"pocket", "type", "nether", "c"}
|
|
)
|
|
);
|
|
assertEquals(
|
|
List.of("hostile"),
|
|
command.onTabComplete(
|
|
null, null, "basesettings", new String[] {"pocket", "mobs", "h"}
|
|
)
|
|
);
|
|
assertEquals(
|
|
List.of("passive"),
|
|
command.onTabComplete(
|
|
null, null, "basesettings", new String[] {"pocket", "mobs", "p"}
|
|
)
|
|
);
|
|
assertEquals(
|
|
List.of("enable"),
|
|
command.onTabComplete(
|
|
null, null, "basesettings",
|
|
new String[] {"pocket", "mobs", "hostile", "e"}
|
|
)
|
|
);
|
|
for (String setting : List.of("navigation", "flight", "border", "spawnable", "bossbar")) {
|
|
assertEquals(
|
|
List.of("disable"),
|
|
command.onTabComplete(null, null, "basesettings", new String[] {setting, "d"})
|
|
);
|
|
}
|
|
}
|
|
|
|
@Test
|
|
void autocompletesSettingNames() {
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
mock(BaseStateManager.class),
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class)
|
|
);
|
|
|
|
assertEquals(
|
|
List.of(
|
|
"ui", "status", "upgrade", "pocket", "visitors", "navigation", "flight",
|
|
"border", "spawnable", "bossbar"
|
|
),
|
|
command.onTabComplete(null, null, "basesettings", new String[] {""})
|
|
);
|
|
}
|
|
|
|
@Test
|
|
void upgradePurchasesBaseIv() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Host");
|
|
PlayerInventory inventory = mock(PlayerInventory.class);
|
|
ItemStack firstStack = item(Material.DIAMOND, 64);
|
|
ItemStack secondStack = item(Material.DIAMOND, 64);
|
|
when(player.getInventory()).thenReturn(inventory);
|
|
when(inventory.getStorageContents()).thenReturn(new ItemStack[] {
|
|
firstStack,
|
|
secondStack
|
|
});
|
|
|
|
PlayerState current = PlayerState.newPlayer(playerId, "Host")
|
|
.withAdministrativeLevels(3, 0, 0, 0, 0, false, false, false)
|
|
.withBase(
|
|
new BaseLocation(UUID.randomUUID(), "world", 0, 64, 0, 0, 0),
|
|
Instant.EPOCH
|
|
);
|
|
AtomicReference<PlayerState> updated = new AtomicReference<>();
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Host")).thenReturn(current);
|
|
when(stateManager.updateAndSave(any(), anyString(), any())).thenAnswer(invocation -> {
|
|
@SuppressWarnings("unchecked")
|
|
UnaryOperator<PlayerState> operation = invocation.getArgument(2);
|
|
PlayerState result = operation.apply(current);
|
|
updated.set(result);
|
|
return result;
|
|
});
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class)
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {"upgrade"});
|
|
|
|
assertEquals(4, updated.get().baseLevel());
|
|
assertTrue(updated.get().visitorsEnabled());
|
|
}
|
|
|
|
@Test
|
|
void pocketUpgradePurchasesFirstLevelAfterBaseIv() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
PlayerInventory inventory = mock(PlayerInventory.class);
|
|
ItemStack currency = item(Material.DIAMOND_BLOCK, 64);
|
|
when(player.getInventory()).thenReturn(inventory);
|
|
when(inventory.getStorageContents()).thenReturn(new ItemStack[] {currency});
|
|
PlayerState owner = PlayerState.newPlayer(playerId, "Builder")
|
|
.withAdministrativeLevels(4, 0, 0, 0, 0, false, false, true)
|
|
.withBase(
|
|
new BaseLocation(UUID.randomUUID(), "world", 0, 64, 0, 0, 0),
|
|
Instant.EPOCH
|
|
);
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder")).thenReturn(owner);
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
when(pocketBases.state(playerId)).thenReturn(PocketBaseState.locked(playerId));
|
|
when(pocketBases.upgrade(playerId)).thenReturn(
|
|
new PocketBaseState(playerId, 1, java.util.Optional.empty())
|
|
);
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {"pocket", "upgrade"});
|
|
|
|
verify(pocketBases).upgrade(playerId);
|
|
verify(inventory).setStorageContents(any(ItemStack[].class));
|
|
}
|
|
|
|
@Test
|
|
void pocketOwnerCanPurchaseBiomeChangeWithConfiguredCurrency() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
PlayerInventory inventory = mock(PlayerInventory.class);
|
|
ItemStack currency = item(Material.NETHERITE_BLOCK, 16);
|
|
when(player.getInventory()).thenReturn(inventory);
|
|
when(inventory.getStorageContents()).thenReturn(new ItemStack[] {currency});
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder"))
|
|
.thenReturn(PlayerState.newPlayer(playerId, "Builder"));
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
PocketBaseState current = new PocketBaseState(playerId, 1, java.util.Optional.empty());
|
|
when(pocketBases.state(playerId)).thenReturn(current);
|
|
when(pocketBases.setBiome(playerId, PocketBaseBiome.CRIMSON_FOREST))
|
|
.thenReturn(current.withBiome(PocketBaseBiome.CRIMSON_FOREST));
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {
|
|
"pocket", "type", "nether", "crimson_forest"
|
|
});
|
|
|
|
verify(pocketBases).setBiome(playerId, PocketBaseBiome.CRIMSON_FOREST);
|
|
verify(inventory).setStorageContents(any(ItemStack[].class));
|
|
}
|
|
|
|
@Test
|
|
void selectingCurrentPocketBiomeDoesNotCharge() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
PlayerInventory inventory = mock(PlayerInventory.class);
|
|
when(player.getInventory()).thenReturn(inventory);
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder"))
|
|
.thenReturn(PlayerState.newPlayer(playerId, "Builder"));
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
when(pocketBases.state(playerId)).thenReturn(
|
|
new PocketBaseState(playerId, 1, java.util.Optional.empty())
|
|
);
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {
|
|
"pocket", "type", "void", "the_void"
|
|
});
|
|
|
|
verify(pocketBases, never()).setBiome(
|
|
org.mockito.ArgumentMatchers.eq(playerId),
|
|
org.mockito.ArgumentMatchers.any(PocketBaseBiome.class)
|
|
);
|
|
verify(inventory, never()).setStorageContents(any(ItemStack[].class));
|
|
}
|
|
|
|
@Test
|
|
void pocketOwnerCanEnableHostileMobSpawningWithoutChangingPassive() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder"))
|
|
.thenReturn(PlayerState.newPlayer(playerId, "Builder"));
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
PocketBaseState current = new PocketBaseState(
|
|
playerId, 1, java.util.Optional.empty(), java.util.Optional.empty(),
|
|
false, true, PocketBaseBiome.THE_VOID
|
|
);
|
|
when(pocketBases.state(playerId)).thenReturn(current);
|
|
when(pocketBases.setHostileMobSpawning(playerId, true)).thenReturn(
|
|
current.withHostileMobSpawningEnabled(true)
|
|
);
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {
|
|
"pocket", "mobs", "hostile", "enable"
|
|
});
|
|
|
|
verify(pocketBases).setHostileMobSpawning(playerId, true);
|
|
verify(pocketBases, never()).setPassiveMobSpawning(playerId, true);
|
|
verify(player).sendMessage(org.mockito.ArgumentMatchers.<String>argThat(
|
|
message -> message.contains("hostile mob spawning") && message.contains("enabled")
|
|
));
|
|
}
|
|
|
|
@Test
|
|
void failedPocketMobSpawningChangeReportsOnlyFailure() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder"))
|
|
.thenReturn(PlayerState.newPlayer(playerId, "Builder"));
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
when(pocketBases.state(playerId)).thenReturn(
|
|
new PocketBaseState(playerId, 1, java.util.Optional.empty())
|
|
);
|
|
when(pocketBases.setPassiveMobSpawning(playerId, true))
|
|
.thenThrow(new IOException("save failed"));
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {
|
|
"pocket", "mobs", "passive", "enable"
|
|
});
|
|
|
|
verify(player).sendMessage(org.mockito.ArgumentMatchers.<String>argThat(
|
|
message -> message.contains("could not be changed")
|
|
));
|
|
verify(player, never()).sendMessage(org.mockito.ArgumentMatchers.<String>argThat(
|
|
message -> message.contains("is now")
|
|
));
|
|
}
|
|
|
|
@Test
|
|
void lockedPlayerCannotEnablePocketMobSpawning() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder"))
|
|
.thenReturn(PlayerState.newPlayer(playerId, "Builder"));
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
when(pocketBases.state(playerId)).thenReturn(PocketBaseState.locked(playerId));
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {
|
|
"pocket", "mobs", "hostile", "enable"
|
|
});
|
|
|
|
verify(pocketBases, never()).setHostileMobSpawning(playerId, true);
|
|
verify(player).sendMessage(org.mockito.ArgumentMatchers.<String>argThat(
|
|
message -> message.contains("Pocket Base I") && message.contains("locked")
|
|
));
|
|
}
|
|
|
|
@Test
|
|
void failedPocketUpgradeRestoresPayment() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
PlayerInventory inventory = mock(PlayerInventory.class);
|
|
ItemStack currency = item(Material.DIAMOND_BLOCK, 64);
|
|
when(player.getInventory()).thenReturn(inventory);
|
|
when(inventory.getStorageContents()).thenReturn(new ItemStack[] {currency});
|
|
PlayerState owner = PlayerState.newPlayer(playerId, "Builder")
|
|
.withAdministrativeLevels(4, 0, 0, 0, 0, false, false, true)
|
|
.withBase(
|
|
new BaseLocation(UUID.randomUUID(), "world", 0, 64, 0, 0, 0),
|
|
Instant.EPOCH
|
|
);
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder")).thenReturn(owner);
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
when(pocketBases.state(playerId)).thenReturn(PocketBaseState.locked(playerId));
|
|
when(pocketBases.upgrade(playerId)).thenThrow(new IOException("save failed"));
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {"pocket", "upgrade"});
|
|
|
|
ArgumentCaptor<ItemStack[]> contents = ArgumentCaptor.forClass(ItemStack[].class);
|
|
verify(inventory, times(2)).setStorageContents(contents.capture());
|
|
ItemStack[] restored = contents.getAllValues().get(1);
|
|
assertEquals(Material.DIAMOND_BLOCK, restored[0].getType());
|
|
assertEquals(64, restored[0].getAmount());
|
|
}
|
|
|
|
@Test
|
|
void ownerCanDisableAutomaticPocketBaseFlight() throws Exception {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder")).thenReturn(
|
|
PlayerState.newPlayer(playerId, "Builder")
|
|
);
|
|
PocketBaseState enabled = new PocketBaseState(playerId, 1, Optional.empty())
|
|
.withFlightUnlocked();
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
when(pocketBases.state(playerId)).thenReturn(enabled);
|
|
when(pocketBases.setFlightEnabled(playerId, false)).thenReturn(
|
|
enabled.withFlightEnabled(false)
|
|
);
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(
|
|
player, null, "basesettings",
|
|
new String[] {"pocket", "flight", "disable"}
|
|
);
|
|
|
|
verify(pocketBases).setFlightEnabled(playerId, false);
|
|
verify(player).sendMessage(org.mockito.ArgumentMatchers.<String>argThat(
|
|
message -> message.contains("automatic flight") && message.contains("disabled")
|
|
));
|
|
}
|
|
|
|
@Test
|
|
void statusDisplaysPocketMobSpawningPreferences() {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder"))
|
|
.thenReturn(PlayerState.newPlayer(playerId, "Builder"));
|
|
PocketBaseManager pocketBases = mock(PocketBaseManager.class);
|
|
when(pocketBases.state(playerId)).thenReturn(
|
|
new PocketBaseState(
|
|
playerId, 1, java.util.Optional.empty(), java.util.Optional.empty(),
|
|
true, false, PocketBaseBiome.THE_VOID
|
|
)
|
|
);
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
pocketBases
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[] {"status"});
|
|
|
|
verify(player).sendMessage(org.mockito.ArgumentMatchers.<String>argThat(
|
|
message -> message.contains("Pocket Base 1")
|
|
&& message.contains("type=void/the_void")
|
|
&& message.contains("hostile spawning=enabled")
|
|
&& message.contains("passive spawning=disabled")
|
|
&& message.contains("flight=complete a raid to unlock")
|
|
));
|
|
}
|
|
|
|
@Test
|
|
void bossbarEnableIsIdempotent() {
|
|
UUID playerId = UUID.randomUUID();
|
|
PlayerState current = PlayerState.newPlayer(playerId, "Miner");
|
|
|
|
CommandResult result = execute(current, "bossbar", "enable");
|
|
|
|
assertTrue(result.updated().bossBarEnabled());
|
|
}
|
|
|
|
@Test
|
|
void flightDisableIsIdempotentAndRemovesGrantedFlight() {
|
|
UUID playerId = UUID.randomUUID();
|
|
PlayerState current = PlayerState.newPlayer(playerId, "Pilot")
|
|
.withAdministrativeLevels(1, 0, 1, 0, 0, false, true, false);
|
|
|
|
CommandResult result = execute(current, "flight", "disable");
|
|
|
|
assertFalse(result.updated().flightEnabled());
|
|
verify(result.flightController()).removeGrantedFlight(any(Player.class));
|
|
}
|
|
|
|
@Test
|
|
void navigationDisableIsIdempotent() {
|
|
UUID playerId = UUID.randomUUID();
|
|
PlayerState current = PlayerState.newPlayer(playerId, "Explorer")
|
|
.withAdministrativeLevels(2, 0, 0, 0, 0, true, false, false)
|
|
.withBase(
|
|
new BaseLocation(UUID.randomUUID(), "world", 0, 64, 0, 0, 0),
|
|
Instant.EPOCH
|
|
);
|
|
|
|
CommandResult result = execute(current, "navigation", "disable");
|
|
|
|
assertFalse(result.updated().navigationEnabled());
|
|
}
|
|
|
|
@Test
|
|
void visitorsAllowedIsIdempotent() {
|
|
UUID playerId = UUID.randomUUID();
|
|
PlayerState current = PlayerState.newPlayer(playerId, "Host")
|
|
.withAdministrativeLevels(4, 0, 0, 0, 0, false, false, true);
|
|
|
|
CommandResult result = execute(current, "visitors", "allowed");
|
|
|
|
assertTrue(result.updated().visitorsEnabled());
|
|
}
|
|
|
|
@Test
|
|
void defaultAndUiOpenDialogWhileStatusDisplaysTheFullProgressReport() {
|
|
UUID playerId = UUID.randomUUID();
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(playerId);
|
|
when(player.getName()).thenReturn("Builder");
|
|
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(playerId, "Builder"))
|
|
.thenReturn(PlayerState.newPlayer(playerId, "Builder"));
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
mock(BaseFlightController.class),
|
|
null,
|
|
(owner, pocket) -> null
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", new String[0]);
|
|
command.onCommand(player, null, "homesettings", new String[] {"ui"});
|
|
command.onCommand(player, null, "basesettings", new String[] {"status"});
|
|
|
|
verify(player, times(2)).showDialog((DialogLike) null);
|
|
verify(player).sendMessage(ChatColor.GOLD + "=== Base Progress ===");
|
|
verify(player).sendMessage(
|
|
org.mockito.ArgumentMatchers.<String>argThat(message ->
|
|
message.contains("Spawnable Overlay:")
|
|
&& message.contains("0/250 placements")
|
|
&& message.contains("locked")
|
|
)
|
|
);
|
|
verify(player).sendMessage(
|
|
org.mockito.ArgumentMatchers.<String>argThat(message ->
|
|
message.contains("Settings: visitors=")
|
|
&& message.contains("navigation=")
|
|
&& message.contains("flight=")
|
|
&& message.contains("border=")
|
|
&& message.contains("spawnable=")
|
|
&& message.contains("bossbar=")
|
|
)
|
|
);
|
|
}
|
|
|
|
private static ItemStack item(Material material, int amount) {
|
|
ItemStack item = mock(ItemStack.class);
|
|
ItemStack copy = mock(ItemStack.class);
|
|
when(item.getType()).thenReturn(material);
|
|
when(item.getAmount()).thenReturn(amount);
|
|
when(item.clone()).thenReturn(copy);
|
|
when(copy.getType()).thenReturn(material);
|
|
when(copy.getAmount()).thenReturn(amount);
|
|
when(copy.clone()).thenReturn(copy);
|
|
return item;
|
|
}
|
|
|
|
private static CommandResult execute(PlayerState current, String... arguments) {
|
|
Player player = mock(Player.class);
|
|
when(player.getUniqueId()).thenReturn(current.playerId());
|
|
when(player.getName()).thenReturn(current.latestName());
|
|
|
|
AtomicReference<PlayerState> updated = new AtomicReference<>();
|
|
BaseStateManager stateManager = mock(BaseStateManager.class);
|
|
when(stateManager.player(current.playerId(), current.latestName())).thenReturn(current);
|
|
when(stateManager.update(any(), anyString(), any())).thenAnswer(invocation -> {
|
|
@SuppressWarnings("unchecked")
|
|
UnaryOperator<PlayerState> operation = invocation.getArgument(2);
|
|
PlayerState result = operation.apply(current);
|
|
updated.set(result);
|
|
return result;
|
|
});
|
|
BaseFlightController flightController = mock(BaseFlightController.class);
|
|
BaseSettingsCommand command = new BaseSettingsCommand(
|
|
stateManager,
|
|
new PluginSettingsProvider(PluginSettings.from(Map.of())),
|
|
flightController
|
|
);
|
|
|
|
command.onCommand(player, null, "basesettings", arguments);
|
|
return new CommandResult(updated.get(), flightController);
|
|
}
|
|
|
|
private record CommandResult(PlayerState updated, BaseFlightController flightController) {
|
|
}
|
|
}
|