使用request.post跨服务器传图返回undefined,求技术解决指导
解决Sails.js中转发上传图片到第三方服务器失败的问题
看起来你遇到了Sails.js里转发前端上传图片到example2.com的问题,主要是对Sails的文件上传对象处理有误,加上代码里的语法小错误导致的。我来帮你一步步修复:
首先看代码里的明显问题
- 语法错误:你的
options里url: 'myurl''多了一个单引号,这会导致语法报错,应该改成正确的目标服务器接口地址,比如url: 'https://example2.com/your-upload-endpoint'。 - 错误传递FormData:
req.file('image')是Sails的Upstream对象,不是标准的FormData实例,直接传给request的话,第三方服务器无法识别这个格式。
正确的解决方案
步骤1:安装必要依赖
我们需要用form-data库来构建符合要求的表单数据,先安装它:
npm install form-data
步骤2:修改代码,正确处理文件上传与转发
下面是修复后的完整代码,我加了详细注释:
const FormData = require('form-data'); const request = require('request'); const fs = require('fs'); const path = require('path'); module.exports = { forwardImage: async function(req, res) { try { // 1. 先通过Sails处理前端上传的文件,获取本地临时文件信息 const uploadedFiles = await req.file('image').upload({ // 设置临时存储目录,你可以根据需求调整 dirname: path.resolve(sails.config.appPath, '.tmp/uploads'), maxBytes: 10 * 1024 * 1024 // 限制文件大小为10MB }); // 检查是否有文件被上传 if (uploadedFiles.length === 0) { return res.json({ success: false, message: '没有检测到上传的文件' }); } const targetFile = uploadedFiles[0]; // 2. 创建合法的FormData实例,添加文件流 const formData = new FormData(); // 第一个参数是第三方服务器接收文件的字段名(要和对方接口一致) formData.append('image', fs.createReadStream(targetFile.fd), { filename: targetFile.filename, // 保持原文件名 contentType: targetFile.type // 保持原文件类型 }); // 3. 配置request请求选项 const options = { url: 'https://example2.com/your-actual-upload-endpoint', // 替换成真实的接口地址 method: 'POST', formData: formData, // 让form-data自动生成正确的请求头(包含boundary信息) headers: formData.getHeaders() }; // 4. 发送请求,用Promise包装适配async/await await new Promise((resolve, reject) => { request.post(options, (err, response, body) => { if (err) { console.error('转发请求出错:', err); return reject(err); } // 可以额外检查第三方服务器的响应状态码 if (response.statusCode !== 200) { return reject(new Error(`第三方服务器返回异常状态码: ${response.statusCode}, 响应内容: ${body}`)); } resolve(body); }); }); res.json({ success: true }); } catch (err) { console.error('整体流程出错:', err); res.json({ success: false, message: `文件转发失败: ${err.message}` }); } } };
关键知识点解释
- Sails的
req.file('image').upload()会把前端上传的文件保存到临时目录,并返回包含文件信息的数组,我们需要从中拿到文件的本地路径(fd字段)。 - 用
form-data库创建的FormData实例,配合文件流添加文件,才能让第三方服务器正确解析multipart/form-data格式的请求。 - 手动设置
headers: formData.getHeaders()可以避免request自动生成的请求头缺失必要的boundary信息,这是很多转发失败的常见原因。 - 用Promise包装request的回调,适配async/await语法,让错误处理更清晰,也避免了回调地狱。
额外排查点
- 确认
example2.com的上传接口支持multipart/form-data格式,并且接收文件的字段名和你formData.append的第一个参数一致(比如对方接口用req.file('image')接收,你就传image)。 - 检查你的
example1.com服务器是否能正常访问example2.com,有没有防火墙、代理或者网络限制(服务器端转发不受浏览器跨域规则影响)。 - 如果你用的是旧版本的request库,建议升级到最新版(不过request已经停止维护,长期来看可以考虑替换成axios,用法类似)。
内容的提问来源于stack exchange,提问作者Sunil Dubey
相关产品推荐
相关产品推荐

