使用maven构建android项目

更好的阅读效果,请查看原文地址:http://keepcleargas.bitbucket.org/android/2014/04/01/using-maven-to-package-android.html

为什么引入maven构建方式

做过java后台开发的人员应该都知道,maven使用解决依赖包管理问题的,同时优化测试,打包,部署等流程的.

在android里,

  • maven可以管理你的依赖包
  • 打包成apklib,管理自己的组件库
  • 动态配置你的发布渠道(此点非常方便)
  • 签名,打包,混淆一条龙服务.

开始使用maven

引入pom.xml


<project xmlns=“http://maven.apache.org/POM/4.0.0”

     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
     xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">

<modelVersion>4.0.0</modelVersion>
<groupId>com.test</groupId>
<artifactId>apkDeplorer</artifactId>
<version>1.0.0</version>
<packaging>apk</packaging>
<name>apkDeplorer</name>

<dependencies>
    <dependency>
        <groupId>com.google.android</groupId>
        <artifactId>android</artifactId>
        <version>4.1.1.4</version>
        <scope>provided</scope>
    </dependency>
    <dependency>
        <groupId>com.google.android</groupId>
        <artifactId>support-v4</artifactId>
        <version>r7</version>
    </dependency>
</dependencies>

<properties>
    <keystore.filename>apkDeplorer.keystore</keystore.filename>
    <keystore.storepass>kison.chen@zaozao</keystore.storepass>
    <keystore.keypass>kison.chen@zaozao</keystore.keypass>
    <keystore.alias>kison-android-app</keystore.alias>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>

<build>
    <finalName>${project.artifactId}-${project.version}-${manifest.metadata.id}</finalName>
    <sourceDirectory>src/main/java</sourceDirectory>
    <resources>
        <resource>
            <directory>.</directory>
            <filtering>true</filtering>
            <targetPath>../filtered-resources</targetPath>
            <includes>
                <include>AndroidManifest.xml</include>
            </includes>
        </resource>
        <resource>
            <directory>src/main/resources</directory>
            <filtering>true</filtering>
            <includes>
                <include>**/*</include>
            </includes>
            <excludes>
                <exclude>**/env-*.properties</exclude>
            </excludes>
        </resource>
    </resources>
    <pluginManagement>
        <plugins>
            <plugin>
                <groupId>com.jayway.maven.plugins.android.generation2</groupId>
                <artifactId>android-maven-plugin</artifactId>
                <version>3.6.0</version>
                <extensions>true</extensions>
                <executions>
                    <execution>
                        <id>run</id>
                        <goals>
                            <goal>deploy</goal>
                            <goal>run</goal>
                        </goals>
                        <phase>install</phase>
                    </execution>
                </executions>
                <configuration>
                    <proguardConfig>proguard-project.txt</proguardConfig>
                    <proguardSkip>${project.build.proguardSkip}</proguardSkip>
                    <manifestDebuggable>${manifest.debuggable}</manifestDebuggable>
                    <androidManifestFile>target/filtered-resources/AndroidManifest.xml
                    </androidManifestFile>
                    <release>${project.build.release}</release>
                    <run>
                        <debug>${project.build.debug}</debug>
                    </run>
                    <runDebug>${project.build.runDebug}</runDebug>
                    <sign>
                        <debug>${project.build.sign.debug}</debug>
                    </sign>
                    <undeployBeforeDeploy>true</undeployBeforeDeploy>
                </configuration>
            </plugin>
        </plugins>
    </pluginManagement>
    <plugins>
        <plugin>
            <groupId>com.jayway.maven.plugins.android.generation2</groupId>
            <artifactId>android-maven-plugin</artifactId>
            <version>3.8.0</version>
            <configuration>
                <sdk>
                    <platform>15</platform>
                </sdk>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>keytool-maven-plugin</artifactId>
            <version>1.2</version>
            <configuration>
                <keystore>${keystore.filename}</keystore>
                <storepass>${keystore.storepass}</storepass>
                <keypass>${keystore.keypass}</keypass>
                <alias>${keystore.alias}</alias>
                <dname>CN=iKoding, OU=iKoding, O=iKoding, C=CN</dname>
                <sigalg>SHA1withDSA</sigalg>
                <validity>10000</validity>
                <keyalg>DSA</keyalg>
                <keysize>1024</keysize>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-compiler-plugin</artifactId>
            <configuration>
                <source>1.6</source>
                <target>1.6</target>
                <encoding>UTF8</encoding>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-resources-plugin</artifactId>
            <version>2.6</version>
            <executions>
                <execution>
                    <phase>initialize</phase>
                    <goals>
                        <goal>resources</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

<profiles>
    <profile>
        <id>debug</id>
        <activation>
            <activeByDefault>true</activeByDefault>
        </activation>
        <build>
            <filters>
                <filter>src/main/resources/env-debug.properties</filter>
            </filters>
        </build>
        <properties>
            <project.build.debug>true</project.build.debug>
            <project.build.runDebug>false</project.build.runDebug>
            <project.build.proguardSkip>true</project.build.proguardSkip>
            <project.build.release>false</project.build.release>
            <project.build.sign.debug>true</project.build.sign.debug>
            <manifest.debuggable>true</manifest.debuggable>
        </properties>
    </profile>
    <profile>
        <id>release</id>
        <properties>
            <project.build.debug>false</project.build.debug>
            <project.build.runDebug>false</project.build.runDebug>
            <project.build.proguardSkip>false</project.build.proguardSkip>
            <project.build.release>true</project.build.release>
            <project.build.sign.debug>false</project.build.sign.debug>
            <manifest.debuggable>false</manifest.debuggable>
        </properties>
        <build>
            <filters>
                <filter>src/main/resources/env-release.properties</filter>
            </filters>
            <plugins>
                <plugin>
                    <groupId>org.apache.maven.plugins</groupId>
                    <artifactId>maven-jarsigner-plugin</artifactId>
                    <version>1.2</version>
                    <executions>
                        <execution>
                            <id>sign</id>
                            <goals>
                                <goal>sign</goal>
                            </goals>
                            <phase>package</phase>
                            <inherited>true</inherited>
                            <configuration>
                                <includes>
                                    <include>${project.build.outputDirectory}/*.apk</include>
                                </includes>
                                <keystore>${keystore.filename}</keystore>
                                <storepass>${keystore.storepass}</storepass>
                                <keypass>${keystore.keypass}</keypass>
                                <alias>${keystore.alias}</alias>
                            </configuration>
                        </execution>
                    </executions>
                </plugin>
            </plugins>
        </build>
    </profile>
    <!-- 渠道profiles -->
    <profile>
        <id>channel-test</id>
        <activation>
            <activeByDefault>true</activeByDefault>
        </activation>
        <properties>
            <manifest.metadata.id>test</manifest.metadata.id>
            <manifest.metadata.channel>test</manifest.metadata.channel>
        </properties>
    </profile>
    <profile>
        <id>channel-91</id>
        <properties>
            <manifest.metadata.id>91-market</manifest.metadata.id>
            <manifest.metadata.channel>91 market</manifest.metadata.channel>
        </properties>
    </profile>
    <profile>
        <id>channel-yingyonghui</id>
        <properties>
            <manifest.metadata.id>yingyonghui-market</manifest.metadata.id>
            <manifest.metadata.channel>yingyonghui market</manifest.metadata.channel>
        </properties>
    </profile>
    <profile>
        <id>channel-tongbutui</id>
        <properties>
            <manifest.metadata.id>tongbutui-market</manifest.metadata.id>
            <manifest.metadata.channel>tongbutui market</manifest.metadata.channel>
        </properties>
    </profile>
    <profile>
        <id>channel-tengxun</id>
        <properties>
            <manifest.metadata.id>tengxun-market</manifest.metadata.id>
            <manifest.metadata.channel>tengxun market</manifest.metadata.channel>
        </properties>
    </profile>
    <profile>
        <id>channel-anzhi</id>
        <properties>
            <manifest.metadata.id>anzhi-market</manifest.metadata.id>
            <manifest.metadata.channel>anzhi market</manifest.metadata.channel>
        </properties>
    </profile>
    <profile>
        <id>channel-gfan</id>
        <properties>
            <manifest.metadata.id>gfan</manifest.metadata.id>
            <manifest.metadata.channel>gfan</manifest.metadata.channel>
        </properties>
    </profile>
</profiles>


安装本地依赖包

由于国内的第三方库多未以maven形式打包,故我们要手动将jar包安装到本地maven库.(高德地图为例)
{% highlight xml %}
mvn install:install-file -DgroupId=com.autonavi -DartifactId=libamapv3 -Dversion=v3 -Dfile=/Users/keepcleargas/Downloads/AMapSDKV2Demo/libs/armeabi/libamapv3.so -Dpackaging=so -DgeneratePom=true -Dclassifier=armeabi

mvn install:install-file -DgroupId=com.autonavi -DartifactId=location -Dversion=2.0.0 -Dfile=/Users/keepcleargas/Downloads/AMapSDKV2Demo/libs/MapApiLocation.jar -Dpackaging=jar -DgeneratePom=true

{% endhighlight %}
添加依赖包到pom.xml
{% highlight xml %}

      <groupId>com.autonavi</groupId>
       <artifactId>libamapv3</artifactId>
       <version>v3</version>
       <classifier>armeabi</classifier>
        <scope>runtime</scope>
        <type>so</type>


          <groupId>com.autonavi</groupId>
          <artifactId>map</artifactId>
          <version>2.0.0</version>


           <groupId>com.autonavi</groupId>
           <artifactId>ApiLocation</artifactId>
           <version>2.0.0</version>


           <groupId>com.autonavi</groupId>
           <artifactId>ApiSearch</artifactId>
            <version>2.0.0</version>


{% endhighlight %}

android的maven版本构建

由于在maven central中 android版本只有4.1.1.4

我们需要一个工具来安装新版的android sdk. Maven Android SDK Deployer.

根据Maven Android SDK Deployer的wiki 文案,mvn install -P 4.4 在pom.xml导入 4.4.2的安卓包.

{% highlight xml %}

    <dependency>
        <groupId>android</groupId>
        <artifactId>android</artifactId>
        <version>4.4.2_r3</version>
        <scope>provided</scope>
    </dependency>

{% endhighlight %}

构建中可能出现的问题

  • maven版本问题
    使用过程中可能会出现版本问题,笔者这里用的是maven 3.1.1,com.jayway.maven.plugins.android.generation2:android-maven-plugin:3.8.2
  • .9图片问题
    {% highlight xml %}
    ERROR: 9-patch image Project/res/drawable- hdpi/input_03_mid.9.png malformed.
    [INFO] Must have one-pixel frame that is either transparent or white.
    [INFO] ERROR: Failure processing PNG image Project/res/drawable-hdpi/input_03_mid.9.png
    {% endhighlight %}

将.9图片标准化 即可

命令执行

{% highlight xml %}
mvn clean package

打包,但不部署。
mvn clean install

打包,部署并运行。
mvn clean package android:redeploy android:run

这个命令通常用于手机上已经安装了要部署的应用,但签名不同,所以我们打包的同时使用redeploy命令将现有应用删除并重新部署,最后使用run命令运行应用。
mvn android:redeploy android:run

不打包,将已生成的包重新部署并运行。
mvn android:deploy android:run

部署并运行已生成的包,与redeploy不同的是,deploy不会删除已有部署和应用数据。

mvn clean install -Prelease,channel-91

打包签名,的渠道为channel-91的apk
{% endhighlight %}

参考文献

  • 使用Maven构建Android项目
  • MAVEN Invalid SDK: Platform/API level 16 not available
  • .9图片问题
  • maven中使用高德地图
  • Maven Android SDK Deployer
  • maven-android-plugin
  • apkDeplorer-maven打包android的demo

你可能感兴趣的:(maven,android)