Program hang with asyncio
<p>Here is my code:</p>

<pre><code>import asyncio, socket

sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
sock.bind(('', 1234))
sock.setblocking(False)

queue = asyncio.Queue()

def sock_reader():
    print(sock.recv(1024))
    # x = yield from queue

def test_sock_reader():
    sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    sock.sendto(b'HELLO', ('127.0.0.1', 1234))

loop = asyncio.get_event_loop()
loop.add_reader(sock, sock_reader)
loop.call_later(0.5, test_sock_reader)
loop.run_forever()
loop.close()
</code></pre>

<p>This is the output:</p>

<pre><code>b'HELLO'
</code></pre>

<blockquote>
  <p>When the line <code># x = yield from queue</code> is uncommented the program is not printing <code>b'Hello'</code> anymore.</p>
</blockquote>

<p>Why is the <code>yield from</code> affecting a command that should already be <strong>executed</strong>?</p>

<p>The problem is a combination of syntax and API definition.</p>

<p>First of, refer to the <a href="https://docs.python.org/3/library/asyncio-eventloop.html#asyncio.AbstractEventLoop.add_reader">documentation of <code>add_reader</code></a>, which states that it expects a <em>callback</em>. It is not obvious from the word itself, but by saying <em>callback</em> it means a regular function.</p>

<p>Now, when you uncomment the <code># x = yield from queue</code> line, your <code>sock_reader</code> function actually becomes a generator/coroutine due to <code>yield from</code>, in which case when called like a regular function (i.e. <code>sock_reader(...)</code>), it returns a generator object, and does not get executed.</p>

python python-3.5 python-asyncio