Python 3.x 异步套接字.send()异常

Python 3.x 异步套接字.send()异常,python-3.x,asynchronous,boto3,python-asyncio,Python 3.x,Asynchronous,Boto3,Python Asyncio,您好,我的异步循环有以下内容 async def start_process(restore_items, args, loop): with GlacierRestorer(args.temp_dir, args.error_log_bucket, loop) as restorer: restorer.initiate_restore_all(restore_items) tasks = [] semaphore = asyncio

您好,我的异步循环有以下内容

 async def start_process(restore_items, args, loop):
    with GlacierRestorer(args.temp_dir, args.error_log_bucket, loop) as restorer:
        restorer.initiate_restore_all(restore_items)

        tasks = []
        semaphore = asyncio.BoundedSemaphore(4)
        for item in restore_items:
            tasks.append(asyncio.ensure_future(restorer.transfer(item, semaphore)))
        await asyncio.gather(*tasks)

def main():
    args = get_args()
    restore_items = get_restore_items(args)

    for item in restore_items:
        print(item.source, ':', item.destination)

    try:
        loop = asyncio.get_event_loop()
        loop.run_until_complete(start_process(restore_items, args, loop))
    except KeyboardInterrupt:
        pass
我的工作和文件越来越大,我看到我不断得到 socket.send()异常 阅读文档后,它似乎来自loop.run_,直到_完成

该异常不会导致程序崩溃,但最终会使程序陷入困境,以至于无法打印该异常


如何修改当前代码以修复此问题?

运行直到\u完成
仅传播在
启动\u进程中引发的异常。这意味着,如果在
start\u进程
期间的任何时候发生异常,并且
start\u进程
没有捕获到异常,则
运行\u直到\u完成(start\u进程())
将重新引发相同的异常

在您的情况下,异常可能最初在
restorer.transfer()中的某个地方引发。调用
gather
返回协同路由的结果,其中包括在发生异常时引发异常

该异常不会导致程序崩溃,但最终会使程序陷入困境,以至于无法打印该异常。如何修改当前代码以修复此问题

理想情况下,您应该修复异常的原因—可能是一次发送的请求太多,或者是错误地使用了
GlacierRestore
API。但有些例外情况是无法避免的,例如由网络故障引起的例外情况。要忽略此类异常,可以将对
restorer.transfer
的调用包装在单独的协同程序中:

async def safe_transfer(restorer, item, semaphore):
    try:
        return await restorer.transfer(item, semaphore)
    except socket.error as e:
        print(e)  # here you can choose not to print exceptions you
                  # don't care about if doing so bogs down the program
start\u process
中,您将调用此协同程序,而不是
restorer\u transfer

        coros = []
        for item in restore_items:
            coros.append(safe_transfer(restorer, item, semaphore))
        await asyncio.gather(*coros)

请注意,您不需要调用
asyncio.sure_future()
将协同路由传递给
asyncio.gather
;它将被自动调用。

run\u直到完成
只传播由
start\u进程
corroutine引发的异常。异常可能发生在一个
传输
协同程序中,并且
收集
尽职尽责地报告它。如果您想忽略异常,可以将
restorer.transfer
包装在一个单独的
async def中,该def仅用于
try/wait restorer.transfer(…)/except SocketError:pass`.@user4815162342我对您的响应感到有点困惑,请在一段代码中解释一下。我现在已将注释扩展为显示代码的答案。这是不完整的,因为我不理解原因的例外,但它显示了如何忽略它,如果你的情况下是好的。@ USSR151516242介意我再次打扰你吗?如果你有一个新的问题,请考虑问一个单独的问题。如果可能,包括一个可用于重现问题的最小示例。