197 lines
7.2 KiB
Java
197 lines
7.2 KiB
Java
package me.viper.teamplugin.manager;
|
|
|
|
import me.viper.teamplugin.Main;
|
|
import me.viper.teamplugin.util.Utils;
|
|
import org.bukkit.configuration.file.FileConfiguration;
|
|
import org.bukkit.configuration.file.YamlConfiguration;
|
|
|
|
import java.io.File;
|
|
import java.io.IOException;
|
|
import java.nio.file.Files;
|
|
import java.nio.file.StandardCopyOption;
|
|
import java.util.*;
|
|
import java.util.stream.Collectors;
|
|
|
|
public class DataManager {
|
|
private static final String FORCE_OFFLINE_PATH = "Status.force-offline";
|
|
|
|
private static File file;
|
|
private static FileConfiguration data;
|
|
|
|
public static void setup() {
|
|
try {
|
|
file = new File(Main.getInstance().getDataFolder(), "data.yml");
|
|
if (!file.exists()) {
|
|
Main.getInstance().getDataFolder().mkdirs();
|
|
file.createNewFile();
|
|
data = YamlConfiguration.loadConfiguration(file);
|
|
data.createSection("Team");
|
|
save();
|
|
} else {
|
|
data = YamlConfiguration.loadConfiguration(file);
|
|
if (data.getConfigurationSection("Team") == null) {
|
|
data.createSection("Team");
|
|
save();
|
|
}
|
|
}
|
|
|
|
// Ensure backup folder exists if enabled
|
|
if (Main.getInstance().getConfig().getBoolean("backup.enabled", true)) {
|
|
File backups = new File(Main.getInstance().getDataFolder(),
|
|
Main.getInstance().getConfig().getString("backup.folder", "backups"));
|
|
if (!backups.exists()) backups.mkdirs();
|
|
}
|
|
} catch (IOException e) {
|
|
e.printStackTrace();
|
|
}
|
|
}
|
|
|
|
/** Reload data.yml from disk (used after restore). */
|
|
public static void reloadData() {
|
|
if (file == null) file = new File(Main.getInstance().getDataFolder(), "data.yml");
|
|
data = YamlConfiguration.loadConfiguration(file);
|
|
if (data.getConfigurationSection("Team") == null) {
|
|
data.createSection("Team");
|
|
save();
|
|
}
|
|
}
|
|
|
|
public static FileConfiguration getData() {
|
|
if (data == null) setup();
|
|
return data;
|
|
}
|
|
|
|
public static void save() {
|
|
try {
|
|
if (data != null && file != null) data.save(file);
|
|
} catch (IOException e) {
|
|
e.printStackTrace();
|
|
}
|
|
}
|
|
|
|
public static void addMember(String rank, String name) {
|
|
List<String> list = data.getStringList("Team." + rank);
|
|
if (!list.contains(name)) {
|
|
list.add(name);
|
|
data.set("Team." + rank, list);
|
|
|
|
// store join date if enabled
|
|
if (Main.getInstance().getConfig().getBoolean("storeJoinDate", true)) {
|
|
data.set("JoinDates." + name, Utils.formatIsoNow());
|
|
}
|
|
|
|
save();
|
|
}
|
|
}
|
|
|
|
public static boolean removeMember(String name) {
|
|
boolean removed = false;
|
|
if (data.getConfigurationSection("Team") != null) {
|
|
for (String rank : data.getConfigurationSection("Team").getKeys(false)) {
|
|
List<String> members = data.getStringList("Team." + rank);
|
|
if (members.removeIf(s -> s.equalsIgnoreCase(name))) {
|
|
data.set("Team." + rank, members);
|
|
removed = true;
|
|
}
|
|
}
|
|
if (removed) {
|
|
data.set("JoinDates." + name, null);
|
|
data.set(FORCE_OFFLINE_PATH + "." + normalizeName(name), null);
|
|
save();
|
|
}
|
|
}
|
|
return removed;
|
|
}
|
|
|
|
// Backups
|
|
public static String createBackup() {
|
|
String folderName = Main.getInstance().getConfig().getString("backup.folder", "backups");
|
|
File backupsFolder = new File(Main.getInstance().getDataFolder(), folderName);
|
|
if (!backupsFolder.exists()) backupsFolder.mkdirs();
|
|
|
|
String timestamp = Utils.formatIsoNow().replace(":", "-");
|
|
String fileName = "data-backup-" + timestamp + ".yml";
|
|
File dest = new File(backupsFolder, fileName);
|
|
|
|
try {
|
|
// ensure current file exists
|
|
if (file == null) file = new File(Main.getInstance().getDataFolder(), "data.yml");
|
|
if (!file.exists()) {
|
|
// nothing to backup
|
|
return null;
|
|
}
|
|
|
|
Files.copy(file.toPath(), dest.toPath(), StandardCopyOption.REPLACE_EXISTING);
|
|
// prune backups
|
|
pruneBackups(backupsFolder);
|
|
return fileName;
|
|
} catch (IOException e) {
|
|
e.printStackTrace();
|
|
return null;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Restore a backup by filename (relative to backup folder).
|
|
* Returns true on success.
|
|
*/
|
|
public static boolean restoreBackup(String fileName) {
|
|
String folderName = Main.getInstance().getConfig().getString("backup.folder", "backups");
|
|
File backupsFolder = new File(Main.getInstance().getDataFolder(), folderName);
|
|
File src = new File(backupsFolder, fileName);
|
|
if (!src.exists()) return false;
|
|
|
|
try {
|
|
if (file == null) file = new File(Main.getInstance().getDataFolder(), "data.yml");
|
|
Files.copy(src.toPath(), file.toPath(), StandardCopyOption.REPLACE_EXISTING);
|
|
// reload data from the restored file
|
|
reloadData();
|
|
return true;
|
|
} catch (IOException e) {
|
|
e.printStackTrace();
|
|
return false;
|
|
}
|
|
}
|
|
|
|
public static List<String> listBackups() {
|
|
String folderName = Main.getInstance().getConfig().getString("backup.folder", "backups");
|
|
File backupsFolder = new File(Main.getInstance().getDataFolder(), folderName);
|
|
if (!backupsFolder.exists()) return Collections.emptyList();
|
|
return Arrays.stream(Objects.requireNonNull(backupsFolder.listFiles()))
|
|
.filter(File::isFile)
|
|
.map(File::getName)
|
|
.sorted(Comparator.reverseOrder())
|
|
.collect(Collectors.toList());
|
|
}
|
|
|
|
private static void pruneBackups(File backupsFolder) {
|
|
int keep = Main.getInstance().getConfig().getInt("backup.keep", 10);
|
|
List<File> files = Arrays.stream(Objects.requireNonNull(backupsFolder.listFiles()))
|
|
.filter(File::isFile)
|
|
.sorted(Comparator.comparingLong(File::lastModified).reversed())
|
|
.collect(Collectors.toList());
|
|
|
|
for (int i = keep; i < files.size(); i++) {
|
|
files.get(i).delete();
|
|
}
|
|
}
|
|
|
|
// helper
|
|
public static String getJoinDate(String name) {
|
|
return data.getString("JoinDates." + name, "");
|
|
}
|
|
|
|
public static boolean isForcedOffline(String name) {
|
|
return data.getBoolean(FORCE_OFFLINE_PATH + "." + normalizeName(name), false);
|
|
}
|
|
|
|
public static void setForcedOffline(String name, boolean forcedOffline) {
|
|
data.set(FORCE_OFFLINE_PATH + "." + normalizeName(name), forcedOffline ? true : null);
|
|
save();
|
|
}
|
|
|
|
private static String normalizeName(String name) {
|
|
return name == null ? "" : name.toLowerCase(Locale.ROOT);
|
|
}
|
|
}
|