Files
2026-07-03 15:56:07 +08:00

917 lines
35 KiB
Groovy

/*
* Copyright 2018-2024 Frederic Thevenet
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import org.gradle.api.internal.file.copy.CopyAction
import org.gradle.api.internal.file.copy.CopyActionProcessingStream
import java.nio.file.Files
import java.nio.file.Paths
import java.nio.file.StandardCopyOption
import java.text.SimpleDateFormat
import java.time.Duration
plugins {
id "de.undercouch.download" version "5.6.0"
id 'org.kordamp.gradle.markdown' version '2.2.0'
id "com.github.ben-manes.versions" version "0.51.0"
id "de.marcphilipp.nexus-publish" version "0.4.0" apply false
id "signing"
}
ext.IS_TAG = System.getenv('IS_TAG') != null ? System.getenv('IS_TAG') == "true" : false
ext.IS_RELEASE = IS_TAG && !(System.getenv('REPO_TAG_NAME').endsWith('-SNAPSHOT'))
ext.IS_BETA = false
ext.BINJR_BETA_VERSION = "0.0.0"
ext.BINJR_VERSION_STEM = "3.19.0"
ext.LINUX_APP_RELEASE = "1"
ext.BINJR_VERSION = "${BINJR_VERSION_STEM}${IS_RELEASE ? '' : '-SNAPSHOT'}"
ext.BINJR_BUILD_NUMBER = System.getenv('BINJR_BUILD_NUMBER') == null ? ("000") : System.getenv('BINJR_BUILD_NUMBER')
ext.GROUP_ID = 'eu.binjr'
ext.LICENSE_NAME = 'Apache License, Version 2.0'
ext.LICENSE_URL = 'http ://www.apache.org/licenses/LICENSE-2.0.txt'
ext.LICENSE_DISTRIBUTION = 'repo'
ext.BINJR_COPYRIGHT = "Copyright (c) 2016-2024 Frederic Thevenet"
ext.BINJR_DESCRIPTION = "A Time Series Browser"
ext.OS_NAME = System.getProperty("os.name").toLowerCase()
ext.OS_ARCH = System.getProperty("os.arch")
ext.IS_64 = OS_ARCH.toLowerCase().contains("64")
ext.BINJR_MAX_HEAP_SIZE = IS_64 ? "4096M" : "2048M"
ext.IS_MONOCLE = false
ext.IS_MAC = OS_NAME.contains("mac") || OS_NAME.contains("darwin")
ext.IS_WINDOWS = OS_NAME.contains("windows")
ext.IS_LINUX = OS_NAME.contains("linux")
ext.OS_FAMILY = IS_MAC ? 'mac' : IS_WINDOWS ? 'windows' : IS_LINUX ? 'linux' : 'unsupported'
ext.JDK_HOME = System.getProperty("java.home")
ext.OPENJFX_VERSION = "22.0.1"
ext.USE_BUILD_JDK_IN_BUNDLE = false
ext.BUNDLE_JDK_VERSION = "jdk-22.0.1+8"
ext.OPENJFX_VERSION_STEM = OPENJFX_VERSION.replaceAll("-ea\\+[0-9]+", "")
ext.OPENJFX_PLATEFORM_CLASSIFIER = craftPlatformClassifier()
ext.DL_CACHE_PATH = System.getProperty("java.io.tmpdir") + "/gradle_dl_cache/"
ext.IS_JAVAFX_BUNDLED = ModuleLayer.boot().findModule("javafx.controls").isPresent()
ext.ADDITIONAL_JMOD_PATH = IS_JAVAFX_BUNDLED ? "" : "${File.pathSeparator}${buildDir}/jmods/javafx-jmods-${OPENJFX_VERSION_STEM}"
ext.JLINK_ADD_MODULES = "javafx.controls," +
"javafx.fxml," +
"javafx.swing," +
"java.base," +
"java.prefs," +
"java.sql," +
"java.xml," +
"java.management," +
"java.net.http," +
"java.rmi," +
"jdk.localedata," +
"java.management.rmi," +
"jdk.management.agent," +
"jdk.security.auth,jdk.management," +
"jdk.management.jfr," +
"jdk.zipfs," +
"jdk.unsupported.desktop," +
"jdk.crypto.ec," +
"jdk.crypto.cryptoki" +
"${IS_WINDOWS ? ",jdk.crypto.mscapi" : ""}"
ext.DISTRIBUTION_NAME = "${project.name}-${BINJR_VERSION}_${OS_FAMILY}-${OS_ARCH}"
ext.APP_IMAGE_ROOT = "${buildDir}/app_image/${DISTRIBUTION_NAME}"
ext.APP_IMAGE_PATH = IS_WINDOWS ? "${APP_IMAGE_ROOT}" : "${APP_IMAGE_ROOT}/${BINJR_VERSION}"
ext.WIX_HOME = System.getenv("WIX")
ext.WIX_HEAT_HOME = System.getenv("WIX_HEAT_HOME")
ext.ARTIFACTS_ROOT_PATH = "${buildDir}/artifacts/"
ext.ARTIFACTS_PATH_ZIP = file("${ARTIFACTS_ROOT_PATH}/zip/")
ext.ARTIFACTS_PATH_MSI = file("${ARTIFACTS_ROOT_PATH}/msi/")
ext.ARTIFACTS_PATH_DMG = file("${ARTIFACTS_ROOT_PATH}/dmg/")
ext.ARTIFACTS_PATH_PKG = file("${ARTIFACTS_ROOT_PATH}/pkg/")
ext.ARTIFACTS_PATH_RPM = file("${ARTIFACTS_ROOT_PATH}/rpm/")
ext.ARTIFACTS_PATH_DEB = file("${ARTIFACTS_ROOT_PATH}/deb/")
ext.ARTIFACTS_PATH_TGZ = file("${ARTIFACTS_ROOT_PATH}/tgz/")
ext."signing.keyId" = System.getenv('GPG_KEY_NAME')
ext."signing.secretKeyRingFile" = System.getenv('GPG_KEYRING_PATH')
ext."signing.password" = System.getenv('GPG_PASSPHRASE')
System.out.println("Building version: ${BINJR_VERSION}")
System.out.println("Is tag: ${IS_TAG}")
System.out.println("Is release: ${IS_RELEASE}")
if (IS_TAG && System.getenv('REPO_TAG_NAME') != "v${BINJR_VERSION}") {
throw new GradleException("Tag name [${System.getenv('REPO_TAG_NAME')}] does not match version [${BINJR_VERSION}]")
}
configure(subprojects) {
if (project == project(':binjr-app'))
apply plugin: 'application'
else
apply plugin: 'java-library'
apply plugin: "de.marcphilipp.nexus-publish"
apply plugin: "signing"
group GROUP_ID
version BINJR_VERSION
sourceCompatibility = 21
targetCompatibility = 21
description BINJR_DESCRIPTION
compileJava.options.encoding = 'UTF-8'
if (project != project(':binjr-app')) {
project.javadoc {
options.encoding = 'UTF-8'
options.tags = ["XmlJavaTypeAdapter", "XmlJavaTypeAdapters"]
}
task javadocJar(type: Jar) {
archiveClassifier = 'javadoc'
from javadoc
}
task sourcesJar(type: Jar) {
archiveClassifier = 'sources'
from sourceSets.main.allSource
}
dependencies {
testImplementation('org.junit.jupiter:junit-jupiter-api:5.10.2')
testRuntimeOnly('org.junit.jupiter:junit-jupiter-engine:5.10.2')
compileOnly "org.openjfx:javafx-base:$OPENJFX_VERSION:$OPENJFX_PLATEFORM_CLASSIFIER"
compileOnly "org.openjfx:javafx-graphics:$OPENJFX_VERSION:$OPENJFX_PLATEFORM_CLASSIFIER"
compileOnly "org.openjfx:javafx-controls:$OPENJFX_VERSION:$OPENJFX_PLATEFORM_CLASSIFIER"
compileOnly "org.openjfx:javafx-fxml:$OPENJFX_VERSION:$OPENJFX_PLATEFORM_CLASSIFIER"
compileOnly "org.openjfx:javafx-swing:$OPENJFX_VERSION:$OPENJFX_PLATEFORM_CLASSIFIER"
}
}
repositories {
// mavenLocal()
mavenCentral()
if (!IS_RELEASE) {
// maven { url 'https://oss.sonatype.org/content/repositories/snapshots' }
// maven { url 'https://s01.oss.sonatype.org/content/repositories/snapshots' }
// maven { url 'https://repository.apache.org/snapshots/' }
}
}
publishing {
publications {
mavenJava(MavenPublication) {
artifactId = project.name
if (project != project(':binjr-app')) {
from components.java
artifact sourcesJar
artifact javadocJar
}
pom {
name = project.name
description = 'A Time Series Data Browser'
url = 'https://binjr.eu'
if (project == project(':binjr-app')) {
packaging = 'pom'
} else {
packaging = 'jar'
}
licenses {
license {
name = 'The Apache License, Version 2.0'
url = 'http://www.apache.org/licenses/LICENSE-2.0.txt'
distribution = 'repo'
}
}
developers {
developer {
id = 'fthevenet'
name = 'Frederic Thevenet'
}
}
scm {
connection = 'scm:git:https://github.com/binjr/binjr.git'
developerConnection = 'scm:git:https://github.com/binjr/binjr.git'
url = 'https://github.com/binjr/binjr'
}
if (project == project(':binjr-app')) {
withXml {
Node pluginNode = asNode().appendNode('build')
.appendNode('plugins')
.appendNode('plugin')
pluginNode.appendNode('groupId', 'org.codehaus.mojo')
pluginNode.appendNode('artifactId', 'exec-maven-plugin')
pluginNode.appendNode('version', '1.2.1')
pluginNode.appendNode('executions')
.appendNode('execution')
.appendNode('goals')
.appendNode('goal', 'java')
pluginNode.appendNode('configuration')
.appendNode('mainClass', 'eu.binjr.core.Bootstrap')
Node depsNode = asNode().appendNode('dependencies')
project.configurations.runtimeClasspath.each {
if (it.name.startsWith('binjr')) {
Node depNode = depsNode.appendNode('dependency')
depNode.appendNode('groupId', GROUP_ID)
depNode.appendNode('artifactId', it.name.replace("-${BINJR_VERSION}.jar", ""))
depNode.appendNode('version', BINJR_VERSION)
}
}
}
}
}
}
}
}
signing {
required { IS_RELEASE && gradle.taskGraph.hasTask("publishArtifacts") }
sign publishing.publications.mavenJava
}
tasks.withType(Sign) {
onlyIf { IS_RELEASE }
}
nexusPublishing {
repositories {
sonatype {
username = System.getenv('OSSRH_TOKEN_USERNAME')
password = System.getenv('OSSRH_TOKEN_PASSWORD')
connectTimeout = Duration.ofSeconds(300)
clientTimeout = Duration.ofSeconds(300)
}
}
}
}
task publishArtifacts(dependsOn: subprojects.publishToSonatype) {
doLast {
System.out.println("Done publishing artifacts from subprojects.")
}
}
task copyAppLibs(type: Copy) {
into "$APP_IMAGE_PATH/libs"
from(project(":binjr-core").configurations.runtimeClasspath) {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-jrds").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-csv").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-jfr").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-rrd4j").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-netdata").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
// from project(":binjr-adapter-text").configurations.runtimeClasspath {
// exclude "javafx-*.jar"
// }
from project(":binjr-adapter-logs").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-core").jar
}
task copyPluginLibs(type: Copy) {
into IS_MAC ? "$APP_IMAGE_PATH/libs" : "$APP_IMAGE_PATH/plugins"
from project(":binjr-adapter-jrds").jar
from project(":binjr-adapter-csv").jar
from project(":binjr-adapter-jfr").jar
from project(":binjr-adapter-rrd4j").jar
from project(":binjr-adapter-netdata").jar
// from project(":binjr-adapter-text").jar
from project(":binjr-adapter-logs").jar
}
task copyJpackageInputLibs(type: Copy) {
into "${buildDir}/tmp/input"
from(project(":binjr-core").configurations.runtimeClasspath) {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-jrds").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-jfr").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-csv").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-rrd4j").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-adapter-netdata").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
// from project(":binjr-adapter-text").configurations.runtimeClasspath {
// exclude "javafx-*.jar"
// }
from project(":binjr-adapter-logs").configurations.runtimeClasspath {
exclude "javafx-*.jar"
}
from project(":binjr-core").jar
from project(":binjr-adapter-jrds").jar
from project(":binjr-adapter-jfr").jar
from project(":binjr-adapter-csv").jar
from project(":binjr-adapter-rrd4j").jar
from project(":binjr-adapter-netdata").jar
// from project(":binjr-adapter-text").jar
from project(":binjr-adapter-logs").jar
}
task copyPlatformSpecific(type: Copy) {
into APP_IMAGE_PATH
from "${projectDir}/distribution/platforms/${OS_FAMILY}"
}
task copyResources(type: Copy) {
into "$APP_IMAGE_PATH/resources"
from "${projectDir}/distribution/resources"
}
task expandMdTemplates(type: Copy) {
from "${projectDir}/distribution/templates"
into "${buildDir}/tmp/expanded"
filteringCharset = 'UTF-8'
def changeHistory = new File("${project.projectDir}/CHANGELOG.md").getText("UTF-8")
def currentChanges = new File("${project.projectDir}/UNRELEASED.md").getText("UTF-8")
expand(["version" : "$BINJR_VERSION",
"releaseDate" : "${new SimpleDateFormat("EEE, d MMM yyyy").format(new Date())}",
"changeHistory" : "$changeHistory",
"currentChanges": "$currentChanges",
"tagName" : "v${BINJR_VERSION}"
])
}
task copyInfo(type: Copy, dependsOn: expandMdTemplates) {
from {
["${buildDir}/tmp/expanded/CHANGELOG.md",
"${buildDir}/tmp/expanded/LICENSE.md",
"${buildDir}/tmp/expanded/NOTICE.md",
"${buildDir}/tmp/expanded/README.md"]
}
into "${buildDir}/tmp/info"
}
markdownToHtml.dependsOn(copyInfo)
markdownToHtml {
sourceDir = file("${buildDir}/tmp/info")
outputDir = file("$APP_IMAGE_PATH")
doLast {
ConfigurableFileTree tree = fileTree(dir: "$APP_IMAGE_PATH")
tree.include '**/*.html'
tree.each { File file ->
String path = file.path
File newFile = new File("${APP_IMAGE_PATH}/tmp_${file.name}")
newFile << "<html lang=\"en\">\n" +
"<head>\n" +
" <title>" + (file.name - ".html") + "</title>\n" +
" <meta charset=\"utf-8\"/>\n" +
" <link rel=\"stylesheet\" href=\"./resources/css/plain.css\">\n" +
"</head>"
newFile << file.getText("utf-8")
if (!file.name.startsWith("LICENSE")) {
newFile << "<footer>\n" +
" <br>\n" +
" <hr>\n" +
" <p style=\"text-align:left;\">\n" +
" ${BINJR_COPYRIGHT}\n" +
" <span style=\"float:right;\"><a href=\"https://binjr.eu\">https://binjr.eu</a></span>\n" +
" </p>\n" +
"</footer>"
}
file.delete()
newFile.renameTo(path)
}
}
}
task downloadOpenJfxModules(type: Download) {
onlyIfModified true
src craftOpenJfxModsUrl()
dest new File(DL_CACHE_PATH, "openjfx-jmods_${OPENJFX_VERSION}.zip")
}
task downloadJlinkOpenJdk(type: Download) {
onlyIfModified true
src craftJlinkJdkUrl()
dest new File(DL_CACHE_PATH, "openjdk_${BUNDLE_JDK_VERSION}${IS_WINDOWS ? '.zip' : '.tar.gz'}")
}
task unzipOpenJfxModules(dependsOn: downloadOpenJfxModules, type: Copy) {
from zipTree(downloadOpenJfxModules.dest)
into "${buildDir}/jmods/"
}
task unzipJlinkOpenJdk(dependsOn: downloadJlinkOpenJdk, type: Copy) {
from zipTree(downloadJlinkOpenJdk.dest)
into "${buildDir}/jlinkOpenJDK/"
}
task untarJlinkOpenJdk(dependsOn: downloadJlinkOpenJdk, type: Copy) {
from tarTree(downloadJlinkOpenJdk.dest)
into "${buildDir}/jlinkOpenJDK/"
}
task createRuntimeImage(type: Exec) {
if (!IS_JAVAFX_BUNDLED) {
dependsOn unzipOpenJfxModules
}
def jlinkJdkDir
if (USE_BUILD_JDK_IN_BUNDLE) {
jlinkJdkDir = "${JDK_HOME}"
} else {
if (IS_WINDOWS) {
dependsOn unzipJlinkOpenJdk
} else {
dependsOn untarJlinkOpenJdk
}
jlinkJdkDir = "${buildDir}/jlinkOpenJDK/${BUNDLE_JDK_VERSION}${IS_MAC ? '/Contents/Home' : ''}"
}
workingDir project.projectDir
commandLine = [
"${jlinkJdkDir}/bin/jlink",
'-p', "${jlinkJdkDir}/jmods${ADDITIONAL_JMOD_PATH}",
'--add-modules', JLINK_ADD_MODULES,
'--strip-debug',
'--no-header-files',
'--no-man-pages',
"--vm=server",
"--compress=zip-6",
'--output', "${APP_IMAGE_PATH}/runtime"
]
doLast {
System.out.println("Application '${project.name}' packaged.")
System.out.println(" -> location: ${APP_IMAGE_PATH}/")
}
}
task prepareAppBundle(dependsOn: [copyAppLibs, copyPluginLibs, copyResources, copyPlatformSpecific, markdownToHtml, createRuntimeImage]) {
doFirst {
mkdir ARTIFACTS_ROOT_PATH
}
}
task listPackageContent(type: Exec, dependsOn: prepareAppBundle) {
workingDir APP_IMAGE_PATH
commandLine = [
"sh", "-c",
"find . -mindepth 1 | sed -n 's@^\\./@@p' > .installed"
]
}
task packageDistributionZip(type: Zip, dependsOn: prepareAppBundle) {
doFirst {
Files.copy(Paths.get("${projectDir}/distribution/bundlers/win_zip/binjr.ini"),
Paths.get("${APP_IMAGE_PATH}/binjr.ini"),
StandardCopyOption.REPLACE_EXISTING)
}
from APP_IMAGE_ROOT
destinationDirectory = ARTIFACTS_PATH_ZIP
archiveFileName = "${DISTRIBUTION_NAME}.zip"
outputs.dir ARTIFACTS_PATH_ZIP
}
task packageDistributionTar(type: Exec, dependsOn: [listPackageContent]) {
workingDir APP_IMAGE_ROOT
commandLine = [
"sh", "-c",
"ln -s \"${BINJR_VERSION}/binjr\" \"binjr\" && tar czf \"${ARTIFACTS_PATH_TGZ}/${DISTRIBUTION_NAME}.tar.gz\" \"${BINJR_VERSION}\" \"binjr\""
]
outputs.dir ARTIFACTS_PATH_TGZ
}
task wixRunHeat(type: Exec, dependsOn: prepareAppBundle) {
doFirst {
Files.copy(Paths.get("${projectDir}/distribution/bundlers/win_msi/binjr.ini"),
Paths.get("${APP_IMAGE_PATH}/binjr.ini"),
StandardCopyOption.REPLACE_EXISTING)
}
workingDir project.projectDir
commandLine = [
"${WIX_HEAT_HOME}/heat.exe",
"dir", "${APP_IMAGE_PATH}",
"-cg", "binjrFiles",
"-suid", "-gg", "-scom", "-sreg", "-sfrag", "-srd",
"-dr", "APPLICATIONFOLDER",
"-var", "var.buildSourceDir",
"-out", "${buildDir}/wix/binjrFiles.wxs"
]
}
//task wixRunCandle(type: Exec, dependsOn: [wixRunHeat]) {
// workingDir project.projectDir
// commandLine = [
// "${WIX_HOME}/bin/candle.exe",
// "-arch", "x64",
// "-out", "${buildDir}/wix/obj/",
// "${projectDir}/distribution/bundlers/win_msi/binjr.wxs",
// "${buildDir}/wix/binjrFiles.wxs",
// "-dbinjrVersion=${IS_BETA ? BINJR_BETA_VERSION : BINJR_VERSION_STEM}",
// "-dbuildSourceDir=${APP_IMAGE_PATH}",
// "-dresourcesDir=${projectDir}/distribution"
// ]
//}
//
//task wixRunLight(type: Exec, dependsOn: [wixRunCandle]) {
// workingDir project.projectDir
// commandLine = [
// "${WIX_HOME}/bin/light.exe",
// "-sw", "-sice:ICE38", "-sice:ICE64",
// "-out", "${ARTIFACTS_PATH_MSI}/${DISTRIBUTION_NAME}.msi",
// "${buildDir}/wix/obj/*.wixobj",
// "-ext", "WixUtilExtension", "-ext", "WixUIExtension.dll"
// ]
// outputs.dir ARTIFACTS_PATH_MSI
//}
task wixAddUiExt(type: Exec, dependsOn: wixRunHeat) {
commandLine = ["wix.exe", "extension", "add", "-g", "WixToolset.UI.wixext"]
}
task wixAddUtilExt(type: Exec, dependsOn: wixAddUiExt) {
commandLine = ["wix.exe", "extension", "add", "-g", "WixToolset.Util.wixext"]
}
task wixRunBuild(type: Exec, dependsOn: [wixAddUtilExt]) {
workingDir project.projectDir
commandLine = [
"wix.exe", "build", "-arch", "${getArch()}",
"${projectDir}/distribution/bundlers/win_msi/binjr.wxs",
"${buildDir}/wix/binjrFiles.wxs",
"-ext", "WixToolset.UI.wixext",
"-ext", "WixToolset.Util.wixext",
"-d", "binjrVersion=${IS_BETA ? BINJR_BETA_VERSION : BINJR_VERSION_STEM}",
"-d", "buildSourceDir=${APP_IMAGE_PATH}",
"-d", "resourcesDir=${projectDir}/distribution",
"-out", "${ARTIFACTS_PATH_MSI}/${DISTRIBUTION_NAME}.msi",
"-pdbtype", "none"
]
outputs.dir ARTIFACTS_PATH_MSI
}
task jpackageDmg(type: Exec, dependsOn: [prepareAppBundle, copyJpackageInputLibs]) {
workingDir ARTIFACTS_PATH_DMG
commandLine = [
"jpackage",
"--name", project.name,
"--input", "${buildDir}/tmp/input",
"--main-jar", "binjr-core-${BINJR_VERSION}.jar",
"--main-class", "eu.binjr.core.Bootstrap",
"--runtime-image", "${APP_IMAGE_PATH}/runtime",
"--type", "dmg",
"--copyright", BINJR_COPYRIGHT,
"--description", BINJR_DESCRIPTION,
"--app-version", "${IS_BETA ? BINJR_BETA_VERSION : BINJR_VERSION_STEM}",
"--icon", "${APP_IMAGE_PATH}/resources/icons/binjr.icns",
"--file-associations", "${projectDir}/distribution/bundlers/mac_dmg/file-associations.properties",
"--arguments", "--packaging=MAC_DMG",
"--java-options", "-Xmx${BINJR_MAX_HEAP_SIZE}",
"--java-options", "-XX:+UnlockExperimentalVMOptions",
"--java-options", "-XX:+UseShenandoahGC",
"--java-options", "-XX:ShenandoahGCHeuristics=compact",
"--java-options", "-XX:ShenandoahAllocationThreshold=20",
"--java-options", "--add-exports=javafx.base/com.sun.javafx.event=ALL-UNNAMED",
"--java-options", "--add-exports=javafx.controls/com.sun.javafx.charts=ALL-UNNAMED",
"--java-options", "--add-opens=javafx.graphics/javafx.geometry=ALL-UNNAMED",
"--java-options", "-Dapple.awt.application.appearance=system"
]
doLast {
def source = java.nio.file.Path.of("${ARTIFACTS_PATH_DMG}/${project.name}-${IS_BETA ? BINJR_BETA_VERSION : BINJR_VERSION_STEM}.dmg")
Files.move(source, source.resolveSibling("${DISTRIBUTION_NAME}.dmg"))
}
outputs.dir ARTIFACTS_PATH_DMG
}
task jpackagePkg(type: Exec, dependsOn: [prepareAppBundle, copyJpackageInputLibs]) {
workingDir ARTIFACTS_PATH_PKG
commandLine = [
"jpackage",
"--name", project.name,
"--input", "${buildDir}/tmp/input",
"--main-jar", "binjr-core-${BINJR_VERSION}.jar",
"--main-class", "eu.binjr.core.Bootstrap",
"--runtime-image", "${APP_IMAGE_PATH}/runtime",
"--type", "pkg",
"--copyright", BINJR_COPYRIGHT,
"--description", BINJR_DESCRIPTION,
"--app-version", "${IS_BETA ? BINJR_BETA_VERSION : BINJR_VERSION_STEM}",
"--icon", "${APP_IMAGE_PATH}/resources/icons/binjr.icns",
"--file-associations", "${projectDir}/distribution/bundlers/mac_pkg/file-associations.properties",
"--arguments", "--packaging=MAC_PKG",
"--java-options", "-Xmx${BINJR_MAX_HEAP_SIZE}",
"--java-options", "-XX:+UnlockExperimentalVMOptions",
"--java-options", "-XX:+UseShenandoahGC",
"--java-options", "-XX:ShenandoahGCHeuristics=compact",
"--java-options", "-XX:ShenandoahAllocationThreshold=20",
"--java-options", "--add-exports=javafx.base/com.sun.javafx.event=ALL-UNNAMED",
"--java-options", "--add-exports=javafx.controls/com.sun.javafx.charts=ALL-UNNAMED",
"--java-options", "--add-opens=javafx.graphics/javafx.geometry=ALL-UNNAMED",
"--java-options", "-Dapple.awt.application.appearance=system"
]
doLast {
def source = java.nio.file.Path.of("${ARTIFACTS_PATH_PKG}/${project.name}-${IS_BETA ? BINJR_BETA_VERSION : BINJR_VERSION_STEM}.pkg")
Files.move(source, source.resolveSibling("${DISTRIBUTION_NAME}.pkg"))
}
outputs.dir ARTIFACTS_PATH_PKG
}
task jpackageDeb(type: Exec, dependsOn: [prepareAppBundle, copyJpackageInputLibs]) {
workingDir ARTIFACTS_PATH_DEB
commandLine = [
"jpackage",
"--name", project.name,
"--input", "${buildDir}/tmp/input",
"--main-jar", "binjr-core-${BINJR_VERSION}.jar",
"--main-class", "eu.binjr.core.Bootstrap",
"--runtime-image", "${APP_IMAGE_PATH}/runtime",
"--type", "deb",
"--copyright", BINJR_COPYRIGHT,
"--description", BINJR_DESCRIPTION,
"--app-version", BINJR_VERSION,
"--icon", "${APP_IMAGE_PATH}/resources/icons/binjr.png",
"--license-file", "${projectDir}/LICENSE.md",
"--file-associations", "${projectDir}/distribution/bundlers/linux_deb/file-associations.properties",
"--resource-dir", "${projectDir}/distribution/bundlers/linux_deb/",
"--java-options", "-Xmx${BINJR_MAX_HEAP_SIZE}",
"--java-options", "-XX:+UnlockExperimentalVMOptions",
"--java-options", "-XX:+UseShenandoahGC",
"--java-options", "-XX:ShenandoahGCHeuristics=compact",
"--java-options", "-XX:ShenandoahAllocationThreshold=20",
"--java-options", "--add-exports=javafx.base/com.sun.javafx.event=ALL-UNNAMED",
"--java-options", "--add-exports=javafx.controls/com.sun.javafx.charts=ALL-UNNAMED",
"--java-options", "--add-opens=javafx.graphics/javafx.geometry=ALL-UNNAMED",
"--arguments", "--system-plugins-path=/opt/binjr/plugins",
"--arguments", "--packaging=LINUX_DEB",
"--linux-package-name", "binjr",
"--linux-deb-maintainer", "binjr@free.fr",
"--linux-app-category", "Utility",
"--linux-app-release", LINUX_APP_RELEASE,
"--linux-menu-group", "Utility",
"--linux-rpm-license-type", "Apache-2.0",
"--linux-shortcut",
"--temp", "${buildDir}/tmp/apt",
"--verbose"
]
doLast {
def source = java.nio.file.Path.of("${ARTIFACTS_PATH_DEB}/${project.name}_${BINJR_VERSION}-1_${OS_ARCH}.deb")
Files.move(source, source.resolveSibling("${DISTRIBUTION_NAME}.deb"))
}
outputs.dir ARTIFACTS_PATH_DEB
}
task jpackageRpm(type: Exec, dependsOn: [prepareAppBundle, copyJpackageInputLibs]) {
workingDir ARTIFACTS_PATH_RPM
commandLine = [
"jpackage",
"--name", project.name,
"--input", "${buildDir}/tmp/input",
"--main-jar", "binjr-core-${BINJR_VERSION}.jar",
"--main-class", "eu.binjr.core.Bootstrap",
"--runtime-image", "${APP_IMAGE_PATH}/runtime",
"--type", "rpm",
"--copyright", BINJR_COPYRIGHT,
"--description", BINJR_DESCRIPTION,
"--app-version", BINJR_VERSION.replace("-", "."),
"--icon", "${APP_IMAGE_PATH}/resources/icons/binjr.png",
"--license-file", "${projectDir}/LICENSE.md",
"--file-associations", "${projectDir}/distribution/bundlers/linux_rpm/file-associations.properties",
"--resource-dir", "${projectDir}/distribution/bundlers/linux_rpm/",
"--java-options", "-Xmx${BINJR_MAX_HEAP_SIZE}",
"--java-options", "-XX:+UnlockExperimentalVMOptions",
"--java-options", "-XX:+UseShenandoahGC",
"--java-options", "-XX:ShenandoahGCHeuristics=compact",
"--java-options", "-XX:ShenandoahAllocationThreshold=20",
"--java-options", "--add-exports=javafx.base/com.sun.javafx.event=ALL-UNNAMED",
"--java-options", "--add-exports=javafx.controls/com.sun.javafx.charts=ALL-UNNAMED",
"--java-options", "--add-opens=javafx.graphics/javafx.geometry=ALL-UNNAMED",
"--arguments", "--system-plugins-path=/opt/binjr/plugins",
"--arguments", "--packaging=LINUX_RPM",
"--linux-package-name", "binjr",
"--linux-app-category", "Utility",
"--linux-app-release", LINUX_APP_RELEASE,
"--linux-menu-group", "Utility",
"--linux-rpm-license-type", "Apache-2.0",
"--linux-shortcut",
"--temp", "${buildDir}/tmp/rpm",
"--verbose"
]
doLast {
def source = java.nio.file.Path.of("${ARTIFACTS_PATH_RPM}/${project.name}-${BINJR_VERSION.replace("-", ".")}-1.x86_64.rpm")
Files.move(source, source.resolveSibling("${DISTRIBUTION_NAME}.rpm"))
}
outputs.dir ARTIFACTS_PATH_RPM
}
task packageAsZip(type: WrapTaskForSigning, dependsOn: [packageDistributionZip]) {
from "${ARTIFACTS_PATH_ZIP}/${DISTRIBUTION_NAME}.zip"
destinationDirectory = ARTIFACTS_PATH_ZIP
archiveFileName = "${DISTRIBUTION_NAME}.zip"
}
task packageAsMsi(type: WrapTaskForSigning, dependsOn: [wixRunBuild]) {
from "${ARTIFACTS_PATH_MSI}/${DISTRIBUTION_NAME}.msi"
destinationDirectory = ARTIFACTS_PATH_MSI
archiveFileName = "${DISTRIBUTION_NAME}.msi"
}
task packageAsDmg(type: WrapTaskForSigning, dependsOn: [jpackageDmg]) {
from "${ARTIFACTS_PATH_DMG}/${DISTRIBUTION_NAME}.dmg"
destinationDirectory = ARTIFACTS_PATH_DMG
archiveFileName = "${DISTRIBUTION_NAME}.dmg"
}
task packageAsPkg(type: WrapTaskForSigning, dependsOn: [jpackagePkg]) {
from "${ARTIFACTS_PATH_PKG}/${DISTRIBUTION_NAME}.pkg"
destinationDirectory = ARTIFACTS_PATH_PKG
archiveFileName = "${DISTRIBUTION_NAME}.pkg"
}
task packageAsTarGz(type: WrapTaskForSigning, dependsOn: [packageDistributionTar]) {
from "${ARTIFACTS_PATH_TGZ}/${DISTRIBUTION_NAME}.tar.gz"
destinationDirectory = ARTIFACTS_PATH_TGZ
archiveFileName = "${DISTRIBUTION_NAME}.tar.gz"
}
task packageAsRpm(type: WrapTaskForSigning, dependsOn: [jpackageRpm]) {
from "${ARTIFACTS_PATH_RPM}/${DISTRIBUTION_NAME}.rpm"
destinationDirectory = ARTIFACTS_PATH_RPM
archiveFileName = "${DISTRIBUTION_NAME}.rpm"
}
task packageAsDeb(type: WrapTaskForSigning, dependsOn: [jpackageDeb]) {
from "${ARTIFACTS_PATH_DEB}/${DISTRIBUTION_NAME}.deb"
destinationDirectory = ARTIFACTS_PATH_DEB
archiveFileName = "${DISTRIBUTION_NAME}.deb"
}
signing {
sign packageAsZip
sign packageAsMsi
sign packageAsPkg
sign packageAsTarGz
sign packageAsRpm
sign packageAsDeb
}
task packageDistribution() {
if (IS_WINDOWS) {
finalizedBy(packageAsMsi, packageAsZip)
} else if (IS_MAC) {
finalizedBy(packageAsPkg, packageAsTarGz)
} else {
finalizedBy(packageAsTarGz, packageAsDeb, packageAsRpm)
}
}
task signPackageDistribution() {
if (IS_WINDOWS) {
finalizedBy(signPackageAsMsi, signPackageAsZip)
} else if (IS_MAC) {
finalizedBy(signPackageAsPkg, signPackageAsTarGz)
} else {
finalizedBy(signPackageAsTarGz, signPackageAsDeb, signPackageAsRpm)
}
}
def isNonStable = { String version ->
// Ignore javafx early access and glassfish beta
def regex = /(?i)^[0-9,.v-]+\-((ea)|(rc)|(alpha)|(b)|(m))[-\+]*[0-9.]+$/
return (version ==~ regex)
}
def craftPlatformClassifier() {
def classifier
if (IS_MAC) {
classifier = "mac"
if (OS_ARCH == "aarch64") {
classifier += "-aarch64"
}
} else if (IS_LINUX) {
classifier = "linux"
if (OS_ARCH == "aarch64") {
classifier += "-aarch64"
} else if (OS_ARCH == "aarch32" || OS_ARCH == "arm32") {
classifier += "-arm32"
}
} else if (IS_WINDOWS) {
classifier = "win"
if (OS_ARCH == "x86") {
classifier += "-x86"
}
}
if (IS_MONOCLE) {
classifier += "-monocle"
}
return classifier
}
def craftJlinkJdkUrl() {
def platform
switch (OS_FAMILY) {
case "windows":
platform = "windows"
break
case "linux":
platform = "linux"
break
case "mac":
platform = "mac"
break
default:
throw new Exception("Cannot download OpenJFX modules for unsupported platform: ${OS_FAMILY} - ${OS_ARCH}")
}
def arch = getArch()
return "https://api.adoptium.net/v3/binary/version/${BUNDLE_JDK_VERSION}/${platform}/${arch}/jdk/hotspot/normal/eclipse"
}
def craftOpenJfxModsUrl() {
def platform
switch (OS_FAMILY) {
case "windows":
platform = "windows"
break
case "linux":
platform = "linux"
break
case "mac":
platform = "osx"
break
default:
throw new Exception("Cannot download OpenJFX modules for unsupported platform: ${OS_FAMILY} - ${OS_ARCH}")
}
def arch = getArch()
return "https://download2.gluonhq.com/openjfx/${OPENJFX_VERSION_STEM}/openjfx-${OPENJFX_VERSION}_${platform}-${arch}_bin-jmods.zip"
}
def getArch() {
def arch
switch (OS_ARCH) {
case "amd64":
case "x86_64":
arch = "x64"
break
case "x86":
arch = "x86"
break
case "aarch64":
arch = "aarch64"
break
default:
throw new Exception("Cannot download OpenJFX modules for unsupported platform: ${OS_FAMILY} - ${OS_ARCH}")
}
return arch
}
dependencyUpdates {
rejectVersionIf {
isNonStable(it.candidate.version)
}
}
/**
* This class is a no-op copy task whose purpose is to allow using the
* standard gradle signing plugin to sign any arbitrary file.
* The idea is to piggy-back on the existing support for signing
* of tasks extending AbstractArchiveTask; to use it, simply declare a
* task of that type and use the path to the file to be signed both as
* the source and target of the archive.
* NB: No copy/move/archiving will actually take place.
*/
class WrapTaskForSigning extends AbstractArchiveTask {
@Override
protected CopyAction createCopyAction() {
return new noopCopyAction();
}
class noopCopyAction implements CopyAction {
@Override
WorkResult execute(CopyActionProcessingStream stream) {
return WorkResults.didWork(true);
}
}
}