- VERSION at repo root (0.1.2); bump it to cut a release - App: generated AppVersion.kt (config-cache-safe Gradle task with VERSION as declared input) shown in Settings; sent to the gateway via X-Iris-App-Version header on the SSE open - Gateway: reports its own version in hello.ack server_caps.app_version (read from the repo-root VERSION via the plugin symlink); stores the app's version in the device registry caps (merge, not overwrite, so an old app reconnecting without the header doesn't wipe it) - Settings: app + gateway version rows, mismatch hint, and a best-effort Gitea latest-release check (ReleaseCheck) with an 'update available' hint - Release workflow: reads VERSION from the repo (no manual input), with a guard against an empty file - Docs: frames.schema.json + 04-wire-protocol.md updated for app_version
93 lines
3.1 KiB
Kotlin
93 lines
3.1 KiB
Kotlin
import org.jetbrains.kotlin.gradle.dsl.JvmTarget
|
|
|
|
plugins {
|
|
id("com.android.application")
|
|
id("org.jetbrains.kotlin.plugin.compose")
|
|
}
|
|
|
|
android {
|
|
namespace = "dev.iris.app"
|
|
compileSdk = 37
|
|
|
|
defaultConfig {
|
|
applicationId = "dev.iris.app"
|
|
minSdk = 29
|
|
targetSdk = 34
|
|
// Play Store requires an incrementing versionCode per upload; CI can
|
|
// pass -PappVersionCode=<n>. Local builds keep the default.
|
|
versionCode = (project.findProperty("appVersionCode")?.toString()?.toIntOrNull()) ?: 1
|
|
// The repo-root VERSION file is the single source of truth (bump it
|
|
// to cut a release); CI can still override with -PappVersion.
|
|
versionName =
|
|
(project.findProperty("appVersion") as? String)
|
|
?: project
|
|
.file("../../VERSION")
|
|
.takeIf { it.exists() }
|
|
?.readText()
|
|
?.trim()
|
|
?: "0.1.0"
|
|
}
|
|
|
|
buildTypes {
|
|
release {
|
|
isMinifyEnabled = false
|
|
}
|
|
}
|
|
|
|
// CI release signing: .gitea/workflows/release.yml restores a keystore
|
|
// from Gitea secrets and exports ANDROID_KEYSTORE_* env vars (see
|
|
// scripts/make_release_keystore.sh). Without them the release build stays
|
|
// unsigned and the workflow falls back to a debug APK.
|
|
val ciKeystore = System.getenv("ANDROID_KEYSTORE_FILE")
|
|
if (ciKeystore != null) {
|
|
signingConfigs {
|
|
create("release") {
|
|
storeFile = file(ciKeystore)
|
|
storePassword = System.getenv("ANDROID_KEYSTORE_PASSWORD")
|
|
keyAlias = System.getenv("ANDROID_KEY_ALIAS")
|
|
keyPassword = System.getenv("ANDROID_KEY_PASSWORD")
|
|
}
|
|
}
|
|
buildTypes {
|
|
release {
|
|
signingConfig = signingConfigs.getByName("release")
|
|
}
|
|
}
|
|
}
|
|
|
|
compileOptions {
|
|
sourceCompatibility = JavaVersion.VERSION_17
|
|
targetCompatibility = JavaVersion.VERSION_17
|
|
}
|
|
|
|
// targetSdk is deliberately pinned to 34 (a stable API level): the
|
|
// reference device is API 29 and API 37 (the only newer installed
|
|
// platform) is a preview SDK, which is not appropriate to target for a
|
|
// stable build. Silence the informational OldTargetApi hint.
|
|
lint {
|
|
disable += "OldTargetApi"
|
|
}
|
|
}
|
|
|
|
kotlin {
|
|
compilerOptions {
|
|
jvmTarget.set(JvmTarget.JVM_17)
|
|
}
|
|
}
|
|
|
|
dependencies {
|
|
implementation(project(":shared"))
|
|
implementation(platform("androidx.compose:compose-bom:2026.08.00"))
|
|
implementation("androidx.compose.material3:material3")
|
|
implementation("androidx.compose.ui:ui")
|
|
implementation("androidx.activity:activity-compose:1.13.0")
|
|
implementation("androidx.core:core-splashscreen:1.2.0")
|
|
}
|
|
|
|
// M5: apply the google-services plugin only when a Firebase project is
|
|
// configured (google-services.json present). Without it the FCM service is
|
|
// inert and the ntfy listener is the push path.
|
|
if (file("google-services.json").exists()) {
|
|
apply(plugin = "com.google.gms.google-services")
|
|
}
|