首页 > 解决方案 > 使用 boto3 等待同步 lambda 调用

问题描述

我想同步调用一个 lambda 函数(请求 - 响应),但想对响应使用 python async-await await

    response = await client.invoke('my-func', InvocationType='RequestResponse', Payload='...'))

我在这里找到了一种解决方案,但它很麻烦,而且从 2016 年开始。

今天有更好的方法吗?

标签: pythonboto3python-asyncio

解决方案


我通过invoke在 asyncio 事件循环上手动运行该函数找到了一种方法:

import asyncio
import concurrent
import boto3
import json

import botocore


class LambdaClient():
    def __init__(self, concurrency: int = 20):
        self.executor = concurrent.futures.ThreadPoolExecutor(
            max_workers=concurrency,
        )
        client_config = botocore.config.Config(
           max_pool_connections=concurrency
        )
        self.client = boto3.client('lambda', config=client_config)
    
    async def invoke_async(self, snapshot):
        loop = asyncio.get_running_loop()
        result = await loop.run_in_executor(self.executor, lambda: self.invoke(snapshot))
        return result

    def invoke(self, snapshot):
        payload = {
        'path': '/calculate/value',
        'body': json.dumps(snapshot)
        }
        b = bytes(json.dumps(payload), encoding='utf8')
        response = self.client.invoke(
            FunctionName='function-name',
            InvocationType='RequestResponse',
            LogType='None',
            Payload=b)
        if 'StatusCode' not in response or response['StatusCode'] != 200:
            raise ValueError(f'Lambda invocation failed with response {response}')
        output = response["Payload"].read()
        return output

推荐阅读