【发布时间】:2012-12-12 05:16:31
【问题描述】:
我使用一个 Android 库项目编写了一个 Android 应用程序,该项目也是我编写的。我必须发布应用程序的源代码,但我不想分发库的源代码。该库除其他外还定义了自定义视图,因此它包括 XML 布局和资源。我正在考虑以二进制形式(可能是.jar?)发布这个库,以供主项目引用。我希望通过 Proguard 混淆这个二进制库。这可行吗?怎么样?
谢谢。
【问题讨论】:
我使用一个 Android 库项目编写了一个 Android 应用程序,该项目也是我编写的。我必须发布应用程序的源代码,但我不想分发库的源代码。该库除其他外还定义了自定义视图,因此它包括 XML 布局和资源。我正在考虑以二进制形式(可能是.jar?)发布这个库,以供主项目引用。我希望通过 Proguard 混淆这个二进制库。这可行吗?怎么样?
谢谢。
【问题讨论】:
正如 Morrison Chang 所说,目前没有任何方法可以将 android 库项目作为 jar 发布,也没有任何方法可以对项目进行混淆,除了 java 源代码。但是,有一种方法可以混淆源代码,尽管这不受官方支持。
您需要做的就是在您的库中运行“ant clean release”命令。混淆的源代码被写入“bin/proguard/obfuscated.jar”。只需将该 jar 文件放在导出的库项目的 libs 目录中,然后删除 src 目录的内容,就大功告成了。
但是,上述方法存在一个问题。它不能完全正确地处理资源。要解决此问题,您应该从 obfuscated.jar 副本中删除所有资源类(R.class 和 R$*.class)。这反过来将要求您禁用这些资源类的混淆。这可以通过将以下内容添加到 proguard-project.txt 来完成:
-keep public class **.R {
public *;
}
-keep public class **.R$* {
public *;
}
供您参考,这是我用来构建一个混淆的、无源的 android 库项目的 ant 目标:
<?xml version="1.0" encoding="UTF-8"?>
<project name="library_rules" default="librelease">
<target name="librelease" depends="release"
description="Build a sourceless and obfuscated android library.">
<property name="libname" value="myProject" />
<property name="librelease.dir" location="bin/${libname}" />
<delete file="${librelease.dir}"/>
<mkdir dir="${librelease.dir}"/>
<mkdir dir="${librelease.dir}/libs"/>
<mkdir dir="${librelease.dir}/src"/>
<copy todir="${librelease.dir}/res">
<fileset dir="res"/>
</copy>
<copy file="AndroidManifest.xml" todir="${librelease.dir}" />
<copy file="ant.properties" todir="${librelease.dir}" />
<copy file="build.xml" todir="${librelease.dir}" />
<copy file="project.properties" tofile="${librelease.dir}/project.properties" />
<jar destfile="${librelease.dir}/libs/${libname}.jar">
<zipfileset src="bin/proguard/obfuscated.jar" excludes="**/R.class,**/R$$*.class"/>
</jar>
</target>
</project>
要导出的android库项目将位于bin/myProject。这已使用 Android SDK 工具 v20.0.3 和 v21 进行了测试。
【讨论】:
我不认为你能得到你想要的。 Android 库项目是一个完整的 Android 项目,包含您提到的所有资源。如果您想混淆纯代码,以便只有您的 API 可见,那么您可以通过 Proguard 创建一个。然而,由于 Proguard 只能处理 Java 文件,它不知道需要 Android SDK 工具链打包到 APK 中的 Android xml 和资源。因此,简而言之,如果只是外部 jar 中的 Java 代码(可能会调用 Android API),您可以对其进行 Proguard。如果您正在考虑其他 Android 资源文件,那么我不相信。
【讨论】: