mozilla / rust-android-gradle

Apache License 2.0
1.03k stars 67 forks source link

JNI libraries missing in AAR file on first build #43

Open tmcguire opened 3 years ago

tmcguire commented 3 years ago

When I build my library project for the first time after cleaning the build, build/outputs/aar/library-debug.aar does not contain the JNI libraries. Only when building for a second time, the JNI libraries are included.

This can be reproduced with samples/library of this repo:

  1. Checkout the repo

    git clone git@github.com:mozilla/rust-android-gradle.git
    cd rust-android-gradle/
  2. Copy the gradle wrapper into samples/library

    cd samples/library
    cp ../../gradlew .
    cp -Ra ../../gradle .
  3. Update the gradle wrapper to the latest version

    export ANDROID_HOME=~/Library/Android/sdk/
    ./gradlew wrapper --gradle-version 6.6.1
  4. Make the project use the rust plugin from the repository instead of the locally build one

    rm settings.gradle
    touch settings.gradle

    In build.gradle, change the rust plugin classpath to gradle.plugin.org.mozilla.rust-android-gradle:plugin:0.8.3

  5. Update the Android gradle plugin to 4.0.1 in build.gradle

  6. Build the library

    ./gradlew assembleDebug
  7. Look at build/outputs/aar/library-debug.aar and notice the JNI libraries are not included.

  8. Build the library again by again invoking ./gradlew assembleDebug. Now build/outputs/aar/library-debug.aar will contain the JNI libraries.

Is there a workaround for this that I could apply to build.gradle?

ncalexan commented 3 years ago

In general, you shouldn't expect to be able to upgrade a bunch of versions and have everything work, especially because you're not observing semver. I think that in this specific case, step 3 is probably okay, because Gradle maintains backwards compatibility fairly well. But step 5 is almost certainly not going to work, because the Android-Gradle plugin definitely doesn't maintain backward compatibility and all of the task-dependency monkeying that this plugin does is very likely to be broken.

However, there's a bigger issue here, which is that the principle consumer of this plugin wires up the dependency graph itself -- see https://github.com/mozilla/application-services/blob/3e4afb4db25cbc078c735b18dff6a58e181a34d4/components/rc_log/android/build.gradle#L90-L103. This was tracked by an issue that doesn't seem to have migrated to this repository: https://github.com/ncalexan/rust-android-gradle/issues/29.

I can't remember why this functionality never made it into the plugin itself; probably because it was too much effort and we (Mozilla, any team I was on) didn't need it. If this is better with https://github.com/willir/cargo-ndk-android-gradle that would be a major argument in favour of that plugin!

tmcguire commented 3 years ago

Thanks for the response!

I didn't even occur to me that the version updates could be the culprit, I only upgraded to fix some other build problems. Makes sense though.

I'll probably indeed try out https://github.com/willir/cargo-ndk-android-gradle, although similar to this project there's isn't any commit activity lately.

nschwermann commented 2 years ago

Following thanks... been having troulbes with cargo ndk finishing the rust build myself. This plugin is at least making all the .so files but not putting them into the AAR. I think the linked build.gradle should help!

ncalexan commented 2 years ago

Following thanks... been having troulbes with cargo ndk finishing the rust build myself. This plugin is at least making all the .so files but not putting them into the AAR. I think the linked build.gradle should help!

Indeed, yes. I recently added some Github Actions testing, so it would now be feasible to wire up the dependency graph in this plugin and test that the .so files are in the appropriate locations. Patches appreciated!

nschwermann commented 2 years ago

Following thanks... been having troulbes with cargo ndk finishing the rust build myself. This plugin is at least making all the .so files but not putting them into the AAR. I think the linked build.gradle should help!

Indeed, yes. I recently added some Github Actions testing, so it would now be feasible to wire up the dependency graph in this plugin and test that the .so files are in the appropriate locations. Patches appreciated!

I ended up running with CargoNdk plugin instead and have it generating a proper aar. Good luck!

elsadeny commented 2 years ago

CargoNdk plugin

how to generate the aar?

MatrixDev commented 1 year ago

I had the same problem and fixed by changing dependant tasks:

afterEvaluate {
    for (name in arrayOf("preDebugBuild", "preReleaseBuild")) {
        tasks.getByName(name).dependsOn("cargoBuild")
    }
}

Regarding #85 - there is no mergeJniLibFolders, but instead mergeDebugJniLibFolders/mergeReleaseJniLibFolders. Anyways preXxxBuild seems to work correctly in all my cases.