1. 程式人生 > >如何自定義一個全域性異常捕獲器-SpiderMan

如何自定義一個全域性異常捕獲器-SpiderMan

一圖勝前言

上圖中,我們模擬了NullPointerException的發生,系統捕獲了該異常,並用一個介面展示了出來。

如何實現

想要實現全域性異常的捕獲我們需要了解Thead中的一個內部介面UncaughtExceptionHandler,該介面在JDK1.5中被新增。

所有我們需要自定義一個類去實現該介面,並且設定給ThreadDefaultUncaughtExceptionHandler

//虛擬碼
public class SpiderMan implements Thread.UncaughtExceptionHandler {
    private SpiderMan
()
{ Thread.setDefaultUncaughtExceptionHandler(this); } @Override public void uncaughtException(Thread t, Throwable ex) { } } 複製程式碼

UncaughtExceptionHandler會捕獲程式碼中沒有捕獲的異常,然後回撥給uncaughtException方法。

高階操作

解析Throwable

 private CrashModel parseCrash(Throwable ex) {
        CrashModel model = new
CrashModel(); try { model.setEx(ex); model.setTime(new Date().getTime()); if (ex.getCause() != null) { ex = ex.getCause(); } model.setExceptionMsg(ex.getMessage()); StringWriter sw = new StringWriter(); PrintWriter pw = new
PrintWriter(sw); ex.printStackTrace(pw); pw.flush(); String exceptionType = ex.getClass().getName(); if (ex.getStackTrace() != null && ex.getStackTrace().length > 0) { StackTraceElement element = ex.getStackTrace()[0]; model.setLineNumber(element.getLineNumber()); model.setClassName(element.getClassName()); model.setFileName(element.getFileName()); model.setMethodName(element.getMethodName()); model.setExceptionType(exceptionType); } model.setFullException(sw.toString()); } catch (Exception e) { return model; } return model; } 複製程式碼

如上程式碼所示,我們可以從Throwable類中解析出很多有用的資訊,包括崩潰發生的類所在行數,exception的型別...

跳轉新的介面顯示Crash資訊

Intent intent = new Intent(mContext, CrashActivity.class);
intent.putExtra(CrashActivity.CRASH_MODEL, model);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
mContext.startActivity(intent);
複製程式碼

在對Throwable解析完成後,我們就可以跳轉到一個新的Activity並展示Crash的相關資訊,這裡Context是Application的Context,所有必須使用Intent.FLAG_ACTIVITY_NEW_TASK才能成功跳轉。

分享Crash資訊

分享文字

把Throwable解析成有用的字串,呼叫系統的分享方法

private void shareText(String text) {
        Intent intent = new Intent(Intent.ACTION_SEND);
        intent.setType("text/plain");
        intent.putExtra(Intent.EXTRA_SUBJECT, "崩潰資訊:");
        intent.putExtra(Intent.EXTRA_TEXT, text);
        intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        startActivity(Intent.createChooser(intent, "分享到"));
    }
複製程式碼

分享長圖

分享圖片要涉及東西就多啦,比如ScrollView的截圖,如何儲存到Sd卡,6.0需要動態許可權檢測,7.0還要相容fileprovider,具體看原始碼吧,哈哈哈哈!

原始碼地址

github.com/simplepeng/…