summaryrefslogtreecommitdiff
path: root/devdocs/python~3.12/library%2Fasyncio-stream.html
diff options
context:
space:
mode:
authorCraig Jennings <c@cjennings.net>2024-04-07 13:41:34 -0500
committerCraig Jennings <c@cjennings.net>2024-04-07 13:41:34 -0500
commit754bbf7a25a8dda49b5d08ef0d0443bbf5af0e36 (patch)
treef1190704f78f04a2b0b4c977d20fe96a828377f1 /devdocs/python~3.12/library%2Fasyncio-stream.html
new repository
Diffstat (limited to 'devdocs/python~3.12/library%2Fasyncio-stream.html')
-rw-r--r--devdocs/python~3.12/library%2Fasyncio-stream.html216
1 files changed, 216 insertions, 0 deletions
diff --git a/devdocs/python~3.12/library%2Fasyncio-stream.html b/devdocs/python~3.12/library%2Fasyncio-stream.html
new file mode 100644
index 00000000..e81896ca
--- /dev/null
+++ b/devdocs/python~3.12/library%2Fasyncio-stream.html
@@ -0,0 +1,216 @@
+ <span id="asyncio-streams"></span><h1>Streams</h1> <p><strong>Source code:</strong> <a class="reference external" href="https://github.com/python/cpython/tree/3.12/Lib/asyncio/streams.py">Lib/asyncio/streams.py</a></p> <p>Streams are high-level async/await-ready primitives to work with network connections. Streams allow sending and receiving data without using callbacks or low-level protocols and transports.</p> <p id="asyncio-example-stream">Here is an example of a TCP echo client written using asyncio streams:</p> <pre data-language="python">import asyncio
+
+async def tcp_echo_client(message):
+ reader, writer = await asyncio.open_connection(
+ '127.0.0.1', 8888)
+
+ print(f'Send: {message!r}')
+ writer.write(message.encode())
+ await writer.drain()
+
+ data = await reader.read(100)
+ print(f'Received: {data.decode()!r}')
+
+ print('Close the connection')
+ writer.close()
+ await writer.wait_closed()
+
+asyncio.run(tcp_echo_client('Hello World!'))
+</pre> <p>See also the <a class="reference internal" href="#examples">Examples</a> section below.</p> <h4 class="rubric">Stream Functions</h4> <p>The following top-level asyncio functions can be used to create and work with streams:</p> <dl class="py function"> <dt class="sig sig-object py" id="asyncio.open_connection">
+<code>coroutine asyncio.open_connection(host=None, port=None, *, limit=None, ssl=None, family=0, proto=0, flags=0, sock=None, local_addr=None, server_hostname=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None, happy_eyeballs_delay=None, interleave=None)</code> </dt> <dd>
+<p>Establish a network connection and return a pair of <code>(reader, writer)</code> objects.</p> <p>The returned <em>reader</em> and <em>writer</em> objects are instances of <a class="reference internal" href="#asyncio.StreamReader" title="asyncio.StreamReader"><code>StreamReader</code></a> and <a class="reference internal" href="#asyncio.StreamWriter" title="asyncio.StreamWriter"><code>StreamWriter</code></a> classes.</p> <p><em>limit</em> determines the buffer size limit used by the returned <a class="reference internal" href="#asyncio.StreamReader" title="asyncio.StreamReader"><code>StreamReader</code></a> instance. By default the <em>limit</em> is set to 64 KiB.</p> <p>The rest of the arguments are passed directly to <a class="reference internal" href="asyncio-eventloop#asyncio.loop.create_connection" title="asyncio.loop.create_connection"><code>loop.create_connection()</code></a>.</p> <div class="admonition note"> <p class="admonition-title">Note</p> <p>The <em>sock</em> argument transfers ownership of the socket to the <a class="reference internal" href="#asyncio.StreamWriter" title="asyncio.StreamWriter"><code>StreamWriter</code></a> created. To close the socket, call its <a class="reference internal" href="#asyncio.StreamWriter.close" title="asyncio.StreamWriter.close"><code>close()</code></a> method.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.7: </span>Added the <em>ssl_handshake_timeout</em> parameter.</p> </div> <div class="versionadded"> <p><span class="versionmodified added">New in version 3.8: </span>Added <em>happy_eyeballs_delay</em> and <em>interleave</em> parameters.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.10: </span>Removed the <em>loop</em> parameter.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.11: </span>Added the <em>ssl_shutdown_timeout</em> parameter.</p> </div> </dd>
+</dl> <dl class="py function"> <dt class="sig sig-object py" id="asyncio.start_server">
+<code>coroutine asyncio.start_server(client_connected_cb, host=None, port=None, *, limit=None, family=socket.AF_UNSPEC, flags=socket.AI_PASSIVE, sock=None, backlog=100, ssl=None, reuse_address=None, reuse_port=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None, start_serving=True)</code> </dt> <dd>
+<p>Start a socket server.</p> <p>The <em>client_connected_cb</em> callback is called whenever a new client connection is established. It receives a <code>(reader, writer)</code> pair as two arguments, instances of the <a class="reference internal" href="#asyncio.StreamReader" title="asyncio.StreamReader"><code>StreamReader</code></a> and <a class="reference internal" href="#asyncio.StreamWriter" title="asyncio.StreamWriter"><code>StreamWriter</code></a> classes.</p> <p><em>client_connected_cb</em> can be a plain callable or a <a class="reference internal" href="asyncio-task#coroutine"><span class="std std-ref">coroutine function</span></a>; if it is a coroutine function, it will be automatically scheduled as a <a class="reference internal" href="asyncio-task#asyncio.Task" title="asyncio.Task"><code>Task</code></a>.</p> <p><em>limit</em> determines the buffer size limit used by the returned <a class="reference internal" href="#asyncio.StreamReader" title="asyncio.StreamReader"><code>StreamReader</code></a> instance. By default the <em>limit</em> is set to 64 KiB.</p> <p>The rest of the arguments are passed directly to <a class="reference internal" href="asyncio-eventloop#asyncio.loop.create_server" title="asyncio.loop.create_server"><code>loop.create_server()</code></a>.</p> <div class="admonition note"> <p class="admonition-title">Note</p> <p>The <em>sock</em> argument transfers ownership of the socket to the server created. To close the socket, call the server’s <a class="reference internal" href="asyncio-eventloop#asyncio.Server.close" title="asyncio.Server.close"><code>close()</code></a> method.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.7: </span>Added the <em>ssl_handshake_timeout</em> and <em>start_serving</em> parameters.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.10: </span>Removed the <em>loop</em> parameter.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.11: </span>Added the <em>ssl_shutdown_timeout</em> parameter.</p> </div> </dd>
+</dl> <h4 class="rubric">Unix Sockets</h4> <dl class="py function"> <dt class="sig sig-object py" id="asyncio.open_unix_connection">
+<code>coroutine asyncio.open_unix_connection(path=None, *, limit=None, ssl=None, sock=None, server_hostname=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None)</code> </dt> <dd> <p>Establish a Unix socket connection and return a pair of <code>(reader, writer)</code>.</p> <p>Similar to <a class="reference internal" href="#asyncio.open_connection" title="asyncio.open_connection"><code>open_connection()</code></a> but operates on Unix sockets.</p> <p>See also the documentation of <a class="reference internal" href="asyncio-eventloop#asyncio.loop.create_unix_connection" title="asyncio.loop.create_unix_connection"><code>loop.create_unix_connection()</code></a>.</p> <div class="admonition note"> <p class="admonition-title">Note</p> <p>The <em>sock</em> argument transfers ownership of the socket to the <a class="reference internal" href="#asyncio.StreamWriter" title="asyncio.StreamWriter"><code>StreamWriter</code></a> created. To close the socket, call its <a class="reference internal" href="#asyncio.StreamWriter.close" title="asyncio.StreamWriter.close"><code>close()</code></a> method.</p> </div> <div class="availability docutils container"> <p><a class="reference internal" href="https://docs.python.org/3.12/library/intro.html#availability"><span class="std std-ref">Availability</span></a>: Unix.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.7: </span>Added the <em>ssl_handshake_timeout</em> parameter. The <em>path</em> parameter can now be a <a class="reference internal" href="../glossary#term-path-like-object"><span class="xref std std-term">path-like object</span></a></p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.10: </span>Removed the <em>loop</em> parameter.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.11: </span>Added the <em>ssl_shutdown_timeout</em> parameter.</p> </div> </dd>
+</dl> <dl class="py function"> <dt class="sig sig-object py" id="asyncio.start_unix_server">
+<code>coroutine asyncio.start_unix_server(client_connected_cb, path=None, *, limit=None, sock=None, backlog=100, ssl=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None, start_serving=True)</code> </dt> <dd>
+<p>Start a Unix socket server.</p> <p>Similar to <a class="reference internal" href="#asyncio.start_server" title="asyncio.start_server"><code>start_server()</code></a> but works with Unix sockets.</p> <p>See also the documentation of <a class="reference internal" href="asyncio-eventloop#asyncio.loop.create_unix_server" title="asyncio.loop.create_unix_server"><code>loop.create_unix_server()</code></a>.</p> <div class="admonition note"> <p class="admonition-title">Note</p> <p>The <em>sock</em> argument transfers ownership of the socket to the server created. To close the socket, call the server’s <a class="reference internal" href="asyncio-eventloop#asyncio.Server.close" title="asyncio.Server.close"><code>close()</code></a> method.</p> </div> <div class="availability docutils container"> <p><a class="reference internal" href="https://docs.python.org/3.12/library/intro.html#availability"><span class="std std-ref">Availability</span></a>: Unix.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.7: </span>Added the <em>ssl_handshake_timeout</em> and <em>start_serving</em> parameters. The <em>path</em> parameter can now be a <a class="reference internal" href="../glossary#term-path-like-object"><span class="xref std std-term">path-like object</span></a>.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.10: </span>Removed the <em>loop</em> parameter.</p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.11: </span>Added the <em>ssl_shutdown_timeout</em> parameter.</p> </div> </dd>
+</dl> <section id="streamreader"> <h2>StreamReader</h2> <dl class="py class"> <dt class="sig sig-object py" id="asyncio.StreamReader">
+<code>class asyncio.StreamReader</code> </dt> <dd>
+<p>Represents a reader object that provides APIs to read data from the IO stream. As an <a class="reference internal" href="../glossary#term-asynchronous-iterable"><span class="xref std std-term">asynchronous iterable</span></a>, the object supports the <a class="reference internal" href="../reference/compound_stmts#async-for"><code>async for</code></a> statement.</p> <p>It is not recommended to instantiate <em>StreamReader</em> objects directly; use <a class="reference internal" href="#asyncio.open_connection" title="asyncio.open_connection"><code>open_connection()</code></a> and <a class="reference internal" href="#asyncio.start_server" title="asyncio.start_server"><code>start_server()</code></a> instead.</p> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamReader.feed_eof">
+<code>feed_eof()</code> </dt> <dd>
+<p>Acknowledge the EOF.</p> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamReader.read">
+<code>coroutine read(n=- 1)</code> </dt> <dd>
+<p>Read up to <em>n</em> bytes from the stream.</p> <p>If <em>n</em> is not provided or set to <code>-1</code>, read until EOF, then return all read <a class="reference internal" href="stdtypes#bytes" title="bytes"><code>bytes</code></a>. If EOF was received and the internal buffer is empty, return an empty <code>bytes</code> object.</p> <p>If <em>n</em> is <code>0</code>, return an empty <code>bytes</code> object immediately.</p> <p>If <em>n</em> is positive, return at most <em>n</em> available <code>bytes</code> as soon as at least 1 byte is available in the internal buffer. If EOF is received before any byte is read, return an empty <code>bytes</code> object.</p> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamReader.readline">
+<code>coroutine readline()</code> </dt> <dd>
+<p>Read one line, where “line” is a sequence of bytes ending with <code>\n</code>.</p> <p>If EOF is received and <code>\n</code> was not found, the method returns partially read data.</p> <p>If EOF is received and the internal buffer is empty, return an empty <code>bytes</code> object.</p> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamReader.readexactly">
+<code>coroutine readexactly(n)</code> </dt> <dd>
+<p>Read exactly <em>n</em> bytes.</p> <p>Raise an <a class="reference internal" href="asyncio-exceptions#asyncio.IncompleteReadError" title="asyncio.IncompleteReadError"><code>IncompleteReadError</code></a> if EOF is reached before <em>n</em> can be read. Use the <a class="reference internal" href="asyncio-exceptions#asyncio.IncompleteReadError.partial" title="asyncio.IncompleteReadError.partial"><code>IncompleteReadError.partial</code></a> attribute to get the partially read data.</p> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamReader.readuntil">
+<code>coroutine readuntil(separator=b'\n')</code> </dt> <dd>
+<p>Read data from the stream until <em>separator</em> is found.</p> <p>On success, the data and separator will be removed from the internal buffer (consumed). Returned data will include the separator at the end.</p> <p>If the amount of data read exceeds the configured stream limit, a <a class="reference internal" href="asyncio-exceptions#asyncio.LimitOverrunError" title="asyncio.LimitOverrunError"><code>LimitOverrunError</code></a> exception is raised, and the data is left in the internal buffer and can be read again.</p> <p>If EOF is reached before the complete separator is found, an <a class="reference internal" href="asyncio-exceptions#asyncio.IncompleteReadError" title="asyncio.IncompleteReadError"><code>IncompleteReadError</code></a> exception is raised, and the internal buffer is reset. The <a class="reference internal" href="asyncio-exceptions#asyncio.IncompleteReadError.partial" title="asyncio.IncompleteReadError.partial"><code>IncompleteReadError.partial</code></a> attribute may contain a portion of the separator.</p> <div class="versionadded"> <p><span class="versionmodified added">New in version 3.5.2.</span></p> </div> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamReader.at_eof">
+<code>at_eof()</code> </dt> <dd>
+<p>Return <code>True</code> if the buffer is empty and <a class="reference internal" href="#asyncio.StreamReader.feed_eof" title="asyncio.StreamReader.feed_eof"><code>feed_eof()</code></a> was called.</p> </dd>
+</dl> </dd>
+</dl> </section> <section id="streamwriter"> <h2>StreamWriter</h2> <dl class="py class"> <dt class="sig sig-object py" id="asyncio.StreamWriter">
+<code>class asyncio.StreamWriter</code> </dt> <dd>
+<p>Represents a writer object that provides APIs to write data to the IO stream.</p> <p>It is not recommended to instantiate <em>StreamWriter</em> objects directly; use <a class="reference internal" href="#asyncio.open_connection" title="asyncio.open_connection"><code>open_connection()</code></a> and <a class="reference internal" href="#asyncio.start_server" title="asyncio.start_server"><code>start_server()</code></a> instead.</p> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.write">
+<code>write(data)</code> </dt> <dd>
+<p>The method attempts to write the <em>data</em> to the underlying socket immediately. If that fails, the data is queued in an internal write buffer until it can be sent.</p> <p>The method should be used along with the <code>drain()</code> method:</p> <pre data-language="python">stream.write(data)
+await stream.drain()
+</pre> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.writelines">
+<code>writelines(data)</code> </dt> <dd>
+<p>The method writes a list (or any iterable) of bytes to the underlying socket immediately. If that fails, the data is queued in an internal write buffer until it can be sent.</p> <p>The method should be used along with the <code>drain()</code> method:</p> <pre data-language="python">stream.writelines(lines)
+await stream.drain()
+</pre> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.close">
+<code>close()</code> </dt> <dd>
+<p>The method closes the stream and the underlying socket.</p> <p>The method should be used, though not mandatory, along with the <code>wait_closed()</code> method:</p> <pre data-language="python">stream.close()
+await stream.wait_closed()
+</pre> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.can_write_eof">
+<code>can_write_eof()</code> </dt> <dd>
+<p>Return <code>True</code> if the underlying transport supports the <a class="reference internal" href="#asyncio.StreamWriter.write_eof" title="asyncio.StreamWriter.write_eof"><code>write_eof()</code></a> method, <code>False</code> otherwise.</p> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.write_eof">
+<code>write_eof()</code> </dt> <dd>
+<p>Close the write end of the stream after the buffered write data is flushed.</p> </dd>
+</dl> <dl class="py attribute"> <dt class="sig sig-object py" id="asyncio.StreamWriter.transport">
+<code>transport</code> </dt> <dd>
+<p>Return the underlying asyncio transport.</p> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.get_extra_info">
+<code>get_extra_info(name, default=None)</code> </dt> <dd>
+<p>Access optional transport information; see <a class="reference internal" href="asyncio-protocol#asyncio.BaseTransport.get_extra_info" title="asyncio.BaseTransport.get_extra_info"><code>BaseTransport.get_extra_info()</code></a> for details.</p> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.drain">
+<code>coroutine drain()</code> </dt> <dd>
+<p>Wait until it is appropriate to resume writing to the stream. Example:</p> <pre data-language="python">writer.write(data)
+await writer.drain()
+</pre> <p>This is a flow control method that interacts with the underlying IO write buffer. When the size of the buffer reaches the high watermark, <em>drain()</em> blocks until the size of the buffer is drained down to the low watermark and writing can be resumed. When there is nothing to wait for, the <a class="reference internal" href="#asyncio.StreamWriter.drain" title="asyncio.StreamWriter.drain"><code>drain()</code></a> returns immediately.</p> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.start_tls">
+<code>coroutine start_tls(sslcontext, \*, server_hostname=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None)</code> </dt> <dd>
+<p>Upgrade an existing stream-based connection to TLS.</p> <p>Parameters:</p> <ul class="simple"> <li>
+<em>sslcontext</em>: a configured instance of <a class="reference internal" href="ssl#ssl.SSLContext" title="ssl.SSLContext"><code>SSLContext</code></a>.</li> <li>
+<em>server_hostname</em>: sets or overrides the host name that the target server’s certificate will be matched against.</li> <li>
+<em>ssl_handshake_timeout</em> is the time in seconds to wait for the TLS handshake to complete before aborting the connection. <code>60.0</code> seconds if <code>None</code> (default).</li> <li>
+<em>ssl_shutdown_timeout</em> is the time in seconds to wait for the SSL shutdown to complete before aborting the connection. <code>30.0</code> seconds if <code>None</code> (default).</li> </ul> <div class="versionadded"> <p><span class="versionmodified added">New in version 3.11.</span></p> </div> <div class="versionchanged"> <p><span class="versionmodified changed">Changed in version 3.12: </span>Added the <em>ssl_shutdown_timeout</em> parameter.</p> </div> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.is_closing">
+<code>is_closing()</code> </dt> <dd>
+<p>Return <code>True</code> if the stream is closed or in the process of being closed.</p> <div class="versionadded"> <p><span class="versionmodified added">New in version 3.7.</span></p> </div> </dd>
+</dl> <dl class="py method"> <dt class="sig sig-object py" id="asyncio.StreamWriter.wait_closed">
+<code>coroutine wait_closed()</code> </dt> <dd>
+<p>Wait until the stream is closed.</p> <p>Should be called after <a class="reference internal" href="#asyncio.StreamWriter.close" title="asyncio.StreamWriter.close"><code>close()</code></a> to wait until the underlying connection is closed, ensuring that all data has been flushed before e.g. exiting the program.</p> <div class="versionadded"> <p><span class="versionmodified added">New in version 3.7.</span></p> </div> </dd>
+</dl> </dd>
+</dl> </section> <section id="examples"> <h2>Examples</h2> <section id="tcp-echo-client-using-streams"> <span id="asyncio-tcp-echo-client-streams"></span><h3>TCP echo client using streams</h3> <p>TCP echo client using the <a class="reference internal" href="#asyncio.open_connection" title="asyncio.open_connection"><code>asyncio.open_connection()</code></a> function:</p> <pre data-language="python">import asyncio
+
+async def tcp_echo_client(message):
+ reader, writer = await asyncio.open_connection(
+ '127.0.0.1', 8888)
+
+ print(f'Send: {message!r}')
+ writer.write(message.encode())
+ await writer.drain()
+
+ data = await reader.read(100)
+ print(f'Received: {data.decode()!r}')
+
+ print('Close the connection')
+ writer.close()
+ await writer.wait_closed()
+
+asyncio.run(tcp_echo_client('Hello World!'))
+</pre> <div class="admonition seealso"> <p class="admonition-title">See also</p> <p>The <a class="reference internal" href="asyncio-protocol#asyncio-example-tcp-echo-client-protocol"><span class="std std-ref">TCP echo client protocol</span></a> example uses the low-level <a class="reference internal" href="asyncio-eventloop#asyncio.loop.create_connection" title="asyncio.loop.create_connection"><code>loop.create_connection()</code></a> method.</p> </div> </section> <section id="tcp-echo-server-using-streams"> <span id="asyncio-tcp-echo-server-streams"></span><h3>TCP echo server using streams</h3> <p>TCP echo server using the <a class="reference internal" href="#asyncio.start_server" title="asyncio.start_server"><code>asyncio.start_server()</code></a> function:</p> <pre data-language="python">import asyncio
+
+async def handle_echo(reader, writer):
+ data = await reader.read(100)
+ message = data.decode()
+ addr = writer.get_extra_info('peername')
+
+ print(f"Received {message!r} from {addr!r}")
+
+ print(f"Send: {message!r}")
+ writer.write(data)
+ await writer.drain()
+
+ print("Close the connection")
+ writer.close()
+ await writer.wait_closed()
+
+async def main():
+ server = await asyncio.start_server(
+ handle_echo, '127.0.0.1', 8888)
+
+ addrs = ', '.join(str(sock.getsockname()) for sock in server.sockets)
+ print(f'Serving on {addrs}')
+
+ async with server:
+ await server.serve_forever()
+
+asyncio.run(main())
+</pre> <div class="admonition seealso"> <p class="admonition-title">See also</p> <p>The <a class="reference internal" href="asyncio-protocol#asyncio-example-tcp-echo-server-protocol"><span class="std std-ref">TCP echo server protocol</span></a> example uses the <a class="reference internal" href="asyncio-eventloop#asyncio.loop.create_server" title="asyncio.loop.create_server"><code>loop.create_server()</code></a> method.</p> </div> </section> <section id="get-http-headers"> <h3>Get HTTP headers</h3> <p>Simple example querying HTTP headers of the URL passed on the command line:</p> <pre data-language="python">import asyncio
+import urllib.parse
+import sys
+
+async def print_http_headers(url):
+ url = urllib.parse.urlsplit(url)
+ if url.scheme == 'https':
+ reader, writer = await asyncio.open_connection(
+ url.hostname, 443, ssl=True)
+ else:
+ reader, writer = await asyncio.open_connection(
+ url.hostname, 80)
+
+ query = (
+ f"HEAD {url.path or '/'} HTTP/1.0\r\n"
+ f"Host: {url.hostname}\r\n"
+ f"\r\n"
+ )
+
+ writer.write(query.encode('latin-1'))
+ while True:
+ line = await reader.readline()
+ if not line:
+ break
+
+ line = line.decode('latin1').rstrip()
+ if line:
+ print(f'HTTP header&gt; {line}')
+
+ # Ignore the body, close the socket
+ writer.close()
+ await writer.wait_closed()
+
+url = sys.argv[1]
+asyncio.run(print_http_headers(url))
+</pre> <p>Usage:</p> <pre data-language="python">python example.py http://example.com/path/page.html
+</pre> <p>or with HTTPS:</p> <pre data-language="python">python example.py https://example.com/path/page.html
+</pre> </section> <section id="register-an-open-socket-to-wait-for-data-using-streams"> <span id="asyncio-example-create-connection-streams"></span><h3>Register an open socket to wait for data using streams</h3> <p>Coroutine waiting until a socket receives data using the <a class="reference internal" href="#asyncio.open_connection" title="asyncio.open_connection"><code>open_connection()</code></a> function:</p> <pre data-language="python">import asyncio
+import socket
+
+async def wait_for_data():
+ # Get a reference to the current event loop because
+ # we want to access low-level APIs.
+ loop = asyncio.get_running_loop()
+
+ # Create a pair of connected sockets.
+ rsock, wsock = socket.socketpair()
+
+ # Register the open socket to wait for data.
+ reader, writer = await asyncio.open_connection(sock=rsock)
+
+ # Simulate the reception of data from the network
+ loop.call_soon(wsock.send, 'abc'.encode())
+
+ # Wait for data
+ data = await reader.read(100)
+
+ # Got data, we are done: close the socket
+ print("Received:", data.decode())
+ writer.close()
+ await writer.wait_closed()
+
+ # Close the second socket
+ wsock.close()
+
+asyncio.run(wait_for_data())
+</pre> <div class="admonition seealso"> <p class="admonition-title">See also</p> <p>The <a class="reference internal" href="asyncio-protocol#asyncio-example-create-connection"><span class="std std-ref">register an open socket to wait for data using a protocol</span></a> example uses a low-level protocol and the <a class="reference internal" href="asyncio-eventloop#asyncio.loop.create_connection" title="asyncio.loop.create_connection"><code>loop.create_connection()</code></a> method.</p> <p>The <a class="reference internal" href="asyncio-eventloop#asyncio-example-watch-fd"><span class="std std-ref">watch a file descriptor for read events</span></a> example uses the low-level <a class="reference internal" href="asyncio-eventloop#asyncio.loop.add_reader" title="asyncio.loop.add_reader"><code>loop.add_reader()</code></a> method to watch a file descriptor.</p> </div> </section> </section> <div class="_attribution">
+ <p class="_attribution-p">
+ &copy; 2001&ndash;2023 Python Software Foundation<br>Licensed under the PSF License.<br>
+ <a href="https://docs.python.org/3.12/library/asyncio-stream.html" class="_attribution-link">https://docs.python.org/3.12/library/asyncio-stream.html</a>
+ </p>
+</div>