Android Studio 的 build 过程

如图,
编译器将源代码(包括 Application Module 及其所依赖的所有 Library 源代码)转换成DEX(Dalvik Executable)文件(其中包括运行在 Android 设备上的字节码),将所有其他内容转换成已编译资源。(- 将源代码(包括 Application Module 和 Library Module)编译成 class 文件,再将所有的 class 文件(包括第三方库中)打包生成 dex 文件。
- 解压所有 aar 包中的资源文件,并和项目中所有资源文件合并到一个目录。
- 生成资源文件的索引文件。
)
APK 打包器将 DEX 文件和已编译资源打包生成单个 APK。不过,必须先对 APK 签名,才能将应用安装并部署到 Android 设备上。APK 打包器使用 Debug 或 Release 密钥库对 APK 签名:- 如果您构建的是 Debug 版本的应用(即专用于测试和分析的应用),
打包器会使用 Debug 密钥库签名应用。Android Studio 自动使用 Debug 密钥库配置新项目。 - 如果您构建的是打算向外发布的 Release 版本应用,
打包器会使用 Release 密钥库签名应用。
- 如果您构建的是 Debug 版本的应用(即专用于测试和分析的应用),
- 在生成最终 APK 之前,打包器会使用 zipalign 工具对应用进行优化,减少其在设备上运行时的内存占用。
2. Gradle 构建 tasks 说明
注:这里是用 Debug 模式做例子,Release 模式时只需将 task 中的 Debug 替换成 Release 理解即可)Executing tasks: [:app:assembleDebug] :app:preBuild UP-TO-DATE
:app:preDebugBuild UP-TO-DATE
:app:compileDebugAidl UP-TO-DATE
:app:compileDebugRenderscript UP-TO-DATE
:app:generateDebugResValues UP-TO-DATE
:app:generateDebugResources UP-TO-DATE
:app:mergeDebugResources UP-TO-DATE
:app:transformDataBindingBaseClassLogWithDataBindingMergeGenClassesForDebug UP-TO-DATE
:app:dataBindingGenBaseClassesDebug UP-TO-DATE
:app:checkDebugManifest UP-TO-DATE
:app:generateDebugBuildConfig UP-TO-DATE
:app:prepareLintJar UP-TO-DATE
:app:mainApkListPersistenceDebug UP-TO-DATE
:app:createDebugCompatibleScreenManifests UP-TO-DATE
:app:processDebugManifest
:app:splitsDiscoveryTaskDebug UP-TO-DATE
:app:processDebugResources
:app:generateDebugSources
:app:dataBindingExportBuildInfoDebug
:app:javaPreCompileDebug UP-TO-DATE
:app:transformDataBindingWithDataBindingMergeArtifactsForDebug UP-TO-DATE
:app:compileDebugJavaWithJavac
:app:compileDebugNdk NO-SOURCE
:app:compileDebugSources
:app:mergeDebugShaders UP-TO-DATE
:app:compileDebugShaders UP-TO-DATE
:app:generateDebugAssets UP-TO-DATE
:app:mergeDebugAssets UP-TO-DATE
:app:transformClassesWithDexBuilderForDebug
:app:transformDexArchiveWithExternalLibsDexMergerForDebug
:app:transformDexArchiveWithDexMergerForDebug
:app:mergeDebugJniLibFolders UP-TO-DATE
:app:transformNativeLibsWithMergeJniLibsForDebug UP-TO-DATE
:app:processDebugJavaRes NO-SOURCE
:app:transformResourcesWithMergeJavaResForDebug UP-TO-DATE
:app:validateSigningDebug UP-TO-DATE
:app:packageDebug
:app:assembleDebug BUILD SUCCESSFUL in 20s
特别说明:由于 Gradle 会尝试通过不重复执行输入未发生变化的 task 来节省时间(这些 task 被标记为 UP-TO-DATE,如上所示)
所以第一次编译运行会比较久,而后面就不会了。
上面列出来的 Gradle 构建过程,大致可分为五个阶段:
Preparation of dependecies在这个阶段 Gradle 检测 Module 依赖的所有 library 是否 ready。如果这个 Module 依赖于另一个 Module ,则另一个 Module 也要被编译。Merging resources and processing Manifest打包资源和 Manifest 文件。Compiling在这个阶段处理编译器的注解,源码被编译成字节码。Postprocessing所有带 transform 前缀的 task 都是这个阶段进行处理的。Packaging and publishing这个阶段 library 生成.aar文件,Application 生成.apk文件。
这五个阶段和上面的构建过程中 task 的时序有大致的对应关系,大家可以相互映照着理解。
为了便于大家理解,下面给出一些关键 task 的说明:
mergeDebugResources解压所有的 aar 包输出到app/build/intermediates/exploded-aar,并且把所有的资源文件合并到app/build/intermediates/res/merged/debug目录里。processDebugManifest把所有 aar 包里的AndroidManifest.xml中的节点,合并到项目的AndroidManifest.xml中,并根据app/build.gradle中当前buildType 的 manifestPlaceholders配置内容替换 manifest 文件中的占位符,最后输出到app/build/intermediates/manifests/full/debug/AndroidManifest.xml。processDebugResources- 调用 aapt 生成项目和所有 aar 依赖的
R.java,输出到app/build/generated/source/r/debug目录; - 生成资源索引文件
app/build/intermediates/res/debug/resources-debug.ap_; - 把符号表输出到
app/build/intermediates/symbols/debug/R.txt。
- 调用 aapt 生成项目和所有 aar 依赖的
compileDebugJavaWithJavac用来把 java 文件编译成 class 文件,输出的路径是app/build/intermediates/classes/debug编译的输入目录有
- 项目源码目录,默认路径是
app/src/main/java,可以通过 sourceSets 的 dsl 配置,允许有多个(打印project.android.sourceSets.main.java.srcDirs可以查看当前所有的源码路径,具体配置可以参考 android-doc,以及这里。 app/build/generated/source/aidl。app/build/generated/source/buildConfig。app/build/generated/source/apt(继承javax.annotation.processing.AbstractProcessor做动态代码生成的一些库,输出在这个目录)的代码。
- 项目源码目录,默认路径是
transformClassesWithMultidexlistForDebug(这个任务在使用 Multidex 才会出现)它有两个作用- 扫描项目的
AndroidManifest.xml文件和分析类之间的依赖关系,计算出那些类必须放在第一个 dex 里面,最后把分析的结果写到app/build/intermediates/multi-dex/debug/maindexlist.txt文件里面 - 生成混淆配置项输出到
app/build/intermediates/multi-dex/debug/manifest_keep.txt文件里
项目里的代码入口是 manifest 中 application 节点的属性 android.name 配置的继承自 Application 的类,在 Android 5.0 以前的版本系统只会加载一个 dex(classes.dex),classes2.dex .......classesN.dex 一般是使用
android.support.multidex.MultiDex加载的,所以如果入口的 Application 类不在 classes.dex 里 5.0 以下肯定会挂掉,另外当入口 Application 依赖的类不在 classes.dex 时初始化的时候也会因为类找不到而挂掉,还有如果混淆的时候类名变掉了也会因为对应不了而挂掉,综上所述就是这个任务的作用。- 扫描项目的
Android Studio 的 build 过程的更多相关文章
- 使用Android Studio调试UiAutomator过程中遇到的问题
声明: 这里纪录了个人学习和使用Android Studio调试UiAutomator过程中遇到遇到的问题,不定时进行更新,欢迎一起交流学习 1.Excution faild for task ‘:a ...
- Android studio在使用过程中的问题总汇!
使用android studio也有一段时间了,汇总了一下这段时间内遇到一些常见问题,希望能够帮助到大家! 一.字体大小问题 在android studio的使用过程中没有发现类似于Eclipse中的 ...
- 解决Android Studio Gradle Build Running慢的问题
Android Studio方便好用,但是Android Studio Gradle Build Running很慢 解决方法: C:\Users\你的用户名\.gradle 目录下新建一个文件名为 ...
- 解决Android Studio Gradle Build特别慢的问题
解决Android Studio Gradle Build 特别慢的问题 C:\Users\你的用户名\.gradle目录下新建一个文件名为gradle.properties的文件.内容为:org.g ...
- Android Studio Gradle Build Running 特别慢的问题探讨
本文的本本win7 64bit 6G android studio2.1 在运行程序的时候Gradle Build Running 特别慢,一个helloworld都快2min了 1.开启gradle ...
- 如何用Android Studio查看build.gradle源码
上一篇博客里讲过 build.gradle 里的每一行代码基本都是在调用一个方法,既然是这样,我们就可以用 android studio(下面简称as) 去查看它源码的方法注释说明,这样就可以理解每个 ...
- 第一次用上 Android Studio 2.3 过程及错误解决
因为要开发Android5.0的缘故,抛弃了eclipse转到了Android Studio,第一次使用就是遇到了许多问题,终于是解决问题了,特意写一篇博文给各位要准备从eclipse转到Androi ...
- Android Studio 出现 Build gradle project info
导入Android Studio,一直停留在Build gradle project info.主要是因为google被墙,下载gradle很慢,有时候设置下载不成功. 参考链接 http://blo ...
- 提高Android Studio的Build速度实践
1.在下面的目录创建gradle.properties文件 /home/<username>/.gradle/ (Linux) /Users/<username>/.gradl ...
随机推荐
- google chrome 浏览器去掉 XHR finished loading....
每次Ajax请求,Chrome浏览器控制台提示如图XHR finished loading信息. 要去掉 这些信息显示 ,点击上图的Settings ,在打开的面板中取消 Log XMLHttpReq ...
- Python-Thread(通俗易懂)
此类表示在单独的控制线程中运行的活动,有两种方法可以指定该活动,一是将可调用对象传递给构造函数,二是通过覆盖子类中的run()方法. 如果你对线程不太理解,我们可以打个比方,把线程数看作车辆数,我们来 ...
- [java,2018-06-26] 扑克牌抽牌求和问题
问题: 一副扑克牌,除去大小王后共52张牌,随机从中抽八张牌,问八张牌的和最有可能是多少? 分析: 这52张牌,其实就是数字 1 2 3 ...13, 每个数字出现4次.随机抽出8个数,问组成的和最有 ...
- ef err
InvalidCastException: The field of type jcz.DomainModels.Sex must be a string, array or ICollection ...
- verilog 介绍
Verilog HDL Verilog HDL是在C语言的基础上发展起来的一种硬件描述语言,语法较自由.VHDL和Verilog HDL两者相比,VHDL的书写规则比Verilog HDL烦琐一些,但 ...
- 什么是RESTful API?
要弄清楚什么是RESTful API,首先要弄清楚什么是REST.REST -- REpresentational State Transfer,英语的直译就是"表现层状态转移". ...
- win10 .net3.5的问题及解决方案
近日有网友反映在windows10_64位系统电脑上安装Net framework3.5,操作时总失败,怎么办呢?小编下面就介绍win10 64位系统无法安装Net framework3.5的两种解决 ...
- CentOS7虚拟机配置ip地址
首先安装后的虚拟机选NAT模式配置vm的虚拟网络编辑器(vmware中的编辑),NAT模式中查看DHCP的范围,配置子网(写成和电脑一样),在linux中进入/etc/sysconfig/networ ...
- Linux网络编程学习(八) ----- 文件和记录锁定(第四章)
1.什么是文件和记录锁定? 文件锁定的是整个文件,而记录锁定只锁定文件的一部分,文件和记录锁分为咨询式锁定和强制锁定 1)咨询式锁定 某个进程对某个文件进行了咨询式锁定,其他想访问该文件的进程将会被操 ...
- Android:得到WebView当前页的html源码
WebView没有提供直接的API,需要用JavaScript变通处理一下.本文试图总结一个最简单.优雅的代码. 有两步: 1.先创建一个JavaScript接口类: class MyJavaScri ...