Writing an HTTP fail-over client with resume and partial downloading

You would like to create a fail-over client that will resume downloading a file if it fails for any reason in the first instance.

How to do it...

Let us download the Python 2.7 code from www.python.org. A resume_download() file will resume any unfinished download of that file.

Listing 4.9 explains resume downloading as follows:

#!/usr/bin/env python
# Python Network Programming Cookbook -- Chapter - 4
# This program is optimized for Python 2.7.# It may run on any other version with/without modifications.

import urllib, os
TARGET_URL = 'http://python.org/ftp/python/2.7.4/'
TARGET_FILE = 'Python-2.7.4.tgz'

class CustomURLOpener(urllib.FancyURLopener):
  """Override FancyURLopener to skip error 206 (when a
    partial file is being sent)
  """
  def http_error_206(self, url, fp, errcode, errmsg, headers, 
data=None):
    pass

  def resume_download():
    file_exists = False
    CustomURLClass = CustomURLOpener()
  if os.path.exists(TARGET_FILE):
    out_file = open(TARGET_FILE,"ab")
    file_exists = os.path.getsize(TARGET_FILE)
    #If the file exists, then only download the unfinished part
    CustomURLClass.addheader("Download range","bytes=%s-" % 
(file_exists))
  else:
    out_file = open(TARGET_FILE,"wb")

  web_page = CustomURLClass.open(TARGET_URL + TARGET_FILE)

  #If the file exists, but we already have the whole thing, don't 
download again
  if int(web_page.headers['Content-Length']) == file_exists:
    loop = 0
    print "File already downloaded!"

  byte_count = 0
  while True:
    data = web_page.read(8192)
    if not data:
      break
    out_file.write(data)
    byte_count = byte_count + len(data)

  web_page.close()
  out_file.close()

  for k,v in web_page.headers.items():
    print k, "=",v
  print "File copied", byte_count, "bytes from", web_page.url

if __name__ == '__main__':
  resume_download()

Running this script will result in the following output:

$   python 4_9_http_fail_over_client.py
content-length = 14489063
content-encoding = x-gzip
accept-ranges = bytes
connection = close
server = Apache/2.2.16 (Debian)
last-modified = Sat, 06 Apr 2013 14:16:10 GMT
content-range = bytes 0-14489062/14489063
etag = "1748016-dd15e7-4d9b1d8685e80"
date = Tue, 07 May 2013 12:51:31 GMT
content-type = application/x-tar
File copied 14489063 bytes from http://python.org/ftp/python/2.7.4/Python-2.7.4.tgz

How it works...

In this recipe, we created a custom URL opener class inheriting from the FancyURLopener method of urllib, but http_error_206() is overridden where partial content is downloaded. So, our method checks the existence of the target file and if it is not present, it tries to download with the custom URL opener class.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.223.195.29