1- import com.android.build.api.dsl.ApkSigningConfig
2- import com.android.build.api.dsl.ApplicationExtension
31import com.android.build.gradle.internal.api.BaseVariantOutputImpl
2+ import org.jetbrains.kotlin.gradle.dsl.JvmTarget
43import java.io.ByteArrayOutputStream
5- import java.io.FileInputStream
6- import java.security.KeyStore
7- import java.security.MessageDigest
8- import java.util.Locale
9- import java.util.Properties
104
115plugins {
126 alias(libs.plugins.android.application)
137 alias(libs.plugins.kotlin.android)
148}
159
16- val appVerCode: Int by lazy {
17- getGitCommitCount()
10+ abstract class GitCommitCount : ValueSource <Int , ValueSourceParameters .None > {
11+ @get:Inject abstract val execOperations: ExecOperations
12+
13+ override fun obtain (): Int {
14+ val output = ByteArrayOutputStream ()
15+ execOperations.exec {
16+ commandLine(" git" , " rev-list" , " --count" , " HEAD" )
17+ standardOutput = output
18+ }
19+ return output.toString().trim().toInt()
20+ }
21+ }
22+
23+ abstract class GitShortHash : ValueSource <String , ValueSourceParameters .None > {
24+ @get:Inject abstract val execOperations: ExecOperations
25+
26+ override fun obtain (): String {
27+ val output = ByteArrayOutputStream ()
28+ execOperations.exec {
29+ commandLine(" git" , " rev-parse" , " --short=7" , " HEAD" )
30+ standardOutput = output
31+ }
32+ return output.toString().trim()
33+ }
1834}
19- val appVerName: String = " 3.2.3" + " .r${getGitCommitCount()} ." + getVersionName()
35+
36+ val gitCommitCount = providers.of(GitCommitCount ::class .java) {}
37+ val gitShortHash = providers.of(GitShortHash ::class .java) {}
2038
2139android {
2240 namespace = " moe.ore.txhook"
@@ -26,27 +44,61 @@ android {
2644 applicationId = " moe.ore.txhook"
2745 minSdk = 24
2846 targetSdk = 36
29- versionCode = appVerCode
30- versionName = appVerName
47+ versionCode = providers.provider { getBuildVersionCode(rootProject) }.get()
48+ versionName = " 3.2.3 "
3149 }
3250
3351 compileOptions {
3452 sourceCompatibility = JavaVersion .VERSION_17
3553 targetCompatibility = JavaVersion .VERSION_17
3654 }
3755
38- kotlinOptions {
39- jvmTarget = " 17"
56+ kotlin {
57+ compilerOptions {
58+ jvmTarget.set(JvmTarget .JVM_17 )
59+ }
4060 }
4161
4262 buildFeatures {
4363 viewBinding = true
4464 buildConfig = true
4565 }
4666
67+ buildTypes {
68+ debug {
69+ val gitSuffix = providers.provider { getGitHeadRefsSuffix(rootProject, " debug" ) }.get()
70+ versionNameSuffix = " .${gitSuffix} "
71+ }
72+ release {
73+ val keystorePath: String? = System .getenv(" KEYSTORE_PATH" )
74+ if (! keystorePath.isNullOrBlank()) {
75+ signingConfigs {
76+ create(" release" ) {
77+ storeFile = file(keystorePath)
78+ storePassword = System .getenv(" KEYSTORE_PASSWORD" )
79+ keyAlias = System .getenv(" KEY_ALIAS" )
80+ keyPassword = System .getenv(" KEY_PASSWORD" )
81+ enableV2Signing = true
82+ }
83+ }
84+ }
85+
86+ isMinifyEnabled = true
87+ isShrinkResources = true
88+ isCrunchPngs = true
89+ proguardFiles(getDefaultProguardFile(" proguard-android-optimize.txt" ), " proguard-rules.pro" )
90+ val gitSuffix = providers.provider { getGitHeadRefsSuffix(rootProject, " release" ) }.get()
91+ versionNameSuffix = " .${gitSuffix} "
92+
93+ if (! keystorePath.isNullOrBlank()) {
94+ signingConfig = signingConfigs.findByName(" release" )
95+ }
96+ }
97+ }
98+
4799 packaging {
48- resources {
49- excludes + = setOf (
100+ resources.excludes.addAll(
101+ arrayOf (
50102 " META-INF/**" ,
51103 " kotlin/**" ,
52104 " google/**" ,
@@ -56,126 +108,61 @@ android {
56108 " DebugProbesKt.bin" ,
57109 " kotlin-tooling-metadata.json"
58110 )
59- }
111+ )
60112 }
61113
62- // Disable lint errors for this build
63114 lint {
64115 abortOnError = false
65116 }
66117
67- android.applicationVariants.all {
68- outputs.map { it as BaseVariantOutputImpl }
69- .forEach {
70- it.outputFileName = " TXHook-v${versionName} .apk"
71- }
72- }
73-
74- flavorDimensions.add(" mode" )
75-
76- productFlavors {
77- create(" app" ) {
78- dimension = " mode"
79- }
80- }
81-
82- configureAppSigningConfigsForRelease()
83- }
84-
85- fun configureAppSigningConfigsForRelease () {
86- val keystorePath: String? = System .getenv(" KEYSTORE_PATH" )
87- project.configure<ApplicationExtension > {
88- if (! keystorePath.isNullOrBlank()) {
89- signingConfigs {
90- create(" release" ) {
91- storeFile = file(keystorePath)
92- storePassword = System .getenv(" KEYSTORE_PASSWORD" )
93- keyAlias = System .getenv(" KEY_ALIAS" )
94- keyPassword = System .getenv(" KEY_PASSWORD" )
95- enableV2Signing = true
118+ applicationVariants.all {
119+ outputs.all {
120+ val output = this as BaseVariantOutputImpl
121+ output.outputFileName?.let { fileName ->
122+ if (fileName.endsWith(" .apk" )) {
123+ val projectName = rootProject.name
124+ val currentVersionName = versionName
125+ output.outputFileName = " ${projectName} -v${currentVersionName} .APK"
96126 }
97127 }
98128 }
99- buildTypes {
100- var signatureDigest: String? = getSignatureKeyDigest(signingConfigs.findByName(" release" ))
101- if (signatureDigest != null ) {
102- println (" Signature Digest: $signatureDigest " )
103- } else {
104- println (" No Signature Digest Configured" )
105- }
106- release {
107- isMinifyEnabled = true
108- isShrinkResources = true
109- if (! keystorePath.isNullOrBlank()) {
110- signingConfig = signingConfigs.findByName(" release" )
111- }
112- proguardFiles(" proguard-rules.pro" )
113- }
114- }
115129 }
116130}
117131
118- fun getLocalProperty ( propertyName : String ): String? {
132+ fun getGitHeadRefsSuffix ( project : Project , buildType : String ): String {
119133 val rootProject = project.rootProject
120- val localProp = File (rootProject.projectDir, " local.properties" )
121- if (! localProp.exists()) {
122- return null
123- }
124- val localProperties = Properties ()
125- localProp.inputStream().use {
126- localProperties.load(it)
127- }
128- return localProperties.getProperty(propertyName, null )
129- }
130-
131- fun getGitCommitCount (): Int {
132- val out = ByteArrayOutputStream ()
133- exec {
134- commandLine(" git" , " rev-list" , " --count" , " HEAD" )
135- standardOutput = out
136- }
137- return out .toString().trim().toInt()
138- }
139-
140- fun getGitCommitHash (): String {
141- val out = ByteArrayOutputStream ()
142- exec {
143- commandLine(" git" , " rev-parse" , " --short" , " HEAD" )
144- standardOutput = out
134+ val projectDir = rootProject.projectDir
135+ val headFile = File (projectDir, " .git" + File .separator + " HEAD" )
136+ return if (headFile.exists()) {
137+ try {
138+ val commitCount = gitCommitCount.get()
139+ val hash = gitShortHash.get()
140+ val prefix = if (buildType == " debug" ) " d" else " r"
141+ " $prefix$commitCount .$hash "
142+ } catch (e: Exception ) {
143+ println (" Failed to get git info: ${e.message} " )
144+ " .standalone"
145+ }
146+ } else {
147+ println (" Git HEAD file not found" )
148+ " .standalone"
145149 }
146- return out .toString().trim()
147150}
148151
149- fun getVersionName (): String {
150- return getGitCommitHash()
151- }
152-
153- fun getSignatureKeyDigest (signConfig : ApkSigningConfig ? ): String? {
154- val key1: String? = if (signConfig?.storeFile != null ) {
155- // extract certificate digest
156- val key = signConfig.storeFile
157- val keyStore = KeyStore .getInstance(signConfig.storeType ? : KeyStore .getDefaultType())
158- FileInputStream (key!! ).use {
159- keyStore.load(it, signConfig.storePassword!! .toCharArray())
160- }
161- val cert = keyStore.getCertificate(signConfig.keyAlias!! )
162- val md = MessageDigest .getInstance(" MD5" )
163- val digest = md.digest(cert.encoded)
164- digest.joinToString(" " ) { " %02X" .format(it) }
165- } else null
166- val key2: String? = getLocalProperty(" ffekit.signature.md5digest" )
167- ?.uppercase(Locale .ROOT )?.ifEmpty { null }
168- // check if key1 and key2 are the same
169- if (key1 != null && key2 != null && key1 != key2) {
170- error(
171- " The signature key digest in the signing config and local.properties are different, " +
172- " got $key1 and $key2 , please make sure they are the same."
173- )
174- }
175- return (key1 ? : key2)?.also {
176- check(it.matches(Regex (" [0-9A-F]{32}" ))) {
177- " Invalid signature key digest: $it "
152+ fun getBuildVersionCode (project : Project ): Int {
153+ val rootProject = project.rootProject
154+ val projectDir = rootProject.projectDir
155+ val headFile = File (projectDir, " .git" + File .separator + " HEAD" )
156+ return if (headFile.exists()) {
157+ try {
158+ gitCommitCount.get()
159+ } catch (e: Exception ) {
160+ println (" Failed to get git commit count: ${e.message} " )
161+ 1
178162 }
163+ } else {
164+ println (" Git HEAD file not found" )
165+ 1
179166 }
180167}
181168
0 commit comments