You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android应用能否自行检测自身过往崩溃并接收崩溃通知?

Android应用捕获自身崩溃及Service重启通知方案

Android应用可以捕获自身崩溃事件(包括Service崩溃),并触发通知或在重启后收集调试信息,以下是具体实现方案:

一、捕获全局崩溃(含Service)

通过自定义UncaughtExceptionHandler替换系统默认异常处理器,在崩溃发生时收集调试信息并触发通知。由于崩溃后进程会快速终止,建议先将日志写入本地存储,再通过轻量化逻辑发送通知,或依赖独立进程组件完成通知发送。

示例代码:

public class CrashHandler implements Thread.UncaughtExceptionHandler {
    private final Thread.UncaughtExceptionHandler defaultHandler;
    private final Context context;

    public CrashHandler(Context context) {
        this.context = context;
        defaultHandler = Thread.getDefaultUncaughtExceptionHandler();
    }

    @Override
    public void uncaughtException(Thread thread, Throwable throwable) {
        // 收集崩溃信息:栈轨迹、设备信息、时间戳等
        String crashLog = collectCrashDetails(throwable);
        // 写入本地存储(内部文件或SharedPreferences)
        saveCrashLog(crashLog);
        // 发送崩溃通知
        sendCrashAlert(crashLog);
        // 交给系统默认处理器终止进程
        defaultHandler.uncaughtException(thread, throwable);
    }

    private String collectCrashDetails(Throwable throwable) {
        StringWriter sw = new StringWriter();
        PrintWriter pw = new PrintWriter(sw);
        throwable.printStackTrace(pw);
        // 追加设备信息
        sw.append("\n设备型号:").append(Build.MODEL);
        sw.append("\n系统版本:").append(Build.VERSION.RELEASE);
        return sw.toString();
    }

    private void saveCrashLog(String log) {
        try {
            File logFile = new File(context.getFilesDir(), "crash_records.txt");
            FileWriter writer = new FileWriter(logFile, true);
            writer.write(new Date().toString() + "\n" + log + "\n\n");
            writer.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    private void sendCrashAlert(String log) {
        NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
        // Android 8.0+ 创建通知渠道
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            NotificationChannel channel = new NotificationChannel("crash_channel", "崩溃告警", NotificationManager.IMPORTANCE_HIGH);
            notificationManager.createNotificationChannel(channel);
        }
        Notification notification = new NotificationCompat.Builder(context, "crash_channel")
                .setContentTitle("应用组件崩溃")
                .setContentText("Service发生异常,已保存日志")
                .setSmallIcon(R.drawable.ic_crash_alert)
                .setPriority(NotificationCompat.PRIORITY_HIGH)
                .build();
        notificationManager.notify(1001, notification);
    }
}

在Application初始化时设置异常处理器:

@Override
public void onCreate() {
    super.onCreate();
    CrashHandler crashHandler = new CrashHandler(this);
    Thread.setDefaultUncaughtExceptionHandler(crashHandler);
}

二、监听Service重启并触发通知

若Service配置了前台属性(startForeground)或系统允许自动重启,可在Service的onCreate方法中检查本地崩溃日志,判断是否为崩溃后的重启,进而发送通知并处理日志。

示例代码:

@Override
public void onCreate() {
    super.onCreate();
    File crashLogFile = new File(getFilesDir(), "crash_records.txt");
    if (crashLogFile.exists() && crashLogFile.length() > 0) {
        // 发送重启通知
        sendRestartNotification();
        // 上传或解析崩溃日志(可后台异步执行)
        processStoredCrashLog();
        // 清除历史日志标记(可选)
        crashLogFile.delete();
    }
    // 初始化Service业务逻辑
}

private void sendRestartNotification() {
    NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        NotificationChannel channel = new NotificationChannel("restart_channel", "服务重启通知", NotificationManager.IMPORTANCE_DEFAULT);
        notificationManager.createNotificationChannel(channel);
    }
    Notification notification = new NotificationCompat.Builder(this, "restart_channel")
            .setContentTitle("Service已重启")
            .setContentText("此前发生崩溃,已完成自动恢复")
            .setSmallIcon(R.drawable.ic_restart)
            .build();
    notificationManager.notify(1002, notification);
}

三、关键注意事项

  • Android 12及以上版本需申请POST_NOTIFICATIONS权限,否则通知无法显示。
  • 崩溃后的进程生命周期极短,通知发送逻辑需轻量化,避免耗时操作;若需确保通知发送成功,可使用独立进程的Service或BroadcastReceiver处理。
  • 系统对进程重启的策略受版本、进程优先级影响,部分场景下Service崩溃后可能不会自动重启,建议结合JobScheduler或WorkManager实现兜底的日志上报逻辑。

内容的提问来源于stack exchange,提问作者tse

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.13 14:47:25