Android 6.0 運行時權限檢測

Android 6.0 運行時權限檢測

Android 6.0之前的系統用戶在安裝apk文件時會根據app聲明的權限聲稱權限列表,用戶只有在同意了申請的權限後纔可以繼續安裝應用。這樣就存在了很大的安全隱患。因此在android 6.0後的系統中對權限進行了分級。一種是normal permission,一種是 dangerous permission級別權限。

normal permission權限:

  • ACCESS_LOCATION_EXTRA_COMMANDS
  • ACCESS_NETWORK_STATE
  • ACCESS_NOTIFICATION_POLICY
  • ACCESS_WIFI_STATE
  • BLUETOOTH
  • BLUETOOTH_ADMIN
  • BROADCAST_STICKY
  • CHANGE_NETWORK_STATE
  • CHANGE_WIFI_MULTICAST_STATE
  • CHANGE_WIFI_STATE
  • DISABLE_KEYGUARD
  • EXPAND_STATUS_BAR
  • GET_PACKAGE_SIZE
  • INSTALL_SHORTCUT
  • INTERNET
  • KILL_BACKGROUND_PROCESSES
  • MODIFY_AUDIO_SETTINGS
  • NFC
  • READ_SYNC_SETTINGS
  • READ_SYNC_STATS
  • RECEIVE_BOOT_COMPLETED
  • REORDER_TASKS
  • REQUEST_INSTALL_PACKAGES
  • SET_ALARM
  • SET_TIME_ZONE
  • SET_WALLPAPER
  • SET_WALLPAPER_HINTS
  • TRANSMIT_IR
  • UNINSTALL_SHORTCUT
  • USE_FINGERPRINT
  • VIBRATE
  • WAKE_LOCK
  • WRITE_SYNC_SETTINGS

dangerous permission級別權限

  • permission:android.permission.WRITE_CONTACTS
  • permission:android.permission.GET_ACCOUNTS
  • permission:android.permission.READ_CONTACTS

  • permission:android.permission.READ_CALL_LOG

  • permission:android.permission.READ_PHONE_STATE
    • * permission:android.permission.CALL_PHONE*
  • permission:android.permission.WRITE_CALL_LOG
  • permission:android.permission.USE_SIP
  • permission:android.permission.PROCESS_OUTGOING_CALLS
  • permission:com.android.voicemail.permission.ADD_VOICEMAIL

  • permission:android.permission.READ_CALENDAR

  • permission:android.permission.WRITE_CALENDAR

  • permission:android.permission.CAMERA

  • permission:android.permission.BODY_SENSORS

  • permission:android.permission.ACCESS_FINE_LOCATION

    - * permission:android.permission.ACCESS_COARSE_LOCATION*

  • permission:android.permission.READ_EXTERNAL_STORAGE
  • permission:android.permission.WRITE_EXTERNAL_STORAGE

  • permission:android.permission.RECORD_AUDIO

  • permission:android.permission.READ_SMS

  • permission:android.permission.RECEIVE_WAP_PUSH
  • permission:android.permission.RECEIVE_MMS
  • permission:android.permission.RECEIVE_SMS
  • permission:android.permission.SEND_SMS
    • * permission:android.permission.READ_CELL_BROADCASTS*

Android 6.0在我們原有的AndroidManifest.xml聲明權限的基礎上,又新增了運行時權限動態檢測(就是對dangerous permission級別權限進行動態權限監測),以下權限都需要在運行時判斷:

身體傳感器
日曆
攝像頭
通訊錄
地理位置
麥克風
電話
短信
存儲空間

dangerous permission級別權限其實是分組的,每組中包含多個權限。app在動態獲取權限時顯示的是一組權限,一旦你同意了本組權限中的一種權限在下次app調用本組中其他權限時系統默認已經授權不需要用戶再次確認(在miui系統的6.0中測試發現每次都需要再次授權)。

小實例

在android studio項目中要想測試運行時權限檢測必須在gradle中將targetSdkVersion 設置爲23。如果是小於23系統會默認授予androidmainfast.xml中聲明的權限,但是這是一種臨時的解決方法還是需要做新機制的兼容的。

android {
    compileSdkVersion 23
    buildToolsVersion "23.0.3"
    defaultConfig {
        applicationId "com.example.cike.testpermission"
        minSdkVersion 15
        targetSdkVersion 23
        versionCode 1
        versionName "1.0"
        testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
}

我們需要在app中每次需要危險權限時都去權限是否授予的檢測,檢測代碼如下:

//contextCompat.checkSelfPermission()用於檢測是否授予權限
 if (ContextCompat.checkSelfPermission(MainActivity.this, Manifest.permission.CALL_PHONE) != PackageManager.PERMISSION_GRANTED) {
//activitycompat.requestPermission()請求權限                  ActivityCompat.requestPermissions(MainActivity.this, new String[] {Manifest.permission.CALL_PHONE},1);
                } else {
                    calling();
                }

完整代碼如下:

public class MainActivity extends AppCompatActivity {

    private Button button;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        button = (Button) findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                if (ContextCompat.checkSelfPermission(MainActivity.this, Manifest.permission.CALL_PHONE) != PackageManager.PERMISSION_GRANTED) {
                    ActivityCompat.requestPermissions(MainActivity.this, new String[] {Manifest.permission.CALL_PHONE},1);
                } else {
                    calling();
                }
            }
        });
    }

    private void calling() {
        Intent intent = new Intent(Intent.ACTION_CALL);
        Uri data = Uri.parse("tel:1234567890");
        intent.setData(data);
        startActivity(intent);
    }

    @Override
    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        if (requestCode == 1) {
            if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
                calling();
            } else {
                Toast.makeText(this, "權限被拒絕", Toast.LENGTH_SHORT).show();
            }
            return;
        }
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
    }
}

效果圖:

虛擬機效果

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章