base_futures.py 1.9 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667
  1. __all__ = ()
  2. import reprlib
  3. from . import format_helpers
  4. # States for Future.
  5. _PENDING = 'PENDING'
  6. _CANCELLED = 'CANCELLED'
  7. _FINISHED = 'FINISHED'
  8. def isfuture(obj):
  9. """Check for a Future.
  10. This returns True when obj is a Future instance or is advertising
  11. itself as duck-type compatible by setting _asyncio_future_blocking.
  12. See comment in Future for more details.
  13. """
  14. return (hasattr(obj.__class__, '_asyncio_future_blocking') and
  15. obj._asyncio_future_blocking is not None)
  16. def _format_callbacks(cb):
  17. """helper function for Future.__repr__"""
  18. size = len(cb)
  19. if not size:
  20. cb = ''
  21. def format_cb(callback):
  22. return format_helpers._format_callback_source(callback, ())
  23. if size == 1:
  24. cb = format_cb(cb[0][0])
  25. elif size == 2:
  26. cb = '{}, {}'.format(format_cb(cb[0][0]), format_cb(cb[1][0]))
  27. elif size > 2:
  28. cb = '{}, <{} more>, {}'.format(format_cb(cb[0][0]),
  29. size - 2,
  30. format_cb(cb[-1][0]))
  31. return f'cb=[{cb}]'
  32. def _future_repr_info(future):
  33. # (Future) -> str
  34. """helper function for Future.__repr__"""
  35. info = [future._state.lower()]
  36. if future._state == _FINISHED:
  37. if future._exception is not None:
  38. info.append(f'exception={future._exception!r}')
  39. else:
  40. # use reprlib to limit the length of the output, especially
  41. # for very long strings
  42. result = reprlib.repr(future._result)
  43. info.append(f'result={result}')
  44. if future._callbacks:
  45. info.append(_format_callbacks(future._callbacks))
  46. if future._source_traceback:
  47. frame = future._source_traceback[-1]
  48. info.append(f'created at {frame[0]}:{frame[1]}')
  49. return info
  50. @reprlib.recursive_repr()
  51. def _future_repr(future):
  52. info = ' '.join(_future_repr_info(future))
  53. return f'<{future.__class__.__name__} {info}>'