mirror of
https://github.com/VolmitSoftware/Iris.git
synced 2026-08-27 04:37:47 +00:00
Fixes
This commit is contained in:
+18
-6
@@ -42,12 +42,14 @@ public final class ModdedPackInstaller {
|
||||
}
|
||||
|
||||
public static boolean install(Path configDir, String pack, String branch,
|
||||
boolean forceOverwrite, Consumer<String> feedback) {
|
||||
boolean forceOverwrite, boolean refreshDatapack,
|
||||
Consumer<String> feedback) {
|
||||
if (pack == null || !PACK_NAME.matcher(pack).matches()) {
|
||||
feedback.accept(IrisLanguage.plain(PackDownloadMessages.INVALID_PACK_NAME, MessageArgument.untrusted("pack", String.valueOf(pack))));
|
||||
return false;
|
||||
}
|
||||
if (branch == null || !BRANCH_NAME.matcher(branch).matches()) {
|
||||
boolean managedBeta = PackDownloader.isManagedBetaPack(pack);
|
||||
if (!acceptsBranch(pack, branch)) {
|
||||
feedback.accept(IrisLanguage.plain(PackDownloadMessages.INVALID_BRANCH_NAME, MessageArgument.untrusted("branch", String.valueOf(branch))));
|
||||
return false;
|
||||
}
|
||||
@@ -56,8 +58,8 @@ public final class ModdedPackInstaller {
|
||||
synchronized (installLock) {
|
||||
File packs = configDir.resolve("irisworldgen").resolve("packs").toFile();
|
||||
try {
|
||||
PackDownloader.PackInstallResult result = PackDownloader.isDefaultOverworld(pack)
|
||||
? PackDownloader.downloadDefaultOverworld(packs, forceOverwrite, feedback)
|
||||
PackDownloader.PackInstallResult result = managedBeta
|
||||
? PackDownloader.downloadManagedBeta(packs, pack, forceOverwrite, feedback)
|
||||
: PackDownloader.download(
|
||||
packs,
|
||||
"IrisDimensions/" + pack,
|
||||
@@ -67,7 +69,7 @@ public final class ModdedPackInstaller {
|
||||
pack,
|
||||
feedback);
|
||||
boolean installed = result != null;
|
||||
if (result != null && result.changed()) {
|
||||
if (shouldRefreshDatapack(result, refreshDatapack)) {
|
||||
// Pack-install completion is one of the four forced-datapack regeneration triggers; every
|
||||
// install call site already runs off the server thread, so regenerate inline here. A
|
||||
// regeneration failure must never turn a successful install into a failed one.
|
||||
@@ -82,7 +84,8 @@ public final class ModdedPackInstaller {
|
||||
}
|
||||
return installed;
|
||||
} catch (IOException error) {
|
||||
LOGGER.error("Iris pack download failed for IrisDimensions/{} ({})", pack, branch, error);
|
||||
String source = managedBeta ? "beta release" : "branch " + branch;
|
||||
LOGGER.error("Iris pack download failed for IrisDimensions/{} ({})", pack, source, error);
|
||||
feedback.accept(IrisLanguage.plain(
|
||||
PackDownloadMessages.DOWNLOAD_FAILED,
|
||||
MessageArgument.untrusted("type", error.getClass().getSimpleName()),
|
||||
@@ -92,4 +95,13 @@ public final class ModdedPackInstaller {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static boolean acceptsBranch(String pack, String branch) {
|
||||
return PackDownloader.isManagedBetaPack(pack)
|
||||
|| (branch != null && BRANCH_NAME.matcher(branch).matches());
|
||||
}
|
||||
|
||||
static boolean shouldRefreshDatapack(PackDownloader.PackInstallResult result, boolean refreshDatapack) {
|
||||
return result != null && result.changed() && refreshDatapack;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -37,6 +37,7 @@ import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.nio.file.attribute.BasicFileAttributes;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
@@ -253,20 +254,39 @@ public final class ModdedStartup {
|
||||
if (!config.autoDownloadDefaultPack()) {
|
||||
return;
|
||||
}
|
||||
String pack = config.defaultPack();
|
||||
Path configDir = ModdedEngineBootstrap.loader().configDir();
|
||||
File packFolder = new File(ModdedPackCommands.packsRoot(), pack);
|
||||
if (new File(packFolder, "dimensions/" + pack + ".json").isFile()) {
|
||||
return;
|
||||
}
|
||||
String source = "master branch";
|
||||
LOGGER.info("Iris default pack '{}' missing; downloading IrisDimensions/{} ({})", pack, pack, source);
|
||||
boolean installed = ModdedPackInstaller.install(
|
||||
configDir, pack, "master", false,
|
||||
(String line) -> LOGGER.info("Iris: {}", line));
|
||||
if (!installed) {
|
||||
LOGGER.warn("Iris default pack '{}' could not be downloaded; install it with /iris download {}", pack, pack);
|
||||
File packsRoot = ModdedPackCommands.packsRoot();
|
||||
for (String pack : startupPacks(config.defaultPack())) {
|
||||
ensureStartupPack(configDir, packsRoot, pack);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static List<String> startupPacks(String configuredDefault) {
|
||||
LinkedHashSet<String> packs = new LinkedHashSet<>(PackDownloader.managedBetaPacks());
|
||||
if (configuredDefault != null && !configuredDefault.isBlank()) {
|
||||
packs.add(configuredDefault);
|
||||
}
|
||||
return List.copyOf(packs);
|
||||
}
|
||||
|
||||
private static void ensureStartupPack(Path configDir, File packsRoot, String pack) {
|
||||
boolean present = PackDownloader.isManagedBetaPack(pack)
|
||||
? PackDownloader.isManagedBetaPackPresent(packsRoot, pack)
|
||||
: PackDownloader.isPackPresent(packsRoot, pack);
|
||||
if (present) {
|
||||
return;
|
||||
}
|
||||
boolean managedBeta = PackDownloader.isManagedBetaPack(pack);
|
||||
String branch = managedBeta ? "beta" : "master";
|
||||
String source = managedBeta ? "beta release" : "master branch";
|
||||
String role = managedBeta ? "managed beta pack" : "default pack";
|
||||
LOGGER.info("Iris {} '{}' missing; downloading IrisDimensions/{} ({})", role, pack, pack, source);
|
||||
boolean installed = ModdedPackInstaller.install(
|
||||
configDir, pack, branch, false, false,
|
||||
(String line) -> LOGGER.info("Iris: {}", line));
|
||||
if (!installed) {
|
||||
LOGGER.warn("Iris {} '{}' could not be downloaded; install it with /iris download {}", role, pack, pack);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+3
-3
@@ -258,8 +258,8 @@ public final class IrisModdedCommands {
|
||||
|
||||
static int download(CommandSourceStack source, String pack,
|
||||
String branch, boolean forceOverwrite) {
|
||||
boolean defaultOverworld = PackDownloader.isDefaultOverworld(pack);
|
||||
String baseDownloadSource = defaultOverworld ? "beta release" : "branch " + branch;
|
||||
boolean managedBeta = PackDownloader.isManagedBetaPack(pack);
|
||||
String baseDownloadSource = managedBeta ? "beta release" : "branch " + branch;
|
||||
String downloadSource = forceOverwrite
|
||||
? baseDownloadSource + IrisLanguage.plain(RuntimeUiMessages.DOWNLOAD_OVERWRITE_SUFFIX)
|
||||
: baseDownloadSource;
|
||||
@@ -274,7 +274,7 @@ public final class IrisModdedCommands {
|
||||
}
|
||||
scheduler.async(() -> {
|
||||
boolean installed = ModdedPackInstaller.install(
|
||||
ModdedEngineBootstrap.loader().configDir(), pack, branch, forceOverwrite,
|
||||
ModdedEngineBootstrap.loader().configDir(), pack, branch, forceOverwrite, true,
|
||||
(String message) -> scheduler.global(() -> ok(source, message)));
|
||||
if (installed) {
|
||||
scheduler.global(() -> ok(source, IrisLanguage.plain(ModdedCommandMessages.IRIS_MODDED_COMMANDS_PACK_INSTALLED_ITS_EXACT_DIMENSION_TYPES_CUSTOM_BIOMES_JOIN_FORCED, MessageArgument.untrusted("pack", pack))));
|
||||
|
||||
+2
-2
@@ -383,7 +383,7 @@ public final class ModdedStudioCommands {
|
||||
File packFolder = new File(ModdedPackCommands.packsRoot(), pack);
|
||||
if (!new File(packFolder, "dimensions/" + pack + ".json").isFile()) {
|
||||
server.execute(() -> IrisModdedCommands.ok(source, IrisLanguage.plain(ModdedCommandMessages.MODDED_STUDIO_COMMANDS_PACK_MISSING_DOWNLOADING_IRISDIMENSIONS, MessageArgument.untrusted("pack", pack), MessageArgument.untrusted("pack2", pack))));
|
||||
boolean installed = ModdedPackInstaller.install(ModdedEngineBootstrap.loader().configDir(), pack, "master", false,
|
||||
boolean installed = ModdedPackInstaller.install(ModdedEngineBootstrap.loader().configDir(), pack, "master", false, true,
|
||||
(String line) -> server.execute(() -> IrisModdedCommands.ok(source, line)));
|
||||
if (!installed || !new File(packFolder, "dimensions/" + pack + ".json").isFile()) {
|
||||
server.execute(() -> IrisModdedCommands.fail(source, IrisLanguage.plain(ModdedCommandMessages.MODDED_STUDIO_COMMANDS_PACK_COULD_NOT_BE_DOWNLOADED_CHECK_NAME_TRY_IRIS_DOWNLOAD, MessageArgument.untrusted("pack", pack), MessageArgument.untrusted("pack2", pack))));
|
||||
@@ -588,7 +588,7 @@ public final class ModdedStudioCommands {
|
||||
File templateFolder = new File(packsRoot, template);
|
||||
if (!new File(templateFolder, "dimensions/" + template + ".json").isFile()) {
|
||||
server.execute(() -> IrisModdedCommands.ok(source, IrisLanguage.plain(ModdedCommandMessages.MODDED_STUDIO_COMMANDS_TEMPLATE_IS_NOT_INSTALLED_DOWNLOADING_IRISDIMENSIONS, MessageArgument.untrusted("template", template), MessageArgument.untrusted("template2", template))));
|
||||
boolean installed = ModdedPackInstaller.install(ModdedEngineBootstrap.loader().configDir(), template, "master", false,
|
||||
boolean installed = ModdedPackInstaller.install(ModdedEngineBootstrap.loader().configDir(), template, "master", false, true,
|
||||
(String line) -> server.execute(() -> IrisModdedCommands.ok(source, line)));
|
||||
if (!installed || !new File(templateFolder, "dimensions/" + template + ".json").isFile()) {
|
||||
server.execute(() -> IrisModdedCommands.fail(source, IrisLanguage.plain(ModdedCommandMessages.MODDED_STUDIO_COMMANDS_TEMPLATE_COULD_NOT_BE_DOWNLOADED_INSTALL_PACK_WITH_DIMENSIONS_JSON, MessageArgument.untrusted("template", template), MessageArgument.untrusted("template2", template))));
|
||||
|
||||
+2
-2
@@ -177,7 +177,7 @@ public final class ModdedWorldCommands {
|
||||
}
|
||||
IrisModdedCommands.ok(source, IrisLanguage.plain(ModdedCommandMessages.MODDED_WORLD_COMMANDS_PACK_IS_NOT_INSTALLED_DOWNLOADING_IRISDIMENSIONS, MessageArgument.untrusted("pack", pack), MessageArgument.untrusted("pack2", pack)));
|
||||
Thread thread = new Thread(() -> {
|
||||
boolean installed = ModdedPackInstaller.install(ModdedEngineBootstrap.loader().configDir(), pack, "master", false,
|
||||
boolean installed = ModdedPackInstaller.install(ModdedEngineBootstrap.loader().configDir(), pack, "master", false, true,
|
||||
(String line) -> server.execute(() -> IrisModdedCommands.ok(source, line)));
|
||||
server.execute(() -> {
|
||||
if (!installed || !packFolder.isDirectory()) {
|
||||
@@ -280,7 +280,7 @@ public final class ModdedWorldCommands {
|
||||
}
|
||||
IrisModdedCommands.ok(source, IrisLanguage.plain(ModdedCommandMessages.MODDED_WORLD_COMMANDS_PACK_IS_NOT_INSTALLED_DOWNLOADING_IRISDIMENSIONS_2, MessageArgument.untrusted("pack", pack), MessageArgument.untrusted("pack2", pack)));
|
||||
Thread thread = new Thread(() -> {
|
||||
boolean installed = ModdedPackInstaller.install(ModdedEngineBootstrap.loader().configDir(), pack, "master", false,
|
||||
boolean installed = ModdedPackInstaller.install(ModdedEngineBootstrap.loader().configDir(), pack, "master", false, true,
|
||||
(String line) -> server.execute(() -> IrisModdedCommands.ok(source, line)));
|
||||
server.execute(() -> {
|
||||
if (!installed || !packFolder.isDirectory()) {
|
||||
|
||||
+52
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* Iris is a World Generator for Minecraft Servers
|
||||
* Copyright (c) 2026 Arcane Arts (Volmit Software)
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package art.arcane.iris.modded;
|
||||
|
||||
import art.arcane.iris.core.pack.PackDownloader;
|
||||
import org.junit.Test;
|
||||
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
public class ModdedPackInstallerTest {
|
||||
@Test
|
||||
public void managedBetaPacksIgnoreTheRequestedBranch() {
|
||||
assertTrue(ModdedPackInstaller.acceptsBranch("overworld", null));
|
||||
assertTrue(ModdedPackInstaller.acceptsBranch("underworld", "feature/arbitrary"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void nonManagedPacksStillRequireAValidBranch() {
|
||||
assertTrue(ModdedPackInstaller.acceptsBranch("custom", "stable"));
|
||||
assertFalse(ModdedPackInstaller.acceptsBranch("custom", null));
|
||||
assertFalse(ModdedPackInstaller.acceptsBranch("custom", "feature/arbitrary"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void startupBatchDefersDatapackRefresh() {
|
||||
PackDownloader.PackInstallResult changed = new PackDownloader.PackInstallResult("underworld", true, true);
|
||||
|
||||
assertFalse(ModdedPackInstaller.shouldRefreshDatapack(changed, false));
|
||||
assertTrue(ModdedPackInstaller.shouldRefreshDatapack(changed, true));
|
||||
assertFalse(ModdedPackInstaller.shouldRefreshDatapack(
|
||||
new PackDownloader.PackInstallResult("underworld", false, false),
|
||||
true
|
||||
));
|
||||
}
|
||||
}
|
||||
+41
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
* Iris is a World Generator for Minecraft Servers
|
||||
* Copyright (c) 2026 Arcane Arts (Volmit Software)
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package art.arcane.iris.modded;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
|
||||
public class ModdedStartupPackSelectionTest {
|
||||
@Test
|
||||
public void managedBetaPacksAreAlwaysInstalledInStableOrder() {
|
||||
assertEquals(List.of("overworld", "underworld"), ModdedStartup.startupPacks("overworld"));
|
||||
assertEquals(List.of("overworld", "underworld"), ModdedStartup.startupPacks("underworld"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configuredNonManagedDefaultIsInstalledAfterManagedBetaPacks() {
|
||||
assertEquals(
|
||||
List.of("overworld", "underworld", "custom"),
|
||||
ModdedStartup.startupPacks("custom")
|
||||
);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user