Приложение для Android аварийно завершало работу при запуске в режиме выпуска: java.lang.NoSuchFieldError: ошибка BUILD

У меня есть приложение, которое я обновляю для новой версии. Приложение хорошо работает в режиме отладки, когда я создаю подписанный APK и запускаю его на своем устройстве, оно падает. Я проверил logcat, и ниже приведена трассировка стека:

java.lang.NoSuchFieldError: BUILD
E/AndroidRuntime(28433):        at java.lang.Class.getDeclaredAnnotation(Native Method)
E/AndroidRuntime(28433):        at java.lang.Class.getAnnotation(Class.java:290)
E/AndroidRuntime(28433):        at org.a.a.a(SourceFile:115)
E/AndroidRuntime(28433):        at com.package.utils.MyApplication.onCreate(SourceFile:42)
E/AndroidRuntime(28433):        at android.app.Instrumentation.callApplicationOnCreate(Instrumentation.java:1030)
E/AndroidRuntime(28433):        at android.app.ActivityThread.handleBindApplication(ActivityThread.java:4409)
E/AndroidRuntime(28433):        at android.app.ActivityThread.access$1500(ActivityThread.java:139)
E/AndroidRuntime(28433):        at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1270)
E/AndroidRuntime(28433):        at android.os.Handler.dispatchMessage(Handler.java:102)
E/AndroidRuntime(28433):        at android.os.Looper.loop(Looper.java:136)
E/AndroidRuntime(28433):        at android.app.ActivityThread.main(ActivityThread.java:5086)
E/AndroidRuntime(28433):        at java.lang.reflect.Method.invokeNative(Native Method)
E/AndroidRuntime(28433):        at java.lang.reflect.Method.invoke(Method.java:515)
E/AndroidRuntime(28433):        at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:785)
E/AndroidRuntime(28433):        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:601)
E/AndroidRuntime(28433):        at dalvik.system.NativeStart.main(Native Method)
W/ActivityManager(  861):   Force finishing activity com.package.activities/.SplashActivity

В моем файле MyApplication выглядит так:

package com.package.utils;

import android.app.Application;
import android.content.Context;
import android.support.multidex.MultiDex;

import com.facebook.FacebookSdk;
import com.google.android.gms.analytics.GoogleAnalytics;
import com.google.android.gms.analytics.HitBuilders;
import com.google.android.gms.analytics.StandardExceptionParser;
import com.google.android.gms.analytics.Tracker;
import com.package.activities.R;

import org.acra.ACRA;
import org.acra.ReportField;
import org.acra.ReportingInteractionMode;
import org.acra.annotation.ReportsCrashes;

@ReportsCrashes(formUri = "", mailTo = AppUtils.CRASH_REPORT_EMAIL, customReportContent = {ReportField.BUILD,
    ReportField.USER_APP_START_DATE, ReportField.USER_CRASH_DATE, ReportField.USER_EMAIL, ReportField.APP_VERSION_NAME,
    ReportField.ANDROID_VERSION, ReportField.PHONE_MODEL, ReportField.CUSTOM_DATA, ReportField.STACK_TRACE,
    ReportField.LOGCAT,}, mode = ReportingInteractionMode.TOAST, resToastText = R.string.crashed_report)
public class MyApplication extends Application {

public static final String TAG = MyApplication.class.getSimpleName();

private static MyApplication mInstance;
private static Context context;

public static synchronized MyApplication getInstance() {
    return mInstance;
}

@Override
public void onCreate() {
    super.onCreate();
    FacebookSdk.sdkInitialize(getApplicationContext());
    FacebookSdk.setApplicationId(getResources().getString(R.string.facebook_app_id));
//        MyApplication.context = getApplicationContext();
    //reference: https://github.com/ACRA/acra/wiki/BasicSetup
    //The following line triggers the initialization of ACRA
    ACRA.init(this);

    mInstance = this;

    AnalyticsTrackers.initialize(this);
    AnalyticsTrackers.getInstance().get(AnalyticsTrackers.Target.APP);
}
}

ACRA.init(это) — номер строки. 42 в этом.

Как убрать эту ошибку?

EDITED: Ниже приведен мой полный файл proguead:

-keep class * extends java.util.ListResourceBundle {
protected Object[][] getContents();
    }

-keep public class com.google.android.gms.common.internal.safeparcel.SafeParcelable {
public static final *** NULL;
    }
# This is a configuration file for ProGuard.
# http://proguard.sourceforge.net/index.html    #manual/usage.html

-dontusemixedcaseclassnames
-dontskipnonpubliclibraryclasses
-verbose

-keepnames class org.apache.** {*;    }
-keep class org.apache.** {*;    }
-keep class android.support.v4.** { *;     }
-keep interface android.support.v4.app.** { *;     }
-dontnote android.support.v4.**
-keep class org.joda.time.** { *;     }
-keep interface org.joda.time.** { *;    }
-keep class android.support.v7.app.** { *;     }
-keep interface android.support.v7.app.** { *;     }
-keep class org.acra.** { *;     }

# keep this class so that logging will show 'ACRA' and not a obfuscated name like 'a'.
# Note: if you are removing log messages elsewhere in this file then this isn't necessary
-keep class org.acra.ACRA {
*;
}

# keep this around for some enums that ACRA needs
-keep class org.acra.ReportingInteractionMode {
*;
}

-keepnames class org.acra.sender.HttpSender$** {
*;
}

-keepnames class org.acra.ReportField {
*;
}

# keep this otherwise it is removed by ProGuard
-keep public class org.acra.ErrorReporter{
public void addCustomData(java.lang.String,java.lang.String);
public void putCustomData(java.lang.String,java.lang.String);
public void removeCustomData(java.lang.String);
}

# keep this otherwise it is removed by ProGuard
-keep public class org.acra.ErrorReporter{
public void handleSilentException(java.lang.Throwable);
}

-keepclassmembers class * implements java.io.Serializable{
private static final java.io.ObjectStreamField[] serialPersistentFields;
private void writeObject(java.io.ObjectOutputStream);
private void readObject(java.io.ObjectInputStream);
java.lang.Object writeReplace();
java.lang.Object readResolve();
}

-keep class com.viewpagerindicator.** { *;     }
-dontskipnonpubliclibraryclassmembers

-dontwarn org.apache.commons.logging.LogFactory
-dontwarn org.apache.http.annotation.ThreadSafe
-dontwarn org.apache.http.annotation.Immutable
-dontwarn org.apache.http.annotation.NotThreadSafe
-dontwarn org.jodatime.time.**
-dontwarn org.joda.convert.**
-dontwarn org.apache.http.**
-dontwarn android.net.**
# Optimization is turned off by default. Dex does not like code run
# through the ProGuard optimize and preverify steps (and performs some
# of these optimizations on its own).
-dontoptimize
-dontpreverify

# Note that if you want to enable optimization, you cannot just
# include optimization flags in your own project configuration file;
# instead you will need to point to the
# "proguard-android-optimize.txt" file instead of this one from your
# project.properties file.

-keepattributes *Annotation*
-keep public class com.google.vending.licensing.ILicensingService
-keep public class com.android.vending.licensing.ILicensingService

# For native methods, see http://proguard.sourceforge.net/manual/examples.html    #native
-keepclasseswithmembernames class * {
native <methods>;
}

# keep setters in Views so that animations can still work.
# see http://proguard.sourceforge.net/manual/examples.html    #beans
-keepclassmembers public class * extends android.view.View {
   void set*(***);
   *** get*();
}

# We want to keep methods in Activity that could be used in the XML attribute onClick
-keepclassmembers class * extends android.app.Activity {
   public void *(android.view.View);
}

# For enumeration classes, see     http://proguard.sourceforge.net/manual/examples.html    #enumerations
-keepclassmembers enum * {
public static **[] values();
public static ** valueOf(java.lang.String);
}

-keep class * implements android.os.Parcelable {
  public static final android.os.Parcelable$Creator *;
}

-keepclassmembers class **.R$* {
public static <fields>;
}


#    #---------------Begin: proguard configuration for Gson  ----------

# removes such information by default, so configure it to keep all of it.
-keepattributes Signature

# Gson specific classes
-keep class sun.misc.Unsafe { *;     }

# Application classes that will be serialized/deserialized over Gson



#    #---------------End: proguard configuration for Gson  ----------
# The support library contains references to newer platform versions.
# Don't warn about those in case this app is linking against an older
# platform version.  We know about them, and they are safe.
-dontwarn android.support.**

-keepnames @com.google.android.gms.common.annotation.KeepName class *
-keepclassmembernames class * {
@com.google.android.gms.common.annotation.KeepName *;
}

-keepnames class * implements android.os.Parcelable {
public static final ** CREATOR;
}

-renamesourcefileattribute SourceFile
-keepattributes SourceFile,LineNumberTable

РЕДАКТИРОВАТЬ 2: я не думаю, что с ACRA что-то не так, так как я пытался подписать после удаления ACRA из моего проекта, но ошибка все та же.

РЕДАКТИРОВАТЬ 3: После многих попыток я понял, что причиной этой проблемы является Google Analytics. Когда я собираю APK без Google Analytics (путем удаления последних двух строк onCreate в MyApplication, он работает нормально, тогда как с этими строками происходит сбой, а логарифм остается таким же, как показано выше.


person Aashish Gulabani    schedule 05.05.2016    source источник
comment
Для какой версии ACRA указана трассировка стека выше?   -  person William    schedule 06.05.2016
comment
Трассировка стека была одинаковой для двух версий ACRA, которые я пробовал, и для версий 4.7.0 и 4.8.1.   -  person Aashish Gulabani    schedule 06.05.2016
comment
Нет. Это НЕ трассировка стека из acra-4.8.1. Он соответствует acra-4.7.0 и говорит мне, что ваш прогурдированный код был лишен аннотаций.   -  person William    schedule 06.05.2016
comment
Я впервые создаю подписанный APK из студии Android. Я не очень хорошо знаю этот файл proguard. Я не понял, что вы имеете в виду, говоря, что ваш прогурдированный код лишен аннотаций. И я просто пробовал что-то и заметил, что когда я удаляю ACRA из своего проекта, а затем собираю, эта ошибка все еще существует.   -  person Aashish Gulabani    schedule 06.05.2016
comment
Если вы полностью удалили ACRA из проекта и все еще имеете эту ошибку, это означает, что proguard удалил другую библиотеку или ваш собственный код.   -  person Fiil    schedule 06.05.2016
comment
код зачищен средствами proguard?   -  person Aashish Gulabani    schedule 06.05.2016
comment
Если вы удалили ACRA из своего проекта, вы не могли бы получить точно такую ​​же ошибку, потому что трассировка стека этой ошибки почти наверняка содержит класс ACRA org.a.a.a.   -  person William    schedule 07.05.2016
comment
После многих проб и ошибок я понял, что причиной этой проблемы является Google Analytics. Когда я создаю APK без Google Analytics (путем удаления последних двух строк onCreate в MyApplication, он работает нормально, тогда как с этими строками происходит сбой, а логарифм остается таким же, как показано выше).   -  person Aashish Gulabani    schedule 16.05.2016


Ответы (2)


Вы должны подготовить свою конфигурацию proguard для выпуска версии.

Прочитайте здесь, как настроить proguard для ACRA.

Включите это в свой конфигурационный файл proguard:

#ACRA specifics
# Restore some Source file names and restore approximate line numbers in the stack traces,
# otherwise the stack traces are pretty useless
-keepattributes SourceFile,LineNumberTable

# ACRA needs "annotations" so add this... 
# Note: This may already be defined in the default "proguard-android-optimize.txt"
# file in the SDK. If it is, then you don't need to duplicate it. See your
# "project.properties" file to get the path to the default "proguard-android-optimize.txt".
-keepattributes *Annotation*

# keep this class so that logging will show 'ACRA' and not a obfuscated name like 'a'.
# Note: if you are removing log messages elsewhere in this file then this isn't necessary
-keep class org.acra.ACRA {
    *;
}

# keep this around for some enums that ACRA needs
-keep class org.acra.ReportingInteractionMode {
    *;
}

-keepnames class org.acra.sender.HttpSender$** {
    *;
}

-keepnames class org.acra.ReportField {
    *;
}

# keep this otherwise it is removed by ProGuard
-keep public class org.acra.ErrorReporter
{
    public void addCustomData(java.lang.String,java.lang.String);
    public void putCustomData(java.lang.String,java.lang.String);
    public void removeCustomData(java.lang.String);
}

# keep this otherwise it is removed by ProGuard
-keep public class org.acra.ErrorReporter
{
    public void handleSilentException(java.lang.Throwable);
}
person Fiil    schedule 05.05.2016
comment
Я добавил приведенный выше код и попытался создать подписанный APK, но все тот же журнал ошибок. Я использую ACRA 4.7.0. - person Aashish Gulabani; 05.05.2016

Я согласен с @Fiil, это похоже на ошибку proguard.

Я рекомендую перейти на ACRA 4.8.1 или более позднюю версию, так как она содержит файл конфигурации proguard.

person F43nd1r    schedule 05.05.2016
comment
Я изменил свою библиотеку ACRA на 4.8.1, но ошибка осталась прежней. Я отредактировал свой пост, чтобы добавить полный файл proguard. Пожалуйста, посмотрите и дайте мне знать, если что-то не так. - person Aashish Gulabani; 05.05.2016