diff --git a/src/main/java/net/neoforged/neoform/runtime/artifacts/ArtifactManager.java b/src/main/java/net/neoforged/neoform/runtime/artifacts/ArtifactManager.java index 9265331..010f4df 100644 --- a/src/main/java/net/neoforged/neoform/runtime/artifacts/ArtifactManager.java +++ b/src/main/java/net/neoforged/neoform/runtime/artifacts/ArtifactManager.java @@ -66,7 +66,7 @@ public Artifact get(MinecraftLibrary library) throws IOException { throw new IllegalArgumentException("Cannot download a library that has no artifact defined: " + library); } - var artifactCoordinate = MavenCoordinate.parse(library.artifactId()); + var artifactCoordinate = library.getMavenCoordinate(); var externalArtifact = getFromExternalManifest(artifactCoordinate); if (externalArtifact != null) { return externalArtifact; diff --git a/src/main/java/net/neoforged/neoform/runtime/manifests/MinecraftLibrary.java b/src/main/java/net/neoforged/neoform/runtime/manifests/MinecraftLibrary.java index e6c714a..35de07f 100644 --- a/src/main/java/net/neoforged/neoform/runtime/manifests/MinecraftLibrary.java +++ b/src/main/java/net/neoforged/neoform/runtime/manifests/MinecraftLibrary.java @@ -1,12 +1,17 @@ package net.neoforged.neoform.runtime.manifests; import com.google.gson.annotations.SerializedName; +import net.fabricmc.loom.nativeplatform.OperatingSystem; +import net.neoforged.neoform.runtime.utils.MavenCoordinate; +import net.neoforged.neoform.runtime.utils.OsType; import org.jetbrains.annotations.Nullable; import java.util.List; +import java.util.Map; import java.util.Objects; -public record MinecraftLibrary(@SerializedName("name") String artifactId, Downloads downloads, List rules) { +public record MinecraftLibrary(@SerializedName("name") String artifactId, Downloads downloads, List rules, + @Nullable Map natives) { public MinecraftLibrary { Objects.requireNonNull(artifactId, "name"); rules = Objects.requireNonNullElseGet(rules, List::of); @@ -31,10 +36,44 @@ public boolean rulesMatch() { @Nullable public MinecraftDownload getArtifactDownload() { - return downloads != null ? downloads.artifact : null; + if (downloads == null) { + return null; + } + + if (natives != null) { + var classifier = natives.get(OsType.current()); + if (classifier != null) { + var download = downloads.classifiers.get(classifier); + if (download == null) { + throw new IllegalStateException("Download for " + artifactId + " references classifier " + classifier + + " for natives for OS " + OperatingSystem.CURRENT + " but it doesn't exist."); + } + return download; + } + } + + return downloads.artifact; } - public record Downloads(MinecraftDownload artifact) { + public MavenCoordinate getMavenCoordinate() { + var coordinate = MavenCoordinate.parse(artifactId); + + if (natives != null) { + String classifier = natives.get(OsType.current()); + if (classifier != null) { + coordinate = coordinate.withClassifier(classifier); + } + } + + return coordinate; + } + + public record Downloads(MinecraftDownload artifact, Map classifiers) { + public Downloads { + if (classifiers == null) { + classifiers = Map.of(); + } + } } @Override diff --git a/src/main/java/net/neoforged/neoform/runtime/utils/MavenCoordinate.java b/src/main/java/net/neoforged/neoform/runtime/utils/MavenCoordinate.java index 75f233e..bd9425d 100644 --- a/src/main/java/net/neoforged/neoform/runtime/utils/MavenCoordinate.java +++ b/src/main/java/net/neoforged/neoform/runtime/utils/MavenCoordinate.java @@ -118,4 +118,14 @@ public URI toRepositoryUri(URI baseUri) { return URI.create(originalBaseUri + "/" + relativePath); } } + + public MavenCoordinate withClassifier(String classifier) { + return new MavenCoordinate( + groupId, + artifactId, + extension, + classifier, + version + ); + } } diff --git a/src/main/java/net/neoforged/neoform/runtime/utils/OsType.java b/src/main/java/net/neoforged/neoform/runtime/utils/OsType.java new file mode 100644 index 0000000..2f67af3 --- /dev/null +++ b/src/main/java/net/neoforged/neoform/runtime/utils/OsType.java @@ -0,0 +1,33 @@ +package net.neoforged.neoform.runtime.utils; + +import com.google.gson.annotations.SerializedName; + +public enum OsType { + @SerializedName("windows") + WINDOWS, + @SerializedName("linux") + LINUX, + @SerializedName("osx") + MAC, + UNKNOWN; + + private static final OsType CURRENT; + + static { + var osName = System.getProperty("os.name"); + // The following matches the logic in Apache Commons Lang 3 SystemUtils + if (osName.startsWith("Linux") || osName.startsWith("LINUX")) { + CURRENT = OsType.LINUX; + } else if (osName.startsWith("Mac OS X")) { + CURRENT = OsType.MAC; + } else if (osName.startsWith("Windows")) { + CURRENT = OsType.WINDOWS; + } else { + CURRENT = OsType.UNKNOWN; + } + } + + public static OsType current() { + return CURRENT; + } +} diff --git a/src/main/java/net/neoforged/neoform/runtime/utils/OsUtil.java b/src/main/java/net/neoforged/neoform/runtime/utils/OsUtil.java index 79e335c..f3eaf07 100644 --- a/src/main/java/net/neoforged/neoform/runtime/utils/OsUtil.java +++ b/src/main/java/net/neoforged/neoform/runtime/utils/OsUtil.java @@ -1,41 +1,18 @@ package net.neoforged.neoform.runtime.utils; public final class OsUtil { - private static OsType TYPE; - - static { - var osName = System.getProperty("os.name"); - // The following matches the logic in Apache Commons Lang 3 SystemUtils - if (osName.startsWith("Linux") || osName.startsWith("LINUX")) { - TYPE = OsType.LINUX; - } else if (osName.startsWith("Mac OS X")) { - TYPE = OsType.MAC; - } else if (osName.startsWith("Windows")) { - TYPE = OsType.WINDOWS; - } else { - TYPE = OsType.UNKNOWN; - } - } - private OsUtil() { } public static boolean isWindows() { - return TYPE == OsType.WINDOWS; + return OsType.current() == OsType.WINDOWS; } public static boolean isLinux() { - return TYPE == OsType.LINUX; + return OsType.current() == OsType.LINUX; } public static boolean isMac() { - return TYPE == OsType.MAC; - } - - enum OsType { - WINDOWS, - LINUX, - MAC, - UNKNOWN + return OsType.current() == OsType.MAC; } }