async 10 to 20% faster

pull/106/head
Ciro 2023-02-08 15:53:52 -03:00
rodzic ea202f8e4d
commit f9a76df2f1
5 zmienionych plików z 20 dodań i 21 usunięć

Wyświetl plik

@ -20,4 +20,4 @@ async def app(scope, receive, send):
if __name__ == "__main__":
ASGI(app).listen(8000, lambda config: print(f"Listening on port http://localhost:{config.port} now\n")).run(8)
ASGI(app, lifespan=False).listen(8000, lambda config: print(f"Listening on port http://localhost:{config.port} now\n")).run(8)

Wyświetl plik

@ -533,7 +533,8 @@ class _ASGI:
else:
def run_task(task):
create_task(loop, task_wrapper(task))
future = create_task(loop, task_wrapper(task))
future._log_destroy_pending = False
loop._run_once()
self._run_task = run_task
@ -542,19 +543,16 @@ class _ASGI:
if sys.version_info >= (3, 8): # name fixed to avoid dynamic name
def run_task(task):
future = loop.create_task(
task_wrapper(task), name="socketify.py-request-task"
)
future = create_task(loop, task_wrapper(task))
future._log_destroy_pending = False
loop._run_once()
self._run_task = run_task
else:
def run_task(task):
future = loop.create_task(task_wrapper(task))
future = create_task(loop, task_wrapper(task))
future._log_destroy_pending = False
loop._run_once()
self._run_task = run_task

Wyświetl plik

@ -129,18 +129,16 @@ class Loop:
future = self._task_factory(
self.loop, task_wrapper(self.exception_handler, self.loop, response, task)
)
# force asyncio run once to enable req in async functions before first await
# this call makes pypy 10% to 20% faster in async, but will work without it
# this also makes uvloop incompatible if uvloop becomes compatible with pypy
self.loop._run_once()
return None # this future maybe already done and reused not safe to await
def _run_async_cpython(self, task, response=None):
# this garanties error 500 in case of uncaught exceptions, and can trigger the custom error handler
# using an coroutine wrapper generates less overhead than using add_done_callback
future = self.loop.create_task(
task_wrapper(self.exception_handler, self.loop, response, task)
)
# force asyncio run once to enable req in async functions before first await
self.loop._run_once()
# custom task will call _step, reusing tasks in CPython is not worth
future = create_task(self.loop, task_wrapper(self.exception_handler, self.loop, response, task))
return None # this future is safe to await but we return None for compatibility, and in the future will be the same behavior as PyPy
def dispose(self):

Wyświetl plik

@ -115,7 +115,8 @@ class RequestTask:
self._log_destroy_pending = False
if self._loop.get_debug():
self._source_traceback = format_helpers.extract_stack(sys._getframe(1))
self._loop.call_soon(self.__step, context=self._context)
# self._loop.call_soon(self.__step, context=self._context)
self.__step()
_register_task(self)
def _reuse(self, coro, loop, default_done_callback=None):
@ -147,7 +148,8 @@ class RequestTask:
self._fut_waiter = None
self._coro = coro
self._loop.call_soon(self.__step, context=self._context)
# self._loop.call_soon(self.__step, context=self._context)
self.__step()
_register_task(self)
def __repr__(self):

Wyświetl plik

@ -361,7 +361,8 @@ class _WSGI:
else:
def run_task(task):
create_task(loop, task)
future = create_task(loop, task)
future._log_destroy_pending = False
loop._run_once()
self._run_task = run_task
@ -370,15 +371,15 @@ class _WSGI:
if sys.version_info >= (3, 8): # name fixed to avoid dynamic name
def run_task(task):
loop.create_task(task, name="socketify.py-request-task")
loop._run_once()
future = create_task(loop, task)
future._log_destroy_pending = False
self._run_task = run_task
else:
def run_task(task):
loop.create_task(task)
loop._run_once()
future = create_task(loop, task)
future._log_destroy_pending = False
self._run_task = run_task