从生产Android应用程序中删除日志记录的最佳方法是什么。似乎proguard没有完全做到这一点,字符串仍然写入,所以我想知道从生产代码中删除日志记录的最佳解决方案是什么?
答案 0 :(得分:24)
IMO最佳解决方案是在您调用日志记录方法的任何地方编写如下代码。
if (SOME_LOG_CONSTANT) Log.d(TAG, "event:" + someSlowToEvaluateMethod());
通过更改1常量,您将删除每个不需要的日志记录。这样,if (false)
后面的部分甚至不应该进入你的.class文件,因为编译器可以完全删除它(它是无法访问的代码)。
这也意味着如果将它们包装在if
中,则可以从发布软件中排除整个代码块。这甚至是一些无法做到的事情。
SOME_LOG_CONSTANT
可以是BuildConfig.DEBUG
。根据构建类型,该常量会自动更改。 Thx @Christopher
答案 1 :(得分:9)
使用Timber,它是一个很好的库来配置您的日志: https://github.com/JakeWharton/timber
使用示例:Timber.d("活动创建");
配置示例:
public class ExampleApp extends Application {
@Override public void onCreate() {
super.onCreate();
if (BuildConfig.DEBUG) {
Timber.plant(new DebugTree());
} else {
Timber.plant(new CrashReportingTree());
}
}
/** A tree which logs important information for crash reporting. */
private static class CrashReportingTree extends Timber.Tree {
@Override protected void log(int priority, String tag, String message, Throwable t) {
if (priority == Log.VERBOSE || priority == Log.DEBUG) {
return;
}
FakeCrashLibrary.log(priority, tag, message);
if (t != null) {
if (priority == Log.ERROR) {
FakeCrashLibrary.logError(t);
} else if (priority == Log.WARN) {
FakeCrashLibrary.logWarning(t);
}
}
}
}
答案 2 :(得分:6)
Configuring Your Application for Release告诉您在发布应用程序之前只需删除Log
命令。
您可以通过删除源文件中对Log方法的调用来停用日志记录。
我所做的是创建一个专有的静态日志方法,该方法读取类似这样的全局布尔值:
class MyLog {
private static final boolean LOGGING = true; //false to disable logging
public static void d(String tag, String message) {
if (LOGGING) {
Log.d(tag, message);
}
}
/* ... same for v, e, w, i */
}
在您想要记录的任何地方使用它。
MyLog.d("Tag", "This will only work with LOGGING true");
答案 3 :(得分:1)
我建议你看看Log extension class。
它使您可以对日志进行精细控制。 例如,您可以禁用所有日志(感谢配置文件)或仅禁用某些包或类的日志。
此外,它添加了一些有用的功能(例如,您不必为每个日志传递标记)。
答案 4 :(得分:0)
我建议您查看Roboguice - http://code.google.com/p/roboguice/ - 如果您使用内置的Ln功能,它将自动无法登录已签名的APK。它还简化了大量其他Android样板。你可以在使用基线 - https://github.com/achuinard/basedroid
的情况下看到它答案 5 :(得分:0)
答案 6 :(得分:0)
只需将此方法添加到您的代码中,然后使用Logd而不是Log.d
private static final String TAG = "your own tag to recognize log entries from this app";
public static void Logd(String txt) {
if (BuildConfig.DEBUG&&BuildConfig.BUILD_TYPE.equals("debug")) Log.d(TAG,txt);
}
我知道仍会对字符串进行评估,但我们正在谈论额外处理时间内的微秒。没有人会注意到应用程序速度的差异,除非您在循环中进行了数千次记录。
DEBUG和BUILD_TYPE可在Android Studio中使用。 DEBUG布尔值是build.gradle文件中的“debuggable”选项:
buildTypes {
debug {
debuggable true
runProguard false
proguardFile getDefaultProguardFile('proguard-android.txt')
}
release {
debuggable false
runProguard true
proguardFile getDefaultProguardFile('proguard-android.txt')
}
}
在Android Studio中运行时,BUILD_TYPE会自动设置为“debug”。
因此,如果您将debuggable设置为false或者用户具有发布版本,那么日志将会消失。
答案 7 :(得分:0)
最好的方法是根据我的经验来处理这个问题,
首先记录检查BuildConfig.DEBUG标志以打印日志。
Class LogUtils{
public static void log(Class clazz, String message) {
if (BuildConfig.DEBUG) {//log only in debug mode
Log.d(clazz.getSimpleName(), message);
}
}
}
然后启用minify到您的app模块gradle文件,这将使proguard优化您的二进制文件
android {
buildTypes {
release {
minifyEnabled true
//shrinkResources true
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
signingConfig signingConfigs.release
}
}
}
这会将调试日志保留在调试版本中。
但是在您的发布版本中,if (BuildConfig.DEBUG)
条件永远不会成立,因此proguard将从二进制文件中删除无法访问的日志代码。