Resolving R8 Missing Class Errors in Flutter App Bundle Build
Introduction
While building an app bundle for my Flutter project using the production flavor, I encountered R8 errors related to missing classes. These errors referenced classes from libraries such as Conscrypt and OpenJSSE, which are used by OkHttp for enhanced TLS support. In this post, I will detail my situation, explain why the errors occurred, and describe how I resolved them.
The Problem
I executed the following command to build the app bundle:
fvm flutter build appbundle --flavor prod -t lib/main_production.dart
During the build, several warnings appeared:
warning: [options] source value 8 is obsolete and will be removed in a future release
...
And then, the build failed with errors like:
ERROR: Missing class org.conscrypt.Conscrypt$Version (referenced from: boolean okhttp3.internal.platform.ConscryptPlatform$Companion.atLeastVersion(int, int, int))
Missing class org.conscrypt.Conscrypt (referenced from: ... )
Missing class org.conscrypt.ConscryptHostnameVerifier (referenced from: ...)
The error occurred during the minification step (:app:minifyProdReleaseWithR8).
Why the Error Occurred
R8 is the code shrinker and optimizer used during Android builds. It analyzes your code and libraries to remove unused code and optimize the final build. During this process, R8 detected references to classes from the Conscrypt and OpenJSSE libraries within OkHttp. Although these classes might not be strictly necessary at runtime (or might be provided by the system), R8 fails the build if it cannot locate them. This problem is common when:
- A library (like OkHttp) references optional dependencies (e.g., Conscrypt for improved TLS support).
- There is no ProGuard/R8 configuration file (proguard-rules.pro) instructing R8 to ignore warnings for missing classes.
How I Solved the Issue
I resolved the issue by using one of the following methods:
- Adding ProGuard (R8) Keep Rules:
Since I did not have a proguard-rules.pro file, I created one in the android/app/ directory and added the following rules:Then, I modified the android/app/build.gradle file to reference this file in the release build type:
# Ignore missing classes related to Conscrypt and OpenJSSE
-dontwarn com.android.org.conscrypt.SSLParametersImpl
-dontwarn org.apache.harmony.xnet.provider.jsse.SSLParametersImpl
-dontwarn org.openjsse.javax.net.ssl.SSLParameters
-dontwarn org.openjsse.javax.net.ssl.SSLSocket
-dontwarn org.openjsse.net.ssl.OpenJSSE
# Additional rule for org.conscrypt classes
-dontwarn org.conscrypt.**
Then, I modified the android/app/build.gradle file to reference this file in the release build type:
buildTypes {
release {
signingConfig signingConfigs.release
minifyEnabled true
shrinkResources true
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
2. Adding the Conscrypt Dependency (Optional):
Alternatively, I could include the Conscrypt library directly by adding it to the dependencies in android/app/build.gradle:
dependencies {
coreLibraryDesugaring 'com.android.tools:desugar_jdk_libs:1.2.2'
implementation 'org.conscrypt:conscrypt-android:2.5.2'
}
In my case, adding the ProGuard rules was sufficient to resolve the error.
Conclusion
The R8 errors occurred because the build process detected references to optional classes (from Conscrypt and OpenJSSE) that were not present in the project. By adding appropriate keep rules in a newly created proguard-rules.pro file (or by including the missing library), I was able to instruct R8 to ignore these missing classes and successfully build the app bundle. This experience underlines the importance of proper ProGuard/R8 configuration when working with Flutter and third-party libraries.
Happy coding!