Android SDK 構建工具介紹
前面的小節(jié)我們學習了 Android SDK 工具。本小節(jié)我們學習 Android SDK 構建工具。
1. 概述
Android SDK 構建工具位于以下位置:android_sdk/build-tools/version/
Android SDK 構建工具用于構建 Android 應用。這里的工具大多數(shù)都是由編譯工具調用的,而不是供我們使用的。不過,以下命令行工具可能很有用:
-
aapt2
解析 Android 資源,為其編制索引,然后將其編譯為針對 Android 平臺優(yōu)化的二進制格式,最后將編譯后的資源打包到單個輸出中。 -
apksigner
為 APK 簽名,并檢查簽名能否在給定 APK 支持的所有平臺版本上成功通過驗證。 -
zipalign
確保所有未壓縮數(shù)據(jù)的開頭均相對于文件開頭部分執(zhí)行特定的對齊,從而優(yōu)化 APK 文件。
2. aapt2
AAPT2(Android 資源打包工具)是一個構建工具,Android Studio 和 Android Gradle 插件使用它來編譯和打包應用的資源。AAPT2 會解析資源、為資源編制索引,并將資源編譯為針對 Android 平臺進行過優(yōu)化的二進制格式。
AAPT2 支持通過啟用增量編譯實現(xiàn)更快的資源編譯。這是通過將資源處理拆分為兩個步驟來實現(xiàn)的:
-
編譯:將資源文件編譯為二進制格式。
-
鏈接:合并所有已編譯的文件并將它們打包到一個軟件包中
2.1 編譯
- 編譯語法
aapt2 compile path-to-input-files [options] -o output-directory/
在以下示例中,AAPT2 分別編譯了名為 strings.xml 和 myImage.png 的資源文件:
aapt2 compile project_root/module_root/src/main/res/values-en/
strings.xml -o compiled/
aapt2 compile project_root/module_root/src/main/res/drawable
/myImage.png -o compiled/
如上表中所示,輸出文件的名稱取決于輸入文件的名稱及其父目錄(資源類型和配置)的名稱。對于以 strings.xml 作為輸入的上述示例,aapt2 會自動將輸出文件命名為 values-en_strings.arsc.flat。另一方面,存儲在 drawable 目錄中的已編譯可繪制對象文件的文件名將為 drawable_img.png.flat。
- 編譯選項
命令選項 | 說明 |
---|---|
-o | 指定已編譯資源的輸出路徑。 |
–dir | 指定要在其中搜索資源的目錄。 |
–pseudo-localize | 生成默認字符串的偽本地化版本,如 en-XA 和 en-XB。 |
–no-crunch | 停用 PNG 處理。 |
–legacy | 將使用早期版本的 AAPT 時允許的錯誤視為警告。 |
-v | 啟用詳細日志記錄。 |
2.2 鏈接
- 鏈接語法
aapt2 link path-to-input-files [options] -o
outputdirectory/outputfilename.apk --manifest AndroidManifest.xml
在以下示例中,AAPT2 將兩個中間文件(drawable_Image.flat 和 values_values.arsc.flat)與 AndroidManifest.xml 文件進行了合并。AAPT2 會根據(jù) android.jar 文件鏈接結果,該文件中包含了 android 軟件包中定義的資源:
aapt2 link -o output.apk
-I android_sdk/platforms/android_version/android.jar
compiled/res/values_values.arsc.flat
compiled/res/drawable_Image.flat --manifest /path/to/AndroidManifest.xml -v
- 鏈接選項
命令選項 | 說明 |
---|---|
-o | 指定鏈接的資源 APK 的輸出路徑。 |
–manifest | 指定要構建的 Android 清單文件的路徑。 |
-I | 提供平臺的 android.jar 或其他 APK(如 framework-res.apk)的路徑。 |
-A | 指定要包含在 APK 中的資產(chǎn)目錄。 |
-R | 傳遞要鏈接的單個 .flat 文件,使用 overlay 語義。 |
–package-id | 指定要用于應用的軟件包 ID。 |
–allow-reserved-package-id | 允許使用保留的軟件包 ID。 |
–java | 指定要在其中生成 R.java 的目錄。 |
–proguard | 為 ProGuard 規(guī)則生成輸出文件。 |
–proguard-conditional-keep-rules | 為主 dex 的 ProGuard 規(guī)則生成輸出文件。 |
–no-auto-version | 停用自動樣式和布局 SDK 版本控制。 |
–no-version-vectors | 停用矢量可繪制對象的自動版本控制。 |
–no-version-transitions | 停用轉換資源的自動版本控制。 |
–no-resource-deduping | 禁止在兼容配置中自動刪除具有相同值的重復資源。 |
–enable-sparse-encoding | 允許使用二進制搜索樹對稀疏條目進行編碼。 |
-z | 要求對標記為“建議”的字符串進行本地化。 |
-c | 提供以英文逗號分隔的配置列表。 |
–preferred-density | 允許 AAPT2 選擇最相符的密度并刪除其他所有密度。 |
–output-to-dir | 將 APK 內容輸出到 -o 指定的目錄中。 |
–min-sdk-version | 設置要用于 AndroidManifest.xml 的默認最低 SDK 版本。 |
–target-sdk-version | 設置要用于 AndroidManifest.xml 的默認目標 SDK 版本。 |
–version-code | 指定沒有版本代碼時要注入 AndroidManifest.xml 中的版本代碼。 |
–compile-sdk-version-name | 指定沒有版本名稱時要注入 AndroidManifest.xml 中的版本名稱。 |
–proto-format | 以 Protobuf 格式生成已編譯的資源。 |
–non-final-ids | 使用非最終資源 ID 生成 R.java。 |
–emit-ids | 在給定的路徑上生成一個文件,該文件包含資源類型的名稱及其 ID 映射的列表。 |
–stable-ids | 使用通過 --emit-ids 生成的文件,該文件包含資源類型的名稱以及為其分配的 ID 的列表。 |
–custom-package | 指定要在其下生成 R.java 的自定義 Java 軟件包。 |
–extra-packages | 生成相同的 R.java 文件,但軟件包名稱不同。 |
–add-javadoc-annotation | 向已生成的所有 Java 類添加 JavaDoc 注釋。 |
–output-text-symbols | 生成包含指定文件中 R 類的資源符號的文本文件。 |
–auto-add-overlay | 允許在疊加層中添加新資源。 |
–rename-manifest-package | 重命名 AndroidManifest.xml 中的軟件包。 |
–rename-instrumentation-target-package | 更改插樁的目標軟件包的名稱。 |
-0 | 指定不想壓縮的文件的擴展名。 |
–split | 根據(jù)一組配置拆分資源,以生成另一個版本的 APK。 |
-v | 可提高輸出的詳細程度。 |
3. apksigner
3.1 語法
- 為 APK 簽名
apksigner sign --ks keystore.jks |
--key key.pk8 --cert cert.x509.pem
[signer_options] app-name.apk
在使用 apksigner 工具為 APK 簽名時,必須提供簽名者的私鑰和證書。我們可以通過兩種不同的方式添加此信息:
-
使用 –ks 選項指定密鑰庫文件。
-
使用 –key 和 –cert 選項分別指定私鑰文件和證書文件。私鑰文件必須使用 PKCS #8 格式,證書文件必須使用 X.509 格式。
通常情況下,我們只會使用一個簽名者為 APK 簽名。如果我們需要使用多個簽名者為 APK 簽名,請使用 –next-signer 選項將要應用于每個簽名者的常規(guī)選項集分隔開:
apksigner sign [signer_1_options] --next-signer [signer_2_options] app-name.apk
以下示例使用 release.jks(密鑰庫中唯一的密鑰)為 APK 簽名:
apksigner sign --ks release.jks app.apk
以下示例使用私鑰和證書(存儲為不同的文件)為 APK 簽名:
apksigner sign --key release.pk8 --cert release.x509.pem app.apk
以下示例使用兩個密鑰為 APK 簽名:
apksigner sign --ks first-release-key.jks --next-signer --ks second-release-key.jks app.apk
- 驗證 APK 簽名
apksigner verify [options] app-name.apk
以下示例檢查 APK 的簽名是否可在 APK 支持的所有 Android 平臺上被確認為有效:
apksigner verify app.apk
以下示例檢查 APK 的簽名是否可在 Android 4.0.3(API 級別 15)及更高版本上被確認為有效:
apksigner verify --min-sdk-version 15 app.apk
- 輪替簽名密鑰
apksigner rotate --in /path/to/existing/lineage \
--out /path/to/new/file \
--old-signer --ks old-signer-jks \
--new-signer --ks new-signer-jks
以下示例啟用支持密鑰輪替的簽名證書沿襲:
apksigner rotate --out /path/to/new/file --old-signer \
--ks release.jks --new-signer --ks release2.jks
以下示例再次輪替我們的簽名密鑰:
apksigner rotate --in /path/to/existing/lineage \
--out /path/to/new/file --old-signer --ks release2.jks \
--new-signer --ks release3.jks
3.2 簽名命令選項
命令選項 | 說明 |
---|---|
–out | 將要保存已簽名 APK 的位置。 |
–min-sdk-version | 用來確認 APK 簽名將通過驗證的最低 Android 框架 API 級別。 |
–max-sdk-version | 用來確認 APK 簽名將通過驗證的最高 Android 框架 API 級別。 |
–v1-signing-enabled | 確定是否會使用基于 JAR 的傳統(tǒng)簽名方案為給定的 APK 軟件包簽名。 |
–v2-signing-enabled | 確定是否會使用 APK 簽名方案 v2 為給定的 APK 軟件包簽名。 |
–v3-signing-enabled | 確定是否會使用 APK 簽名方案 v3 為給定的 APK 軟件包簽名。 |
–v4-signing-enabled | 確定是否會使用 APK 簽名方案 v4 為給定的 APK 軟件包簽名。 |
–v4-no-merkle-tree | 使用此標志時,不會嵌入完整的 Merkle 樹。 |
–verbose | 使用詳細輸出模式。 |
–ks | 簽名者的私鑰和證書鏈包含在給定的基于 Java 的密鑰庫文件中。 |
–ks-key-alias | 簽名者在密鑰庫中的私鑰和證書數(shù)據(jù)的別名的名稱。 |
–ks-pass | 包含簽名者私鑰和證書的密鑰庫的密碼。 pass:密碼與 apksigner sign 命令的其余部分一起提供。 env:密碼存儲在給定的環(huán)境變量中。 file:密碼作為單行存儲在給定文件中。 stdin:密碼作為單行在標準輸入流中提供。這是 --ks-pass 的默認行為。 |
–ks-type | 與包含簽名者的私鑰和證書的密鑰庫關聯(lián)的類型或算法。 |
–ks-provider-name | 請求簽名者的密鑰庫實現(xiàn)時使用的 JCA 提供程序的名稱。 |
–ks-provider-class | 請求簽名者的密鑰庫實現(xiàn)時使用的 JCA 提供程序的完全限定類名。 |
–ks-provider-arg | 要作為 JCA 提供程序類的構造函數(shù)的參數(shù)傳入的字符串值。 |
–key | 包含簽名者私鑰的文件的名稱。 |
–key-pass | 簽名者私鑰的密碼。 pass:密碼與 apksigner sign 命令的其余部分一起提供。 env:密碼存儲在給定的環(huán)境變量中。 file:密碼作為單行存儲在給定文件中。 stdin:密碼作為單行在標準輸入流中提供。這是 --key-pass 的默認行為。 |
–cert | 包含簽名者證書鏈的文件的名稱。 |
3.3 驗證命令選項
命令選項 | 說明 |
---|---|
–print-certs | 顯示有關 APK 簽名證書的信息。 |
–min-sdk-version | 用來確認 APK 簽名將通過驗證的最低 Android 框架 API 級別。 |
–max-sdk-version | 用來確認 APK 簽名將通過驗證的最高 Android 框架 API 級別。 |
–verbose | 使用詳細輸出模式。 |
-Werr | 將警告視為錯誤。 |
4. zipalign
zipalign 是一種歸檔對齊工具,可對 Android 應用 (APK) 文件提供重要的優(yōu)化。其目的是要確保所有未壓縮數(shù)據(jù)的開頭均相對于文件開頭部分執(zhí)行特定的對齊。具體來說,它會使 APK 中的所有未壓縮數(shù)據(jù)(例如圖片或原始文件)在 4 字節(jié)邊界上對齊。這樣做的好處是可以減少運行應用時消耗的 RAM 容量。
4.1 語法
要對齊 infile.apk 并將其保存為 outfile.apk,請運行以下命令:
zipalign [-f] [-v] <alignment> infile.apk outfile.apk
要確認 existing.apk 的對齊方式,請運行以下命令:
zipalign -c -v <alignment> existing.apk
alignment 是一個整數(shù),用于定義字節(jié)對齊邊界。此值必須始終為 4(可提供 32 位對齊),否則實際將不會執(zhí)行任何操作。
標記:
-
-f:覆蓋現(xiàn)有的 outfile.zip
-
-v:詳細輸出
-
-p:outfile.zip 應對 infile.zip 中的所有共享對象文件使用相同的頁面對齊方式
-
-c:確認給定文件的對齊方式
5. 小結
本節(jié)課程我們主要學習了 Android SDK 構建工具。本節(jié)課程的重點如下:
- 掌握如何使用 Android SDK 構建工具。