Android Basic Training Course: Requesting and Requiring Permissions

    Nowadays, many applications that hold onto contact data secure that data by requiring that a user explicitly grant rights for other programs to access the contact information. Those rights could be granted on a case-by-case basis or once at install time.
    Android is no different, in that it requires permissions for applications to read or write contact data. Android’s permission system is useful well beyond contact data, and for content providers and services beyond those supplied by the Android framework.
    You, as an Android developer, will frequently need to ensure your applications have the appropriate permissions to do what you want to do with other applications’ data. You may also elect to require permissions for other applications to use your data or services, if you make those available to other Android components. This post covers how to accomplish both these ends.

Requesting a permission

    Requesting the use of other applications’ data or services requires the <use-permission> element to be added to your AndroidManifest.xml file. Your manifest may have zero or more uses-permission elements, all as direct children of the root manifest element. For example:
<uses-permission android:name="android.permission.INTERNET"/>
    Here is some popular permissions in Android:
  • INTERNET: in case your application wants to access the Internet in any manner whatsoever.
  • WRITE_EXTERNAL_STORAGE: to write data into the SD card (or any equipment that has been designed as a storage device).
  • ACCESS_COARSE_LOCATION and ACCESS_FINE_LOCATION: to determine where devices.
    Permissions are confirmed at the time the application is installed - the user will be prompted to confirm it is OK for your application to do what the permission calls for. However, this prompt is not available in the current emulator. For example, installing an app in a real device:

Declaring permissions

    The other side of the coin, of course, is to secure your own application. If your application is merely activities and intent receivers, security may be just an outbound thing, where you request the right to use resources of other applications. If, on the other hand, you put content providers or services in your application, you will want to implement inbound security to control which applications can do what with the data.
    Note that the issue here is less about whether other applications might “mess up” your data, and more about privacy of the user’s information or use of services that might incur expense. That is where the stock permissions for built-in Android applications are focused - can you read or modify contacts, can you send SMS messages, etc. If your application does not store information that might be considered private, security is less of an issue. If, on the other hand, your application stores private data, such as medical information, security is much more important.
    The first step to securing your own application using permissions is to declare said permissions, once again in the AndroidManifest.xml. In this case, instead of <uses-permission>, you add <permission> elements. Once again, you can have zero or more permission elements, all as direct children of the root <manifest> element.
    Declaring a permission is slightly more complicated than using a permission. There are three pieces of information you need to supply:
  • The symbolic name of the permission. To keep your permissions from colliding with those from other applications, you should use your application’s Java namespace as a prefix.
  • A label for the permission: something short that is understandable by users.
  • A description for the permission: something a wee bit longer that is understandable by users.
    For example:
<permission
 android:name="vnd.tlagency.sekrits.SEE_SEKRITS"
 android:label="@string/see_sekrits_label"
 android:description="@string/see_sekrits_description" />
    This does not enforce the permission. Rather, it indicates that it is a possible permission, your application must still flag security violations as they occur. There are two ways for your application to enforce permissions, dictating where and under what circumstances they are required. You can enforce permissions in your code, but the easier option is to indicate in the manifest where permissions are required.
    Activities, services, and intent receivers can all declare an attribute name android:permission, whose value is the name of the permission that is required to access those items:
<activity android:name=".MainActivity" android:label="Top Sekrit"
 android:permission="vnd.tlagency.sekrits.SEE_SEKRITS">
 <intent-filter>
  <action android:name="android.intent.action.MAIN" />
  <category android:name="android.intent.category.LAUNCHER" />
 </intent-filter>
</activity>
    Only applications that have requested your indicated permission will be able to access the secured component. In this case, “access” means the following:
  • Activities cannot be started without the permission.
  • Services cannot be started, stopped, or bound to an activity without the permission.
  • Intent receivers ignore messages sent via sendBroadcast() unless the sender has the permission.

Enforcing Permissions Elsewhere

 
    In your code, you have two additional ways to enforce permissions. Your services can check permissions on a per-call basis via checkCallingPermission(). This returns PERMISSION_GRANTED or PERMISSION_DENIED, depending on whether the caller has the permission you specified. For example, if your service implements separate read and write methods, you could get the effect of readPermission and writePermission in code by checking those methods for the permissions you need from Java.
Also, you can include a permission when you call sendBroadcast(). This means that eligible receivers must hold that permission; those without the permission are ineligible to receive it.
For example, the Android subsystem presumably includes the RECEIVE_SMS permission when it broadcasts that an SMS message has arrived — this will restrict the receivers of that intent to be only those authorized to receive SMS messages.

Conclcusions

 
    Over here, I have presented an overview of permissions in Android. Further, there is no automatic discovery of permissions at compile time; all permission failures occur at runtime. Hence, it is important that you document the permissions required for your public APIs, including content providers, services, and activities intended for launching from other activities. Otherwise, the programmers attempting to interface with your application will have to find out the permission rules by trial and error.
    Further more, you should expect that users of your application will be prompted to confirm any permissions your application says it needs. Hence, you need to document for your users what they should expect, lest they get confused by the question posed by the phone and elect to not install or use your application.

Share


Previous post
« Prev Post
Next post
Next Post »