在编写android客户端应用时,总会由于各种各样的原因,导致我们的程序异常退出,这些原因包括:程序的不合理,异常的未捕获,这些通过我们的review都是可以提高的,但是如果是由于android不同的系统版本,不同的配置的机型导致我们的程序异常退出,这是无法避免的,但如何才能减少这个原因导致的程序异常呢,这正是写本篇文章的意图.

  在全局异常处理开始前,有两个类是我们必须要知道的,一个是android的Application类,这个类是一个应用程序的全局类,可以将一些所有模块都会用的公共信息都放在这个类中初始化,例如:用户登陆信息,手机信息等,一个应用程序的启动最先启动的就是其对应的Application类的实例,然后再由这个实例去调用要启动的那个Activity,另一个就是全局异常捕获类:Thread.UncaughtExceptionHandler,线程未捕获异常处理器,用来处理未捕获异常。如果程序出现了未捕获异常,默认会弹出系统中强制关闭对话框。我们需要实现此接口,并注册为程序中默认未捕获异常处理。这样当未捕获异常发生时,就可以定制异常处理操作,例如:将异常信息存放到SD卡文件中,将应用程序强制关闭,上传错误的日志文件等.

   一般情况下出现这种异常的原因有以下几点:

  1.应用的兼容性欠缺,不过这个孔明 没有办法的事件,android手机千差万别,不同的硬件配置,不同的的手机尺寸,不同的系统版本,所以难免会有考虑不周全的地方.

  2.编写程序时使用了高版本的API,这样当应用跑到低版本的android系统时自然会有异常发生.

  第二种情况是我们在写代码时可以尽量避免的,那就是如果用到了高版本的API,那一定要针对低版本的系统去做处理,这样就可减少这个原因产生的异常.那对于第一种情况怎么办呢,就要用到我们今天的主角,全局异常捕获了.

  当APP异常退出时,这部分异常信息是可以通过全局异常处理机制捕获到的,一旦捕获到后,就可以上传到我们的文件服务器中,去做分析,针对性的改进,这就是全局异常处理最主要的作用.

   全局异常示例代码:

/********************************************************** * @文件名称:MicCrashHandler.java * @创建时间:2014年10月20日 下午1:10:15 * @文件描述:捕获全局未处理到的异常,上传服务器 * @修改历史:2014年10月20日创建初始版本 **********************************************************/public class MicCrashHandler implements UncaughtExceptionHandler{    public static final String TAG = "MicCrashHandler";    /**     * 系统默认的异常捕获类     */    private Thread.UncaughtExceptionHandler mDefaultHandler;    /**     * 自定义异常处理类     */    private static MicCrashHandler INSTANCE;    private Context mContext;    /**     * 存储异常信息     */    private HashMap infos = new HashMap();    // 存储文件夹路径    private static final String path = Environment.getExternalStorageDirectory() + "/focustech/mic/log/";    private File dirFile;    private File file;    private static final String fileName = "mic_crash_exception.log";    private MicCrashHandler()    {    }    static    {        INSTANCE = new MicCrashHandler();    }    /**     * 单例模式,获取自定义异常处理类     */    public static MicCrashHandler getInstance()    {        return INSTANCE;    }    public void init(Context context)    {        mContext = context;        mDefaultHandler = Thread.getDefaultUncaughtExceptionHandler();        Thread.setDefaultUncaughtExceptionHandler(this);    }    /**     *      * 自定义异常处理     * @param thread     * @param ex     */    @Override    public void uncaughtException(Thread thread, Throwable ex)    {        if (!handleException(ex) && mDefaultHandler != null)        {            // 如果用户没有处理则让系统默认的异常处理器来处理            mDefaultHandler.uncaughtException(thread, ex);        }        else        {        }    }    /**     * 自定义错误处理,收集错误信息 发送错误报告等操作均在此完成.     */    private boolean handleException(Throwable ex)    {        if (ex == null)        {            return false;        }        new Thread()        {            @Override            public void run()            {                Looper.prepare();                ToastUtil.toast(mContext, R.string.crash_exception);                Looper.loop();            }        }.start();        // 收集设备参数信息        Util.collectDeviceInfo(mContext, infos);        // 保存日志文件        saveCrashInfo2File(ex);        /**         * 以后要加上传功能,需要启动服务去上传应该         */        // uploadExceptionFile();        ActivityManager.getInstance().finishAllActivity();        Process.killProcess(Process.myPid());        System.exit(0);        return true;    }    /**     * 保存错误信息到文件中     * @param ex     * @return    返回文件名称,便于将文件传送到服务器     */    private void saveCrashInfo2File(Throwable ex)    {        /**         * 组装异常信息         */        String exceptionMsg = assembleExceptionMsg(ex);        try        {            if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED))            {                dirFile = new File(path);                if (!dirFile.exists())                {                    dirFile.mkdirs();                }                file = new File(path + fileName);                RandomAccessFile fos = new RandomAccessFile(file, "rw");                fos.seek(file.length());                fos.write(exceptionMsg.getBytes());                fos.close();            }        }        catch (Exception e)        {            e.printStackTrace();        }    }    /**     * 组装异常信息,在这里拼装想要的格式     */    private String assembleExceptionMsg(Throwable ex)    {        StringBuffer sb = new StringBuffer();        for (Map.Entry entry : infos.entrySet())        {            String key = entry.getKey();            String value = entry.getValue();            sb.append(key + "=" + value + "\n");        }        Writer writer = new StringWriter();        PrintWriter printWriter = new PrintWriter(writer);        ex.printStackTrace(printWriter);        Throwable cause = ex.getCause();        while (cause != null)        {            cause.printStackTrace(printWriter);            cause = cause.getCause();        }        printWriter.close();        String result = writer.toString();        sb.append(result + "\r\n");        return sb.toString();    }    /**     * 发送上传文件请求     */    @SuppressWarnings("unused")    private void uploadExceptionFile()    {        if (!NetworkUtils.isConnectInternet(mContext))        {            return;        }        if (file == null || !file.exists())        {            return;        }        else        {            RequestCenter.uploadExceptionFile(mContext, listener, file);        }    }    private DisposeDataListener listener = new DisposeDataListener()    {        @Override        public void onSuccess(Object obj)        {            /**             * 发送成功后,还要删除此异常文件,才退出                         */            SysManager.exitSystem(mContext);        }        @Override        public void onFailure(Object failedReason)        {            SysManager.exitSystem(mContext);        }    };}



更多相关文章

  1. Android中Activity全局共享方法AppContext
  2. Android(安卓)Touch事件传递机制解析
  3. Android音视频处理技术 视频录制
  4. Android调用系统相机、自定义相机、处理大图片
  5. Android(安卓)之 Window、WindowManager 与窗口管理
  6. 让editView、AutoCompleteTextView开始捕获的焦点
  7. Android菜鸟的成长笔记(11)——Android中的事件处理
  8. Android中Activity全局共享方法AppContext
  9. Android日志打印与处理 UncaughtExceptionHandler 提交服务器

随机推荐

  1. TextView中ellipsize属性焦点异常处理
  2. 如何为香蕉派 banana pi BPI-M2编译Andro
  3. android菜单Tips
  4. Android 编程设置 APN
  5. [android]Activity切换动画
  6. Android(安卓)EGL_BAD_CONFIG error,配置E
  7. Android适配器之-----SimpleAdapter
  8. Android UI开发第二篇——多级列表(Expand
  9. android布局学习利器-Hierarchy Viewer
  10. Android中/system/build.prop文件解读