How Android uses the Downloadmanager management system to download tasks

Source: Internet
Author: User

Starting with Android 2.3 (API level 9), Android uses system Services (service) to provide download Manager to optimize the processing of long-time download operations. Download Manager handles HTTP connections and monitors status changes in connections and system restarts to ensure that each download task is completed successfully.

Using Download Manager in most cases involving downloads is a good choice, especially if the user switches between different apps and the download needs to continue in the background. And a very important situation when the task is successfully completed (Downloadmanager support for the breakpoint continuation function is very good).

To use the download Manager, use the Getsystemservice method to request the system's Download_service service, which is the following code snippet:




Download file

To request a download operation, you need to create a Downloadmanager.request object that passes the URI of the file you want to download to the Downloadmanager Enqueue method, as shown in the following code snippet:

String servicestring =context.download_service; Downloadmanager Downloadmanager; Downloadmanager = (Downloadmanager) getsystemservice (servicestring);  


The reference variable returned here is a unique ID that the system assigns to the current download request, which we can use to regain the download task, do some of the things we want to do or query the download status, cancel the download, and so on.

We can add HTTP headers for Downloadmanager.request object request through the Addrequestheader method, or you can override the MimeType returned from the server through the Setmimetype method.

We can also specify what connection state to perform the download operation. The Setallowednetworktypes method can be used to restrict the download to the WiFi or mobile network, and the Setallowedoverroaming method can be used to prevent the phone from being downloaded in a roaming state.

The following code fragment is used to specify that a larger file can only be downloaded under WiFi:



Android API Level 11 describes the Getrecommendedmaxbytesovermobile class method (static method), which returns the maximum recommended number of bytes under the current mobile network connection, to determine if the download should be limited to the WiFi condition. After the Enqueue method is called, the download begins as long as the data connection is available and download Manager is available. To get a system notification (notification) when the download is complete, register a broadcast receiver to receive the Action_download_complete broadcast, which will contain a extra_download_ The ID information in intent contains the ID of the download that has been completed, as shown in the following code snippet:


Intentfilter filter = Newintentfilter (downloadmanager.action_download_complete);      Broadcastreceiver receiver = Newbroadcastreceiver () {  @Override public  void OnReceive (context context, Intent Intent) {    Long reference = Intent.getlongextra (downloadmanager.extra_download_id,-1);    if (mydownloadreference = = reference) {          }  


Using the Opendownloadedfile method of the Download manager, you can open a file that has already been downloaded and return a Parcelfiledescriptor object. We can use the Download Manager to query the save address of the download file, if we have a path and file name at the time of downloading, we can also manipulate the file directly. We can register a broadcast recipient for action_notification_clicked action, and when a user clicks on a download item from the notification bar or clicks a downloadable item from the Downloads app, a click-to-download broadcast will be issued.

The code snippet is as follows:


Intentfilter filter = Newintentfilter (downloadmanager.action_notification_clicked);  Broadcastreceiver receiver = Newbroadcastreceiver () {  @Override public  void OnReceive (context context, Intent Intent) {    String extraid =downloadmanager.extra_notification_click_download_ids;    long[] References = Intent.getlongarrayextra (extraid);    for (long reference:references)      if (reference = = mydownloadreference) {        //do something with downloading file.
   }}}  ;  


Customizing the style of the download Manager notifications

By default, each download that is managed by Download Manager is displayed in the notification bar, and each notification displays the current download progress and file name

With Download Manager, you can customize the notification style for each download request, including a full hidden notification. The following code snippet shows how to customize the text displayed in the file download notification by using the Settitle and SetDescription methods.




The Setnotificationvisibility method can be used to control when the notification is displayed, even the notification that hides the request. There are several parameters:

Request.visibility_visible: During the download process, the notification of the download will always be displayed in the notification bar, and when the download is complete, the notification will be removed, which is the default parameter value.

request.visibility_visible_notify_completed: The notification bar will always display the downloaded notification during the download process, and the notification will continue to display after the download is complete. Until the user clicks on the notification or removes the notification.

Request.visibility_visible_notify_only_completion: The notification will not be displayed until the download is complete.

Request.visibility_hidden: The notification of the download request is not displayed. If you want to use this parameter, you need to add the Download_without_notification permission to the app's manifest file.

Specify download Save Address

By default, all files downloaded through Download Manager are saved in a shared download cache, and each request object can be created with a system-generated file name for a download

The saved address, usually, all of the downloaded files should be stored in the external storage, so we need to add Write_external_storage permissions in the app manifest file:




The following code fragment is a method of specifying an arbitrary save location in an external store:




F is a file object.

If the file you downloaded is dedicated to your app, you may want to put the file in a proprietary folder in your app's external storage. Note that this folder does not provide access control, so other applications can also access this folder. In this case, if your app is uninstalled, it will also be deleted in this folder.

The following code snippet is a way to specify that the path to the stored file is a private folder that is applied to the external store:


Request.setdestinationinexternalfilesdir (This,  


If the downloaded file wants to be shared by other apps, especially those files you download that you want to be scanned by media scanner (such as music files), then you can specify that your download path is under a public folder stored externally, The following code snippet is a way to store a file in a public music folder in an external store:


Request.setdestinationinexternalpublicdir (Environment.directory_music,  


By default, files downloaded through Download Manager cannot be scanned by media scanner, and these downloaded files (music, video, etc.) are not gallery and

Seen in apps like Music player.

In order for the downloaded music file to be scanned by other applications, we need to invoke the Allowscaningbymediascanner method of the Request object.

If we want the downloaded file to be scanned and managed by the system's downloads application, we need to invoke the Setvisibleindownloadsui method of the Request object, passing the parameter true.

Cancel and Delete Downloads

The Remove method of the Download manager can be used to cancel a prepared download, abort an in-progress download, or delete a completed download.

The Remove method takes several download IDs as parameters, and you can set one or several download IDs that you want to cancel, as shown in the following code snippet:




This method returns the number of successfully canceled downloads, and if a download is canceled, all associated files, partially downloaded files, and fully downloaded files will be deleted.

Query Download Manager

You can get the status, progress, and details of the download task by querying download Manager to return a cursor with the details of the download task through the Query method. The Query method passes a Downloadmanager.query object as a parameter, and the Downloadmanager.query object's Setfilterbyid method allows you to filter the ID of the download task that we want to query. You can also use the Setfilterbystatus method to filter the download task for one of the states that we want to query, the parameter passed is the downloadmanager.status_* constant, and you can specify

Four states are in progress, paused, failed, and completed.

Download Manager contains a series of column_* static string constants that can be used to query the index of the result column in the cursor. We can query the various details of the download task, including the status, file size, number of bytes already downloaded, title, description, URI, local file name and URI, media type, and medium Provider download URI.

The following code snippet is an implementation of the local file name and URI for downloading the completed file by registering the broadcast recipient who listens for the download completion event:


@Override public void OnReceive (Context context,intent Intent) {  Long reference = Intent.getlongextra ( DOWNLOADMANAGER.EXTRA_DOWNLOAD_ID,-1);   if (mydownloadreference = = reference) {          query mydownloadquery = new Query ();    Mydownloadquery.setfilterbyid (reference);           Cursor mydownload = Downloadmanager.query (mydownloadquery);    if (Mydownload.movetofirst ()) {      int filenameidx =         Mydownload.getcolumnindex (downloadmanager.column_local_ FILENAME);      int fileuriidx =         Mydownload.getcolumnindex (downloadmanager.column_local_uri);       String fileName = mydownload.getstring (FILENAMEIDX);      String Fileuri = mydownload.getstring (FILEURIIDX);           TODO do something with the file.      LOG.D (TAG, FileName + ":" + Fileuri);    }    Mydownload.close ();   


For paused and failed downloads, we can query the Column_reason column to find out the cause of the whole digital.

For the download of the status_paused state, it is possible to translate the integer digit of the reason by downloadmanager.paused_* Static constants, and then determine that the download is due to waiting for the network connection

Or wait for the WiFi connection or prepare to re-download for three different reasons and pause.

For the download of the status_failed state, we can determine the cause of the failure by downloadmanager.error_*, which may be the error code (failure reason) including no storage device,

Insufficient storage space, duplicate file name, or HTTP errors.

The following code is how to query out all the currently paused download tasks, extract the reason for the pause and the file name, download the title, and the current progress of the implementation method:


Obtain the Download ManagerService. String servicestring =context.download_service; Downloadmanager Downloadmanager;  Downloadmanager = (Downloadmanager) getsystemservice (servicestring); Create a query for pauseddownloads. Query pauseddownloadquery = NewQuery ();  Pauseddownloadquery.setfilterbystatus (downloadmanager.status_paused); Query the Download Manager for Pauseddownloads.  Cursor pauseddownloads =downloadmanager.query (pauseddownloadquery); Find The column indexes for the data werequire. int Reasonidx =pauseddownloads.getcolumnindex (Downloadmanager.column_reason); int Titleidx =pauseddownloads.getcolumnindex (downloadmanager.column_title);     int filesizeidx = Pauseddownloads.getcolumnindex (downloadmanager.column_total_size_bytes);  int bytesdlidx = Pauseddownloads.getcolumnindex (Downloadmanager.column_bytes_downloaded_so_far); Iterate over the result Cursor.  while (Pauseddownloads.movetonext ()) {//extract The data we require from the Cursor. String title = PAuseddownloads.getstring (TITLEIDX);   Intfilesize = Pauseddownloads.getint (FILESIZEIDX);    INTBYTESDL = Pauseddownloads.getint (BYTESDLIDX);   Translate The pause reason to friendly text.  Intreason = Pauseddownloads.getint (REASONIDX);  String reasonstring = "Unknown";    Switch (reason) {case DownloadManager.PAUSED_QUEUED_FOR_WIFI:reasonString = ' Waiting for WIFI '; Case DownloadManager.PAUSED_WAITING_FOR_NETWORK:reasonString = "Waiting for connectivity";    Break Case DownloadManager.PAUSED_WAITING_TO_RETRY:reasonString = "Waiting to RETRY";    Break  Default:break;  }//construct A status summary StringBuilder sb = new StringBuilder ();  Sb.append (title). Append ("\ n");  Sb.append (reasonstring). Append ("\ n");    Sb.append ("downloaded"). Append (bytesdl). Append ("/"). Append (FileSize); Display the status log.d ("DOWNLOAD", sb.tostring ()); }//Close the result Cursor.   Pauseddownloads.close ();


Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.