用 python 实现一个多线程网页下载器

本文介绍了一个使用Python实现的多线程HTTP请求池。该请求池能够并发处理多个HTTP请求任务,支持GET和POST方法,并能记录操作日志及处理失败情况。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

关键字:  Python , 多线程

转自http://blog.youkuaiyun.com/lanphaday/archive/2009/04/16/4083852.aspx

学习之

  1. #!/usr/bin/env python  
  2. # -*- coding:utf-8 -*-    
  3. import urllib, httplib    
  4. import thread    
  5. import time    
  6. from Queue import Queue, Empty, Full    
  7. HEADERS = {"Content-type""application/x-www-form-urlencoded",    
  8.                         'Accept-Language':'zh-cn',    
  9.                         'User-Agent''Mozilla/4.0 (compatible; MSIE 6.0;Windows NT 5.0)',    
  10.                         "Accept""text/plain"}    
  11. UNEXPECTED_ERROR = -1    
  12. POST = 'POST'    
  13. GET = 'GET'    
  14. def base_log(msg):    
  15.     print msg    
  16. def base_fail_op(task, status, log):    
  17.     log('fail op. task = %s, status = %d'%(str(task), status))    
  18. def get_remote_data(tasks, results, fail_op = base_fail_op, log = base_log):    
  19.     while True:    
  20.         task = tasks.get()    
  21.         try:    
  22.             tid = task['id']    
  23.             hpt = task['conn_args'# hpt <= host:port, timeout    
  24.         except KeyError, e:    
  25.             log(str(e))    
  26.             continue    
  27.         log('thread_%s doing task %d'%(thread.get_ident(), tid))    
  28.         #log('hpt = ' + str(hpt))    
  29.         conn = httplib.HTTPConnection(**hpt)    
  30.                 
  31.         try:    
  32.             params = task['params']    
  33.         except KeyError, e:    
  34.             params = {}    
  35.         params = urllib.urlencode(params)    
  36.         #log('params = ' + params)    
  37.             
  38.         try:    
  39.             method = task['method']    
  40.         except KeyError:    
  41.             method = 'GET'    
  42.         #log('method = ' + method)    
  43.             
  44.         try:    
  45.             url = task['url']    
  46.         except KeyError:    
  47.             url = '/'    
  48.         #log('url = ' + url)    
  49.             
  50.         headers = HEADERS    
  51.         try:    
  52.             tmp = task['headers']    
  53.         except KeyError, e:    
  54.             tmp = {}    
  55.         headers.update(tmp)    
  56.         #log('headers = ' + str(headers))    
  57.         headers['Content-Length'] = len(params)    
  58.             
  59.         try:    
  60.             if method == POST:    
  61.                 conn.request(method, url, params, headers)    
  62.             else:    
  63.                 conn.request(method, url + params)    
  64.             response = conn.getresponse()    
  65.         except Exception, e:    
  66.             log('request failed. method = %s, url = %s, params = %s headers = %s'%(    
  67.                         method, url, params, headers))    
  68.             log(str(e))    
  69.             fail_op(task, UNEXPECTED_ERROR, log)    
  70.             continue    
  71.                 
  72.         if response.status != httplib.OK:    
  73.             fail_op(task, response.status, log)    
  74.             continue    
  75.                 
  76.         data = response.read()    
  77.         results.put((tid, data), True)    
  78.             
  79. class HttpPool(object):    
  80.     def __init__(self, threads_count, fail_op, log):    
  81.         self._tasks = Queue()    
  82.         self._results = Queue()    
  83.             
  84.         for i in xrange(threads_count):    
  85.             thread.start_new_thread(get_remote_data,(self._tasks, self._results, fail_op, log))    
  86.                 
  87.     def add_task(self, tid, host, url, params, headers = {}, method = 'GET', timeout = None
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值