Android Convenience Image Moving to Java v11 on August 17th

There has been a lot of people asking for a Java/OpenJDK update in the Android Convenience Image for awhile now. AdoptOpenJDK has a great blog post explaining why they’re moving to Java v11 as their default as well. You can find that here. Last month I posted a GitHub Issue discussing this change for August 2020, maybe sooner in July. Considering we’re already in July, we’re going to stick with an August date for this change, updating the image August 17th.

Testing this change

While not available today, we’ll have images you can use to test Android and OpenJDK v11 very soon. This will be our staging images though so my suggestion is to simply use them to test your CI builds for Java v11 support, not as production images to stay on forever.

Stay tuned to this post (there’s a dropdown to “watch” this topic below) or the GitHub Issue to see when these staging images are available.

Avoiding this Change

We will not be running multiple versions of the Android image so you can’t really avoid it long term. Java 8 support for many tools is actively being dropped so this change is going to be needed for many Android ecosystem tools. If by August 17th you are still not ready for this change, you could pin the specific Android image you are using, thus preventing the version of Java from being changed out from under you. Keep in mind, that freezes your image meaning there’ll be no updates at all to it. You can learn more about pinning an image here.

Questions? Please respond below.

How to Test

Testing images are now available for this change. Instead of using the circleci Docker Hub namespace that you would normally use for an image, you need to use ccistaging. For example:

Normal image with Java v8 Testing image with Java v11
circleci/android:api-30 ccistaging/android:api-30
circleci/android:api-29-node ccistaging/android:api-29-node
circleci/android:api-28-ndk ccistaging/android:api-28-ndk

The Changes

  1. The main change is a simple but significant one. The version of Java used has switched from v8 to v11. It’s useful to make sure your build pipeline still works the same (if not better) with this major Java version change. Java v11 is the next LTS version after v8 and now has complete support from Android Studio, which is why it was chosen.
  2. We now install sdkmanager and related via Android’s Command-Line Tools package instead of the deprecated SDK Tools package.

Reporting

If you run into issues with these testing images, please report them here or on this GitHub Issue.

The Android images have been updated with Java v11.

Migration Notes

Information that might help, curated from the CircleCI Community.

UseCGroupMemoryLimitForHeap

If you’re running into an error with UseCGroupMemoryLimitForHeap, this is because this was an experimental flag that was dropped in Java v10. The new Android images use Java v11 and thus don’t support this. You can use -XX:+UseContainerSupport instead.

JAXB

JAXB is not included with JDK 11, so your project has dependencies on the JAXB API or tools, you may need to include them yourself.

Robolectric

Someone has said that Robolectric doesn’t work with version <= 4.2.1. They recently released Robolectric 4.4 which officially includes support for Java v11 (and Java v13 for that matter).

SDKManager Binary

It looks like some people were calling sdkmanager using the full path $ANDROID_HOME/tools/bin/sdkmanager. The preferred method is to just call the binary itself sdkmanager.

This is especially relevant if you get an error like this:

Exception in thread "main" java.lang.NoClassDefFoundError: javax/xml/bind/annotation/XmlSchema
	at com.android.repository.api.SchemaModule$SchemaModuleVersion.<init>(SchemaModule.java:156)
	at com.android.repository.api.SchemaModule.<init>(SchemaModule.java:75)
	at com.android.sdklib.repository.AndroidSdkHandler.<clinit>(AndroidSdkHandler.java:81)
	at com.android.sdklib.tool.sdkmanager.SdkManagerCli.main(SdkManagerCli.java:73)
	at com.android.sdklib.tool.sdkmanager.SdkManagerCli.main(SdkManagerCli.java:48)
Caused by: java.lang.ClassNotFoundException: javax.xml.bind.annotation.XmlSchema
	at java.base/jdk.internal.loader.BuiltinClassLoader.loadClass(BuiltinClassLoader.java:581)
	at java.base/jdk.internal.loader.ClassLoaders$AppClassLoader.loadClass(ClassLoaders.java:178)
	at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:522)
	... 5 more

Sticking with the old image

You can use the old image by switching your config from specifying the SHA hash of the image you were using instead of the tag. We don’t recommend sticking with the old Java v8 based images if you can avoid it. When pinning an image via a hash, they’re no longer supported thus won’t receive any updates. This can be done as a temporary measure. Information on how to do this can be found here.

Android API 29 digest: circleci/android@sha256:b6646fdf7457f61825526e7bfce364d8e533da6ceb1cdb98e371e94348ecc834

Android API 28 digest: circleci/android@sha256:061e2535826cc3fe4c4a440e716bf06c36c80401ee635c339c6803b3e427ebb3

2 Likes

Please do better about communicating potentially breaking changes like this. Two of our developers lost an entire day tracking down why our test suite was failing randomly.

An email or some other explicit notification would have been very helpful. I doubt most people are checking these discussion boards or the CircleCI GitHub issues on a regular basis.

Thanks!

6 Likes

Hi @starkej2! Thanks for the feedback. We’ll do our best to make sure these changes are communicated better in the future.

1 Like

a bad day for us.

The Android images have been updated with Java v11.

No notice of this issue is sent to our mailboxes.
This took us a lot of time to investigate the cause of the error.

7 Likes

The Javadoc generation is failing with Java 11 when generating the documentation for a subset of classes (with includes or excludes).

Since I am using the Android ORB, I cannot specify the sha256 as the tag for the Docker image…

This is a bad idea, since Android DataBinding (being part of build-tools) is internally using JAXB even with latest Gradle Plugin. I had a hard time figuring out why my project builds locally on Java 8 but refuses to build on Java 11.

1 Like

They even updated Android images like circleci/android:api-29 to Java 11, so every android project is failing because of this? https://github.com/circleci/circleci-images/issues/458

My project was runing fine and I just got this without any change, this is related to accepting the android licenses with ${ANDROID_HOME}/tools/bin/sdkmanager --licenses.

Exception in thread "main" java.lang.NoClassDefFoundError: javax/xml/bind/annotation/XmlSchema
	at com.android.repository.api.SchemaModule$SchemaModuleVersion.<init>(SchemaModule.java:156)
	at com.android.repository.api.SchemaModule.<init>(SchemaModule.java:75)
	at com.android.sdklib.repository.AndroidSdkHandler.<clinit>(AndroidSdkHandler.java:81)
	at com.android.sdklib.tool.sdkmanager.SdkManagerCli.main(SdkManagerCli.java:73)
	at com.android.sdklib.tool.sdkmanager.SdkManagerCli.main(SdkManagerCli.java:48)
Caused by: java.lang.ClassNotFoundException: javax.xml.bind.annotation.XmlSchema
	at java.base/jdk.internal.loader.BuiltinClassLoader.loadClass(BuiltinClassLoader.java:581)
	at java.base/jdk.internal.loader.ClassLoaders$AppClassLoader.loadClass(ClassLoaders.java:178)
	at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:522)
	... 5 more

This was extremely poorly communicated. We had no notice of this breaking change occurring. Spent way too much time figuring out what was happening till I came across this discussion. Disappointing to say the least.

@aneesh We totally understand. We’re working now on making sure these are communicated better in the future via emails and social media. Is there anywhere else you’d like to see an update that would help?

A banner in the web app for the pipeline/workflow/job pages would have been nice. Especially after the change was made. Day to day, that’s probably the only CircleCi content most devs look at.

2 Likes