diff options
author | Kyomotoi <1172294279@qq.com> | 2021-01-26 18:43:13 +0800 |
---|---|---|
committer | Kyomotoi <1172294279@qq.com> | 2021-01-26 18:43:13 +0800 |
commit | 7640568a42493bc5a5e44bc82b1ecfa87e51c5f1 (patch) | |
tree | 60f29b756d58b085c95573515d3e4bd6f41426a8 /ATRI/syncer.py | |
parent | d0d31b2630697c97e848f00142f06b81f63b255a (diff) | |
download | ATRI-7640568a42493bc5a5e44bc82b1ecfa87e51c5f1.tar.gz ATRI-7640568a42493bc5a5e44bc82b1ecfa87e51c5f1.tar.bz2 ATRI-7640568a42493bc5a5e44bc82b1ecfa87e51c5f1.zip |
[Update]
Diffstat (limited to 'ATRI/syncer.py')
-rw-r--r-- | ATRI/syncer.py | 47 |
1 files changed, 47 insertions, 0 deletions
diff --git a/ATRI/syncer.py b/ATRI/syncer.py new file mode 100644 index 0000000..b4c59b1 --- /dev/null +++ b/ATRI/syncer.py @@ -0,0 +1,47 @@ +import sys +import asyncio +import inspect +import types +from functools import singledispatch, wraps + +from typing import Any, Callable, Generator + + +PY37 = sys.version_info >= (3, 7) + + +def _is_awaitable(co: Generator[Any, None, Any]) -> bool: + if PY37: + return inspect.isawaitable(co) + else: + return (isinstance(co, types.GeneratorType) or + isinstance(co, asyncio.Future)) + + +@singledispatch +def sync(co: Any) -> Any: + raise TypeError(f'Called with unsupported argument: {co}') + + +@sync.register(asyncio.Future) +@sync.register(types.GeneratorType) +def sync_co(co: Generator[Any, None, Any]) -> Any: + if not _is_awaitable(co): + raise TypeError(f'Called with unsupported argument: {co}') + return asyncio.get_event_loop().run_until_complete(co) + + +@sync.register(types.FunctionType) +@sync.register(types.MethodType) # type: ignore +def sync_fu(f: Callable[..., Any]) -> Callable[..., Any]: + if not asyncio.iscoroutinefunction(f): + raise TypeError(f'Called with unsupported argument: {f}') + + @wraps(f) + def run(*args, **kwargs) -> Any: + return asyncio.get_event_loop().run_until_complete(f(*args, **kwargs)) + return run + + +if PY37: + sync.register(types.CoroutineType)(sync_co) |