Update from Git Manager GUI
This commit is contained in:
@@ -17,6 +17,8 @@ import org.bukkit.inventory.meta.ItemMeta;
|
||||
import org.bukkit.plugin.java.JavaPlugin;
|
||||
import org.bukkit.Note;
|
||||
import org.bukkit.Note.Tone;
|
||||
import net.md_5.bungee.api.ChatMessageType;
|
||||
import net.md_5.bungee.api.chat.TextComponent;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
@@ -37,6 +39,9 @@ public class ButtonControl extends JavaPlugin {
|
||||
// Zeitgesteuerte Automation – verhindert mehrfaches Auslösen pro Zustandswechsel
|
||||
private final Map<String, Boolean> timedControllerLastState = new HashMap<>();
|
||||
|
||||
// Actionbar-Status pro Spieler für die Namensanzeige
|
||||
private final Map<java.util.UUID, String> lastControllerActionbar = new HashMap<>();
|
||||
|
||||
@Override
|
||||
public void onEnable() {
|
||||
configManager = new ConfigManager(this);
|
||||
@@ -84,10 +89,18 @@ public class ButtonControl extends JavaPlugin {
|
||||
getServer().getScheduler().runTaskTimer(this, this::checkDaylightSensors, 0L, 20L * 10);
|
||||
getServer().getScheduler().runTaskTimer(this, this::checkMotionSensors, 0L, 10L);
|
||||
getServer().getScheduler().runTaskTimer(this, this::checkTimedControllers, 0L, 20L * 5);
|
||||
getServer().getScheduler().runTaskTimer(this, this::updateControllerNameActionBar, 0L, 5L);
|
||||
|
||||
getLogger().info("ButtonControl v" + getDescription().getVersion() + " wurde erfolgreich aktiviert!");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDisable() {
|
||||
if (dataManager != null) {
|
||||
dataManager.shutdown();
|
||||
}
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
// Update-Hilfe
|
||||
// -----------------------------------------------------------------------
|
||||
@@ -278,6 +291,65 @@ public class ButtonControl extends JavaPlugin {
|
||||
}
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
// Controller-Name bei Blickkontakt (Actionbar)
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
private void updateControllerNameActionBar() {
|
||||
if (!configManager.getConfig().getBoolean("controller-name-display.enabled", true)) {
|
||||
clearAllControllerActionBars();
|
||||
return;
|
||||
}
|
||||
|
||||
int maxDistance = Math.max(1,
|
||||
configManager.getConfig().getInt("controller-name-display.max-look-distance", 8));
|
||||
String format = configManager.getConfig().getString(
|
||||
"controller-name-display.format", "§6Controller: §f%s");
|
||||
|
||||
for (Player player : getServer().getOnlinePlayers()) {
|
||||
String message = null;
|
||||
Block target = player.getTargetBlockExact(maxDistance);
|
||||
if (isValidController(target)) {
|
||||
String targetLoc = toLoc(target);
|
||||
String buttonId = dataManager.getButtonIdForLocation(targetLoc);
|
||||
if (buttonId != null) {
|
||||
boolean canSee = dataManager.canAccess(buttonId, player.getUniqueId())
|
||||
|| player.hasPermission("buttoncontrol.admin");
|
||||
String name = dataManager.getControllerName(buttonId);
|
||||
if (canSee && name != null && !name.trim().isEmpty()) {
|
||||
message = String.format(format, name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
java.util.UUID uuid = player.getUniqueId();
|
||||
String previous = lastControllerActionbar.get(uuid);
|
||||
if (message == null) {
|
||||
if (previous != null) {
|
||||
sendActionBar(player, " ");
|
||||
lastControllerActionbar.remove(uuid);
|
||||
}
|
||||
} else if (!message.equals(previous)) {
|
||||
sendActionBar(player, message);
|
||||
lastControllerActionbar.put(uuid, message);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void clearAllControllerActionBars() {
|
||||
if (lastControllerActionbar.isEmpty()) return;
|
||||
for (Player player : getServer().getOnlinePlayers()) {
|
||||
if (lastControllerActionbar.containsKey(player.getUniqueId())) {
|
||||
sendActionBar(player, " ");
|
||||
}
|
||||
}
|
||||
lastControllerActionbar.clear();
|
||||
}
|
||||
|
||||
private void sendActionBar(Player player, String message) {
|
||||
player.spigot().sendMessage(ChatMessageType.ACTION_BAR, TextComponent.fromLegacyText(message));
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
// Bewegungsmelder
|
||||
// -----------------------------------------------------------------------
|
||||
@@ -379,6 +451,7 @@ public class ButtonControl extends JavaPlugin {
|
||||
configManager.reloadConfig();
|
||||
dataManager.reloadData();
|
||||
timedControllerLastState.clear();
|
||||
clearAllControllerActionBars();
|
||||
sender.sendMessage(configManager.getMessage("konfiguration-neugeladen"));
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -75,6 +75,19 @@ public class ConfigManager {
|
||||
def(config, "motion-close-delay-ms", 5000);
|
||||
def(config, "motion-trigger-cooldown-ms", 2000);
|
||||
|
||||
// Optionales MySQL-Backend
|
||||
def(config, "mysql.enabled", false);
|
||||
def(config, "mysql.host", "127.0.0.1");
|
||||
def(config, "mysql.port", 3306);
|
||||
def(config, "mysql.database", "buttoncontrol");
|
||||
def(config, "mysql.user", "root");
|
||||
def(config, "mysql.password", "");
|
||||
|
||||
// Controller-Namensanzeige beim Anschauen
|
||||
def(config, "controller-name-display.enabled", true);
|
||||
def(config, "controller-name-display.max-look-distance", 8);
|
||||
def(config, "controller-name-display.format", "§6Controller: §f%s");
|
||||
|
||||
// Sounds (NEU)
|
||||
def(config, "sounds.enabled", true);
|
||||
def(config, "sounds.door-open", "BLOCK_WOODEN_DOOR_OPEN");
|
||||
|
||||
@@ -14,10 +14,19 @@ public class DataManager {
|
||||
private final ButtonControl plugin;
|
||||
private FileConfiguration data;
|
||||
private File dataFile;
|
||||
private MySQLStorage mySQLStorage;
|
||||
|
||||
public DataManager(ButtonControl plugin) {
|
||||
this.plugin = plugin;
|
||||
loadData();
|
||||
initializeStorage();
|
||||
}
|
||||
|
||||
private void initializeStorage() {
|
||||
mySQLStorage = new MySQLStorage(plugin);
|
||||
if (!mySQLStorage.initialize()) {
|
||||
mySQLStorage = null;
|
||||
}
|
||||
}
|
||||
|
||||
private void loadData() {
|
||||
@@ -28,6 +37,16 @@ public class DataManager {
|
||||
|
||||
public void reloadData() {
|
||||
data = YamlConfiguration.loadConfiguration(dataFile);
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.close();
|
||||
}
|
||||
initializeStorage();
|
||||
}
|
||||
|
||||
public void shutdown() {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.close();
|
||||
}
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
@@ -35,12 +54,14 @@ public class DataManager {
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
public boolean canAccess(String buttonId, UUID playerUUID) {
|
||||
if (mySQLStorage != null) return mySQLStorage.canAccess(buttonId, playerUUID);
|
||||
if (isPublic(buttonId)) return true;
|
||||
if (isOwner(buttonId, playerUUID)) return true;
|
||||
return data.getStringList("trust." + buttonId).contains(playerUUID.toString());
|
||||
}
|
||||
|
||||
public boolean isOwner(String buttonId, UUID playerUUID) {
|
||||
if (mySQLStorage != null) return mySQLStorage.isOwner(buttonId, playerUUID);
|
||||
return data.contains("players." + playerUUID + ".buttons." + buttonId)
|
||||
|| data.contains("players." + playerUUID + ".placed-controllers");
|
||||
// Zweite Bedingung: prüft ob irgendein placed-controller dieser UUID die buttonId enthält
|
||||
@@ -51,10 +72,15 @@ public class DataManager {
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
public String getButtonIdForLocation(String location) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getButtonIdForLocation(location);
|
||||
return getButtonIdForPlacedController(location);
|
||||
}
|
||||
|
||||
public void registerController(String location, UUID ownerUUID, String buttonId) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.registerController(location, ownerUUID, buttonId);
|
||||
return;
|
||||
}
|
||||
data.set("players." + ownerUUID + ".placed-controllers." + location, buttonId);
|
||||
// Leere buttons-Liste anlegen damit isOwner() sofort greift
|
||||
if (!data.contains("players." + ownerUUID + ".buttons." + buttonId)) {
|
||||
@@ -64,16 +90,38 @@ public class DataManager {
|
||||
}
|
||||
|
||||
public void removeController(String location) {
|
||||
if (data.getConfigurationSection("players") == null) return;
|
||||
for (String uuid : data.getConfigurationSection("players").getKeys(false)) {
|
||||
String path = "players." + uuid + ".placed-controllers." + location;
|
||||
if (data.contains(path)) data.set(path, null);
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.removeController(location);
|
||||
return;
|
||||
}
|
||||
// buttonId vor dem Löschen des Location-Eintrags ermitteln
|
||||
String buttonId = getButtonIdForPlacedController(location);
|
||||
String ownerUUID = null;
|
||||
if (data.getConfigurationSection("players") != null) {
|
||||
for (String uuid : data.getConfigurationSection("players").getKeys(false)) {
|
||||
String path = "players." + uuid + ".placed-controllers." + location;
|
||||
if (data.contains(path)) {
|
||||
data.set(path, null);
|
||||
ownerUUID = uuid;
|
||||
}
|
||||
}
|
||||
}
|
||||
// Alle zugehörigen Daten (Name, Status, Trust, Zeitplan, Verbindungen) bereinigen
|
||||
if (buttonId != null) {
|
||||
data.set("names." + buttonId, null);
|
||||
data.set("public-status." + buttonId, null);
|
||||
data.set("trust." + buttonId, null);
|
||||
data.set("schedules." + buttonId, null);
|
||||
if (ownerUUID != null) {
|
||||
data.set("players." + ownerUUID + ".buttons." + buttonId, null);
|
||||
}
|
||||
}
|
||||
removeMotionSensorSettings(location);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public String getButtonIdForPlacedController(String location) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getButtonIdForPlacedController(location);
|
||||
if (data.getConfigurationSection("players") == null) return null;
|
||||
for (String uuid : data.getConfigurationSection("players").getKeys(false)) {
|
||||
String val = data.getString("players." + uuid + ".placed-controllers." + location);
|
||||
@@ -83,6 +131,7 @@ public class DataManager {
|
||||
}
|
||||
|
||||
public List<String> getAllPlacedControllers() {
|
||||
if (mySQLStorage != null) return mySQLStorage.getAllPlacedControllers();
|
||||
List<String> result = new ArrayList<>();
|
||||
if (data.getConfigurationSection("players") == null) return result;
|
||||
for (String uuid : data.getConfigurationSection("players").getKeys(false)) {
|
||||
@@ -97,11 +146,16 @@ public class DataManager {
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
public void setConnectedBlocks(String playerUUID, String buttonId, List<String> blocks) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.setConnectedBlocks(playerUUID, buttonId, blocks);
|
||||
return;
|
||||
}
|
||||
data.set("players." + playerUUID + ".buttons." + buttonId, blocks);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public List<String> getConnectedBlocks(String buttonId) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getConnectedBlocks(buttonId);
|
||||
if (data.getConfigurationSection("players") == null) return new ArrayList<>();
|
||||
for (String uuid : data.getConfigurationSection("players").getKeys(false)) {
|
||||
String path = "players." + uuid + ".buttons." + buttonId;
|
||||
@@ -115,6 +169,7 @@ public class DataManager {
|
||||
* Wird aufgerufen wenn ein verbundener Block abgebaut wird.
|
||||
*/
|
||||
public boolean removeFromAllConnectedBlocks(String locStr) {
|
||||
if (mySQLStorage != null) return mySQLStorage.removeFromAllConnectedBlocks(locStr);
|
||||
if (data.getConfigurationSection("players") == null) return false;
|
||||
boolean changed = false;
|
||||
for (String uuid : data.getConfigurationSection("players").getKeys(false)) {
|
||||
@@ -138,11 +193,16 @@ public class DataManager {
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
public void setControllerName(String buttonId, String name) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.setControllerName(buttonId, name);
|
||||
return;
|
||||
}
|
||||
data.set("names." + buttonId, name);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public String getControllerName(String buttonId) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getControllerName(buttonId);
|
||||
return data.getString("names." + buttonId);
|
||||
}
|
||||
|
||||
@@ -151,25 +211,39 @@ public class DataManager {
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
public void setScheduleOpenTime(String buttonId, long ticks) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.setScheduleOpenTime(buttonId, ticks);
|
||||
return;
|
||||
}
|
||||
data.set("schedules." + buttonId + ".open-time", ticks);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public long getScheduleOpenTime(String buttonId) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getScheduleOpenTime(buttonId);
|
||||
return data.getLong("schedules." + buttonId + ".open-time", -1);
|
||||
}
|
||||
|
||||
public void setScheduleCloseTime(String buttonId, long ticks) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.setScheduleCloseTime(buttonId, ticks);
|
||||
return;
|
||||
}
|
||||
data.set("schedules." + buttonId + ".close-time", ticks);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public long getScheduleCloseTime(String buttonId) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getScheduleCloseTime(buttonId);
|
||||
return data.getLong("schedules." + buttonId + ".close-time", -1);
|
||||
}
|
||||
|
||||
/** Entfernt den kompletten Zeitplan für einen Controller. */
|
||||
public void clearSchedule(String buttonId) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.clearSchedule(buttonId);
|
||||
return;
|
||||
}
|
||||
data.set("schedules." + buttonId, null);
|
||||
saveData();
|
||||
}
|
||||
@@ -179,6 +253,10 @@ public class DataManager {
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
public void addTrustedPlayer(String buttonId, UUID targetUUID) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.addTrustedPlayer(buttonId, targetUUID);
|
||||
return;
|
||||
}
|
||||
List<String> trusted = data.getStringList("trust." + buttonId);
|
||||
if (!trusted.contains(targetUUID.toString())) {
|
||||
trusted.add(targetUUID.toString());
|
||||
@@ -188,6 +266,10 @@ public class DataManager {
|
||||
}
|
||||
|
||||
public void removeTrustedPlayer(String buttonId, UUID targetUUID) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.removeTrustedPlayer(buttonId, targetUUID);
|
||||
return;
|
||||
}
|
||||
List<String> trusted = data.getStringList("trust." + buttonId);
|
||||
trusted.remove(targetUUID.toString());
|
||||
data.set("trust." + buttonId, trusted);
|
||||
@@ -195,11 +277,16 @@ public class DataManager {
|
||||
}
|
||||
|
||||
public void setPublic(String buttonId, boolean isPublic) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.setPublic(buttonId, isPublic);
|
||||
return;
|
||||
}
|
||||
data.set("public-status." + buttonId, isPublic);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public boolean isPublic(String buttonId) {
|
||||
if (mySQLStorage != null) return mySQLStorage.isPublic(buttonId);
|
||||
return data.getBoolean("public-status." + buttonId, false);
|
||||
}
|
||||
|
||||
@@ -208,11 +295,16 @@ public class DataManager {
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
public void setPlayerInstrument(UUID playerUUID, String instrument) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.setPlayerInstrument(playerUUID, instrument);
|
||||
return;
|
||||
}
|
||||
data.set("players." + playerUUID + ".instrument", instrument);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public String getPlayerInstrument(UUID playerUUID) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getPlayerInstrument(playerUUID);
|
||||
return data.getString("players." + playerUUID + ".instrument");
|
||||
}
|
||||
|
||||
@@ -221,24 +313,38 @@ public class DataManager {
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
public void setMotionSensorRadius(String location, double radius) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.setMotionSensorRadius(location, radius);
|
||||
return;
|
||||
}
|
||||
data.set("motion-sensors." + location + ".radius", radius);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public double getMotionSensorRadius(String location) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getMotionSensorRadius(location);
|
||||
return data.getDouble("motion-sensors." + location + ".radius", -1);
|
||||
}
|
||||
|
||||
public void setMotionSensorDelay(String location, long delay) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.setMotionSensorDelay(location, delay);
|
||||
return;
|
||||
}
|
||||
data.set("motion-sensors." + location + ".delay", delay);
|
||||
saveData();
|
||||
}
|
||||
|
||||
public long getMotionSensorDelay(String location) {
|
||||
if (mySQLStorage != null) return mySQLStorage.getMotionSensorDelay(location);
|
||||
return data.getLong("motion-sensors." + location + ".delay", -1);
|
||||
}
|
||||
|
||||
public void removeMotionSensorSettings(String location) {
|
||||
if (mySQLStorage != null) {
|
||||
mySQLStorage.removeMotionSensorSettings(location);
|
||||
return;
|
||||
}
|
||||
data.set("motion-sensors." + location, null);
|
||||
saveData();
|
||||
}
|
||||
@@ -252,6 +358,7 @@ public class DataManager {
|
||||
* Verhindert I/O-Lags auf dem Main-Thread.
|
||||
*/
|
||||
public void saveData() {
|
||||
if (mySQLStorage != null) return;
|
||||
final String serialized;
|
||||
try {
|
||||
serialized = data.saveToString();
|
||||
|
||||
506
src/main/java/viper/MySQLStorage.java
Normal file
506
src/main/java/viper/MySQLStorage.java
Normal file
@@ -0,0 +1,506 @@
|
||||
package viper;
|
||||
|
||||
import org.bukkit.configuration.file.FileConfiguration;
|
||||
|
||||
import java.sql.Connection;
|
||||
import java.sql.DriverManager;
|
||||
import java.sql.PreparedStatement;
|
||||
import java.sql.ResultSet;
|
||||
import java.sql.SQLException;
|
||||
import java.sql.Statement;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.UUID;
|
||||
|
||||
public class MySQLStorage {
|
||||
private final ButtonControl plugin;
|
||||
|
||||
private final String host;
|
||||
private final int port;
|
||||
private final String database;
|
||||
private final String user;
|
||||
private final String password;
|
||||
private final boolean enabled;
|
||||
|
||||
private Connection connection;
|
||||
|
||||
public MySQLStorage(ButtonControl plugin) {
|
||||
this.plugin = plugin;
|
||||
|
||||
FileConfiguration cfg = plugin.getConfigManager().getConfig();
|
||||
this.enabled = cfg.getBoolean("mysql.enabled", false);
|
||||
this.host = cfg.getString("mysql.host", "127.0.0.1");
|
||||
this.port = cfg.getInt("mysql.port", 3306);
|
||||
this.database = cfg.getString("mysql.database", "buttoncontrol");
|
||||
this.user = cfg.getString("mysql.user", "root");
|
||||
this.password = cfg.getString("mysql.password", "");
|
||||
}
|
||||
|
||||
public boolean initialize() {
|
||||
if (!enabled) return false;
|
||||
try {
|
||||
Class.forName("com.mysql.cj.jdbc.Driver");
|
||||
getConnection();
|
||||
createTables();
|
||||
plugin.getLogger().info("MySQL aktiviert.");
|
||||
return true;
|
||||
} catch (Exception e) {
|
||||
plugin.getLogger().warning("MySQL konnte nicht initialisiert werden, verwende data.yml: " + e.getMessage());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public void close() {
|
||||
if (connection != null) {
|
||||
try {
|
||||
connection.close();
|
||||
} catch (SQLException ignored) {
|
||||
}
|
||||
connection = null;
|
||||
}
|
||||
}
|
||||
|
||||
private Connection getConnection() throws SQLException {
|
||||
if (connection != null && connection.isValid(2)) {
|
||||
return connection;
|
||||
}
|
||||
String url = "jdbc:mysql://" + host + ":" + port + "/" + database
|
||||
+ "?useSSL=false&allowPublicKeyRetrieval=true&useUnicode=true&characterEncoding=utf8&serverTimezone=UTC";
|
||||
connection = DriverManager.getConnection(url, user, password);
|
||||
return connection;
|
||||
}
|
||||
|
||||
private void createTables() throws SQLException {
|
||||
try (Statement st = getConnection().createStatement()) {
|
||||
st.executeUpdate("CREATE TABLE IF NOT EXISTS bc_controllers ("
|
||||
+ "location VARCHAR(128) PRIMARY KEY,"
|
||||
+ "owner_uuid VARCHAR(36) NOT NULL,"
|
||||
+ "button_id VARCHAR(64) NOT NULL"
|
||||
+ ")");
|
||||
|
||||
st.executeUpdate("CREATE TABLE IF NOT EXISTS bc_button_connections ("
|
||||
+ "owner_uuid VARCHAR(36) NOT NULL,"
|
||||
+ "button_id VARCHAR(64) NOT NULL,"
|
||||
+ "block_location VARCHAR(128) NOT NULL,"
|
||||
+ "PRIMARY KEY (button_id, block_location)"
|
||||
+ ")");
|
||||
|
||||
st.executeUpdate("CREATE TABLE IF NOT EXISTS bc_controller_names ("
|
||||
+ "button_id VARCHAR(64) PRIMARY KEY,"
|
||||
+ "name VARCHAR(64)"
|
||||
+ ")");
|
||||
|
||||
st.executeUpdate("CREATE TABLE IF NOT EXISTS bc_schedules ("
|
||||
+ "button_id VARCHAR(64) PRIMARY KEY,"
|
||||
+ "open_time BIGINT,"
|
||||
+ "close_time BIGINT"
|
||||
+ ")");
|
||||
|
||||
st.executeUpdate("CREATE TABLE IF NOT EXISTS bc_trust ("
|
||||
+ "button_id VARCHAR(64) NOT NULL,"
|
||||
+ "target_uuid VARCHAR(36) NOT NULL,"
|
||||
+ "PRIMARY KEY (button_id, target_uuid)"
|
||||
+ ")");
|
||||
|
||||
st.executeUpdate("CREATE TABLE IF NOT EXISTS bc_public_status ("
|
||||
+ "button_id VARCHAR(64) PRIMARY KEY,"
|
||||
+ "is_public BOOLEAN NOT NULL"
|
||||
+ ")");
|
||||
|
||||
st.executeUpdate("CREATE TABLE IF NOT EXISTS bc_player_settings ("
|
||||
+ "player_uuid VARCHAR(36) PRIMARY KEY,"
|
||||
+ "instrument VARCHAR(32)"
|
||||
+ ")");
|
||||
|
||||
st.executeUpdate("CREATE TABLE IF NOT EXISTS bc_motion_sensors ("
|
||||
+ "location VARCHAR(128) PRIMARY KEY,"
|
||||
+ "radius DOUBLE,"
|
||||
+ "delay_ms BIGINT"
|
||||
+ ")");
|
||||
}
|
||||
}
|
||||
|
||||
public boolean canAccess(String buttonId, UUID playerUUID) {
|
||||
return isPublic(buttonId) || isOwner(buttonId, playerUUID) || isTrusted(buttonId, playerUUID);
|
||||
}
|
||||
|
||||
public boolean isOwner(String buttonId, UUID playerUUID) {
|
||||
String uuid = playerUUID.toString();
|
||||
String q1 = "SELECT 1 FROM bc_controllers WHERE button_id = ? AND owner_uuid = ? LIMIT 1";
|
||||
String q2 = "SELECT 1 FROM bc_button_connections WHERE button_id = ? AND owner_uuid = ? LIMIT 1";
|
||||
try (PreparedStatement ps1 = getConnection().prepareStatement(q1);
|
||||
PreparedStatement ps2 = getConnection().prepareStatement(q2)) {
|
||||
ps1.setString(1, buttonId);
|
||||
ps1.setString(2, uuid);
|
||||
try (ResultSet rs = ps1.executeQuery()) {
|
||||
if (rs.next()) return true;
|
||||
}
|
||||
ps2.setString(1, buttonId);
|
||||
ps2.setString(2, uuid);
|
||||
try (ResultSet rs = ps2.executeQuery()) {
|
||||
return rs.next();
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL isOwner Fehler: " + e.getMessage());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public String getButtonIdForLocation(String location) {
|
||||
String q = "SELECT button_id FROM bc_controllers WHERE location = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, location);
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next() ? rs.getString(1) : null;
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getButtonIdForLocation Fehler: " + e.getMessage());
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public void registerController(String location, UUID ownerUUID, String buttonId) {
|
||||
String q = "INSERT INTO bc_controllers (location, owner_uuid, button_id) VALUES (?, ?, ?)"
|
||||
+ " ON DUPLICATE KEY UPDATE owner_uuid = VALUES(owner_uuid), button_id = VALUES(button_id)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, location);
|
||||
ps.setString(2, ownerUUID.toString());
|
||||
ps.setString(3, buttonId);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL registerController Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public void removeController(String location) {
|
||||
// buttonId vor dem Löschen ermitteln
|
||||
String buttonId = getButtonIdForLocation(location);
|
||||
String q = "DELETE FROM bc_controllers WHERE location = ?";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, location);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL removeController Fehler: " + e.getMessage());
|
||||
}
|
||||
// Alle zugehörigen Tabellen bereinigen
|
||||
if (buttonId != null) {
|
||||
deleteButtonData(buttonId);
|
||||
}
|
||||
removeMotionSensorSettings(location);
|
||||
}
|
||||
|
||||
private void deleteButtonData(String buttonId) {
|
||||
String[] queries = {
|
||||
"DELETE FROM bc_controller_names WHERE button_id = ?",
|
||||
"DELETE FROM bc_public_status WHERE button_id = ?",
|
||||
"DELETE FROM bc_trust WHERE button_id = ?",
|
||||
"DELETE FROM bc_schedules WHERE button_id = ?",
|
||||
"DELETE FROM bc_button_connections WHERE button_id = ?"
|
||||
};
|
||||
for (String q : queries) {
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL deleteButtonData Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public String getButtonIdForPlacedController(String location) {
|
||||
return getButtonIdForLocation(location);
|
||||
}
|
||||
|
||||
public List<String> getAllPlacedControllers() {
|
||||
List<String> result = new ArrayList<>();
|
||||
String q = "SELECT location FROM bc_controllers";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q);
|
||||
ResultSet rs = ps.executeQuery()) {
|
||||
while (rs.next()) result.add(rs.getString(1));
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getAllPlacedControllers Fehler: " + e.getMessage());
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public void setConnectedBlocks(String playerUUID, String buttonId, List<String> blocks) {
|
||||
String del = "DELETE FROM bc_button_connections WHERE owner_uuid = ? AND button_id = ?";
|
||||
String ins = "INSERT INTO bc_button_connections (owner_uuid, button_id, block_location) VALUES (?, ?, ?)";
|
||||
try (PreparedStatement psDel = getConnection().prepareStatement(del);
|
||||
PreparedStatement psIns = getConnection().prepareStatement(ins)) {
|
||||
psDel.setString(1, playerUUID);
|
||||
psDel.setString(2, buttonId);
|
||||
psDel.executeUpdate();
|
||||
|
||||
for (String block : blocks) {
|
||||
psIns.setString(1, playerUUID);
|
||||
psIns.setString(2, buttonId);
|
||||
psIns.setString(3, block);
|
||||
psIns.addBatch();
|
||||
}
|
||||
psIns.executeBatch();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL setConnectedBlocks Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public List<String> getConnectedBlocks(String buttonId) {
|
||||
List<String> result = new ArrayList<>();
|
||||
String q = "SELECT block_location FROM bc_button_connections WHERE button_id = ?";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
while (rs.next()) result.add(rs.getString(1));
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getConnectedBlocks Fehler: " + e.getMessage());
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public boolean removeFromAllConnectedBlocks(String locStr) {
|
||||
String q = "DELETE FROM bc_button_connections WHERE block_location = ?";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, locStr);
|
||||
return ps.executeUpdate() > 0;
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL removeFromAllConnectedBlocks Fehler: " + e.getMessage());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public void setControllerName(String buttonId, String name) {
|
||||
String q = "INSERT INTO bc_controller_names (button_id, name) VALUES (?, ?)"
|
||||
+ " ON DUPLICATE KEY UPDATE name = VALUES(name)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.setString(2, name);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL setControllerName Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public String getControllerName(String buttonId) {
|
||||
String q = "SELECT name FROM bc_controller_names WHERE button_id = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next() ? rs.getString(1) : null;
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getControllerName Fehler: " + e.getMessage());
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public void setScheduleOpenTime(String buttonId, long ticks) {
|
||||
String q = "INSERT INTO bc_schedules (button_id, open_time, close_time) VALUES (?, ?, COALESCE((SELECT close_time FROM bc_schedules WHERE button_id = ?), -1))"
|
||||
+ " ON DUPLICATE KEY UPDATE open_time = VALUES(open_time)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.setLong(2, ticks);
|
||||
ps.setString(3, buttonId);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL setScheduleOpenTime Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public long getScheduleOpenTime(String buttonId) {
|
||||
String q = "SELECT open_time FROM bc_schedules WHERE button_id = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next() ? rs.getLong(1) : -1;
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getScheduleOpenTime Fehler: " + e.getMessage());
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
public void setScheduleCloseTime(String buttonId, long ticks) {
|
||||
String q = "INSERT INTO bc_schedules (button_id, open_time, close_time) VALUES (?, COALESCE((SELECT open_time FROM bc_schedules WHERE button_id = ?), -1), ?)"
|
||||
+ " ON DUPLICATE KEY UPDATE close_time = VALUES(close_time)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.setString(2, buttonId);
|
||||
ps.setLong(3, ticks);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL setScheduleCloseTime Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public long getScheduleCloseTime(String buttonId) {
|
||||
String q = "SELECT close_time FROM bc_schedules WHERE button_id = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next() ? rs.getLong(1) : -1;
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getScheduleCloseTime Fehler: " + e.getMessage());
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
public void clearSchedule(String buttonId) {
|
||||
String q = "DELETE FROM bc_schedules WHERE button_id = ?";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL clearSchedule Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public void addTrustedPlayer(String buttonId, UUID targetUUID) {
|
||||
String q = "INSERT IGNORE INTO bc_trust (button_id, target_uuid) VALUES (?, ?)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.setString(2, targetUUID.toString());
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL addTrustedPlayer Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public void removeTrustedPlayer(String buttonId, UUID targetUUID) {
|
||||
String q = "DELETE FROM bc_trust WHERE button_id = ? AND target_uuid = ?";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.setString(2, targetUUID.toString());
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL removeTrustedPlayer Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public void setPublic(String buttonId, boolean isPublic) {
|
||||
String q = "INSERT INTO bc_public_status (button_id, is_public) VALUES (?, ?)"
|
||||
+ " ON DUPLICATE KEY UPDATE is_public = VALUES(is_public)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.setBoolean(2, isPublic);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL setPublic Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isPublic(String buttonId) {
|
||||
String q = "SELECT is_public FROM bc_public_status WHERE button_id = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next() && rs.getBoolean(1);
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL isPublic Fehler: " + e.getMessage());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public void setPlayerInstrument(UUID playerUUID, String instrument) {
|
||||
String q = "INSERT INTO bc_player_settings (player_uuid, instrument) VALUES (?, ?)"
|
||||
+ " ON DUPLICATE KEY UPDATE instrument = VALUES(instrument)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, playerUUID.toString());
|
||||
ps.setString(2, instrument);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL setPlayerInstrument Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public String getPlayerInstrument(UUID playerUUID) {
|
||||
String q = "SELECT instrument FROM bc_player_settings WHERE player_uuid = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, playerUUID.toString());
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next() ? rs.getString(1) : null;
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getPlayerInstrument Fehler: " + e.getMessage());
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public void setMotionSensorRadius(String location, double radius) {
|
||||
String q = "INSERT INTO bc_motion_sensors (location, radius, delay_ms) VALUES (?, ?, COALESCE((SELECT delay_ms FROM bc_motion_sensors WHERE location = ?), -1))"
|
||||
+ " ON DUPLICATE KEY UPDATE radius = VALUES(radius)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, location);
|
||||
ps.setDouble(2, radius);
|
||||
ps.setString(3, location);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL setMotionSensorRadius Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public double getMotionSensorRadius(String location) {
|
||||
String q = "SELECT radius FROM bc_motion_sensors WHERE location = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, location);
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next() ? rs.getDouble(1) : -1;
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getMotionSensorRadius Fehler: " + e.getMessage());
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
public void setMotionSensorDelay(String location, long delay) {
|
||||
String q = "INSERT INTO bc_motion_sensors (location, radius, delay_ms) VALUES (?, COALESCE((SELECT radius FROM bc_motion_sensors WHERE location = ?), -1), ?)"
|
||||
+ " ON DUPLICATE KEY UPDATE delay_ms = VALUES(delay_ms)";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, location);
|
||||
ps.setString(2, location);
|
||||
ps.setLong(3, delay);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL setMotionSensorDelay Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public long getMotionSensorDelay(String location) {
|
||||
String q = "SELECT delay_ms FROM bc_motion_sensors WHERE location = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, location);
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next() ? rs.getLong(1) : -1;
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL getMotionSensorDelay Fehler: " + e.getMessage());
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
public void removeMotionSensorSettings(String location) {
|
||||
String q = "DELETE FROM bc_motion_sensors WHERE location = ?";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, location);
|
||||
ps.executeUpdate();
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL removeMotionSensorSettings Fehler: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isTrusted(String buttonId, UUID playerUUID) {
|
||||
String q = "SELECT 1 FROM bc_trust WHERE button_id = ? AND target_uuid = ? LIMIT 1";
|
||||
try (PreparedStatement ps = getConnection().prepareStatement(q)) {
|
||||
ps.setString(1, buttonId);
|
||||
ps.setString(2, playerUUID.toString());
|
||||
try (ResultSet rs = ps.executeQuery()) {
|
||||
return rs.next();
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
plugin.getLogger().warning("MySQL isTrusted Fehler: " + e.getMessage());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -20,6 +20,24 @@ motion-close-delay-ms: 5000
|
||||
# Cooldown: wie lange nach dem Schließen der Sensor nicht erneut auslöst
|
||||
motion-trigger-cooldown-ms: 2000
|
||||
|
||||
# ── Optionales MySQL-Backend ────────────────────────────────────────────────
|
||||
mysql:
|
||||
# false = data.yml verwenden, true = MySQL verwenden
|
||||
enabled: false
|
||||
host: "127.0.0.1"
|
||||
port: 3306
|
||||
database: "controll"
|
||||
user: "controll"
|
||||
password: "controll"
|
||||
|
||||
# ── Controller-Name beim Anschauen ──────────────────────────────────────────
|
||||
controller-name-display:
|
||||
enabled: true
|
||||
# Distanz in Blöcken für die Blickerkennung
|
||||
max-look-distance: 8
|
||||
# %s = Name aus /bc rename
|
||||
format: "§6Controller: §f%s"
|
||||
|
||||
# ── Sounds beim Öffnen/Schließen (NEU) ──────────────────────────────────────
|
||||
# Auf false setzen um alle Controller-Sounds zu deaktivieren
|
||||
sounds:
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
name: ButtonControl
|
||||
version: 1.6
|
||||
version: 1.7
|
||||
main: viper.ButtonControl
|
||||
api-version: 1.21
|
||||
author: M_Viper
|
||||
|
||||
Reference in New Issue
Block a user