基于开源项目acra实现的定制化Android crash上报库及后台系统
2013-12-04 14:21
573 查看
出发点:
开源的acra crash上报库(
http://code.google.com/p/acra/
)的缺点有: 1. crash上报到google doc里的话,由于被墙了,所以看不到数据。 2 如果基于邮件上报crash的话,不方便统计crash崩溃率。3. acra上报的字段过多,需要过滤一些没用的字段。
目的:
当Android应用程序崩溃时,可以及时通过浏览器查看到崩溃的堆栈信息,同时后台还可以统计每天的崩溃比率,以方便应用程序的体验改进
实践过程:
1. 首先下载acra的源码svn checkout http://acra.googlecode.com/svn/trunk,
在eclipse中导入该项目,在ACRA.java中发现默认上报的字段内容有:
public static final ReportField[] DEFAULT_REPORT_FIELDS = { REPORT_ID, APP_VERSION_CODE, APP_VERSION_NAME,
PACKAGE_NAME, FILE_PATH, PHONE_MODEL, BRAND, PRODUCT, ANDROID_VERSION, BUILD, TOTAL_MEM_SIZE,
AVAILABLE_MEM_SIZE, CUSTOM_DATA, IS_SILENT, STACK_TRACE, INITIAL_CONFIGURATION, CRASH_CONFIGURATION,
DISPLAY, USER_COMMENT, USER_EMAIL, USER_APP_START_DATE, USER_CRASH_DATE, DUMPSYS_MEMINFO, LOGCAT,
DEVICE_ID, INSTALLATION_ID, DEVICE_FEATURES, ENVIRONMENT, SHARED_PREFERENCES, SETTINGS_SYSTEM,
SETTINGS_SECURE };
复制代码
2.过滤一些无用的字段,当Android应用崩溃后,需要统计的数据只有11个,如下所示:
字段 说明
Firgure 1 上报字段
在ACRA.java中的addReportSenders函数中增加Figure1中上报字段的映射:
if (conf.formUri() != null && !"".equals(conf.formUri())) {
Map<ReportField, String> mapField = new HashMap<ReportField,String>();
mapField.put(ReportField.ANDROID_VERSION, "android_version");
mapField.put(ReportField.APP_VERSION_CODE, "app_version_code");
mapField.put(ReportField.APP_VERSION_NAME, "app_version_name");
mapField.put(ReportField.DEVICE_ID, "device_id");
mapField.put(ReportField.PHONE_MODEL, "model");
mapField.put(ReportField.BRAND, "brand");
mapField.put(ReportField.PRODUCT, "product");
mapField.put(ReportField.STACK_TRACE, "stack_trace");
mapField.put(ReportField.USER_CRASH_DATE, "crash_date");
mapField.put(ReportField.PACKAGE_NAME, "package_name");
errorReporter.addReportSender(new HttpPostSender(conf.formUri(), mapField));
return;
}
复制代码
在HttpPostSender.java中的remap函数中修改如下:
for (ReportField field : fields) {
/* if (mMapping == null || mMapping.get(field) == null) {
finalReport.put(field.toString(), report.get(field));
} else {
finalReport.put(mMapping.get(field), report.get(field));
}*/
if(mMapping!=null && mMapping.get(field) != null){
finalReport.put(mMapping.get(field), report.get(field));
}
}
复制代码
finalReport.put("platform_id", ACRA.getConfig().platformId());
3. 修改完后,只需要在应用程序中增加如下几行代码,就可以实时的上报崩溃的堆栈信息(这点比ios平台方便)
@ReportsCrashes(formKey = "", // will not be used
platformId="1",
formUriBasicAuthLogin = "user",
formUriBasicAuthPassword = "password",
formUri = "http://weiwangzi.com:8080/CrashReport/CrashServerlet")
public class TestApplication extends Application {
@Override
public void onCreate() {
// TODO Auto-generated method stub
super.onCreate();
ACRA.init(this);
}
复制代码
4. 实现serverlet来统计上报的crash数据到数据库中
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
Connection conn = null;
PreparedStatement pstmt = null;
try{
conn = DBUtil.getConnection();
String platformId=request.getParameter("platform_id");
String androidVersion=request.getParameter("android_version");
String appVersionCode=request.getParameter("app_version_code");
String appVersionName=request.getParameter("app_version_name");
String deviceId=request.getParameter("device_id");
String model=request.getParameter("model");
String brand=request.getParameter("brand");
String product=request.getParameter("product");
String stackTrace=request.getParameter("stack_trace");
String crashDate=request.getParameter("crash_date");
String packageName=request.getParameter("package_name");
pstmt = conn.prepareStatement("insert into report(platform_id, android_version, app_version_code,appversion_name,device_id,model,brand,product,stack_trace,crash_date,package_name) values (?, ?, ?,?,?,?,?,?,?,?,?)");
pstmt.setString(1, platformId);
pstmt.setString(2, androidVersion);
pstmt.setString(3, appVersionCode);
pstmt.setString(4, appVersionName);
pstmt.setString(5, deviceId);
pstmt.setString(6, model);
pstmt.setString(7, brand);
pstmt.setString(8, product);
pstmt.setString(9, stackTrace);
pstmt.setString(10, crashDate);
pstmt.setString(11, packageName);
pstmt.executeUpdate();
}catch(Exception e){
e.printStackTrace();
}finally{
if(pstmt!=null){
try {
pstmt.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
//e.printStackTrace();
}
}
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
//e.printStackTrace();
}
}
}
}
复制代码
实践结果:通过数据库可以导出一个excel的crash报表,或者直接通过浏览器查看
开源的acra crash上报库(
http://code.google.com/p/acra/
)的缺点有: 1. crash上报到google doc里的话,由于被墙了,所以看不到数据。 2 如果基于邮件上报crash的话,不方便统计crash崩溃率。3. acra上报的字段过多,需要过滤一些没用的字段。
目的:
当Android应用程序崩溃时,可以及时通过浏览器查看到崩溃的堆栈信息,同时后台还可以统计每天的崩溃比率,以方便应用程序的体验改进
实践过程:
1. 首先下载acra的源码svn checkout http://acra.googlecode.com/svn/trunk,
在eclipse中导入该项目,在ACRA.java中发现默认上报的字段内容有:
public static final ReportField[] DEFAULT_REPORT_FIELDS = { REPORT_ID, APP_VERSION_CODE, APP_VERSION_NAME,
PACKAGE_NAME, FILE_PATH, PHONE_MODEL, BRAND, PRODUCT, ANDROID_VERSION, BUILD, TOTAL_MEM_SIZE,
AVAILABLE_MEM_SIZE, CUSTOM_DATA, IS_SILENT, STACK_TRACE, INITIAL_CONFIGURATION, CRASH_CONFIGURATION,
DISPLAY, USER_COMMENT, USER_EMAIL, USER_APP_START_DATE, USER_CRASH_DATE, DUMPSYS_MEMINFO, LOGCAT,
DEVICE_ID, INSTALLATION_ID, DEVICE_FEATURES, ENVIRONMENT, SHARED_PREFERENCES, SETTINGS_SYSTEM,
SETTINGS_SECURE };
复制代码
2.过滤一些无用的字段,当Android应用崩溃后,需要统计的数据只有11个,如下所示:
字段 说明
[align=left]字段[/align] | [align=left]说明[/align] |
[align=left]platform_id[/align] | [align=left]1 =aPad,2=aPhone[/align] |
[align=left]android_version[/align] | [align=left]Android版本号[/align] |
[align=left]app_version_code[/align] | [align=left]应用的版本代码 如 9[/align] |
[align=left]app_version_name[/align] | [align=left]应用的版本名称 如 1.2.2[/align] |
[align=left]device_id[/align] | [align=left]设备的唯一id[/align] |
[align=left]model[/align] | [align=left]手机/平板的模型,如BCM63[/align] |
[align=left]brand[/align] | [align=left]Android设备牌子,如三星[/align] |
[align=left]product[/align] | [align=left]Android产品信息[/align] |
[align=left]stack_trace[/align] | [align=left]崩溃的堆栈信息[/align] |
[align=left]crash_date[/align] | [align=left]崩溃的时间点[/align] |
[align=left]package_name[/align] | [align=left]应用的包名[/align] |
在ACRA.java中的addReportSenders函数中增加Figure1中上报字段的映射:
if (conf.formUri() != null && !"".equals(conf.formUri())) {
Map<ReportField, String> mapField = new HashMap<ReportField,String>();
mapField.put(ReportField.ANDROID_VERSION, "android_version");
mapField.put(ReportField.APP_VERSION_CODE, "app_version_code");
mapField.put(ReportField.APP_VERSION_NAME, "app_version_name");
mapField.put(ReportField.DEVICE_ID, "device_id");
mapField.put(ReportField.PHONE_MODEL, "model");
mapField.put(ReportField.BRAND, "brand");
mapField.put(ReportField.PRODUCT, "product");
mapField.put(ReportField.STACK_TRACE, "stack_trace");
mapField.put(ReportField.USER_CRASH_DATE, "crash_date");
mapField.put(ReportField.PACKAGE_NAME, "package_name");
errorReporter.addReportSender(new HttpPostSender(conf.formUri(), mapField));
return;
}
复制代码
在HttpPostSender.java中的remap函数中修改如下:
for (ReportField field : fields) {
/* if (mMapping == null || mMapping.get(field) == null) {
finalReport.put(field.toString(), report.get(field));
} else {
finalReport.put(mMapping.get(field), report.get(field));
}*/
if(mMapping!=null && mMapping.get(field) != null){
finalReport.put(mMapping.get(field), report.get(field));
}
}
复制代码
finalReport.put("platform_id", ACRA.getConfig().platformId());
3. 修改完后,只需要在应用程序中增加如下几行代码,就可以实时的上报崩溃的堆栈信息(这点比ios平台方便)
@ReportsCrashes(formKey = "", // will not be used
platformId="1",
formUriBasicAuthLogin = "user",
formUriBasicAuthPassword = "password",
formUri = "http://weiwangzi.com:8080/CrashReport/CrashServerlet")
public class TestApplication extends Application {
@Override
public void onCreate() {
// TODO Auto-generated method stub
super.onCreate();
ACRA.init(this);
}
复制代码
4. 实现serverlet来统计上报的crash数据到数据库中
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
Connection conn = null;
PreparedStatement pstmt = null;
try{
conn = DBUtil.getConnection();
String platformId=request.getParameter("platform_id");
String androidVersion=request.getParameter("android_version");
String appVersionCode=request.getParameter("app_version_code");
String appVersionName=request.getParameter("app_version_name");
String deviceId=request.getParameter("device_id");
String model=request.getParameter("model");
String brand=request.getParameter("brand");
String product=request.getParameter("product");
String stackTrace=request.getParameter("stack_trace");
String crashDate=request.getParameter("crash_date");
String packageName=request.getParameter("package_name");
pstmt = conn.prepareStatement("insert into report(platform_id, android_version, app_version_code,appversion_name,device_id,model,brand,product,stack_trace,crash_date,package_name) values (?, ?, ?,?,?,?,?,?,?,?,?)");
pstmt.setString(1, platformId);
pstmt.setString(2, androidVersion);
pstmt.setString(3, appVersionCode);
pstmt.setString(4, appVersionName);
pstmt.setString(5, deviceId);
pstmt.setString(6, model);
pstmt.setString(7, brand);
pstmt.setString(8, product);
pstmt.setString(9, stackTrace);
pstmt.setString(10, crashDate);
pstmt.setString(11, packageName);
pstmt.executeUpdate();
}catch(Exception e){
e.printStackTrace();
}finally{
if(pstmt!=null){
try {
pstmt.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
//e.printStackTrace();
}
}
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
//e.printStackTrace();
}
}
}
}
复制代码
实践结果:通过数据库可以导出一个excel的crash报表,或者直接通过浏览器查看
相关文章推荐
- 基于开源项目acra实现的定制化Android crash上报库及后台系统
- Android弹幕实现:基于B站弹幕开源系统(3)-文本弹幕的完善和细节调整
- Android弹幕实现:基于B站弹幕开源系统(5)-抽象和复用
- Android弹幕实现:基于B站弹幕开源系统(7)QQ、微信聊天气泡样式的弹幕
- Android弹幕实现:基于B站弹幕开源系统(7)QQ、微信聊天气泡样式的弹幕
- Android弹幕实现:基于B站弹幕开源系统(4)-重构
- Android弹幕实现:基于B站弹幕开源系统(7)QQ、微信聊天气泡样式的弹幕
- Android弹幕实现:基于B站弹幕开源系统(3)-文本弹幕的完善和细节调整
- Android弹幕实现:基于B站弹幕开源系统(5)-抽象和复用
- (开源项目)基于springboot的后台管理系统基本框架
- Android弹幕实现:基于B站弹幕开源系统(4)-重构
- 深入解析Android系统中应用程序前后台切换的实现要点
- SpringBoot入门项目-基于JPA的App日记后台系统之数据库的创建与JPA的CRUD(二)
- 【Android开源项目解析】仿支付宝付款成功及"天女散花"效果实现——看PathMeasure大展身手
- DoNet开源项目-基于Amaze UI的点餐系统
- 基于android系统实现的简单定位功能
- android远程控制(三)----通过后台服务实现系统点击事件模拟
- 基于.NET 2.0的GIS开源项目SharpMap分析手记(十四):ASP.NET2.0实现无刷新客户端回调的Callback机制及例子代码下载
- 基于Android系统的AES加密、解密的JAVA实现
- 基于Android系统的UPNP媒体播放器的实现步骤