gevent.py 1.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940
  1. """A wait callback to allow psycopg2 cooperation with gevent.
  2. Use `patch_psycopg()` to enable gevent support in Psycopg.
  3. """
  4. # Copyright (C) 2010-2020 Daniele Varrazzo <daniele.varrazzo@gmail.com>
  5. # All rights reserved. See COPYING file for details.
  6. from __future__ import absolute_import
  7. import psycopg2
  8. from psycopg2 import extensions
  9. from gevent.socket import wait_read, wait_write
  10. def patch_psycopg():
  11. """Configure Psycopg to be used with gevent in non-blocking way."""
  12. if not hasattr(extensions, 'set_wait_callback'):
  13. raise ImportError(
  14. "support for coroutines not available in this Psycopg version (%s)"
  15. % psycopg2.__version__
  16. )
  17. extensions.set_wait_callback(gevent_wait_callback)
  18. def gevent_wait_callback(conn, timeout=None):
  19. """A wait callback useful to allow gevent to work with Psycopg."""
  20. while 1:
  21. state = conn.poll()
  22. if state == extensions.POLL_OK:
  23. break
  24. elif state == extensions.POLL_READ:
  25. wait_read(conn.fileno(), timeout=timeout)
  26. elif state == extensions.POLL_WRITE:
  27. wait_write(conn.fileno(), timeout=timeout)
  28. else:
  29. raise psycopg2.OperationalError("Bad result from poll: %r" % state)