Merge branch 'develop' of https://github.com/BentoBoxWorld/BentoBox.git into develop

This commit is contained in:
tastybento 2019-09-30 15:38:15 -07:00
commit 7bf0de9eda
29 changed files with 936 additions and 103 deletions

View File

@ -3,6 +3,7 @@ package world.bentobox.bentobox.api.addons;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.HashMap;
import java.util.Map;
import java.util.Optional;
@ -12,6 +13,7 @@ import java.util.logging.Logger;
import org.bukkit.Bukkit;
import org.bukkit.Server;
import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.event.Listener;
@ -244,8 +246,9 @@ public abstract class Addon {
* - if true, will overwrite previous file
* @param noPath
* - if true, the resource's path will be ignored when saving
* @return file written, or null if none
*/
public void saveResource(String jarResource, File destinationFolder, boolean replace, boolean noPath) {
public File saveResource(String jarResource, File destinationFolder, boolean replace, boolean noPath) {
if (jarResource == null || jarResource.equals("")) {
throw new IllegalArgumentException("ResourcePath cannot be null or empty");
}
@ -269,6 +272,7 @@ public abstract class Addon {
if (!outFile.exists() || replace) {
java.nio.file.Files.copy(in, outFile.toPath());
}
return outFile;
}
} else {
// No file in the jar
@ -279,6 +283,31 @@ public abstract class Addon {
BentoBox.getInstance().logError(
"Could not save from jar file. From " + jarResource + " to " + destinationFolder.getAbsolutePath());
}
return null;
}
/**
* Tries to load a YAML file from the Jar
* @param jarResource - YAML file in jar
* @return YamlConfiguration - may be empty
* @throws IOException - if the file cannot be found or loaded from the Jar
* @throws InvalidConfigurationException - if the yaml is malformed
*/
public YamlConfiguration getYamlFromJar(String jarResource) throws IOException, InvalidConfigurationException {
if (jarResource == null || jarResource.equals("")) {
throw new IllegalArgumentException("jarResource cannot be null or empty");
}
YamlConfiguration result = new YamlConfiguration();
jarResource = jarResource.replace('\\', '/');
try (JarFile jar = new JarFile(file)) {
JarEntry jarConfig = jar.getJarEntry(jarResource);
if (jarConfig != null) {
try (InputStreamReader in = new InputStreamReader(jar.getInputStream(jarConfig))) {
result.load(in);
}
}
}
return result;
}
/**

View File

@ -5,6 +5,7 @@ import java.util.List;
import java.util.Optional;
import java.util.UUID;
import org.bukkit.Bukkit;
import org.bukkit.util.Vector;
import world.bentobox.bentobox.api.commands.CompositeCommand;
@ -76,6 +77,17 @@ public class AdminDeleteCommand extends ConfirmableCommand {
// Remove them from this island (it still exists and will be deleted later)
getIslands().removePlayer(getWorld(), targetUUID);
if (target.isOnline()) {
// Execute commands when leaving
getIWM().getOnLeaveCommands(getWorld()).forEach(command -> {
command = command.replace("[player]", target.getName());
if (command.startsWith("[SUDO]")) {
// Execute the command by the player
target.performCommand(command.substring(6));
} else {
// Otherwise execute as the server console
getPlugin().getServer().dispatchCommand(Bukkit.getConsoleSender(), command);
}
});
// Remove money inventory etc.
if (getIWM().isOnLeaveResetEnderChest(getWorld())) {
target.getPlayer().getEnderChest().clear();

View File

@ -1,10 +1,17 @@
package world.bentobox.bentobox.api.commands.admin;
import java.util.List;
import java.util.Locale;
import java.util.Optional;
import java.util.stream.Collectors;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.commands.ConfirmableCommand;
import world.bentobox.bentobox.api.flags.Flag;
import world.bentobox.bentobox.api.flags.Flag.Type;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.util.Util;
/**
* Admin command to reset all islands in a world to the default flag setting in the game mode config.yml
@ -13,25 +20,47 @@ import world.bentobox.bentobox.api.user.User;
*/
public class AdminResetFlagsCommand extends ConfirmableCommand {
private List<String> options;
public AdminResetFlagsCommand(CompositeCommand parent) {
super(parent, "resetflags");
options = getPlugin().getFlagsManager().getFlags().stream()
.filter(f -> f.getType().equals(Type.PROTECTION) || f.getType().equals(Type.SETTING))
.map(Flag::getID).collect(Collectors.toList());
}
@Override
public void setup() {
setPermission("admin.resetflags");
setOnlyPlayer(false);
setParametersHelp("commands.admin.resetflags.parameters");
setDescription("commands.admin.resetflags.description");
}
@Override
public boolean execute(User user, String label, List<String> args) {
// Everything's fine, we can set the island as spawn :)
askConfirmation(user, () -> {
getIslands().resetAllFlags(getWorld());
user.sendMessage("commands.admin.resetflags.success");
});
return true;
if (args.isEmpty()) {
askConfirmation(user, user.getTranslation("commands.admin.resetflags.confirm"), () -> {
getIslands().resetAllFlags(getWorld());
user.sendMessage("commands.admin.resetflags.success");
});
return true;
} else if (args.size() == 1 && options.contains(args.get(0).toUpperCase(Locale.ENGLISH))) {
getPlugin().getFlagsManager().getFlag(args.get(0).toUpperCase(Locale.ENGLISH)).ifPresent(flag ->
askConfirmation(user, user.getTranslation("commands.admin.resetflags.confirm"), () -> {
getIslands().resetFlag(getWorld(), flag);
user.sendMessage("commands.admin.resetflags.success-one", TextVariables.NAME, flag.getID());
}));
return true;
}
// Show help
showHelp(this, user);
return false;
}
@Override
public Optional<List<String>> tabComplete(User user, String alias, List<String> args) {
String lastArg = !args.isEmpty() ? args.get(args.size()-1) : "";
return Optional.of(Util.tabLimit(options, lastArg));
}
}

View File

@ -0,0 +1,50 @@
package world.bentobox.bentobox.api.commands.admin.deaths;
import org.apache.commons.lang.math.NumberUtils;
import org.eclipse.jdt.annotation.NonNull;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import java.util.List;
import java.util.UUID;
/**
* @since 1.8.0
* @author Poslovitch
*/
public class AdminDeathsAddCommand extends CompositeCommand {
public AdminDeathsAddCommand(AdminDeathsCommand parent) {
super(parent, "add");
}
@Override
public void setup() {
setDescription("commands.admin.deaths.add.description");
setParametersHelp("commands.admin.deaths.add.parameters");
}
@Override
public boolean execute(User user, String label, @NonNull List<String> args) {
if (args.size() != 2) {
showHelp(this, user);
return false;
}
UUID target = getPlayers().getUUID(args.get(0));
if (target == null) {
user.sendMessage("general.errors.unknown-player", TextVariables.NAME, args.get(0));
} else if (!NumberUtils.isNumber(args.get(1)) || Integer.valueOf(args.get(1)) < 0) {
user.sendMessage("general.errors.must-be-positive-number", TextVariables.NUMBER, args.get(1));
} else {
getPlayers().setDeaths(getWorld(), target, getPlayers().getDeaths(getWorld(), target) + Integer.valueOf(args.get(1)));
user.sendMessage("commands.admin.deaths.add.success",
TextVariables.NAME, args.get(0), TextVariables.NUMBER, args.get(1),
"[total]", String.valueOf(getPlayers().getDeaths(getWorld(), target)));
return true;
}
return false;
}
}

View File

@ -21,6 +21,8 @@ public class AdminDeathsCommand extends CompositeCommand {
new AdminDeathsResetCommand(this);
new AdminDeathsSetCommand(this);
new AdminDeathsAddCommand(this);
new AdminDeathsRemoveCommand(this);
}
@Override

View File

@ -0,0 +1,52 @@
package world.bentobox.bentobox.api.commands.admin.deaths;
import org.apache.commons.lang.math.NumberUtils;
import org.eclipse.jdt.annotation.NonNull;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import java.util.List;
import java.util.UUID;
/**
* @since 1.8.0
* @author Poslovitch
*/
public class AdminDeathsRemoveCommand extends CompositeCommand {
public AdminDeathsRemoveCommand(AdminDeathsCommand parent) {
super(parent, "remove");
}
@Override
public void setup() {
setDescription("commands.admin.deaths.remove.description");
setParametersHelp("commands.admin.deaths.remove.parameters");
}
@Override
public boolean execute(User user, String label, @NonNull List<String> args) {
if (args.size() != 2) {
showHelp(this, user);
return false;
}
UUID target = getPlayers().getUUID(args.get(0));
if (target == null) {
user.sendMessage("general.errors.unknown-player", TextVariables.NAME, args.get(0));
} else if (!NumberUtils.isNumber(args.get(1)) || Integer.valueOf(args.get(1)) < 0) {
user.sendMessage("general.errors.must-be-positive-number", TextVariables.NUMBER, args.get(1));
} else {
// Make sure it cannot go under 0.
int newDeaths = Math.max(getPlayers().getDeaths(getWorld(), target) - Integer.valueOf(args.get(1)), 0);
getPlayers().setDeaths(getWorld(), target, newDeaths);
user.sendMessage("commands.admin.deaths.remove.success",
TextVariables.NAME, args.get(0), TextVariables.NUMBER, args.get(1),
"[total]", String.valueOf(newDeaths));
return true;
}
return false;
}
}

View File

@ -0,0 +1,50 @@
package world.bentobox.bentobox.api.commands.admin.resets;
import org.apache.commons.lang.math.NumberUtils;
import org.eclipse.jdt.annotation.NonNull;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import java.util.List;
import java.util.UUID;
/**
* @author Poslovitch
* @since 1.8.0
*/
public class AdminResetsAddCommand extends CompositeCommand {
public AdminResetsAddCommand(AdminResetsCommand parent) {
super(parent, "add");
}
@Override
public void setup() {
setDescription("commands.admin.resets.add.description");
setParametersHelp("commands.admin.resets.add.parameters");
}
@Override
public boolean execute(User user, String label, @NonNull List<String> args) {
if (args.size() != 2) {
showHelp(this, user);
return false;
}
UUID target = getPlayers().getUUID(args.get(0));
if (target == null) {
user.sendMessage("general.errors.unknown-player", TextVariables.NAME, args.get(0));
} else if (!NumberUtils.isNumber(args.get(1)) || Integer.valueOf(args.get(1)) < 0) {
user.sendMessage("general.errors.must-be-positive-number", TextVariables.NUMBER, args.get(1));
} else {
getPlayers().setResets(getWorld(), target, getPlayers().getResets(getWorld(), target) + Integer.valueOf(args.get(1)));
user.sendMessage("commands.admin.resets.add.success",
TextVariables.NAME, args.get(0), TextVariables.NUMBER, args.get(1),
"[total]", String.valueOf(getPlayers().getResets(getWorld(), target)));
return true;
}
return false;
}
}

View File

@ -18,6 +18,8 @@ public class AdminResetsCommand extends CompositeCommand {
new AdminResetsSetCommand(this);
new AdminResetsResetCommand(this);
new AdminResetsAddCommand(this);
new AdminResetsRemoveCommand(this);
}
@Override

View File

@ -0,0 +1,52 @@
package world.bentobox.bentobox.api.commands.admin.resets;
import org.apache.commons.lang.math.NumberUtils;
import org.eclipse.jdt.annotation.NonNull;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.user.User;
import java.util.List;
import java.util.UUID;
/**
* @author Poslovitch
* @since 1.8.0
*/
public class AdminResetsRemoveCommand extends CompositeCommand {
public AdminResetsRemoveCommand(AdminResetsCommand parent) {
super(parent, "remove");
}
@Override
public void setup() {
setDescription("commands.admin.resets.remove.description");
setParametersHelp("commands.admin.resets.remove.parameters");
}
@Override
public boolean execute(User user, String label, @NonNull List<String> args) {
if (args.size() != 2) {
showHelp(this, user);
return false;
}
UUID target = getPlayers().getUUID(args.get(0));
if (target == null) {
user.sendMessage("general.errors.unknown-player", TextVariables.NAME, args.get(0));
} else if (!NumberUtils.isNumber(args.get(1)) || Integer.valueOf(args.get(1)) < 0) {
user.sendMessage("general.errors.must-be-positive-number", TextVariables.NUMBER, args.get(1));
} else {
// Make sure it cannot go under 0.
int newResets = Math.max(getPlayers().getResets(getWorld(), target) - Integer.valueOf(args.get(1)), 0);
getPlayers().setResets(getWorld(), target, newResets);
user.sendMessage("commands.admin.resets.remove.success",
TextVariables.NAME, args.get(0), TextVariables.NUMBER, args.get(1),
"[total]", String.valueOf(newResets));
return true;
}
return false;
}
}

View File

@ -39,7 +39,7 @@ public class AdminResetsResetCommand extends ConfirmableCommand {
getIWM().setResetEpoch(getWorld());
// Reset all current players
Bukkit.getOnlinePlayers().stream().map(Player::getUniqueId).filter(getPlayers()::isKnown).forEach(u -> getPlayers().setResets(getWorld(), u, 0));
user.sendMessage("general.success");
user.sendMessage("commands.admin.resets.reset.success-everyone");
});
return true;
} else {
@ -50,7 +50,7 @@ public class AdminResetsResetCommand extends ConfirmableCommand {
return false;
} else {
getPlayers().setResets(getWorld(), target, 0);
user.sendMessage("general.success");
user.sendMessage("commands.admin.resets.reset.success", TextVariables.NAME, args.get(0));
return true;
}
}

View File

@ -23,7 +23,7 @@ public class AdminResetsSetCommand extends CompositeCommand {
@Override
public boolean execute(User user, String label, List<String> args) {
if (args.isEmpty() || args.size() != 2) {
if (args.size() != 2) {
showHelp(this, user);
return false;
}
@ -31,11 +31,12 @@ public class AdminResetsSetCommand extends CompositeCommand {
UUID target = getPlayers().getUUID(args.get(0));
if (target == null) {
user.sendMessage("general.errors.unknown-player", TextVariables.NAME, args.get(0));
} else if (!NumberUtils.isNumber(args.get(1)) || Integer.valueOf(args.get(1)) < 0) {
} else if (!NumberUtils.isNumber(args.get(1)) || Integer.valueOf(args.get(1)) <= 0) {
user.sendMessage("general.errors.must-be-positive-number", TextVariables.NUMBER, args.get(1));
} else {
getPlayers().setResets(getWorld(), target, Integer.valueOf(args.get(1)));
user.sendMessage("general.success");
user.sendMessage("commands.admin.resets.set.success",
TextVariables.NAME, args.get(0), TextVariables.NUMBER, args.get(1));
return true;
}

View File

@ -165,6 +165,18 @@ public class IslandResetCommand extends ConfirmableCommand {
// Remove player
getIslands().removePlayer(getWorld(), memberUUID);
// Execute commands when leaving
getIWM().getOnLeaveCommands(island.getWorld()).forEach(command -> {
command = command.replace("[player]", member.getName());
if (command.startsWith("[SUDO]") && member.isOnline()) {
// Execute the command by the player
member.performCommand(command.substring(6));
} else {
// Otherwise execute as the server console
getPlugin().getServer().dispatchCommand(Bukkit.getConsoleSender(), command);
}
});
// Remove money inventory etc.
if (getIWM().isOnLeaveResetEnderChest(getWorld())) {
if (member.isOnline()) {

View File

@ -78,6 +78,17 @@ public class IslandTeamKickCommand extends ConfirmableCommand {
target.sendMessage("commands.island.team.kick.owner-kicked", "[gamemode]", getAddon().getDescription().getName());
Island oldIsland = getIslands().getIsland(getWorld(), targetUUID);
getIslands().removePlayer(getWorld(), targetUUID);
// Execute commands when leaving
getIWM().getOnLeaveCommands(oldIsland.getWorld()).forEach(command -> {
command = command.replace("[player]", target.getName());
if (command.startsWith("[SUDO]") && target.isOnline()) {
// Execute the command by the player
target.performCommand(command.substring(6));
} else {
// Otherwise execute as the server console
getPlugin().getServer().dispatchCommand(Bukkit.getConsoleSender(), command);
}
});
// Remove money inventory etc.
if (getIWM().isOnLeaveResetEnderChest(getWorld())) {
if (target.isOnline()) {

View File

@ -72,6 +72,17 @@ public class IslandTeamLeaveCommand extends ConfirmableCommand {
User.getInstance(ownerUUID).sendMessage("commands.island.team.leave.left-your-island", TextVariables.NAME, user.getName());
}
getIslands().setLeaveTeam(getWorld(), user.getUniqueId());
// Execute commands when leaving
getIWM().getOnLeaveCommands(island.getWorld()).forEach(command -> {
command = command.replace("[player]", user.getName());
if (command.startsWith("[SUDO]") && user.isOnline()) {
// Execute the command by the player
user.performCommand(command.substring(6));
} else {
// Otherwise execute as the server console
getPlugin().getServer().dispatchCommand(Bukkit.getConsoleSender(), command);
}
});
// Remove money inventory etc.
if (getIWM().isOnLeaveResetEnderChest(getWorld())) {
user.getPlayer().getEnderChest().clear();

View File

@ -8,6 +8,7 @@ import org.bukkit.Difficulty;
import org.bukkit.GameMode;
import org.bukkit.entity.EntityType;
import org.eclipse.jdt.annotation.NonNull;
import world.bentobox.bentobox.api.flags.Flag;
/**
@ -186,6 +187,27 @@ public interface WorldSettings extends ConfigObject {
*/
boolean isOnJoinResetMoney();
/**
* Returns a list of commands that should be executed when the player joins an island or creates one.<br/>
* These commands are executed by the console, unless otherwise stated using the {@code [SUDO]} prefix, in which case they are executed by the player.<br/>
* <br/>
* Available placeholders for the commands are the following:
* <ul>
* <li>{@code [player]}: name of the player</li>
* </ul>
* <br/>
* Here are some examples of valid commands to execute:
* <ul>
* <li>{@code "[SUDO] bbox version"}</li>
* <li>{@code "bsbadmin deaths set [player] 0"}</li>
* </ul>
* @return a list of commands.
* @since 1.8.0
* @see #getOnLeaveCommands()
*/
@NonNull
List<String> getOnJoinCommands();
/**
* @return the onLeaveResetEnderChest
*/
@ -201,6 +223,29 @@ public interface WorldSettings extends ConfigObject {
*/
boolean isOnLeaveResetMoney();
/**
* Returns a list of commands that should be executed when the player leaves an island or resets one.<br/>
* These commands are executed by the console, unless otherwise stated using the {@code [SUDO]} prefix, in which case they are executed by the player.<br/>
* <br/>
* Available placeholders for the commands are the following:
* <ul>
* <li>{@code [player]}: name of the player</li>
* </ul>
* <br/>
* Here are some examples of valid commands to execute:
* <ul>
* <li>{@code "[SUDO] bbox version"}</li>
* <li>{@code "bsbadmin deaths set [player] 0"}</li>
* </ul>
* <br/>
* Note that player-executed commands might not work, as these commands can be run with said player being offline.
* @return a list of commands.
* @since 1.8.0
* @see #getOnJoinCommands()
*/
@NonNull
List<String> getOnLeaveCommands();
/**
* @return true if the default world generator should not operate in this world
*/

View File

@ -14,6 +14,7 @@ import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Banner;
import org.bukkit.block.Block;
import org.bukkit.block.BlockState;
import org.bukkit.block.CreatureSpawner;
@ -288,6 +289,12 @@ public class BlueprintClipboard {
cs.setSpawnRange(spawner.getSpawnRange());
b.setCreatureSpawner(cs);
}
// Banners
if (blockState instanceof Banner) {
b.setBannerPatterns(((Banner) blockState).getPatterns());
}
this.bpBlocks.put(pos, b);
return true;
}

View File

@ -11,6 +11,7 @@ import org.bukkit.ChatColor;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Banner;
import org.bukkit.block.Block;
import org.bukkit.block.BlockFace;
import org.bukkit.block.BlockState;
@ -246,6 +247,12 @@ public class BlueprintPaster {
spawner.setSpawnRange(s.getSpawnRange());
bs.update(true, false);
}
// Banners
if (bs instanceof Banner) {
Banner banner = (Banner) bs;
banner.setPatterns(bpBlock.getBannerPatterns());
banner.update(true, false);
}
}
/**

View File

@ -4,6 +4,7 @@ import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.bukkit.block.banner.Pattern;
import org.bukkit.inventory.ItemStack;
import com.google.gson.annotations.Expose;
@ -22,6 +23,11 @@ public class BlueprintBlock {
private Map<Integer, ItemStack> inventory;
@Expose
private BlueprintCreatureSpawner creatureSpawner;
/**
* @since 1.8.0
*/
@Expose
private List<Pattern> bannerPatterns;
public BlueprintBlock(String blockData) {
this.blockData = blockData;
@ -82,4 +88,20 @@ public class BlueprintBlock {
public void setCreatureSpawner(BlueprintCreatureSpawner creatureSpawner) {
this.creatureSpawner = creatureSpawner;
}
/**
* @return list of the banner patterns
* @since 1.8.0
*/
public List<Pattern> getBannerPatterns() {
return bannerPatterns;
}
/**
* @param bannerPatterns the banner Patterns to set
* @since 1.8.0
*/
public void setBannerPatterns(List<Pattern> bannerPatterns) {
this.bannerPatterns = bannerPatterns;
}
}

View File

@ -41,6 +41,9 @@ public class BlueprintEntity {
@Expose
private Style style;
/**
* @since 1.8.0
*/
public void configureEntity(Entity e) {
if (e instanceof Colorable) {
((Colorable) e).setColor(color);

View File

@ -562,6 +562,18 @@ public class IslandWorldManager {
return gameModes.get(world).getWorldSettings().isOnJoinResetEnderChest();
}
/**
* Returns a list of commands to execute when the player creates or joins an island.
* @param world the World
* @return a list of commands
* @since 1.8.0
* @see #getOnLeaveCommands(World)
*/
@NonNull
public List<String> getOnJoinCommands(@NonNull World world) {
return gameModes.get(world).getWorldSettings().getOnJoinCommands();
}
/**
* @return the onLeaveResetMoney
*/
@ -583,6 +595,18 @@ public class IslandWorldManager {
return gameModes.get(world).getWorldSettings().isOnLeaveResetEnderChest();
}
/**
* Returns a list of commands to execute when the player resets or leaves an island.
* @param world the World
* @return a list of commands
* @since 1.8.0
* @see #getOnJoinCommands(World)
*/
@NonNull
public List<String> getOnLeaveCommands(@NonNull World world) {
return gameModes.get(world).getWorldSettings().getOnLeaveCommands();
}
/**
* Get data folder for the addon that registered this world
*

View File

@ -38,6 +38,7 @@ import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.events.IslandBaseEvent;
import world.bentobox.bentobox.api.events.island.IslandEvent;
import world.bentobox.bentobox.api.events.island.IslandEvent.Reason;
import world.bentobox.bentobox.api.flags.Flag;
import world.bentobox.bentobox.api.localization.TextVariables;
import world.bentobox.bentobox.api.logs.LogEntry;
import world.bentobox.bentobox.api.user.User;
@ -670,7 +671,17 @@ public class IslandsManager {
}
// If this is a new island, then run commands and do resets
if (newIsland) {
// TODO add command running
// Execute commands
plugin.getIWM().getOnJoinCommands(world).forEach(command -> {
command = command.replace("[player]", player.getName());
if (command.startsWith("[SUDO]")) {
// Execute the command by the player
player.performCommand(command.substring(6));
} else {
// Otherwise execute as the server console
plugin.getServer().dispatchCommand(Bukkit.getConsoleSender(), command);
}
});
// Remove money inventory etc.
if (plugin.getIWM().isOnJoinResetEnderChest(world)) {
@ -1201,6 +1212,17 @@ public class IslandsManager {
this.saveAll();
}
/**
* Resets a flag to gamemode config.yml default
* @param world - world
* @param flag - flag to reset
* @since 1.8.0
*/
public void resetFlag(World world, Flag flag) {
islandCache.resetFlag(world, flag);
this.saveAll();
}
/**
* Returns whether the specified island custom name exists in this world.
* @param world World of the gamemode
@ -1212,4 +1234,5 @@ public class IslandsManager {
return getIslands(world).stream().filter(island -> island.getName() != null).map(Island::getName)
.anyMatch(n -> ChatColor.stripColor(n).equals(ChatColor.stripColor(name)));
}
}

View File

@ -4,6 +4,7 @@ import java.io.File;
import java.io.FilenameFilter;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedList;
@ -15,6 +16,7 @@ import java.util.jar.JarFile;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.configuration.InvalidConfigurationException;
import org.bukkit.configuration.file.YamlConfiguration;
import world.bentobox.bentobox.BentoBox;
@ -108,7 +110,7 @@ public class LocalesManager {
}
/**
* Copies locale files from the addon jar to the file system
* Copies locale files from the addon jar to the file system and updates current locales with the latest references
* @param addon - addon
*/
void copyLocalesFromAddonJar(Addon addon) {
@ -116,14 +118,39 @@ public class LocalesManager {
File localeDir = new File(plugin.getDataFolder(), LOCALE_FOLDER + File.separator + addon.getDescription().getName());
if (!localeDir.exists()) {
localeDir.mkdirs();
// Obtain any locale files and save them
Util.listJarFiles(jar, LOCALE_FOLDER, ".yml").forEach(lf -> addon.saveResource(lf, localeDir, false, true));
}
// Obtain any locale files, save them and update
Util.listJarFiles(jar, LOCALE_FOLDER, ".yml").forEach(lf -> {
File file = addon.saveResource(lf, localeDir, false, true);
// Update
if (file != null) {
updateLocale(addon, file, lf);
}
});
} catch (Exception e) {
plugin.logError(e.getMessage());
}
}
private void updateLocale(Addon addon, File fileLocaleFile, String lf) {
try {
// Load the JAR locale file
YamlConfiguration jarLocale = addon.getYamlFromJar(lf);
// Load the locale file system locale file
YamlConfiguration fileLocale = new YamlConfiguration();
fileLocale.load(fileLocaleFile);
// Copy new keys to file
jarLocale.getKeys(true).stream().filter(k -> !fileLocale.contains(k, false)).forEach(k -> fileLocale.set(k, jarLocale.get(k)));
// Save file
fileLocale.save(fileLocaleFile);
} catch (Exception e) {
plugin.logError("Error updating locale file: " + lf + " : " + e.getMessage());
plugin.logStacktrace(e);
}
}
/**
* Copies all the locale files from the plugin jar to the filesystem.
* Only done if the locale folder does not already exist.
@ -135,18 +162,36 @@ public class LocalesManager {
// If it does exist, then new files will NOT be written!
if (!localeDir.exists()) {
localeDir.mkdirs();
FileLister lister = new FileLister(plugin);
try {
for (String name : lister.listJar(LOCALE_FOLDER)) {
// We cannot use Bukkit's saveResource, because we want it to go into a specific folder, so...
// Get the last part of the name
int lastIndex = name.lastIndexOf('/');
File targetFile = new File(localeDir, name.substring(lastIndex >= 0 ? lastIndex : 0));
copyFile(name, targetFile);
}
FileLister lister = new FileLister(plugin);
try {
for (String name : lister.listJar(LOCALE_FOLDER)) {
// We cannot use Bukkit's saveResource, because we want it to go into a specific folder, so...
// Get the last part of the name
int lastIndex = name.lastIndexOf('/');
File targetFile = new File(localeDir, name.substring(lastIndex >= 0 ? lastIndex : 0));
copyFile(name, targetFile);
// Update the locale file if it exists already
try (InputStreamReader in = new InputStreamReader(plugin.getResource(name))) {
YamlConfiguration jarLocale = new YamlConfiguration();
jarLocale.load(in);
YamlConfiguration fileLocale = new YamlConfiguration();
fileLocale.load(targetFile);
for (String k : jarLocale.getKeys(true)) {
if (!fileLocale.contains(k, false)) {
fileLocale.set(k, jarLocale.get(k));
}
}
// Save it
fileLocale.save(targetFile);
} catch (InvalidConfigurationException e) {
plugin.logError("Could not update locale files from jar " + e.getMessage());
}
} catch (IOException e) {
plugin.logError("Could not copy locale files from jar " + e.getMessage());
}
} catch (IOException e) {
plugin.logError("Could not copy locale files from jar " + e.getMessage());
}
}
@ -180,9 +225,9 @@ public class LocalesManager {
languages.put(localeObject, new BentoBoxLocale(localeObject, languageYaml));
}
} catch (Exception e) {
BentoBox.getInstance().logError("Could not load '" + language.getName() + "' : " + e.getMessage()
plugin.logError("Could not load '" + language.getName() + "' : " + e.getMessage()
+ " with the following cause '" + e.getCause() + "'." +
" The file has likely an invalid YML format or has been made unreadable during the process.");
" The file has likely an invalid YML format or has been made unreadable during the process.");
}
}
}
@ -256,7 +301,11 @@ public class LocalesManager {
plugin.log(ChatColor.AQUA + "Analyzing BentoBox locale files");
user.sendRawMessage(ChatColor.AQUA + SPACER);
loadLocalesFromFile(BENTOBOX);
analyze(fix);
if (languages.containsKey(Locale.US)) {
analyze(user, fix);
} else {
user.sendRawMessage(ChatColor.RED + "No US English in BentoBox to use for analysis!");
}
user.sendRawMessage(ChatColor.AQUA + "Analyzing Addon locale files");
plugin.getAddonsManager().getAddons().forEach(addon -> {
user.sendRawMessage(ChatColor.AQUA + SPACER);
@ -264,22 +313,23 @@ public class LocalesManager {
user.sendRawMessage(ChatColor.AQUA + SPACER);
languages.clear();
loadLocalesFromFile(addon.getDescription().getName());
analyze(fix);
if (languages.containsKey(Locale.US)) {
analyze(user, fix);
} else {
user.sendRawMessage(ChatColor.RED + "No US English to use for analysis!");
}
});
reloadLanguages();
}
/**
*
* @param user
* @param fix whether or not locale files with missing translations should be fixed.
* Not currently supported.
* @since 1.5.0
*/
private void analyze(boolean fix) {
if (!languages.containsKey(Locale.US)) {
return;
}
User user = User.getInstance(Bukkit.getConsoleSender());
private void analyze(User user, boolean fix) {
user.sendRawMessage(ChatColor.GREEN + "The following locales are supported:");
languages.forEach((k,v) -> user.sendRawMessage(ChatColor.GOLD + k.toLanguageTag() + " " + k.getDisplayLanguage() + " " + k.getDisplayCountry()));

View File

@ -59,36 +59,27 @@ public class WebManager {
if (plugin.getSettings().isLogGithubDownloadData()) {
plugin.log("Downloading data from GitHub...");
}
GitHubRepository repo = new GitHubRepository(gh, "BentoBoxWorld/weblink");
GitHubRepository repo;
try {
repo = new GitHubRepository(gh, "BentoBoxWorld/weblink");
} catch (Exception e) {
plugin.logError("An unhandled exception occurred when trying to connect to GitHub...");
plugin.logStacktrace(e);
String tagsContent = "";
String topicsContent = "";
String catalogContent = "";
// Stop the execution of the method right away.
return;
}
// Downloading the data
try {
tagsContent = repo.getContent("catalog/tags.json").getContent().replaceAll("\\n", "");
topicsContent = repo.getContent("catalog/topics.json").getContent().replaceAll("\\n", "");
catalogContent = repo.getContent("catalog/catalog.json").getContent().replaceAll("\\n", "");
} catch (IllegalAccessException e) {
if (plugin.getSettings().isLogGithubDownloadData()) {
plugin.log("Could not connect to GitHub.");
}
} catch (Exception e) {
plugin.logError("An unhandled exception occurred when downloading data from GitHub...");
plugin.logStacktrace(e);
}
String tagsContent = getContent(repo, "catalog/tags.json");
String topicsContent = getContent(repo, "catalog/topics.json");
String catalogContent = getContent(repo, "catalog/catalog.json");
// People were concerned that the download took ages, so we need to tell them it's over now.
if (plugin.getSettings().isLogGithubDownloadData()) {
plugin.log("Successfully downloaded data from GitHub.");
}
// Decoding the Base64 encoded contents
tagsContent = new String(Base64.getDecoder().decode(tagsContent), StandardCharsets.UTF_8);
topicsContent = new String(Base64.getDecoder().decode(topicsContent), StandardCharsets.UTF_8);
catalogContent = new String(Base64.getDecoder().decode(catalogContent), StandardCharsets.UTF_8);
/* Parsing the data */
// Register the tags translations in the locales
@ -140,6 +131,29 @@ public class WebManager {
});
}
/**
*
* @param repo
* @param fileName
* @return
* @since 1.8.0
*/
@NonNull
private String getContent(@NonNull GitHubRepository repo, String fileName) {
try {
String content = repo.getContent(fileName).getContent().replaceAll("\\n", "");
return new String(Base64.getDecoder().decode(content), StandardCharsets.UTF_8);
} catch (IllegalAccessException e) {
if (plugin.getSettings().isLogGithubDownloadData()) {
plugin.log("Could not connect to GitHub.");
}
} catch (Exception e) {
plugin.logError("An unhandled exception occurred when downloading '" + fileName + "' from GitHub...");
plugin.logStacktrace(e);
}
return "";
}
/**
* Returns the contents of the addons catalog (may be an empty list).
* @return the contents of the addons catalog.

View File

@ -16,6 +16,8 @@ import org.bukkit.World;
import org.eclipse.jdt.annotation.NonNull;
import org.eclipse.jdt.annotation.Nullable;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.flags.Flag;
import world.bentobox.bentobox.database.objects.Island;
import world.bentobox.bentobox.util.Util;
@ -312,4 +314,16 @@ public class IslandCache {
World w = Util.getWorld(world);
islandsById.values().stream().filter(i -> i.getWorld().equals(w)).forEach(Island::setFlagsDefaults);
}
/**
* Resets a specific flag on all game mode islands in world to default setting
* @param world - world
* @param flag - flag to reset
* @since 1.8.0
*/
public void resetFlag(World world, Flag flag) {
World w = Util.getWorld(world);
int setting = BentoBox.getInstance().getIWM().getDefaultIslandFlags(w).getOrDefault(flag, flag.getDefaultRank());
islandsById.values().stream().filter(i -> i.getWorld().equals(w)).forEach(i -> i.setFlag(flag, setting));
}
}

View File

@ -54,9 +54,20 @@ commands:
set:
description: "sets the resets of this player"
parameters: "<player> <resets>"
success: "&aSuccessfully set &b[name]&a's resets to &b[number]&a."
reset:
description: "resets the resets of this player to 0"
parameters: "<player>"
success-everyone: "&aSuccessfully reset &beveryone&a's resets to &b0&a."
success: "&aSuccessfully reset &b[name]&a's resets to &b0&a."
add:
description: "adds resets to the player"
parameters: "<player> <resets>"
success: "&aSuccessfully added &b[number] &aresets to &b[name], increasing the total to &b[total]&a resets."
remove:
description: "removes resets to the player"
parameters: "<player> <resets>"
success: "&aSuccessfully removed &b[number] &aresets to &b[name], decreasing the total to &b[total]&a resets."
purge:
parameters: "[days]"
description: "purge islands abandoned for more than [days]"
@ -310,8 +321,11 @@ commands:
&aLeft click to increment
&aRight click to decrement
resetflags:
parameters: "[flag]"
description: "Reset all islands to default flag settings in config.yml"
confirm: "&4This will reset the flag(s) to default for all islands!"
success: "&aSuccessfully reset all islands' flags to the default settings."
success-one: "&a[name] flag set to default for all islands."
world:
description: "Manage world settings"
delete:
@ -334,6 +348,14 @@ commands:
description: "sets deaths of the player"
parameters: "<player> <deaths>"
success: "&aSuccessfully set &b[name]&a's deaths to &b[number]&a."
add:
description: "adds deaths to the player"
parameters: "<player> <deaths>"
success: "&aSuccessfully added &b[number] &adeaths to &b[name], increasing the total to &b[total]&a deaths."
remove:
description: "removes deaths to the player"
parameters: "<player> <deaths>"
success: "&aSuccessfully removed &b[number] &adeaths to &b[name], decreasing the total to &b[total]&a deaths."
bentobox:
description: "BentoBox admin command"
about:

View File

@ -0,0 +1,227 @@
package world.bentobox.bentobox.api.commands.admin;
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.eq;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Optional;
import java.util.UUID;
import org.bukkit.Bukkit;
import org.bukkit.entity.Player;
import org.bukkit.scheduler.BukkitScheduler;
import org.eclipse.jdt.annotation.NonNull;
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.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.Settings;
import world.bentobox.bentobox.api.commands.CompositeCommand;
import world.bentobox.bentobox.api.flags.Flag;
import world.bentobox.bentobox.api.flags.Flag.Type;
import world.bentobox.bentobox.api.user.User;
import world.bentobox.bentobox.managers.CommandsManager;
import world.bentobox.bentobox.managers.FlagsManager;
import world.bentobox.bentobox.managers.IslandsManager;
import world.bentobox.bentobox.managers.LocalesManager;
import world.bentobox.bentobox.managers.PlaceholdersManager;
import world.bentobox.bentobox.managers.PlayersManager;
/**
* @author tastybento
*
*/
@RunWith(PowerMockRunner.class)
@PrepareForTest({Bukkit.class, BentoBox.class, User.class })
public class AdminResetFlagsCommandTest {
@Mock
private CompositeCommand ac;
private UUID uuid = UUID.randomUUID();
@Mock
private IslandsManager im;
@Mock
private PlayersManager pm;
@Mock
private FlagsManager fm;
@Mock
private Flag flag;
@Mock
private Flag flag2;
@Mock
private Flag flag3;
@Mock
private Player player;
private AdminResetFlagsCommand arf;
private @Nullable User user;
/**
* @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);
// Parent command has no aliases
ac = mock(CompositeCommand.class);
when(ac.getSubCommandAliases()).thenReturn(new HashMap<>());
when(ac.getPermissionPrefix()).thenReturn("bskyblock.");
// Player
when(player.getUniqueId()).thenReturn(uuid);
user = User.getInstance(player);
// Flags manager
when(plugin.getFlagsManager()).thenReturn(fm);
when(flag.getType()).thenReturn(Type.PROTECTION);
when(flag2.getType()).thenReturn(Type.SETTING);
when(flag3.getType()).thenReturn(Type.WORLD_SETTING);
when(flag.getID()).thenReturn("FLAG1");
when(flag2.getID()).thenReturn("FLAG2");
when(flag3.getID()).thenReturn("FLAG3");
@NonNull
List<Flag> list = new ArrayList<>();
list.add(flag);
list.add(flag2);
list.add(flag3);
when(fm.getFlags()).thenReturn(list);
// Locales & Placeholders
LocalesManager lm = mock(LocalesManager.class);
when(lm.get(any(), any())).thenAnswer((Answer<String>) invocation -> invocation.getArgument(1, String.class));
PlaceholdersManager phm = mock(PlaceholdersManager.class);
when(plugin.getPlaceholdersManager()).thenReturn(phm);
when(phm.replacePlaceholders(any(), any())).thenAnswer((Answer<String>) invocation -> invocation.getArgument(1, String.class));
when(plugin.getLocalesManager()).thenReturn(lm);
// Confirmation
Settings settings = mock(Settings.class);
when(settings.getConfirmationTime()).thenReturn(10);
when(plugin.getSettings()).thenReturn(settings);
// Server & Scheduler
BukkitScheduler sch = mock(BukkitScheduler.class);
PowerMockito.mockStatic(Bukkit.class);
when(Bukkit.getScheduler()).thenReturn(sch);
// Class
arf = new AdminResetFlagsCommand(ac);
}
/**
* @throws java.lang.Exception
*/
@After
public void tearDown() throws Exception {
User.clearUsers();
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.admin.AdminResetFlagsCommand#AdminResetFlagsCommand(world.bentobox.bentobox.api.commands.CompositeCommand)}.
*/
@Test
public void testAdminResetFlagsCommand() {
assertEquals("resetflags", arf.getLabel());
verify(flag).getID();
verify(flag2).getID();
verify(flag3, never()).getID();
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.admin.AdminResetFlagsCommand#setup()}.
*/
@Test
public void testSetup() {
assertFalse(arf.isOnlyPlayer());
assertEquals("bskyblock.admin.resetflags", arf.getPermission());
assertEquals("commands.admin.resetflags.parameters", arf.getParameters());
assertEquals("commands.admin.resetflags.description", arf.getDescription());
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.admin.AdminResetFlagsCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringTwoArgs() {
List<String> args = Arrays.asList("sdfsd", "werwerw");
assertFalse(arf.execute(user, "", args));
verify(player).sendMessage(eq("commands.help.header"));
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.admin.AdminResetFlagsCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringOneArgNotFlag() {
assertFalse(arf.execute(user, "", Collections.singletonList("FLAG3")));
verify(player).sendMessage(eq("commands.help.header"));
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.admin.AdminResetFlagsCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringOneArgFlag2() {
assertTrue(arf.execute(user, "", Collections.singletonList("FLAG2")));
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.admin.AdminResetFlagsCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfStringOneArgFlag1() {
assertTrue(arf.execute(user, "", Collections.singletonList("FLAG1")));
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.admin.AdminResetFlagsCommand#execute(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testExecuteUserStringListOfString() {
assertTrue(arf.execute(user, "", Collections.emptyList()));
}
/**
* Test method for {@link world.bentobox.bentobox.api.commands.admin.AdminResetFlagsCommand#tabComplete(world.bentobox.bentobox.api.user.User, java.lang.String, java.util.List)}.
*/
@Test
public void testTabCompleteUserStringListOfString() {
Optional<List<String>> list = arf.tabComplete(user, "", Collections.emptyList());
assertTrue(list.isPresent());
assertTrue(list.get().size() == 2);
assertTrue(list.get().contains("FLAG1"));
assertTrue(list.get().contains("FLAG2"));
assertFalse(list.get().contains("FLAG3"));
}
}

View File

@ -30,6 +30,7 @@ import org.bukkit.plugin.PluginManager;
import org.bukkit.scheduler.BukkitScheduler;
import org.bukkit.scheduler.BukkitTask;
import org.bukkit.util.Vector;
import org.eclipse.jdt.annotation.NonNull;
import org.eclipse.jdt.annotation.Nullable;
import org.junit.After;
import org.junit.Before;
@ -701,5 +702,14 @@ public class IslandGoCommandTest {
return false;
}
@Override
public @NonNull List<String> getOnJoinCommands() {
return null;
}
@Override
public @NonNull List<String> getOnLeaveCommands() {
return null;
}
}
}

View File

@ -29,6 +29,7 @@ import org.bukkit.event.block.BlockBreakEvent;
import org.bukkit.event.block.BlockPlaceEvent;
import org.bukkit.event.player.PlayerChangedWorldEvent;
import org.bukkit.event.player.PlayerJoinEvent;
import org.eclipse.jdt.annotation.NonNull;
import org.eclipse.jdt.annotation.Nullable;
import org.junit.After;
import org.junit.Before;
@ -275,6 +276,15 @@ public class BlockEndDragonTest {
private Map<String, Boolean> worldFlags = new HashMap<>();
@Override
public @NonNull List<String> getOnLeaveCommands() {
return null;
}
@Override
public @NonNull List<String> getOnJoinCommands() {
return null;
}
@Override
public GameMode getDefaultGameMode() {

View File

@ -2,14 +2,16 @@ package world.bentobox.bentobox.managers.island;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNotSame;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import static org.mockito.Matchers.any;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;
import static org.mockito.Mockito.verify;
import java.util.Collections;
import java.util.UUID;
import org.bukkit.Location;
@ -17,15 +19,18 @@ import org.bukkit.World;
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 com.google.common.collect.ImmutableSet;
import com.google.common.collect.ImmutableSet.Builder;
import world.bentobox.bentobox.BentoBox;
import world.bentobox.bentobox.api.flags.Flag;
import world.bentobox.bentobox.database.objects.Island;
import world.bentobox.bentobox.managers.IslandWorldManager;
import world.bentobox.bentobox.managers.IslandsManager;
@ -33,25 +38,37 @@ import world.bentobox.bentobox.managers.RanksManager;
import world.bentobox.bentobox.util.Util;
@RunWith(PowerMockRunner.class)
@PrepareForTest(Util.class)
@PrepareForTest({BentoBox.class, Util.class})
public class IslandCacheTest {
@Mock
private BentoBox plugin;
private static World world;
@Mock
private World world;
@Mock
private Island island;
// UUID
private UUID owner = UUID.randomUUID();
@Mock
private Location location;
// Test class
private IslandCache ic;
@Mock
private IslandWorldManager iwm;
@Mock
private Flag flag;
@Mock
private IslandsManager im;
@Before
public void setUp() throws Exception {
plugin = mock(BentoBox.class);
world = mock(World.class);
// Plugin
Whitebox.setInternalState(BentoBox.class, "instance", plugin);
// Worlds
IslandWorldManager iwm = mock(IslandWorldManager.class);
when(plugin.getIWM()).thenReturn(iwm);
// IWM
when(iwm.getDefaultIslandFlags(any())).thenReturn(Collections.singletonMap(flag, 400));
when(iwm.inWorld(any(World.class))).thenReturn(true);
when(iwm.inWorld(any(Location.class))).thenReturn(true);
@ -59,14 +76,11 @@ public class IslandCacheTest {
when(Util.getWorld(Mockito.any())).thenReturn(world);
// Mock up IslandsManager
IslandsManager im = mock(IslandsManager.class);
when(plugin.getIslands()).thenReturn(im);
island = mock(Island.class);
// Island
when(island.getWorld()).thenReturn(world);
location = mock(Location.class);
// Location
when(location.getWorld()).thenReturn(world);
when(location.getBlockX()).thenReturn(0);
when(location.getBlockY()).thenReturn(0);
@ -82,25 +96,26 @@ public class IslandCacheTest {
when(island.getMinX()).thenReturn(-200);
when(island.getMinZ()).thenReturn(-200);
// New cache
ic = new IslandCache();
}
@Test
public void testIslandCache() {
assertNotNull(new IslandCache());
}
/**
* Test for {@link IslandCache#addIsland(Island)}
*/
@Test
public void testAddIsland() {
IslandCache ic = new IslandCache();
assertTrue(ic.addIsland(island));
// Check if they are added
assertEquals(island, ic.get(world, owner));
assertEquals(island, ic.get(location));
}
/**
* Test for {@link IslandCache#addPlayer(UUID, Island)}
*/
@Test
public void testAddPlayer() {
IslandCache ic = new IslandCache();
UUID playerUUID = UUID.randomUUID();
ic.addPlayer(playerUUID, island);
// Check if they are added
@ -109,9 +124,11 @@ public class IslandCacheTest {
}
/**
* Test for {@link IslandCache#clear()}
*/
@Test
public void testClear() {
IslandCache ic = new IslandCache();
ic.addIsland(island);
// Check if they are added
assertEquals(island, ic.get(world, owner));
@ -121,10 +138,11 @@ public class IslandCacheTest {
assertNull(ic.get(location));
}
/**
* Test for {@link IslandCache#deleteIslandFromCache(Island)}
*/
@Test
public void testDeleteIslandFromCache() {
IslandCache ic = new IslandCache();
ic.addIsland(island);
// Check if they are added
assertEquals(island, ic.get(world, owner));
@ -156,31 +174,35 @@ public class IslandCacheTest {
}
/**
* Test for {@link IslandCache#get(Location)}
*/
@Test
public void testGetLocation() {
IslandCache ic = new IslandCache();
ic.addIsland(island);
// Check if they are added
assertEquals(island, ic.get(location));
}
/**
* Test for {@link IslandCache#get(World, UUID)}
*/
@Test
public void testGetUUID() {
IslandCache ic = new IslandCache();
ic.addIsland(island);
// Check if they are added
assertEquals(island, ic.get(world, owner));
}
/**
* Test for {@link IslandCache#getIslandAt(Location)}
*/
@Test
public void testGetIslandAtLocation() {
// Set coords to be in island space
when(island.inIslandSpace(Mockito.any(Integer.class), Mockito.any(Integer.class))).thenReturn(true);
// Set plugin
Util.setPlugin(plugin);
// New cache
IslandCache ic = new IslandCache();
ic.addIsland(island);
// Check exact match for location
@ -199,16 +221,11 @@ public class IslandCacheTest {
assertNull(ic.getIslandAt(location2));
}
/*
@Test
public void testGetIslands() {
fail("Not yet implemented"); // TODO
}
/**
* Test for {@link IslandCache#getMembers(World, UUID, int)}
*/
@Test
public void testGetMembers() {
// New cache
IslandCache ic = new IslandCache();
ic.addIsland(island);
assertTrue(ic.getMembers(world, null, RanksManager.MEMBER_RANK).isEmpty());
@ -217,10 +234,12 @@ public class IslandCacheTest {
assertEquals(3, ic.getMembers(world, island.getOwner(), RanksManager.MEMBER_RANK).size());
}
/**
* Test for {@link IslandCache#getOwner(World, UUID)}
*/
@Test
public void testGetOwner() {
// New cache
IslandCache ic = new IslandCache();
ic.addIsland(island);
assertEquals(owner, ic.getOwner(world, owner));
@ -228,10 +247,11 @@ public class IslandCacheTest {
assertNull(ic.getOwner(world, UUID.randomUUID()));
}
/**
* Test for {@link IslandCache#hasIsland(World, UUID)}
*/
@Test
public void testHasIsland() {
// New cache
IslandCache ic = new IslandCache();
ic.addIsland(island);
assertTrue(ic.hasIsland(world, owner));
@ -239,12 +259,12 @@ public class IslandCacheTest {
assertFalse(ic.hasIsland(world, null));
}
/**
* Test for {@link IslandCache#removePlayer(World, UUID)}
*/
@Test
public void testRemovePlayer() {
// New cache
IslandCache ic = new IslandCache();
ic.addIsland(island);
assertTrue(ic.hasIsland(world, owner));
ic.removePlayer(world, null);
assertTrue(ic.hasIsland(world, owner));
@ -254,18 +274,20 @@ public class IslandCacheTest {
assertFalse(ic.hasIsland(world, owner));
}
/**
* Test for {@link IslandCache#size()}
*/
@Test
public void testSize() {
// New cache
IslandCache ic = new IslandCache();
ic.addIsland(island);
assertEquals(1, ic.size());
}
/**
* Test for {@link IslandCache#setOwner(Island, UUID)}
*/
@Test
public void testSetOwner() {
// New cache
IslandCache ic = new IslandCache();
ic.addIsland(island);
UUID newOwnerUUID = UUID.randomUUID();
ic.setOwner(island, newOwnerUUID);
@ -274,4 +296,24 @@ public class IslandCacheTest {
assertEquals(island, ic.get(world, newOwnerUUID));
assertEquals(island, ic.get(island.getCenter()));
}
/**
* Test for {@link IslandCache#resetFlag(World, world.bentobox.bentobox.api.flags.Flag)}
*/
@Test
public void testResetFlag() {
ic.addIsland(island);
ic.resetFlag(world, flag);
verify(island).setFlag(eq(flag), eq(400));
}
/**
* Test for {@link IslandCache#resetAllFlags(World)}
*/
@Test
public void testResetAllFlags() {
ic.addIsland(island);
ic.resetAllFlags(world);
verify(island).setFlagsDefaults();
}
}