Build script improvements (#3493)

* Move more to filament

* Fix build

* Mabye fix

* Update enigma

* Fix config caching warning.

* Update engima again

* Enable configuration cache

* Update gradle

* Update loom

* Fixes and improvements.

* Small cleanup

* Fix typo
This commit is contained in:
modmuss50 2023-03-25 17:43:54 +00:00 committed by GitHub
parent 2b9d67d863
commit bb890099bb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
28 changed files with 656 additions and 467 deletions

View File

@ -10,18 +10,14 @@ buildscript {
dependencies {
classpath "cuchaz:enigma-cli:${project.enigma_version}"
classpath "net.fabricmc:stitch:${project.stitch_version}"
classpath "de.undercouch:gradle-download-task:4.1.1"
classpath "net.fabricmc.unpick:unpick:${project.unpick_version}"
classpath "net.fabricmc.unpick:unpick-format-utils:${project.unpick_version}"
classpath "net.fabricmc:name-proposal:${project.name_proposal_version}"
}
}
plugins {
id 'java' // for constants, packages, javadoc
id 'de.undercouch.download' version '4.1.2'
id 'maven-publish'
id "com.diffplug.spotless" version "6.4.2"
id "com.diffplug.spotless" version "6.17.0"
id 'net.fabricmc.filament'
}
@ -73,9 +69,6 @@ configurations {
extendsFrom asm
transitive = true
}
unpick {
extendsFrom asm
}
}
def unpickMetaFile = file("unpick-definitions/unpick.json")
@ -88,98 +81,67 @@ dependencies {
javadocClasspath "com.google.code.findbugs:jsr305:3.0.2" // for some other jsr annotations
decompileClasspath "net.fabricmc:cfr:${project.cfr_version}"
mappingPoetJar "net.fabricmc:mappingpoet:${project.mappingpoet_version}"
unpick "net.fabricmc.unpick:unpick-cli:${project.unpick_version}"
asm "org.ow2.asm:asm:${project.asm_version}"
asm "org.ow2.asm:asm-tree:${project.asm_version}"
asm "org.ow2.asm:asm-commons:${project.asm_version}"
asm "org.ow2.asm:asm-util:${project.asm_version}"
}
def setupGroup = "jar setup"
def yarnGroup = "yarn"
def buildMappingGroup = "mapping build"
def mapJarGroup = "jar mapping"
def mappingsDir = file("mappings")
def cacheFilesMinecraft = file(".gradle/minecraft")
def tempDir = file(".gradle/temp")
def intermediaryJar = file("${minecraft_version}-intermediary.jar")
def unpickedJar = file("${minecraft_version}-intermediary-unpicked.jar")
def namedJar = file("${minecraft_version}-named.jar")
def serverIntermediaryJar = file("${minecraft_version}-server-intermediary.jar")
def tempDir = file("build/temp/yarn")
def cacheFilesMinecraft = new File(tempDir, "minecraft")
def libs = new File("build/libs/")
def minecraftLibraries = tasks.minecraftLibraries.files
def minecraftLibraries = configurations.minecraftLibraries
import com.google.common.hash.Hashing
import cuchaz.enigma.command.CheckMappingsCommand
import cuchaz.enigma.command.ComposeMappingsCommand
import cuchaz.enigma.command.ConvertMappingsCommand
import cuchaz.enigma.command.MapSpecializedMethodsCommand
import net.fabricmc.filament.task.MapJarTask
import net.fabricmc.filament.task.DownloadTask
import net.fabricmc.filament.task.ExtractZipEntryTask
import net.fabricmc.filament.task.UnpickJarTask
import net.fabricmc.filament.task.base.WithFileInput
import net.fabricmc.filament.task.base.WithFileOutput
import net.fabricmc.filament.task.enigma.ConvertMappingsTask
import net.fabricmc.filament.task.enigma.MapSpecializedMethodsTask
import net.fabricmc.stitch.commands.CommandMergeTiny
import net.fabricmc.stitch.commands.CommandReorderTiny
import net.fabricmc.stitch.commands.CommandRewriteIntermediary
import net.fabricmc.stitch.commands.tinyv2.CommandMergeTinyV2
import net.fabricmc.stitch.commands.tinyv2.CommandReorderTinyV2
import net.fabricmc.nameproposal.MappingNameCompleter
import org.gradle.work.DisableCachingByDefault
import java.util.zip.GZIPOutputStream
boolean validateChecksum(File file, String checksum) {
if (file != null) {
def hash = com.google.common.io.Files.asByteSource(file).hash(Hashing.sha1())
def builder = new StringBuilder()
hash.asBytes().each {
builder.append(Integer.toString((it & 0xFF) + 0x100, 16).substring(1))
}
return builder.toString().equals(checksum)
}
return false
task downloadIntermediary(type: DownloadTask) {
group = buildMappingGroup
url = "https://github.com/FabricMC/intermediary/raw/master/mappings/${minecraft_version}.tiny"
output = new File(cacheFilesMinecraft, "${minecraft_version}-intermediary.tiny")
}
task downloadIntermediary(type: Download) {
task downloadIntermediaryV2(type: DownloadTask) {
group = buildMappingGroup
def url = "https://github.com/FabricMC/intermediary/raw/master/mappings/${minecraft_version}.tiny"
src com.google.common.net.UrlEscapers.urlFragmentEscaper().escape(url)
dest new File(cacheFilesMinecraft, "${minecraft_version}-intermediary.tiny")
url = "https://maven.fabricmc.net/net/fabricmc/intermediary/${minecraft_version}/intermediary-${minecraft_version}-v2.jar"
output = new File(cacheFilesMinecraft, "${minecraft_version}-intermediary-v2.jar")
}
task downloadIntermediaryV2(type: Download) {
group = buildMappingGroup
def url = "https://maven.fabricmc.net/net/fabricmc/intermediary/${minecraft_version}/intermediary-${minecraft_version}-v2.jar"
src com.google.common.net.UrlEscapers.urlFragmentEscaper().escape(url)
dest new File(cacheFilesMinecraft, "${minecraft_version}-intermediary-v2.jar")
def output = new File(cacheFilesMinecraft, "${minecraft_version}-intermediary-v2.tiny")
outputs.file output
doLast {
copy {
from({ zipTree(downloadIntermediaryV2.dest) }) {
from 'mappings/mappings.tiny'
rename 'mappings.tiny', "../${output.name}"
}
into output.parentFile
}
}
task extractIntermediaryV2(type: ExtractZipEntryTask) {
input = downloadIntermediaryV2.output
output = new File(cacheFilesMinecraft, "${minecraft_version}-intermediary-v2.tiny")
entry = "mappings/mappings.tiny"
}
task invertIntermediary(dependsOn: downloadIntermediary, type: FileOutput) {
task invertIntermediary(dependsOn: downloadIntermediary, type: FileInputOutput) {
group = buildMappingGroup
def v1Input = downloadIntermediary.dest
input = downloadIntermediary.output
output = new File(cacheFilesMinecraft, "${minecraft_version}-intermediary-inverted.tiny")
outputs.file(output)
outputs.upToDateWhen { false }
doLast {
logger.lifecycle(":building inverted intermediary")
String[] v1Args = [
v1Input.getAbsolutePath(),
output.getAbsolutePath(),
inputFile.getAbsolutePath(),
outputFile.getAbsolutePath(),
"intermediary", "official"
]
@ -187,21 +149,15 @@ task invertIntermediary(dependsOn: downloadIntermediary, type: FileOutput) {
}
}
task invertIntermediaryv2(dependsOn: downloadIntermediaryV2, type: FileOutput) {
task invertIntermediaryv2(dependsOn: [downloadIntermediaryV2, extractIntermediaryV2], type: FileInputOutput) {
group = buildMappingGroup
def v2Input = new File(cacheFilesMinecraft, "${minecraft_version}-intermediary-v2.tiny")
output = new File(cacheFilesMinecraft, "${minecraft_version}-intermediary-inverted-v2.tiny")
outputs.file(output)
outputs.upToDateWhen { false }
input = extractIntermediaryV2.output
doLast {
logger.lifecycle(":building inverted intermediary v2")
String[] v2Args = [
v2Input.getAbsolutePath(),
output.getAbsolutePath(),
inputFile.getAbsolutePath(),
outputFile.getAbsolutePath(),
"intermediary", "official"
]
@ -209,33 +165,11 @@ task invertIntermediaryv2(dependsOn: downloadIntermediaryV2, type: FileOutput) {
}
}
task patchIntermediary(dependsOn: [mergeMinecraftJars, downloadIntermediary]) {
group = buildMappingGroup
def intermediaryTinyInput = downloadIntermediary.outputs.files.singleFile
def outputFile = new File(cacheFilesMinecraft, "${minecraft_version}-intermediary-full.tiny")
outputs.file(outputFile)
outputs.upToDateWhen { false }
doLast {
logger.lifecycle(":patching intermediary")
String[] args = [
mergeMinecraftJars.output.getAbsolutePath(),
intermediaryTinyInput.getAbsolutePath(),
outputFile.getAbsolutePath(),
"--writeAll"
]
new CommandRewriteIntermediary().run(args)
}
}
task mapIntermediaryJar(type: MapJarTask, dependsOn: [downloadIntermediary, mergeMinecraftJars]) {
group = mapJarGroup
output = intermediaryJar
input = mergeMinecraftJars.outputFile
mappings = downloadIntermediary.dest
output = file("${minecraft_version}-intermediary.jar")
input = mergeMinecraftJars.output
mappings = downloadIntermediary.output
classpath.from minecraftLibraries
from = 'official'
to = 'intermediary'
@ -243,40 +177,36 @@ task mapIntermediaryJar(type: MapJarTask, dependsOn: [downloadIntermediary, merg
task mapServerIntermediaryJar(type: MapJarTask, dependsOn: [downloadIntermediary, extractBundledServer]) {
group = mapJarGroup
output = serverIntermediaryJar
input = extractBundledServer.outputFile
mappings = downloadIntermediary.dest
output = file("${minecraft_version}-server-intermediary.jar")
input = extractBundledServer.output
mappings = downloadIntermediary.output
classpath.from minecraftLibraries
from = 'official'
to = 'intermediary'
}
task yarnUnpicked(dependsOn: "unpickIntermediaryJar", type: EnigmaTask) {
group = yarnGroup
jar = unpickedJar
mappings = mappingsDir
}
task yarn(dependsOn: mapIntermediaryJar, type: EnigmaTask) {
group = yarnGroup
jar = intermediaryJar
jar = mapIntermediaryJar.output
mappings = mappingsDir
}
task yarnCommon(dependsOn: mapServerIntermediaryJar, type: EnigmaTask) {
task yarnCommon(type: EnigmaTask) {
group = yarnGroup
jar = serverIntermediaryJar
jar = mapServerIntermediaryJar.output
mappings = mappingsDir
}
task checkMappings(dependsOn: mapIntermediaryJar) {
task checkMappings() {
group = buildMappingGroup
inputs.dir mappingsDir
doLast {
logger.lifecycle(":checking mappings")
inputs.file mapIntermediaryJar.output
def intermediaryJarPath = mapIntermediaryJar.outputFile.absolutePath
doLast {
String[] args = [
intermediaryJar.getAbsolutePath(),
intermediaryJarPath,
mappingsDir.getAbsolutePath()
]
@ -288,61 +218,49 @@ task checkMappings(dependsOn: mapIntermediaryJar) {
}
}
task buildYarnTiny(dependsOn: mapIntermediaryJar, type: WithV2FileOutput) {
group = buildMappingGroup
inputs.dir mappingsDir
if (!libs.exists()) {
libs.mkdirs()
}
task mapSpecializedMethods(type: MapSpecializedMethodsTask) {
intermediaryJarFile = mapIntermediaryJar.output
mappings = mappingsDir
output = new File(tempDir, "yarn-mappings-v2.tiny")
v1Output = new File(tempDir, "yarn-mappings.tiny")
v2Output = new File(tempDir, "yarn-mappings-v2.tiny")
outputs.upToDateWhen { false }
doLast {
logger.lifecycle(":generating tiny mappings")
new MapSpecializedMethodsCommand().run(
intermediaryJar.getAbsolutePath(),
"enigma",
mappingsDir.getAbsolutePath(),
"tinyv2:intermediary:named",
v2Output.getAbsolutePath()
)
new ConvertMappingsCommand().run(
"tinyv2",
v2Output.getAbsolutePath(),
"tiny:intermediary:named",
v1Output.getAbsolutePath())
}
inputMappingsFormat = "enigma"
outputMappingsFormat = "tinyv2:intermediary:named"
}
task mergeTiny(dependsOn: ["buildYarnTiny", "invertIntermediary"], type: FileOutput) {
task convertToV1(type: ConvertMappingsTask) {
input = mapSpecializedMethods.output
output = new File(tempDir, "yarn-mappings.tiny")
inputMappingsFormat = "tinyv2"
outputMappingsFormat = "tiny:intermediary:named"
}
task mergeTiny(dependsOn: ["convertToV1", "invertIntermediary"], type: FileOutput) {
group = buildMappingGroup
def yarnTinyInput = buildYarnTiny.v1Output
def intermediaryTinyInput = invertIntermediary.output
def unorderedResultMappings = new File(tempDir, "mappings-unordered.tiny")
output = new File(tempDir, "mappings.tiny")
outputs.file(output)
outputs.file unorderedResultMappings
outputs.upToDateWhen { false }
output = new File(tempDir, "mappings.tiny")
inputs.file convertToV1.output
inputs.file invertIntermediary.output
def intermediaryTinyPath = invertIntermediary.outputFile.absolutePath
def yarnTinyPath = convertToV1.outputFile.absolutePath
def outputPath = unorderedResultMappings.absolutePath
doLast {
logger.lifecycle(":merging yarn and intermediary")
String[] args = [
intermediaryTinyInput.getAbsolutePath(),
yarnTinyInput.getAbsolutePath(),
unorderedResultMappings.getAbsolutePath(),
intermediaryTinyPath,
yarnTinyPath,
outputPath,
"intermediary",
"official"
]
new CommandMergeTiny().run(args)
logger.lifecycle(":reordering merged intermediary")
String[] args2 = [
unorderedResultMappings.getAbsolutePath(),
output.getAbsolutePath(),
@ -353,12 +271,17 @@ task mergeTiny(dependsOn: ["buildYarnTiny", "invertIntermediary"], type: FileOut
}
}
// Disable the default jar task
jar {
enabled = false
}
task tinyJar(type: Jar, dependsOn: mergeTiny) {
group = buildMappingGroup
outputs.upToDateWhen { false }
archiveFileName = "yarn-${yarnVersion}.jar"
destinationDirectory.set(file("build/libs"))
classifier = ""
archiveClassifier = ""
from(mergeTiny.output) {
rename { "mappings/mappings.tiny" }
}
@ -367,19 +290,13 @@ task tinyJar(type: Jar, dependsOn: mergeTiny) {
}
}
task compressTiny(dependsOn: [tinyJar, mergeTiny], type: FileOutput) {
task compressTiny(dependsOn: [tinyJar, mergeTiny], type: FileInputOutput) {
group = buildMappingGroup
def outputFile = new File(libs, "yarn-tiny-${yarnVersion}.gz")
outputs.file(outputFile)
output = outputFile
def inputFile = mergeTiny.output
outputs.upToDateWhen { false }
input = mergeTiny.output
output = new File(libs, "yarn-tiny-${yarnVersion}.gz")
doLast {
logger.lifecycle(":compressing tiny mappings")
def buffer = new byte[1024]
def fileOutputStream = new FileOutputStream(outputFile)
def outputStream = new GZIPOutputStream(fileOutputStream)
@ -400,102 +317,44 @@ clean.doFirst {
delete tempDir, cacheFilesMinecraft
}
sourceSets {
constants
packageDocs // package info files
}
task constantsJar(type: Jar) {
from sourceSets.constants.output
archiveClassifier = "constants"
}
tasks.build.dependsOn "compressTiny","tinyJar","v2UnmergedYarnJar", "v2MergedYarnJar", "javadocJar"
task exportMappingsOfficial(dependsOn: downloadIntermediary) {
def composeInput = downloadIntermediary.dest
doLast {
logger.lifecycle(":exporting mappings")
String[] args = [
"tiny",
composeInput.getAbsolutePath(),
"enigma",
file("mappings/").getAbsolutePath(),
"enigma",
file("mappings_official/").getAbsolutePath(),
"right"
]
new ComposeMappingsCommand().run(args)
}
}
task importMappingsOfficial(dependsOn: invertIntermediary) {
def composeInput = invertIntermediary.output
doLast {
logger.lifecycle(":importing mappings")
String[] args = [
"tiny",
composeInput.getAbsolutePath(),
"enigma",
file("mappings_official/").getAbsolutePath(),
"enigma",
file("mappings/").getAbsolutePath(),
"right"
]
new ComposeMappingsCommand().run(args)
}
}
combineUnpickDefinitions {
group = 'unpick'
input = file('unpick-definitions')
output = new File(tempDir, 'definitions.unpick')
}
remapUnpickDefinitionsIntermediary {
dependsOn buildYarnTiny
group = 'unpick'
output = new File(tempDir, 'intermediary-definitions.unpick')
mappings = buildYarnTiny.v2Output
}
task unpickIntermediaryJar(type: JavaExec, dependsOn: [mapIntermediaryJar, "constantsJar", remapUnpickDefinitionsIntermediary]) {
outputs.upToDateWhen { false }
group "unpick"
mainClass = "daomephsta.unpick.cli.Main"
systemProperty "java.util.logging.config.file", file('unpick-logging.properties')
classpath configurations.unpick
doFirst {
args intermediaryJar.absolutePath, unpickedJar.absolutePath, remapUnpickDefinitionsIntermediary.output.get().asFile.absolutePath, constantsJar.archiveFile.get().asFile.absolutePath
minecraftLibraries.files.forEach {
args it.absolutePath
}
}
}
// Setup the build for the unpicked constants
sourceCompatibility = JavaVersion.VERSION_17
targetCompatibility = JavaVersion.VERSION_17
java {
sourceCompatibility = JavaVersion.VERSION_17
targetCompatibility = JavaVersion.VERSION_17
}
tasks.withType(JavaCompile).configureEach {
it.options.encoding = "UTF-8"
it.options.release = 17
}
sourceSets {
constants
packageDocs // package info files
}
spotless {
lineEndings = com.diffplug.spotless.LineEnding.UNIX
java {
licenseHeaderFile(rootProject.file("HEADER"))
}
}
task constantsJar(type: Jar) {
from sourceSets.constants.output
archiveClassifier = "constants"
}
task sourcesJar(type: Jar, dependsOn: classes) {
archiveClassifier = "sources"
from sourceSets.constants.allSource
@ -505,36 +364,64 @@ task sourcesJar(type: Jar, dependsOn: classes) {
build.dependsOn constantsJar
task insertAutoGeneratedEnumMappings(dependsOn : [buildYarnTiny,mapIntermediaryJar], type : FileOutput){
task insertAutoGeneratedEnumMappings(dependsOn : [mapIntermediaryJar, downloadIntermediary], type : FileInputOutput){
group = buildMappingGroup
File noEnumV2 = buildYarnTiny.v2Output
input = mapSpecializedMethods.output
output = new File(tempDir, "unmerged-named-v2-with-enum.tiny")
outputs.upToDateWhen { false }
inputs.file mapIntermediaryJar.output
inputs.file downloadIntermediary.output
def intermediaryJarPath = mapIntermediaryJar.outputPath
def intermediaryMappingsPath = downloadIntermediary.outputPath
doLast {
logger.lifecycle(":seeking auto-mappable fields for unmerged mappings")
MappingNameCompleter.completeNames(
intermediaryJar.toPath(),
noEnumV2.toPath(),
downloadIntermediary.dest.toPath(),
output.toPath()
intermediaryJarPath,
inputPath,
intermediaryMappingsPath,
outputPath
)
}
}
task mergeV2(dependsOn: ["v2UnmergedYarnJar", "invertIntermediaryv2"], type: FileOutput) {
remapUnpickDefinitionsIntermediary {
group = 'unpick'
output = new File(tempDir, 'intermediary-definitions.unpick')
mappings = insertAutoGeneratedEnumMappings.output
}
task unpickIntermediaryJar(type: UnpickJarTask) {
group = 'unpick'
input = mapIntermediaryJar.output
output = file("${minecraft_version}-intermediary-unpicked.jar")
unpickDefinition = remapUnpickDefinitionsIntermediary.output
constantsJarFile = constantsJar.archiveFile
classpath.from minecraftLibraries
}
task yarnUnpicked(dependsOn: "unpickIntermediaryJar", type: EnigmaTask) {
group = yarnGroup
jar = unpickIntermediaryJar.output
mappings = mappingsDir
}
task mergeV2(dependsOn: ["v2UnmergedYarnJar"], type: FileOutput) {
def mergedV2 = new File(tempDir, "merged-v2.tiny");
outputs.file mergedV2
output = new File(tempDir, "merged-reordered-v2.tiny")
outputs.upToDateWhen { false }
inputs.file insertAutoGeneratedEnumMappings.output
inputs.file invertIntermediaryv2.output
def intermediaryPath = invertIntermediaryv2.outputFile.absolutePath
def mappingsPath = insertAutoGeneratedEnumMappings.outputFile.absolutePath
doLast {
logger.lifecycle(":merging yarn and intermediary v2")
String[] args = [
invertIntermediaryv2.output.getAbsolutePath(),
insertAutoGeneratedEnumMappings.output.getAbsolutePath(),
intermediaryPath,
mappingsPath,
mergedV2.getAbsolutePath(),
"intermediary",
"official"
@ -557,11 +444,10 @@ task mergeV2(dependsOn: ["v2UnmergedYarnJar", "invertIntermediaryv2"], type: Fil
task v2UnmergedYarnJar(dependsOn: [insertAutoGeneratedEnumMappings, combineUnpickDefinitions], type: Jar) {
def mappings = insertAutoGeneratedEnumMappings.output
group = "mapping build"
outputs.upToDateWhen { false }
archiveFileName = "yarn-${yarnVersion}-v2.jar"
from(file(mappings)) {
rename mappings.name, "mappings/mappings.tiny"
rename mappings.get().asFile.name, "mappings/mappings.tiny"
}
from(combineUnpickDefinitions.output) {
rename combineUnpickDefinitions.output.get().asFile.name, "extras/definitions.unpick"
@ -579,7 +465,6 @@ task v2UnmergedYarnJar(dependsOn: [insertAutoGeneratedEnumMappings, combineUnpic
task v2MergedYarnJar(dependsOn: ["mergeV2"], type: Jar) {
def mappings = mergeV2.output
group = "mapping build"
outputs.upToDateWhen { false }
archiveFileName = "yarn-${yarnVersion}-mergedv2.jar"
from(file(mappings)) {
@ -600,8 +485,8 @@ task v2MergedYarnJar(dependsOn: ["mergeV2"], type: Jar) {
task mapNamedJar(type: MapJarTask, dependsOn: ["mergeV2", "unpickIntermediaryJar"]) {
group = mapJarGroup
output = namedJar
input = unpickedJar
output = file("${minecraft_version}-named.jar")
input = unpickIntermediaryJar.output
mappings = mergeV2.output
classpath.from minecraftLibraries
from = 'intermediary'
@ -624,22 +509,23 @@ task syncDependencies(type: Sync) {
def fakeSourceDir = file(".gradle/temp/fakeSource")
task genFakeSource(type: JavaExec, dependsOn: ["mergeV2", "mapNamedJar", syncDependencies]) {
group = "javadoc generation"
outputs.upToDateWhen { false }
inputs.file mergeV2.output
inputs.file mapNamedJar.output
inputs.dir mcLibsDir
outputs.dir fakeSourceDir
mainClass = "net.fabricmc.mappingpoet.Main"
classpath configurations.mappingPoet
// use merged v2 so we have all namespaces in jd
args mergeV2.output.getAbsolutePath(), namedJar.getAbsolutePath(), fakeSourceDir.getAbsolutePath(), mcLibsDir.getAbsolutePath()
doLast {
logger.lifecycle ":Fake source generated"
}
args mergeV2.output.getAbsolutePath(), mapNamedJar.outputFile.getAbsolutePath(), fakeSourceDir.getAbsolutePath(), mcLibsDir.getAbsolutePath()
}
task decompileCFR(type: JavaExec, dependsOn: [mapNamedJar]) {
mainClass = "org.benf.cfr.reader.Main"
args namedJar.getAbsolutePath(), "--outputdir", file("namedSrc").absolutePath
args mapNamedJar.outputFile.getAbsolutePath(), "--outputdir", file("namedSrc").absolutePath
doFirst {
file("namedSrc").deleteDir()
@ -651,7 +537,6 @@ task decompileCFR(type: JavaExec, dependsOn: [mapNamedJar]) {
javadoc {
dependsOn genFakeSource
group = "javadoc generation"
outputs.upToDateWhen { false }
def mappingPoetJar = project.provider { zipTree configurations.mappingPoetJar.singleFile }
@ -710,18 +595,23 @@ javadoc {
source fileTree(fakeSourceDir) + sourceSets.constants.allJava + sourceSets.packageDocs.allJava
classpath = configurations.javadocClasspath.plus minecraftLibraries
def fs = services.get(FileSystemOperations.class)
def outputDir = javadoc.outputDirectory
doLast {
project.copy {
fs.copy {
from mappingPoetJar
include "copy_on_click.js"
into javadoc.outputDirectory
into outputDir
}
}
def tagletClasspath = configurations.mappingPoet.files.toList()
doFirst {
// lazy setting
options {
tagletPath configurations.mappingPoet.files.toList()
tagletPath tagletClasspath
header mappingPoetJar.get().filter { it.name == 'javadoc_header.txt' }.singleFile.text.trim() // cannot include line breaks
addFileOption "-add-stylesheet", mappingPoetJar.get().filter { it.name == 'forms.css' }.singleFile
}
@ -738,8 +628,7 @@ task javadocJar(type: Jar, dependsOn: ["javadoc"]) {
}
generatePackageInfoMappings {
dependsOn mapIntermediaryJar
inputJar = intermediaryJar
inputJar = mapIntermediaryJar.output
packageName = "net/minecraft/unused/packageinfo/"
outputDir = file("mappings/net/minecraft/unused/packageinfo")
}
@ -804,21 +693,18 @@ task checkVersion {
publish.mustRunAfter checkVersion
class FileOutput extends DefaultTask {
abstract class FileOutput extends DefaultTask {
@OutputFile
File output
}
class WithV2FileOutput extends DefaultTask {
@OutputFile
File v1Output
@OutputFile
File v2Output
abstract class FileInputOutput extends DefaultTask implements WithFileInput, WithFileOutput {
}
@DisableCachingByDefault
abstract class EnigmaTask extends JavaExec {
@Input
abstract Property<File> getJar()
@InputFile
abstract RegularFileProperty getJar()
@Input
abstract Property<File> getMappings()
@ -831,7 +717,7 @@ abstract class EnigmaTask extends JavaExec {
@TaskAction
void exec() {
args '-jar'
args jar.get().absolutePath
args jar.get().asFile.absolutePath
args '-mappings'
args mappings.get().absolutePath
args '-profile'

View File

@ -30,15 +30,18 @@ dependencies {
implementation "org.ow2.asm:asm:${properties.asm_version}"
implementation "org.ow2.asm:asm-tree:${properties.asm_version}"
implementation "cuchaz:enigma:$properties.enigma_version"
implementation "cuchaz:enigma-cli:$properties.enigma_version"
implementation "net.fabricmc.unpick:unpick:$properties.unpick_version"
implementation "net.fabricmc.unpick:unpick-format-utils:$properties.unpick_version"
implementation "net.fabricmc.unpick:unpick-cli:$properties.unpick_version"
implementation "net.fabricmc:tiny-mappings-parser:$properties.tiny_mappings_parser_version"
implementation "net.fabricmc:tiny-remapper:$properties.tiny_remapper_version"
implementation "net.fabricmc:mappingpoet:$properties.mappingpoet_version"
implementation 'com.fasterxml.jackson.core:jackson-databind:2.13.4.2'
// Contains a number of useful utilities we can re-use.
implementation ("net.fabricmc:fabric-loom:1.0.7") {
transitive = true
implementation ("net.fabricmc:fabric-loom:1.1.10") {
transitive = false
}
implementation ('net.fabricmc:stitch:0.6.2') {

View File

@ -1 +1 @@
filament_version=0.4.0
filament_version=0.5.0

View File

@ -5,7 +5,14 @@ import java.io.File;
import javax.inject.Inject;
import org.gradle.api.Project;
import org.gradle.api.file.Directory;
import org.gradle.api.file.DirectoryProperty;
import org.gradle.api.file.RegularFile;
import org.gradle.api.provider.Property;
import org.gradle.api.provider.Provider;
import net.fabricmc.filament.util.MinecraftVersionMetaHelper;
import net.fabricmc.loom.configuration.providers.minecraft.MinecraftVersionMeta;
public abstract class FilamentExtension {
public static FilamentExtension get(Project project) {
@ -19,17 +26,31 @@ public abstract class FilamentExtension {
public abstract Property<String> getMinecraftVersionManifestUrl();
private final MinecraftVersionMetaHelper metaHelper;
private final Provider<MinecraftVersionMeta> metaProvider;
@Inject
public FilamentExtension() {
getMinecraftVersion().finalizeValueOnRead();
getMinecraftVersionManifestUrl().convention("https://piston-meta.mojang.com/mc/game/version_manifest_v2.json").finalizeValueOnRead();
metaHelper = getProject().getObjects().newInstance(MinecraftVersionMetaHelper.class, this);
metaProvider = getProject().provider(metaHelper::setup);
}
public File getCacheDirectory() {
return new File(getProject().getRootDir(), ".gradle/filament");
public DirectoryProperty getCacheDirectory() {
return getProject().getObjects().directoryProperty().fileValue(new File(getProject().getRootDir(), ".gradle/filament"));
}
public File getMinecraftDirectory() {
return new File(getCacheDirectory(), getMinecraftVersion().get());
public Provider<Directory> getMinecraftDirectory() {
return getCacheDirectory().dir(getMinecraftVersion());
}
public Provider<RegularFile> getMinecraftFile(String filename) {
return getMinecraftDirectory().map(directory -> directory.file(filename));
}
public Provider<MinecraftVersionMeta> getMinecraftVersionMetadata() {
return metaProvider;
}
}

View File

@ -1,13 +1,14 @@
package net.fabricmc.filament;
import java.io.File;
import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.gradle.api.Plugin;
import org.gradle.api.Project;
import org.gradle.api.artifacts.Dependency;
import org.gradle.api.artifacts.dsl.DependencyHandler;
import org.gradle.api.file.RegularFile;
import org.gradle.api.provider.Provider;
import org.gradle.api.tasks.Delete;
import org.gradle.api.tasks.TaskContainer;
import org.gradle.api.tasks.TaskProvider;
@ -16,12 +17,11 @@ import net.fabricmc.filament.task.DownloadTask;
import net.fabricmc.filament.task.GeneratePackageInfoMappingsTask;
import net.fabricmc.filament.task.JavadocLintTask;
import net.fabricmc.filament.task.RemapUnpickDefinitionsTask;
import net.fabricmc.filament.task.base.FileOutputTask;
import net.fabricmc.filament.task.base.WithFileOutput;
import net.fabricmc.filament.task.minecraft.ExtractBundledServerTask;
import net.fabricmc.filament.task.minecraft.MergeMinecraftTask;
import net.fabricmc.filament.task.minecraft.MinecraftLibrariesTask;
import net.fabricmc.filament.task.minecraft.MinecraftVersionMetaTask;
import net.fabricmc.loom.configuration.providers.minecraft.MinecraftVersionMeta;
import net.fabricmc.loom.util.gradle.GradleUtils;
public final class FilamentGradlePlugin implements Plugin<Project> {
public static final ObjectMapper OBJECT_MAPPER = new ObjectMapper().configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
@ -31,33 +31,32 @@ public final class FilamentGradlePlugin implements Plugin<Project> {
final FilamentExtension extension = project.getExtensions().create("filament", FilamentExtension.class);
final TaskContainer tasks = project.getTasks();
var minecraftMetaTask = tasks.register("downloadMinecraftMeta", MinecraftVersionMetaTask.class);
var metaProvider = MinecraftVersionMetaTask.readMetadata(minecraftMetaTask);
var metaProvider = extension.getMinecraftVersionMetadata();
var minecraftClient = tasks.register("downloadMinecraftClientJar", DownloadTask.class, task -> {
Provider<MinecraftVersionMeta.Download> downloadProvider = metaProvider.map(meta -> meta.download("client"));
task.getUrl().set(downloadProvider.map(MinecraftVersionMeta.Download::url));
task.getSha1().set(downloadProvider.map(MinecraftVersionMeta.Download::sha1));
task.getOutputFile().set(new File(extension.getMinecraftDirectory(), "client.jar"));
task.getOutput().set(extension.getMinecraftFile("client.jar"));
});
var minecraftServer = tasks.register("downloadMinecraftServerJar", DownloadTask.class, task -> {
Provider<MinecraftVersionMeta.Download> downloadProvider = metaProvider.map(meta -> meta.download("server"));
task.getUrl().set(downloadProvider.map(MinecraftVersionMeta.Download::url));
task.getSha1().set(downloadProvider.map(MinecraftVersionMeta.Download::sha1));
task.getOutputFile().set(new File(extension.getMinecraftDirectory(), "server_bundle.jar"));
task.getOutput().set(extension.getMinecraftFile("server_bundle.jar"));
});
var extractBundledServer = tasks.register("extractBundledServer", ExtractBundledServerTask.class, task -> {
task.dependsOn(minecraftServer);
task.getServerJar().set(getOutput(minecraftServer));
task.getOutputFile().set(new File(extension.getMinecraftDirectory(), "server.jar"));
task.getInput().set(getOutput(minecraftServer));
task.getOutput().set(extension.getMinecraftFile("server.jar"));
});
tasks.register("mergeMinecraftJars", MergeMinecraftTask.class, task -> {
task.getClientJar().set(getOutput(minecraftClient));
task.getServerJar().set(getOutput(extractBundledServer));
task.getOutputFile().set(new File(extension.getMinecraftDirectory(), "merged.jar"));
task.getOutput().set(extension.getMinecraftFile("merged.jar"));
});
tasks.register("generatePackageInfoMappings", GeneratePackageInfoMappingsTask.class);
tasks.register("javadocLint", JavadocLintTask.class);
@ -70,17 +69,28 @@ public final class FilamentGradlePlugin implements Plugin<Project> {
task.getTargetNamespace().set("intermediary");
});
tasks.register("minecraftLibraries", MinecraftLibrariesTask.class, task -> {
task.dependsOn(minecraftMetaTask);
var cleanFilament = tasks.register("cleanFilament", Delete.class, task -> task.delete(extension.getCacheDirectory()));
tasks.named("clean", task -> task.dependsOn(cleanFilament));
var files = MinecraftVersionMetaTask.readMetadata(minecraftMetaTask)
.map(meta -> MinecraftLibrariesTask.getDependencies(project, meta))
.map(dependencies -> project.getConfigurations().detachedConfiguration(dependencies).resolve());
task.getFiles().from(files);
var minecraftLibraries = project.getConfigurations().register("minecraftLibraries");
GradleUtils.afterSuccessfulEvaluation(project, () -> {
var name = minecraftLibraries.getName();
for (Dependency dependency : getDependencies(metaProvider.get(), project.getDependencies())) {
project.getDependencies().add(name, dependency);
}
});
}
private Provider<RegularFile> getOutput(TaskProvider<? extends FileOutputTask> taskProvider) {
return taskProvider.flatMap(FileOutputTask::getOutputFile);
private Provider<? extends RegularFile> getOutput(TaskProvider<? extends WithFileOutput> taskProvider) {
return taskProvider.flatMap(WithFileOutput::getOutput);
}
private Dependency[] getDependencies(MinecraftVersionMeta meta, DependencyHandler dependencyHandler) {
return meta.libraries().stream()
.filter(library -> library.artifact() != null)
.map(library -> dependencyHandler.create(library.name()))
.toArray(Dependency[]::new);
}
}

View File

@ -13,11 +13,12 @@ import org.gradle.workers.WorkParameters;
import org.gradle.workers.WorkQueue;
import org.gradle.workers.WorkerExecutor;
import net.fabricmc.filament.task.base.FileOutputTask;
import net.fabricmc.filament.task.base.FilamentTask;
import net.fabricmc.filament.task.base.WithFileOutput;
import net.fabricmc.loom.util.download.Download;
import net.fabricmc.loom.util.download.DownloadException;
public abstract class DownloadTask extends FileOutputTask {
public abstract class DownloadTask extends FilamentTask implements WithFileOutput {
@Input
public abstract Property<String> getUrl();
@Input
@ -26,13 +27,18 @@ public abstract class DownloadTask extends FileOutputTask {
@Inject
protected abstract WorkerExecutor getWorkerExecutor();
@Inject
public DownloadTask() {
getSha1().convention("");
}
@TaskAction
public void run() {
WorkQueue workQueue = getWorkerExecutor().noIsolation();
workQueue.submit(DownloadAction.class, parameters -> {
parameters.getUrl().set(getUrl());
parameters.getSha1().set(getSha1());
parameters.getOutput().set(getOutputFile());
parameters.getOutput().set(getOutput());
});
}
@ -46,9 +52,16 @@ public abstract class DownloadTask extends FileOutputTask {
@Override
public void execute() {
try {
Download.create(getParameters().getUrl().get())
.sha1(getParameters().getSha1().get())
.downloadPath(getParameters().getOutput().get().getAsFile().toPath());
var sha1 = getParameters().getSha1().get();
var download = Download.create(getParameters().getUrl().get());
if (!sha1.isEmpty()) {
download.sha1(sha1);
} else {
download.defaultCache();
}
download.downloadPath(getParameters().getOutput().get().getAsFile().toPath());
} catch (DownloadException | URISyntaxException e) {
throw new RuntimeException("Failed to download", e);
}

View File

@ -0,0 +1,24 @@
package net.fabricmc.filament.task;
import java.io.IOException;
import java.nio.file.Files;
import org.gradle.api.provider.Property;
import org.gradle.api.tasks.Input;
import org.gradle.api.tasks.TaskAction;
import net.fabricmc.filament.task.base.FilamentTask;
import net.fabricmc.filament.task.base.WithFileInput;
import net.fabricmc.filament.task.base.WithFileOutput;
import net.fabricmc.loom.util.ZipUtils;
public abstract class ExtractZipEntryTask extends FilamentTask implements WithFileInput, WithFileOutput {
@Input
public abstract Property<String> getEntry();
@TaskAction
public void run() throws IOException {
byte[] bytes = ZipUtils.unpack(getInputPath(), getEntry().get());
Files.write(getOutputPath(), bytes);
}
}

View File

@ -19,21 +19,20 @@ import org.gradle.api.provider.Provider;
import org.gradle.api.tasks.Classpath;
import org.gradle.api.tasks.Input;
import org.gradle.api.tasks.InputFile;
import org.gradle.api.tasks.OutputFile;
import org.gradle.api.tasks.TaskAction;
import org.gradle.workers.WorkAction;
import org.gradle.workers.WorkParameters;
import org.gradle.workers.WorkQueue;
import org.gradle.workers.WorkerExecutor;
import net.fabricmc.filament.task.base.WithFileInput;
import net.fabricmc.filament.task.base.WithFileOutput;
import net.fabricmc.tinyremapper.OutputConsumerPath;
import net.fabricmc.tinyremapper.TinyRemapper;
import net.fabricmc.tinyremapper.TinyUtils;
public abstract class MapJarTask extends DefaultTask {
@InputFile public abstract RegularFileProperty getInput();
public abstract class MapJarTask extends DefaultTask implements WithFileOutput, WithFileInput {
@InputFile public abstract RegularFileProperty getMappings();
@OutputFile public abstract RegularFileProperty getOutput();
@Classpath public abstract ConfigurableFileCollection getClasspath();
@Input public abstract Property<String> getFrom();
@Input public abstract Property<String> getTo();
@ -48,8 +47,6 @@ public abstract class MapJarTask extends DefaultTask {
@TaskAction
public void remap() {
getProject().getLogger().lifecycle(":remapping {} from {} to {}", getInput().get().getAsFile(), getFrom().get(), getTo().get());
WorkQueue workQueue = getWorkerExecutor().noIsolation();
workQueue.submit(RemapAction.class, parameters -> {
parameters.getInput().set(getInput());
@ -63,20 +60,16 @@ public abstract class MapJarTask extends DefaultTask {
}
public interface RemapParameters extends WorkParameters {
@InputFile RegularFileProperty getInput();
@InputFile RegularFileProperty getMappings();
@OutputFile RegularFileProperty getOutput();
@Classpath ConfigurableFileCollection getClasspath();
@Input Property<String> getFrom();
@Input Property<String> getTo();
@Input MapProperty<String, String> getClassMappings();
RegularFileProperty getInput();
RegularFileProperty getMappings();
RegularFileProperty getOutput();
ConfigurableFileCollection getClasspath();
Property<String> getFrom();
Property<String> getTo();
MapProperty<String, String> getClassMappings();
}
public abstract static class RemapAction implements WorkAction<RemapParameters> {
@Inject
public RemapAction() {
}
private static Path getPath(Provider<? extends FileSystemLocation> provider) {
return provider.get().getAsFile().toPath();
}

View File

@ -0,0 +1,80 @@
package net.fabricmc.filament.task;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import javax.inject.Inject;
import daomephsta.unpick.cli.Main;
import org.gradle.api.file.ConfigurableFileCollection;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.tasks.InputFile;
import org.gradle.api.tasks.InputFiles;
import org.gradle.api.tasks.TaskAction;
import org.gradle.workers.WorkAction;
import org.gradle.workers.WorkParameters;
import org.gradle.workers.WorkQueue;
import org.gradle.workers.WorkerExecutor;
import net.fabricmc.filament.task.base.FilamentTask;
import net.fabricmc.filament.task.base.WithFileInput;
import net.fabricmc.filament.task.base.WithFileOutput;
public abstract class UnpickJarTask extends FilamentTask implements WithFileInput, WithFileOutput {
@InputFile
public abstract RegularFileProperty getUnpickDefinition();
@InputFile
public abstract RegularFileProperty getConstantsJarFile();
@InputFiles
public abstract ConfigurableFileCollection getClasspath();
@Inject
protected abstract WorkerExecutor getWorkerExecutor();
@TaskAction
public void run() {
WorkQueue workQueue = getWorkerExecutor().noIsolation();
workQueue.submit(UnpickAction.class, parameters -> {
parameters.getInput().set(getInput());
parameters.getOutput().set(getOutput());
parameters.getUnpickDefinition().set(getUnpickDefinition());
parameters.getConstantJar().set(getConstantsJarFile());
parameters.getClasspath().from(getClasspath());
});
}
public interface UnpickParameters extends WorkParameters {
RegularFileProperty getInput();
RegularFileProperty getOutput();
RegularFileProperty getUnpickDefinition();
RegularFileProperty getConstantJar();
ConfigurableFileCollection getClasspath();
}
public abstract static class UnpickAction implements WorkAction<UnpickParameters> {
@Override
public void execute() {
List<String> args = new ArrayList<>();
args.add(getPath(getParameters().getInput()));
args.add(getPath(getParameters().getOutput()));
args.add(getPath(getParameters().getUnpickDefinition()));
args.add(getPath(getParameters().getConstantJar()));
for (File file : getParameters().getClasspath().getFiles()) {
args.add(file.getAbsolutePath());
}
try {
Main.main(args.toArray(String[]::new));
} catch (IOException e) {
throw new RuntimeException(e);
}
}
private String getPath(RegularFileProperty fileProperty) {
return fileProperty.get().getAsFile().getAbsolutePath();
}
}
}

View File

@ -1,9 +1,4 @@
package net.fabricmc.filament.task.base;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.tasks.OutputFile;
public abstract class FileOutputTask extends FilamentTask {
@OutputFile
public abstract RegularFileProperty getOutputFile();
public abstract class FileOutputTask extends FilamentTask implements WithFileOutput {
}

View File

@ -0,0 +1,23 @@
package net.fabricmc.filament.task.base;
import java.io.File;
import java.nio.file.Path;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.tasks.InputFile;
import org.gradle.api.tasks.Internal;
public interface WithFileInput {
@InputFile
RegularFileProperty getInput();
@Internal
default File getInputFile() {
return getInput().get().getAsFile();
}
@Internal
default Path getInputPath() {
return getInputFile().toPath();
}
}

View File

@ -0,0 +1,23 @@
package net.fabricmc.filament.task.base;
import java.io.File;
import java.nio.file.Path;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.tasks.Internal;
import org.gradle.api.tasks.OutputFile;
public interface WithFileOutput {
@OutputFile
RegularFileProperty getOutput();
@Internal
default File getOutputFile() {
return getOutput().get().getAsFile();
}
@Internal
default Path getOutputPath() {
return getOutputFile().toPath();
}
}

View File

@ -0,0 +1,34 @@
package net.fabricmc.filament.task.enigma;
import java.util.List;
import cuchaz.enigma.command.Command;
import cuchaz.enigma.command.ConvertMappingsCommand;
import org.gradle.api.provider.Property;
import org.gradle.api.tasks.Input;
import net.fabricmc.filament.task.base.WithFileInput;
import net.fabricmc.filament.task.base.WithFileOutput;
public abstract class ConvertMappingsTask extends EnigmaCommandTask implements WithFileInput, WithFileOutput {
@Input
public abstract Property<String> getInputMappingsFormat();
@Input
public abstract Property<String> getOutputMappingsFormat();
@Override
public Class<? extends Command> getCommandClass() {
return ConvertMappingsCommand.class;
}
@Override
protected List<String> getArguments() {
return List.of(
getInputMappingsFormat().get(),
getInputFile().getAbsolutePath(),
getOutputMappingsFormat().get(),
getOutputFile().getAbsolutePath()
);
}
}

View File

@ -0,0 +1,55 @@
package net.fabricmc.filament.task.enigma;
import java.util.List;
import javax.inject.Inject;
import cuchaz.enigma.command.Command;
import org.gradle.api.provider.ListProperty;
import org.gradle.api.provider.Property;
import org.gradle.api.tasks.Internal;
import org.gradle.api.tasks.TaskAction;
import org.gradle.workers.WorkAction;
import org.gradle.workers.WorkParameters;
import org.gradle.workers.WorkQueue;
import org.gradle.workers.WorkerExecutor;
import net.fabricmc.filament.task.base.FilamentTask;
public abstract class EnigmaCommandTask extends FilamentTask {
@Internal
public abstract Class<? extends Command> getCommandClass();
@Internal
protected abstract List<String> getArguments();
@Inject
protected abstract WorkerExecutor getWorkerExecutor();
@TaskAction
public void run() {
WorkQueue workQueue = getWorkerExecutor().noIsolation();
workQueue.submit(EnigmaAction.class, parameters -> {
parameters.getCommandClassName().set(getCommandClass().getName());
parameters.getArguments().set(getArguments());
});
}
public interface EnimgaParameters extends WorkParameters {
Property<String> getCommandClassName();
ListProperty<String> getArguments();
}
public abstract static class EnigmaAction implements WorkAction<EnimgaParameters> {
@Override
public void execute() {
try {
Class<?> commandClass = Class.forName(getParameters().getCommandClassName().get());
Command command = (Command) commandClass.getConstructor().newInstance();
command.run(getParameters().getArguments().get().toArray(String[]::new));
} catch (Throwable e) {
throw new RuntimeException(e);
}
}
}
}

View File

@ -0,0 +1,52 @@
package net.fabricmc.filament.task.enigma;
import java.util.List;
import javax.inject.Inject;
import cuchaz.enigma.command.Command;
import cuchaz.enigma.command.MapSpecializedMethodsCommand;
import org.gradle.api.file.DirectoryProperty;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.provider.Property;
import org.gradle.api.tasks.Input;
import org.gradle.api.tasks.InputDirectory;
import org.gradle.api.tasks.InputFile;
import net.fabricmc.filament.task.base.WithFileOutput;
public abstract class MapSpecializedMethodsTask extends EnigmaCommandTask implements WithFileOutput {
@InputFile
public abstract RegularFileProperty getIntermediaryJarFile();
@Input
public abstract Property<String> getInputMappingsFormat();
@InputDirectory
public abstract DirectoryProperty getMappings();
@Input
public abstract Property<String> getOutputMappingsFormat();
@Inject
public MapSpecializedMethodsTask() {
getInputMappingsFormat().convention("engima");
getOutputMappingsFormat().convention("tinyv2:intermediary:named");
}
@Override
public Class<? extends Command> getCommandClass() {
return MapSpecializedMethodsCommand.class;
}
@Override
protected List<String> getArguments() {
return List.of(
getIntermediaryJarFile().get().getAsFile().getAbsolutePath(),
getInputMappingsFormat().get(),
getMappings().get().getAsFile().getAbsolutePath(),
getOutputMappingsFormat().get(),
getOutputFile().getAbsolutePath()
);
}
}

View File

@ -5,23 +5,20 @@ import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.StandardCopyOption;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.tasks.InputFile;
import org.gradle.api.tasks.TaskAction;
import net.fabricmc.filament.task.base.FileOutputTask;
import net.fabricmc.filament.task.base.FilamentTask;
import net.fabricmc.filament.task.base.WithFileInput;
import net.fabricmc.filament.task.base.WithFileOutput;
import net.fabricmc.loom.util.FileSystemUtil;
public abstract class ExtractBundledServerTask extends FileOutputTask {
@InputFile
public abstract RegularFileProperty getServerJar();
public abstract class ExtractBundledServerTask extends FilamentTask implements WithFileOutput, WithFileInput {
@TaskAction
public void run() throws IOException {
try (FileSystemUtil.Delegate fs = FileSystemUtil.getJarFileSystem(getServerJar().get().getAsFile().toPath(), false)) {
try (FileSystemUtil.Delegate fs = FileSystemUtil.getJarFileSystem(getInputPath(), false)) {
String versionsList = new String(fs.readAllBytes("META-INF/versions.list"), StandardCharsets.UTF_8);
String jarPath = "META-INF/versions/" + versionsList.split("\t")[2];
Files.copy(fs.getPath(jarPath), getOutputFile().get().getAsFile().toPath(), StandardCopyOption.REPLACE_EXISTING);
Files.copy(fs.getPath(jarPath), getOutputPath(), StandardCopyOption.REPLACE_EXISTING);
}
}
}

View File

@ -21,7 +21,7 @@ public abstract class MergeMinecraftTask extends FileOutputTask {
try (JarMerger jarMerger = new JarMerger(
getClientJar().getAsFile().get(),
getServerJar().getAsFile().get(),
getOutputFile().getAsFile().get())) {
getOutput().getAsFile().get())) {
jarMerger.merge();
}
}

View File

@ -1,21 +0,0 @@
package net.fabricmc.filament.task.minecraft;
import org.gradle.api.Project;
import org.gradle.api.artifacts.Dependency;
import org.gradle.api.file.ConfigurableFileCollection;
import org.gradle.api.tasks.OutputFiles;
import net.fabricmc.filament.task.base.FilamentTask;
import net.fabricmc.loom.configuration.providers.minecraft.MinecraftVersionMeta;
public abstract class MinecraftLibrariesTask extends FilamentTask {
@OutputFiles
public abstract ConfigurableFileCollection getFiles();
public static Dependency[] getDependencies(Project project, MinecraftVersionMeta meta) {
return meta.libraries().stream()
.filter(library -> library.artifact() != null)
.map(library -> project.getDependencies().create(library.name()))
.toArray(Dependency[]::new);
}
}

View File

@ -1,84 +0,0 @@
package net.fabricmc.filament.task.minecraft;
import java.io.File;
import java.io.IOException;
import java.io.UncheckedIOException;
import java.net.URISyntaxException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.provider.Property;
import org.gradle.api.provider.Provider;
import org.gradle.api.tasks.Input;
import org.gradle.api.tasks.OutputFile;
import org.gradle.api.tasks.TaskAction;
import net.fabricmc.filament.FilamentGradlePlugin;
import net.fabricmc.filament.task.base.FilamentTask;
import net.fabricmc.loom.configuration.providers.minecraft.ManifestVersion;
import net.fabricmc.loom.configuration.providers.minecraft.MinecraftVersionMeta;
import net.fabricmc.loom.util.download.Download;
public abstract class MinecraftVersionMetaTask extends FilamentTask {
@Input
public abstract Property<String> getMinecraftVersion();
@Input
public abstract Property<String> getMinecraftVersionManifestUrl();
@OutputFile
public abstract RegularFileProperty getVersionManifest();
@OutputFile
public abstract RegularFileProperty getVersionMetadata();
public MinecraftVersionMetaTask() {
// Use the Minecraft version as an input to ensure the task re-runs on upgrade
getMinecraftVersion().set(getExtension().getMinecraftVersion());
getMinecraftVersionManifestUrl().set(getExtension().getMinecraftVersionManifestUrl());
getVersionManifest().set(new File(getExtension().getCacheDirectory(), "version_manifest.json"));
getVersionMetadata().set(new File(getExtension().getMinecraftDirectory(), "version.json"));
}
@TaskAction
public void run() throws IOException, URISyntaxException {
final Path versionManifestPath = getVersionManifest().getAsFile().get().toPath();
final Path versionMetadataPath = getVersionMetadata().getAsFile().get().toPath();
final String versionManifest = Download.create(getMinecraftVersionManifestUrl().get())
.downloadString(versionManifestPath);
final ManifestVersion mcManifest = FilamentGradlePlugin.OBJECT_MAPPER.readValue(versionManifest, ManifestVersion.class);
ManifestVersion.Versions version = mcManifest.versions().stream()
.filter(versions -> versions.id.equalsIgnoreCase(getMinecraftVersion().get()))
.findFirst()
.orElse(null);
if (version == null) {
throw new RuntimeException("Failed to find minecraft version: " + getMinecraftVersion().get());
}
Download.create(version.url)
.sha1(version.sha1)
.downloadPath(versionMetadataPath);
}
public static Provider<MinecraftVersionMeta> readMetadata(Provider<MinecraftVersionMetaTask> task) {
return task.flatMap(t -> readMetadata(t.getVersionMetadata()));
}
public static Provider<MinecraftVersionMeta> readMetadata(RegularFileProperty file) {
return file.map(regularFile -> {
try {
String versionManifest = Files.readString(regularFile.getAsFile().toPath(), StandardCharsets.UTF_8);
return FilamentGradlePlugin.OBJECT_MAPPER.readValue(versionManifest, MinecraftVersionMeta.class);
} catch (IOException e) {
throw new UncheckedIOException(e);
}
});
}
}

View File

@ -0,0 +1,66 @@
package net.fabricmc.filament.util;
import java.io.IOException;
import java.io.UncheckedIOException;
import java.net.URISyntaxException;
import java.nio.file.Path;
import javax.inject.Inject;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.provider.Property;
import net.fabricmc.filament.FilamentExtension;
import net.fabricmc.filament.FilamentGradlePlugin;
import net.fabricmc.loom.configuration.providers.minecraft.ManifestVersion;
import net.fabricmc.loom.configuration.providers.minecraft.MinecraftVersionMeta;
import net.fabricmc.loom.util.download.Download;
public abstract class MinecraftVersionMetaHelper {
public abstract Property<String> getMinecraftVersion();
public abstract Property<String> getMinecraftVersionManifestUrl();
public abstract RegularFileProperty getVersionManifestFile();
public abstract RegularFileProperty getVersionMetadataFile();
@Inject
public MinecraftVersionMetaHelper(FilamentExtension extension) {
// Use the Minecraft version as an input to ensure the task re-runs on upgrade
getMinecraftVersion().set(extension.getMinecraftVersion());
getMinecraftVersionManifestUrl().set(extension.getMinecraftVersionManifestUrl());
getVersionManifestFile().set(extension.getMinecraftFile("version_manifest.json"));
getVersionMetadataFile().set(extension.getMinecraftFile("version.json"));
}
public MinecraftVersionMeta setup() throws IOException, URISyntaxException {
final Path versionManifestPath = getVersionManifestFile().getAsFile().get().toPath();
final Path versionMetadataPath = getVersionMetadataFile().getAsFile().get().toPath();
final String versionManifest = Download.create(getMinecraftVersionManifestUrl().get())
.defaultCache()
.downloadString(versionManifestPath);
final ManifestVersion mcManifest = FilamentGradlePlugin.OBJECT_MAPPER.readValue(versionManifest, ManifestVersion.class);
ManifestVersion.Versions version = mcManifest.versions().stream()
.filter(versions -> versions.id.equalsIgnoreCase(getMinecraftVersion().get()))
.findFirst()
.orElse(null);
if (version == null) {
throw new RuntimeException("Failed to find minecraft version: " + getMinecraftVersion().get());
}
final String versionMetadata = Download.create(version.url)
.sha1(version.sha1)
.downloadString(versionMetadataPath);
try {
return FilamentGradlePlugin.OBJECT_MAPPER.readValue(versionMetadata, MinecraftVersionMeta.class);
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
}

View File

@ -1,4 +1,5 @@
plugins {
id 'java'
id 'net.fabricmc.filament'
}

View File

@ -1,4 +1,5 @@
plugins {
id 'java'
id 'net.fabricmc.filament'
}

View File

@ -1,16 +1,18 @@
# Done to increase the memory available to gradle.
org.gradle.jvmargs=-Xmx1G
org.gradle.parallel=true
org.gradle.configuration-cache=true
enigma_version=2.1.0
enigma_version=2.3.0
stitch_version=0.6.1
unpick_version=2.3.0
cfr_version=0.1.1
name_proposal_version=0.1.4
tiny_remapper_version=0.8.2
tiny_remapper_version=0.8.5
asm_version=9.4
# Javadoc generation/linking
fabric_loader_version=0.13.3
fabric_loader_version=0.14.14
jetbrains_annotations_version=23.0.0
mappingpoet_version=0.3.2

Binary file not shown.

View File

@ -1,6 +1,6 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-7.5.1-bin.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-8.1-rc-1-bin.zip
networkTimeout=10000
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
distributionSha256Sum=f6b8596b10cce501591e92f229816aa4046424f3b24d771751b06779d58c8ec4

18
gradlew vendored
View File

@ -55,7 +55,7 @@
# Darwin, MinGW, and NonStop.
#
# (3) This script is generated from the Groovy template
# https://github.com/gradle/gradle/blob/master/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
# https://github.com/gradle/gradle/blob/HEAD/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
# within the Gradle project.
#
# You can find Gradle at https://github.com/gradle/gradle/.
@ -80,10 +80,10 @@ do
esac
done
APP_HOME=$( cd "${APP_HOME:-./}" && pwd -P ) || exit
APP_NAME="Gradle"
# This is normally unused
# shellcheck disable=SC2034
APP_BASE_NAME=${0##*/}
APP_HOME=$( cd "${APP_HOME:-./}" && pwd -P ) || exit
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
@ -143,12 +143,16 @@ fi
if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then
case $MAX_FD in #(
max*)
# In POSIX sh, ulimit -H is undefined. That's why the result is checked to see if it worked.
# shellcheck disable=SC3045
MAX_FD=$( ulimit -H -n ) ||
warn "Could not query maximum file descriptor limit"
esac
case $MAX_FD in #(
'' | soft) :;; #(
*)
# In POSIX sh, ulimit -n is undefined. That's why the result is checked to see if it worked.
# shellcheck disable=SC3045
ulimit -n "$MAX_FD" ||
warn "Could not set maximum file descriptor limit to $MAX_FD"
esac
@ -205,6 +209,12 @@ set -- \
org.gradle.wrapper.GradleWrapperMain \
"$@"
# Stop when "xargs" is not available.
if ! command -v xargs >/dev/null 2>&1
then
die "xargs is not available"
fi
# Use "xargs" to parse quoted args.
#
# With -n1 it outputs one arg per line, with the quotes and backslashes removed.

15
gradlew.bat vendored
View File

@ -14,7 +14,7 @@
@rem limitations under the License.
@rem
@if "%DEBUG%" == "" @echo off
@if "%DEBUG%"=="" @echo off
@rem ##########################################################################
@rem
@rem Gradle startup script for Windows
@ -25,7 +25,8 @@
if "%OS%"=="Windows_NT" setlocal
set DIRNAME=%~dp0
if "%DIRNAME%" == "" set DIRNAME=.
if "%DIRNAME%"=="" set DIRNAME=.
@rem This is normally unused
set APP_BASE_NAME=%~n0
set APP_HOME=%DIRNAME%
@ -40,7 +41,7 @@ if defined JAVA_HOME goto findJavaFromJavaHome
set JAVA_EXE=java.exe
%JAVA_EXE% -version >NUL 2>&1
if "%ERRORLEVEL%" == "0" goto execute
if %ERRORLEVEL% equ 0 goto execute
echo.
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
@ -75,13 +76,15 @@ set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
:end
@rem End local scope for the variables with windows NT shell
if "%ERRORLEVEL%"=="0" goto mainEnd
if %ERRORLEVEL% equ 0 goto mainEnd
:fail
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
rem the _cmd.exe /c_ return code!
if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
exit /b 1
set EXIT_CODE=%ERRORLEVEL%
if %EXIT_CODE% equ 0 set EXIT_CODE=1
if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE%
exit /b %EXIT_CODE%
:mainEnd
if "%OS%"=="Windows_NT" endlocal

View File

@ -14,6 +14,8 @@ if (!JavaVersion.current().isCompatibleWith(JavaVersion.VERSION_17)) {
throw new UnsupportedOperationException("Yarn's buildscript requires Java 17 or higher.")
}
enableFeaturePreview "STABLE_CONFIGURATION_CACHE"
rootProject.name = "yarn"
includeBuild 'filament'