mod load order

This commit is contained in:
Bixilon 2022-10-31 14:29:56 +01:00
parent 68291b0aec
commit b0185c3aa0
No known key found for this signature in database
GPG Key ID: 5CAD791931B09AC4
3 changed files with 149 additions and 6 deletions

View File

@ -210,7 +210,6 @@ object ModLoader {
state = PhaseStates.VALIDATING
worker = UnconditionalWorker()
val invalid: MutableSet<MinosoftMod> = mutableSetOf()
for (mod in list) {
worker += {
try {
@ -219,16 +218,16 @@ object ModLoader {
} catch (error: Throwable) {
mod.latch.count = 0
error.printStackTrace()
invalid += mod
list -= mod
}
}
}
worker.work(inner)
list -= invalid
val sorted = list.sorted().toMutableList()
state = PhaseStates.CONSTRUCTING
worker = UnconditionalWorker()
for (mod in list) {
for (mod in sorted) {
worker += {
try {
mod.construct()
@ -237,6 +236,7 @@ object ModLoader {
mod.latch.count = 0
error.printStackTrace()
list -= mod
sorted -= mod
}
}
}
@ -244,7 +244,7 @@ object ModLoader {
state = PhaseStates.POST_INIT
worker = UnconditionalWorker()
for (mod in list) {
for (mod in sorted) {
worker += {
try {
mod.postInit()
@ -253,6 +253,7 @@ object ModLoader {
mod.latch.count = 0
error.printStackTrace()
list -= mod
sorted -= mod
}
}
}

View File

@ -25,7 +25,7 @@ class MinosoftMod(
val path: File,
val phase: LoadingPhases,
val latch: CountUpAndDownLatch,
) {
) : Comparable<MinosoftMod> {
val classLoader = JarClassLoader()
var manifest: ModManifest? = null
var assetsManager: AssetsManager? = null
@ -41,4 +41,25 @@ class MinosoftMod(
error.printStackTrace()
}
}
override fun compareTo(other: MinosoftMod): Int {
val manifest = manifest!!
val otherManifest = other.manifest!!
val depends: MutableSet<String> = mutableSetOf()
manifest.packages?.depends?.let { depends += it }
manifest.load?.after?.let { depends += it }
if (otherManifest.name in depends) {
return 1 // load before
}
manifest.load?.before?.let {
if (otherManifest.name in it) {
return -1
}
}
return 0
}
}

View File

@ -0,0 +1,121 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* 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/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.modding.loader.mod
import de.bixilon.kutil.latch.CountUpAndDownLatch
import de.bixilon.minosoft.modding.loader.LoadingPhases
import de.bixilon.minosoft.modding.loader.ModList
import de.bixilon.minosoft.modding.loader.mod.manifest.ModManifest
import de.bixilon.minosoft.modding.loader.mod.manifest.load.LoadM
import de.bixilon.minosoft.modding.loader.mod.manifest.packages.PackagesM
import java.io.File
import kotlin.test.Test
import kotlin.test.assertEquals
internal class MinosoftModTest {
private fun createMod(): MinosoftMod {
return MinosoftMod(File("."), LoadingPhases.PRE_BOOT, CountUpAndDownLatch(0))
}
@Test
fun testDependsOn1() {
val dependency = createMod().apply { manifest = ModManifest("dependency", version = "0", main = "") }
val b = createMod().apply { manifest = ModManifest("bbb", version = "0", main = "", packages = PackagesM(setOf("dependency"))) }
val c = createMod().apply { manifest = ModManifest("ccc", version = "0", main = "", packages = PackagesM(setOf("dependency"))) }
val list = ModList()
list += dependency
list += b
list += c
assertEquals(list.sorted(), mutableListOf(dependency, b, c))
}
@Test
fun testDependsOn2() {
val dependency = createMod().apply { manifest = ModManifest("dependency", version = "0", main = "") }
val b = createMod().apply { manifest = ModManifest("bbb", version = "0", main = "", packages = PackagesM(setOf("dependency"))) }
val c = createMod().apply { manifest = ModManifest("ccc", version = "0", main = "", packages = PackagesM(setOf("dependency", "ccc"))) }
val list = ModList()
list += dependency
list += b
list += c
assertEquals(list.sorted(), mutableListOf(dependency, b, c))
}
@Test
fun testDependsOn3() {
val dependency = createMod().apply { manifest = ModManifest("dependency", version = "0", main = "") }
val c = createMod().apply { manifest = ModManifest("ccc", version = "0", main = "", packages = PackagesM(setOf("dependency", "bbb"))) }
val b = createMod().apply { manifest = ModManifest("bbb", version = "0", main = "", packages = PackagesM(setOf("dependency"))) }
val list = ModList()
list += dependency
list += b
list += c
assertEquals(list.sorted(), mutableListOf(dependency, b, c))
}
@Test
fun testDependsOn4() {
val dependency = createMod().apply { manifest = ModManifest("dependency", version = "0", main = "") }
val b = createMod().apply { manifest = ModManifest("bbb", version = "0", main = "", packages = PackagesM(setOf("dependency"))) }
val c = createMod().apply { manifest = ModManifest("ccc", version = "0", main = "", packages = PackagesM(setOf("bbb"))) }
val list = ModList()
list += dependency
list += b
list += c
assertEquals(list.sorted(), mutableListOf(dependency, b, c))
}
@Test
fun testLoadingOrder1() {
val dependency = createMod().apply { manifest = ModManifest("dependency", version = "0", main = "") }
val c = createMod().apply { manifest = ModManifest("ccc", version = "0", main = "", load = LoadM(after = setOf("bbb"))) }
val b = createMod().apply { manifest = ModManifest("bbb", version = "0", main = "", packages = PackagesM(setOf("dependency"))) }
val list = ModList()
list += dependency
list += b
list += c
assertEquals(list.sorted(), mutableListOf(dependency, b, c))
}
@Test
fun testLoadingOrder2() {
val dependency = createMod().apply { manifest = ModManifest("dependency", version = "0", main = "") }
val c = createMod().apply { manifest = ModManifest("ccc", version = "0", main = "", load = LoadM(before = setOf("bbb"))) }
val b = createMod().apply { manifest = ModManifest("bbb", version = "0", main = "", packages = PackagesM(setOf("dependency"))) }
val list = ModList()
list += dependency
list += b
list += c
assertEquals(list.sorted(), mutableListOf(dependency, c, b))
}
}