Skip to content

Update jvm artifact deployment for new maven central portal #838

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 13 commits into
base: master
Choose a base branch
from
Open
14 changes: 11 additions & 3 deletions .github/workflows/deploy_jvm.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,10 @@ on:
type: string

env:
GODOT_KOTLIN_GPG_PRIVATE_KEY_ASCII: ${{ secrets.GODOT_KOTLIN_GPG_PRIVATE_KEY_ASCII }}
GODOT_KOTLIN_GPG_PRIVATE_KEY_ASCII: ${{ secrets.GODOT_KOTLIN_GPG_PRIVATE_KEY_ASCII_CLEANED }} # TODO: remove old key and rename this one once we're sure that the new deployment works
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would rename GODOT_KOTLIN prefix to UTOPIA_RISE

GODOT_KOTLIN_GPG_KEY_PASSPHRASE: ${{ secrets.GODOT_KOTLIN_GPG_KEY_PASSPHRASE }}
GODOT_KOTLIN_MAVEN_CENTRAL_TOKEN_USERNAME: ${{ secrets.GODOT_KOTLIN_MAVEN_CENTRAL_TOKEN_USERNAME }}
GODOT_KOTLIN_MAVEN_CENTRAL_TOKEN_PASSWORD: ${{ secrets.GODOT_KOTLIN_MAVEN_CENTRAL_TOKEN_PASSWORD }}
GODOT_KOTLIN_MAVEN_CENTRAL_PORTAL_TOKEN_USERNAME: ${{ secrets.GODOT_KOTLIN_MAVEN_CENTRAL_PORTAL_TOKEN_USERNAME }} # TODO: remove old username and password from secrets once we're sure the deployment works
GODOT_KOTLIN_MAVEN_CENTRAL_PORTAL_TOKEN_PASSWORD: ${{ secrets.GODOT_KOTLIN_MAVEN_CENTRAL_PORTAL_TOKEN_PASSWORD }} # TODO: remove old username and password from secrets once we're sure the deployment works
GRADLE_PUBLISH_KEY: ${{ secrets.GRADLE_PUBLISH_KEY }}
GRADLE_PUBLISH_SECRET: ${{ secrets.GRADLE_PUBLISH_SECRET }}
GODOT_KOTLIN_INTELLIJ_PLUGIN_PUBLISH: ${{secrets.GODOT_KOTLIN_INTELLIJ_PLUGIN_PUBLISH }}
Expand Down Expand Up @@ -47,6 +47,14 @@ jobs:
with:
cache-read-only: ${{ github.ref != 'refs/heads/master' }}

- name: Setup publish gradle properties
shell: sh
run: |
echo "mavenCentralUsername=$GODOT_KOTLIN_MAVEN_CENTRAL_PORTAL_TOKEN_USERNAME" >> ~/.gradle/gradle.properties
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why do we write those to properties ?

echo "mavenCentralPassword=$GODOT_KOTLIN_MAVEN_CENTRAL_PORTAL_TOKEN_PASSWORD" >> ~/.gradle/gradle.properties
echo "signingInMemoryKey=$GODOT_KOTLIN_GPG_PRIVATE_KEY_ASCII" >> ~/.gradle/gradle.properties
echo "signingInMemoryKeyPassword=$GODOT_KOTLIN_GPG_KEY_PASSPHRASE" >> ~/.gradle/gradle.properties

- name: Publish common
shell: sh
run: |
Expand Down
1 change: 1 addition & 0 deletions kt/build-logic/convention/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ kotlin {
dependencies {
compileOnly(kotlin("gradle-plugin", version = libs.versions.kotlin.get()))
implementation(libs.grgit)
implementation(libs.maven.publish)
}

gradlePlugin {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,83 +1,45 @@

package publish

import com.vanniktech.maven.publish.MavenPublishBaseExtension
import com.vanniktech.maven.publish.MavenPublishPlugin
import com.vanniktech.maven.publish.SonatypeHost
import org.gradle.api.Plugin
import org.gradle.api.Project
import org.gradle.api.plugins.JavaPluginExtension
import org.gradle.api.publish.PublishingExtension
import org.gradle.api.publish.maven.MavenPublication
import org.gradle.api.tasks.SourceSetContainer
import org.gradle.jvm.tasks.Jar
import org.gradle.plugins.signing.Sign
import org.gradle.plugins.signing.SigningExtension

@Suppress("unused") // false positive
class PublishToMavenCentralPlugin : Plugin<Project> {
override fun apply(target: Project) {
target.plugins.apply("maven-publish")

val ossrhUser = target.propOrEnv("GODOT_KOTLIN_MAVEN_CENTRAL_TOKEN_USERNAME")
val ossrhPassword = target.propOrEnv("GODOT_KOTLIN_MAVEN_CENTRAL_TOKEN_PASSWORD")
val signingKey = target.propOrEnv("GODOT_KOTLIN_GPG_PRIVATE_KEY_ASCII")
val signingPassword = target.propOrEnv("GODOT_KOTLIN_GPG_KEY_PASSPHRASE")
val canSign = ossrhUser != null && ossrhPassword != null && signingKey != null && signingPassword != null

if (canSign) {
target.plugins.apply("signing")
target.logger.info("Will sign artifact for project \"${target.name}\" and setup publishing")
} else {
target.logger.warn("Cannot sign project \"${target.name}\" as credentials are missing. Will not setup signing and remote publishing credentials. Publishing will only work to maven local!")
}

target.afterEvaluate { project ->
val isReleaseMode = !(project.version as String).endsWith("-SNAPSHOT")

if (canSign) { // for local development, If missing in CI it will fail later on deploy so we would notice the issue then
project.extensions.configure(SigningExtension::class.java) { signingExtension ->
signingExtension.useInMemoryPgpKeys(signingKey, signingPassword)
project.extensions.findByType(PublishingExtension::class.java)?.publications?.all { publication ->
signingExtension.sign(publication)
}
}
}
target.plugins.apply(org.gradle.api.publish.maven.plugins.MavenPublishPlugin::class.java)

project.extensions.getByType(JavaPluginExtension::class.java).apply {
withSourcesJar()
withJavadocJar()
}
target.afterEvaluate { evaluatedProject ->
val mavenCentralUser = target.propOrEnv("GODOT_KOTLIN_MAVEN_CENTRAL_PORTAL_TOKEN_USERNAME") ?: target.propOrEnv("mavenCentralUsername")
val mavenCentralPassword = target.propOrEnv("GODOT_KOTLIN_MAVEN_CENTRAL_PORTAL_TOKEN_PASSWORD") ?: target.propOrEnv("mavenCentralPassword")
val gpgInMemoryKey = target.propOrEnv("GODOT_KOTLIN_GPG_PRIVATE_KEY_ASCII") ?: target.propOrEnv("signingInMemoryKey")
val gpgPassword = target.propOrEnv("GODOT_KOTLIN_GPG_KEY_PASSPHRASE") ?: target.propOrEnv("signingInMemoryKeyPassword")

project.extensions.getByType(PublishingExtension::class.java).apply {
repositories.apply {
maven { mavenArtifactRepository ->
val targetRepo = if (isReleaseMode) {
"https://s01.oss.sonatype.org/service/local/staging/deploy/maven2/"
} else {
"https://s01.oss.sonatype.org/content/repositories/snapshots/"
}
mavenArtifactRepository.setUrl(targetRepo)
val canSign = mavenCentralUser != null && mavenCentralPassword != null && gpgInMemoryKey != null && gpgPassword != null

if (canSign) {
mavenArtifactRepository.credentials { passwordCredentials ->
passwordCredentials.username = ossrhUser
passwordCredentials.password = ossrhPassword
}
}
}
}
target.extensions.getByType(PublishingExtension::class.java).apply {
publications { publicationContainer ->
publicationContainer.all { publication ->
if (publication is MavenPublication) {
publication.groupId = "com.utopia-rise"
val artifactId = publication.artifactId
publication.artifactId = if (artifactId.isNullOrEmpty()) project.name else artifactId
publication.version = project.version as String
publication.artifactId = if (artifactId.isNullOrEmpty()) target.name else artifactId
publication.version = target.version as String

publication.pom { mavenPom ->
mavenPom.url.set("https://github.com/utopia-rise/godot-kotlin-jvm.git")

if (mavenPom.name.getOrElse("").isNullOrEmpty()) {
mavenPom.name.set(project.name)
mavenPom.name.set(target.name)
}
if (mavenPom.description.getOrElse("").isNullOrEmpty()) {
mavenPom.description.set(project.description ?: "Godot kotlin jvm module")
mavenPom.description.set(target.description ?: "Godot kotlin jvm module")
}

mavenPom.scm { mavenPomScm ->
Expand Down Expand Up @@ -127,20 +89,33 @@ class PublishToMavenCentralPlugin : Plugin<Project> {
}
}


if (canSign) {
project
.tasks
.filter { task -> task.name.startsWith("publish") }
.forEach { task ->
task.dependsOn(project.tasks.withType(Sign::class.java))
}
evaluatedProject.logger.info("Will sign artifact for project \"${evaluatedProject.name}\" and setup publishing")

evaluatedProject.pluginManager.apply(MavenPublishPlugin::class.java)
evaluatedProject.extensions.getByType(MavenPublishBaseExtension::class.java).apply {
publishToMavenCentral(SonatypeHost.CENTRAL_PORTAL)
signAllPublications()
}

target.afterEvaluate {
target
.tasks
.filter { task -> task.name.startsWith("publish") }
.forEach { task ->
task.dependsOn(target.tasks.withType(Sign::class.java))
}
}
} else {
evaluatedProject.logger.warn("Cannot sign project \"${evaluatedProject.name}\" as credentials are missing. Will not setup signing and remote publishing credentials. Publishing will only work to maven local!")
}
}
}
}

fun Project.propOrEnv(name: String): String? {
var property: String? = findProperty(name) as String?
var property: String? = findProperty(name) as? String?
if (property == null) {
property = System.getenv(name)
}
Expand Down
3 changes: 3 additions & 0 deletions kt/gradle/libs.versions.toml
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ jacksonDataFormatXml = "2.18.2" # https://mvnrepository.com/artifact/com.fasterx
grgit = "5.3.0" # https://github.com/ajoberstar/grgit/releases

gradlePublish = "1.3.1" # https://plugins.gradle.org/plugin/com.gradle.plugin-publish
maven-publish="0.32.0" # https://github.com/vanniktech/gradle-maven-publish-plugin/releases

changelog = "2.2.1" # https://github.com/JetBrains/gradle-changelog-plugin/releases
gradleIntelliJPlugin = "2.3.0" # https://github.com/JetBrains/intellij-platform-gradle-plugin/releases
Expand All @@ -41,6 +42,8 @@ jacksonDataFormatXml = { module = "com.fasterxml.jackson.dataformat:jackson-data
grgit = { module = "org.ajoberstar.grgit:grgit-gradle", version.ref = "grgit" }
ideaSync = { module = "org.jetbrains.gradle.plugin.idea-ext:org.jetbrains.gradle.plugin.idea-ext.gradle.plugin", version.ref = "ideaSync" }

maven-publish = { group = "com.vanniktech", name = "gradle-maven-publish-plugin", version.ref = "maven-publish" } # needed for publishing to new maven central repositories

[plugins]
changelog = { id = "org.jetbrains.changelog", version.ref = "changelog" }
gradleIntelliJPlugin = { id = "org.jetbrains.intellij.platform", version.ref = "gradleIntelliJPlugin" }
Expand Down
Loading