使用 asyncpg 时如何修复异步代码锁定

如何解决使用 asyncpg 时如何修复异步代码锁定

这是我正在使用的示例代码。我想快速解析页面并将结果数据输入到数据库中。但是,添加一行后,我的代码开始运行速度明显变慢。我了解这与数据库的工作有关。但我不明白如何解决它。

如果您对加速此代码有任何其他建议,我将非常感谢您的帮助。

import asyncpg
import asyncio
import aiohttp
from settings import URI,sql,URLS


class Singleton(type):
    _instances = {}

    def __call__(cls,*args,**kwargs):
        if cls not in cls._instances:
            cls._instances[cls] = super(Singleton,cls).__call__(*args,**kwargs)
        return cls._instances[cls]


class DBManager(Metaclass=Singleton):
    """ Class for interacting with Postgres database """

    def __init__(self,dsn) -> None:
        """ The constructor takes the database """
        self.dsn = dsn
        self.pool = None

    async def connect(self):
        self.pool = await asyncpg.create_pool(dsn=self.dsn)


    async def insert_data(self,peson: str,address: str):
        async with self.pool.acquire() as connect:
            return await connect.execute(sql,type_tx,address)


db = DBManager(URI)


async def check_address(url,session):
    async with session.get(url) as result:
        try:
            result = await result.json()
            person = 'adult' if result['age'] >= 21 else 'child'
            address = result['address']
            await db.insert_data(person,address)
            return print(address,person)
        except Exception as e:
            print(e)


async def bound_fetch(sem,url,session):
    async with sem:
        return await check_address(url,session)


async def main():
    await db.connect()
    urls = [url for i in URLS]
    sem = asyncio.Semaphore(50)
    tasks = []
    async with aiohttp.ClientSession() as session:
        for url in urls:
            task = asyncio.ensure_future(bound_fetch(sem,session))
            tasks.append(task)
        responses = asyncio.gather(*tasks)
        await responses

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

解决方法

等待任务完成很慢。必然地,await 将等待一个任务完成。当不需要等待时,简单地继续而不阻塞您的代码通常是可取的。

正如您所提到的,这一行:await db.insert_data(person,address) 很慢。那是因为它正在等待 db.insert。但是您没有使用此结果,因此您可以省略等待并允许插入异步进行,而不是等待。

你提到了 asynchio,python 文档很好地概述了这个 here

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?
Java在半透明框架/面板/组件上重新绘画。
Java“ Class.forName()”和“ Class.forName()。newInstance()”之间有什么区别?
在此环境中不提供编译器。也许是在JRE而不是JDK上运行?
Java用相同的方法在一个类中实现两个接口。哪种接口方法被覆盖?
Java 什么是Runtime.getRuntime()。totalMemory()和freeMemory()?
java.library.path中的java.lang.UnsatisfiedLinkError否*****。dll
JavaFX“位置是必需的。” 即使在同一包装中
Java 导入两个具有相同名称的类。怎么处理?
Java 是否应该在HttpServletResponse.getOutputStream()/。getWriter()上调用.close()?
Java RegEx元字符(。)和普通点?