Skip to content

Commit

Permalink
Merge pull request #21 from GerardPaligot/feat/firebase/kmp
Browse files Browse the repository at this point in the history
Road to KMP 🚀
  • Loading branch information
martinbonnin authored Mar 25, 2024
2 parents 45aab71 + ea18d38 commit fe21e9a
Show file tree
Hide file tree
Showing 123 changed files with 2,167 additions and 1,622 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,8 @@ repositories {
val openfeedbackVersion = "0.1.2"
dependencies {
// Material 3
implementation("io.openfeedback:feedback-android-sdk-m3:$openfeedbackVersion")
implementation("io.openfeedback:feedback-sdk-m3:$openfeedbackVersion")
// ViewModel
implementation("io.openfeedback:feedback-android-sdk-viewmodel:$openfeedbackVersion")
implementation("io.openfeedback:feedback-sdk-viewmodel:$openfeedbackVersion")
}
```
26 changes: 7 additions & 19 deletions build-logic/build.gradle.kts
Original file line number Diff line number Diff line change
@@ -1,34 +1,22 @@
plugins {
`embedded-kotlin`
`kotlin-dsl`
`java-gradle-plugin`
}

group = "build-logic"

repositories {
mavenCentral()
google()
gradlePluginPortal()
}

dependencies {
implementation(gradleApi())
implementation(libs.vespene)
implementation(libs.kotlin.coroutines.core)
implementation(libs.android.gradle.plugin)
implementation(libs.kotlin.gradle.plugin)
}

gradlePlugin {
plugins {
register("io.openfeedback.plugins.lib") {
id = "io.openfeedback.plugins.lib"
implementationClass = "io.openfeedback.plugins.LibraryPlugin"
}
register("io.openfeedback.plugins.compose.lib") {
id = "io.openfeedback.plugins.compose.lib"
implementationClass = "io.openfeedback.plugins.ComposeLibraryPlugin"
}
register("io.openfeedback.plugins.app") {
id = "io.openfeedback.plugins.app"
implementationClass = "io.openfeedback.plugins.AppPlugin"
}
}
implementation(libs.kotlin.serialization.plugin)
implementation(libs.moko.gradle.plugin)
implementation(libs.jetbrains.compose)
}
3 changes: 2 additions & 1 deletion build-logic/settings.gradle.kts
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
rootProject.name = "build-logic"
enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS")

dependencyResolutionManagement {
versionCatalogs {
create("libs") {
from(files("../libs.versions.toml"))
from(files("../gradle/libs.versions.toml"))
}
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
package io.openfeedback

object EnvVarKeys {
object Nexus {
const val username = "SONATYPE_NEXUS_USERNAME"
Expand All @@ -16,4 +14,4 @@ object EnvVarKeys {
const val event = "GITHUB_EVENT_NAME"
const val ref = "GITHUB_REF"
}
}
}
23 changes: 23 additions & 0 deletions build-logic/src/main/kotlin/accessors.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import org.gradle.api.Project
import org.gradle.api.plugins.ExtensionAware
import org.jetbrains.compose.ComposePlugin
import org.jetbrains.kotlin.gradle.dsl.KotlinMultiplatformExtension


inline fun <reified T> Project.extensionOrNull(): T? {
return extensions.findByType(T::class.java)
}

inline fun <reified T> Project.extension(): T {
return extensionOrNull<T>() ?: error("No extension of type '${T::class.java.name}")
}

inline fun <reified T> Project.extension(block: T.() -> Unit) {
extension<T>().apply(block)
}


val KotlinMultiplatformExtension.compose: ComposePlugin.Dependencies
get() {
return (this as ExtensionAware).extensions.getByName("compose") as ComposePlugin.Dependencies
}
221 changes: 221 additions & 0 deletions build-logic/src/main/kotlin/internal/Publishing.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,221 @@
package internal

import EnvVarKeys
import applyPublishingPlugin
import applySigningPlugin
import extension
import kotlinx.coroutines.runBlocking
import kotlinx.coroutines.withTimeout
import net.mbonnin.vespene.lib.NexusStagingClient
import org.gradle.api.Project
import org.gradle.api.Task
import org.gradle.api.UnknownDomainObjectException
import org.gradle.api.artifacts.dsl.RepositoryHandler
import org.gradle.api.logging.LogLevel
import org.gradle.api.plugins.ExtensionContainer
import org.gradle.api.provider.Provider
import org.gradle.api.publish.PublishingExtension
import org.gradle.api.publish.maven.MavenPublication
import org.gradle.api.tasks.TaskProvider
import org.gradle.plugins.signing.Sign
import org.jetbrains.kotlin.gradle.plugin.mpp.KotlinAndroidTarget
import kotlin.time.Duration.Companion.minutes

internal fun Project.configurePublications(
publishing: PublishingExtension,
artifactName: String
) {
val project = this

publishing.publications.configureEach {
(it as MavenPublication).apply {
groupId = "io.openfeedback"
version = project.rootProject.version.toString()
artifactId = artifactName

pom {
it.name.set(artifactName)

it.description.set(artifactId)
it.url.set("https://github.com/paug/openfeedback-android-sdk")

it.scm {
it.url.set("https://github.com/paug/openfeedback-android-sdk")
it.connection.set("https://github.com/paug/openfeedback-android-sdk")
it.developerConnection.set("https://github.com/paug/openfeedback-android-sdk")
}

it.licenses {
it.license {
it.name.set("MIT License")
it.url.set("https://github.com/paug/openfeedback-android-sdk/blob/master/LICENSE")
}
}

it.developers {
it.developer {
it.id.set("openfeedback team")
it.name.set("openfeedback team")
}
}
}
}
}
}


internal fun Project.configurePublishingInternal(
androidTarget: KotlinAndroidTarget
) {
val publishing = applyPublishingPlugin()

/**
* Signing
*/
val privateKey = System.getenv(EnvVarKeys.GPG.privateKey)
val password = System.getenv(EnvVarKeys.GPG.password)
applySigningPlugin().apply {
// GPG_PRIVATE_KEY should contain the armoured private key that starts with -----BEGIN PGP PRIVATE KEY BLOCK-----
// It can be obtained with gpg --armour --export-secret-keys KEY_ID
useInMemoryPgpKeys(
privateKey,
password
)
sign(publishing.publications)
}

tasks.withType(Sign::class.java).configureEach {
it.isEnabled = !privateKey.isNullOrBlank()
}

/**
* Android publication
*/
androidTarget.apply {
publishLibraryVariants("release")
}

/**
* Pom
*/
configurePublications(
publishing = publishing,
artifactName = name
)

/**
* Repositories
*/
publishing.repositories {
it.mavenSonatypeSnapshot(project = project)
it.mavenSonatypeStaging(project = project)
}

rootProject.tasks.named("ossStagingRelease").configure {
it.dependsOn(this@configurePublishingInternal.tasks.named("publishAllPublicationsToOssStagingRepository"))
}
}

private fun Project.getOrCreateRepoIdTask(): TaskProvider<Task> {
return try {
rootProject.tasks.named("createStagingRepo")
} catch (e: UnknownDomainObjectException) {
rootProject.tasks.register("createStagingRepo") {
it.outputs.file(rootProject.layout.buildDirectory.file("stagingRepoId"))

it.doLast {
val repoId = runBlocking {
nexusStagingClient.createRepository(
profileId = System.getenv(EnvVarKeys.Nexus.profileId),
description = "io.openfeedback ${rootProject.version}"
)
}
logger.log(LogLevel.LIFECYCLE, "repo created: $repoId")
it.outputs.files.singleFile.writeText(repoId)
}
}
}
}

fun Project.publishIfNeededTaskProvider(): TaskProvider<Task> {
return try {
tasks.named("publishIfNeeded")
} catch (ignored: Exception) {
tasks.register("publishIfNeeded")
}
}

private val baseUrl = "https://s01.oss.sonatype.org/service/local/"

private val nexusStagingClient by lazy {
NexusStagingClient(
baseUrl = baseUrl,
username = System.getenv(EnvVarKeys.Nexus.username)
?: error("please set the ${EnvVarKeys.Nexus.username} environment variable"),
password = System.getenv(EnvVarKeys.Nexus.password)
?: error("please set the ${EnvVarKeys.Nexus.password} environment variable"),
)
}

fun Project.getOrCreateRepoId(): Provider<String> {
return getOrCreateRepoIdTask().map {
it.outputs.files.singleFile.readText()
}
}

fun Project.getOrCreateRepoUrl(): Provider<String> {
return getOrCreateRepoId().map { "${baseUrl}staging/deployByRepositoryId/$it/" }
}

fun Task.closeAndReleaseStagingRepository(repoId: String) {
runBlocking {
logger.log(LogLevel.LIFECYCLE, "Closing repository $repoId")
nexusStagingClient.closeRepositories(listOf(repoId))
withTimeout(5.minutes) {
nexusStagingClient.waitForClose(repoId, 1000) {
logger.log(LogLevel.LIFECYCLE, ".")
}
}
nexusStagingClient.releaseRepositories(listOf(repoId), true)
}
}

internal fun Project.registerReleaseTask(name: String): TaskProvider<Task> {
val task = try {
rootProject.tasks.named(name)
} catch (e: UnknownDomainObjectException) {
val repoId = getOrCreateRepoId()
rootProject.tasks.register(name) {
it.inputs.property(
"repoId",
repoId
)
it.doLast {
it.closeAndReleaseStagingRepository(it.inputs.properties.get("repoId") as String)
}
}
}

return task
}

fun RepositoryHandler.mavenSonatypeSnapshot(project: Project) = maven {
it.name = "ossSnapshots"
it.url = project.uri("https://s01.oss.sonatype.org/content/repositories/snapshots/")
it.credentials {
it.username = System.getenv(EnvVarKeys.Nexus.username)
it.password = System.getenv(EnvVarKeys.Nexus.password)
}
}

fun RepositoryHandler.mavenSonatypeStaging(project: Project) = maven {
it.name = "ossStaging"
it.setUrl {
project.uri(project.getOrCreateRepoUrl())
}
it.credentials {
it.username = System.getenv(EnvVarKeys.Nexus.username)
it.password = System.getenv(EnvVarKeys.Nexus.password)
}
}

10 changes: 0 additions & 10 deletions build-logic/src/main/kotlin/io/openfeedback/OpenFeedback.kt

This file was deleted.

This file was deleted.

Loading

0 comments on commit fe21e9a

Please sign in to comment.