Skip to content

Commit 3ffaa8e

Browse files
committed
fix: wire merge classes to asm transformer
1 parent 1280e08 commit 3ffaa8e

10 files changed

Lines changed: 140 additions & 136 deletions

File tree

apps/RNApp/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
"ios": "yarn brownfield:package:ios && brownfield codegen && react-native run-ios",
88
"build:example:android-rn": "react-native build-android",
99
"build:example:ios-rn": "react-native build-ios",
10-
"brownfield:package:android": "brownfield package:android --variant release",
10+
"brownfield:package:android": "brownfield package:android",
1111
"brownfield:publish:android": "brownfield publish:android",
1212
"brownfield:package:ios": "brownfield package:ios --configuration Release",
1313
"lint": "eslint .",

gradle-plugins/react/brownfield/src/main/kotlin/com/callstack/react/brownfield/plugin/RNBrownfieldPlugin.kt

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import com.callstack.react.brownfield.processors.JNILibsProcessor
1111
import com.callstack.react.brownfield.processors.ManifestTaskProcessor
1212
import com.callstack.react.brownfield.processors.ProguardProcessor
1313
import com.callstack.react.brownfield.processors.ResourceTaskProcessor
14+
import com.callstack.react.brownfield.processors.VariantHelper
1415
import com.callstack.react.brownfield.processors.VariantPackagesProperty
1516
import com.callstack.react.brownfield.processors.VariantTaskProvider
1617
import com.callstack.react.brownfield.shared.BaseProject
@@ -139,6 +140,12 @@ class RNBrownfieldPlugin : Plugin<Project> {
139140

140141
val aarLibraries = getAarLibraries(artifacts, variantName)
141142

143+
/** ======= MERGE CLASSES =========*/
144+
val mergeClassesTask = variantTaskProvider.mergeClasses(aarLibraries, explodeTask, variantName)
145+
project.tasks.named(VariantHelper.getAsmTransformTaskName(capitalizedVariantName)).configure {
146+
it.dependsOn(mergeClassesTask)
147+
}
148+
142149
/**
143150
* Flat IDs to be put into the variant property, required for RClass Transformer
144151
*/

gradle-plugins/react/brownfield/src/main/kotlin/com/callstack/react/brownfield/plugin/RNSourceSets.kt

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ package com.callstack.react.brownfield.plugin
33
import com.android.build.api.variant.LibraryAndroidComponentsExtension
44
import com.android.build.gradle.LibraryExtension
55
import com.callstack.react.brownfield.exceptions.NameSpaceNotFound
6+
import com.callstack.react.brownfield.processors.VariantHelper
67
import com.callstack.react.brownfield.utils.Extension
78
import com.callstack.react.brownfield.utils.Utils
89
import com.callstack.react.brownfield.utils.capitalized
@@ -49,7 +50,7 @@ object RNSourceSets {
4950
componentsExtension.onVariants { variant ->
5051
val variantName = variant.name
5152
val bundledAssetsVariantName =
52-
Utils.getBundledAssetsVariantName(
53+
VariantHelper.getBundledAssetsVariantName(
5354
variantName = variantName,
5455
buildTypeName = variant.buildType,
5556
isDebuggable = variant.debuggable,
@@ -66,7 +67,7 @@ object RNSourceSets {
6667
// outputs for RN >= 0.82
6768
"react/$bundledAssetsVariantName",
6869
)
69-
val updateResourcesPathSegment = Utils.getExpoUpdatesResourcesTaskName(variant.name)
70+
val updateResourcesPathSegment = VariantHelper.getExpoUpdatesResourcesTaskName(variant.name)
7071

7172
val appBuildDir = getAppBuildDir()
7273
sourceSet.assets.srcDirs(bundlePathSegments.map { "$appBuildDir/generated/assets/$it" })

gradle-plugins/react/brownfield/src/main/kotlin/com/callstack/react/brownfield/processors/ExplodeTaskProvider.kt

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,6 @@ object ExplodeTaskProvider {
2626
ExplodeAarTask::class.java,
2727
) { task ->
2828
task.variantName.set(variant.name)
29-
task.minifyEnabled.set(variant.buildType.isMinifyEnabled)
3029

3130
val finalArtifacts = mutableListOf<UnresolvedArtifactInfo>()
3231
artifacts.forEach { art ->

gradle-plugins/react/brownfield/src/main/kotlin/com/callstack/react/brownfield/processors/MergeProcessor.kt

Lines changed: 7 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -5,48 +5,26 @@ import org.gradle.api.Project
55
import java.io.File
66

77
object MergeProcessor {
8-
fun mergeClassesJarIntoClasses(
8+
fun mergeClassesJarFilesIntoClasses(
99
project: Project,
10-
androidLibraries: Collection<AndroidArchiveLibrary>,
10+
classJarFiles: Collection<File>,
1111
folderOut: File,
1212
) {
13-
val allJarFiles: MutableCollection<File> = ArrayList()
14-
val filteredLibs = getFilteredAarLibs(androidLibraries)
15-
filteredLibs.forEach {
16-
allJarFiles.add(it.getClassesJarFile())
17-
}
18-
19-
val filteredAllJarFiles = allJarFiles.filter { it.exists() }
20-
filteredAllJarFiles.forEach { jarFile ->
13+
classJarFiles.filter { it.exists() }.forEach { jarFile ->
2114
project.copy {
2215
it.from(project.zipTree(jarFile))
2316
it.into(folderOut)
2417
}
2518
}
2619
}
2720

28-
fun mergeLibsIntoClasses(
21+
fun mergeClassesJarIntoClasses(
2922
project: Project,
3023
androidLibraries: Collection<AndroidArchiveLibrary>,
31-
jarFiles: Collection<File>,
32-
outputDir: File,
24+
folderOut: File,
3325
) {
34-
val allJarFiles: MutableCollection<File> = ArrayList()
35-
val filteredLibs = getFilteredAarLibs(androidLibraries)
36-
filteredLibs.forEach {
37-
allJarFiles.addAll(it.getLocalJars())
38-
}
39-
40-
val filteredJarFiles = jarFiles.filter { it.exists() }
41-
filteredJarFiles.forEach { allJarFiles.add(it) }
42-
43-
allJarFiles.forEach { jarFile ->
44-
project.copy {
45-
it.from(project.zipTree(jarFile))
46-
it.into(outputDir)
47-
it.exclude("META-INF/")
48-
}
49-
}
26+
val classesJarFiles = getFilteredAarLibs(androidLibraries).map { it.getClassesJarFile() }
27+
mergeClassesJarFilesIntoClasses(project, classesJarFiles, folderOut)
5028
}
5129

5230
private fun getFilteredAarLibs(androidLibraries: Collection<AndroidArchiveLibrary>): Collection<AndroidArchiveLibrary> {
Lines changed: 28 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -1,61 +1,42 @@
11
package com.callstack.react.brownfield.processors
22

3-
import com.callstack.react.brownfield.shared.BaseProject
4-
import com.callstack.react.brownfield.utils.AndroidArchiveLibrary
5-
import com.callstack.react.brownfield.utils.DirectoryManager
63
import com.callstack.react.brownfield.utils.capitalized
7-
import org.gradle.api.file.ConfigurableFileCollection
8-
import java.io.File
9-
import java.nio.file.Files
10-
import java.nio.file.Path
11-
import java.nio.file.Paths
12-
13-
class VariantHelper : BaseProject() {
14-
private fun getClassPathDirFiles(variantName: String): ConfigurableFileCollection {
15-
return project.files(
16-
"$buildDir/intermediates/javac/$variantName/compile${variantName.capitalized()}JavaWithJavac/classes",
17-
)
4+
5+
object VariantHelper {
6+
fun getAsmTransformTaskName(capitalizedVariantName: String): String {
7+
return "transform${capitalizedVariantName}ClassesWithAsm"
188
}
199

20-
fun classesMergeTaskDoFirst(
21-
outputDir: File,
22-
variantName: String,
23-
) {
24-
val pathsToDelete = mutableListOf<Path>()
25-
val javacDir = getClassPathDirFiles(variantName).first()
26-
project.fileTree(outputDir).forEach { path ->
27-
pathsToDelete.add(
28-
Paths.get(outputDir.absolutePath).relativize(Paths.get(path.absolutePath)),
29-
)
10+
fun getBundledAssetsVariantName(
11+
variantName: String?,
12+
buildTypeName: String?,
13+
isDebuggable: Boolean,
14+
): String {
15+
require(!variantName.isNullOrEmpty()) {
16+
"getBundledAssetsVariantName: Variant name cannot be empty"
3017
}
31-
outputDir.deleteRecursively()
32-
pathsToDelete.forEach { path ->
33-
Files.deleteIfExists(Paths.get("$javacDir.absolutePath/$path"))
18+
19+
require(!buildTypeName.isNullOrEmpty()) {
20+
"getBundledAssetsVariantName: Build Type cannot be empty"
3421
}
35-
}
3622

37-
fun classesMergeTaskDoLast(
38-
outputDir: File,
39-
aarLibraries: Collection<AndroidArchiveLibrary>,
40-
jarFiles: MutableList<File>,
41-
variantName: String,
42-
isMinifyEnabled: Boolean,
43-
) {
44-
MergeProcessor.mergeClassesJarIntoClasses(project, aarLibraries, outputDir)
45-
if (isMinifyEnabled) {
46-
MergeProcessor.mergeLibsIntoClasses(project, aarLibraries, jarFiles, outputDir)
23+
if (!isDebuggable) {
24+
return variantName
4725
}
48-
val javacDir = getClassPathDirFiles(variantName).first()
49-
project.copy { copyTask ->
50-
copyTask.from(outputDir)
51-
copyTask.into(javacDir)
52-
copyTask.exclude("META-INF/")
26+
27+
if (variantName == buildTypeName) {
28+
return "release"
5329
}
5430

55-
project.copy { copyTask ->
56-
copyTask.from("${outputDir.absolutePath}/META-INF")
57-
copyTask.into(DirectoryManager.getKotlinMetaDirectory(variantName))
58-
copyTask.include("*.kotlin_module")
31+
val capitalizedBuildTypeName = buildTypeName.capitalized()
32+
return if (variantName.endsWith(capitalizedBuildTypeName)) {
33+
"${variantName.removeSuffix(capitalizedBuildTypeName)}Release"
34+
} else {
35+
"release"
5936
}
6037
}
38+
39+
fun getExpoUpdatesResourcesTaskName(variantName: String): String {
40+
return "create${variantName.capitalized()}UpdatesResources"
41+
}
6142
}

gradle-plugins/react/brownfield/src/main/kotlin/com/callstack/react/brownfield/processors/VariantTaskProvider.kt

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ package com.callstack.react.brownfield.processors
33
import com.android.build.gradle.internal.tasks.factory.dependsOn
44
import com.callstack.react.brownfield.exceptions.TaskNotFound
55
import com.callstack.react.brownfield.shared.ExplodeAarTask
6+
import com.callstack.react.brownfield.shared.MergeClassesTask
67
import com.callstack.react.brownfield.utils.AndroidArchiveLibrary
78
import com.callstack.react.brownfield.utils.DirectoryManager
89
import com.callstack.react.brownfield.utils.Extension
@@ -12,6 +13,7 @@ import org.gradle.api.Project
1213
import org.gradle.api.Task
1314
import org.gradle.api.UnknownTaskException
1415
import org.gradle.api.tasks.TaskProvider
16+
import org.gradle.configurationcache.extensions.capitalized
1517
import java.io.File
1618

1719
class VariantTaskProvider(val project: Project) {
@@ -83,7 +85,7 @@ class VariantTaskProvider(val project: Project) {
8385
preBuildTask.dependsOn(explodeAarTask)
8486

8587
val bundledAssetsVariantName =
86-
Utils.getBundledAssetsVariantName(
88+
VariantHelper.getBundledAssetsVariantName(
8789
variantName = variantName,
8890
buildTypeName = buildTypeName,
8991
isDebuggable = isVariantDebuggable,
@@ -95,10 +97,28 @@ class VariantTaskProvider(val project: Project) {
9597
preBuildTask.dependsOn("${appProject.path}:createBundle${capitalizedBundledAssetsVariantName}JsAndAssets")
9698

9799
if (Utils.isExpoProject(project)) {
98-
val updatesResourcesTaskName = Utils.getExpoUpdatesResourcesTaskName(variantName)
100+
val updatesResourcesTaskName = VariantHelper.getExpoUpdatesResourcesTaskName(variantName)
99101
if (Utils.hasExpoUpdates(appProject, variantName)) {
100102
preBuildTask.dependsOn("${appProject.path}:$updatesResourcesTaskName")
101103
}
102104
}
103105
}
106+
107+
fun mergeClasses(
108+
aarLibraries: Collection<AndroidArchiveLibrary>,
109+
explodeTasks: TaskProvider<ExplodeAarTask>,
110+
variantName: String,
111+
): TaskProvider<MergeClassesTask> {
112+
val capitalizedVariantName = variantName.capitalized()
113+
val mergeClassesTaskName = "mergeClasses$capitalizedVariantName"
114+
val kotlinCompileTaskName = "compile${capitalizedVariantName}Kotlin"
115+
116+
return project.tasks.register(mergeClassesTaskName, MergeClassesTask::class.java) {
117+
it.dependsOn(explodeTasks)
118+
it.dependsOn(project.tasks.named(kotlinCompileTaskName))
119+
it.variantName.set(variantName)
120+
it.inputClassesJars.from(aarLibraries.map { aarLibrary -> aarLibrary.getClassesJarFile() })
121+
it.outputDir.set(DirectoryManager.getMergeClassDirectory(variantName))
122+
}
123+
}
104124
}

gradle-plugins/react/brownfield/src/main/kotlin/com/callstack/react/brownfield/shared/ExplodeAarTask.kt

Lines changed: 0 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,6 @@
11
package com.callstack.react.brownfield.shared
22

3-
import com.callstack.react.brownfield.processors.VariantHelper
43
import com.callstack.react.brownfield.utils.AndroidArchiveLibrary
5-
import com.callstack.react.brownfield.utils.DirectoryManager
64
import org.gradle.api.DefaultTask
75
import org.gradle.api.provider.ListProperty
86
import org.gradle.api.provider.Property
@@ -17,25 +15,11 @@ abstract class ExplodeAarTask : DefaultTask() {
1715
@get:Input
1816
abstract val variantName: Property<String>
1917

20-
@get:Input
21-
abstract val minifyEnabled: Property<Boolean>
22-
2318
@TaskAction
2419
fun run() {
2520
val artifacts = inputArtifacts.get()
2621
val resolvedVariantName = variantName.get()
2722

28-
val variantHelper = VariantHelper()
29-
variantHelper.project = project
30-
31-
// classes-merge
32-
variantHelper.classesMergeTaskDoFirst(
33-
DirectoryManager.getMergeClassDirectory(
34-
resolvedVariantName,
35-
),
36-
resolvedVariantName,
37-
)
38-
3923
val aarLibraries = mutableListOf<AndroidArchiveLibrary>()
4024
artifacts.forEach { art ->
4125
val artifactFile =
@@ -64,9 +48,5 @@ abstract class ExplodeAarTask : DefaultTask() {
6448
it.into(zipFolder)
6549
}
6650
}
67-
68-
// classes-merge
69-
val mergeClassesOutputDir = DirectoryManager.getMergeClassDirectory(resolvedVariantName)
70-
variantHelper.classesMergeTaskDoLast(mergeClassesOutputDir, aarLibraries, mutableListOf(), resolvedVariantName, minifyEnabled.get())
7151
}
7252
}
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
package com.callstack.react.brownfield.shared
2+
3+
import com.callstack.react.brownfield.processors.MergeProcessor
4+
import com.callstack.react.brownfield.utils.DirectoryManager
5+
import com.callstack.react.brownfield.utils.capitalized
6+
import org.gradle.api.DefaultTask
7+
import org.gradle.api.file.ConfigurableFileCollection
8+
import org.gradle.api.file.DirectoryProperty
9+
import org.gradle.api.provider.Property
10+
import org.gradle.api.tasks.Classpath
11+
import org.gradle.api.tasks.Input
12+
import org.gradle.api.tasks.OutputDirectory
13+
import org.gradle.api.tasks.TaskAction
14+
import java.io.File
15+
import java.nio.file.Files
16+
import java.nio.file.Path
17+
import java.nio.file.Paths
18+
19+
abstract class MergeClassesTask : DefaultTask() {
20+
@get:Classpath
21+
abstract val inputClassesJars: ConfigurableFileCollection
22+
23+
@get:Input
24+
abstract val variantName: Property<String>
25+
26+
@get:OutputDirectory
27+
abstract val outputDir: DirectoryProperty
28+
29+
@TaskAction
30+
fun run() {
31+
val resolvedVariantName = variantName.get()
32+
val mergedOutputDir = outputDir.get().asFile
33+
val javacDir = getClassPathDir(resolvedVariantName)
34+
val pathsToDelete = mutableListOf<Path>()
35+
36+
if (mergedOutputDir.exists()) {
37+
project.fileTree(mergedOutputDir).forEach { path ->
38+
pathsToDelete.add(
39+
Paths.get(mergedOutputDir.absolutePath).relativize(Paths.get(path.absolutePath)),
40+
)
41+
}
42+
}
43+
44+
mergedOutputDir.deleteRecursively()
45+
pathsToDelete.forEach { path ->
46+
Files.deleteIfExists(javacDir.toPath().resolve(path))
47+
}
48+
49+
MergeProcessor.mergeClassesJarFilesIntoClasses(project, inputClassesJars.files, mergedOutputDir)
50+
51+
project.copy { copyTask ->
52+
copyTask.from(mergedOutputDir)
53+
copyTask.into(javacDir)
54+
copyTask.exclude("META-INF/")
55+
}
56+
57+
project.copy { copyTask ->
58+
copyTask.from(File(mergedOutputDir, "META-INF"))
59+
copyTask.into(DirectoryManager.getKotlinMetaDirectory(resolvedVariantName))
60+
copyTask.include("*.kotlin_module")
61+
}
62+
}
63+
64+
private fun getClassPathDir(variantName: String): File {
65+
val buildDirectory = project.layout.buildDirectory.get().asFile
66+
return project.file(
67+
"$buildDirectory/intermediates/javac/$variantName/compile${variantName.capitalized()}JavaWithJavac/classes",
68+
)
69+
}
70+
}

0 commit comments

Comments
 (0)