在云函数中调用另一个云函数时出现TLS连接错误
云函数间调用出现TLS连接失败的解决方案
问题场景
在Cloud Functions中通过fetch调用另一个云函数时,触发以下错误:
Exception from a finished function: FetchError: request to https://us-central1-betty-sport.cloudfunctions.net/check failed, reason: Client network socket disconnected before secure TLS connection was established
发起调用的云函数代码:
exports.addMessage = functions.https.onRequest(async (req, res) => { var currentTime = Math.floor(Date.now() / 1000); const risultati = await firestore.collection("Risultati").doc("risultati").get(); const ref1 = await firestore.collection("Schedine").get(); await ref1.forEach(async doc => { let url = "https://us-central1-betty-sport.cloudfunctions.net/check" await fetch(url, { method: 'GET', qs: { name : doc}, headers: { 'Content-Type': 'application/json', }, }) });
问题根源
- 异步循环处理错误:
forEach不会等待内部异步函数执行完成,主函数可能提前终止,导致网络连接被强制断开,触发TLS连接失败。 - GET参数传递错误:
fetchAPI不支持qs配置项,无法通过该字段传递查询参数。 - 未遵循同项目云函数调用最佳实践:通过公网HTTP调用同项目云函数,容易出现网络层面的不稳定问题。
修复方案
1. 修正异步循环逻辑
用map生成Promise数组,配合Promise.all等待所有异步调用完成,避免主函数提前结束:
exports.addMessage = functions.https.onRequest(async (req, res) => { var currentTime = Math.floor(Date.now() / 1000); const risultati = await firestore.collection("Risultati").doc("risultati").get(); const ref1 = await firestore.collection("Schedine").get(); // 用Promise.all确保所有调用完成后再继续 await Promise.all(ref1.docs.map(async doc => { // 正确拼接GET请求参数 const url = new URL("https://us-central1-betty-sport.cloudfunctions.net/check"); // 根据被调用函数需求,传递doc.id或doc.data(),此处示例用doc.id url.searchParams.append('name', doc.id); await fetch(url.toString(), { method: 'GET', headers: { 'Content-Type': 'application/json', }, }); })); // 必须返回响应,避免函数超时 res.status(200).send("调用完成"); });
2. 使用内部调用替代HTTP请求(推荐)
同GCP项目内的云函数,优先用内部调用方式,无需走公网,更稳定高效:
首先安装依赖:
npm install @google-cloud/functions-framework
修改调用代码:
const { getFunction } = require('@google-cloud/functions-framework'); exports.addMessage = functions.https.onRequest(async (req, res) => { var currentTime = Math.floor(Date.now() / 1000); const risultati = await firestore.collection("Risultati").doc("risultati").get(); const ref1 = await firestore.collection("Schedine").get(); // 获取内部云函数实例 const checkFunction = getFunction('check'); await Promise.all(ref1.docs.map(async doc => { // 构造模拟请求对象 const mockReq = { query: { name: doc.id } }; // 构造模拟响应对象 const mockRes = { send: () => {}, status: () => ({ send: () => {} }) }; // 直接调用内部函数 await checkFunction(mockReq, mockRes); })); res.status(200).send("调用完成"); });
3. 检查被调用函数配置
确保check云函数:
- 已正常部署并处于运行状态
- 未设置限制访问的VPC或防火墙规则
- 函数本身无超时或异常逻辑,避免提前断开连接
内容的提问来源于stack exchange,提问作者faccio
相关产品推荐
相关产品推荐

