특별 권한 요청

특별 권한은 특별히 민감하거나 사용자 개인 정보 보호와 직접적인 관련이 없는 시스템 리소스에 대한 액세스를 보호합니다. 이러한 권한은 설치 시간 권한런타임 권한과 다릅니다.

그림 1. 시스템 설정의 특수 앱 액세스 화면

특별 권한의 예는 다음과 같습니다.

  • 정확한 알람을 예약합니다.
  • 다른 앱 위에 표시하거나 그립니다.
  • 모든 저장소 데이터에 액세스합니다.

특별 권한을 선언하는 앱은 시스템 설정의 특수 앱 액세스 페이지에 표시됩니다(그림 1). 앱에 특별 권한을 부여하려면 사용자는 설정 > 앱 > 특수 앱 액세스 페이지로 이동해야 합니다.

워크플로

특별 권한을 요청하려면 다음 단계를 따르세요.

  1. 앱의 매니페스트 파일에서 앱이 요청할 수도 있는 특별 권한을 선언합니다.
  2. 앱의 특정 작업이 특정 특별 권한과 연결되도록 앱의 UX를 설계합니다. 앱이 비공개 사용자 데이터에 액세스하도록 권한을 부여해야 할 수도 있는 작업을 사용자에게 알립니다.
  3. 특정 비공개 사용자 데이터에 액세스해야 하는 앱의 작업을 사용자가 호출할 때까지 기다립니다. 이때 앱은 데이터에 액세스하는 데 필요한 특별 권한을 요청할 수 있습니다.
  4. 사용자가 이미 앱에 필요한 특별 권한을 부여했는지 확인합니다. 그렇게 하려면 각 권한의 맞춤 검사 함수를 사용합니다. 부여했다면 앱에서 비공개 사용자 데이터에 액세스할 수 있습니다. 부여하지 않았다면 다음 단계로 이동합니다. 참고: 권한이 필요한 작업을 실행할 때마다 권한이 있는지 확인해야 합니다.
  5. UI 요소에 사용자가 특별 권한을 부여하면 앱이 어떤 데이터에 액세스하는지 그리고 앱이 사용자에게 어떤 이점을 제공할 수 있는지 명확하게 설명하는 근거를 제시합니다. 또한 앱이 권한 부여를 위해 사용자를 시스템 설정으로 이동시키므로, 사용자가 권한을 부여할 수 있는 방법을 설명하는 간단한 안내도 포함합니다. 근거 UI는 사용자가 권한 부여를 거부할 수 있는 명확한 옵션을 제공해야 합니다. 사용자가 근거를 확인한 후 다음 단계를 진행합니다.
  6. 앱에서 비공개 사용자 데이터에 액세스하는 데 필요한 특별 권한을 요청합니다. 여기에는 시스템 설정 내에서 사용자가 권한을 부여할 수 있는 해당 페이지로 연결되는 인텐트가 포함될 수 있습니다. 런타임 권한과 달리 팝업 권한 대화상자가 없습니다.
  7. 사용자의 응답(사용자가 특별 권한을 부여하도록 선택했는지 아니면 거부하도록 선택했는지)을 onResume() 메서드에서 확인합니다.
  8. 사용자가 앱에 권한을 부여하면 비공개 사용자 데이터에 액세스할 수 있습니다. 사용자가 권한을 거부하면 권한으로 보호되는 정보 없이도 사용자에게 기능을 제공하도록 앱 환경의 성능을 단계적으로 저하합니다.
그림 2. Android에서 특별 권한을 선언하고 요청하기 위한 워크플로

특별 권한 요청

런타임 권한과 달리 사용자는 시스템 설정의 특수 앱 액세스 페이지에서 특별 권한을 부여해야 합니다. 앱은 인텐트를 사용하여 사용자를 이 페이지로 이동시킬 수 있습니다. 인텐트는 앱을 일시중지하고 지정된 특별 권한에 상응하는 설정 페이지를 실행합니다. 사용자가 앱으로 돌아온 후 앱은 onResume() 함수에서 권한이 부여되었는지 확인할 수 있습니다.

다음 샘플 코드는 사용자에게 SCHEDULE_EXACT_ALARMS 특별 권한을 요청하는 방법을 보여줍니다.

val alarmManager = getSystemService<AlarmManager>()!!
when {
   // if permission is granted, proceed with scheduling exact alarms…
   alarmManager.canScheduleExactAlarms() -> {
       alarmManager.setExact(...)
   }
   else -> {
       // ask users to grant the permission in the corresponding settings page
       startActivity(Intent(ACTION_REQUEST_SCHEDULE_EXACT_ALARM))
   }
}

다음은 onResume()에서 권한을 확인하고 사용자 결정을 처리하는 샘플 코드입니다.

override fun onResume() {
   // ...

   if (alarmManager.canScheduleExactAlarms()) {
       // proceed with the action (setting exact alarms)
       alarmManager.setExact(...)
   }
   else {
       // permission not yet approved. Display user notice and gracefully degrade
       your app experience.
       alarmManager.setWindow(...)
   }
}

권장사항 및 도움말

다음 섹션에서는 특별 권한을 요청할 때의 권장사항과 고려사항을 제공합니다.

권한별 자체 검사 방법

특별 권한은 런타임 권한과 다르게 작동합니다. 권한 API 참조 페이지를 참고하고 각 특별 권한의 맞춤 액세스 검사 함수를 사용하세요. 예로는 AlarmManager#canScheduleExactAlarms()(SCHEDULE_EXACT_ALARMS 권한) 및 Environment#isExternalStorageManager()(MANAGE_EXTERNAL_STORAGE 권한)가 있습니다.

컨텍스트 내에서 요청

런타임 권한과 마찬가지로 앱은 사용자가 권한이 필요한 특정 작업을 요청할 때 컨텍스트 내에서 특별 권한을 요청해야 합니다. 예를 들어 사용자가 특정 시간에 전송될 이메일을 예약할 때까지 SCHEDULE_EXACT_ALARMS 권한 요청을 대기합니다.

요청 설명

시스템 설정으로 리디렉션하기 전에 이유를 제공합니다. 사용자가 특별 권한을 부여하기 위해 일시적으로 앱을 나가므로, 시스템 설정의 특수 앱 액세스 페이지로 인텐트를 실행하기 전에 인앱 UI를 표시합니다. 이 UI는 앱에 권한이 필요한 이유와 사용자가 설정 페이지에서 권한을 부여하는 방법을 명확하게 설명해야 합니다.