我有一个使用大量Log.d()
或Log.e()
调用调试的应用程序。现在我想创建我的最终发布包。Eclipse 的 Android 导出功能提到要删除"Debuggable"
清单中的标志,我已经这样做了。我是否还应该评论所有Log
调用以提高我的应用程序的性能,或者这些调用在不可调试的最终版本包中什么都不做?
4 回答
我将 Log 类子类化为一个名为 Trace 的类,它反映了 Log 上的方法。所以我执行 Trace.d(TAG,"blah") 然后在 Trace.d 方法中,代码仅基于名为 LOGGING_LEVEL 的静态最终类变量执行,该变量具有 1-5 级(无,仅错误,错误和警告,错误和警告和信息,以及包括调试在内的所有内容)。在生成生产 APK 时,Proguard 会删除应用程序中未使用的所有代码,因此它会为我执行此操作。
对我来说,日志记录太重要了,不能从源头中删除,但出于性能、安全和知识产权的原因,它必须从生产应用程序中删除。
这种结构允许我向应用程序添加更多的日志记录,这使得调试问题变得更加容易,但对生产 APK 没有任何影响
public class Trace
{
public static final int NONE = 0;
public static final int ERRORS_ONLY = 1;
public static final int ERRORS_WARNINGS = 2;
public static final int ERRORS_WARNINGS_INFO = 3;
public static final int ERRORS_WARNINGS_INFO_DEBUG = 4;
private static final int LOGGING_LEVEL = ERRORS_ONLY; // Errors + warnings + info + debug (default)
public static void e(String tag, String msg)
{
if ( LOGGING_LEVEL >=1) Log.e(tag,msg);
}
public static void e(String tag, String msg, Exception e)
{
if ( LOGGING_LEVEL >=1) Log.e(tag,msg,e);
}
public static void w(String tag, String msg)
{
if ( LOGGING_LEVEL >=2) Log.w(tag, msg);
}
public static void i(String tag, String msg)
{
if ( LOGGING_LEVEL >=3) Log.i(tag,msg);
}
public static void d(String tag, String msg)
{
if ( LOGGING_LEVEL >=4) Log.d(tag, msg);
}
}
这让我检查了我的假设,即log.d
如果没有在清单中设置可调试标志,代码中的行不会以某种方式出现在已签名的发布 apk 上,我错了,它们仍然出现。
对 SO 的快速搜索使我得到了这个问题的公认答案: 在发布之前删除所有调试日志记录调用:是否有工具可以做到这一点?
它工作得很好,您不必更改任何代码。
来自 developer.android.com:
关闭日志记录和调试并清理数据/文件 对于发布,您应该确保关闭调试工具并从您的应用程序项目中删除调试和其他不必要的数据/文件。
从清单的元素中删除 android:debuggable="true" 属性。从应用程序项目中删除日志文件、备份文件和其他不必要的文件。检查私人或专有数据并在必要时将其删除。在源代码中停用对 Log 方法的任何调用。
我将删除日志记录代码,如下所示:
-assumenosideeffects class android.util.Log {
public static boolean isLoggable(java.lang.String, int);
public static int v(...);
public static int i(...);
public static int w(...);
public static int d(...);
public static int e(...);
public static java.lang.String getStackTraceString(java.lang.Throwable);
}
-assumenosideeffects class java.lang.Exception {
public void printStackTrace();
}
-assumenosideeffects class * implements org.slf4j.Logger {
public void trace(...);
public void debug(...);
public void info(...);
public void warn(...);
public void error(...);
public boolean isTraceEnabled(...);
public boolean isDebugEnabled(...);
public boolean isInfoEnabled(...);
public boolean isWarnEnabled(...);
public boolean isErrorEnabled(...);
}
如果需要,可以保留错误和警告类别。但请确保只有在代码删除有效时才为构建启用优化和收缩