Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[BREAKING CHANGE] Refactoring: Split event loop in several modules (#537
) * [BREAKING CHANGE] Refactoring: Split event loop in several modules * `urwid.main_loop` is split into multiple modules which is easier to maintain * `urwid.compat` is not used anymore and removed * `TornadoEventLoop`, `GLibEventLoop`, `TwistedEventLoop` and `TrioEventLoop` accessible ONLY if required dependencies installed (like: Tornado installed -> `TornadoEventLoop` is accessible for import) * `TornadoEventLoop` use the same idle logic as `AsyncioLoop`: tornado.ioloop.IOLoop is asyncio based. * Trio < 0.15 is not supported. Version 0.15 was released almost 3 years ago. * Tornado < 5.0 is not supported. Tornado 5.0 was released 5 years ago. * Remove useless shebang * `EventLoop` should be real abstract * add new module docstrings * Fix docstrings * remove unneeded import --------- Co-authored-by: Aleksei Stepanov <alekseis@nvidia.com>
- Loading branch information
1 parent
db10343
commit d1710f0
Showing
18 changed files
with
1,935 additions
and
1,701 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,4 @@ | ||
tornado<5.0.0 | ||
tornado>=5 | ||
coverage[toml] | ||
twisted | ||
trio |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
"""Package with EventLoop implementations for urwid.""" | ||
|
||
from __future__ import annotations | ||
|
||
from .abstract_loop import EventLoop, ExitMainLoop | ||
from .asyncio_loop import AsyncioEventLoop | ||
from .main_loop import MainLoop | ||
from .select_loop import SelectEventLoop | ||
|
||
try: | ||
from .twisted_loop import TwistedEventLoop | ||
except ImportError: | ||
pass | ||
|
||
try: | ||
from .tornado_loop import TornadoEventLoop | ||
except ImportError: | ||
pass | ||
|
||
try: | ||
from .glib_loop import GLibEventLoop | ||
except ImportError: | ||
pass | ||
|
||
try: | ||
from .twisted_loop import TwistedEventLoop | ||
except ImportError: | ||
pass | ||
|
||
try: | ||
from .trio_loop import TrioEventLoop | ||
except ImportError: | ||
pass |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,143 @@ | ||
# Urwid main loop code | ||
# Copyright (C) 2004-2012 Ian Ward | ||
# Copyright (C) 2008 Walter Mundt | ||
# Copyright (C) 2009 Andrew Psaltis | ||
# | ||
# This library is free software; you can redistribute it and/or | ||
# modify it under the terms of the GNU Lesser General Public | ||
# License as published by the Free Software Foundation; either | ||
# version 2.1 of the License, or (at your option) any later version. | ||
# | ||
# This library is distributed in the hope that it will be useful, | ||
# but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
# Lesser General Public License for more details. | ||
# | ||
# You should have received a copy of the GNU Lesser General Public | ||
# License along with this library; if not, write to the Free Software | ||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | ||
# | ||
# Urwid web site: https://urwid.org/ | ||
|
||
"""Abstract shared code for urwid EventLoop implementation.""" | ||
|
||
from __future__ import annotations | ||
|
||
import abc | ||
import signal | ||
import typing | ||
from collections.abc import Callable | ||
|
||
if typing.TYPE_CHECKING: | ||
from types import FrameType | ||
|
||
__all__ = ("ExitMainLoop", "EventLoop") | ||
|
||
|
||
class ExitMainLoop(Exception): | ||
""" | ||
When this exception is raised within a main loop the main loop | ||
will exit cleanly. | ||
""" | ||
pass | ||
|
||
|
||
class EventLoop(abc.ABC): | ||
""" | ||
Abstract class representing an event loop to be used by :class:`MainLoop`. | ||
""" | ||
|
||
@abc.abstractmethod | ||
def alarm(self, seconds: float | int, callback: Callable[[], typing.Any]) -> typing.Any: | ||
""" | ||
Call callback() a given time from now. No parameters are | ||
passed to callback. | ||
This method has no default implementation. | ||
Returns a handle that may be passed to remove_alarm() | ||
seconds -- floating point time to wait before calling callback | ||
callback -- function to call from event loop | ||
""" | ||
|
||
@abc.abstractmethod | ||
def enter_idle(self, callback): | ||
""" | ||
Add a callback for entering idle. | ||
This method has no default implementation. | ||
Returns a handle that may be passed to remove_idle() | ||
""" | ||
|
||
@abc.abstractmethod | ||
def remove_alarm(self, handle) -> bool: | ||
""" | ||
Remove an alarm. | ||
This method has no default implementation. | ||
Returns True if the alarm exists, False otherwise | ||
""" | ||
|
||
@abc.abstractmethod | ||
def remove_enter_idle(self, handle) -> bool: | ||
""" | ||
Remove an idle callback. | ||
This method has no default implementation. | ||
Returns True if the handle was removed. | ||
""" | ||
|
||
@abc.abstractmethod | ||
def remove_watch_file(self, handle) -> bool: | ||
""" | ||
Remove an input file. | ||
This method has no default implementation. | ||
Returns True if the input file exists, False otherwise | ||
""" | ||
|
||
@abc.abstractmethod | ||
def run(self) -> None: | ||
""" | ||
Start the event loop. Exit the loop when any callback raises | ||
an exception. If ExitMainLoop is raised, exit cleanly. | ||
This method has no default implementation. | ||
""" | ||
|
||
@abc.abstractmethod | ||
def watch_file(self, fd: int, callback: Callable[[], typing.Any]): | ||
""" | ||
Call callback() when fd has some data to read. No parameters | ||
are passed to callback. | ||
This method has no default implementation. | ||
Returns a handle that may be passed to remove_watch_file() | ||
fd -- file descriptor to watch for input | ||
callback -- function to call when input is available | ||
""" | ||
|
||
def set_signal_handler( | ||
self, | ||
signum: int, | ||
handler: Callable[[int, FrameType | None], typing.Any] | int | signal.Handlers, | ||
) -> Callable[[int, FrameType | None], typing.Any] | int | signal.Handlers | None: | ||
""" | ||
Sets the signal handler for signal signum. | ||
The default implementation of :meth:`set_signal_handler` | ||
is simply a proxy function that calls :func:`signal.signal()` | ||
and returns the resulting value. | ||
signum -- signal number | ||
handler -- function (taking signum as its single argument), | ||
or `signal.SIG_IGN`, or `signal.SIG_DFL` | ||
""" | ||
return signal.signal(signum, handler) |
Oops, something went wrong.