通过 ant 解决 android 版本的问题

前提,本文的要求是你要懂一些 ant


在 Android 的sdk 中有一个已经写好的 build.sh, 通常情况下在各个 apk 中都是创建一个 build.xml,在里面会引用或者重载这个 build.xml 中的部分字段,而不是自己完全开始重头写一个新的。sdk 这个 build.xml 位置 “android-sdk-windows\tools\ant\build.xml”


如果你自己的工程目录中没有 build.xml ,那么可以通过命令

android update project -p .
来产生一个,如果不能创建,说没有指定什么 target 那么需要在创建一个 project.properties,然后在里面指定 target,例如:

target=android-14

执行成功后通常会创建出来两个文件:local.properties,build.xml


好了,下面开始解决实际问题:


问题一: 如何给 Apk 加上版本号,例如:abc_1.1.apk 这样的形式

在自己的 app 的工程中增加一个新的文件 "custom_rules.xml" 为什么是这个文件呢? 因为在你 build.xml 中有如下文字

<import file="custom_rules.xml" optional="true" />
来指定可以导入的第三方文件,名字叫做 custom_rules.xml,好了,这个 xml 的内容如下

<?xml version="1.0" encoding="UTF-8"?>
<project>
    <target name="rename-release-with-version-number">
        <xmlproperty file="AndroidManifest.xml" prefix="themanifest" collapseAttributes="true" />
        <property name="out.final.file" location="${out.absolute.dir}/${ant.project.name}-${themanifest.manifest.android:versionName}.apk" />
    </target>

    <target name="-set-release-mode" depends="rename-release-with-version-number,android_rules.-set-release-mode">
        <echo message="target: ${build.target}"></echo>
    </target>
</project>
简单来说就是,

1. 写一个 target 解析 AndroidManifest.xml 得到 version name 和 version code 这两个属性,然后重载 "out.final.file" 字段将其设为这新的名字

2. 然后将这个 target 放到 "-set-release-mode" 的 depends 中这样保证调用 "-set-release-mode" 的时候就会调用这个写好的 target

说明:

"-set-release-mode" 这的实在 sdk 的 build.xml 中有定义的,每次使用 ant release 的时候都会执行这个字段

“out.final.file”在 sdk 的 build.xml 中的定义如下

<property name="out.final.file" location="${out.absolute.dir}/${ant.project.name}-release.apk" />
我们就是要重载它。

“android_rules.-set-release-mode” 这个指的就是要执行 sdk build.xml中原本  "-set-release-mode" 所定义的 depends


另外在 sdk 的 build.xml 中本来就定义好了两个 property 叫做,

<property name="version.code" value="" />
<property name="version.name" value="" />

但是不知道为什么,这两个 property 一直是空值,用不起来。


好了,将这个 custom_rules.xml 放到你的工作中,然后在 AndroidManifest.xml 中设置好 version code 和 version name,然后执行 ant clean 就可以在 bin 目录下看到新的 apk,并且是 abc-1.0.1.apk 这样的形式。


问题二:如何在 jar 的 build 过程中将版本信息从 AndroidManifest.xml 中保存到 MANIFEST.MF 中

需求,将代码打包成一个 jar 包,但是通常 jar 包中不会将 AndroidManifest.xml 打包进去,并且通常 jar 的版本都放到 MANIFEST.MF 中,并且也有专门的代码去解析它。

解决方法:

创建 custom_rules.xml,内容如下

<?xml version="1.0" encoding="UTF-8"?>
<project>
    <!-- Override the default compile process -->
    <target name="-compile" depends="android_rules.-compile">
        <!-- Parse AndroidManifest.xml since ${version.code} and ${version.name} is empty -->
        <xmlproperty file="AndroidManifest.xml" prefix="themanifest" collapseAttributes="true" />

        <jar destfile="${out.library.jar.file}">
            <!-- Override manifest.mf add code version -->
            <manifest>
                <section name="custom_section">
                    <attribute name="verion_name" value="${themanifest.manifest.android:versionName}" />
                    <attribute name="verion_code" value="${themanifest.manifest.android:versionCode}" />
                </section>
            </manifest>

            <!-- Copy code from android sdk build.xml to create jar -->
            <fileset dir="${out.classes.absolute.dir}"
                     includes="**/*.class"
                     excludes="${manifest.package.path}/R.class ${manifest.package.path}/R$*.class ${manifest.package.path}/Manifest.class ${manifest.package.path}/Manifest$*.class ${manifest.package.path}/BuildConfig.class"/>
            <fileset dir="${source.absolute.dir}" excludes="**/*.java ${android.package.excludes}" />
        </jar>
    </target>
</project>
重载 “compile” target,在生成 jar 的地方完全用这块代码来替换


<manifest> 的那块代码就是要放到 MF文件中的内容,<section name="custom_section"> 这个表示是在 MF 文件中创建一个自己的 section,这个可有可无,下面的

<fileset dir="${out.classes.absolute.dir}" 直接从 sdk build.xml 中拷贝过来没有改变。


好了,执行完 ant 命令之后再 MANIFEST.MF 中就可以看到来自 AndroidManifest.xml 中的版本信息了。



你可能感兴趣的:(ant)