1

I have a multi-project setup. Consider two separate apps AppA and AppB. AppA has two library modules modA and modB. modA has a dependency on modB via gradle API.

consider modA build.gradle file

dependencies {
    api project(":mobB")
}

modA has a file ModASample.kt which looks like

class ModASample{
    fun modASample(){
        println("modASample")
    }
}

modB has a file ModBSample.kt which looks like

class ModBSample{
    fun modBSample(){
        println("modBSample")
    }
}

AppA build.gradle file

dependencies {
    implementation project(":modA")
}

from a class in appA AppASample.kt

class AppASample{

    fun access(){
        val modA = ModASample() //accessible
        val modB = ModBSample() //accessible
    }

}

both ModASample and ModBSamle are accessible which is expected as well because modB is used in modA via api access.

The issue arises when I try to extract an aar of modA and try to use this aar in AppB.

AppB has build.gradle file which looks like this

dependencies {
    implementation project(":modA")
}

Now this time an aar of modA is prepared and is added as a separate module.

From a class AppBSample.kt

class AppASample{

    fun access(){
        val modA = ModASample() //accessible
        val modB = ModBSample() // NOT ACCESSIBLE
    }

}

Can anyone please provide some insight why is this happening. I was expecting modB will be accessible but that is not the case if direct aar is used.

Any suggestions will be appreciated.

Ankush
  • 1,888
  • 20
  • 22

2 Answers2

1

The AAR doesn't contain transitive dependencies, it doesn't have any pom file with the list of their dependencies. Check this build.gradle.kts from a library I developed: https://github.com/GiuseppeGiacoppo/RemoteConfig/blob/master/build.gradle.kts

What you can do is define a task that creates a jar file with all the sources.

Since it's a kotlin library and not Android, you should change it with this:

val sourcesJar by tasks.creating(Jar::class) {
    archiveClassifier.set("sources")
    from(android.sourceSets.getByName("main").java.srcDirs)
}
  • The purpose of the code was just to portray the situation. The library is for Android, has other code than this. But I'll give your suggestion a try. If the AAR doesn't contain transitive dependencies, the scope of implementation and api gradle profiles is limited to just multi module setup? That is quite strange. – Ankush Feb 25 '21 at 03:31
  • Api and implementation work only at compile time and they're a gradle feature for your gradle project. They guide you to organize in a better way your code along multiple modules. Once you build, your artifact (aar, jar, etc.) won't have info about modules and their dependency mode (api or implementation) – Giuseppe Giacoppo Feb 25 '21 at 09:41
0

I got it working with another stackoverflow post

What I could understand was, while packaging the aar file, the supplied dependency declaring modifiers (api/implementation) does not actually include the dependency files along with the package. Though the modifiers(api/implementation) still stands up for their intended usage, they seemingly are not responsible for actually moving the dependencies into the package.

So for bringing the dependencies along, we need to explicitly package them together. In my case I used maven publish plugin to get the dependencies packaged along with the aar.

Ankush
  • 1,888
  • 20
  • 22