异步案例

uvloop

windows 不支持
是asyncio 的事件循环的替代方案。 事件循环 > 默认asyncio的事件循环(性能更高)。

pip install uvloop

import asyncio
import uvloop
asyncio.set_event_loop_policy(uvloop.EventLoopPolicy())
# 编写asyncio的代码,与之前写的代码一致。

# 内部的事件循环自动化会变成uvloop
asyncio.run()

注意: 一个asgi -> uvicorn 内部使用的就是uvloop

异步操作redis

再通过python代码操作redis时,链接、操作、断开都是网络IO。

# aioredis 1.3.1 之前
pip install aioredis==1.3.1

示例一

import aioredis
import asyncio


async def execute(address, password):
    print("开始执行,", address)
    # 网络IO操作,创建redis链接
    redis = await aioredis.create_redis(address, password=password)

    # 网络IO操作:在redis中设置哈希值car,内部在设三个键值对,即 redis = {car:{key1:1,key2:2,key3:3}}
    await redis.hmset_dict('car', key1=1, key2=2, key3=3)

    # 网络IO操作:去redis中获取值
    result = await redis.hgetall('car', encoding='utf-8')
    print(result)

    redis.close()

    # 网络IO操作:关闭redis连接
    await redis.wait_closed()

    print("结束", address)


asyncio.run(execute("redis://127.0.0.1:6379", None))

示例二

import aioredis
import asyncio


async def execute(address, password):
    print("开始执行,", address)
    # 网络IO操作,创建redis链接
    redis = await aioredis.create_redis(address, password=password)

    # 网络IO操作:在redis中设置哈希值car,内部在设三个键值对,即 redis = {car:{key1:1,key2:2,key3:3}}
    await redis.hmset_dict('car', key1=1, key2=2, key3=3)

    # 网络IO操作:去redis中获取值
    result = await redis.hgetall('car', encoding='utf-8')
    print(result)

    redis.close()

    # 网络IO操作:关闭redis连接
    await redis.wait_closed()

    print("结束", address)


task_list = [
    execute("redis://127.0.0.1:6379", None),
    execute("redis://127.0.0.1:6379", None)
]
if __name__ == '__main__':
    asyncio.run(asyncio.wait(task_list))

异步Mysql

pip install aiomysql

示例一

import asyncio
import aiomysql


async def execute():
    # 网络IO操作,链接mysql
    conn = await aiomysql.connect(host="127.0.0.1", port=3306, user='root', password="123456",db="mysql")

    # 网络IO操作:创建cursor
    cur = await conn.cursor()

    # 网络IO操作:执行mysql
    await cur.execute("select Host,user from user")

    # 网络IO操作:获取SQL结果
    result = await cur.fetchall()
    print(result)

    # 网络IO操作:关闭链接
    await cur.close()
    conn.close()


asyncio.run(execute())

示例二

import asyncio
import aiomysql


async def execute(host, password):
    print("开始了:",host)
    # 网络IO操作,链接mysql
    conn = await aiomysql.connect(host=host, port=3306, user='root', password=password, db="mysql")

    # 网络IO操作:创建cursor
    cur = await conn.cursor()

    # 网络IO操作:执行mysql
    await cur.execute("select Host,user from user")

    # 网络IO操作:获取SQL结果
    result = await cur.fetchall()
    print(result)

    # 网络IO操作:关闭链接
    await cur.close()
    conn.close()


task_list = [
    execute("127.0.0.1", '123456'),
    execute("127.0.0.1", '123456')
]
asyncio.run(asyncio.wait(task_list))

FastAPI 框架

pip install fastapi
pip install uvicorn (aswi内部基于uvloop)

示例一

import asyncio
import uvicorn

from fastapi import FastAPI

app = FastAPI()


@app.get('/')
def index():
    """普通接口操作"""
    return {"message": "Hello World"}


if __name__ == '__main__':
    uvicorn.run("now:app", host="127.0.0.1", port=8002, log_level="info")

爬虫

pip install aiohttp

import aiohttp
import asyncio


async def fetch(session, url):
    print("发送请求:", url)
    async with session.get(url,verify_ssl=False) as response:
        text = await response.text()
        print("得到结果:", url, text,len(text))
        return text
async def main():
    async with aiohttp.ClientSession() as session:
        url_list = [
            "https://cn.bing.com/",
            "https://www.aiqumi.com/",
            "https://www.baidu.com/"
        ]
        tasks = [ asyncio.create_task( fetch(session,url)) for url in url_list]

        done, pending = await asyncio.wait(tasks)


if __name__ == '__main__':
    asyncio.run(main())


总结

最大的意义:通过一个线程利用其IO等待事件去做一些其他事情

posted @ 2022-03-15 12:35  辻渃。  阅读(150)  评论(0)    收藏  举报