首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 更多程式語言 >> 程式設計疑難解答

Android 6.0+ 動態權限適配:Manifest 聲明不夠,需運行時請求

     編輯:程式設計疑難解答

問題現象

AndroidManifest.xml 已聲明 READ_CONTACTS、WRITE_CONTACTS,但在 Android 6.0 (API 23) 以上設備運行時仍拋出 SecurityException: Permission Denial。

根本原因

Android 6.0 引入 運行時權限模型:危險權限(通訊錄、定位、存儲等)除在 Manifest 聲明外,必須在運行時向用戶彈窗請求授權,用戶同意後方可使用。

解決步驟

  1. 檢查 targetSdkVersion:若 ≥ 23,必須適配動態權限。
  2. 檢查權限狀態:ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CONTACTS)。
  3. 請求權限:ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.READ_CONTACTS}, REQUEST_CODE)。
  4. 處理回調:重寫 onRequestPermissionsResult,根據 grantResults 判斷用戶是否授權。
  5. 引導用戶開啟設置:用戶勾選「不再詢問」並拒絕後,需跳轉應用詳情頁手動開啟。

核心代碼

private static final int REQ_CONTACTS = 100;

private void loadContacts() {
    if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CONTACTS)
            != PackageManager.PERMISSION_GRANTED) {
        // 需請求
        if (ActivityCompat.shouldShowRequestPermissionRationale(this,
                Manifest.permission.READ_CONTACTS)) {
            // 解釋對話框
            new AlertDialog.Builder(this)
                .setMessage("需要讀取通訊錄才能顯示聯系人")
                .setPositiveButton("確定", (d, w) -> request())
                .show();
        } else {
            request();
        }
    } else {
        doQueryContacts(); // 已授權直接查詢
    }
}

private void request() {
    ActivityCompat.requestPermissions(this,
        new String[]{Manifest.permission.READ_CONTACTS}, REQ_CONTACTS);
}

@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions,
                                       @NonNull int[] grantResults) {
    if (requestCode == REQ_CONTACTS) {
        if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
            doQueryContacts();
        } else {
            Toast.makeText(this, "權限被拒絕,無法讀取通訊錄", Toast.LENGTH_SHORT).show();
        }
    }
}

最佳實踐

  • 封裝權限請求工具類或使用成熟庫(EasyPermissions、PermissionX、Accompanist Permissions)。
  • 在功能入口處統一檢查,避免分散邏輯。
  • 針對「永久拒絕」提供跳轉設置頁引導:Intent(Settings.ACTION_APPLICATION_DETAILS_SETTINGS)。

總結

Manifest 聲明只是「申請資格」,運行時請求才是「拿到通行證」。Android 6.0+ 所有危險權限均需雙重保障,否則必崩。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved