コード例 #1
0
ファイル: __init__.py プロジェクト: thesamesam/portage
def _safe_loop():
    """
    Return an event loop that's safe to use within the current context.
    For portage internal callers or external API consumers calling from
    the main thread, this returns a globally shared event loop instance.

    For external API consumers calling from a non-main thread, an
    asyncio loop must be registered for the current thread, or else the
    asyncio.get_event_loop() function will raise an error like this:

      RuntimeError: There is no current event loop in thread 'Thread-1'.

    In order to avoid this RuntimeError, a loop will be automatically
    created like this:

      asyncio.set_event_loop(asyncio.new_event_loop())

    In order to avoid a ResourceWarning, automatically created loops
    are added to a WeakValueDictionary, and closed via an atexit hook
    if they still exist during exit for the current pid.

    @rtype: asyncio.AbstractEventLoop (or compatible)
    @return: event loop instance
    """
    loop = _get_running_loop()
    if loop is not None:
        return loop

    thread_key = threading.get_ident()
    with _thread_weakrefs.lock:
        if _thread_weakrefs.pid != portage.getpid():
            _thread_weakrefs.pid = portage.getpid()
            _thread_weakrefs.mainloop = None
            _thread_weakrefs.loops = weakref.WeakValueDictionary()
        try:
            loop = _thread_weakrefs.loops[thread_key]
        except KeyError:
            try:
                try:
                    _loop = _real_asyncio.get_running_loop()
                except AttributeError:
                    _loop = _real_asyncio.get_event_loop()
            except RuntimeError:
                _loop = _real_asyncio.new_event_loop()
                _real_asyncio.set_event_loop(_loop)
            loop = _thread_weakrefs.loops[thread_key] = _AsyncioEventLoop(loop=_loop)

    if (
        _thread_weakrefs.mainloop is None
        and threading.current_thread() is threading.main_thread()
    ):
        _thread_weakrefs.mainloop = loop

    return loop
コード例 #2
0
ファイル: __init__.py プロジェクト: thesamesam/portage
def _wrap_loop(loop=None):
    """
    In order to deal with asyncio event loop compatibility issues,
    use this function to wrap the loop parameter for functions
    that support it. For example, since python3.4 does not have the
    AbstractEventLoop.create_future() method, this helper function
    can be used to add a wrapper that implements the create_future
    method for python3.4.

    @type loop: asyncio.AbstractEventLoop (or compatible)
    @param loop: event loop
    @rtype: asyncio.AbstractEventLoop (or compatible)
    @return: event loop
    """
    # The default loop returned by _wrap_loop should be consistent
    # with global_event_loop, in order to avoid accidental registration
    # of callbacks with a loop that is not intended to run.
    loop = loop or _safe_loop()
    return loop if hasattr(loop, "_asyncio_wrapper") else _AsyncioEventLoop(loop=loop)
コード例 #3
0
ファイル: __init__.py プロジェクト: yangfl/portage
	def _wrap_loop(loop=None):
		loop = loop or _global_event_loop()
		return (loop if hasattr(loop, '_asyncio_wrapper')
			else _AsyncioEventLoop(loop=loop))