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

Cloud Run部署Discord Bot连接Cloud SQL MySQL遇ETIMEDOUT问题

解决Cloud Run部署Discord Bot连接Cloud SQL MySQL的ETIMEDOUT问题

核心排查方向及解决方案

1. 确认Cloud Run与Cloud SQL的关联配置有效性

  • 检查Cloud Run部署页面的「Cloud SQL connections」,确保已添加目标Cloud SQL实例,且两者处于同一区域(跨区域Unix Socket连接会直接超时)
  • 验证环境变量INSTANCE_UNIX_SOCKET的格式:必须严格为/cloudsql/[PROJECT_ID]:[REGION]:[INSTANCE_NAME],注意分隔符是冒号而非斜杠,这是最容易出错的点

2. 验证服务账号权限落地情况

  • 确认Cloud Run的服务账号(格式为[SERVICE_NAME]@[PROJECT_ID].iam.gserviceaccount.com)已被授予Cloud SQL Client或Cloud SQL Admin角色,且无IAM deny策略限制该账号的连接权限
  • 无需在Cloud SQL实例的「用户」页面添加该服务账号,IAM角色已足够授权通过Auth Proxy连接

3. 修复代码的错误捕获与日志输出

本地能打印连接池但Cloud日志无输出,说明错误未被正确捕获或日志未上报,修改代码如下:

function createConnectionPoolCloud(){
  const dboptions = {
    connectionLimit : 10,
    socketPath: process.env.INSTANCE_UNIX_SOCKET,
    user     : process.env.DB_USER,
    password : process.env.DB_PASS,
    database : process.env.DB_NAME,
    waitForConnections: true,
    connectTimeout: 10000 // 延长超时时间便于排查
  }
  const pool = mysql.createPool(dboptions);
  // 添加连接池错误监听
  pool.on('error', (err) => {
    console.error('Connection pool error:', err.stack);
  });
  return pool;
};

// 调用时添加错误捕获
async function testPoolConnection() {
  try {
    const pool = createConnectionPoolCloud();
    const promisePool = pool.promise();
    const [rows] = await promisePool.query('SELECT 1 FROM DUAL');
    console.log('Database connection successful:', rows);
  } catch (err) {
    console.error('Query execution failed:', err.stack);
  }
}

// 启动时执行测试
testPoolConnection();

修改后查看Cloud Logging,能获取更详细的错误栈信息,定位问题根源

4. 排查Dockerfile配置问题

  • 使用官方Node.js镜像(如node:18-slim)而非Alpine镜像,避免底层依赖缺失导致的连接异常
  • 确认启动命令正确(如CMD ["node", "index.js"]),确保服务正常启动后再尝试数据库连接
  • 无需暴露端口(Discord Bot为主动出站服务),但需确保Cloud Run配置的端口与服务监听端口一致(若服务有HTTP接口)

5. 跳过连接池测试单连接

若连接池一直超时,先测试单连接排除连接池配置问题:

const mysql = require('mysql2');

async function testDirectConnection() {
  const connection = mysql.createConnection({
    socketPath: process.env.INSTANCE_UNIX_SOCKET,
    user: process.env.DB_USER,
    password: process.env.DB_PASS,
    database: process.env.DB_NAME,
    connectTimeout: 10000
  });

  connection.connect((err) => {
    if (err) {
      console.error('Direct connection error:', err.stack);
      return;
    }
    console.log('Direct connection successful');
    connection.query('SELECT 1 FROM DUAL', (err, rows) => {
      if (err) {
        console.error('Direct query error:', err.stack);
      } else {
        console.log('Direct query result:', rows);
      }
      connection.end();
    });
  });
}

testDirectConnection();
  • 若单连接成功:问题出在连接池配置(如connectionLimit过高、waitForConnections逻辑冲突),可逐步调整连接池参数
  • 若单连接也超时:问题在网络或权限层面,回到前两步重新排查

6. 确认Cloud SQL实例状态

  • 检查Cloud SQL实例是否处于运行状态,无维护或暂停情况
  • 确认Cloud SQL Admin API已启用(在Google Cloud Console的API库中查看)
  • 无需配置Cloud SQL的公网IP白名单(Unix Socket通过Auth Proxy连接,不依赖公网IP防火墙)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.06 20:02:48