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

如何在JavaScript及WSO2中不依赖XMLHttpRequest发送multipart/form-data

刚好这两个问题我都有实际处理经验,给你详细拆解下:

1. 在JavaScript环境中不使用XMLHttpRequest发送multipart/form-data请求

现在几乎没人用XHR发请求了,Fetch API是更现代、更简洁的替代方案,不管是浏览器端还是Node.js环境都能轻松搞定,搭配FormData对象就能自动处理multipart/form-data的格式和头部。

举个浏览器端的实际例子:

// 先构造FormData,把表单字段和文件加进去
const formData = new FormData();
formData.append('username', 'john_doe');
// 这里假设你有个file类型的input元素,获取选中的文件
formData.append('avatar', document.getElementById('avatar-input').files[0], 'user-avatar.jpg');

// 用Fetch发送POST请求
fetch('/api/user/profile', {
  method: 'POST',
  body: formData // 直接传FormData就行,Fetch会自动设置正确的Content-Type
})
.then(response => {
  if (!response.ok) throw new Error('请求失败');
  return response.json();
})
.then(data => console.log('上传成功,返回数据:', data))
.catch(err => console.error('出问题了:', err));

如果是在Node.js环境,v18及以上已经原生支持Fetch,低版本的话可以装个node-fetch包,用法和浏览器端几乎一致。另外用axios库也很方便,它会自动识别FormData并设置头部:

const axios = require('axios');
const FormData = require('form-data');
const fs = require('fs');

const formData = new FormData();
// 读取本地文件并添加到表单
formData.append('report', fs.createReadStream('./annual-report.pdf'));
formData.append('year', '2024');

axios.post('https://api.example.com/submit-report', formData, {
  headers: formData.getHeaders() // 让axios用FormData自动生成的头部
})
.then(res => console.log('提交成功:', res.data))
.catch(err => console.error('提交失败:', err.response?.data || err.message));
2. WSO2环境中无XMLHttpRequest时发送multipart/form-data请求

WSO2的运行环境(比如EI、APIM的JS脚本中介)用的是Java虚拟机上的JS引擎,确实不支持浏览器端的XHR或Fetch,得用WSO2兼容的方式来实现,这里给你两种常用方案:

方案一:在JS脚本中调用Apache HttpClient

WSO2内置了Apache HttpClient库,直接在脚本里调用Java类就能构造multipart请求,比如:

// 引入WSO2自带的Java类
var HttpClient = Packages.org.apache.http.impl.client.HttpClients;
var HttpPost = Packages.org.apache.http.client.methods.HttpPost;
var MultipartEntityBuilder = Packages.org.apache.http.entity.mime.MultipartEntityBuilder;
var File = Packages.java.io.File;

// 初始化客户端和POST请求
var httpClient = HttpClient.createDefault();
var postRequest = new HttpPost('https://your-target-api.com/upload');

// 构造multipart表单内容
var entityBuilder = MultipartEntityBuilder.create();
// 添加文本字段
entityBuilder.addTextBody('request-id', 'REQ-2024-001');
// 添加本地文件(注意路径是WSO2服务器上的路径)
entityBuilder.addBinaryBody('attachment', new File('/opt/wso2/files/invoice.pdf'));

// 把实体设置到请求里
postRequest.setEntity(entityBuilder.build());

// 发送请求并获取响应
var response = httpClient.execute(postRequest);
var statusCode = response.getStatusLine().getStatusCode();
print('请求返回状态码:', statusCode);

// 别忘了关闭资源
response.close();
httpClient.close();

方案二:用WSO2的中介组件实现(无脚本)

如果是在WSO2的集成序列里,直接用中介组件更规范,比如用PayloadFactory构造multipart payload,再用Send中介发送:

<sequence xmlns="http://ws.apache.org/ns/synapse">
    <!-- 强制设置消息类型为multipart/form-data -->
    <property name="messageType" value="multipart/form-data" scope="axis2"/>
    
    <!-- 构造multipart格式的请求体 -->
    <payloadFactory media-type="multipart/form-data">
        <format>
            --custom-boundary-12345
            Content-Disposition: form-data; name="form-field"
            
            sample-value
            --custom-boundary-12345
            Content-Disposition: form-data; name="upload-file"; filename="invoice.pdf"
            Content-Type: application/pdf
            
            $1
            --custom-boundary-12345--
        </format>
        <args>
            <!-- 这里从属性获取预先加载的文件内容 -->
            <arg evaluator="xml" expression="get-property('upload-file-content')"/>
        </args>
    </payloadFactory>
    
    <!-- 发送到目标地址 -->
    <send>
        <endpoint>
            <address uri="https://your-target-api.com/upload"/>
        </endpoint>
    </send>
</sequence>

这种方式不需要写JS,完全用WSO2的原生中介就能搞定,适合企业级集成场景。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.26 08:45:12