實作 Java SDK 程式庫

Android 平台包含大量共用 Java 程式庫 也可以視需要加到應用程式的類別路徑中 應用程式資訊清單中的 <uses-library> 標記。應用程式連結 請比照 Android API 的其他內容處理這些程式庫 相容性、API 審查及工具支援但請注意 但大多數程式庫都不會提供這些功能

java_sdk_library 模組類型可協助管理程式庫 這類模型裝置製造商可以為自家機構 共用 Java 程式庫,以維持其 API 的回溯相容性。 如果裝置製造商透過 <uses-library> 標記,而非 bootclass 路徑 java_sdk_library 可以驗證這些 Java 程式庫是否 API 穩定版。

java_sdk_library 會導入選用的 SDK API,以供 應用程式。透過 java_sdk_library 中以 建構檔案 (Android.bp) 會執行下列作業:

  • 產生虛設常式程式庫,包含 stubsstubs.systemstubs.test。這些 系統會辨識 @hide@SystemApi@TestApi 註解。
  • java_sdk_library 會管理 API 規格檔案 (例如 current.txt)。這些檔案 檢查最新的程式碼,確保 先前的版本否則會看到 更新方式。手動檢查所有更新項目 確保這些做法與您的期望相符

    如要更新所有 API,請使用 m update-api。如要驗證 API 是否為最新版本 使用 m checkapi
  • 會根據最近一次檢查的 API 規格檔案來檢查 API 規格檔案 已發布 Android 版本,確保 API 能回溯相容 和早期版本整合提供的 java_sdk_library 模組 因為 Android 開放原始碼計畫會將先前發布的版本放到 prebuilts/sdk/<latest number>
  • 關於 API 規格檔案檢查,您可以 下列三個項目的其中一個
    • 如要繼續操作,請允許檢查。(什麼都不做)。
    • 將下列程式碼新增至 java_sdk_library,即可停用檢查功能:
      unsafe_ignore_missing_latest_api: true,
    • 為新的 java_sdk_library 模組提供空白 API 方法是在 module_name.txt version/scope/api 目錄
  • 如果已安裝執行階段實作程式庫,則會產生 XML 檔案 。

java_sdk_library 的運作方式

名為 Xjava_sdk_library 會建立以下項目:

  1. 實作程式庫的兩個副本:一個名為 X 的程式庫 還有另一個名為 X.impl已安裝程式庫 X 應用程式。只有在獲得明確存取權時,才能使用程式庫 X.impl 其他模組 (例如 進行測試。請注意,很少需要明確授予存取權。
  2. 您可以啟用及停用範圍來自訂存取權。(與 Java 類似 為關鍵字存取權修飾符提供廣泛的存取權換 測試範圍包含僅供測試使用的 API)。對於每個已啟用的範圍 程式庫會建立以下項目:
    • 虛設常式來源模組 (droidstubs 模組類型) - 取用 實作來源,並輸出一組虛設常式來源及 API 規格檔案
    • 虛設常式程式庫 (屬於 java_library 模組類型) - 是 產生的程式碼副本編譯使用的程式庫並非 與提供給 java_sdk_library 的資料相同,可確保 實作詳細資料不會洩漏至 API 虛設常式。
    • 如果您需要其他程式庫來編譯虛設常式,請使用 「stub_only_libs」和「stub_only_static_libs」 資源

如果 java_sdk_library 稱為「X」,且 彙整為「X」,請一律以這種方式參照,且不會修改 基礎架構建構作業會選取合適的程式庫。為了確保您具備 檢查您的虛設常式,確認該版本是否已導入 發生錯誤。請按照本文指示進行必要的修正:

  • 查看指令列並 檢查其中有哪些虛設常式,以判斷範圍:
    • 範圍太寬:依附程式庫需要特定的 API 範圍。但 您會看到程式庫中超出該範圍的 API,例如 公用 API 所包含的系統 API
    • 範圍太小:子程式庫無法存取 所需的程式庫例如,相依的程式庫需要使用 但改為取得公用 API這通常會導致 缺少必要的 API,導致發生編譯錯誤。
  • 如要修正程式庫,請只執行以下一個步驟:
    • 變更 sdk_version 來選取您需要的版本。或
    • 明確指定適當的程式庫,例如 <X>.stubs<X>.stubs.system

java_sdk_library X 使用方式

參照實作資料庫 X 時,系統會從 apex.java_libs。但由於 Soong 限制 從另一個 java_sdk_library 模組參照 X 在同一個 APEX 程式庫中,明確使用 X.impl 必須使用,而非程式庫 X

從其他位置參照 java_sdk_library 時,虛設常式 程式庫系統會根據 模組的 sdk_version 屬性設定。舉例來說,某個模組 會指定 sdk_version: "current" 使用公開虛設常式,而 指定 sdk_version: "system_current" 的模組會使用 系統虛設常式如果找不到完全相符的結果,系統會傳回最接近的虛設常式資料庫 只提供公用 API 的 java_sdk_library 將會 為所有人提供公開虛設常式

使用 Java SDK 程式庫建構流程
圖 1.使用 Java SDK 程式庫建構流程

範例和來源

srcsapi_packages 屬性必須 出現在 java_sdk_library

java_sdk_library {
        name: "com.android.future.usb.accessory",
        srcs: ["src/**/*.java"],
        api_packages: ["com.android.future.usb"],
    }

Android 開放原始碼計畫建議 (但不一定要) 新的 java_sdk_library 執行個體明確啟用要使用的 API 範圍。你也可以 (選擇性) 將現有的 java_sdk_library 執行個體遷移至 明確啟用他們要使用的 API 範圍:

java_sdk_library {
         name: "lib",
         public: {
           enabled: true,
         },
         system: {
           enabled: true,
         },
         …
    }

如要設定用於執行階段的 impl 程式庫,請使用所有 一般 java_library 屬性,例如 hostdex compile_dexerrorprone

java_sdk_library {
        name: "android.test.base",

        srcs: ["src/**/*.java"],

        errorprone: {
          javacflags: ["-Xep:DepAnn:ERROR"],
        },

        hostdex: true,

        api_packages: [
            "android.test",
            "android.test.suitebuilder.annotation",
            "com.android.internal.util",
            "junit.framework",
        ],

        compile_dex: true,
    }

如要設定虛設常式程式庫,請使用下列屬性:

  • merge_annotations_dirs》和《merge_inclusion_annotations_dirs》。
  • api_srcs:部分的選用來源檔案清單 但不屬於執行階段程式庫的一部分
  • stubs_only_libs:值區中的 Java 程式庫清單 建立虛設常式的類別路徑
  • hidden_api_packages:必須列出的套件名稱清單 隱藏。
  • droiddoc_options:其他引數 Metalava
  • droiddoc_option_files:列出可參照的檔案 在 droiddoc_options內使用 $(location <label>) 其中 <file> 是清單中的項目。
  • annotations_enabled

java_sdk_libraryjava_library,但不是 droidstubs 模組因此不支援所有 droidstubs 資源。以下範例取自 android.test.mock 程式庫版本 檔案。

java_sdk_library {
        name: "android.test.mock",

        srcs: [":android-test-mock-sources"],
        api_srcs: [
            // Note: The following aren’t APIs of this library. Only APIs under the
            // android.test.mock package are taken. These do provide private APIs
            // to which android.test.mock APIs reference. These classes are present
            // in source code form to access necessary comments that disappear when
            // the classes are compiled into a Jar library.
            ":framework-core-sources-for-test-mock",
            ":framework_native_aidl",
        ],

        libs: [
            "framework",
            "framework-annotations-lib",
            "app-compat-annotations",
            "Unsupportedappusage",
        ],

        api_packages: [
            "android.test.mock",
        ],
        permitted_packages: [
            "android.test.mock",
        ],
        compile_dex: true,
        default_to_stubs: true,
    }

維持回溯相容性

建構系統會檢查 API 是否已回溯維護 比較最新 API 檔案與 建構的 API 檔案java_sdk_library 會執行 相容性檢查功能會使用 prebuilt_apis 提供的資訊。 使用 java_sdk_library 建構的所有程式庫都必須具有 API 檔案 最新版 api_dirs 功能 prebuilt_apis 發布版本時,API 會列出檔案和虛設常式 可使用 PRODUCT=sdk_phone_armv7-sdk 取得程式庫。

api_dirs 屬性是 API 版本目錄的清單 位置:prebuilt_apis。API 版本目錄必須 位於 Android.bp 目錄層級

prebuilt_apis {
       name: "foo",
       api_dirs: [
           "1",
           "2",
             ....
           "30",
           "current",
       ],
    }

使用 version/scope/api/ 設定目錄 預先建構目錄下的結構值version 對應 API 級別,而 scope 定義 公開、系統或測試

  • version/scope 包含 Java 程式庫
  • version/scope/api 包含 API .txt 個檔案。建立空白文字檔並命名為 module_name.txtmodule_name-removed.txt這裡。
     ├── 30
          │   ├── public
          │   │   ├── api
          │   │   │   ├── android.test.mock-removed.txt
          │   │   │   └── android.test.mock.txt
          │   │   └── android.test.mock.jar
          │   ├── system
          │   │   ├── api
          │   │   │   ├── android.test.mock-removed.txt
          │   │   │   └── android.test.mock.txt
          │   │   └── android.test.mock.jar
          │   └── test
          │       ├── api
          │       │   ├── android.test.mock-removed.txt
          │       │   └── android.test.mock.txt
          │       └── android.test.mock.jar
          └── Android.bp