我的 AWS Lambda 未连接到 postgres 数据库,我不知道为什么

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

我正在尝试为博客设置一些基本的 CRUD 功能,以熟悉 AWS。这是我正在使用的 lambda 函数:

public class StoreDataLambda implements RequestStreamHandler {

    public static final Logger LOGGER = LoggerFactory.getLogger(StoreDataLambda.class);
    private static final String DB_URL = "<my jdbc url>.us-east-2.rds.amazonaws.com:5432/postgres";
    @Override
    public void handleRequest(InputStream input, OutputStream output, Context context) throws IOException {
        ObjectMapper mapper = new ObjectMapper();
        Connection connection = null;

        try {
            String secretName = "<mySecretName>";
            Region region = Region.of("us-east-2");

            // Create a Secrets Manager client
            SecretsManagerClient client = SecretsManagerClient.builder()
                    .region(region)
                    .build();

            GetSecretValueRequest getSecretValueRequest = GetSecretValueRequest.builder()
                    .secretId(secretName)
                    .build();

            GetSecretValueResponse getSecretValueResponse = null;

            try {
                getSecretValueResponse = client.getSecretValue(getSecretValueRequest);
            } catch (Exception e) {
                // For a list of exceptions thrown, see
                // https://docs.aws.amazon.com/secretsmanager/latest/apireference/API_GetSecretValue.html
                LOGGER.error("Error occurred while retrieving secret value: " + e.getMessage());
                e.printStackTrace();
            }

            String secret = getSecretValueResponse.secretString();
            JsonNode secretJson = mapper.readTree(secret);
            String dbUrl = DB_URL;
            String dbUsername = secretJson.get("username").asText();
            String dbPassword = secretJson.get("password").asText();
            LOGGER.info("Attempting to connect to the DB...");
            connection = DriverManager.getConnection(dbUrl, dbUsername, dbPassword);
            JsonNode jsonInput = mapper.readTree(input);

            // Assuming JSON structure: { "title": "value1", "content": "value2" }
            String title = jsonInput.get("title").asText();
            String content = jsonInput.get("content").asText();

            // Store data into PostgreSQL using prepared statement
            String sql = "INSERT INTO blog_page.blog_post (title, content) VALUES (?, ?)";
            PreparedStatement statement = connection.prepareStatement(sql);
            statement.setString(1, title);
            statement.setString(2, content);
            statement.executeUpdate();

            // Close resources
            statement.close();
            connection.close();
        } catch (SQLException e) {
            // Handle database exceptions
            LOGGER.error("Error occurred while connecting to the database: " + e.getMessage());
            e.printStackTrace();

        } finally {
            try {
                if (connection != null && !connection.isClosed()) {
                    connection.close();
                }
            } catch (SQLException e) {
                LOGGER.error("Error occurred while closing the connection: " + e.getMessage());
                e.printStackTrace();
            }
        }
    }

lambda 函数和数据库都位于同一 VPC/安全组/子网中,并且我已经为 lambda 设置了角色,以便它应该提供对数据库的读/写访问权限。每当我在 AWS 中通过发送 json 进行测试时,它都会在 3 秒后超时。

这就是我在日志中得到的全部内容:

2023-12-12T06:00:11.938Z 3bd24ba5-8e9e-472a-b0ef-458898205451 任务在 3.01 秒后超时

任何关于从哪里开始故障排除的想法都将非常受欢迎。

amazon-web-services aws-lambda amazon-rds
1个回答
0
投票

仅仅将资源“放在同一个安全组中”并不能确保连接性。安全组的规则单独应用于每个资源。不存在资源“位于”安全组中的概念。

首选配置是:

  • Lambda 函数上的安全组 (
    Lambda-SG
    ),允许所有出站流量
  • 数据库上的安全组 (
    DB-SG
    ),允许适当端口(例如 MySQL 的端口 3306)上的入站流量,并将
    source
    设置为
    Lambda-SG

也就是说,

DB-SG
专门引用了入站规则中的
Lambda-SG

或者,如果您希望使用单个安全组(不推荐),则需要向该安全组添加规则以允许来自自身的入站流量。这将允许使用安全组的所有资源相互通信。

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