web-dev-qa-db-ja.com

Crashlytics Android SDK-カスタムUncaughtExceptionHandler

カスタムのUncaughtExceptionHandlerをcrashlyticsと一緒に1つのアプリケーションに組み込むことは可能ですか?はいの場合-どのように?

28
jskierbi

Crashlyticsの最近のバージョンは初期化を非同期で実行するため、Fabricの初期化コールバックを使用することをお勧めします。

private static Thread.UncaughtExceptionHandler mDefaultUEH;
private static Thread.UncaughtExceptionHandler mCaughtExceptionHandler = 
   new Thread.UncaughtExceptionHandler() {
     @Override 
public void uncaughtException(Thread thread, Throwable ex) {
        // Custom logic goes here

        // This will make Crashlytics do its job
        mDefaultUEH.uncaughtException(thread, ex);
    }
};

CrashlyticsCore core = new CrashlyticsCore.Builder()
            .disabled(BuildConfig.DEBUG)
            .build();
Fabric.with(new Fabric.Builder(this).kits(new Crashlytics.Builder()
            .core(core)
            .build())
            .initializationCallback(new InitializationCallback<Fabric>() {
                @Override
                public void success(Fabric fabric) {
                    mDefaultUEH = Thread.getDefaultUncaughtExceptionHandler();
                    Thread.setDefaultUncaughtExceptionHandler(mCaughtExceptionHandler);
                }

                @Override
                public void failure(Exception e) {

                }
            })
            .build());
14
kmityak

[〜#〜]更新[〜#〜]

@kmityak answer を参照してください。Crashlytics/ Fabricの初期化が非同期になり、以下のソリューションが無効になったためです。

元の回答

例外をデフォルトのUncaughtExceptionHandlerに渡し、後でCrashlyticsを介して処理されるように、カスタムUncaughtExceptionHandlerを設定できます。

以下のコードはApplicationサブクラス内に実装されています。

private static Thread.UncaughtExceptionHandler mDefaultUEH;
private static Thread.UncaughtExceptionHandler mCaughtExceptionHandler = new Thread.UncaughtExceptionHandler() {
    @Override 
    public void uncaughtException(Thread thread, Throwable ex) {
        // Custom logic goes here

        // This will make Crashlytics do its job
        mDefaultUEH.uncaughtException(thread, ex);
    }
};

@Override
public void onCreate() {
    super.onCreate();

    // Order is important!
    // First, start Crashlytics
    Crashlytics.start(this);

    // Second, set custom UncaughtExceptionHandler
    mDefaultUEH = Thread.getDefaultUncaughtExceptionHandler();
    Thread.setDefaultUncaughtExceptionHandler(mCaughtExceptionHandler);
}

2番目のオプションは、カスタムUncaughtExceptionHandlerを設定した後でCrashlyticsafterを登録することです。キャッチされなかったすべての例外は、Crashlyticsによって致命的と報告され、その後、カスタムハンドラーに渡されます。

34
jskierbi

それらの解決策が私にとってうまくいったなら、何もありません。私はそれを次のように行いました:

// Setup handler for uncaught exceptions.
Thread.setDefaultUncaughtExceptionHandler (new Thread.UncaughtExceptionHandler()
{
    @Override
    public void uncaughtException (Thread thread, Throwable e)
    {
        //Send Report to Crashlytics. Crashlytics will send it as soon as it starts to work
        Crashlytics.logException(e);

        //Your custom codes to Restart the app or handle this crash
        HandleCrashes(thread, e);
    }
});

そして、これがアプリを再起動するための私のカスタムメソッドです:

private void HandleCrashes(Thread t, Throwable e) {

    Intent i = new Intent(mContext, frmLogin.class);
    i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK);
    i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
    i.putExtra("JustLogin", true);
    startActivity(i);

    System.exit(1);
}
2
user3682694

はい、可能です。

あなたのアプリケーションクラスで:

@Override
public void onCreate() {
    super.onCreate();
    Crashlytics.start(this);
    initUncaughtExceptionHandler();
}

private void initUncaughtExceptionHandler() {
    final ScheduledThreadPoolExecutor c = new ScheduledThreadPoolExecutor(1);
    c.schedule(new Runnable() {
        @Override
        public void run() {
            final UncaughtExceptionHandler defaultHandler = Thread.getDefaultUncaughtExceptionHandler();
            Thread.setDefaultUncaughtExceptionHandler(new UncaughtExceptionHandler() {
                @Override
                public void uncaughtException(Thread paramThread, Throwable paramThrowable) {
                    // do my amazing stuff here 
                    System.err.println("Error!");
                    //then pass the job to the previous handler
                    defaultHandler.uncaughtException(paramThread, paramThrowable);
                }
            });
        }
    }, 5, TimeUnit.SECONDS);
}

5秒後にこれをスケジュールするのは、Crashlyticsがセットアップするのに時間がかかるためです。私はこのコードを使用しており、完全に機能します。もちろん、アプリが起動時にクラッシュした場合、申し訳ありませんがカスタムハンドラーはありません;)

2
Manza

私はファブリック2.10.1の解決策を見つけました:

Thread.setDefaultUncaughtExceptionHandler(yourExceptionHandler)
Fabric.with(this, Crashlytics())