You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用VS Code SAM构建Lambda函数连接VPC内MySQL RDS失败求助

解决Lambda通过SSH隧道连接VPC内RDS无报错但无法连接的问题

首先,我发现你的代码里没处理mysqlssh.connect()的Promise拒绝情况——这大概率是问题的核心!如果SSH连接本身失败了,你的代码不会抛出任何错误,看起来就像“没反应”。先给代码加个catch块,把具体错误打出来:

const fs = require('fs'); 
const mysqlssh = require('mysql-ssh'); 
mysqlssh.connect( 
  { host: 'XXX.XXX.XX.XX', user: 'ec2-user', privateKey: fs.readFileSync('./XXXX-txlarge.pem') }, 
  { host: '-staging-instanceXXXXX.rds.amazonaws.com', user: 'user', password: 'password', database: 'db' } 
) 
.then(client => { 
  client.query('SELECT * FROM users', function (err, results, fields) { 
    if (err) throw err 
    console.log(results); 
    mysqlssh.close() 
  }) 
})
.catch(err => {
  console.error('连接失败详情:', err); // 这里能看到SSH或数据库连接的具体错误信息
});

接下来按你的使用场景分情况排查:

场景1:本地用SAM CLI调试Lambda

  • EC2安全组检查:确保你的本地公网IP被允许访问EC2的22端口(SSH)。去AWS控制台的EC2安全组里,添加入站规则,允许你的本地公网IP/32访问22端口。
  • RDS安全组检查:确认EC2的私有IP被允许访问RDS的3306端口。RDS的安全组入站规则要加EC2的私有IP/32或者EC2所在的安全组,端口设为3306。
  • 密钥文件权限与路径:本地调试时,./XXXX-txlarge.pem的路径要准确,确保文件在SAM项目根目录;另外Linux/macOS下要把密钥权限改成600(执行chmod 600 XXXX-txlarge.pem),否则SSH会直接拒绝连接。

场景2:Lambda已部署到AWS

  • Lambda的VPC配置:如果Lambda不在目标VPC里,根本没法直接访问VPC内的EC2和RDS。要把Lambda放到和EC2、RDS同VPC的子网里,同时给Lambda分配安全组,这个安全组要允许访问EC2的22端口。
  • 安全组规则调整:EC2的安全组要允许Lambda所在的安全组访问22端口;RDS的安全组要允许EC2的私有IP或EC2所在安全组访问3306端口。
  • 密钥文件的正确存储:Lambda里不能直接用本地的pem文件,建议把密钥放到AWS Secrets Manager或者S3里,在Lambda代码里读取。如果非要打包到部署包,要确保文件路径正确,并且把文件放到/tmp目录后设置权限为600。
  • Lambda执行角色权限:确保Lambda的IAM角色有创建VPC网络接口(ENI)的权限,以及访问Secrets Manager/S3(如果存密钥的话)的权限。

通用排查步骤

  • 先手动验证EC2到RDS的连通性:SSH到EC2实例,用命令mysql -h <RDS端点> -u user -p尝试连接RDS,如果这一步都失败,那隧道肯定也没法工作,先解决RDS本身的访问问题。
  • 检查EC2的公网/内网可达性:如果是本地调试,EC2必须有弹性公网IP;如果Lambda在VPC内,用EC2的私有IP连接即可。
  • 升级依赖版本:试试把mysql-ssh升级到最新版本,可能存在版本兼容性问题导致的隐性错误。

内容的提问来源于stack exchange,提问作者Sonali

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.06 10:28:12