mirror of
https://github.com/filoghost/HolographicDisplays.git
synced 2024-12-30 04:37:42 +01:00
Improve automatic configuration upgrades and use separate folder for backups
This commit is contained in:
parent
4dc46456a3
commit
72cdacb998
@ -8,7 +8,6 @@ package me.filoghost.holographicdisplays.plugin;
|
||||
import com.gmail.filoghost.holographicdisplays.api.internal.HologramsAPIProvider;
|
||||
import me.filoghost.fcommons.FCommonsPlugin;
|
||||
import me.filoghost.fcommons.FeatureSupport;
|
||||
import me.filoghost.fcommons.config.exception.ConfigException;
|
||||
import me.filoghost.fcommons.logging.ErrorCollector;
|
||||
import me.filoghost.holographicdisplays.api.internal.HolographicDisplaysAPIProvider;
|
||||
import me.filoghost.holographicdisplays.common.nms.NMSManager;
|
||||
@ -20,9 +19,9 @@ import me.filoghost.holographicdisplays.plugin.commands.HologramCommandManager;
|
||||
import me.filoghost.holographicdisplays.plugin.config.ConfigManager;
|
||||
import me.filoghost.holographicdisplays.plugin.config.HologramDatabase;
|
||||
import me.filoghost.holographicdisplays.plugin.config.Settings;
|
||||
import me.filoghost.holographicdisplays.plugin.config.upgrade.LegacyAnimationsUpgrade;
|
||||
import me.filoghost.holographicdisplays.plugin.config.upgrade.LegacyDatabaseUpgrade;
|
||||
import me.filoghost.holographicdisplays.plugin.config.upgrade.LegacySymbolsUpgrade;
|
||||
import me.filoghost.holographicdisplays.plugin.config.upgrade.AnimationsLegacyUpgrade;
|
||||
import me.filoghost.holographicdisplays.plugin.config.upgrade.DatabaseLegacyUpgrade;
|
||||
import me.filoghost.holographicdisplays.plugin.config.upgrade.SymbolsLegacyUpgrade;
|
||||
import me.filoghost.holographicdisplays.plugin.hologram.api.APIHologramManager;
|
||||
import me.filoghost.holographicdisplays.plugin.hologram.internal.InternalHologramManager;
|
||||
import me.filoghost.holographicdisplays.plugin.hologram.tracking.LineTrackerManager;
|
||||
@ -44,7 +43,6 @@ import org.bukkit.Bukkit;
|
||||
import org.bukkit.ChatColor;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
public class HolographicDisplays extends FCommonsPlugin {
|
||||
@ -107,21 +105,9 @@ public class HolographicDisplays extends FCommonsPlugin {
|
||||
APIHologramManager apiHologramManager = new APIHologramManager(lineTrackerManager);
|
||||
|
||||
// Run only once at startup, before loading the configuration
|
||||
try {
|
||||
LegacySymbolsUpgrade.run(configManager, errorCollector);
|
||||
} catch (ConfigException e) {
|
||||
errorCollector.add(e, "couldn't automatically convert symbols file to the new format");
|
||||
}
|
||||
try {
|
||||
LegacyAnimationsUpgrade.run(configManager, errorCollector);
|
||||
} catch (IOException e) {
|
||||
errorCollector.add(e, "couldn't automatically convert animation files to the new format");
|
||||
}
|
||||
try {
|
||||
LegacyDatabaseUpgrade.run(configManager);
|
||||
} catch (ConfigException | IOException e) {
|
||||
errorCollector.add(e, "couldn't automatically convert database file to the new format");
|
||||
}
|
||||
new SymbolsLegacyUpgrade(configManager, errorCollector).tryRun();
|
||||
new AnimationsLegacyUpgrade(configManager, errorCollector).tryRun();
|
||||
new DatabaseLegacyUpgrade(configManager, errorCollector).tryRun();
|
||||
|
||||
// Load the configuration
|
||||
load(true, errorCollector);
|
||||
|
@ -145,7 +145,7 @@ public class ConfigManager extends BaseConfigManager {
|
||||
errorCollector.add(e, "error while loading config file \"" + formatPath(file) + "\"");
|
||||
}
|
||||
|
||||
private String formatPath(Path path) {
|
||||
public String formatPath(Path path) {
|
||||
return ConfigErrors.formatPath(getRootDataFolder(), path);
|
||||
}
|
||||
|
||||
|
@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright (C) filoghost and contributors
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
package me.filoghost.holographicdisplays.plugin.config.upgrade;
|
||||
|
||||
import me.filoghost.fcommons.config.Config;
|
||||
import me.filoghost.fcommons.config.exception.ConfigSaveException;
|
||||
import me.filoghost.fcommons.logging.ErrorCollector;
|
||||
import me.filoghost.holographicdisplays.plugin.config.ConfigManager;
|
||||
import me.filoghost.holographicdisplays.plugin.util.FileUtils;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.util.List;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public class AnimationsLegacyUpgrade extends LegacyUpgrade {
|
||||
|
||||
private static final String SPEED_PREFIX = "speed:";
|
||||
|
||||
private final Path animationFolder;
|
||||
|
||||
public AnimationsLegacyUpgrade(ConfigManager configManager, ErrorCollector errorCollector) {
|
||||
super(configManager, errorCollector);
|
||||
this.animationFolder = configManager.getAnimationsFolder();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Path getFile() {
|
||||
return animationFolder;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() throws IOException {
|
||||
if (!Files.isDirectory(animationFolder)) {
|
||||
return;
|
||||
}
|
||||
|
||||
try (Stream<Path> animationFiles = Files.list(animationFolder)) {
|
||||
animationFiles.filter(Files::isRegularFile).forEach(file -> {
|
||||
tryRun(file, () -> upgradeAnimationFile(file));
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private void upgradeAnimationFile(Path oldFile) throws IOException, ConfigSaveException {
|
||||
String oldFileName = oldFile.getFileName().toString();
|
||||
if (FileUtils.hasFileExtension(oldFileName, "yml")) {
|
||||
return; // Probably a file already with the new format
|
||||
}
|
||||
|
||||
List<String> lines = Files.readAllLines(oldFile);
|
||||
if (lines.size() == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Remove the first line that only contains the speed
|
||||
String firstLine = lines.remove(0).trim();
|
||||
if (!firstLine.toLowerCase().startsWith(SPEED_PREFIX)) {
|
||||
return; // Not a valid animation
|
||||
}
|
||||
|
||||
String newFileName;
|
||||
if (FileUtils.hasFileExtension(oldFileName, "txt")) {
|
||||
newFileName = FileUtils.removeFileExtension(oldFileName) + ".yml";
|
||||
} else {
|
||||
newFileName = oldFileName + ".yml";
|
||||
}
|
||||
Path newFile = oldFile.resolveSibling(newFileName);
|
||||
|
||||
if (Files.isRegularFile(newFile)) {
|
||||
return; // Already existing, do not override
|
||||
}
|
||||
|
||||
double speed;
|
||||
try {
|
||||
speed = Double.parseDouble(firstLine.substring(SPEED_PREFIX.length()).trim());
|
||||
} catch (NumberFormatException e) {
|
||||
speed = 0.5;
|
||||
}
|
||||
|
||||
Config config = new Config();
|
||||
config.setDouble("interval-seconds", speed);
|
||||
config.setStringList("animation-frames", lines);
|
||||
|
||||
createBackupFile(oldFile);
|
||||
configManager.getConfigLoader(newFile).save(config);
|
||||
Files.delete(oldFile);
|
||||
}
|
||||
|
||||
}
|
@ -11,20 +11,30 @@ import me.filoghost.fcommons.config.ConfigSection;
|
||||
import me.filoghost.fcommons.config.ConfigType;
|
||||
import me.filoghost.fcommons.config.ConfigValue;
|
||||
import me.filoghost.fcommons.config.FileConfig;
|
||||
import me.filoghost.fcommons.config.exception.ConfigLoadException;
|
||||
import me.filoghost.fcommons.config.exception.ConfigSaveException;
|
||||
import me.filoghost.fcommons.config.exception.ConfigException;
|
||||
import me.filoghost.fcommons.logging.ErrorCollector;
|
||||
import me.filoghost.holographicdisplays.plugin.config.ConfigManager;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
|
||||
public class LegacyDatabaseUpgrade {
|
||||
public class DatabaseLegacyUpgrade extends LegacyUpgrade implements LegacyUpgradeTask {
|
||||
|
||||
public static void run(ConfigManager configManager) throws ConfigLoadException, ConfigSaveException, IOException {
|
||||
ConfigLoader databaseConfigLoader = configManager.getConfigLoader("database.yml");
|
||||
private final ConfigLoader databaseConfigLoader;
|
||||
|
||||
public DatabaseLegacyUpgrade(ConfigManager configManager, ErrorCollector errorCollector) {
|
||||
super(configManager, errorCollector);
|
||||
this.databaseConfigLoader = configManager.getConfigLoader("database.yml");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Path getFile() {
|
||||
return databaseConfigLoader.getFile();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() throws ConfigException {
|
||||
if (!databaseConfigLoader.fileExists()) {
|
||||
return; // Database doesn't exist yet, nothing to convert
|
||||
return; // Database file doesn't exist, nothing to upgrade
|
||||
}
|
||||
|
||||
FileConfig databaseConfig = databaseConfigLoader.load();
|
||||
@ -42,12 +52,12 @@ public class LegacyDatabaseUpgrade {
|
||||
}
|
||||
|
||||
if (changed) {
|
||||
Files.copy(databaseConfigLoader.getFile(), LegacyUpgradeUtils.getBackupFile(databaseConfigLoader.getFile()));
|
||||
createBackupFile(databaseConfigLoader.getFile());
|
||||
databaseConfigLoader.save(databaseConfig);
|
||||
}
|
||||
}
|
||||
|
||||
private static ConfigSection convertLegacySerializedLocation(String legacySerializedLocation) {
|
||||
private ConfigSection convertLegacySerializedLocation(String legacySerializedLocation) {
|
||||
String[] legacyLocationParts = Strings.splitAndTrim(legacySerializedLocation, ",");
|
||||
|
||||
ConfigSection positionSection = new ConfigSection();
|
@ -1,81 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) filoghost and contributors
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
package me.filoghost.holographicdisplays.plugin.config.upgrade;
|
||||
|
||||
import me.filoghost.fcommons.config.Config;
|
||||
import me.filoghost.fcommons.logging.ErrorCollector;
|
||||
import me.filoghost.holographicdisplays.plugin.config.ConfigManager;
|
||||
import me.filoghost.holographicdisplays.plugin.util.FileUtils;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.util.List;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public class LegacyAnimationsUpgrade {
|
||||
|
||||
private static final String SPEED_PREFIX = "speed:";
|
||||
|
||||
public static void run(ConfigManager configManager, ErrorCollector errorCollector) throws IOException {
|
||||
Path animationFolder = configManager.getAnimationsFolder();
|
||||
|
||||
if (!Files.isDirectory(animationFolder)) {
|
||||
return;
|
||||
}
|
||||
|
||||
try (Stream<Path> animationFiles = Files.list(animationFolder)) {
|
||||
animationFiles.filter(Files::isRegularFile).forEach(file -> convertFile(file, configManager, errorCollector));
|
||||
}
|
||||
}
|
||||
|
||||
private static void convertFile(Path oldFile, ConfigManager configManager, ErrorCollector errorCollector) {
|
||||
if (LegacyUpgradeUtils.isBackupFile(oldFile)) {
|
||||
return; // Ignore backup files
|
||||
}
|
||||
|
||||
try {
|
||||
List<String> lines = Files.readAllLines(oldFile);
|
||||
if (lines.size() == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Remove the first line that only contains the speed
|
||||
String firstLine = lines.remove(0).trim();
|
||||
if (!firstLine.toLowerCase().startsWith(SPEED_PREFIX)) {
|
||||
return; // Not a valid animation
|
||||
}
|
||||
|
||||
String newFileName = oldFile.getFileName().toString();
|
||||
if (FileUtils.hasFileExtension(newFileName, "txt")) {
|
||||
newFileName = FileUtils.removeFileExtension(newFileName);
|
||||
}
|
||||
newFileName += ".yml";
|
||||
Path newFile = oldFile.resolveSibling(newFileName);
|
||||
|
||||
if (Files.isRegularFile(newFile)) {
|
||||
return; // Already created, do not override
|
||||
}
|
||||
|
||||
double speed;
|
||||
try {
|
||||
speed = Double.parseDouble(firstLine.substring(SPEED_PREFIX.length()).trim());
|
||||
} catch (NumberFormatException e) {
|
||||
speed = 0.5;
|
||||
}
|
||||
|
||||
Config config = new Config();
|
||||
config.setDouble("interval-seconds", speed);
|
||||
config.setStringList("animation-frames", lines);
|
||||
configManager.getConfigLoader(newFile).save(config);
|
||||
|
||||
Files.move(oldFile, LegacyUpgradeUtils.getBackupFile(oldFile));
|
||||
} catch (Exception e) {
|
||||
errorCollector.add(e, "couldn't automatically convert animation file \"" + oldFile.getFileName() + "\" to the new format");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,86 @@
|
||||
/*
|
||||
* Copyright (C) filoghost and contributors
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
package me.filoghost.holographicdisplays.plugin.config.upgrade;
|
||||
|
||||
import me.filoghost.fcommons.Preconditions;
|
||||
import me.filoghost.fcommons.config.exception.ConfigException;
|
||||
import me.filoghost.fcommons.logging.ErrorCollector;
|
||||
import me.filoghost.holographicdisplays.plugin.config.ConfigManager;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
|
||||
public abstract class LegacyUpgrade implements LegacyUpgradeTask {
|
||||
|
||||
protected final ConfigManager configManager;
|
||||
private final ErrorCollector errorCollector;
|
||||
private final Path rootDataFolder;
|
||||
private final Path backupsFolder;
|
||||
|
||||
public LegacyUpgrade(ConfigManager configManager, ErrorCollector errorCollector) {
|
||||
this.configManager = configManager;
|
||||
this.errorCollector = errorCollector;
|
||||
this.rootDataFolder = configManager.getRootDataFolder();
|
||||
this.backupsFolder = rootDataFolder.resolve("old-files");
|
||||
}
|
||||
|
||||
protected abstract Path getFile();
|
||||
|
||||
public final void tryRun() {
|
||||
tryRun(getFile(), this);
|
||||
}
|
||||
|
||||
protected final void tryRun(Path file, LegacyUpgradeTask task) {
|
||||
try {
|
||||
task.run();
|
||||
} catch (IOException | ConfigException e) {
|
||||
errorCollector.add(e, "error while upgrading \"" + configManager.formatPath(file) + "\" to the new format");
|
||||
}
|
||||
}
|
||||
|
||||
protected final void createBackupFile(Path file) {
|
||||
Preconditions.checkArgument(file.startsWith(rootDataFolder), "file is outside data folder");
|
||||
Preconditions.checkArgument(!file.startsWith(backupsFolder), "file is inside backups folder");
|
||||
|
||||
Path pathFromRootDataFolderToFile = file.subpath(rootDataFolder.getNameCount(), file.getNameCount());
|
||||
Path backupFile = backupsFolder.resolve(pathFromRootDataFolderToFile);
|
||||
|
||||
// Find the first available destination file if already existing
|
||||
int copyIndex = 1;
|
||||
while (Files.isRegularFile(backupFile)) {
|
||||
backupFile = getAlternativeCopyFile(backupFile, copyIndex);
|
||||
copyIndex++;
|
||||
}
|
||||
|
||||
try {
|
||||
Files.createDirectories(backupFile.getParent());
|
||||
Files.copy(file, backupFile);
|
||||
} catch (IOException e) {
|
||||
errorCollector.add(e, "error while copying file \"" + configManager.formatPath(file) + "\""
|
||||
+ " to \"" + configManager.formatPath(backupsFolder) + "\"");
|
||||
}
|
||||
}
|
||||
|
||||
private Path getAlternativeCopyFile(Path file, int copyIndex) {
|
||||
String fileName = file.getFileName().toString();
|
||||
int extensionBeginIndex = fileName.lastIndexOf('.');
|
||||
String fileNameWithoutExtension;
|
||||
String extensionWithSeparator;
|
||||
|
||||
if (extensionBeginIndex >= 0) {
|
||||
fileNameWithoutExtension = fileName.substring(0, extensionBeginIndex);
|
||||
extensionWithSeparator = fileName.substring(extensionBeginIndex);
|
||||
} else {
|
||||
fileNameWithoutExtension = fileName;
|
||||
extensionWithSeparator = "";
|
||||
}
|
||||
|
||||
// Insert the copy index before the extension
|
||||
return file.resolveSibling(fileNameWithoutExtension + " (" + copyIndex + ")" + extensionWithSeparator);
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) filoghost and contributors
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
package me.filoghost.holographicdisplays.plugin.config.upgrade;
|
||||
|
||||
import me.filoghost.fcommons.config.exception.ConfigException;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
public interface LegacyUpgradeTask {
|
||||
|
||||
void run() throws IOException, ConfigException;
|
||||
|
||||
}
|
@ -1,22 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) filoghost and contributors
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
package me.filoghost.holographicdisplays.plugin.config.upgrade;
|
||||
|
||||
import me.filoghost.holographicdisplays.plugin.util.FileUtils;
|
||||
|
||||
import java.nio.file.Path;
|
||||
|
||||
class LegacyUpgradeUtils {
|
||||
|
||||
static Path getBackupFile(Path file) {
|
||||
return file.resolveSibling(file.getFileName() + ".backup");
|
||||
}
|
||||
|
||||
static boolean isBackupFile(Path file) {
|
||||
return FileUtils.hasFileExtension(file, "backup");
|
||||
}
|
||||
|
||||
}
|
@ -11,8 +11,8 @@ import me.filoghost.fcommons.config.ConfigErrors;
|
||||
import me.filoghost.fcommons.config.ConfigLoader;
|
||||
import me.filoghost.fcommons.config.ConfigPath;
|
||||
import me.filoghost.fcommons.config.ConfigSection;
|
||||
import me.filoghost.fcommons.config.exception.ConfigException;
|
||||
import me.filoghost.fcommons.config.exception.ConfigLoadException;
|
||||
import me.filoghost.fcommons.config.exception.ConfigSaveException;
|
||||
import me.filoghost.fcommons.logging.ErrorCollector;
|
||||
import me.filoghost.holographicdisplays.plugin.config.ConfigManager;
|
||||
import org.apache.commons.lang.StringEscapeUtils;
|
||||
@ -22,19 +22,31 @@ import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.util.List;
|
||||
|
||||
public class LegacySymbolsUpgrade {
|
||||
public class SymbolsLegacyUpgrade extends LegacyUpgrade {
|
||||
|
||||
public static void run(ConfigManager configManager, ErrorCollector errorCollector) throws ConfigLoadException, ConfigSaveException {
|
||||
Path oldFile = configManager.getRootDataFolder().resolve("symbols.yml");
|
||||
private final Path oldFile;
|
||||
|
||||
public SymbolsLegacyUpgrade(ConfigManager configManager, ErrorCollector errorCollector) {
|
||||
super(configManager, errorCollector);
|
||||
this.oldFile = configManager.getRootDataFolder().resolve("symbols.yml");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Path getFile() {
|
||||
return oldFile;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() throws IOException, ConfigException {
|
||||
ConfigLoader newConfigLoader = configManager.getConfigLoader("custom-placeholders.yml");
|
||||
Path newFile = newConfigLoader.getFile();
|
||||
|
||||
if (!Files.isRegularFile(oldFile)) {
|
||||
return; // Old file doesn't exist, ignore upgrade
|
||||
return; // Old file doesn't exist, nothing to upgrade
|
||||
}
|
||||
|
||||
if (Files.isRegularFile(newFile)) {
|
||||
return; // Already created, do not override
|
||||
return; // Already existing, do not override
|
||||
}
|
||||
|
||||
Config newConfig = new Config();
|
||||
@ -55,37 +67,32 @@ public class LegacySymbolsUpgrade {
|
||||
|
||||
// Ignore bad line
|
||||
if (!line.contains(":")) {
|
||||
errorCollector.add("couldn't convert invalid line in " + oldFile.getFileName() + ": " + line);
|
||||
continue;
|
||||
}
|
||||
|
||||
String[] parts = Strings.splitAndTrim(line, ":", 2);
|
||||
String placeholder = unquote(parts[0]);
|
||||
String replacement = StringEscapeUtils.unescapeJava(unquote(parts[1]));
|
||||
String[] placeholderAndReplacement = Strings.splitAndTrim(line, ":", 2);
|
||||
String placeholder = unquote(placeholderAndReplacement[0]);
|
||||
String replacement = StringEscapeUtils.unescapeJava(unquote(placeholderAndReplacement[1]));
|
||||
|
||||
placeholdersSection.setString(ConfigPath.literal(placeholder), replacement);
|
||||
}
|
||||
|
||||
try {
|
||||
Files.move(oldFile, LegacyUpgradeUtils.getBackupFile(oldFile));
|
||||
} catch (IOException e) {
|
||||
errorCollector.add(e, "couldn't rename " + oldFile.getFileName());
|
||||
}
|
||||
createBackupFile(oldFile);
|
||||
newConfigLoader.save(newConfig);
|
||||
Files.delete(oldFile);
|
||||
}
|
||||
|
||||
private static String unquote(String input) {
|
||||
if (input.length() < 2) {
|
||||
// Too short, cannot be a quoted string
|
||||
// Too short to be a quoted string
|
||||
return input;
|
||||
}
|
||||
if (input.startsWith("'") && input.endsWith("'")) {
|
||||
return input.substring(1, input.length() - 1);
|
||||
} else if (input.startsWith("\"") && input.endsWith("\"")) {
|
||||
return input.substring(1, input.length() - 1);
|
||||
}
|
||||
|
||||
return input;
|
||||
if ((input.startsWith("'") && input.endsWith("'")) || (input.startsWith("\"") && input.endsWith("\""))) {
|
||||
return input.substring(1, input.length() - 1);
|
||||
} else {
|
||||
return input;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
Loading…
Reference in New Issue
Block a user