使用Python boto3超时本地DynamoDB表

问题描述 投票:0回答:2

我试图通过触发Python lambda表达式以编程方式将数据放入本地运行的DynamoDB容器中。

我正在尝试按照此处提供的模板:https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/GettingStarted.Python.03.html我使用的是amazon / dynamodb-local,您可以在这里下载:https://hub.docker.com/r/amazon/dynamodb-local

使用Ubuntu 18.04.2 LTS运行容器和lambda服务器AWS Sam CLI来运行我的Lambda api Docker版本18.09.4 Python 3.6(你可以在下面的sam日志中看到这个)python lambda的启动命令只是“sam本地启动 - API”

首先是我的Lambda代码

import json
import boto3

def lambda_handler(event, context):
    print("before grabbing dynamodb")
#    dynamodb = boto3.resource('dynamodb', endpoint_url="http://localhost:8000",region_name='us-west-2',AWS_ACCESS_KEY_ID='RANDOM',AWS_SECRET_ACCESS_KEY='RANDOM')
    dynamodb = boto3.resource('dynamodb', endpoint_url="http://localhost:8000")
    table = dynamodb.Table('ContactRequests')
    try:
        response = table.put_item(
            Item={
                'id': "1234",
                'name': "test user",
                'email': "[email protected]"
                }
            )

    print("response: " + str(response))

    return {
        "statusCode": 200,
        "body": json.dumps({
            "message": "hello world"
        }),
    }

我知道我应该在localhost:8000中使用此表ContactRequests,因为我可以运行此脚本来查看我的docker容器dynamodb表我已经使用boto.resource调用中的各种值对其进行了测试,以包含访问键,区域名称和密钥,没有改进结果

dev@ubuntu:~/Projects$ aws dynamodb list-tables --endpoint-url http://localhost:8000
{
    "TableNames": [
        "ContactRequests"
    ]
}

我也能成功击中dynamodb提供的localhost:8000 / shell

不幸的是,在运行时,如果我点击触发此方法的端点,我会得到一个像这样记录的超时

Fetching lambci/lambda:python3.6 Docker container image......
2019-04-09 15:52:08 Mounting /home/dev/Projects/sam-app/.aws-sam/build/HelloWorldFunction as /var/task:ro inside runtime container
2019-04-09 15:52:12 Function 'HelloWorldFunction' timed out after 3 seconds
2019-04-09 15:52:13 Function returned an invalid response (must include one of: body, headers or statusCode in the response object). Response received: 
2019-04-09 15:52:13 127.0.0.1 - - [09/Apr/2019 15:52:13] "GET /hello HTTP/1.1" 502 -

请注意,我没有触发任何打印方法,如果我删除对table.put的调用,则成功调用print方法。

我在Stack Overflow上看过类似的问题,比如这个lambda python dynamodb write gets timeout error说明问题是我使用的是本地数据库,但我不应该用boto3写一个本地数据库,如果我把它指向我的本地运行dynamodb实例?

aws-lambda amazon-dynamodb boto3
2个回答
1
投票

运行Lambda函数的Docker容器无法通过127.0.0.1访问DynamoDB。请尝试将DynamoDB本地docker容器的名称作为端点的主机名:

dynamodb = boto3.resource('dynamodb', endpoint_url="http://<DynamoDB_LOCAL_NAME>:8000")

您可以使用docker ps查找<DynamoDB_LOCAL_NAME>或为其命名:

 docker run --name dynamodb amazon/dynamodb-local

然后连接:

dynamodb = boto3.resource('dynamodb', endpoint_url="http://dynamodb:8000")

0
投票

在这里找到问题的解决方案:connecting AWS SAM Local with dynamodb in docker提问者注意到他在网上看到他可能需要使用以下连接到同一个docker网络:

docker network create lambda-local

所以创建了这个网络,然后更新了我的sam命令和我的docker命令来使用这个网络,如下所示:

docker run --name dynamodb -p 8000:8000 --network=local-lambda amazon/dynamodb-local

sam local start-api --docker-network local-lambda

之后我不再遇到超时问题。我还在努力弄清楚为什么会出现这个问题

为了公平起见,我必须使用dynamodb容器名称作为我的boto3资源调用的主机。最后,它结合了上述解决方案和“Reto Aebersold”提供的答案,创造了最终解决方案

dynamodb = boto3.resource('dynamodb', endpoint_url="http://<DynamoDB_LOCAL_NAME>:8000")

© www.soinside.com 2019 - 2024. All rights reserved.