Android 9 (API 級別 28) 對 Android 系統進行了多項變更。以下行為變更僅適用於指定 API 級別 28 以上版本的應用程式。如果應用程式將 targetSdkVersion 設為 API 級別 28 以上,則必須視情況修改應用程式,以支援這些行為。
如要瞭解影響所有 Android 9 應用程式的變更 (無論指定哪個 API 級別),請參閱「行為變更:所有應用程式」。
前景服務
如果應用程式指定 Android 9 以上版本為目標,且使用前景服務,就必須要求 FOREGROUND_SERVICE 權限。這是一般權限,因此系統會自動授予要求權限的應用程式。
如果指定 Android 9 以上版本為目標的應用程式嘗試建立前景服務,但未要求 FOREGROUND_SERVICE,系統會擲回 SecurityException。
隱私權變更
如果應用程式指定 Android 9 為目標,請注意下列行為變更。裝置序號和 DNS 資訊的這些更新可提升使用者隱私權。
建構序號淘汰機制
在 Android 9 中,Build.SERIAL 一律會設為 "UNKNOWN",以保護使用者隱私。
如果應用程式需要存取裝置的硬體序號,請改為要求 READ_PHONE_STATE 權限,然後呼叫 getSerial()。
DNS 隱私權
以 Android 9 為目標的應用程式應遵守私人 DNS API。具體來說,如果系統解析器正在執行 DNS-over-TLS,應用程式應確保任何內建 DNS 用戶端使用加密 DNS 連線至與系統相同的伺服器主機名稱,或停用內建 DNS 用戶端,改用系統解析器。
架構安全性異動
Android 9 包含多項行為變更,可提升應用程式的安全性,但只有在應用程式指定 API 級別 28 以上版本時,這些變更才會生效。
預設啟用網路 TLS
如果應用程式指定 Android 9 以上版本,isCleartextTrafficPermitted() 方法預設會傳回 false。如果應用程式需要為特定網域啟用明文,您必須在應用程式的網路安全性設定中,將這些網域的 cleartextTrafficPermitted 明確設為 true。
以程序區隔的網路資料目錄
為提升 Android 9 的應用程式穩定性和資料完整性,應用程式無法在多個程序之間共用單一 WebView 資料目錄。這類資料目錄通常會儲存 Cookie、HTTP 快取,以及與網頁瀏覽相關的其他永久和暫時儲存空間。
在大多數情況下,應用程式應只在一個程序中使用 android.webkit 套件中的類別,例如 WebView 和 CookieManager。舉例來說,您應將使用 WebView 的所有
Activity 物件移至相同程序。您可以在應用程式的其他程序中呼叫 disableWebView(),更嚴格地強制執行「僅限一個程序」規則。即使是從相依程式庫呼叫,這個呼叫也能防止在其他程序中誤用 WebView 初始化。
如果應用程式必須在多個程序中使用 WebView 執行個體,請務必先使用 WebView.setDataDirectorySuffix() 方法,為每個程序指派專屬的資料目錄尾碼,再於該程序中使用特定 WebView 執行個體。這個方法會將每個程序的網頁資料放在應用程式資料目錄內的專屬目錄中。
每個應用程式的 SELinux 網域
如果應用程式指定 Android 9 以上版本,就無法使用世界可存取的 Unix 權限與其他應用程式共用資料。這項異動可提升 Android 應用程式沙箱的完整性,尤其是應用程式私密資料只能由該應用程式存取的規定。
如要與其他應用程式共用檔案,請使用內容供應器。
連線變更
連線資料計數和多重路徑
在指定 Android 9 以上版本的應用程式中,系統會計算非目前預設網路的網路流量 (例如裝置連上 Wi-Fi 時的行動網路流量),並在 NetworkStatsManager 類別中提供方法,供您查詢該流量。
具體來說,getMultipathPreference() 現在會根據上述網路流量傳回值。從 Android 9 開始,這個方法會傳回 Cell 網路資料的 true,但如果一天內累積的流量超過一定數量,就會開始傳回 false。在 Android 9 上執行的應用程式必須呼叫這個方法,並遵守這項提示。
ConnectivityManager.NetworkCallback 類別現在會將 VPN 相關資訊傳送給應用程式。這項變更可讓應用程式更輕鬆地監聽連線事件,不必混用同步和非同步呼叫,也不必使用受限的 API。此外,這也表示當裝置同時連上多個 Wi-Fi 網路或多個行動網路時,資訊傳輸作業會正常運作。
淘汰 Apache HTTP 用戶端
Android 6.0 已移除對 Apache HTTP 用戶端的支援。自 Android 9 開始,該程式庫會從啟動類別路徑中移除,且預設不適用於應用程式。
如要繼續使用 Apache HTTP 用戶端,以 Android 9 以上版本為目標的應用程式可以在 AndroidManifest.xml 中新增下列項目:
<uses-library android:name="org.apache.http.legacy" android:required="false"/>
除了使用執行階段 Apache 程式庫,應用程式也可以在 APK 中封裝自己的 org.apache.http 程式庫版本。如果這麼做,您必須重新封裝程式庫 (使用 Jar Jar 等公用程式),避免與執行階段提供的類別發生類別相容性問題。
使用者介面變更
查看焦點
面積為 0 的檢視區塊 (寬度或高度為 0) 不再可聚焦。
此外,活動也不再於觸控模式中隱含指派初始焦點。如有需要,您必須明確地要求起始焦點。
CSS RGBA 十六進位值處理方式
指定 Android 9 以上版本的應用程式必須啟用草案 CSS 顏色模組第 4 級行為,才能處理 4 位數和 8 位數的十六進位 CSS 顏色。
Chrome 自 52 版起支援 CSS 顏色模組第 4 級,但 WebView 目前會停用這項功能,因為我們發現現有的 Android 應用程式在 Android 排序 (ARGB) 中含有 32 位元十六進位顏色,這會導致轉譯錯誤。
舉例來說,針對以 API 級別 27 以下為目標的應用程式,顏色 #80ff8080 目前在 WebView 中會以不透明的淺紅色 (#ff8080) 顯示。目前系統會忽略開頭元件 (Android 會將其解讀為 Alpha 元件)。如果應用程式指定的 API 級別為 28 以上,#80ff8080 會解讀為 50% 透明的淺綠色 (#80ff80)。
檔案:URI 的 MIME 類型嗅探
Android 9 之前的版本可以從檔案內容推斷 MIME 類型。自 Android 9 (API 級別 28) 起,應用程式在 WebView 中載入 file: URI 時,必須使用正確的副檔名。
使用檔案內容推斷 MIME 類型可能會導致安全性錯誤,現代瀏覽器通常不允許這麼做。
如果檔案具有可辨識的副檔名,例如 .html、.txt、.js 或 .css,系統會根據副檔名判斷 MIME 類型。如果檔案沒有副檔名或副檔名無法辨識,MIME 類型會是純文字。
舉例來說,file:///sdcard/test.html 這類 URI 會以 HTML 形式顯示,但 file:///sdcard/test 這類 URI 會以純文字形式顯示,即使檔案包含 HTML 資料也一樣。
文件捲動元素
Android 9 可妥善處理文件根元素為捲動元素的情況。在舊版中,捲動位置是設定在 body 元素上,而根元素的捲動值為零。Android 9 支援標準相容行為,也就是捲動元素是根元素。
此外,直接存取 document.body.scrollTop、document.body.scrollLeft、document.documentElement.scrollTop 或 document.documentElement.scrollLeft 時,行為會因目標 SDK 而異。如要存取可視區域捲動值,請使用 document.scrollingElement (如有)。
遭停權應用程式的通知
在 Android 9 之前,系統會取消已暫停應用程式的通知。 從 Android 9 開始,系統會隱藏已暫停應用程式的通知,直到應用程式恢復運作為止。