Skip to content

Commit

Permalink
config: add scripts and modules
Browse files Browse the repository at this point in the history
  • Loading branch information
Tamim Attafi committed Jun 30, 2024
1 parent 01abcbe commit 79a13a1
Show file tree
Hide file tree
Showing 20 changed files with 820 additions and 7 deletions.
29 changes: 29 additions & 0 deletions .github/workflows/publish.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
name: Publish

on:
release:
# We'll run this workflow when a new GitHub release is created
types: [published]

jobs:
publish:
name: Release build and publish
runs-on: macos-latest
steps:
- name: Check out code
uses: actions/checkout@v2
- name: Set up JDK 17
uses: actions/setup-java@v2
with:
distribution: adopt
java-version: 17

# Runs upload, and then closes & releases the repository
- name: Publish to MavenCentral
run: ./gradlew publishAllPublicationsToMavenCentralRepository
env:
ORG_GRADLE_PROJECT_mavenCentralUsername: ${{ secrets.ORG_GRADLE_PROJECT_mavenCentralUsername }}
ORG_GRADLE_PROJECT_mavenCentralPassword: ${{ secrets.ORG_GRADLE_PROJECT_mavenCentralPassword }}
ORG_GRADLE_PROJECT_signingInMemoryKey: ${{ secrets.ORG_GRADLE_PROJECT_signingInMemoryKey }}
ORG_GRADLE_PROJECT_signingInMemoryKeyId: ${{ secrets.ORG_GRADLE_PROJECT_signingInMemoryKeyId }}
ORG_GRADLE_PROJECT_signingInMemoryKeyPassword: ${{ secrets.ORG_GRADLE_PROJECT_signingInMemoryKeyPassword }}
36 changes: 29 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,22 +2,44 @@
Kotlin Multiplatform library template for quick-starts without dealing with boilerplate code

## Introductions

It covers the following boilerplate

1. Publication to local and remote maven repository
2. Multiplatform module conventions
3. Gradle files and build scripts
4. Version catalog
5. Popular gitignore setting
6. GitHub actions script
7. Sample app
5. Popular gitignore settings
6. GitHub release actions script
7. Sample shared module

## Usage
To use this template all you have to do is to follow these steps:

1. Download a zip file or clone this repository (Don't forget to change git remote settings)
2. Replace `com.attafitamim.kalib` with your package using `Command + Shift + R`
3. Update `README.md` file
2. Replace `com.attafitamim.kalib` with your package everywhere in the project
3. Replace `klib-template` with your library name everywhere in the project
4. Adjust targets in `MultiplatformConventions.kt`
5. Adjust publishing information in `PublishConventions.kt`
6. Update `README.md` file

That's it! Now you can add your modules, dependencies, adjust targets and start coding!

## Maven central
To publish your library to maven central you need to follow these steps:

1. Crate an account on [central portal](https://central.sonatype.com/)
2. Create a namespace with your package as shown in these [docs](https://central.sonatype.org/register/namespace/)
3. Generate a token as shown [here](https://central.sonatype.org/publish/generate-portal-token/)
4. Generate gpg key using your sonatype email, upload it, then confirm your email using the received link in your inbox
5. Add secrets for publishing as shown [here](https://vanniktech.github.io/gradle-maven-publish-plugin/central/#secrets)
6. Don't forget to add secrets as environment variables for GitHub actions as shown [here](https://docs.github.com/en/actions/learn-github-actions/variables)

To publish your artifacts to central portal you can either run `./gradlew publishAllPublicationsToMavenCentralRepository` locally or create a GitBub release

> [!IMPORTANT]
> Don't forget to change publishing version in `PublishConventions.kt`
That's it! Now you can add your modules, dependencies, adjust targets and start coding!
## Future plans
1. Upgrade to Kotlin 2.0.0
2. Add testing examples and GitHub actions for the matter
3. Add lint example and GitHub actions for the matter
27 changes: 27 additions & 0 deletions build.gradle.kts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
plugins {
alias(libs.plugins.android.application).apply(false)
alias(libs.plugins.android.library).apply(false)
alias(libs.plugins.kotlin.android).apply(false)
alias(libs.plugins.kotlin.jvm).apply(false)
alias(libs.plugins.kotlin.multiplatform).apply(false)
alias(libs.plugins.kotlin.js).apply(false)
alias(libs.plugins.kotlin.native.cocoapods).apply(false)
alias(libs.plugins.dokka)
alias(libs.plugins.maven.publish)
}

buildscript {
repositories {
mavenLocal()
mavenCentral()
google()
}
}

allprojects {
repositories {
mavenLocal()
mavenCentral()
google()
}
}
20 changes: 20 additions & 0 deletions convention/multiplatform/build.gradle.kts
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
plugins {
alias(libs.plugins.kotlin.jvm)
id(libs.plugins.java.gradle.plugin.get().pluginId)
}

kotlin {
jvmToolchain(17)
}

gradlePlugin {
plugins.create("multiplatform") {
id = "com.attafitamim.klib.multiplatform"
implementationClass = "com.attafitamim.klib.multiplatform.MultiplatformConventions"
}
}

dependencies {
compileOnly(libs.kotlin.plugin)
compileOnly(libs.android.build.tools)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
package com.attafitamim.klib.multiplatform

import com.android.build.api.dsl.LibraryExtension
import org.gradle.api.JavaVersion
import org.gradle.api.Plugin
import org.gradle.api.Project
import org.jetbrains.kotlin.gradle.dsl.KotlinMultiplatformExtension
import org.jetbrains.kotlin.gradle.dsl.kotlinExtension

class MultiplatformConventions : Plugin<Project> {
override fun apply(project: Project) {
project.plugins.apply {
apply("org.jetbrains.kotlin.multiplatform")
apply("com.android.library")
}

val extension = project.kotlinExtension as KotlinMultiplatformExtension
extension.apply {
applyDefaultHierarchyTemplate()
jvmToolchain(17)

jvm()

androidTarget {
compilations.all {
it.kotlinOptions {
jvmTarget = "17"
}
}
}

js {
browser {
testTask {
it.useKarma {
useChromeHeadless()
}
}
}
compilations.configureEach {
it.kotlinOptions {
moduleKind = "umd"
}
}
}

iosX64()
iosArm64()
iosSimulatorArm64()
}

val jvmSourceSet = extension.sourceSets.getByName("jvmMain")
val androidSourceSet = extension.sourceSets.getByName("androidMain")
androidSourceSet.dependsOn(jvmSourceSet)

val androidExtension = project.extensions.getByName("android") as LibraryExtension
androidExtension.apply {
namespace = "com.attafitamim.klib.${project.name}"
compileSdk = 34

defaultConfig {
minSdk = 21
}

compileOptions {
sourceCompatibility = JavaVersion.VERSION_17
targetCompatibility = JavaVersion.VERSION_17
}
}
}
}
20 changes: 20 additions & 0 deletions convention/publishing/build.gradle.kts
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
plugins {
alias(libs.plugins.kotlin.jvm)
id(libs.plugins.java.gradle.plugin.get().pluginId)
}

kotlin {
jvmToolchain(17)
}

gradlePlugin {
plugins.create("publish") {
id = "com.attafitamim.klib.publish"
implementationClass = "com.attafitamim.klib.publish.PublishConventions"
}
}

dependencies {
compileOnly(libs.kotlin.plugin)
compileOnly(libs.maven.publish.plugin)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
package com.attafitamim.klib.publish

import com.vanniktech.maven.publish.MavenPublishBaseExtension
import org.gradle.api.Plugin
import org.gradle.api.Project
import org.gradle.api.publish.maven.MavenPom
import org.gradle.api.publish.maven.MavenPomDeveloper
import org.gradle.api.publish.maven.MavenPomLicense
import org.gradle.api.publish.maven.MavenPomScm

class PublishConventions : Plugin<Project> {

private val version = "0.1.0"
private val group = "com.attafitamim.klib"

override fun apply(project: Project) {
project.plugins.apply("com.vanniktech.maven.publish")

val mavenPublishing = project.extensions.getByName("mavenPublishing")
as MavenPublishBaseExtension

val artifact = project.fullName
mavenPublishing.apply {
coordinates(group, artifact, version)
pom(MavenPom::configure)
publishToMavenCentral(
com.vanniktech.maven.publish.SonatypeHost.CENTRAL_PORTAL,
automaticRelease = true
)
signAllPublications()
}
}
}

private val Project.fullName: String get() {
val names = ArrayList<String>()
names.add(name)

var currentProject = this
while (currentProject.parent != null && currentProject.parent != rootProject) {
val parentProject = currentProject.parent!!
names.add(parentProject.name)
currentProject = parentProject
}

return names.reversed().joinToString("-")
}

private fun MavenPom.configure() {
name.set("klib-template")
description.set("klib-template for Kotlin Multiplatform")
url.set("https://github.com/tamimattafi/klib-template")

licenses { licenseSpec ->
licenseSpec.license(MavenPomLicense::configure)
}

developers { developerSpec ->
developerSpec.developer(MavenPomDeveloper::configure)
}

scm(MavenPomScm::configure)
}

private fun MavenPomLicense.configure() {
name.set("Apache License 2.0")
url.set("https://github.com/tamimattafi/klib-template/blob/main/LICENSE")
}

private fun MavenPomDeveloper.configure() {
id.set("attafitamim")
name.set("Tamim Attafi")
email.set("[email protected]")
}

private fun MavenPomScm.configure() {
connection.set("scm:git:github.com/tamimattafi/klib-template.git")
developerConnection.set("scm:git:ssh://github.com/tamimattafi/klib-template.git")
url.set("https://github.com/tamimattafi/klib-template/tree/main")
}
27 changes: 27 additions & 0 deletions convention/settings.gradle.kts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS")
pluginManagement {
repositories {
gradlePluginPortal()
mavenLocal()
mavenCentral()
gradlePluginPortal()
}
}

dependencyResolutionManagement {
@Suppress("UnstableApiUsage")
repositories {
mavenLocal()
mavenCentral()
google()
}

versionCatalogs.create("libs") {
from(files("../gradle/libs.versions.toml"))
}
}

rootProject.name = "convention"

include(":multiplatform")
include(":publishing")
34 changes: 34 additions & 0 deletions gradle.properties
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
# Gradle
org.gradle.daemon=true
org.gradle.jvmargs=-Xmx16384M -Xms8192M
org.gradle.parallel=true
useDeprecatedNdkorg.gradle.configureondemand=true
org.gradle.caching=true

# Kotlin
ksp.incremental.intermodule=true

# Android
android.enableJetifier=true
android.enableR8.fullMode=true
android.nonFinalResIds=false
android.nonTransitiveRClass=false
android.useAndroidX=true
apmsInstrumentationEnabled=false
android.compileOptions.incremental =false

# MPP
kotlin.mpp.enableCInteropCommonization=true
kotlin.mpp.androidSourceSetLayoutVersion=2
kotlin.js.compiler=ir

# atomicfu
kotlinx.atomicfu.enableJvmIrTransformation=true
kotlinx.atomicfu.enableJsIrTransformation=true

# Compose
org.jetbrains.compose.experimental.wasm.enabled=true
org.jetbrains.compose.experimental.jscanvas.enabled=true

# JS
development=false
Loading

0 comments on commit 79a13a1

Please sign in to comment.