R8 provides global options that either modify R8's optimizations throughout the
app or affect every keep rule. These options are maintained in the
proguard-rules.pro
file, along with keep rules. A few of these global options
configure additional optimization, while others turn off certain aspects of the
optimization.
Global options for additional optimization
The following global options enable additional optimization:
-repackageclasses [<optional-package-name>]
: Repackages classes into a single, specified package, for further app size reduction. If you don't supply the optional package name, the classes are moved into the empty, default package. This is a recommended setting for apps.-allowaccessmodification
: Lets R8 change (typically widen) the visibility of classes, fields, and methods to perform more extensive optimizations. Enabled whenproguard-android-optimize.txt
is used. Since Android Gradle Plugin (AGP) 8.2, this is the default configuration if you use R8 in full mode.
The following is an example of a configuration with additional optimization enabled:
-repackageclasses
-allowaccessmodification
Global options to limit optimization
The following global options let you turn off certain aspects of app optimization, and are helpful when you're refining your keep rules or turning on R8 for the first time.
-dontoptimize
: Prevents code optimization, for example method inlining. This option can be used during development but shouldn't be used in production builds.-dontshrink
: Prevents the removal of unreferenced code and code optimizations. This option can be used during development but shouldn't be used in production builds.-dontobfuscate
: Prevents shortening the names of classes and methods. It can be especially helpful to turn off obfuscation during debugging so stack traces are easier to read. This option can be used during development but shouldn't be used in production builds.-keepattributes <attributes>
: Accepts a comma-separated list of attributes that should be preserved. If you're not using the defaultproguard-android-optimize.txt
, R8 strips all attributes includingRuntimeVisibleAnnotations
andSignature
, however it can be helpful to preserve these attributes if they are needed in cases like reflection. For a list of attributes you can specify, see Keep attributes.
Keep attributes
Attributes are extra pieces of information attached to different parts of your code. Attributes store information like annotations and generic signatures from your code.
Certain reflective operations require specific attributes to be kept for successful execution. For example:
- When accessing the inner or outer class structure using
getEnclosingMethod()
orgetDeclaredClasses()
, the attributesEnclosingMethod
andInnerClasses
are needed. - When accessing generic signatures using
getTypeParameters()
, the attributeSignature
is needed. When accessing annotations using
getAnnotation()
, the attributeRuntimeVisibleAnnotations
is needed.
Commonly required attributes
When using the default Proguard file (proguard-android-optimize.txt
or
proguard-android.txt
), the Android Gradle plugin (AGP) keeps the following
attributes. Note that some of these attributes require newer versions of AGP:
Attribute | Description |
---|---|
AnnotationDefault |
This attribute is found on annotation types themselves and stores the default value for an annotation element. Note: This attribute is kept by default since AGP 7.1, and only needs to be explicitly kept in apps using earlier versions of AGP. |
EnclosingMethod |
This attribute is present in inner classes that are not local or anonymous classes. It identifies the method or initializer that immediately contains the class. |
InnerClasses |
This attribute records information about nested classes (inner classes, static nested classes, local classes, and anonymous classes) defined within another class. |
LineNumberTable |
This attribute maps bytecode instructions to their corresponding line numbers in the original source file. Note: This attribute is kept by default since Android Gradle Plugin (AGP) 8.6, and only needs to be explicitly kept in apps using earlier versions of AGP. |
RuntimeVisibleAnnotations |
This attribute stores annotations that are visible at runtime by reflection. Typically, if annotations are used at runtime, this is the only annotation from the *Annotation attributes that is needed by apps and in library consumer rules. |
RuntimeVisibleParameterAnnotations |
This attribute stores annotations that are visible at runtime by reflection on the parameters of a method. |
RuntimeVisibleTypeAnnotations |
This attribute stores annotations that apply to type uses rather than just declarations. This attribute is visible at runtime. |
Signature |
This attribute stores a more generic type signature for classes, methods, and fields, particularly when they use generics (like List<String> ). |
SourceFile |
This attribute stores the name of the source file (.kt or .java file) from which a class was compiled. It is primarily used by debuggers to display the original source code lines when stepping through compiled Java code. It helps developers trace execution back to their written code. Note: This attribute is kept by default since AGP 8.2, and only needs to be explicitly kept in apps using earlier versions of AGP. |
For apps that use proguard-android-optimize.txt
, the keep rules defined by AGP
are adequate in most scenarios. However, if you are writing code for a library,
you should specify all the attributes required by your library in its consumer
keep rules, even if they are defined in this list. This makes sure that your
library is robust if developers decide not to include
proguard-android-optimize.txt
.
Additional keep attributes
You can specify additional attributes to be kept, however they are not needed for the vast majority of reflective or JNI access scenarios. However, some of these might still frequently be used while optimizing libraries.
Attribute | Description |
---|---|
MethodParameters |
This attribute provides information about the parameters of a method, specifically their names and access flags. |
Exceptions |
This attribute lists the checked exceptions that a method is declared to throw. This attribute is not typically used for apps. For library authors, it is not typically used in consumer keep rules, but is often used when building libraries. For details about optimizing libraries, see Optimization for library authors. |
RuntimeInvisibleAnnotations |
This attribute stores annotations that are not visible with reflection at runtime on a class, field, or method. App developers shouldn't keep this attribute. For library authors, this attribute is not relevant in consumer keep rules, but is often used when building libraries. For details about optimizing libraries, see Optimization for library authors. |
RuntimeInvisibleParameterAnnotations |
This attribute stores annotations that are not visible with reflection at runtime on the parameters of a method. App developers shouldn't keep this attribute. For library authors, this attribute is not relevant in consumer keep rules, but is often used when building libraries. For details about optimizing libraries, see Optimization for library authors. |
RuntimeInvisibleTypeAnnotations |
This attribute stores annotations that apply to type uses rather than just declarations. This attribute is not visible at runtime. App developers shouldn't keep this attribute. For library authors, this attribute is not relevant in consumer keep rules, but is often used when building libraries. For details about optimizing libraries, see Optimization for library authors. |