summaryrefslogtreecommitdiff
path: root/eventlet/timeout.py
diff options
context:
space:
mode:
authorSergey Shepelev <temotor@gmail.com>2016-12-22 04:35:14 +0300
committerSergey Shepelev <temotor@gmail.com>2017-01-04 23:42:32 +0300
commite4049a8a0016b28cbbdf3ab01425fc92a623e380 (patch)
tree58d140b6e9f784e5b28a0435fb41ae8f238984af /eventlet/timeout.py
parent461348f9a8459724be87c281eea4e0408138a82c (diff)
downloadeventlet-is-timeout.tar.gz
WIP https://github.com/eventlet/eventlet/pull/346is-timeout
Diffstat (limited to 'eventlet/timeout.py')
-rw-r--r--eventlet/timeout.py41
1 files changed, 36 insertions, 5 deletions
diff --git a/eventlet/timeout.py b/eventlet/timeout.py
index f45c6d1..f431871 100644
--- a/eventlet/timeout.py
+++ b/eventlet/timeout.py
@@ -20,13 +20,16 @@
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
# THE SOFTWARE.from eventlet.support import greenlets as greenlet
+import functools
+import inspect
+
+import eventlet
from eventlet.support import greenlets as greenlet
from eventlet.hubs import get_hub
-__all__ = ['Timeout',
- 'with_timeout']
+__all__ = ['Timeout', 'with_timeout', 'wrap_is_timeout', 'is_timeout']
-_NONE = object()
+_MISSING = object()
# deriving from BaseException so that "except Exception as e" doesn't catch
# Timeout exceptions.
@@ -128,20 +131,48 @@ class Timeout(BaseException):
if value is self and self.exception is False:
return True
+ @property
+ def is_timeout(self):
+ return True
+
def with_timeout(seconds, function, *args, **kwds):
"""Wrap a call to some (yielding) function with a timeout; if the called
function fails to return before the timeout, cancel it and return a flag
value.
"""
- timeout_value = kwds.pop("timeout_value", _NONE)
+ timeout_value = kwds.pop("timeout_value", _MISSING)
timeout = Timeout(seconds)
try:
try:
return function(*args, **kwds)
except Timeout as ex:
- if ex is timeout and timeout_value is not _NONE:
+ if ex is timeout and timeout_value is not _MISSING:
return timeout_value
raise
finally:
timeout.cancel()
+
+
+def wrap_is_timeout(base):
+ '''Adds `.is_timeout=True` attribute to objects returned by `base()`.
+
+ When `base` is class, attribute is added as read-only property. Returns `base`.
+ Otherwise, it returns a function that sets attribute on result of `base()` call.
+
+ Wrappers make best effort to be transparent.
+ '''
+ if inspect.isclass(base):
+ base.is_timeout = property(lambda _: True)
+ return base
+
+ @functools.wraps(base)
+ def fun(*args, **kwargs):
+ ex = base(*args, **kwargs)
+ ex.is_timeout = True
+ return ex
+ return fun
+
+
+def is_timeout(obj):
+ return bool(getattr(obj, 'is_timeout', False))