Package restkit :: Module conn
[hide private]

Source Code for Module restkit.conn

  1  # -*- coding: utf-8 - 
  2  # 
  3  # This file is part of restkit released under the MIT license. 
  4  # See the NOTICE for more information. 
  5   
  6  import logging 
  7  import random 
  8  import select 
  9  import socket 
 10  import ssl 
 11  import time 
 12  import cStringIO 
 13   
 14  from socketpool import Connector 
 15  from socketpool.util import is_connected 
 16   
 17  CHUNK_SIZE = 16 * 1024 
 18  MAX_BODY = 1024 * 112 
 19  DNS_TIMEOUT = 60 
 20   
 21   
22 -class Connection(Connector):
23
24 - def __init__(self, host, port, backend_mod=None, pool=None, 25 is_ssl=False, extra_headers=[], proxy_pieces=None, **ssl_args):
26 27 # connect the socket, if we are using an SSL connection, we wrap 28 # the socket. 29 self._s = backend_mod.Socket(socket.AF_INET, socket.SOCK_STREAM) 30 self._s.connect((host, port)) 31 if proxy_pieces: 32 self._s.sendall(proxy_pieces) 33 response = cStringIO.StringIO() 34 while response.getvalue()[-4:] != '\r\n\r\n': 35 response.write(self._s.recv(1)) 36 response.close() 37 if is_ssl: 38 self._s = ssl.wrap_socket(self._s, **ssl_args) 39 40 self.extra_headers = extra_headers 41 self.is_ssl = is_ssl 42 self.backend_mod = backend_mod 43 self.host = host 44 self.port = port 45 self._connected = True 46 self._life = time.time() - random.randint(0, 10) 47 self._pool = pool 48 self._released = False
49
50 - def matches(self, **match_options):
51 target_host = match_options.get('host') 52 target_port = match_options.get('port') 53 return target_host == self.host and target_port == self.port
54
55 - def is_connected(self):
56 if self._connected: 57 return is_connected(self._s) 58 return False
59
60 - def handle_exception(self, exception):
61 raise
62
63 - def get_lifetime(self):
64 return self._life
65
66 - def invalidate(self):
67 self.close() 68 self._connected = False 69 self._life = -1
70
71 - def release(self, should_close=False):
72 if self._pool is not None: 73 if self._connected: 74 if should_close: 75 self.invalidate() 76 self._pool.release_connection(self) 77 else: 78 self._pool = None 79 elif self._connected: 80 self.invalidate()
81
82 - def close(self):
83 if not self._s or not hasattr(self._s, "close"): 84 return 85 try: 86 self._s.close() 87 except: 88 pass
89
90 - def socket(self):
91 return self._s
92
93 - def send_chunk(self, data):
94 chunk = "".join(("%X\r\n" % len(data), data, "\r\n")) 95 self._s.sendall(chunk)
96
97 - def send(self, data, chunked=False):
98 if chunked: 99 return self.send_chunk(data) 100 101 return self._s.sendall(data)
102
103 - def sendlines(self, lines, chunked=False):
104 for line in list(lines): 105 self.send(line, chunked=chunked)
106 107 108 # TODO: add support for sendfile api
109 - def sendfile(self, data, chunked=False):
110 """ send a data from a FileObject """ 111 112 if hasattr(data, 'seek'): 113 data.seek(0) 114 115 while True: 116 binarydata = data.read(CHUNK_SIZE) 117 if binarydata == '': 118 break 119 self.send(binarydata, chunked=chunked)
120 121
122 - def recv(self, size=1024):
123 return self._s.recv(size)
124