All libraries can be downloaded by MultiMC now.

This commit is contained in:
ZekerZhayard 2020-03-27 14:11:43 +08:00
parent 812a810acc
commit fb8888aed9
6 changed files with 63 additions and 45 deletions

View file

@ -5,16 +5,14 @@ apply plugin: "idea"
sourceCompatibility = targetCompatibility = 1.8
version = "1.3.1"
version = "1.4.0"
group = "io.github.zekerzhayard"
archivesBaseName = rootProject.name
repositories {
mavenCentral()
jcenter()
maven {
name = "forge"
url = "https://files.minecraftforge.net/maven"
url = "https://files.minecraftforge.net/maven/"
}
}

View file

@ -10,6 +10,7 @@ import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;
@ -24,12 +25,13 @@ import com.google.gson.JsonParser;
import io.github.zekerzhayard.forgewrapper.Utils;
public class Converter {
public static void convert(Path installerPath, Path targetDir, String cursepack) throws Exception {
public static void convert(Path installerPath, Path targetDir, Path multimcDir, String cursepack) throws Exception {
if (cursepack != null) {
installerPath = getForgeInstallerFromCursePack(cursepack);
}
JsonObject installer = getJsonFromZip(installerPath, "version.json");
JsonObject installProfile = getJsonFromZip(installerPath, "install_profile.json");
List<String> arguments = getAdditionalArgs(installer);
String mcVersion = arguments.get(arguments.indexOf("--fml.mcVersion") + 1);
String forgeVersion = arguments.get(arguments.indexOf("--fml.forgeVersion") + 1);
@ -38,7 +40,7 @@ public class Converter {
StringBuilder wrapperVersion = new StringBuilder();
JsonObject pack = convertPackJson(mcVersion);
JsonObject patches = convertPatchesJson(installer, mcVersion, forgeVersion, wrapperVersion, cursepack);
JsonObject patches = convertPatchesJson(installer, installProfile, mcVersion, forgeVersion, wrapperVersion, cursepack);
Files.createDirectories(targetDir);
@ -71,10 +73,12 @@ public class Converter {
}
}
// Copy forge installer to <instance>/.minecraft/.forgewrapper folder.
Path forgeWrapperPath = minecraftPath.resolve(".forgewrapper");
Files.createDirectories(forgeWrapperPath);
Files.copy(installerPath, forgeWrapperPath.resolve(forgeFullVersion + "-installer.jar"), StandardCopyOption.REPLACE_EXISTING);
// Copy forge installer to MultiMC/libraries/net/minecraftforge/forge/<mcVersion>-<forgeVersion> folder.
if (multimcDir != null) {
Path targetInstallerPath = multimcDir.resolve("net").resolve("minecraftforge").resolve("forge").resolve(forgeVersion);
Files.createDirectories(targetInstallerPath);
Files.copy(installerPath, targetInstallerPath.resolve(forgeFullVersion + "-installer.jar"), StandardCopyOption.REPLACE_EXISTING);
}
}
public static List<String> getAdditionalArgs(JsonObject installer) {
@ -138,13 +142,18 @@ public class Converter {
// - Add libraries
// - Add forge-launcher url
// - Replace Minecraft & Forge versions
private static JsonObject convertPatchesJson(JsonObject installer, String mcVersion, String forgeVersion, StringBuilder wrapperVersion, String cursepack) {
private static JsonObject convertPatchesJson(JsonObject installer, JsonObject installProfile, String mcVersion, String forgeVersion, StringBuilder wrapperVersion, String cursepack) {
JsonObject patches = new JsonParser().parse(new InputStreamReader(Converter.class.getResourceAsStream("/patches/net.minecraftforge.json"))).getAsJsonObject();
JsonArray mavenFiles = getElement(patches, "mavenFiles").getAsJsonArray();
JsonArray libraries = getElement(patches, "libraries").getAsJsonArray();
String minecraftArguments = String.join(" ", getElement(patches, "minecraftArguments").getAsString(), "--username ${auth_player_name} --version ${version_name} --gameDir ${game_directory} --assetsDir ${assets_root} --assetIndex ${assets_index_name} --uuid ${auth_uuid} --accessToken ${auth_access_token} --userType ${user_type} --versionType ${version_type}", String.join(" ", getAdditionalArgs(installer))).trim();
patches.addProperty("minecraftArguments", minecraftArguments);
for (JsonElement mavenFile : mavenFiles) {
String name = getElement(mavenFile.getAsJsonObject(), "name").getAsString();
mavenFile.getAsJsonObject().addProperty("name", name.replace("{VERSION}", mcVersion).replace("{FORGE_VERSION}", forgeVersion));
}
for (JsonElement lib : libraries) {
String name = getElement(lib.getAsJsonObject(), "name").getAsString();
if (name.startsWith("io.github.zekerzhayard:ForgeWrapper:")) {
@ -157,14 +166,13 @@ public class Converter {
cursepacklocator.addProperty("url", "https://files.minecraftforge.net/maven/");
libraries.add(cursepacklocator);
}
for (JsonElement lib : getElement(installer ,"libraries").getAsJsonArray()) {
JsonObject artifact = getElement(getElement(lib.getAsJsonObject(), "downloads").getAsJsonObject(), "artifact").getAsJsonObject();
String path = getElement(artifact, "path").getAsString();
if (path.equals(String.format("net/minecraftforge/forge/%s-%s/forge-%s-%s.jar", mcVersion, forgeVersion, mcVersion, forgeVersion))) {
artifact.getAsJsonObject().addProperty("url", "https://files.minecraftforge.net/maven/" + path.replace(".jar", "-launcher.jar"));
}
libraries.add(lib);
}
Map<String, String> additionalUrls = new HashMap<>();
String path = String.format("net/minecraftforge/forge/%s-%s/forge-%s-%s", mcVersion, forgeVersion, mcVersion, forgeVersion);
additionalUrls.put(path + "-universal.jar", "https://files.minecraftforge.net/maven/" + path + "-universal.jar");
transformLibraries(getElement(installProfile, "libraries").getAsJsonArray(), mavenFiles, additionalUrls);
additionalUrls.clear();
additionalUrls.put(path + ".jar", "https://files.minecraftforge.net/maven/" + path + "-launcher.jar");
transformLibraries(getElement(installer ,"libraries").getAsJsonArray(), libraries, additionalUrls);
patches.addProperty("version", forgeVersion);
for (JsonElement require : getElement(patches, "requires").getAsJsonArray()) {
@ -183,4 +191,15 @@ public class Converter {
}
return JsonNull.INSTANCE;
}
private static void transformLibraries(JsonArray source, JsonArray target, Map<String, String> additionalUrls) {
for (JsonElement lib : source) {
JsonObject artifact = getElement(getElement(lib.getAsJsonObject(), "downloads").getAsJsonObject(), "artifact").getAsJsonObject();
String path = getElement(artifact, "path").getAsString();
if (additionalUrls.containsKey(path)) {
artifact.getAsJsonObject().addProperty("url", additionalUrls.get(path));
}
target.add(lib);
}
}
}

View file

@ -10,7 +10,7 @@ import io.github.zekerzhayard.forgewrapper.Utils;
public class Main {
public static void main(String[] args) {
Path installer = null, instance = Paths.get(".");
Path installer = null, instance = Paths.get("."), multimc = null;
String cursepack = null;
try {
HashMap<String, String> argsMap = parseArgs(args);
@ -22,6 +22,7 @@ public class Main {
}
if (argsMap.containsKey("--instance")) {
instance = Paths.get(argsMap.get("--instance"));
multimc = instance.getParent();
}
if (argsMap.containsKey("--cursepack")) {
cursepack = argsMap.get("--cursepack");
@ -36,7 +37,7 @@ public class Main {
Converter.class.getProtectionDomain().getCodeSource().getLocation(),
installer.toUri().toURL()
}, null);
ucl.loadClass("io.github.zekerzhayard.forgewrapper.converter.Converter").getMethod("convert", Path.class, Path.class, String.class).invoke(null, installer, instance, cursepack);
ucl.loadClass("io.github.zekerzhayard.forgewrapper.converter.Converter").getMethod("convert", Path.class, Path.class, Path.class, String.class).invoke(null, installer, instance, multimc, cursepack);
System.out.println("Successfully install Forge for MultiMC!");
} catch (Exception e) {
System.out.println("Failed to install Forge!");

View file

@ -3,7 +3,6 @@ package io.github.zekerzhayard.forgewrapper.installer;
import java.io.File;
import java.util.function.Predicate;
import net.minecraftforge.installer.actions.ActionCanceledException;
import net.minecraftforge.installer.actions.ClientInstall;
import net.minecraftforge.installer.actions.ProgressCallback;
import net.minecraftforge.installer.json.Install;
@ -17,16 +16,6 @@ public class ClientInstall4MultiMC extends ClientInstall {
public boolean run(File target, Predicate<String> optionals) {
File librariesDir = Main.getLibrariesDir();
File clientTarget = new File(String.format("%s/com/mojang/minecraft/%s/minecraft-%s-client.jar", librariesDir.getAbsolutePath(), this.profile.getMinecraft(), this.profile.getMinecraft()));
boolean downloadLibraries = true; // Force true when without an internet connection.
try {
downloadLibraries = this.downloadLibraries(librariesDir, optionals);
} catch (ActionCanceledException e) {
e.printStackTrace();
}
if (!downloadLibraries) {
return false;
}
return this.processors.process(librariesDir, clientTarget);
}
}

View file

@ -11,25 +11,23 @@ import java.util.stream.Collectors;
import java.util.stream.Stream;
import cpw.mods.modlauncher.Launcher;
import io.github.zekerzhayard.forgewrapper.Utils;
public class Main {
public static void main(String[] args) throws Exception {
List<String> argsList = Stream.of(args).collect(Collectors.toList());
String version = argsList.get(argsList.indexOf("--fml.mcVersion") + 1) + "-" + argsList.get(argsList.indexOf("--fml.forgeVersion") + 1);
Path forgeDir = getLibrariesDir().toPath().resolve("net").resolve("minecraftforge").resolve("forge").resolve(version);
Path clientJar = forgeDir.resolve("forge-" + version + "-client.jar");
Path extraJar = forgeDir.resolve("forge-" + version + "-extra.jar");
if (Files.exists(clientJar) && Files.exists(extraJar)) {
String installerUrl = String.format("https://files.minecraftforge.net/maven/net/minecraftforge/forge/%s/forge-%s-installer.jar", version, version);
String installerFileStr = String.format("./.forgewrapper/forge-%s-installer.jar", version);
Utils.download(installerUrl, installerFileStr);
String mcVersion = argsList.get(argsList.indexOf("--fml.mcVersion") + 1);
String mcpFullVersion = mcVersion + "-" + argsList.get(argsList.indexOf("--fml.mcpVersion") + 1);
String forgeFullVersion = mcVersion + "-" + argsList.get(argsList.indexOf("--fml.forgeVersion") + 1);
Path librariesDir = getLibrariesDir().toPath();
Path minecraftDir = librariesDir.resolve("net").resolve("minecraft").resolve("client");
Path forgeDir = librariesDir.resolve("net").resolve("minecraftforge").resolve("forge").resolve(forgeFullVersion);
if (getAdditionalLibraries(minecraftDir, forgeDir, mcVersion, forgeFullVersion, mcpFullVersion).anyMatch(path -> !Files.exists(path))) {
System.out.println("Some extra libraries are missing! Run installer to spawn them now.");
URLClassLoader ucl = URLClassLoader.newInstance(new URL[] {
Main.class.getProtectionDomain().getCodeSource().getLocation(),
Launcher.class.getProtectionDomain().getCodeSource().getLocation(),
new File(installerFileStr).toURI().toURL()
forgeDir.resolve("forge-" + forgeFullVersion + "-installer.jar").toUri().toURL()
}, null);
Class<?> installer = ucl.loadClass("io.github.zekerzhayard.forgewrapper.installer.Installer");
@ -44,11 +42,18 @@ public class Main {
public static File getLibrariesDir() {
try {
File laucnher = new File(Launcher.class.getProtectionDomain().getCodeSource().getLocation().toURI());
// see https://github.com/MinecraftForge/MinecraftForge/blob/863ab2ca184cf2e2dfa134d07bfc20d6a9a6a4e8/src/main/java/net/minecraftforge/fml/relauncher/libraries/LibraryManager.java#L151
// /<version> /modlauncher /mods /cpw /libraries
return laucnher.getParentFile().getParentFile().getParentFile().getParentFile().getParentFile();
} catch (URISyntaxException e) {
throw new RuntimeException(e);
}
}
public static Stream<Path> getAdditionalLibraries(Path minecraftDir, Path forgeDir, String mcVersion, String forgeFullVersion, String mcpFullVersion) {
return Stream.of(
forgeDir.resolve("forge-" + forgeFullVersion + "-client.jar"),
minecraftDir.resolve(mcVersion).resolve("client-" + mcVersion + "-extra.jar"),
minecraftDir.resolve(mcpFullVersion).resolve("client-" + mcpFullVersion + "-srg.jar")
);
}
}

View file

@ -12,9 +12,15 @@
"type": "release",
"uid": "net.minecraftforge",
"version": "{FORGE_VERSION}",
"mavenFiles": [
{
"name": "net.minecraftforge:forge:{VERSION}-{FORGE_VERSION}:installer",
"url": "https://files.minecraftforge.net/maven/"
}
],
"libraries": [
{
"name": "io.github.zekerzhayard:Forge-Wrapper:${version}",
"name": "io.github.zekerzhayard:ForgeWrapper:${version}",
"MMC-hint": "local",
"MMC-filename": "ForgeWrapper-${version}.jar"
}