Skip to content

Commit 67d3a1b

Browse files
committed
add aidl parcelables into aar
1 parent c4dae7c commit 67d3a1b

File tree

18 files changed

+558
-18
lines changed

18 files changed

+558
-18
lines changed

grease/src/main/kotlin/io/deepmedia/tools/grease/GreasePlugin.kt

Lines changed: 97 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -27,11 +27,15 @@ import com.android.ide.common.symbols.parseManifest
2727
import com.android.manifmerger.ManifestMerger2
2828
import com.android.manifmerger.ManifestProvider
2929
import com.android.utils.appendCapitalized
30+
import com.github.jengelman.gradle.plugins.shadow.ShadowStats
31+
import com.github.jengelman.gradle.plugins.shadow.relocation.RelocatePathContext
3032
import com.github.jengelman.gradle.plugins.shadow.relocation.Relocator
3133
import com.github.jengelman.gradle.plugins.shadow.tasks.ShadowJar
3234
import org.gradle.api.Plugin
3335
import org.gradle.api.Project
3436
import org.gradle.api.artifacts.Configuration
37+
import org.gradle.api.attributes.Usage
38+
import org.gradle.api.file.Directory
3539
import org.gradle.api.publish.maven.internal.publication.DefaultMavenPublication
3640
import org.gradle.api.publish.maven.tasks.PublishToMavenRepository
3741
import org.gradle.kotlin.dsl.support.unzipTo
@@ -71,6 +75,7 @@ open class GreasePlugin : Plugin<Project> {
7175
fun configure(variant: Variant, vararg configurations: Configuration) {
7276
configureVariantManifest(target, variant, configurations, log)
7377
configureVariantJniLibs(target, variant, configurations, log)
78+
configureVariantAidlParcelables(target, variant, configurations, log)
7479
configureVariantResources(target, variant, configurations, log)
7580
configureVariantSources(target, variant, configurations, greaseExtension, log)
7681
configureVariantAssets(target, variant, configurations, log)
@@ -121,7 +126,7 @@ open class GreasePlugin : Plugin<Project> {
121126
target.locateTask(componentConfig.resolveTaskName("process", "Manifest"))?.configure {
122127
val processManifestTask = this as ProcessLibraryManifest
123128

124-
val extraManifests = configurations.artifactsOf(AndroidArtifacts.ArtifactType.MANIFEST)
129+
val extraManifests = configurations.artifactsOf(target, AndroidArtifacts.ArtifactType.MANIFEST)
125130
dependsOn(extraManifests)
126131

127132
// After the file is copied we can go on with the actual manifest merging.
@@ -220,7 +225,7 @@ open class GreasePlugin : Plugin<Project> {
220225

221226
target.locateTask(creationConfig.resolveTaskName("copy", "JniLibsProjectAndLocalJars"))?.configure {
222227
val copyJniTask = this as LibraryJniLibsTask
223-
val extraJniLibs = configurations.artifactsOf(AndroidArtifacts.ArtifactType.JNI)
228+
val extraJniLibs = configurations.artifactsOf(target, AndroidArtifacts.ArtifactType.JNI)
224229
dependsOn(extraJniLibs)
225230

226231
fun injectJniLibs() {
@@ -248,6 +253,37 @@ open class GreasePlugin : Plugin<Project> {
248253
}
249254
}
250255

256+
private fun configureVariantAidlParcelables(
257+
target: Project,
258+
variant: Variant,
259+
configurations: Array<out Configuration>,
260+
logger: Logger
261+
) {
262+
val log = logger.child("configureVariantAidlParcelables")
263+
log.d { "Configuring variant ${variant.name}..." }
264+
val creationConfig = variant.componentCreationConfigOrThrow()
265+
creationConfig.taskContainer.aidlCompileTask?.configure {
266+
val extraAidlFiles = configurations.artifactsOf(target, AndroidArtifacts.ArtifactType.AIDL, Usage.JAVA_API)
267+
dependsOn(extraAidlFiles)
268+
fun injectAidlFiles() {
269+
log.d { "Executing for variant ${variant.name} and ${extraAidlFiles.files.size} roots..." }
270+
extraAidlFiles.files.forEach { inputRoot ->
271+
log.d { "Found aidl parcelables files root: $inputRoot" }
272+
val inputFiles = target.fileTree(inputRoot)
273+
target.copy {
274+
from(inputFiles)
275+
into(packagedDir.get())
276+
}
277+
}
278+
}
279+
if (sourceFiles.get().files.isNotEmpty()) {
280+
doLast { injectAidlFiles() }
281+
} else {
282+
injectAidlFiles()
283+
}
284+
}
285+
}
286+
251287
/**
252288
* AARs ship with a file called R.txt which already includes all resource ids from dependencies,
253289
* so we shouldn't probably do nothing about it as it comes for free.
@@ -321,7 +357,7 @@ open class GreasePlugin : Plugin<Project> {
321357
val resourcesMergingWorkdir = target.greaseBuildDir.get().dir(variant.name).dir("resources")
322358
val mergedResourcesDir = resourcesMergingWorkdir.dir("merged")
323359
val blameDir = resourcesMergingWorkdir.dir("blame")
324-
val extraAndroidRes = configurations.artifactsOf(AndroidArtifacts.ArtifactType.ANDROID_RES)
360+
val extraAndroidRes = configurations.artifactsOf(target, AndroidArtifacts.ArtifactType.ANDROID_RES)
325361
dependsOn(extraAndroidRes)
326362

327363
outputs.upToDateWhen { false } // always execute
@@ -386,6 +422,7 @@ open class GreasePlugin : Plugin<Project> {
386422
val creationConfig = variant.componentCreationConfigOrThrow()
387423

388424
val workdir = target.greaseBuildDir.get().dir(variant.name)
425+
workdir.asFile.deleteRecursively()
389426
val aarExtractWorkdir = workdir.dir("extract").dir("aar")
390427
val jarExtractWorkdir = workdir.dir("extract").dir("jar")
391428
val jarFileName = "classes.jar"
@@ -414,7 +451,7 @@ open class GreasePlugin : Plugin<Project> {
414451

415452
// There are many options here. PROCESSED_JAR, PROCESSED_AAR, CLASSES, CLASSES_JAR ...
416453
// CLASSES_JAR seems to be the best though it's not clear if it's jetified or not.
417-
val extraJars = configurations.artifactsOf(AndroidArtifacts.ArtifactType.CLASSES_JAR)
454+
val extraJars = configurations.artifactsOf(target, AndroidArtifacts.ArtifactType.CLASSES_JAR)
418455
dependsOn(extraJars)
419456
dependsOn(greaseExpandTask)
420457

@@ -444,7 +481,7 @@ open class GreasePlugin : Plugin<Project> {
444481
ShadowJar::class.java
445482
) {
446483
val compileTask = creationConfig.taskContainer.javacTask
447-
val extraManifests = configurations.artifactsOf(AndroidArtifacts.ArtifactType.MANIFEST)
484+
val extraManifests = configurations.artifactsOf(target, AndroidArtifacts.ArtifactType.MANIFEST)
448485
val greaseShadowDir = workdir.dir("shadow")
449486
val bundleAar = bundleLibraryTask?.get() as BundleAar
450487

@@ -475,8 +512,8 @@ open class GreasePlugin : Plugin<Project> {
475512

476513
val relocationPrefix = greaseExtension.prefix.get()
477514
if (relocationPrefix.isNotEmpty()) {
478-
greaseProcessTask.get().outputs.files
479-
.asSequence()
515+
val sequence = greaseProcessTask.get().outputs.files.asSequence() + aarExtractWorkdir.dir("aidl").asFile
516+
sequence
480517
.flatMap { inputFile -> inputFile.packageNames }
481518
.distinct()
482519
.map { packageName -> packageName to "${relocationPrefix}.$packageName" }
@@ -502,13 +539,20 @@ open class GreasePlugin : Plugin<Project> {
502539
into(aarExtractWorkdir)
503540
}
504541

505-
replacePackagesInFile(
542+
replacePackagesInManifest(
506543
aarExtractWorkdir.file("AndroidManifest.xml").asFile,
507544
greaseShadowDir.file("AndroidManifest.xml").asFile,
508545
relocators,
509546
target,
510547
)
511548

549+
relocateAidlFiles(
550+
aarExtractWorkdir.dir("aidl"),
551+
greaseShadowDir.dir("aidl"),
552+
relocators,
553+
target,
554+
)
555+
512556
val oldArchive = bundleAar.archiveFile.get().asFile
513557
val archiveParent = oldArchive.parentFile
514558
val archiveName = oldArchive.name
@@ -544,7 +588,7 @@ open class GreasePlugin : Plugin<Project> {
544588
}
545589
}
546590

547-
private fun replacePackagesInFile(
591+
private fun replacePackagesInManifest(
548592
input: File,
549593
output: File,
550594
relocators: List<Relocator>,
@@ -573,6 +617,48 @@ open class GreasePlugin : Plugin<Project> {
573617
}
574618
}
575619

620+
621+
private fun relocateAidlFiles(
622+
inputDir: Directory,
623+
outputDir: Directory,
624+
relocators: List<Relocator>,
625+
target: Project,
626+
) {
627+
if (inputDir.asFileTree.isEmpty) return
628+
629+
inputDir.asFileTree.forEach { file ->
630+
val relocatePathContext = RelocatePathContext().apply {
631+
stats = ShadowStats()
632+
}
633+
val reader = file.bufferedReader()
634+
val relocatedPath = relocators
635+
.filterNot { it is RClassRelocator }
636+
.fold(file.toRelativeString(inputDir.asFile)) { acc, relocator ->
637+
relocator.relocatePath(relocatePathContext.apply { path = acc })
638+
}
639+
val writer = outputDir.asFile.file(relocatedPath).bufferedWriter()
640+
reader.useLines { strings ->
641+
strings
642+
.map { string ->
643+
relocators
644+
.filterNot { it is RClassRelocator }
645+
.fold(string) { acc, relocator ->
646+
relocator.applyToSourceContent(acc)
647+
}
648+
}.forEach {
649+
writer.write(it)
650+
writer.newLine()
651+
}
652+
}
653+
writer.close()
654+
}
655+
inputDir.asFile.deleteRecursively()
656+
target.copy {
657+
from(outputDir)
658+
into(inputDir)
659+
}
660+
}
661+
576662
/**
577663
* Interesting tasks:
578664
* 1. generate<>Assets: See [MutableTaskContainer].
@@ -592,7 +678,7 @@ open class GreasePlugin : Plugin<Project> {
592678
log.d { "Configuring variant ${variant.name}..." }
593679
val creationConfig = variant.componentCreationConfigOrThrow()
594680
creationConfig.taskContainer.mergeAssetsTask.configure {
595-
val extraAssets = configurations.artifactsOf(AndroidArtifacts.ArtifactType.ASSETS)
681+
val extraAssets = configurations.artifactsOf(target, AndroidArtifacts.ArtifactType.ASSETS)
596682
dependsOn(extraAssets)
597683
fun injectAssets() {
598684
log.d { "Executing for variant ${variant.name} and ${extraAssets.files.size} roots..." }
@@ -650,7 +736,7 @@ open class GreasePlugin : Plugin<Project> {
650736
// UNFILTERED_PROGUARD_RULES, FILTERED_PROGUARD_RULES, AAPT_PROGUARD_RULES, ...
651737
// UNFILTERED_PROGUARD_RULES is output of the AarTransform. FILTERED_PROGUARD_RULES
652738
// is processed by another transform and is probably what we want in the end.
653-
val extraInputs = configurations.artifactsOf(AndroidArtifacts.ArtifactType.FILTERED_PROGUARD_RULES)
739+
val extraInputs = configurations.artifactsOf(target, AndroidArtifacts.ArtifactType.FILTERED_PROGUARD_RULES)
654740
dependsOn(extraInputs)
655741

656742
mergeFileTask.inputs.files(extraInputs + mergeFileTask.inputFiles.files)

grease/src/main/kotlin/io/deepmedia/tools/grease/configurations.kt

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,15 +16,17 @@ import org.gradle.kotlin.dsl.get
1616
import org.gradle.kotlin.dsl.named
1717
import java.util.function.Consumer
1818

19-
internal fun Configuration.artifactsOf(type: AndroidArtifacts.ArtifactType): FileCollection = incoming.artifactView {
19+
internal fun Configuration.artifactsOf(project: Project, type: AndroidArtifacts.ArtifactType, usageAttr: String = Usage.JAVA_RUNTIME): FileCollection = incoming.artifactView {
2020
attributes {
21+
attribute(Usage.USAGE_ATTRIBUTE, project.objects.named(Usage::class.java, usageAttr))
2122
attribute(AndroidArtifacts.ARTIFACT_TYPE, type.type)
2223
}
2324
}.files
2425

25-
internal fun Array<out Configuration>.artifactsOf(type: AndroidArtifacts.ArtifactType): FileCollection = map {
26+
internal fun Array<out Configuration>.artifactsOf(project: Project, type: AndroidArtifacts.ArtifactType, usageAttr: String = Usage.JAVA_RUNTIME): FileCollection = map {
2627
it.incoming.artifactView {
2728
attributes {
29+
attribute(Usage.USAGE_ATTRIBUTE, project.objects.named(Usage::class.java, usageAttr))
2830
attribute(AndroidArtifacts.ARTIFACT_TYPE, type.type)
2931
}
3032
}.files as FileCollectionInternal
@@ -77,6 +79,7 @@ private fun Project.createGrease(name: String, isTransitive: Boolean): Configura
7779
// so drop everything marked as implementation() in the original library. Not good.
7880
// (Still, we currently put in A LOT OF STUFF, like org.jetbrains.annotations ... Not sure how to avoid this.)
7981
attribute(Usage.USAGE_ATTRIBUTE, objects.named(Usage::class.java, Usage.JAVA_RUNTIME))
82+
attribute(Usage.USAGE_ATTRIBUTE, objects.named(Usage::class.java, Usage.JAVA_API))
8083
}
8184
configurations.configureEach {
8285
val other = this

grease/src/main/kotlin/io/deepmedia/tools/grease/files.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ val JarFile.packageNames: Set<String>
3939
}.toSet()
4040

4141
val File.packageNames: Set<String>
42-
get() = listFilesRecursive("class").mapNotNull { file ->
42+
get() = (listFilesRecursive("class") + listFilesRecursive("aidl")).mapNotNull { file ->
4343
if (file.name != "module-info.class") {
4444
val cleanedPath = file.path.removePrefix(this.path).removePrefix("/")
4545
cleanedPath
42.4 KB
Binary file not shown.
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
distributionBase=GRADLE_USER_HOME
2+
distributionPath=wrapper/dists
3+
distributionUrl=https\://services.gradle.org/distributions/gradle-8.5-bin.zip
4+
networkTimeout=10000
5+
validateDistributionUrl=true
6+
zipStoreBase=GRADLE_USER_HOME
7+
zipStorePath=wrapper/dists

0 commit comments

Comments
 (0)