Merge pull request #2152 from BentoBoxWorld/develop

Version 1.24.0
This commit is contained in:
tastybento 2023-07-03 16:27:37 -07:00 committed by GitHub
commit 363b23a049
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
84 changed files with 2304 additions and 342 deletions

View File

@ -10,22 +10,22 @@ jobs:
name: Build
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v3
with:
fetch-depth: 0 # Shallow clones should be disabled for a better relevancy of analysis
- name: Set up JDK 17
uses: actions/setup-java@v2
uses: actions/setup-java@v3
with:
distribution: 'adopt'
java-version: '17'
- name: Cache SonarCloud packages
uses: actions/cache@v2
uses: actions/cache@v3
with:
path: ~/.sonar/cache
key: ${{ runner.os }}-sonar
restore-keys: ${{ runner.os }}-sonar
- name: Cache Maven packages
uses: actions/cache@v2
uses: actions/cache@v3
with:
path: ~/.m2
key: ${{ runner.os }}-m2-${{ hashFiles('**/pom.xml') }}
@ -38,7 +38,7 @@ jobs:
- run: mvn --batch-mode clean org.jacoco:jacoco-maven-plugin:prepare-agent install
- run: mkdir staging && cp target/*.jar staging
- name: Save artifacts
uses: actions/upload-artifact@v2
uses: actions/upload-artifact@v3
with:
name: Package
path: staging

View File

@ -73,10 +73,10 @@
<postgresql.version>42.2.18</postgresql.version>
<hikaricp.version>5.0.1</hikaricp.version>
<!-- More visible way to change dependency versions -->
<spigot.version>1.19.4-R0.1-SNAPSHOT</spigot.version>
<spigot.version>1.20.1-R0.1-SNAPSHOT</spigot.version>
<!-- Might differ from the last Spigot release for short periods
of time -->
<paper.version>1.19.3-R0.1-SNAPSHOT</paper.version>
<paper.version>1.20.1-R0.1-SNAPSHOT</paper.version>
<bstats.version>3.0.0</bstats.version>
<vault.version>1.7.1</vault.version>
<placeholderapi.version>2.10.9</placeholderapi.version>
@ -88,7 +88,7 @@
<!-- Do not change unless you want different name for local builds. -->
<build.number>-LOCAL</build.number>
<!-- This allows to change between versions. -->
<build.version>1.23.2</build.version>
<build.version>1.24.0</build.version>
<sonar.organization>bentobox-world</sonar.organization>
<sonar.host.url>https://sonarcloud.io</sonar.host.url>
<server.jars>${project.basedir}/lib</server.jars>

View File

@ -5,6 +5,9 @@ import java.util.Optional;
import org.apache.commons.lang.exception.ExceptionUtils;
import org.bukkit.Bukkit;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.server.ServerCommandEvent;
import org.bukkit.generator.ChunkGenerator;
import org.bukkit.plugin.PluginManager;
import org.bukkit.plugin.java.JavaPlugin;
@ -36,7 +39,6 @@ import world.bentobox.bentobox.managers.BlueprintsManager;
import world.bentobox.bentobox.managers.CommandsManager;
import world.bentobox.bentobox.managers.FlagsManager;
import world.bentobox.bentobox.managers.HooksManager;
import world.bentobox.bentobox.managers.IslandChunkDeletionManager;
import world.bentobox.bentobox.managers.IslandDeletionManager;
import world.bentobox.bentobox.managers.IslandWorldManager;
import world.bentobox.bentobox.managers.IslandsManager;
@ -52,7 +54,7 @@ import world.bentobox.bentobox.versions.ServerCompatibility;
* Main BentoBox class
* @author tastybento, Poslovitch
*/
public class BentoBox extends JavaPlugin {
public class BentoBox extends JavaPlugin implements Listener {
private static BentoBox instance;
@ -71,7 +73,6 @@ public class BentoBox extends JavaPlugin {
private HooksManager hooksManager;
private PlaceholdersManager placeholdersManager;
private IslandDeletionManager islandDeletionManager;
private IslandChunkDeletionManager islandChunkDeletionManager;
private WebManager webManager;
// Settings
@ -227,7 +228,7 @@ public class BentoBox extends JavaPlugin {
// Make sure all worlds are already registered to Multiverse.
hooksManager.registerHook(new MultiverseCoreHook());
hooksManager.registerHook(new MyWorldsHook());
islandWorldManager.registerWorldsToMultiverse();
islandWorldManager.registerWorldsToMultiverse(true);
// TODO: re-enable after implementation
//hooksManager.registerHook(new DynmapHook());
@ -300,8 +301,9 @@ public class BentoBox extends JavaPlugin {
manager.registerEvents(new BannedCommands(this), this);
// Death counter
manager.registerEvents(new DeathListener(this), this);
// MV unregister
manager.registerEvents(this, this);
// Island Delete Manager
islandChunkDeletionManager = new IslandChunkDeletionManager(this);
islandDeletionManager = new IslandDeletionManager(this);
manager.registerEvents(islandDeletionManager, this);
}
@ -321,6 +323,15 @@ public class BentoBox extends JavaPlugin {
if (islandsManager != null) {
islandsManager.shutdown();
}
}
@EventHandler
public void onServerStop(ServerCommandEvent e) {
if (islandWorldManager != null && (e.getCommand().equalsIgnoreCase("stop") || e.getCommand().equalsIgnoreCase("restart"))) {
// Unregister any MV worlds if () {
islandWorldManager.registerWorldsToMultiverse(false);
}
}
/**
@ -531,13 +542,6 @@ public class BentoBox extends JavaPlugin {
return islandDeletionManager;
}
/**
* @return the islandChunkDeletionManager
*/
public IslandChunkDeletionManager getIslandChunkDeletionManager() {
return islandChunkDeletionManager;
}
/**
* @return an optional of the Bstats instance
* @since 1.1

View File

@ -48,6 +48,13 @@ public abstract class CompositeCommand extends Command implements PluginIdentifi
*/
private boolean onlyPlayer = false;
/**
* True if the command is only for the console
* @since 1.24.0
*/
private boolean onlyConsole = false;
/**
* True if command is a configurable rank
*/
@ -241,7 +248,6 @@ public abstract class CompositeCommand extends Command implements PluginIdentifi
CompositeCommand cmd = getCommandFromArgs(args);
String cmdLabel = (cmd.subCommandLevel > 0) ? args[cmd.subCommandLevel-1] : label;
List<String> cmdArgs = Arrays.asList(args).subList(cmd.subCommandLevel, args.length);
// Call
return cmd.call(user, cmdLabel, cmdArgs);
}
@ -257,17 +263,21 @@ public abstract class CompositeCommand extends Command implements PluginIdentifi
*/
public boolean call(User user, String cmdLabel, List<String> cmdArgs) {
// Check for console and permissions
if (onlyPlayer && !user.isPlayer()) {
if (isOnlyPlayer() && !user.isPlayer()) {
user.sendMessage("general.errors.use-in-game");
return false;
}
if (isOnlyConsole() && user.isPlayer()) {
user.sendMessage("general.errors.use-in-console");
return false;
}
if (!this.runPermissionCheck(user))
{
// Error message is displayed by permission check.
return false;
}
// Set the user's addon context
user.setAddon(addon);
// Execute and trim args
@ -513,6 +523,14 @@ public abstract class CompositeCommand extends Command implements PluginIdentifi
return onlyPlayer;
}
/**
* Check if this command is only for consoles.
* @return true or false
*/
public boolean isOnlyConsole() {
return onlyConsole;
}
/**
* Sets whether this command should only be run by players.
* If this is set to {@code true}, this command will only be runnable by objects implementing {@link Player}.
@ -525,6 +543,18 @@ public abstract class CompositeCommand extends Command implements PluginIdentifi
this.onlyPlayer = onlyPlayer;
}
/**
* Sets whether this command should only be run in the console.
* This is for commands that dump a lot of data or are for debugging.
* The default value provided when instantiating this CompositeCommand is {@code false}.
* Therefore, this method should only be used in case you want to explicitly edit the value.
* @param onlyConsole {@code true} if this command should only be run in the console.
* @since 1.24.0
*/
public void setOnlyConsole(boolean onlyConsole) {
this.onlyConsole = onlyConsole;
}
/**
* Sets locale reference to this command's description.
* It is used to display the help of this command.
@ -623,16 +653,17 @@ public abstract class CompositeCommand extends Command implements PluginIdentifi
@Override
@NonNull
public List<String> tabComplete(final @NonNull CommandSender sender, final @NonNull String alias, final String[] args) {
List<String> options = new ArrayList<>();
// Get command object based on args entered so far
CompositeCommand command = getCommandFromArgs(args);
// Check for console and permissions
if (command.isOnlyPlayer() && !(sender instanceof Player)) {
return options;
if ((command.isOnlyPlayer() && !(sender instanceof Player))
|| (command.isOnlyConsole() && sender instanceof Player)) {
return List.of();
}
if (command.getPermission() != null && !command.getPermission().isEmpty() && !sender.hasPermission(command.getPermission()) && !sender.isOp()) {
return options;
return List.of();
}
List<String> options = new ArrayList<>();
// Add any tab completion from the subcommand
options.addAll(command.tabComplete(User.getInstance(sender), alias, new LinkedList<>(Arrays.asList(args))).orElseGet(ArrayList::new));
if (command.hasSubCommands()) {
@ -654,17 +685,26 @@ public abstract class CompositeCommand extends Command implements PluginIdentifi
}
/**
* Returns a list containing all the labels of the subcommands for the provided CompositeCommand excluding any hidden commands
* Returns a list containing all the labels of the subcommands for the provided
* CompositeCommand excluding any hidden commands
* @param sender the CommandSender
* @param command the CompositeCommand to get the subcommands from
* @return a list of subcommands labels or an empty list.
*/
@NonNull
private List<String> getSubCommandLabels(@NonNull CommandSender sender, @NonNull CompositeCommand command) {
return command.getSubCommands().values().stream()
.filter(cmd -> !cmd.isHidden())
.filter(cmd -> !cmd.isOnlyPlayer() || sender.isOp() || (sender instanceof Player && cmd.getPermission() != null && (cmd.getPermission().isEmpty() || sender.hasPermission(cmd.getPermission()))) )
.map(CompositeCommand::getLabel).toList();
List<String> result = new ArrayList<>();
for (CompositeCommand cc: command.getSubCommands().values()) {
// Player or not
if (sender instanceof Player) {
if (!cc.isHidden() && !cc.isOnlyConsole() && (cc.getPermission().isEmpty() || sender.hasPermission(cc.getPermission()))) {
result.add(cc.getLabel());
}
} else if (!cc.isOnlyPlayer()) {
result.add(cc.getLabel());
}
}
return result;
}
/**

View File

@ -35,7 +35,7 @@ public class AdminInfoCommand extends CompositeCommand {
}
// If there are no args, then the player wants info on the island at this location
if (args.isEmpty()) {
getIslands().getIslandAt(user.getLocation()).ifPresentOrElse(i -> new IslandInfo(i).showAdminInfo(user), () ->
getIslands().getIslandAt(user.getLocation()).ifPresentOrElse(i -> new IslandInfo(i).showAdminInfo(user, getAddon()), () ->
user.sendMessage("commands.admin.info.no-island"));
return true;
}
@ -48,7 +48,7 @@ public class AdminInfoCommand extends CompositeCommand {
// Show info for this player
Island island = getIslands().getIsland(getWorld(), targetUUID);
if (island != null) {
new IslandInfo(island).showAdminInfo(user);
new IslandInfo(island).showAdminInfo(user, getAddon());
if (!getIslands().getQuarantinedIslandByUser(getWorld(), targetUUID).isEmpty()) {
user.sendMessage("commands.admin.info.islands-in-trash");
}

View File

@ -19,7 +19,7 @@ public class AdminBlueprintCopyCommand extends CompositeCommand
@Override
public void setup()
{
inheritPermission();
setPermission("admin.blueprint.copy");
setParametersHelp("commands.admin.blueprint.copy.parameters");
setDescription("commands.admin.blueprint.copy.description");
}
@ -37,7 +37,7 @@ public class AdminBlueprintCopyCommand extends CompositeCommand
AdminBlueprintCommand parent = (AdminBlueprintCommand) getParent();
BlueprintClipboard clipboard =
parent.getClipboards().computeIfAbsent(user.getUniqueId(), v -> new BlueprintClipboard());
parent.getClipboards().computeIfAbsent(user.getUniqueId(), v -> new BlueprintClipboard());
boolean copyAir = args.stream().anyMatch(key -> key.equalsIgnoreCase("air"));
boolean copyBiome = args.stream().anyMatch(key -> key.equalsIgnoreCase("biome"));

View File

@ -26,7 +26,7 @@ public class AdminBlueprintDeleteCommand extends ConfirmableCommand
@Override
public void setup()
{
this.inheritPermission();
setPermission("admin.blueprint.delete");
this.setParametersHelp("commands.admin.blueprint.delete.parameters");
this.setDescription("commands.admin.blueprint.delete.description");
}
@ -47,10 +47,10 @@ public class AdminBlueprintDeleteCommand extends ConfirmableCommand
if (this.getPlugin().getBlueprintsManager().getBlueprints(this.getAddon()).containsKey(blueprintName))
{
this.askConfirmation(user, user.getTranslation("commands.admin.blueprint.delete.confirmation"),
() -> {
this.getPlugin().getBlueprintsManager().deleteBlueprint(this.getAddon(), blueprintName);
user.sendMessage("commands.admin.blueprint.delete.success", TextVariables.NAME, blueprintName);
});
() -> {
this.getPlugin().getBlueprintsManager().deleteBlueprint(this.getAddon(), blueprintName);
user.sendMessage("commands.admin.blueprint.delete.success", TextVariables.NAME, blueprintName);
});
return true;
}
else

View File

@ -22,7 +22,7 @@ public class AdminBlueprintListCommand extends CompositeCommand
@Override
public void setup()
{
this.inheritPermission();
setPermission("admin.blueprint.list");
this.setDescription("commands.admin.blueprint.list.description");
}
@ -54,8 +54,8 @@ public class AdminBlueprintListCommand extends CompositeCommand
FilenameFilter blueprintFilter = (File dir, String name) -> name.endsWith(BlueprintsManager.BLUEPRINT_SUFFIX);
List<String> blueprintList = Arrays.stream(Objects.requireNonNull(blueprints.list(blueprintFilter))).
map(name -> name.substring(0, name.length() - BlueprintsManager.BLUEPRINT_SUFFIX.length())).
toList();
map(name -> name.substring(0, name.length() - BlueprintsManager.BLUEPRINT_SUFFIX.length())).
toList();
if (blueprintList.isEmpty())
{

View File

@ -17,7 +17,7 @@ public class AdminBlueprintLoadCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.blueprint.load");
setParametersHelp("commands.admin.blueprint.load.parameters");
setDescription("commands.admin.blueprint.load.description");
}

View File

@ -19,7 +19,7 @@ public class AdminBlueprintOriginCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.blueprint.origin");
setParametersHelp("commands.admin.blueprint.origin.parameters");
setDescription("commands.admin.blueprint.origin.description");
}

View File

@ -15,7 +15,7 @@ public class AdminBlueprintPasteCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.blueprint.paste");
setParametersHelp("commands.admin.blueprint.paste.parameters");
setDescription("commands.admin.blueprint.paste.description");
}

View File

@ -15,7 +15,7 @@ public class AdminBlueprintPos1Command extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.blueprint.pos1");
setParametersHelp("commands.admin.blueprint.pos1.parameters");
setDescription("commands.admin.blueprint.pos1.description");
}

View File

@ -15,7 +15,7 @@ public class AdminBlueprintPos2Command extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.blueprint.pos2");
setParametersHelp("commands.admin.blueprint.pos2.parameters");
setDescription("commands.admin.blueprint.pos2.description");
}

View File

@ -27,7 +27,7 @@ public class AdminBlueprintRenameCommand extends ConfirmableCommand
@Override
public void setup()
{
this.inheritPermission();
setPermission("admin.blueprint.rename");
this.setParametersHelp("commands.admin.blueprint.rename.parameters");
this.setDescription("commands.admin.blueprint.rename.description");
}
@ -83,8 +83,8 @@ public class AdminBlueprintRenameCommand extends ConfirmableCommand
{
// Ask for confirmation to overwrite
this.askConfirmation(user,
user.getTranslation("commands.admin.blueprint.file-exists"),
() -> this.rename(user, from, to, args.get(1)));
user.getTranslation("commands.admin.blueprint.file-exists"),
() -> this.rename(user, from, to, args.get(1)));
}
else
{
@ -102,11 +102,11 @@ public class AdminBlueprintRenameCommand extends ConfirmableCommand
this.getPlugin().getBlueprintsManager().renameBlueprint(this.getAddon(), blueprint, fileName, displayName);
user.sendMessage("commands.admin.blueprint.rename.success",
"[old]",
blueprintName,
TextVariables.NAME,
blueprint.getName(),
"[display]",
blueprint.getDisplayName());
"[old]",
blueprintName,
TextVariables.NAME,
blueprint.getName(),
"[display]",
blueprint.getDisplayName());
}
}

View File

@ -25,7 +25,7 @@ public class AdminBlueprintSaveCommand extends ConfirmableCommand
@Override
public void setup()
{
this.inheritPermission();
setPermission("admin.blueprint.save");
this.setParametersHelp("commands.admin.blueprint.save.parameters");
this.setDescription("commands.admin.blueprint.save.description");
}

View File

@ -22,7 +22,7 @@ public class AdminDeathsAddCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.deaths.add");
setDescription("commands.admin.deaths.add.description");
setParametersHelp("commands.admin.deaths.add.parameters");
}

View File

@ -22,7 +22,7 @@ public class AdminDeathsRemoveCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.deaths.remove");
setDescription("commands.admin.deaths.remove.description");
setParametersHelp("commands.admin.deaths.remove.parameters");
}

View File

@ -21,7 +21,7 @@ public class AdminDeathsResetCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.deaths.reset");
setDescription("commands.admin.deaths.reset.description");
setParametersHelp("commands.admin.deaths.reset.parameters");
}

View File

@ -21,7 +21,7 @@ public class AdminDeathsSetCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.deaths.set");
setDescription("commands.admin.deaths.set.description");
setParametersHelp("commands.admin.deaths.set.parameters");
}

View File

@ -16,7 +16,7 @@ public class AdminPurgeProtectCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.purge.protect");
setOnlyPlayer(true);
setDescription("commands.admin.purge.protect.description");
}

View File

@ -19,7 +19,7 @@ public class AdminPurgeStatusCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.purge.status");
setOnlyPlayer(false);
setParametersHelp("commands.admin.purge.status.parameters");
setDescription("commands.admin.purge.status.description");

View File

@ -13,7 +13,7 @@ public class AdminPurgeStopCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.purge.stop");
setOnlyPlayer(false);
setDescription("commands.admin.purge.stop.description");
}

View File

@ -17,7 +17,7 @@ public class AdminPurgeUnownedCommand extends ConfirmableCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.purge.unowned");
setOnlyPlayer(false);
setParametersHelp("commands.admin.purge.unowned.parameters");
setDescription("commands.admin.purge.unowned.description");

View File

@ -25,7 +25,7 @@ public class AdminRangeAddCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.range.add");
setDescription("commands.admin.range.add.description");
setParametersHelp("commands.admin.range.add.parameters");
}

View File

@ -25,7 +25,7 @@ public class AdminRangeRemoveCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.range.remove");
setDescription("commands.admin.range.remove.description");
setParametersHelp("commands.admin.range.remove.parameters");
}

View File

@ -22,7 +22,7 @@ public class AdminResetsAddCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.resets.add");
setDescription("commands.admin.resets.add.description");
setParametersHelp("commands.admin.resets.add.parameters");
}

View File

@ -22,7 +22,7 @@ public class AdminResetsRemoveCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.resets.remove");
setDescription("commands.admin.resets.remove.description");
setParametersHelp("commands.admin.resets.remove.parameters");
}

View File

@ -22,7 +22,7 @@ public class AdminResetsResetCommand extends ConfirmableCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.resets.remove");
setDescription("commands.admin.resets.reset.description");
setParametersHelp("commands.admin.resets.reset.parameters");
}

View File

@ -16,7 +16,7 @@ public class AdminResetsSetCommand extends CompositeCommand {
@Override
public void setup() {
inheritPermission();
setPermission("admin.resets.set");
setDescription("commands.admin.resets.set.description");
setParametersHelp("commands.admin.resets.set.parameters");
}

View File

@ -21,7 +21,7 @@ public class AdminTeamAddCommand extends CompositeCommand {
@Override
public void setup() {
setPermission("mod.team");
setPermission("mod.team.add");
setParametersHelp("commands.admin.team.add.parameters");
setDescription("commands.admin.team.add.description");
}

View File

@ -20,7 +20,7 @@ public class AdminTeamDisbandCommand extends CompositeCommand {
@Override
public void setup() {
setPermission("mod.team");
setPermission("mod.team.disband");
setParametersHelp("commands.admin.team.disband.parameters");
setDescription("commands.admin.team.disband.description");
}

View File

@ -14,7 +14,7 @@ public class AdminTeamFixCommand extends CompositeCommand {
@Override
public void setup() {
setPermission("mod.team");
setPermission("mod.team.fix");
setDescription("commands.admin.team.fix.description");
}

View File

@ -30,7 +30,7 @@ public class AdminTeamKickCommand extends CompositeCommand {
@Override
public void setup() {
setPermission("mod.team");
setPermission("mod.team.kick");
setParametersHelp("commands.admin.team.kick.parameters");
setDescription("commands.admin.team.kick.description");
}

View File

@ -25,7 +25,7 @@ public class AdminTeamSetownerCommand extends CompositeCommand {
@Override
public void setup() {
setPermission("mod.team");
setPermission("mod.team.setowner");
setParametersHelp("commands.admin.team.setowner.parameters");
setDescription("commands.admin.team.setowner.description");
}

View File

@ -24,6 +24,10 @@ public class IslandDeletehomeCommand extends ConfirmableCommand {
private @Nullable Island island;
/**
* Deletes a home
* @param islandCommand parent command
*/
public IslandDeletehomeCommand(CompositeCommand islandCommand) {
super(islandCommand, "deletehome");
}
@ -51,11 +55,11 @@ public class IslandDeletehomeCommand extends ConfirmableCommand {
return false;
}
// check command permission
// check command ranks
int rank = Objects.requireNonNull(island).getRank(user);
if (rank < island.getRankCommand(getUsage())) {
user.sendMessage("general.errors.insufficient-rank",
TextVariables.RANK, user.getTranslation(getPlugin().getRanksManager().getRank(rank)));
TextVariables.RANK, user.getTranslation(getPlugin().getRanksManager().getRank(rank)));
return false;
}

View File

@ -6,6 +6,7 @@ import java.util.Objects;
import org.bukkit.ChatColor;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.events.island.IslandEvent;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.database.objects.Island;
@ -93,8 +94,18 @@ public class IslandSetnameCommand extends CompositeCommand {
}
// Everything's good!
Objects.requireNonNull(getIslands().getIsland(getWorld(), user)).setName(name);
Island island = Objects.requireNonNull(getIslands().getIsland(getWorld(), user));
String previousName = island.getName();
island.setName(name);
user.sendMessage("commands.island.setname.success", TextVariables.NAME, name);
// Fire the IslandNameEvent
new IslandEvent.IslandEventBuilder()
.island(island)
.involvedPlayer(user.getUniqueId())
.reason(IslandEvent.Reason.NAME)
.previousName(previousName)
.admin(false)
.build();
return true;
}
}

View File

@ -7,7 +7,9 @@ import org.bukkit.Location;
import org.bukkit.event.Event;
import org.bukkit.event.HandlerList;
import org.eclipse.jdt.annotation.NonNull;
import org.eclipse.jdt.annotation.Nullable;
import world.bentobox.bentobox.api.addons.Addon;
import world.bentobox.bentobox.api.events.IslandBaseEvent;
import world.bentobox.bentobox.blueprints.dataobjects.BlueprintBundle;
import world.bentobox.bentobox.database.objects.Island;
@ -169,7 +171,17 @@ public class IslandEvent extends IslandBaseEvent {
* Event that will fire any time a player's rank changes on an island.
* @since 1.13.0
*/
RANK_CHANGE
RANK_CHANGE,
/**
* Event that will fire when an island is named or renamed
* @since 1.24.0
*/
NAME,
/**
* Event that will fire when the info command is executed. Allows addons to add to it
* @since 1.24.0
*/
INFO
}
public static IslandEventBuilder builder() {
@ -213,6 +225,14 @@ public class IslandEvent extends IslandBaseEvent {
* @since 1.13.0
*/
private int newRank;
/**
* @since 1.24.0 Previous name of island
*/
private String previousName;
/**
* @since 1.24.0 GameMode addon causing this event
*/
private Addon addon;
public IslandEventBuilder island(Island island) {
this.island = island;
@ -305,6 +325,26 @@ public class IslandEvent extends IslandBaseEvent {
return this;
}
/**
* Sets the previous name of the island
* @param previousName previous name. May be null.
* @since 1.24.0
*/
public IslandEventBuilder previousName(@Nullable String previousName) {
this.previousName = previousName;
return this;
}
/**
* Addon that triggered this event, e.g. BSkyBlock
* @param addon Addon.
* @since 1.24.0
*/
public IslandEventBuilder addon(Addon addon) {
this.addon = addon;
return this;
}
private IslandBaseEvent getEvent() {
return switch (reason) {
case EXPEL -> new IslandExpelEvent(island, player, admin, location);
@ -329,6 +369,8 @@ public class IslandEvent extends IslandBaseEvent {
case RESERVED -> new IslandReservedEvent(island, player, admin, location);
case RANK_CHANGE -> new IslandRankChangeEvent(island, player, admin, location, oldRank, newRank);
case NEW_ISLAND -> new IslandNewIslandEvent(island, player, admin, location);
case NAME -> new IslandNameEvent(island, player, admin, location, previousName);
case INFO -> new IslandInfoEvent(island, player, admin, location, addon);
default -> new IslandGeneralEvent(island, player, admin, location);
};
}
@ -345,5 +387,6 @@ public class IslandEvent extends IslandBaseEvent {
Bukkit.getPluginManager().callEvent(newEvent);
return newEvent;
}
}
}

View File

@ -0,0 +1,55 @@
package world.bentobox.bentobox.api.events.island;
import java.util.UUID;
import org.bukkit.Location;
import org.bukkit.event.HandlerList;
import org.eclipse.jdt.annotation.NonNull;
import world.bentobox.bentobox.api.addons.Addon;
import world.bentobox.bentobox.api.events.IslandBaseEvent;
import world.bentobox.bentobox.database.objects.Island;
/**
* Fired when an a player reuqets info about an island
* Cancellation has no effect.
* @since 1.24.0
*/
public class IslandInfoEvent extends IslandBaseEvent {
private final Addon addon;
private static final HandlerList handlers = new HandlerList();
@Override
public @NonNull HandlerList getHandlers() {
return getHandlerList();
}
public static HandlerList getHandlerList() {
return handlers;
}
/**
* @param island island
* @param player player asking for the info
* @param admin true if this is an admin request
* @param location location of the player asking for the info
* @param addon the addon parent that is calling this info command, e.g., BSkyBlock
*/
public IslandInfoEvent(Island island, UUID player, boolean admin, Location location, Addon addon) {
// Final variables have to be declared in the constructor
super(island, player, admin, location);
this.addon = addon;
}
/**
* @return the gameMode that is for this island
*/
public Addon getAddon() {
return addon;
}
}

View File

@ -0,0 +1,44 @@
package world.bentobox.bentobox.api.events.island;
import java.util.UUID;
import org.bukkit.Location;
import org.bukkit.event.HandlerList;
import org.eclipse.jdt.annotation.NonNull;
import org.eclipse.jdt.annotation.Nullable;
import world.bentobox.bentobox.api.events.IslandBaseEvent;
import world.bentobox.bentobox.database.objects.Island;
/**
* Fired when an a player names or renames an island.
* Cancellation has no effect.
*/
public class IslandNameEvent extends IslandBaseEvent {
private final String previousName;
private static final HandlerList handlers = new HandlerList();
@Override
public @NonNull HandlerList getHandlers() {
return getHandlerList();
}
public static HandlerList getHandlerList() {
return handlers;
}
public IslandNameEvent(Island island, UUID player, boolean admin, Location location, @Nullable String previousName) {
// Final variables have to be declared in the constructor
super(island, player, admin, location);
this.previousName = previousName;
}
/**
* @return the previous name of the island, if any. May be null if no name previously used.
*/
@Nullable
public String getPreviousNameIsland() {
return previousName;
}
}

View File

@ -125,6 +125,7 @@ public abstract class FlagListener implements Listener {
* @return true if the check is okay, false if it was disallowed
*/
public boolean checkIsland(@NonNull Event e, @Nullable Player player, @Nullable Location loc, @NonNull Flag flag, boolean silent) {
// Set user
user = player == null ? null : User.getInstance(player);
if (loc == null) {

View File

@ -19,6 +19,9 @@ import world.bentobox.bentobox.api.user.User;
*/
public class PanelItem {
/**
* @return an empty PanelItem
*/
public static PanelItem empty() {
return new PanelItemBuilder().build();
}
@ -58,6 +61,9 @@ public class PanelItem {
}
/**
* @return the icon itemstack
*/
public ItemStack getItem() {
return icon;
}
@ -135,14 +141,14 @@ public class PanelItem {
public boolean isPlayerHead() {
return playerHeadName != null && !playerHeadName.isEmpty();
}
/**
* @return the playerHeadName
* @since 1.9.0
*/
public String getPlayerHeadName() {
return playerHeadName;
}
}
/**
* Click handler interface

View File

@ -472,7 +472,10 @@ public class User implements MetaDataAble {
// Then replace variables
if (variables.length > 1) {
for (int i = 0; i < variables.length; i += 2) {
translation = translation.replace(variables[i], variables[i + 1]);
// Prevent a NPE if the substituting variable is null
if (variables[i + 1] != null) {
translation = translation.replace(variables[i], variables[i + 1]);
}
}
}

View File

@ -18,6 +18,7 @@ import org.bukkit.block.Block;
import org.bukkit.block.BlockState;
import org.bukkit.block.CreatureSpawner;
import org.bukkit.block.Sign;
import org.bukkit.block.sign.Side;
import org.bukkit.entity.AbstractHorse;
import org.bukkit.entity.Ageable;
import org.bukkit.entity.ChestedHorse;
@ -221,8 +222,10 @@ public class BlueprintClipboard {
// Signs
if (blockState instanceof Sign sign) {
b.setSignLines(Arrays.asList(sign.getLines()));
b.setGlowingText(sign.isGlowingText());
for (Side side : Side.values()) {
b.setSignLines(side, Arrays.asList(sign.getSide(side).getLines()));
b.setGlowingText(side, sign.getSide(side).isGlowingText());
}
}
// Set block data
if (blockState.getData() instanceof Attachable) {

View File

@ -6,6 +6,7 @@ import java.util.Map;
import org.bukkit.block.Biome;
import org.bukkit.block.banner.Pattern;
import org.bukkit.block.sign.Side;
import org.bukkit.inventory.ItemStack;
import com.google.gson.annotations.Expose;
@ -21,6 +22,8 @@ public class BlueprintBlock {
@Expose
private List<String> signLines;
@Expose
private List<String> signLines2;
@Expose
private Map<Integer, ItemStack> inventory;
@Expose
private BlueprintCreatureSpawner creatureSpawner;
@ -36,6 +39,8 @@ public class BlueprintBlock {
private List<Pattern> bannerPatterns;
@Expose
private boolean glowingText;
@Expose
private boolean glowingText2;
public BlueprintBlock(String blockData) {
this.blockData = blockData;
@ -57,14 +62,20 @@ public class BlueprintBlock {
/**
* @return the signLines
* @deprecated signs now have two sides
* @since 1.24.0
*/
@Deprecated
public List<String> getSignLines() {
return signLines;
}
/**
* @param signLines the signLines to set
* @deprecated signs now have two sides
* @since 1.24.0
*/
@Deprecated
public void setSignLines(List<String> signLines) {
this.signLines = signLines;
}
@ -129,17 +140,73 @@ public class BlueprintBlock {
/**
* @return the glowingText
* @deprecated signs now have two sides
* @since 1.24.0
*/
@Deprecated
public boolean isGlowingText() {
return glowingText;
}
/**
* @param glowingText the glowingText to set
* @deprecated signs now have two sides
* @since 1.24.0
*/
@Deprecated
public void setGlowingText(boolean glowingText) {
this.glowingText = glowingText;
}
/**
* @param side side of sign
* @param glowingText the glowingText to set
* @since 1.24.0
*/
public void setGlowingText(Side side, boolean glowingText) {
switch (side) {
case FRONT -> this.glowingText = glowingText;
default -> this.glowingText2 = glowingText;
};
}
/**
* @param side side of sign
* @return the glowingText
* @since 1.24.0
*/
public boolean isGlowingText(Side side) {
return switch (side) {
case FRONT -> glowingText;
default -> glowingText2;
};
}
/**
* @param side side of sign
* @return the signLines
* @since 1.24.0
*/
public List<String> getSignLines(Side side) {
return switch (side) {
case FRONT -> signLines;
default -> signLines2;
};
}
/**
* @param side side of sign
* @param signLines the signLines to set
* @since 1.24.0
*/
public void setSignLines(Side side, List<String> signLines) {
switch (side) {
case FRONT -> this.signLines = signLines;
default -> this.signLines2 = signLines;
};
}
}

View File

@ -28,7 +28,7 @@ public class BentoBoxAboutCommand extends CompositeCommand {
@Override
public boolean execute(User user, String label, List<String> args) {
user.sendRawMessage("About " + BentoBox.getInstance().getDescription().getName() + " v" + BentoBox.getInstance().getDescription().getVersion() + ":");
user.sendRawMessage("Copyright (c) 2017 - 2021 Tastybento, Poslovitch and the BentoBoxWorld contributors");
user.sendRawMessage("Copyright (c) 2017 - 2023 Tastybento, Poslovitch and the BentoBoxWorld contributors");
user.sendRawMessage("See https://www.eclipse.org/legal/epl-2.0/ for license information.");
return true;
}

View File

@ -24,6 +24,7 @@ public class BentoBoxCommand extends CompositeCommand {
new BentoBoxReloadCommand(this);
new BentoBoxLocaleCommand(this);
new BentoBoxHelpCommand(this);
new BentoBoxPermsCommand(this);
// Database names with a 2 in them are migration databases
if (getPlugin().getSettings().getDatabaseType().name().contains("2")) {
new BentoBoxMigrateCommand(this);

View File

@ -0,0 +1,82 @@
package world.bentobox.bentobox.commands;
import java.util.List;
import org.bukkit.Bukkit;
import org.bukkit.permissions.Permission;
import world.bentobox.bentobox.api.addons.GameModeAddon;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.user.User;
/**
* Displays permissions that have been set by BentoBox.
*
* @author tastybento
*/
public class BentoBoxPermsCommand extends CompositeCommand {
/**
* Info command
* @param parent - command parent
*/
public BentoBoxPermsCommand(CompositeCommand parent) {
super(parent, "perms");
}
@Override
public void setup() {
setPermission("bentobox.admin.perms");
setParametersHelp("commands.bentobox.perms.parameters");
setDescription("commands.bentobox.perms.description");
this.setOnlyConsole(true);
}
@Override
public boolean execute(User user, String label, List<String> args) {
// Loop all the known top-level commands
getPlugin().getCommandsManager().getCommands().values().stream().distinct().forEach(cc -> {
if (cc.getAddon() == null) {
user.sendMessage("*** BentoBox effective perms:");
} else if (cc.getAddon() instanceof GameModeAddon gma) {
user.sendRawMessage("**** " + gma.getDescription().getName() + " effective perms:");
} else {
user.sendRawMessage("**** " + cc.getAddon().getDescription().getName() + " effective perms:");
}
user.sendRawMessage("permissions:");
printData(user, cc, cc.getLabel());
printSubCommandData(user, cc, cc.getLabel());
});
return true;
}
private void printData(User user, CompositeCommand cc, String label) {
if (cc.getPermission().isBlank()) return;
String desc = user.getTranslation(cc.getWorld(), cc.getDescription());
user.sendRawMessage(" " + cc.getPermission() + ":");
user.sendRawMessage(" description: Allow use of '/" + label + "' command - " + desc);
Permission p = Bukkit.getPluginManager().getPermission(cc.getPermission());
if (p != null) {
user.sendRawMessage(" default: " + p.getDefault().name());
} else {
user.sendRawMessage(" default: OP"); // If not def
}
}
/**
* Iterates over sub-commands
* @param user user
* @param parent parent command
* @param label
*/
private void printSubCommandData(User user, CompositeCommand parent, String label) {
for (CompositeCommand cc : parent.getSubCommands().values()) {
if (cc.getLabel().equalsIgnoreCase("help")) continue; // Ignore the help command
String newLabel = label + " " + cc.getLabel();
printData(user, cc, newLabel);
printSubCommandData(user, cc, newLabel);
}
}
}

View File

@ -49,6 +49,12 @@ public class MultiverseCoreHook extends Hook implements WorldManagementHook {
}
}
@Override
public void unregisterWorld(World world) {
String cmd = "mv remove " + world.getName();
Bukkit.getServer().dispatchCommand(Bukkit.getServer().getConsoleSender(), cmd);
}
@Override
public boolean hook() {
return true; // The hook process shouldn't fail

View File

@ -13,8 +13,17 @@ public interface WorldManagementHook {
/**
* Register the world with the World Management hook
*
*
* @param world - world to register
* @param islandWorld - if true, then this is an island world
*/
void registerWorld(World world, boolean islandWorld);
/**
* Unregisters a world.
* @param world - world to unregister
*/
default void unregisterWorld(World world) {
// Do nothing
}
}

View File

@ -57,20 +57,19 @@ public class BannedCommands implements Listener {
}
private boolean checkCmd(String cmd, String[] args) {
// Commands are guilty until proven innocent :-)
boolean banned = true;
// Get the elements of the banned command by splitting it
String[] bannedSplit = cmd.toLowerCase(java.util.Locale.ENGLISH).split(" ");
// If the banned command has the same number of elements or less than the entered command then it may be banned
if (bannedSplit.length <= args.length) {
if (bannedSplit.length <= args.length) {
for (int i = 0; i < bannedSplit.length; i++) {
if (!bannedSplit[i].equals(args[i])) {
banned = false;
break;
if (!bannedSplit[i].equalsIgnoreCase(args[i])) {
return false;
}
}
} else {
return false;
}
return banned;
return true;
}
/**

View File

@ -1,6 +1,5 @@
package world.bentobox.bentobox.listeners.flags.protection;
import java.util.Map;
import java.util.Optional;
import org.bukkit.FluidCollisionMode;
@ -8,6 +7,8 @@ import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.Tag;
import org.bukkit.block.Block;
import org.bukkit.block.BrushableBlock;
import org.bukkit.block.Sign;
import org.bukkit.block.data.Waterlogged;
import org.bukkit.entity.Player;
import org.bukkit.event.Event;
@ -18,8 +19,6 @@ import org.bukkit.event.block.BlockBreakEvent;
import org.bukkit.event.block.BlockFromToEvent;
import org.bukkit.event.player.PlayerInteractEvent;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.flags.Flag;
import world.bentobox.bentobox.api.flags.FlagListener;
import world.bentobox.bentobox.database.objects.Island;
import world.bentobox.bentobox.lists.Flags;
@ -31,31 +30,12 @@ import world.bentobox.bentobox.lists.Flags;
public class BlockInteractionListener extends FlagListener
{
/**
* These cover materials in another server version. This avoids run time errors due to unknown enum values, at the
* expense of a string comparison
*/
private static final Map<String, String> stringFlags;
private static final String CHEST = "CHEST";
static
{
stringFlags = Map.of(
"ACACIA_CHEST_BOAT", CHEST,
"BIRCH_CHEST_BOAT", CHEST,
"JUNGLE_CHEST_BOAT", CHEST,
"DARK_OAK_CHEST_BOAT", CHEST,
"MANGROVE_CHEST_BOAT", CHEST,
"OAK_CHEST_BOAT", CHEST,
"SPRUCE_CHEST_BOAT", CHEST);
}
/**
* Handle interaction with blocks
*
* @param e - event
*/
@EventHandler(priority = EventPriority.LOWEST, ignoreCancelled = true)
@EventHandler(priority = EventPriority.NORMAL, ignoreCancelled = true)
public void onPlayerInteract(final PlayerInteractEvent e)
{
// We only care about the RIGHT_CLICK_BLOCK action.
@ -65,13 +45,13 @@ public class BlockInteractionListener extends FlagListener
}
// Check clicked block
this.checkClickedBlock(e, e.getPlayer(), e.getClickedBlock().getLocation(), e.getClickedBlock().getType());
this.checkClickedBlock(e, e.getPlayer(), e.getClickedBlock());
// Now check for in-hand items
if (e.getItem() != null && !e.getItem().getType().equals(Material.AIR))
{
// Boats
if (e.getItem().getType().name().endsWith("BOAT"))
if (Tag.ITEMS_BOATS.isTagged(e.getItem().getType()))
{
this.checkIsland(e, e.getPlayer(), e.getClickedBlock().getLocation(), Flags.BOAT);
}
@ -107,11 +87,12 @@ public class BlockInteractionListener extends FlagListener
*
* @param e - event called
* @param player - player
* @param loc - location of clicked block
* @param type - material type of clicked block
* @param block - block being clicked or used
*/
private void checkClickedBlock(Event e, Player player, Location loc, Material type)
private void checkClickedBlock(Event e, Player player, Block block)
{
Material type = block.getType();
Location loc = block.getLocation();
// Handle pots
if (type.name().startsWith("POTTED"))
{
@ -119,6 +100,12 @@ public class BlockInteractionListener extends FlagListener
return;
}
if (block.getState() instanceof BrushableBlock bb && BlockInteractionListener.holds(player, Material.BRUSH)) {
// Protect this using break blocks flag for now. Maybe in the future it can have its own flag.
this.checkIsland(e, player, loc, Flags.BREAK_BLOCKS);
return;
}
if (Tag.ANVIL.isTagged(type))
{
this.checkIsland(e, player, loc, Flags.ANVIL);
@ -155,14 +142,21 @@ public class BlockInteractionListener extends FlagListener
return;
}
if (Tag.SIGNS.isTagged(type) && block.getState() instanceof Sign sign && !sign.isWaxed()) {
// If waxed, then sign cannot be edited otherwise check
this.checkIsland(e, player, loc, Flags.SIGN_EDITING);
return;
}
if (Tag.FENCE_GATES.isTagged(type))
{
this.checkIsland(e, player, loc, Flags.GATE);
}
// TODO: 1.18 compatibility
// if (Tag.ITEMS_CHEST_BOATS.isTagged(type)) {
// this.checkIsland(e, player, loc, Flags.CHEST);
// }
if (Tag.ITEMS_CHEST_BOATS.isTagged(type))
{
this.checkIsland(e, player, loc, Flags.CHEST);
}
switch (type)
{
@ -177,14 +171,12 @@ public class BlockInteractionListener extends FlagListener
case DISPENSER -> this.checkIsland(e, player, loc, Flags.DISPENSER);
case DROPPER -> this.checkIsland(e, player, loc, Flags.DROPPER);
case HOPPER, HOPPER_MINECART -> this.checkIsland(e, player, loc, Flags.HOPPER);
case BLAST_FURNACE, CAMPFIRE, FURNACE_MINECART, FURNACE, SMOKER ->
this.checkIsland(e, player, loc, Flags.FURNACE);
case BLAST_FURNACE, CAMPFIRE, FURNACE_MINECART, FURNACE, SMOKER -> this.checkIsland(e, player, loc, Flags.FURNACE);
case ENCHANTING_TABLE -> this.checkIsland(e, player, loc, Flags.ENCHANTING);
case ENDER_CHEST -> this.checkIsland(e, player, loc, Flags.ENDER_CHEST);
case JUKEBOX -> this.checkIsland(e, player, loc, Flags.JUKEBOX);
case NOTE_BLOCK -> this.checkIsland(e, player, loc, Flags.NOTE_BLOCK);
case CRAFTING_TABLE, CARTOGRAPHY_TABLE, GRINDSTONE, STONECUTTER, LOOM ->
this.checkIsland(e, player, loc, Flags.CRAFTING);
case CRAFTING_TABLE, CARTOGRAPHY_TABLE, GRINDSTONE, STONECUTTER, LOOM -> this.checkIsland(e, player, loc, Flags.CRAFTING);
case LEVER -> this.checkIsland(e, player, loc, Flags.LEVER);
case REDSTONE_WIRE, REPEATER, COMPARATOR, DAYLIGHT_DETECTOR -> this.checkIsland(e, player, loc, Flags.REDSTONE);
case DRAGON_EGG -> this.checkIsland(e, player, loc, Flags.DRAGON_EGG);
@ -192,6 +184,7 @@ public class BlockInteractionListener extends FlagListener
case GLOW_ITEM_FRAME, ITEM_FRAME -> this.checkIsland(e, player, loc, Flags.ITEM_FRAME);
case SWEET_BERRY_BUSH, CAVE_VINES -> this.checkIsland(e, player, loc, Flags.BREAK_BLOCKS);
case CAKE -> this.checkIsland(e, player, loc, Flags.CAKE);
case CHISELED_BOOKSHELF -> this.checkIsland(e, player, loc, Flags.BOOKSHELF);
case LAVA_CAULDRON ->
{
if (BlockInteractionListener.holds(player, Material.BUCKET))
@ -232,12 +225,7 @@ public class BlockInteractionListener extends FlagListener
}
}
default ->
{
if (stringFlags.containsKey(type.name()))
{
Optional<Flag> f = BentoBox.getInstance().getFlagsManager().getFlag(stringFlags.get(type.name()));
f.ifPresent(flag -> this.checkIsland(e, player, loc, flag));
}
{ // nothing to do
}
}
}
@ -253,7 +241,7 @@ public class BlockInteractionListener extends FlagListener
@EventHandler(priority = EventPriority.NORMAL, ignoreCancelled = true)
public void onBlockBreak(final BlockBreakEvent e)
{
this.checkClickedBlock(e, e.getPlayer(), e.getBlock().getLocation(), e.getBlock().getType());
this.checkClickedBlock(e, e.getPlayer(), e.getBlock());
}

View File

@ -39,7 +39,7 @@ public class EntityInteractListener extends FlagListener {
}
}
@EventHandler(priority = EventPriority.LOW, ignoreCancelled = true)
@EventHandler(priority = EventPriority.NORMAL, ignoreCancelled = true)
public void onPlayerInteractEntity(PlayerInteractEntityEvent e)
{
Player p = e.getPlayer();

View File

@ -3,6 +3,7 @@ package world.bentobox.bentobox.listeners.flags.protection;
import java.util.Set;
import org.bukkit.Material;
import org.bukkit.Tag;
import org.bukkit.entity.EntityType;
import org.bukkit.entity.Player;
import org.bukkit.event.EventHandler;
@ -44,7 +45,7 @@ public class PlaceBlocksListener extends FlagListener
// Crops
if (against.equals(Material.FARMLAND) && SEEDS.contains(e.getItemInHand().getType())) {
this.checkIsland(e, e.getPlayer(), e.getBlock().getLocation(), Flags.CROP_PLANTING);
} else {
} else {
this.checkIsland(e, e.getPlayer(), e.getBlock().getLocation(), Flags.PLACE_BLOCKS);
}
}
@ -124,7 +125,7 @@ public class PlaceBlocksListener extends FlagListener
{
this.checkIsland(e, e.getPlayer(), e.getPlayer().getLocation(), Flags.PLACE_BLOCKS);
}
else if (e.getMaterial().name().contains("BOAT"))
else if (Tag.ITEMS_BOATS.isTagged(e.getMaterial()))
{
this.checkIsland(e, e.getPlayer(), e.getPlayer().getLocation(), Flags.BOAT);
}

View File

@ -13,6 +13,8 @@ import org.bukkit.event.EventHandler;
import org.bukkit.event.EventPriority;
import org.bukkit.event.block.BlockReceiveGameEvent;
import com.google.common.base.Enums;
import world.bentobox.bentobox.api.flags.FlagListener;
import world.bentobox.bentobox.lists.Flags;
@ -34,11 +36,12 @@ public class SculkSensorListener extends FlagListener
return;
}
if (event.getBlock().getType() == Material.SCULK_SENSOR &&
event.getEntity() != null &&
event.getEntity() instanceof Player player)
if ((event.getBlock().getType() == Material.SCULK_SENSOR
|| event.getBlock().getType() == Enums.getIfPresent(Material.class, "CALIBRATED_SCULK_SENSOR").or(Material.SCULK_SENSOR))
&& event.getEntity() != null && event.getEntity() instanceof Player player)
{
this.checkIsland(event, player, event.getBlock().getLocation(), Flags.SCULK_SENSOR, true);
}
return;
}
}

View File

@ -9,6 +9,7 @@ import org.bukkit.Material;
import com.google.common.base.Enums;
import world.bentobox.bentobox.api.flags.Flag;
import world.bentobox.bentobox.api.flags.Flag.Mode;
import world.bentobox.bentobox.api.flags.Flag.Type;
import world.bentobox.bentobox.api.flags.clicklisteners.CycleClick;
import world.bentobox.bentobox.listeners.flags.clicklisteners.CommandRankClickListener;
@ -158,11 +159,18 @@ public final class Flags {
* @since 1.10.0
* @see LecternListener
*/
public static final Flag LECTERN = new Flag.Builder("LECTERN", Material.LECTERN).listener(new LecternListener()).build();
public static final Flag LECTERN = new Flag.Builder("LECTERN", Material.LECTERN).mode(Mode.ADVANCED).listener(new LecternListener()).build();
/**
* Prevents players from placing a book in a bookshelf or taking the book from it.
* @since 1.24.0
* @see BlockInteractionListener
*/
public static final Flag BOOKSHELF = new Flag.Builder("BOOKSHELF", Material.CHISELED_BOOKSHELF).mode(Mode.ADVANCED).build();
// Entity interactions
public static final Flag ARMOR_STAND = new Flag.Builder("ARMOR_STAND", Material.ARMOR_STAND).listener(new EntityInteractListener()).mode(Flag.Mode.ADVANCED).build();
public static final Flag RIDING = new Flag.Builder("RIDING", Material.GOLDEN_HORSE_ARMOR).build();
public static final Flag ARMOR_STAND = new Flag.Builder("ARMOR_STAND", Material.ARMOR_STAND).listener(new EntityInteractListener()).mode(Mode.ADVANCED).build();
public static final Flag RIDING = new Flag.Builder("RIDING", Material.GOLDEN_HORSE_ARMOR).mode(Mode.ADVANCED).build();
/**
* Prevents players from issuing any kind of interactions with Minecarts (entering, placing and opening if chest).
* @since 1.3.0
@ -188,7 +196,7 @@ public final class Flags {
// Buckets. All bucket use is covered by one listener
public static final Flag BUCKET = new Flag.Builder("BUCKET", Material.BUCKET).listener(new BucketListener()).mode(Flag.Mode.BASIC).build();
public static final Flag COLLECT_LAVA = new Flag.Builder("COLLECT_LAVA", Material.LAVA_BUCKET).build();
public static final Flag COLLECT_LAVA = new Flag.Builder("COLLECT_LAVA", Material.LAVA_BUCKET).mode(Mode.ADVANCED).build();
public static final Flag COLLECT_WATER = new Flag.Builder("COLLECT_WATER", Material.WATER_BUCKET).mode(Flag.Mode.ADVANCED).build();
/**
* @since 1.21
@ -215,7 +223,7 @@ public final class Flags {
* Prevents players from throwing eggs.
* @see EggListener
*/
public static final Flag EGGS = new Flag.Builder("EGGS", Material.EGG).listener(new EggListener()).build();
public static final Flag EGGS = new Flag.Builder("EGGS", Material.EGG).mode(Mode.ADVANCED).listener(new EggListener()).build();
/**
* Prevents players from throwing potions / experience bottles.
* @since 1.1
@ -259,7 +267,7 @@ public final class Flags {
* Prevents players from extinguishing fires.
* @see FireListener
*/
public static final Flag FIRE_EXTINGUISH = new Flag.Builder("FIRE_EXTINGUISH", Material.POTION).build();
public static final Flag FIRE_EXTINGUISH = new Flag.Builder("FIRE_EXTINGUISH", Material.POTION).mode(Mode.ADVANCED).build();
// Inventories
public static final Flag MOUNT_INVENTORY = new Flag.Builder("MOUNT_INVENTORY", Material.IRON_HORSE_ARMOR).listener(new InventoryListener()).mode(Flag.Mode.ADVANCED).build();
@ -277,12 +285,12 @@ public final class Flags {
* Prevents players from going through the Nether Portal.
* @see PortalListener
*/
public static final Flag NETHER_PORTAL = new Flag.Builder("NETHER_PORTAL", Material.NETHERRACK).listener(new PortalListener()).build();
public static final Flag NETHER_PORTAL = new Flag.Builder("NETHER_PORTAL", Material.NETHERRACK).mode(Mode.ADVANCED).listener(new PortalListener()).build();
/**
* Prevents players from going through the End Portal.
* @see PortalListener
*/
public static final Flag END_PORTAL = new Flag.Builder("END_PORTAL", Material.END_PORTAL_FRAME).build();
public static final Flag END_PORTAL = new Flag.Builder("END_PORTAL", Material.END_PORTAL_FRAME).mode(Mode.ADVANCED).build();
// Shearing
public static final Flag SHEARING = new Flag.Builder("SHEARING", Material.SHEARS).listener(new ShearingListener()).mode(Flag.Mode.ADVANCED).build();
@ -653,16 +661,21 @@ public final class Flags {
* Controls who gets to harvest any crop related contents. e.g. Wheat, Sugar Cane, melon blocks, not stems, pumpkin blocks, etc.
* @since 1.23.0
*/
public static final Flag HARVEST = new Flag.Builder("HARVEST", Material.PUMPKIN).type(Type.PROTECTION).build();
public static final Flag HARVEST = new Flag.Builder("HARVEST", Material.PUMPKIN).mode(Flag.Mode.BASIC).type(Type.PROTECTION).build();
/**
* Crop Planting
* Controls who gets to plant crops on tilled soil.
* @since 1.23.0
*/
public static final Flag CROP_PLANTING = new Flag.Builder("CROP_PLANTING", Material.PUMPKIN_SEEDS).type(Type.PROTECTION).build();
public static final Flag CROP_PLANTING = new Flag.Builder("CROP_PLANTING", Material.PUMPKIN_SEEDS).mode(Flag.Mode.BASIC).type(Type.PROTECTION).build();
/**
* Sign edit protection
* @since 1.24.0
*/
public static final Flag SIGN_EDITING = new Flag.Builder("SIGN_EDITING", Material.DARK_OAK_SIGN).mode(Flag.Mode.BASIC).type(Type.PROTECTION).build();
/**
* Provides a list of all the Flag instances contained in this class using reflection.
* Deprecated Flags are ignored.

View File

@ -31,11 +31,13 @@ public class IslandDeletionManager implements Listener {
*/
private final Database<IslandDeletion> handler;
private final Set<Location> inDeletion;
private final IslandChunkDeletionManager islandChunkDeletionManager;
public IslandDeletionManager(BentoBox plugin) {
this.plugin = plugin;
handler = new Database<>(plugin, IslandDeletion.class);
inDeletion = new HashSet<>();
islandChunkDeletionManager = new IslandChunkDeletionManager(plugin);
}
/**
@ -56,7 +58,7 @@ public class IslandDeletionManager implements Listener {
} else {
plugin.log("Resuming deletion of island at " + di.getLocation().getWorld().getName() + " " + Util.xyz(di.getLocation().toVector()));
inDeletion.add(di.getLocation());
plugin.getIslandChunkDeletionManager().add(di);
this.islandChunkDeletionManager.add(di);
}
});
}
@ -86,4 +88,12 @@ public class IslandDeletionManager implements Listener {
public boolean inDeletion(Location location) {
return inDeletion.contains(location);
}
/**
* @return the islandChunkDeletionManager
*/
public IslandChunkDeletionManager getIslandChunkDeletionManager() {
return islandChunkDeletionManager;
}
}

View File

@ -50,36 +50,48 @@ public class IslandWorldManager {
gameModes = new HashMap<>();
}
public void registerWorldsToMultiverse() {
/**
* Registers or unregisters worlds with world management plugins
*
* @param reg true to register, false to remove registration
*
* Updated 1.24.0
*/
public void registerWorldsToMultiverse(boolean reg) {
gameModes.values().stream().distinct().forEach(gm -> {
registerToWorldManagementPlugins(gm.getOverWorld(), true);
registerToWorldManagementPlugins(gm.getOverWorld(), true, reg);
if (gm.getWorldSettings().isNetherGenerate()) {
registerToWorldManagementPlugins(gm.getNetherWorld(), gm.getWorldSettings().isNetherIslands());
registerToWorldManagementPlugins(gm.getNetherWorld(), gm.getWorldSettings().isNetherIslands(), reg);
}
if (gm.getWorldSettings().isEndGenerate()) {
registerToWorldManagementPlugins(gm.getEndWorld(), gm.getWorldSettings().isEndIslands());
registerToWorldManagementPlugins(gm.getEndWorld(), gm.getWorldSettings().isEndIslands(), reg);
}
});
}
/**
* Registers a world with world management plugins
*
* @param world the World to register
* @param islandWorld true if this is an island world
*/
private void registerToWorldManagementPlugins(@NonNull World world, boolean islandWorld) {
if (plugin.getHooks() != null) {
for (Hook hook : plugin.getHooks().getHooks()) {
if (hook instanceof final WorldManagementHook worldManagementHook) {
if (Bukkit.isPrimaryThread()) {
worldManagementHook.registerWorld(world, islandWorld);
} else {
Bukkit.getScheduler().runTask(plugin, () -> worldManagementHook.registerWorld(world, islandWorld));
}
private void registerToWorldManagementPlugins(@NonNull World world, boolean islandWorld, boolean reg) {
if (plugin.getHooks() == null) {
return;
}
for (Hook hook : plugin.getHooks().getHooks()) {
if (hook instanceof final WorldManagementHook worldManagementHook) {
if (Bukkit.isPrimaryThread()) {
runTask(worldManagementHook, world, islandWorld, reg);
} else {
Bukkit.getScheduler().runTask(plugin, () -> runTask(worldManagementHook, world, islandWorld, reg));
}
}
}
}
private void runTask(WorldManagementHook worldManagementHook, @NonNull World world, boolean islandWorld, boolean reg) {
if (reg) {
worldManagementHook.registerWorld(world, islandWorld);
} else {
worldManagementHook.unregisterWorld(world);
}
}
/**
@ -143,6 +155,16 @@ public class IslandWorldManager {
.anyMatch(gm -> gm.getWorldSettings().getFriendlyName().equalsIgnoreCase(name));
}
/**
* Associate a world with a game mode. This enables game modes to register more worlds than just the standard
* overworld, nether, and end worlds.
* @param world world
* @param gameMode game mode
* @since 1.24.0
*/
public void addWorld(World world, GameModeAddon gameMode) {
gameModes.put(world, gameMode);
}
/**
* Adds a GameMode to island world manager
@ -159,27 +181,27 @@ public class IslandWorldManager {
// Add worlds to map
gameModes.put(world, gameMode);
// Call Multiverse
registerToWorldManagementPlugins(world, true);
if (settings.isNetherGenerate()) {
registerToWorldManagementPlugins(world, true, true);
if (settings.isNetherGenerate() && gameMode.getNetherWorld() != null) {
gameModes.put(gameMode.getNetherWorld(), gameMode);
if (settings.isNetherIslands()) {
registerToWorldManagementPlugins(gameMode.getNetherWorld(), true);
registerToWorldManagementPlugins(gameMode.getNetherWorld(), true, true);
}
}
if (settings.isEndGenerate()) {
if (settings.isEndGenerate() && gameMode.getEndWorld() != null) {
gameModes.put(gameMode.getEndWorld(), gameMode);
if (settings.isEndIslands()) {
registerToWorldManagementPlugins(gameMode.getEndWorld(), true);
registerToWorldManagementPlugins(gameMode.getEndWorld(), true, true);
}
}
// Set default island settings
plugin.getFlagsManager().getFlags().stream().
filter(f -> f.getType().equals(Flag.Type.PROTECTION)).
forEach(f -> settings.getDefaultIslandFlagNames().putIfAbsent(f.getID(), f.getDefaultRank()));
filter(f -> f.getType().equals(Flag.Type.PROTECTION)).
forEach(f -> settings.getDefaultIslandFlagNames().putIfAbsent(f.getID(), f.getDefaultRank()));
plugin.getFlagsManager().getFlags().stream().
filter(f -> f.getType().equals(Flag.Type.SETTING)).
forEach(f -> settings.getDefaultIslandSettingNames().putIfAbsent(f.getID(), f.getDefaultRank()));
filter(f -> f.getType().equals(Flag.Type.SETTING)).
forEach(f -> settings.getDefaultIslandSettingNames().putIfAbsent(f.getID(), f.getDefaultRank()));
Bukkit.getScheduler().runTask(plugin, () -> {
// Set world difficulty
@ -484,8 +506,8 @@ public class IslandWorldManager {
*/
public String getFriendlyName(@NonNull World world) {
return gameModes.containsKey(world) ?
gameModes.get(world).getWorldSettings().getFriendlyName() :
world.getName();
gameModes.get(world).getWorldSettings().getFriendlyName() :
world.getName();
}
/**
@ -710,8 +732,8 @@ public class IslandWorldManager {
public Map<Flag, Integer> getDefaultIslandFlags(@NonNull World world)
{
return this.gameModes.containsKey(world) ?
this.convertToFlags(this.gameModes.get(world).getWorldSettings().getDefaultIslandFlagNames()) :
Collections.emptyMap();
this.convertToFlags(this.gameModes.get(world).getWorldSettings().getDefaultIslandFlagNames()) :
Collections.emptyMap();
}
/**
@ -732,8 +754,8 @@ public class IslandWorldManager {
public Map<Flag, Integer> getDefaultIslandSettings(@NonNull World world)
{
return this.gameModes.containsKey(world) ?
this.convertToFlags(this.gameModes.get(world).getWorldSettings().getDefaultIslandSettingNames()) :
Collections.emptyMap();
this.convertToFlags(this.gameModes.get(world).getWorldSettings().getDefaultIslandSettingNames()) :
Collections.emptyMap();
}
public boolean isUseOwnGenerator(@NonNull World world) {
@ -945,7 +967,7 @@ public class IslandWorldManager {
{
Map<Flag, Integer> flagMap = new HashMap<>();
flagNamesMap.forEach((key, value) ->
this.plugin.getFlagsManager().getFlag(key).ifPresent(flag -> flagMap.put(flag, value)));
this.plugin.getFlagsManager().getFlag(key).ifPresent(flag -> flagMap.put(flag, value)));
return flagMap;
}
}

View File

@ -22,11 +22,11 @@ import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.Tag;
import org.bukkit.World;
import org.bukkit.block.Block;
import org.bukkit.block.BlockFace;
import org.bukkit.entity.Boat;
import org.bukkit.entity.Boat.Type;
import org.bukkit.entity.Entity;
import org.bukkit.entity.LivingEntity;
import org.bukkit.entity.Player;
@ -38,8 +38,6 @@ import org.bukkit.util.Vector;
import org.eclipse.jdt.annotation.NonNull;
import org.eclipse.jdt.annotation.Nullable;
import com.google.common.collect.ImmutableMap;
import io.papermc.lib.PaperLib;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.events.IslandBaseEvent;
@ -67,15 +65,6 @@ public class IslandsManager {
private final BentoBox plugin;
// Tree species to boat material map
private static final Map<Type, Material> TREE_TO_BOAT = ImmutableMap.<Type, Material>builder().
put(Type.ACACIA, Material.ACACIA_BOAT).
put(Type.BIRCH, Material.BIRCH_BOAT).
put(Type.DARK_OAK, Material.DARK_OAK_BOAT).
put(Type.JUNGLE, Material.JUNGLE_BOAT).
put(Type.OAK, Material.OAK_BOAT).
put(Type.SPRUCE, Material.SPRUCE_BOAT).build();
/**
* One island can be spawn, this is the one - otherwise, this value is null
*/
@ -250,8 +239,8 @@ public class IslandsManager {
public boolean checkIfSafe(@Nullable World world, @NonNull Material ground, @NonNull Material space1, @NonNull Material space2) {
// Ground must be solid, space 1 and 2 must not be solid
if (world == null || !ground.isSolid()
|| (space1.isSolid() && !space1.name().contains("SIGN"))
|| (space2.isSolid() && !space2.name().contains("SIGN"))) {
|| (space1.isSolid() && !Tag.SIGNS.isTagged(space1))
|| (space2.isSolid() && !Tag.SIGNS.isTagged(space2))) {
return false;
}
// Cannot be submerged or water cannot be dangerous
@ -262,14 +251,19 @@ public class IslandsManager {
if (ground.equals(Material.LAVA)
|| space1.equals(Material.LAVA)
|| space2.equals(Material.LAVA)
|| ground.name().contains("FENCE")
|| ground.name().contains("DOOR")
|| ground.name().contains("GATE")
|| ground.name().contains("PLATE")
|| ground.name().contains("SIGN")
|| ground.name().contains("BANNER")
|| ground.name().contains("BUTTON")
|| ground.name().contains("BOAT")
|| Tag.SIGNS.isTagged(ground)
|| Tag.TRAPDOORS.isTagged(ground)
|| Tag.BANNERS.isTagged(ground)
|| Tag.PRESSURE_PLATES.isTagged(ground)
|| Tag.FENCE_GATES.isTagged(ground)
|| Tag.DOORS.isTagged(ground)
|| Tag.FENCES.isTagged(ground)
|| Tag.BUTTONS.isTagged(ground)
|| Tag.ITEMS_BOATS.isTagged(ground)
|| Tag.ITEMS_CHEST_BOATS.isTagged(ground)
|| Tag.CAMPFIRES.isTagged(ground)
|| Tag.FIRE.isTagged(ground)
|| Tag.FIRE.isTagged(space1)
|| space1.equals(Material.END_PORTAL)
|| space2.equals(Material.END_PORTAL)
|| space1.equals(Material.END_GATEWAY)
@ -349,7 +343,7 @@ public class IslandsManager {
// Remove players from island
removePlayersFromIsland(island);
// Remove blocks from world
plugin.getIslandChunkDeletionManager().add(new IslandDeletion(island));
plugin.getIslandDeletionManager().getIslandChunkDeletionManager().add(new IslandDeletion(island));
}
}
@ -1072,19 +1066,7 @@ public class IslandsManager {
User user = User.getInstance(player);
user.sendMessage("commands.island.go.teleport");
goingHome.add(user.getUniqueId());
// Stop any gliding
player.setGliding(false);
// Check if the player is a passenger in a boat
if (player.isInsideVehicle()) {
Entity boat = player.getVehicle();
if (boat instanceof Boat boaty) {
player.leaveVehicle();
// Remove the boat so they don't lie around everywhere
boat.remove();
player.getInventory().addItem(new ItemStack(TREE_TO_BOAT.getOrDefault(boaty.getBoatType(), Material.OAK_BOAT)));
player.updateInventory();
}
}
readyPlayer(player);
this.getAsyncSafeHomeLocation(world, user, name).thenAccept(home -> {
Island island = getIsland(world, user);
if (home == null) {
@ -1196,23 +1178,7 @@ public class IslandsManager {
user.sendMessage("commands.island.spawn.no-spawn");
} else {
// Teleport the player to the spawn
// Stop any gliding
player.setGliding(false);
// Check if the player is a passenger in a boat
if (player.isInsideVehicle()) {
Entity boat = player.getVehicle();
if (boat instanceof Boat boaty) {
player.leaveVehicle();
// Remove the boat so they don't lie around everywhere
boat.remove();
Material boatMat = Material.getMaterial(boaty.getType() + "_BOAT");
if (boatMat == null) {
boatMat = Material.OAK_BOAT;
}
player.getInventory().addItem(new ItemStack(boatMat, 1));
player.updateInventory();
}
}
readyPlayer(player);
user.sendMessage("commands.island.spawn.teleporting");
// Safe teleport
@ -1220,6 +1186,23 @@ public class IslandsManager {
}
}
private void readyPlayer(@NonNull Player player) {
// Stop any gliding
player.setGliding(false);
// Check if the player is a passenger in a boat
if (player.isInsideVehicle()) {
Entity boat = player.getVehicle();
if (boat instanceof Boat boaty) {
player.leaveVehicle();
// Remove the boat so they don't lie around everywhere
boat.remove();
player.getInventory().addItem(new ItemStack(boaty.getBoatType().getMaterial()));
player.updateInventory();
}
}
}
/**
* Indicates whether a player is at an island spawn or not
*

View File

@ -17,6 +17,8 @@ import org.bukkit.block.BlockState;
import org.bukkit.block.CreatureSpawner;
import org.bukkit.block.Sign;
import org.bukkit.block.data.BlockData;
import org.bukkit.block.sign.Side;
import org.bukkit.block.sign.SignSide;
import org.bukkit.entity.AbstractHorse;
import org.bukkit.entity.Ageable;
import org.bukkit.entity.ChestedHorse;
@ -45,6 +47,7 @@ import world.bentobox.bentobox.util.MyBiomeGrid;
*
*/
public abstract class CopyWorldRegenerator implements WorldRegenerator {
private final BentoBox plugin;
protected CopyWorldRegenerator() {
@ -68,7 +71,7 @@ public abstract class CopyWorldRegenerator implements WorldRegenerator {
public CompletableFuture<Void> regenerate(GameModeAddon gm, IslandDeletion di, World world) {
return gm.isUsesNewChunkGeneration() ? regenerateCopy(gm, di, world) : regenerateSimple(gm, di, world);
}
public CompletableFuture<Void> regenerateCopy(GameModeAddon gm, IslandDeletion di, World world) {
CompletableFuture<Void> bigFuture = new CompletableFuture<>();
new BukkitRunnable() {
@ -110,7 +113,7 @@ public abstract class CopyWorldRegenerator implements WorldRegenerator {
@Override
public CompletableFuture<Void> regenerateChunk(Chunk chunk) {
return regenerateChunk(null, chunk.getWorld(), chunk.getX(), chunk.getZ());
return regenerateChunk(null, chunk.getWorld(), chunk.getX(), chunk.getZ());
}
private CompletableFuture<Void> regenerateChunk(@Nullable IslandDeletion di, World world, int chunkX, int chunkZ) {
@ -132,7 +135,7 @@ public abstract class CopyWorldRegenerator implements WorldRegenerator {
copyChunkDataToChunk(chunkTo, chunkFrom, di != null ? di.getBox() : null);
} catch (InterruptedException | ExecutionException e) {
Thread.currentThread().interrupt();
Thread.currentThread().interrupt();
}
});
return CompletableFuture.allOf(cleanFuture, copyFuture);
@ -159,7 +162,7 @@ public abstract class CopyWorldRegenerator implements WorldRegenerator {
);
// Similarly, when the chunk is loaded, remove all the entities in the chunk apart from players
CompletableFuture<Void> entitiesFuture = chunkFuture.thenAccept(chunk ->
CompletableFuture<Void> entitiesFuture = chunkFuture.thenAccept(chunk ->
// Remove all entities in chunk, including any dropped items as a result of clearing the blocks above
Arrays.stream(chunk.getEntities())
.filter(e -> !(e instanceof Player) && di.inBounds(e.getLocation().getBlockX(), e.getLocation().getBlockZ()))
@ -200,35 +203,35 @@ public abstract class CopyWorldRegenerator implements WorldRegenerator {
}
private void processEntity(Entity entity, Location location) {
Entity bpe = location.getWorld().spawnEntity(location, entity.getType());
bpe.setCustomName(entity.getCustomName());
if (entity instanceof Villager villager && bpe instanceof Villager villager2) {
setVillager(villager, villager2);
}
if (entity instanceof Colorable c && bpe instanceof Colorable cc) {
if (c.getColor() != null) {
cc.setColor(c.getColor());
}
}
if (entity instanceof Tameable t && bpe instanceof Tameable tt) {
tt.setTamed(t.isTamed());
}
if (entity instanceof ChestedHorse ch && bpe instanceof ChestedHorse ch2) {
ch2.setCarryingChest(ch.isCarryingChest());
}
// Only set if child. Most animals are adults
if (entity instanceof Ageable a && bpe instanceof Ageable aa) {
if (a.isAdult()) aa.setAdult();
}
if (entity instanceof AbstractHorse horse && bpe instanceof AbstractHorse horse2) {
horse2.setDomestication(horse.getDomestication());
horse2.getInventory().setContents(horse.getInventory().getContents());
}
if (entity instanceof Horse horse && bpe instanceof Horse horse2) {
horse2.setStyle(horse.getStyle());
Entity bpe = location.getWorld().spawnEntity(location, entity.getType());
bpe.setCustomName(entity.getCustomName());
if (entity instanceof Villager villager && bpe instanceof Villager villager2) {
setVillager(villager, villager2);
}
if (entity instanceof Colorable c && bpe instanceof Colorable cc) {
if (c.getColor() != null) {
cc.setColor(c.getColor());
}
}
if (entity instanceof Tameable t && bpe instanceof Tameable tt) {
tt.setTamed(t.isTamed());
}
if (entity instanceof ChestedHorse ch && bpe instanceof ChestedHorse ch2) {
ch2.setCarryingChest(ch.isCarryingChest());
}
// Only set if child. Most animals are adults
if (entity instanceof Ageable a && bpe instanceof Ageable aa) {
if (a.isAdult()) aa.setAdult();
}
if (entity instanceof AbstractHorse horse && bpe instanceof AbstractHorse horse2) {
horse2.setDomestication(horse.getDomestication());
horse2.getInventory().setContents(horse.getInventory().getContents());
}
if (entity instanceof Horse horse && bpe instanceof Horse horse2) {
horse2.setStyle(horse.getStyle());
}
}
/**
* Set the villager stats
@ -241,7 +244,7 @@ public abstract class CopyWorldRegenerator implements WorldRegenerator {
villager2.setProfession(v.getProfession());
villager2.setVillagerType(v.getVillagerType());
}
private void processTileEntity(Block fromBlock, Block toBlock) {
// Block state
BlockState blockState = fromBlock.getState();
@ -249,11 +252,9 @@ public abstract class CopyWorldRegenerator implements WorldRegenerator {
// Signs
if (blockState instanceof Sign fromSign && b instanceof Sign toSign) {
int i = 0;
for (String line : fromSign.getLines()) {
toSign.setLine(i++, line);
for (Side side : Side.values()) {
writeSign(fromSign, toSign, side);
}
toSign.setGlowingText(fromSign.isGlowingText());
}
// Chests
else if (blockState instanceof InventoryHolder ih && b instanceof InventoryHolder toChest) {
@ -270,7 +271,17 @@ public abstract class CopyWorldRegenerator implements WorldRegenerator {
toBanner.setPatterns(banner.getPatterns());
}
}
private void writeSign(Sign fromSign, Sign toSign, Side side) {
SignSide fromSide = fromSign.getSide(side);
SignSide toSide = toSign.getSide(side);
int i = 0;
for (String line : fromSide.getLines()) {
toSide.setLine(i++, line);
}
toSide.setGlowingText(fromSide.isGlowingText());
}
public CompletableFuture<Void> regenerateSimple(GameModeAddon gm, IslandDeletion di, World world) {
CompletableFuture<Void> bigFuture = new CompletableFuture<>();

View File

@ -1,4 +1,4 @@
package world.bentobox.bentobox.nms.v1_19_R3;
package world.bentobox.bentobox.nms.v1_20_R1;
import java.util.List;
import java.util.Map;
@ -11,8 +11,8 @@ import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Block;
import org.bukkit.block.data.BlockData;
import org.bukkit.craftbukkit.v1_19_R3.CraftWorld;
import org.bukkit.craftbukkit.v1_19_R3.block.data.CraftBlockData;
import org.bukkit.craftbukkit.v1_20_R1.CraftWorld;
import org.bukkit.craftbukkit.v1_20_R1.block.data.CraftBlockData;
import net.minecraft.core.BlockPosition;
import net.minecraft.world.level.block.state.IBlockData;

View File

@ -1,10 +1,10 @@
package world.bentobox.bentobox.nms.v1_19_R3;
package world.bentobox.bentobox.nms.v1_20_R1;
import org.bukkit.Bukkit;
import org.bukkit.Material;
import org.bukkit.block.data.BlockData;
import org.bukkit.craftbukkit.v1_19_R3.CraftWorld;
import org.bukkit.craftbukkit.v1_19_R3.block.data.CraftBlockData;
import org.bukkit.craftbukkit.v1_20_R1.CraftWorld;
import org.bukkit.craftbukkit.v1_20_R1.block.data.CraftBlockData;
import net.minecraft.core.BlockPosition;
import net.minecraft.world.level.World;

View File

@ -19,6 +19,8 @@ import org.bukkit.block.CreatureSpawner;
import org.bukkit.block.Sign;
import org.bukkit.block.data.BlockData;
import org.bukkit.block.data.type.WallSign;
import org.bukkit.block.sign.Side;
import org.bukkit.block.sign.SignSide;
import org.bukkit.entity.LivingEntity;
import org.bukkit.entity.Player;
import org.bukkit.inventory.Inventory;
@ -120,7 +122,9 @@ public class DefaultPasteUtil {
BlockState bs = block.getState();
// Signs
if (bs instanceof Sign) {
writeSign(island, block, bpBlock.getSignLines(), bpBlock.isGlowingText());
for (Side side : Side.values()) {
writeSign(island, block, bpBlock, side);
}
}
// Chests, in general
else if (bs instanceof InventoryHolder holder) {
@ -200,8 +204,12 @@ public class DefaultPasteUtil {
* @param block - block
* @param lines - lines
* @param glow - is sign glowing?
* @param side - the side being writted
*/
public static void writeSign(Island island, final Block block, final List<String> lines, boolean glow) {
public static void writeSign(Island island, final Block block, BlueprintBlock bpSign, Side side) {
List<String> lines = bpSign.getSignLines(side);
boolean glow = bpSign.isGlowingText(side);
BlockFace bf;
if (block.getType().name().contains("WALL_SIGN")) {
WallSign wallSign = (WallSign) block.getBlockData();
@ -211,7 +219,7 @@ public class DefaultPasteUtil {
bf = sign.getRotation();
}
// Handle spawn sign
if (island != null && !lines.isEmpty() && lines.get(0).equalsIgnoreCase(TextVariables.SPAWN_HERE)) {
if (side == Side.FRONT && island != null && !lines.isEmpty() && lines.get(0).equalsIgnoreCase(TextVariables.SPAWN_HERE)) {
block.setType(Material.AIR);
// Orient to face same direction as sign
Location spawnPoint = new Location(block.getWorld(), block.getX() + 0.5D, block.getY(),
@ -225,7 +233,8 @@ public class DefaultPasteUtil {
name = plugin.getPlayers().getName(island.getOwner());
}
// Handle locale text for starting sign
org.bukkit.block.Sign s = (org.bukkit.block.Sign) block.getState();
Sign s = (org.bukkit.block.Sign) block.getState();
SignSide signSide = s.getSide(side);
// Sign text must be stored under the addon's name.sign.line0,1,2,3 in the yaml file
if (island != null && !lines.isEmpty() && lines.get(0).equalsIgnoreCase(TextVariables.START_TEXT)) {
// Get the addon that is operating in this world
@ -233,17 +242,17 @@ public class DefaultPasteUtil {
Optional<User> user = Optional.ofNullable(island.getOwner()).map(User::getInstance);
if (user.isPresent()) {
for (int i = 0; i < 4; i++) {
s.setLine(i, Util.translateColorCodes(plugin.getLocalesManager().getOrDefault(user.get(),
signSide.setLine(i, Util.translateColorCodes(plugin.getLocalesManager().getOrDefault(user.get(),
addonName + ".sign.line" + i, "").replace(TextVariables.NAME, name)));
}
}
} else {
// Just paste
for (int i = 0; i < 4; i++) {
s.setLine(i, lines.get(i));
signSide.setLine(i, lines.get(i));
}
}
s.setGlowingText(glow);
signSide.setGlowingText(glow);
// Update the sign
s.update();
}

View File

@ -10,6 +10,8 @@ import org.bukkit.util.Vector;
import org.eclipse.jdt.annotation.Nullable;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.addons.Addon;
import world.bentobox.bentobox.api.events.island.IslandEvent;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.database.objects.Island;
@ -43,8 +45,9 @@ public class IslandInfo {
/**
* Shows admin info of this island
* @param user user asking
* @param addon Addon executing this command
*/
public void showAdminInfo(User user) {
public void showAdminInfo(User user, Addon addon) {
user.sendMessage("commands.admin.info.title");
user.sendMessage("commands.admin.info.island-uuid", TextVariables.UUID, island.getUniqueId());
if (owner == null) {
@ -98,6 +101,15 @@ public class IslandInfo {
if (island.getPurgeProtected()) {
user.sendMessage("commands.admin.info.purge-protected");
}
// Fire info event to allow other addons to add to info
IslandEvent.builder()
.island(island)
.location(island.getCenter())
.reason(IslandEvent.Reason.INFO)
.involvedPlayer(user.getUniqueId())
.addon(addon)
.admin(true)
.build();
}
@ -130,6 +142,13 @@ public class IslandInfo {
user.sendMessage("commands.admin.info.banned-players");
island.getBanned().forEach(u -> user.sendMessage("commands.admin.info.banned-format", TextVariables.NAME, plugin.getPlayers().getName(u)));
}
// Fire info event
IslandEvent.builder()
.island(island)
.location(island.getCenter())
.reason(IslandEvent.Reason.INFO)
.involvedPlayer(user.getUniqueId())
.build();
return true;
}

View File

@ -218,6 +218,14 @@ public class ServerCompatibility {
* @since 1.22.1
*/
V1_19_4(Compatibility.COMPATIBLE),
/**
* @since 1.24.0
*/
V1_20(Compatibility.INCOMPATIBLE),
/**
* @since 1.24.0
*/
V1_20_1(Compatibility.COMPATIBLE),
;
private final Compatibility compatibility;

View File

@ -21,6 +21,7 @@ general:
no-permission: "&c You don't have the permission to execute this command (&7 [permission]&c )."
insufficient-rank: "&c Your rank is not high enough to do that! (&7 [rank]&c )"
use-in-game: "&c This command is only available in-game."
use-in-console: "&c This command is only available in the console."
no-team: "&c You do not have a team!"
no-island: "&c You do not have an island!"
player-has-island: "&c Player already has an island!"
@ -428,6 +429,8 @@ commands:
success: "&a Successfully reset [name]'s island name."
bentobox:
description: "BentoBox admin command"
perms:
description: "displays the effective perms for BentoBox and Addons in a YAML format"
about:
description: "displays copyright and license information"
reload:
@ -773,6 +776,12 @@ protection:
Toggle placing, breaking and
entering into boats.
hint: "No boat interaction allowed"
BOOKSHELF:
name: "Bookshelves"
description: |-
&a Allow to place books
&a or to take books.
hint: "cannot place a book or take a book."
BREAK_BLOCKS:
description: "Toggle breaking"
name: "Break blocks"
@ -1325,6 +1334,12 @@ protection:
&a activation.
name: "Sculk Shrieker"
hint: "sculk shrieker activation is disabled"
SIGN_EDITING:
description: |-
&a Allows text editing
&a of signs
name: "Sign Editing"
hint: "sign editing is disabled"
TNT_DAMAGE:
description: |-
&a Allow TNT and TNT minecarts

View File

@ -60,4 +60,6 @@ permissions:
bentobox.version:
description: Allows to use /bentobox version
default: op
bentobox.perms:
description: Allow use of '/bentobox perms' command
default: OP

View File

@ -13,6 +13,7 @@ import static org.mockito.Mockito.when;
import java.util.List;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
@ -85,6 +86,21 @@ public class HiddenCommandTest {
CommandSender sender = mock(CommandSender.class);
String[] args = {"h"};
List<String> opList = tlc.tabComplete(sender, "top", args);
assertEquals(2, opList.size());
assertEquals("help", opList.get(0)); // Console can see all commands
assertEquals("hidden", opList.get(1)); // Console can see all commands
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.CompositeCommand#tabComplete(Player, java.lang.String, java.lang.String[])}.
*/
@Test
public void testTabCompletePlayerStringStringArrayHidden() {
TopLevelCommand tlc = new TopLevelCommand();
Player sender = mock(Player.class);
String[] args = {"h"};
List<String> opList = tlc.tabComplete(sender, "top", args);
opList.forEach(System.out::println);
assertEquals(1, opList.size());
assertEquals("help", opList.get(0)); // Only help
}
@ -95,7 +111,7 @@ public class HiddenCommandTest {
@Test
public void testTabCompleteCommandSenderStringStringArrayInvisible() {
TopLevelCommand tlc = new TopLevelCommand();
CommandSender sender = mock(CommandSender.class);
Player sender = mock(Player.class);
String[] args = {"i"};
List<String> opList = tlc.tabComplete(sender, "top", args);
assertTrue(opList.isEmpty());

View File

@ -13,6 +13,7 @@ import static org.mockito.Mockito.when;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Optional;
import java.util.UUID;
@ -44,6 +45,7 @@ import world.bentobox.bentobox.managers.CommandsManager;
import world.bentobox.bentobox.managers.IslandWorldManager;
import world.bentobox.bentobox.managers.IslandsManager;
import world.bentobox.bentobox.managers.LocalesManager;
import world.bentobox.bentobox.managers.PlaceholdersManager;
import world.bentobox.bentobox.managers.PlayersManager;
import world.bentobox.bentobox.util.Util;
@ -74,6 +76,8 @@ public class AdminTeleportCommandTest {
private World netherWorld;
@Mock
private World endWorld;
@Mock
private PlaceholdersManager phm;
/**
@ -96,16 +100,25 @@ public class AdminTeleportCommandTest {
while(notUUID.equals(uuid)) {
notUUID = UUID.randomUUID();
}
when(p.getUniqueId()).thenReturn(uuid);
when(p.hasPermission("admin.tp")).thenReturn(true);
when(p.hasPermission("admin")).thenReturn(false);
when(user.getUniqueId()).thenReturn(uuid);
when(user.getPlayer()).thenReturn(p);
when(user.getName()).thenReturn("tastybento");
when(user.isPlayer()).thenReturn(true);
when(user.hasPermission("admin.tp")).thenReturn(true);
when(user.hasPermission("admin")).thenReturn(false);
User.setPlugin(plugin);
// Parent command has no aliases
when(ac.getSubCommandAliases()).thenReturn(new HashMap<>());
when(ac.getTopLabel()).thenReturn("bskyblock");
when(ac.getLabel()).thenReturn("bskyblock");
when(ac.getWorld()).thenReturn(world);
when(ac.getPermission()).thenReturn("admin");
// World
when(world.getEnvironment()).thenReturn(Environment.NORMAL);
@ -132,12 +145,12 @@ public class AdminTeleportCommandTest {
// Server & Scheduler
BukkitScheduler sch = mock(BukkitScheduler.class);
PowerMockito.mockStatic(Bukkit.class);
PowerMockito.mockStatic(Bukkit.class, Mockito.RETURNS_MOCKS);
when(Bukkit.getScheduler()).thenReturn(sch);
// Locales
LocalesManager lm = mock(LocalesManager.class);
when(lm.get(any(), any())).thenReturn("mock translation");
when(lm.get(any(), any())).thenAnswer((Answer<String>) invocation -> invocation.getArgument(1, String.class));
when(plugin.getLocalesManager()).thenReturn(lm);
when(user.getTranslation(Mockito.anyString(),Mockito.anyString(), Mockito.anyString())).thenAnswer((Answer<String>) invocation -> invocation.getArgument(0, String.class));
@ -165,6 +178,9 @@ public class AdminTeleportCommandTest {
// Util
PowerMockito.mockStatic(Util.class, Mockito.RETURNS_MOCKS);
when(Util.getUUID(anyString())).thenCallRealMethod();
// Placeholder manager
when(plugin.getPlaceholdersManager()).thenReturn(phm);
}
@After
@ -276,5 +292,36 @@ public class AdminTeleportCommandTest {
verify(user).getTranslation(eq("commands.admin.tp.manual"), eq("[location]"), eq("0 0 0"));
}
@Test
public void testPermissionsNoRootPermission() {
when(p.hasPermission("admin.tp")).thenReturn(true);
when(p.hasPermission("admin")).thenReturn(false);
when(pm.getUUID(eq("tastybento"))).thenReturn(notUUID);
when(im.hasIsland(any(), any(UUID.class))).thenReturn(true);
AdminTeleportCommand atc = new AdminTeleportCommand(ac,"tpend");
assertTrue(atc.canExecute(user, "tpend", List.of("tastybento")));
String[] list = new String[2];
list[0] = "tpend";
list[1] = "tastybento";
// Should fail
assertFalse(atc.execute(p, "tpend", list));
}
@Test
public void testPermissionsHasRootPermission() {
when(p.hasPermission("admin.tp")).thenReturn(true);
when(p.hasPermission("admin")).thenReturn(true);
when(pm.getUUID(eq("tastybento"))).thenReturn(notUUID);
when(im.hasIsland(any(), any(UUID.class))).thenReturn(true);
AdminTeleportCommand atc = new AdminTeleportCommand(ac,"tpend");
assertTrue(atc.canExecute(user, "tpend", List.of("tastybento")));
String[] list = new String[2];
list[0] = "tpend";
list[1] = "tastybento";
// Should pass
assertTrue(atc.execute(p, "tpend", list));
verify(p).hasPermission("admin.tp");
verify(p).hasPermission("admin");
}
}

View File

@ -0,0 +1,211 @@
package world.bentobox.bentobox.api.commands.island;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import java.util.List;
import java.util.UUID;
import org.bukkit.Bukkit;
import org.bukkit.World;
import org.eclipse.jdt.annotation.Nullable;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import org.powermock.reflect.Whitebox;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.addons.GameModeAddon;
import world.bentobox.bentobox.api.configuration.WorldSettings;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.database.objects.Island;
import world.bentobox.bentobox.managers.CommandsManager;
import world.bentobox.bentobox.managers.IslandsManager;
/**
* @author tastybento
*
*/
@RunWith(PowerMockRunner.class)
@PrepareForTest({Bukkit.class, BentoBox.class})
public class DefaultPlayerCommandTest {
@Mock
GameModeAddon addon;
private PlayerCommand dpc;
@Mock
private WorldSettings ws;
@Mock
private User user;
@Mock
private IslandsManager im;
@Mock
private @Nullable Island island;
class PlayerCommand extends DefaultPlayerCommand {
protected PlayerCommand(GameModeAddon addon) {
super(addon);
}
}
/**
* @throws java.lang.Exception
*/
@Before
public void setUp() throws Exception {
// Set up plugin
BentoBox plugin = mock(BentoBox.class);
Whitebox.setInternalState(BentoBox.class, "instance", plugin);
// Addon
// User
when(user.getUniqueId()).thenReturn(UUID.randomUUID());
// IM
when(plugin.getIslandsManager()).thenReturn(im);
when(plugin.getIslands()).thenReturn(im);
when(im.getIsland(any(World.class), any(UUID.class))).thenReturn(island);
// Command manager
CommandsManager cm = mock(CommandsManager.class);
when(plugin.getCommandsManager()).thenReturn(cm);
// World Settings
when(ws.getDefaultPlayerAction()).thenReturn("go");
when(ws.getDefaultNewPlayerAction()).thenReturn("create");
PowerMockito.mockStatic(Bukkit.class, Mockito.RETURNS_MOCKS);
when(ws.getPlayerCommandAliases()).thenReturn("island is");
when(addon.getWorldSettings()).thenReturn(ws);
dpc = new PlayerCommand(addon);
dpc.setWorld(mock(World.class));
}
/**
* @throws java.lang.Exception
*/
@After
public void tearDown() throws Exception {
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#DefaultPlayerCommand(world.bentobox.bentobox.api.addons.GameModeAddon)}.
*/
@Test
public void testDefaultPlayerCommand() {
assertNotNull(dpc);
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#setup()}.
*/
@Test
public void testSetup() {
assertEquals("commands.island.help.description", dpc.getDescription());
assertTrue(dpc.isOnlyPlayer());
assertEquals("island", dpc.getPermission());
// 20 = 19 subcommands + help command
assertEquals(20, dpc.getSubCommands().size()); // Update when commands are added or removed
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringUnknownCommand() {
assertFalse(dpc.execute(user, "label", List.of("unknown")));
verify(user).sendMessage("general.errors.unknown-command", TextVariables.LABEL, "island");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringNullUser() {
assertFalse(dpc.execute(null, "label", List.of()));
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringEmptyArgsHasIsland() {
assertFalse(dpc.execute(user, "label", List.of()));
verify(user).sendMessage("general.errors.use-in-game");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringEmptyArgsHasNoIsland() {
when(im.getIsland(any(World.class), any(UUID.class))).thenReturn(null);
assertFalse(dpc.execute(user, "label", List.of()));
verify(user).sendMessage("general.errors.use-in-game");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringEmptyArgsHasIslandUnknownCommand() {
when(ws.getDefaultPlayerAction()).thenReturn("goxxx");
assertFalse(dpc.execute(user, "label", List.of()));
verify(user).performCommand("label goxxx");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringEmptyArgsHasNoIslandUnknownCommand() {
when(ws.getDefaultNewPlayerAction()).thenReturn("createxxx");
when(im.getIsland(any(World.class), any(UUID.class))).thenReturn(null);
assertFalse(dpc.execute(user, "label", List.of()));
verify(user).performCommand("label createxxx");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringEmptyArgsHasIslandUnknownCommandSlash() {
when(ws.getDefaultPlayerAction()).thenReturn("/goxxx");
assertFalse(dpc.execute(user, "label", List.of()));
verify(user).performCommand("goxxx");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.DefaultPlayerCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringEmptyArgsHasNoIslandUnknownCommandSlash() {
when(ws.getDefaultNewPlayerAction()).thenReturn("/createxxx");
when(im.getIsland(any(World.class), any(UUID.class))).thenReturn(null);
assertFalse(dpc.execute(user, "label", List.of()));
verify(user).performCommand("createxxx");
}
}

View File

@ -0,0 +1,265 @@
package world.bentobox.bentobox.api.commands.island;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.UUID;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.World;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import org.powermock.reflect.Whitebox;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.Settings;
import world.bentobox.bentobox.api.addons.GameModeAddon;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.database.objects.Island;
import world.bentobox.bentobox.managers.CommandsManager;
import world.bentobox.bentobox.managers.IslandWorldManager;
import world.bentobox.bentobox.managers.IslandsManager;
import world.bentobox.bentobox.managers.PlayersManager;
import world.bentobox.bentobox.managers.RanksManager;
/**
* @author tastybento
*
*/
@RunWith(PowerMockRunner.class)
@PrepareForTest({Bukkit.class, BentoBox.class, User.class })
public class IslandDeletehomeCommandTest {
@Mock
private CompositeCommand ic;
private UUID uuid;
@Mock
private User user;
@Mock
private IslandsManager im;
@Mock
private PlayersManager pm;
@Mock
private Island island;
private IslandDeletehomeCommand idh;
@Mock
private IslandWorldManager iwm;
/**
* @throws java.lang.Exception
*/
@Before
public void setUp() throws Exception {
// Set up plugin
BentoBox plugin = mock(BentoBox.class);
Whitebox.setInternalState(BentoBox.class, "instance", plugin);
// Command manager
CommandsManager cm = mock(CommandsManager.class);
when(plugin.getCommandsManager()).thenReturn(cm);
// Ranks Manager
RanksManager rm = new RanksManager();
when(plugin.getRanksManager()).thenReturn(rm);
// Addon
GameModeAddon addon = mock(GameModeAddon.class);
// Settings
Settings settings = new Settings();
when(plugin.getSettings()).thenReturn(settings);
// Parent command has no aliases
when(ic.getSubCommandAliases()).thenReturn(new HashMap<>());
when(ic.getParameters()).thenReturn("parameters");
when(ic.getDescription()).thenReturn("description");
when(ic.getPermissionPrefix()).thenReturn("permission.");
when(ic.getUsage()).thenReturn("");
when(ic.getSubCommand(Mockito.anyString())).thenReturn(Optional.empty());
when(ic.getAddon()).thenReturn(addon);
when(plugin.getIslands()).thenReturn(im);
// Player
Player player = mock(Player.class);
when(user.isOp()).thenReturn(false);
uuid = UUID.randomUUID();
when(user.getUniqueId()).thenReturn(uuid);
when(user.getPlayer()).thenReturn(player);
when(user.getName()).thenReturn("tastybento");
when(user.getWorld()).thenReturn(mock(World.class));
when(user.getTranslation(anyString())).thenAnswer(i -> i.getArgument(0, String.class));
// Island
when(island.getOwner()).thenReturn(uuid);
when(island.onIsland(any())).thenReturn(true);
when(im.getIsland(any(), any(UUID.class))).thenReturn(island);
when(im.getIsland(any(), any(User.class))).thenReturn(island);
@NotNull
Map<String, Location> homeMap = new HashMap<>();
homeMap.put("Home", null);
homeMap.put("Home2", null);
homeMap.put("Home3", null);
homeMap.put("Home4", null);
when(island.getHomes()).thenReturn(homeMap);
// IWM friendly name
when(iwm.getFriendlyName(any())).thenReturn("BSkyBlock");
// Not in nether
when(iwm.isNether(any())).thenReturn(false);
// Not in end
when(iwm.isEnd(any())).thenReturn(false);
// Number of homes default
when(iwm.getMaxHomes(any())).thenReturn(3);
when(plugin.getIWM()).thenReturn(iwm);
// Bukkit
PowerMockito.mockStatic(Bukkit.class, Mockito.RETURNS_MOCKS);
idh = new IslandDeletehomeCommand(ic);
}
/**
* @throws java.lang.Exception
*/
@After
public void tearDown() throws Exception {
User.clearUsers();
Mockito.framework().clearInlineMocks();
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#IslandDeletehomeCommand(world.bentobox.bentobox.api.commands.CompositeCommand)}.
*/
@Test
public void testIslandDeletehomeCommand() {
assertEquals("deletehome", idh.getLabel());
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#setup()}.
*/
@Test
public void testSetup() {
assertTrue(idh.isOnlyPlayer());
assertEquals("commands.island.deletehome.parameters", idh.getParameters());
assertEquals("commands.island.deletehome.description", idh.getDescription());
assertEquals("permission.island.deletehome", idh.getPermission());
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testCanExecuteHelp() {
idh.canExecute(user, "label", List.of());
verify(user).sendMessage("commands.help.header","[label]","commands.help.console");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testCanExecuteNoIsland() {
when(im.getIsland(any(), eq(user))).thenReturn(null);
assertFalse(idh.canExecute(user, "label", List.of("something")));
verify(user).sendMessage("general.errors.no-island");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testCanExecuteLowRank() {
when(island.getRank(user)).thenReturn(RanksManager.COOP_RANK);
when(island.getRankCommand(anyString())).thenReturn(RanksManager.OWNER_RANK);
assertFalse(idh.canExecute(user, "label", List.of("something")));
verify(user).sendMessage("general.errors.insufficient-rank",
TextVariables.RANK, "ranks.coop");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testCanExecuteUnknownHome() {
when(island.getRank(user)).thenReturn(RanksManager.OWNER_RANK);
when(island.getRankCommand(anyString())).thenReturn(RanksManager.COOP_RANK);
when(island.getHomes()).thenReturn(Map.of("home", mock(Location.class)));
when(im.isHomeLocation(eq(island), anyString())).thenReturn(false);
assertFalse(idh.canExecute(user, "label", List.of("something")));
verify(user).sendMessage("commands.island.go.unknown-home");
verify(user).sendMessage("commands.island.sethome.homes-are");
verify(user).sendMessage("home-list-syntax", TextVariables.NAME, "home");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testCanExecuteKnownHome() {
when(island.getRank(user)).thenReturn(RanksManager.OWNER_RANK);
when(island.getRankCommand(anyString())).thenReturn(RanksManager.COOP_RANK);
when(island.getHomes()).thenReturn(Map.of("home", mock(Location.class)));
when(im.isHomeLocation(eq(island), anyString())).thenReturn(true);
assertTrue(idh.canExecute(user, "label", List.of("home")));
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfString() {
assertTrue(idh.execute(user, "label", List.of("home")));
verify(user).sendMessage("commands.confirmation.confirm", "[seconds]", "10");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#tabComplete(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testTabCompleteUserStringListOfString() {
when(island.getHomes()).thenReturn(Map.of("home", mock(Location.class)));
Optional<List<String>> list = idh.tabComplete(user, "label", List.of("hom"));
assertTrue(list.isPresent());
assertEquals("home", list.get().get(0));
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandDeletehomeCommand#tabComplete(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testTabCompleteUserStringListOfStringNothing() {
when(island.getHomes()).thenReturn(Map.of("home", mock(Location.class)));
Optional<List<String>> list = idh.tabComplete(user, "label", List.of("f"));
assertTrue(list.isPresent());
assertTrue(list.get().isEmpty());
}
}

View File

@ -0,0 +1,281 @@
/**
*
*/
package world.bentobox.bentobox.api.commands.island;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
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.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.UUID;
import org.bukkit.Bukkit;
import org.bukkit.World;
import org.bukkit.entity.Player;
import org.bukkit.plugin.PluginManager;
import org.eclipse.jdt.annotation.NonNull;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import org.powermock.reflect.Whitebox;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.Settings;
import world.bentobox.bentobox.api.addons.Addon;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.database.objects.Island;
import world.bentobox.bentobox.managers.CommandsManager;
import world.bentobox.bentobox.managers.IslandWorldManager;
import world.bentobox.bentobox.managers.IslandsManager;
import world.bentobox.bentobox.managers.LocalesManager;
import world.bentobox.bentobox.managers.PlaceholdersManager;
import world.bentobox.bentobox.managers.PlayersManager;
import world.bentobox.bentobox.managers.RanksManager;
/**
* @author tastybento
*
*/
@RunWith(PowerMockRunner.class)
@PrepareForTest({Bukkit.class, BentoBox.class})
public class IslandSetnameCommandTest {
@Mock
private CompositeCommand ic;
private UUID uuid;
@Mock
private User user;
@Mock
private IslandsManager im;
@Mock
private PlayersManager pm;
@Mock
private Island island;
@Mock
private Addon addon;
private IslandSetnameCommand isc;
@Mock
private @NonNull World world;
private RanksManager rm;
private Settings settings;
@Mock
private PluginManager pim;
/**
* @throws java.lang.Exception
*/
@Before
public void setUp() throws Exception {
// Set up plugin
BentoBox plugin = mock(BentoBox.class);
Whitebox.setInternalState(BentoBox.class, "instance", plugin);
User.setPlugin(plugin);
// Command manager
CommandsManager cm = mock(CommandsManager.class);
when(plugin.getCommandsManager()).thenReturn(cm);
// Settings
settings = new Settings();
when(plugin.getSettings()).thenReturn(settings);
// User
when(user.isOp()).thenReturn(false);
uuid = UUID.randomUUID();
when(user.getUniqueId()).thenReturn(uuid);
Player p = mock(Player.class);
when(user.getPlayer()).thenReturn(p);
when(user.getName()).thenReturn("tastybento");
when(user.getDisplayName()).thenReturn("&Ctastybento");
when(user.getPermissionValue(anyString(), anyInt())).thenReturn(-1);
when(user.getTranslation(any())).thenAnswer(invocation -> invocation.getArgument(0, String.class));
// Parent command has no aliases
when(ic.getSubCommandAliases()).thenReturn(new HashMap<>());
when(ic.getWorld()).thenReturn(world);
// IWM friendly name
IslandWorldManager iwm = mock(IslandWorldManager.class);
when(iwm.getFriendlyName(any())).thenReturn("BSkyBlock");
when(plugin.getIWM()).thenReturn(iwm);
// Player has island to begin with
when(im.getIsland(world, user)).thenReturn(island);
when(plugin.getIslands()).thenReturn(im);
when(island.getName()).thenReturn("previous-name");
// Server and Plugin Manager for events
PowerMockito.mockStatic(Bukkit.class, Mockito.RETURNS_MOCKS);
when(Bukkit.getPluginManager()).thenReturn(pim);
// Locales
LocalesManager lm = mock(LocalesManager.class);
when(lm.get(any(), any())).thenAnswer(invocation -> invocation.getArgument(1, String.class));
when(plugin.getLocalesManager()).thenReturn(lm);
PlaceholdersManager phm = mock(PlaceholdersManager.class);
when(phm.replacePlaceholders(any(), any())).thenAnswer(invocation -> invocation.getArgument(1, String.class));
// Placeholder manager
when(plugin.getPlaceholdersManager()).thenReturn(phm);
// Ranks Manager
rm = new RanksManager();
when(plugin.getRanksManager()).thenReturn(rm);
// Test
isc = new IslandSetnameCommand(ic);
}
/**
* @throws java.lang.Exception
*/
@After
public void tearDown() throws Exception {
User.clearUsers();
Mockito.framework().clearInlineMocks();
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#IslandSetnameCommand(world.bentobox.bentobox.api.commands.CompositeCommand)}.
*/
@Test
public void testIslandSetnameCommand() {
assertEquals("setname", isc.getLabel());
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#setup()}.
*/
@Test
public void testSetup() {
assertTrue(isc.isOnlyPlayer());
assertEquals("commands.island.setname.parameters", isc.getParameters());
assertEquals("commands.island.setname.description", isc.getDescription());
assertEquals("island.name", isc.getPermission());
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testIslandSetnameCommandNoArgs() {
assertFalse(isc.canExecute(user, isc.getLabel(), new ArrayList<>()));
verify(user).sendMessage("commands.help.header", "[label]", "BSkyBlock");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testIslandSetnameCommandNoIsland() {
when(im.getIsland(world, user)).thenReturn(null);
assertFalse(isc.canExecute(user, isc.getLabel(), List.of("name")));
verify(user).sendMessage("general.errors.no-island");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testTooLowRank() {
when(island.getRank(any(User.class))).thenReturn(RanksManager.MEMBER_RANK);
when(island.getRankCommand(anyString())).thenReturn(RanksManager.OWNER_RANK);
assertFalse(isc.canExecute(user, isc.getLabel(), List.of("name")));
verify(user).sendMessage("general.errors.insufficient-rank", TextVariables.RANK, "ranks.member");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testIslandSetnameCommandNameTooShort() {
assertFalse(isc.canExecute(user, isc.getLabel(), List.of("x")));
verify(user).sendMessage("commands.island.setname.name-too-short", TextVariables.NUMBER, "4");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testIslandSetnameCommandNameOnlyColors() {
assertFalse(isc.canExecute(user, isc.getLabel(), List.of("§b§c§d§e")));
verify(user).sendMessage("commands.island.setname.name-too-short", TextVariables.NUMBER, "4");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testIslandSetnameCommandNameTooLong() {
assertFalse(isc.canExecute(user, isc.getLabel(), List.of("This is a very long name that is not allowed and will have to be prevented")));
verify(user).sendMessage("commands.island.setname.name-too-long", TextVariables.NUMBER, "20");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testIslandSetnameCommandNameNotUnique() {
settings.setNameUniqueness(true);
when(im.nameExists(eq(world), anyString())).thenReturn(true);
assertFalse(isc.canExecute(user, isc.getLabel(), List.of("name2")));
verify(user).sendMessage("commands.island.setname.name-already-exists");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testIslandSetnameCommandNameApplyColors() {
when(user.hasPermission(anyString())).thenReturn(true);
settings.setNameUniqueness(true);
when(im.nameExists(world, "name§b")).thenReturn(true);
assertFalse(isc.canExecute(user, isc.getLabel(), List.of("name&b")));
verify(user).sendMessage("commands.island.setname.name-already-exists");
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#canExecute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testIslandSetnameCommandAllOK() {
assertTrue(isc.canExecute(user, isc.getLabel(), List.of("name-okay")));
verify(user, never()).sendMessage(anyString());
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.island.IslandSetnameCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfString() {
when(user.hasPermission(anyString())).thenReturn(true);
assertTrue(isc.execute(user, isc.getLabel(), List.of("name-okay")));
verify(island).setName("name-okay");
verify(user).sendMessage("commands.island.setname.success", TextVariables.NAME, "name-okay");
verify(pim, times(2)).callEvent(any());
}
}

View File

@ -0,0 +1,201 @@
package world.bentobox.bentobox.api.panels;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.mockito.Mockito.when;
import java.util.List;
import java.util.Optional;
import org.bukkit.Bukkit;
import org.bukkit.Material;
import org.bukkit.inventory.ItemStack;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import world.bentobox.bentobox.api.panels.PanelItem.ClickHandler;
import world.bentobox.bentobox.api.panels.builders.PanelItemBuilder;
/**
* @author tastybento
*
*/
@RunWith(PowerMockRunner.class)
@PrepareForTest({ Bukkit.class })
public class PanelItemTest {
@Mock
private PanelItemBuilder pib;
private PanelItem pi;
@Mock
private ClickHandler clickHandler;
/**
* @throws java.lang.Exception
*/
@Before
public void setUp() throws Exception {
PowerMockito.mockStatic(Bukkit.class, Mockito.RETURNS_MOCKS);
// Builder
when(pib.getAmount()).thenReturn(2);
when(pib.getClickHandler()).thenReturn(clickHandler);
when(pib.getDescription()).thenReturn(List.of("Description", "hello"));
when(pib.getIcon()).thenReturn(new ItemStack(Material.STONE));
when(pib.getName()).thenReturn("Name");
when(pib.getPlayerHeadName()).thenReturn("tastybento");
pi = new PanelItem(pib);
}
/**
* @throws java.lang.Exception
*/
@After
public void tearDown() throws Exception {
Mockito.framework().clearInlineMocks();
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#empty()}.
*/
@Test
public void testEmpty() {
PanelItem panelItem = PanelItem.empty();
assertTrue(panelItem.getName().isEmpty());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#getItem()}.
*/
@Test
public void testGetItem() {
ItemStack i = pi.getItem();
assertNotNull(i);
assertEquals(Material.STONE, i.getType());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#getDescription()}.
*/
@Test
public void testGetDescription() {
assertEquals(2, pi.getDescription().size());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#setDescription(java.util.List)}.
*/
@Test
public void testSetDescription() {
assertEquals(2, pi.getDescription().size());
pi.setDescription(List.of("1","2","3"));
assertEquals(3, pi.getDescription().size());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#getName()}.
*/
@Test
public void testGetName() {
assertEquals("Name", pi.getName());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#setName(java.lang.String)}.
*/
@Test
public void testSetName() {
assertEquals("Name", pi.getName());
pi.setName("Name2");
assertEquals("Name2", pi.getName());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#isInvisible()}.
*/
@Test
public void testIsInvisible() {
assertFalse(pi.isInvisible());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#setInvisible(boolean)}.
*/
@Test
public void testSetInvisible() {
assertFalse(pi.isInvisible());
pi.setInvisible(true);
assertTrue(pi.isInvisible());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#getClickHandler()}.
*/
@Test
public void testGetClickHandler() {
assertEquals(clickHandler, pi.getClickHandler().get());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#setClickHandler(world.bentobox.bentobox.api.panels.PanelItem.ClickHandler)}.
*/
@Test
public void testSetClickHandler() {
assertEquals(clickHandler, pi.getClickHandler().get());
pi.setClickHandler(null);
assertEquals(Optional.empty(), pi.getClickHandler());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#isGlow()}.
*/
@Test
public void testIsGlow() {
assertFalse(pi.isGlow());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#setGlow(boolean)}.
*/
@Test
public void testSetGlow() {
assertFalse(pi.isGlow());
pi.setGlow(true);
assertTrue(pi.isGlow());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#isPlayerHead()}.
*/
@Test
public void testIsPlayerHead() {
assertTrue(pi.isPlayerHead());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#getPlayerHeadName()}.
*/
@Test
public void testGetPlayerHeadName() {
assertEquals("tastybento", pi.getPlayerHeadName());
}
/**
* Test method for {@link world.bentobox.bentobox.api.panels.PanelItem#setHead(org.bukkit.inventory.ItemStack)}.
*/
@Test
public void testSetHead() {
pi.setHead(new ItemStack(Material.PLAYER_HEAD));
}
}

View File

@ -0,0 +1,192 @@
package world.bentobox.bentobox.commands;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.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.util.HashMap;
import java.util.List;
import java.util.Map;
import org.bukkit.Bukkit;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.bukkit.permissions.Permission;
import org.bukkit.permissions.PermissionDefault;
import org.bukkit.plugin.PluginManager;
import org.eclipse.jdt.annotation.NonNull;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.stubbing.Answer;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import org.powermock.reflect.Whitebox;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.managers.CommandsManager;
import world.bentobox.bentobox.managers.IslandWorldManager;
import world.bentobox.bentobox.managers.LocalesManager;
import world.bentobox.bentobox.managers.PlaceholdersManager;
/**
* @author tastybento
*
*/
@RunWith(PowerMockRunner.class)
@PrepareForTest({Bukkit.class, BentoBox.class, User.class })
public class BentoBoxPermsCommandTest {
@Mock
private BentoBox plugin;
@Mock
private CompositeCommand ac;
@Mock
private User user;
@Mock
private LocalesManager lm;
BentoBoxPermsCommand cmd;
@Mock
private PlaceholdersManager phm;
@Mock
private PluginManager pim;
@Mock
private Permission perm;
private PermissionDefault defaultPerm = PermissionDefault.OP;
/**
* @throws java.lang.Exception
*/
@Before
public void setUp() throws Exception {
// Set up plugin
Whitebox.setInternalState(BentoBox.class, "instance", plugin);
// Command manager
CommandsManager cm = mock(CommandsManager.class);
when(plugin.getCommandsManager()).thenReturn(cm);
@NonNull
Map<String, CompositeCommand> cmdMap = new HashMap<>();
cmdMap.put("test", ac);
when(cm.getCommands()).thenReturn(cmdMap);
// Parent command has no aliases
when(ac.getSubCommandAliases()).thenReturn(new HashMap<>());
when(ac.getSubCommands()).thenReturn(new HashMap<>());
when(ac.getLabel()).thenReturn("bbox");
when(ac.getTopLabel()).thenReturn("bbox");
when(ac.getPermission()).thenReturn("admin.bbox");
when(ac.getDescription()).thenReturn("description");
// User
when(user.getTranslation(Mockito.anyString())).thenAnswer((Answer<String>) invocation -> invocation.getArgument(0, String.class));
when(user.isPlayer()).thenReturn(false);
User.setPlugin(plugin);
// Bukkit
PowerMockito.mockStatic(Bukkit.class, Mockito.RETURNS_MOCKS);
when(perm.getDefault()).thenReturn(defaultPerm);
when(pim.getPermission(anyString())).thenReturn(perm);
when(Bukkit.getPluginManager()).thenReturn(pim);
// Placeholders
when(phm.replacePlaceholders(any(), anyString())).thenAnswer((Answer<String>) invocation -> invocation.getArgument(1, String.class));
// BentoBox
when(plugin.getLocalesManager()).thenReturn(lm);
when(plugin.getPlaceholdersManager()).thenReturn(phm);
IslandWorldManager iwm = mock(IslandWorldManager.class);
when(plugin.getIWM()).thenReturn(iwm);
// Commands for perms
cmd = new BentoBoxPermsCommand(ac);
}
/**
* @throws java.lang.Exception
*/
@After
public void tearDown() throws Exception {
Mockito.framework().clearInlineMocks();
}
/**
* Test method for {@link world.bentobox.bentobox.commands.BentoBoxPermsCommand#BentoBoxPermsCommand(world.bentobox.bentobox.api.commands.CompositeCommand)}.
*/
@Test
public void testBentoBoxPermsCommand() {
assertNotNull(cmd);
}
/**
* Test method for {@link world.bentobox.bentobox.commands.BentoBoxPermsCommand#setup()}.
*/
@Test
public void testSetup() {
assertTrue(cmd.isOnlyConsole());
assertFalse(cmd.isOnlyPlayer());
assertEquals("bentobox.admin.perms", cmd.getPermission());
assertEquals("commands.bentobox.perms.description", cmd.getDescription());
assertEquals("commands.bentobox.perms.parameters", cmd.getParameters());
}
/**
* Test method for {@link world.bentobox.bentobox.commands.BentoBoxPermsCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfString() {
assertTrue(cmd.execute(user, "perms", List.of()));
verify(user).sendMessage("*** BentoBox effective perms:");
verify(user).sendRawMessage("permissions:");
verify(user).sendRawMessage(" admin.bbox:");
verify(user).sendRawMessage(" description: Allow use of '/bbox' command - null");
verify(user).sendRawMessage(" bentobox.admin.perms:");
verify(user).sendRawMessage(" description: Allow use of '/bbox perms' command - null");
verify(user, times(2)).sendRawMessage(" default: OP");
}
/**
* Test method for {@link world.bentobox.bentobox.commands.BentoBoxPermsCommand#execute(Player, java.lang.String, String[])}.
*/
@Test
public void testExecuteUserStringListOfStringConsole() {
String[] args = new String[1];
args[0] = "";
CommandSender p = mock(CommandSender.class);
assertTrue(cmd.execute(p, "perms", args));
verify(p, never()).sendMessage("general.errors.use-in-console");
}
/**
* Test method for {@link world.bentobox.bentobox.commands.BentoBoxPermsCommand#execute(Player, java.lang.String, String[])}.
*/
@Test
public void testExecuteUserStringListOfStringIsPlayer() {
when(user.isPlayer()).thenReturn(true);
String[] args = new String[1];
args[0] = "";
Player p = mock(Player.class);
assertFalse(cmd.execute(p, "perms", args));
verify(p).sendMessage("general.errors.use-in-console");
}
}

View File

@ -262,6 +262,106 @@ public class BannedCommandsTest {
}
/**
* Test for {@link BannedCommands#onCommand(PlayerCommandPreprocessEvent)}
*/
@Test
public void testBannedCommandsWithBannedCommand2() {
PlayerCommandPreprocessEvent e = new PlayerCommandPreprocessEvent(player, "/spawn");
BannedCommands bvc = new BannedCommands(plugin);
List<String> banned = new ArrayList<>();
banned.add("cmi sethome");
when(iwm.getVisitorBannedCommands(any())).thenReturn(banned);
bvc.onVisitorCommand(e);
verify(iwm).getVisitorBannedCommands(any());
assertFalse(e.isCancelled());
}
/**
* Test for {@link BannedCommands#onCommand(PlayerCommandPreprocessEvent)}
*/
@Test
public void testBannedCommandsWithBannedCommand3() {
PlayerCommandPreprocessEvent e = new PlayerCommandPreprocessEvent(player, "/cmi sethome");
BannedCommands bvc = new BannedCommands(plugin);
List<String> banned = new ArrayList<>();
banned.add("cmi sethome");
when(iwm.getVisitorBannedCommands(any())).thenReturn(banned);
bvc.onVisitorCommand(e);
verify(iwm).getVisitorBannedCommands(any());
assertTrue(e.isCancelled());
}
/**
* Test for {@link BannedCommands#onCommand(PlayerCommandPreprocessEvent)}
*/
@Test
public void testBannedCommandsWithBannedComman4() {
PlayerCommandPreprocessEvent e = new PlayerCommandPreprocessEvent(player, "/cmi");
BannedCommands bvc = new BannedCommands(plugin);
List<String> banned = new ArrayList<>();
banned.add("cmi sethome");
when(iwm.getVisitorBannedCommands(any())).thenReturn(banned);
bvc.onVisitorCommand(e);
verify(iwm).getVisitorBannedCommands(any());
assertFalse(e.isCancelled());
}
/**
* Test for {@link BannedCommands#onCommand(PlayerCommandPreprocessEvent)}
*/
@Test
public void testBannedCommandsWithBannedCommand5() {
PlayerCommandPreprocessEvent e = new PlayerCommandPreprocessEvent(player, "/cmi homey");
BannedCommands bvc = new BannedCommands(plugin);
List<String> banned = new ArrayList<>();
banned.add("cmi sethome");
when(iwm.getVisitorBannedCommands(any())).thenReturn(banned);
bvc.onVisitorCommand(e);
verify(iwm).getVisitorBannedCommands(any());
assertFalse(e.isCancelled());
}
/**
* Test for {@link BannedCommands#onCommand(PlayerCommandPreprocessEvent)}
*/
@Test
public void testBannedCommandsWithBannedCommand6() {
PlayerCommandPreprocessEvent e = new PlayerCommandPreprocessEvent(player, "/spawn");
BannedCommands bvc = new BannedCommands(plugin);
List<String> banned = new ArrayList<>();
banned.add("cmi sethome");
banned.add("spawn sethome now");
when(iwm.getVisitorBannedCommands(any())).thenReturn(banned);
bvc.onVisitorCommand(e);
verify(iwm).getVisitorBannedCommands(any());
assertFalse(e.isCancelled());
}
/**
* Test for {@link BannedCommands#onCommand(PlayerCommandPreprocessEvent)}
*/
@Test
public void testBannedCommandsWithBannedCommand7() {
PlayerCommandPreprocessEvent e = new PlayerCommandPreprocessEvent(player, "/spawn");
BannedCommands bvc = new BannedCommands(plugin);
List<String> banned = new ArrayList<>();
banned.add("cmi sethome");
banned.add("spawn sethome now");
banned.add("cmi multi now");
when(iwm.getVisitorBannedCommands(any())).thenReturn(banned);
bvc.onVisitorCommand(e);
verify(iwm).getVisitorBannedCommands(any());
assertFalse(e.isCancelled());
}
/**
* Test for {@link BannedCommands#onCommand(PlayerCommandPreprocessEvent)}
*/

View File

@ -12,6 +12,8 @@ import java.util.UUID;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.Tag;
import org.bukkit.World;
import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemFactory;
@ -121,6 +123,7 @@ public abstract class AbstractCommonSetup {
when(player.getInventory()).thenReturn(inv);
User.setPlugin(plugin);
User.clearUsers();
User.getInstance(player);
// IWM
@ -169,12 +172,36 @@ public abstract class AbstractCommonSetup {
// Util translate color codes (used in user translate methods)
when(Util.translateColorCodes(anyString())).thenAnswer((Answer<String>) invocation -> invocation.getArgument(0, String.class));
// Tags
for (Material m : Material.values()) {
if (m.name().contains("_SIGN")) {
when(Tag.ALL_SIGNS.isTagged(m)).thenReturn(true);
when(Tag.SIGNS.isTagged(m)).thenReturn(true);
}
if (m.name().contains("_WALL_SIGN")) {
when(Tag.WALL_SIGNS.isTagged(m)).thenReturn(true);
}
if (m.name().contains("_TRAPDOOR")) {
when(Tag.TRAPDOORS.isTagged(m)).thenReturn(true);
}
if (m.name().contains("FENCE")) {
when(Tag.FENCES.isTagged(m)).thenReturn(true);
}
if (m.name().contains("_DOOR")) {
when(Tag.DOORS.isTagged(m)).thenReturn(true);
}
if (m.name().contains("_BOAT") || m.name().contains("_RAFT")) {
when(Tag.ITEMS_BOATS.isTagged(m)).thenReturn(true);
}
}
}
/**
* @throws Exception
*/
@After
public void tearDown() {
public void tearDown() throws Exception {
User.clearUsers();
Mockito.framework().clearInlineMocks();
}

View File

@ -13,7 +13,6 @@ import static org.mockito.Mockito.when;
import org.bukkit.Bukkit;
import org.bukkit.Material;
import org.bukkit.Tag;
import org.bukkit.block.Block;
import org.bukkit.block.BlockFace;
import org.bukkit.block.BlockState;
@ -45,7 +44,7 @@ import world.bentobox.bentobox.util.Util;
*
*/
@RunWith(PowerMockRunner.class)
@PrepareForTest( {BentoBox.class, Flags.class, Util.class, Bukkit.class, Tag.class} )
@PrepareForTest( {BentoBox.class, Flags.class, Util.class, Bukkit.class} )
public class PlaceBlocksListenerTest extends AbstractCommonSetup {
private PlaceBlocksListener pbl;
@ -163,7 +162,7 @@ public class PlaceBlocksListenerTest extends AbstractCommonSetup {
assertTrue(e.isCancelled());
verify(notifier).notify(any(), eq("protection.protected"));
}
/**
* Test method for {@link PlaceBlocksListener#onBlockPlace(org.bukkit.event.block.BlockPlaceEvent)}.
*/
@ -184,7 +183,7 @@ public class PlaceBlocksListenerTest extends AbstractCommonSetup {
pbl.onBlockPlace(e);
assertFalse(e.isCancelled());
}
/**
* Test method for {@link PlaceBlocksListener#onBlockPlace(org.bukkit.event.block.BlockPlaceEvent)}.
*/
@ -206,7 +205,7 @@ public class PlaceBlocksListenerTest extends AbstractCommonSetup {
assertTrue(e.isCancelled());
verify(notifier).notify(any(), eq("protection.protected"));
}
/**
* Test method for {@link PlaceBlocksListener#onBlockPlace(org.bukkit.event.block.BlockPlaceEvent)}.
*/

View File

@ -0,0 +1,166 @@
package world.bentobox.bentobox.listeners.flags.protection;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.when;
import org.bukkit.Bukkit;
import org.bukkit.GameEvent;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Block;
import org.bukkit.event.block.BlockReceiveGameEvent;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.listeners.flags.AbstractCommonSetup;
import world.bentobox.bentobox.lists.Flags;
import world.bentobox.bentobox.util.Util;
/**
* @author tastybento
*
*/
@RunWith(PowerMockRunner.class)
@PrepareForTest( {BentoBox.class, Flags.class, Util.class, Bukkit.class} )
public class SculkSensorListenerTest extends AbstractCommonSetup {
private SculkSensorListener ssl;
@Mock
private Block block;
/**
* @throws java.lang.Exception
*/
@Before
public void setUp() throws Exception {
super.setUp();
// Default is that everything is allowed
when(island.isAllowed(any(), any())).thenReturn(true);
// In world
when(iwm.inWorld(any(World.class))).thenReturn(true);
// Block
when(block.getType()).thenReturn(Material.SCULK_SENSOR);
when(block.getWorld()).thenReturn(world);
when(block.getLocation()).thenReturn(location);
// User
when(player.getWorld()).thenReturn(world);
when(player.getLocation()).thenReturn(location);
User.getInstance(player);
ssl = new SculkSensorListener();
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorNotAllowed() {
when(island.isAllowed(any(), any())).thenReturn(false);
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertTrue(e.isCancelled());
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorAllowed() {
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertFalse(e.isCancelled());
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorNotInWorld() {
when(iwm.inWorld(any(World.class))).thenReturn(false);
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertFalse(e.isCancelled());
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorNotAllowedCalibrated() {
when(block.getType()).thenReturn(Material.CALIBRATED_SCULK_SENSOR);
when(island.isAllowed(any(), any())).thenReturn(false);
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertTrue(e.isCancelled());
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorAllowedCalibrated() {
when(block.getType()).thenReturn(Material.CALIBRATED_SCULK_SENSOR);
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertFalse(e.isCancelled());
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorNotInWorldCalibrated() {
when(block.getType()).thenReturn(Material.CALIBRATED_SCULK_SENSOR);
when(iwm.inWorld(any(World.class))).thenReturn(false);
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertFalse(e.isCancelled());
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorNotAllowedNotSculk() {
when(block.getType()).thenReturn(Material.SHULKER_BOX);
when(island.isAllowed(any(), any())).thenReturn(false);
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertFalse(e.isCancelled());
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorAllowedNotSculk() {
when(block.getType()).thenReturn(Material.SHULKER_BOX);
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertFalse(e.isCancelled());
}
/**
* Test method for {@link world.bentobox.bentobox.listeners.flags.protection.SculkSensorListener#onSculkSensor(org.bukkit.event.block.BlockReceiveGameEvent)}.
*/
@Test
public void testOnSculkSensorNotInWorldNotSculk() {
when(block.getType()).thenReturn(Material.SHULKER_BOX);
when(iwm.inWorld(any(World.class))).thenReturn(false);
BlockReceiveGameEvent e = new BlockReceiveGameEvent(GameEvent.BLOCK_ACTIVATE, block, player);
ssl.onSculkSensor(e);
assertFalse(e.isCancelled());
}
}

View File

@ -23,6 +23,7 @@ import org.bukkit.World;
import org.bukkit.entity.Player;
import org.bukkit.event.entity.PlayerDeathEvent;
import org.bukkit.event.player.PlayerRespawnEvent;
import org.bukkit.event.player.PlayerRespawnEvent.RespawnReason;
import org.bukkit.inventory.ItemStack;
import org.junit.After;
import org.junit.Before;
@ -213,7 +214,7 @@ public class IslandRespawnListenerTest {
// Has island
when(im.hasIsland(any(), any(UUID.class))).thenReturn(true);
// Respawn
PlayerRespawnEvent ev = new PlayerRespawnEvent(player, location, false, false);
PlayerRespawnEvent ev = new PlayerRespawnEvent(player, location, false, false, RespawnReason.DEATH);
l.onPlayerRespawn(ev);
assertEquals(safeLocation, ev.getRespawnLocation());
// Verify commands
@ -232,7 +233,7 @@ public class IslandRespawnListenerTest {
// Has island
when(im.hasIsland(any(), any(UUID.class))).thenReturn(true);
// Respawn
PlayerRespawnEvent ev = new PlayerRespawnEvent(player, location, false, false);
PlayerRespawnEvent ev = new PlayerRespawnEvent(player, location, false, false, RespawnReason.DEATH);
l.onPlayerRespawn(ev);
assertEquals(location, ev.getRespawnLocation());
}
@ -255,7 +256,7 @@ public class IslandRespawnListenerTest {
// Has island
when(im.hasIsland(any(), any(UUID.class))).thenReturn(true);
// Respawn
PlayerRespawnEvent ev = new PlayerRespawnEvent(player, location, false, false);
PlayerRespawnEvent ev = new PlayerRespawnEvent(player, location, false, false, RespawnReason.DEATH);
l.onPlayerRespawn(ev);
assertEquals(location, ev.getRespawnLocation());
}
@ -276,7 +277,7 @@ public class IslandRespawnListenerTest {
// Has island
when(im.hasIsland(any(), any(UUID.class))).thenReturn(true);
// Respawn
PlayerRespawnEvent ev = new PlayerRespawnEvent(player, location, false, false);
PlayerRespawnEvent ev = new PlayerRespawnEvent(player, location, false, false, RespawnReason.DEATH);
l.onPlayerRespawn(ev);
assertEquals(location, ev.getRespawnLocation());
}

View File

@ -17,6 +17,7 @@ import org.bukkit.World;
import org.bukkit.entity.Player;
import org.bukkit.event.player.PlayerRespawnEvent;
import org.bukkit.event.player.PlayerTeleportEvent;
import org.bukkit.event.player.PlayerRespawnEvent.RespawnReason;
import org.bukkit.scheduler.BukkitScheduler;
import org.junit.After;
import org.junit.Before;
@ -200,7 +201,7 @@ public class RemoveMobsListenerTest {
*/
@Test
public void testOnUserRespawn() {
PlayerRespawnEvent e = new PlayerRespawnEvent(player, inside, false, false);
PlayerRespawnEvent e = new PlayerRespawnEvent(player, inside, false, false, RespawnReason.DEATH);
new RemoveMobsListener().onUserRespawn(e);
verify(scheduler).runTask(any(), any(Runnable.class));
}
@ -211,7 +212,7 @@ public class RemoveMobsListenerTest {
@Test
public void testOnUserRespawnDoNotRemove() {
Flags.REMOVE_MOBS.setSetting(world, false);
PlayerRespawnEvent e = new PlayerRespawnEvent(player, inside, false, false);
PlayerRespawnEvent e = new PlayerRespawnEvent(player, inside, false, false, RespawnReason.DEATH);
new RemoveMobsListener().onUserRespawn(e);
verify(scheduler, never()).runTask(any(), any(Runnable.class));
}
@ -223,7 +224,7 @@ public class RemoveMobsListenerTest {
public void testOnUserRespawnNotIsland() {
// Not on island
when(im.locationIsOnIsland(any(), any())).thenReturn(false);
PlayerRespawnEvent e = new PlayerRespawnEvent(player, inside, false, false);
PlayerRespawnEvent e = new PlayerRespawnEvent(player, inside, false, false, RespawnReason.DEATH);
new RemoveMobsListener().onUserRespawn(e);
verify(scheduler, never()).runTask(any(), any(Runnable.class));
}

View File

@ -12,7 +12,6 @@ import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.StandardOpenOption;

View File

@ -40,7 +40,6 @@ import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.invocation.InvocationOnMock;
import org.mockito.stubbing.Answer;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;

View File

@ -67,9 +67,6 @@ public class IslandDeletionManagerTest {
private BukkitScheduler scheduler;
@Mock
private IslandWorldManager iwm;
@Mock
private IslandChunkDeletionManager chunkDeletionManager;
/**
*/
@ -102,8 +99,6 @@ public class IslandDeletionManagerTest {
// IWM
when(plugin.getIWM()).thenReturn(iwm);
when(iwm.getIslandDistance(any())).thenReturn(64);
// Chunk deletion manager
when(plugin.getIslandChunkDeletionManager()).thenReturn(chunkDeletionManager);
// Island Deletion Manager
idm = new IslandDeletionManager(plugin);

View File

@ -114,7 +114,7 @@ public class IslandWorldManagerTest {
*/
@Test
public void testRegisterWorldsToMultiverse() {
iwm.registerWorldsToMultiverse();
iwm.registerWorldsToMultiverse(true);
}
/**
@ -614,6 +614,7 @@ public class IslandWorldManagerTest {
/**
* Test method for {@link world.bentobox.bentobox.managers.IslandWorldManager#getDefaultIslandFlags(org.bukkit.World)}.
*/
@SuppressWarnings("removal")
@Test
public void testGetDefaultIslandFlags() {
Map<Flag, Integer> flags = new HashMap<>();
@ -634,6 +635,7 @@ public class IslandWorldManagerTest {
/**
* Test method for {@link world.bentobox.bentobox.managers.IslandWorldManager#getDefaultIslandSettings(org.bukkit.World)}.
*/
@SuppressWarnings("removal")
@Test
public void testGetDefaultIslandSettings() {
Map<Flag, Integer> flags = new HashMap<>();

View File

@ -78,13 +78,14 @@ import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.database.Database;
import world.bentobox.bentobox.database.DatabaseSetup.DatabaseType;
import world.bentobox.bentobox.database.objects.Island;
import world.bentobox.bentobox.listeners.flags.AbstractCommonSetup;
import world.bentobox.bentobox.lists.Flags;
import world.bentobox.bentobox.managers.island.IslandCache;
import world.bentobox.bentobox.util.Util;
@RunWith(PowerMockRunner.class)
@PrepareForTest( { Bukkit.class, BentoBox.class, Util.class, Location.class })
public class IslandsManagerTest {
public class IslandsManagerTest extends AbstractCommonSetup {
@Mock
private BentoBox plugin;
@ -108,6 +109,8 @@ public class IslandsManagerTest {
@Mock
private IslandWorldManager iwm;
@Mock
private IslandDeletionManager deletionManager;
@Mock
private IslandChunkDeletionManager chunkDeletionManager;
@Mock
private IslandCache islandCache;
@ -141,11 +144,12 @@ public class IslandsManagerTest {
// Class under test
IslandsManager im;
/**
*/
@Override
@SuppressWarnings("unchecked")
@Before
public void setUp() throws Exception {
super.setUp();
// Clear any lingering database
tearDown();
// Set up plugin
@ -159,9 +163,6 @@ public class IslandsManagerTest {
when(iwm.inWorld(any(Location.class))).thenReturn(true);
when(plugin.getIWM()).thenReturn(iwm);
// Chunk deletion manager
when(plugin.getIslandChunkDeletionManager()).thenReturn(chunkDeletionManager);
// Settings
Settings s = mock(Settings.class);
when(plugin.getSettings()).thenReturn(s);
@ -309,20 +310,16 @@ public class IslandsManagerTest {
.getNearbyEntities(any(Location.class), Mockito.anyDouble(), Mockito.anyDouble(), Mockito.anyDouble()))
.thenReturn(collection);
// Deletion Manager
when(deletionManager.getIslandChunkDeletionManager()).thenReturn(chunkDeletionManager);
when(plugin.getIslandDeletionManager()).thenReturn(deletionManager);
// database must be mocked here
db = mock(Database.class);
// Signs
sign = Material.getMaterial("SIGN");
if (sign == null) {
sign = Material.getMaterial("OAK_SIGN");
}
wallSign = Material.getMaterial("WALL_SIGN");
if (wallSign == null) {
wallSign = Material.getMaterial("OAK_WALL_SIGN");
}
sign = Material.BIRCH_SIGN;
wallSign = Material.ACACIA_WALL_SIGN;
// PaperLib
env = new CraftBukkitEnvironment();
@ -337,10 +334,10 @@ public class IslandsManagerTest {
//im.setIslandCache(islandCache);
}
/**
*/
@Override
@After
public void tearDown() throws Exception {
super.tearDown();
Mockito.framework().clearInlineMocks();
deleteAll(new File("database"));
deleteAll(new File("database_backup"));
@ -393,12 +390,13 @@ public class IslandsManagerTest {
assertFalse(im.isSafeLocation(location));
}
@SuppressWarnings("deprecation")
@Test
public void testCheckIfSafeTrapdoor() {
for (Material d : Material.values()) {
if (d.name().contains("DOOR")) {
for (Material s : Material.values()) {
if (s.name().contains("_SIGN")) {
if (s.name().contains("_SIGN") && !s.isLegacy()) {
assertFalse("Fail " + d.name() + " " + s.name(), im.checkIfSafe(world, d, s, Material.AIR));
}
}
@ -486,13 +484,13 @@ public class IslandsManagerTest {
@Test
public void testBadBlocks() {
// Fences
Arrays.stream(Material.values()).filter(m -> m.toString().contains("FENCE")).forEach(m -> {
when(ground.getType()).thenReturn(m);
assertFalse("Fence :" + m.toString(), im.isSafeLocation(location));
});
when(ground.getType()).thenReturn(Material.SPRUCE_FENCE);
assertFalse("Fence :" + Material.SPRUCE_FENCE.toString(), im.isSafeLocation(location));
// Signs
sign = Material.BIRCH_SIGN;
when(ground.getType()).thenReturn(sign);
assertFalse("Sign", im.isSafeLocation(location));
wallSign = Material.ACACIA_WALL_SIGN;
when(ground.getType()).thenReturn(wallSign);
assertFalse("Sign", im.isSafeLocation(location));
// Bad Blocks