connection_cache.py 2.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980
  1. import sys
  2. import time
  3. import random
  4. import Queue
  5. import traceback
  6. from LIFOQueue import LIFOQueue
  7. import pycurllib
  8. max_wait = 5
  9. max_connections = 1
  10. inf_wait_max_connections = 1000
  11. class ConnectionCache(object):
  12. def __init__(self, max=15):
  13. self.size = 0
  14. self.max = max
  15. self.cache = LIFOQueue(maxsize = self.max)
  16. def get_connection(self):
  17. if self.size > max_connections:
  18. # ERROR: Should log this!
  19. #sys.stderr.write("ConnectionCache queue exceeds %d (%d)\n" %
  20. # (max_connections, self.cache.qsize()))
  21. pass
  22. try:
  23. return self.cache.get_nowait()
  24. except Queue.Empty:
  25. pass
  26. # I chose not to lock here. Max is advisory, if two threads
  27. # eagerly await a connection near max, I say allow them both
  28. # to make one
  29. if self.size < self.max:
  30. self.size += 1
  31. return self._make_connection()
  32. try:
  33. return self.cache.get(True, max_wait)
  34. except Queue.Empty:
  35. # ERROR: Should log this!
  36. #sys.stderr.write("ConnectionCache waited more than "
  37. # "%d seconds for one of %d connections!\n" %
  38. # (max_wait, self.size))
  39. pass
  40. if self.size > inf_wait_max_connections:
  41. return self.cache.get()
  42. self.size += 1
  43. return self._make_connection()
  44. def put_connection(self, c):
  45. self.cache.put(c)
  46. class PyCURL_Cache(ConnectionCache):
  47. def __init__(self, uri, max):
  48. self.uri = uri
  49. ConnectionCache.__init__(self, max)
  50. def _make_connection(self):
  51. r = pycurllib.Request(self.uri)
  52. #r.set_timeout(20)
  53. return r
  54. class CacheSet(object):
  55. def __init__(self, max_per_cache = max_connections):
  56. self.cache = {}
  57. self.max_per_cache = max_per_cache
  58. def get_cache(self, cachetype, url):
  59. if url not in self.cache:
  60. self.cache[url] = cachetype(url, max=self.max_per_cache)
  61. return self.cache[url]
  62. cache_set = CacheSet()