asyncio --- bộ lập lịch I/O bất đồng bộ

Mô-đun này cung cấp bộ lập lịch đa nhiệm hợp tác cho các coroutine async/await, cùng với các nguyên thủy để đồng bộ hóa (khóa, sự kiện) và kết nối TCP không chặn qua các luồng đọc và ghi. Các tác vụ chạy đồng thời trên một vòng lặp sự kiện duy nhất; tác vụ đang chạy nhường quyền điều khiển trở lại vòng lặp bằng await.

Ví dụ:

import asyncio

async def blink(led, period_ms):
    while True:
        led.on()
        await asyncio.sleep_ms(5)
        led.off()
        await asyncio.sleep_ms(period_ms)

async def main(led1, led2):
    asyncio.create_task(blink(led1, 700))
    asyncio.create_task(blink(led2, 400))
    await asyncio.sleep_ms(10_000)

# Running on an OpenMV Cam
from machine import LED
asyncio.run(main(LED(1), LED(2)))

Các hàm cốt lõi

asyncio.create_task(coro: Coroutine) Task

Tạo một tác vụ mới từ coroutine đã cho và lên lịch để chạy nó.

Trả về đối tượng Task tương ứng.

asyncio.current_task() Task

Trả về đối tượng Task liên kết với tác vụ đang chạy hiện tại.

asyncio.run(coro: Coroutine) Any

Tạo một tác vụ mới từ coroutine đã cho và chạy nó cho đến khi hoàn thành.

Trả về giá trị được trả về bởi coro.

asyncio.sleep(t: float) None

Ngủ trong t giây (có thể là số thực).

Đây là một coroutine.

asyncio.sleep_ms(t: int) None

Ngủ trong t mili giây.

Đây là một coroutine, và là phần mở rộng của MicroPython.

Các hàm bổ sung

asyncio.wait_for(awaitable: Awaitable, timeout: float) Any

Chờ awaitable hoàn thành, nhưng hủy nó nếu mất hơn timeout giây. Nếu awaitable không phải là tác vụ thì một tác vụ sẽ được tạo từ nó.

Nếu hết thời gian chờ, nó hủy tác vụ và ném asyncio.TimeoutError: ngoại lệ này phải được bắt bởi hàm gọi. Tác vụ nhận được asyncio.CancelledError, có thể bỏ qua hoặc bắt bằng try...except hoặc try...finally để chạy mã dọn dẹp.

Trả về giá trị trả về của awaitable.

Đây là một coroutine.

asyncio.wait_for_ms(awaitable: Awaitable, timeout: int) Any

Tương tự wait_for() nhưng timeout là số nguyên tính bằng mili giây.

Đây là một coroutine, và là phần mở rộng của MicroPython.

asyncio.gather(*awaitables, return_exceptions: bool = False) List

Chạy đồng thời tất cả awaitables. Bất kỳ awaitables nào không phải là tác vụ đều được nâng cấp thành tác vụ.

Trả về danh sách giá trị trả về của tất cả awaitables.

Đây là một coroutine.

class Task

class asyncio.Task

Đối tượng này bọc một coroutine vào một tác vụ đang chạy. Các tác vụ có thể được chờ bằng await task, điều này sẽ chờ tác vụ hoàn thành và trả về giá trị trả về của tác vụ.

Không nên tạo tác vụ trực tiếp, thay vào đó hãy sử dụng create_task() để tạo chúng.

cancel() None

Hủy tác vụ bằng cách chèn asyncio.CancelledError vào nó. Tác vụ có thể bỏ qua ngoại lệ này. Mã dọn dẹp có thể được chạy bằng cách bắt ngoại lệ, hoặc qua try ... finally.

class Event

class asyncio.Event

Tạo một sự kiện mới có thể được dùng để đồng bộ hóa các tác vụ. Các sự kiện bắt đầu ở trạng thái đã xóa.

is_set() bool

Trả về True nếu sự kiện được thiết lập, False ngược lại.

set() None

Thiết lập sự kiện. Bất kỳ tác vụ nào đang chờ sự kiện sẽ được lên lịch để chạy.

Lưu ý: Hàm này phải được gọi từ bên trong một tác vụ. Không an toàn khi gọi từ IRQ, hàm gọi lại của bộ lập lịch, hay luồng khác. Xem ThreadSafeFlag.

clear() None

Xóa sự kiện.

wait() None

Chờ sự kiện được thiết lập. Nếu sự kiện đã được thiết lập thì trả về ngay lập tức.

Đây là một coroutine.

class ThreadSafeFlag

class asyncio.ThreadSafeFlag

Tạo một cờ mới có thể được dùng để đồng bộ hóa một tác vụ với mã chạy bên ngoài vòng lặp asyncio, chẳng hạn như các luồng khác, IRQ, hoặc hàm gọi lại của bộ lập lịch. Các cờ bắt đầu ở trạng thái đã xóa.

set() None

Thiết lập cờ. Nếu có một tác vụ đang chờ cờ, tác vụ đó sẽ được lên lịch để chạy.

clear() None

Xóa cờ. Điều này có thể được dùng để đảm bảo rằng một cờ có thể đã được thiết lập trước đó đã được xóa trước khi chờ nó.

wait() None

Chờ cờ được thiết lập. Nếu cờ đã được thiết lập thì trả về ngay lập tức. Cờ tự động được đặt lại khi trả về từ wait.

Mỗi thời điểm chỉ có một tác vụ có thể chờ một cờ.

Đây là một coroutine.

class Lock

class asyncio.Lock

Tạo một khóa mới có thể được dùng để phối hợp các tác vụ. Các khóa bắt đầu ở trạng thái mở khóa.

Ngoài các phương thức bên dưới, các khóa có thể được sử dụng trong câu lệnh async with.

locked() bool

Trả về True nếu khóa đang bị khóa, ngược lại trả về False.

acquire() bool

Chờ khóa ở trạng thái mở khóa rồi khóa nó theo cách nguyên tử. Chỉ một tác vụ có thể giành được khóa tại bất kỳ thời điểm nào.

Đây là một coroutine.

release() None

Giải phóng khóa. Nếu có tác vụ nào đang chờ khóa thì tác vụ tiếp theo trong hàng đợi được lên lịch để chạy và khóa vẫn ở trạng thái bị khóa. Ngược lại, không có tác vụ nào đang chờ và khóa trở thành trạng thái mở khóa.

Kết nối luồng TCP

asyncio.open_connection(host: str, port: int, ssl: ssl.SSLContext | bool | None = None) Tuple[Stream, Stream]

Mở kết nối TCP tới hostport đã cho. Địa chỉ host sẽ được phân giải bằng socket.getaddrinfo(), hiện tại là một lệnh gọi chặn. Nếu ssl là đối tượng ssl.SSLContext, ngữ cảnh này được dùng để tạo transport; nếu sslTrue, một ngữ cảnh mặc định được sử dụng.

Trả về một cặp luồng: luồng đọc và luồng ghi. Sẽ ném OSError cụ thể theo socket nếu không thể phân giải host hoặc không thể thực hiện kết nối.

Đây là một coroutine.

asyncio.start_server(callback: Callable, host: str, port: int, backlog: int = 5, ssl: ssl.SSLContext | None = None) Server

Khởi động máy chủ TCP trên hostport đã cho. callback sẽ được gọi với các kết nối đến được chấp nhận, và được truyền 2 đối số: luồng đọc và ghi cho kết nối.

Nếu ssl là đối tượng ssl.SSLContext, ngữ cảnh này được dùng để tạo transport.

Trả về đối tượng Server.

Đây là một coroutine.

class asyncio.Stream

Đây đại diện cho một kết nối luồng TCP. Để tối giản mã, lớp này triển khai cả đọc và ghi, và cả StreamReader lẫn StreamWriter đều là bí danh cho lớp này.

get_extra_info(v: str) Any

Lấy thêm thông tin về luồng, được cho bởi v. Các giá trị hợp lệ cho v là: peername.

close() None

Đóng luồng.

wait_closed() None

Chờ luồng đóng.

Đây là một coroutine.

read(n: int = -1) bytes

Đọc tối đa n byte và trả về chúng. Nếu n không được cung cấp hoặc là -1 thì đọc tất cả byte cho đến EOF. Giá trị trả về sẽ là đối tượng bytes rỗng nếu gặp EOF trước khi đọc được byte nào.

Đây là một coroutine.

readinto(buf: bytearray | memoryview) int

Đọc tối đa n byte vào buf với n bằng độ dài của buf.

Trả về số byte đã đọc vào buf.

Đây là một coroutine, và là phần mở rộng của MicroPython.

readexactly(n: int) bytes

Đọc chính xác n byte và trả về chúng dưới dạng đối tượng bytes.

Ném ngoại lệ EOFError nếu luồng kết thúc trước khi đọc đủ n byte.

Đây là một coroutine.

readline() bytes

Đọc một dòng và trả về nó.

Đây là một coroutine.

write(buf: bytes) None

Tích lũy buf vào bộ đệm đầu ra. Dữ liệu chỉ được xả khi Stream.drain() được gọi. Khuyến nghị gọi Stream.drain() ngay sau khi gọi hàm này.

drain() None

Xả (ghi) tất cả dữ liệu đầu ra đã được đệm ra luồng.

Đây là một coroutine.

class asyncio.Server

Đây đại diện cho lớp máy chủ được trả về từ start_server(). Nó có thể được dùng trong câu lệnh async with để đóng máy chủ khi thoát.

close() None

Đóng máy chủ.

wait_closed() None

Chờ máy chủ đóng.

Đây là một coroutine.

Vòng lặp sự kiện

asyncio.get_event_loop() Loop

Trả về vòng lặp sự kiện được dùng để lên lịch và chạy các tác vụ. Xem Loop.

asyncio.new_event_loop() Loop

Đặt lại vòng lặp sự kiện và trả về nó.

Lưu ý: vì MicroPython chỉ có một vòng lặp sự kiện duy nhất, hàm này chỉ đặt lại trạng thái của vòng lặp, không tạo mới.

class asyncio.Loop

Đây đại diện cho đối tượng lên lịch và chạy các tác vụ. Không thể tạo trực tiếp, hãy sử dụng get_event_loop() thay thế.

create_task(coro: Coroutine) Task

Tạo một tác vụ từ coro đã cho và trả về đối tượng Task mới.

run_forever() None

Chạy vòng lặp sự kiện cho đến khi stop() được gọi.

run_until_complete(awaitable: Awaitable) Any

Chạy awaitable đã cho cho đến khi hoàn thành. Nếu awaitable không phải là tác vụ thì nó sẽ được nâng cấp thành một tác vụ.

stop() None

Dừng vòng lặp sự kiện.

close() None

Đóng vòng lặp sự kiện.

set_exception_handler(handler: Callable) None

Đặt trình xử lý ngoại lệ để gọi khi một Task ném ngoại lệ không được bắt. handler phải chấp nhận hai đối số: (loop, context).

get_exception_handler() Callable | None

Lấy trình xử lý ngoại lệ hiện tại. Trả về trình xử lý, hoặc None nếu không có trình xử lý tùy chỉnh nào được đặt.

default_exception_handler(context: dict) None

Trình xử lý ngoại lệ mặc định được gọi.

call_exception_handler(context: dict) None

Gọi trình xử lý ngoại lệ hiện tại. Đối số context được truyền qua và là một từ điển chứa các khóa: 'message', 'exception', 'future'.