如何用JavaScript HTTP请求在Dataverse表中批量插入多条记录
PowerApps模型驱动应用中JS Web Resource批量插入记录的正确实现
优先方案:使用官方executeMultiple API
Dataverse Web API提供了executeMultiple方法,专门用于批量操作,无需手动构建复杂的OData批量请求体,是最可靠的实现方式,能避免绝大多数格式错误。
代码示例
async function batchCreateRecords() { // 构建批量请求数组,每条请求对应一个要插入的记录 const batchRequests = [ Xrm.WebApi.online.createRequest("accounts", { name: "测试账户1", telephone1: "1234567890" }), Xrm.WebApi.online.createRequest("accounts", { name: "测试账户2", telephone1: "0987654321" }) // 可添加更多记录请求 ]; try { // 执行批量操作:continueOnError=false表示事务性(一个失败则全部回滚),true表示忽略错误继续执行 const operationResults = await Xrm.WebApi.online.executeMultiple(batchRequests, { continueOnError: false }); // 处理结果 let successCount = 0; operationResults.forEach(result => { if (result.success) { successCount++; console.log(`记录创建成功,ID: ${result.id}`); } else { console.error(`创建失败: ${result.error.message}`); } }); Xrm.Navigation.openAlertDialog({ text: `批量操作完成,成功插入${successCount}/${batchRequests.length}条记录` }); } catch (error) { console.error("批量操作异常:", error); Xrm.Navigation.openAlertDialog({ text: `批量操作失败: ${error.message}` }); } }
关键说明
- 第一个参数是请求数组,每个请求用
createRequest创建,指定实体逻辑名称和记录数据 continueOnError参数控制事务行为:false:事务性操作,任一请求失败则所有操作回滚true:非事务性,即使部分请求失败,其他请求仍会执行
- 返回结果包含每个操作的成功状态、记录ID(成功时)和错误信息(失败时)
备选方案:手动构建OData $batch请求
如果因特殊需求必须手动使用OData批量端点,需严格遵循OData 4.0规范,重点注意CRLF换行符和multipart/mixed格式(这是你之前出现请求头格式错误的核心原因)。
代码示例
async function batchCreateViaODataBatch() { const globalContext = Xrm.Utility.getGlobalContext(); const clientUrl = globalContext.getClientUrl(); const apiVersion = "v9.2"; // 生成唯一的batch边界字符串,避免与请求体内容冲突 const batchBoundary = `batch_${Math.random().toString(36).slice(2)}`; // 准备要插入的记录数据 const records = [ { name: "测试账户1", telephone1: "1234567890" }, { name: "测试账户2", telephone1: "0987654321" } ]; // 构建批量请求体,必须使用CRLF(\r\n)分隔内容 let batchBody = ""; records.forEach(record => { const changeSetId = `changeset_${Math.random().toString(36).slice(2)}`; // 开始batch的一个part batchBody += `--${batchBoundary}\r\n`; batchBody += `Content-Type: multipart/mixed; boundary=${changeSetId}\r\n\r\n`; // 添加单个创建请求到变更集 batchBody += `--${changeSetId}\r\n`; batchBody += `Content-Type: application/http\r\n`; batchBody += `Content-Transfer-Encoding: binary\r\n\r\n`; batchBody += `POST ${clientUrl}/api/data/${apiVersion}/accounts HTTP/1.1\r\n`; batchBody += `Content-Type: application/json\r\n\r\n`; batchBody += `${JSON.stringify(record)}\r\n\r\n`; // 结束当前变更集 batchBody += `--${changeSetId}--\r\n`; }); // 结束整个batch batchBody += `--${batchBoundary}--`; try { // 获取当前用户的访问令牌 const authToken = await Xrm.WebApi.getAccessToken(clientUrl); const response = await fetch(`${clientUrl}/api/data/${apiVersion}/$batch`, { method: "POST", headers: { "Authorization": `Bearer ${authToken}`, "Content-Type": `multipart/mixed; boundary=${batchBoundary}`, "Accept": "application/json" }, body: batchBody }); if (!response.ok) { const errorDetail = await response.text(); throw new Error(`批量请求失败: ${errorDetail}`); } const responseContent = await response.text(); console.log("批量插入成功", responseContent); Xrm.Navigation.openAlertDialog({ text: "多条记录已成功插入" }); } catch (error) { console.error("批量插入出错:", error); Xrm.Navigation.openAlertDialog({ text: `插入失败: ${error.message}` }); } }
核心注意事项
- 换行符必须用CRLF(\r\n):HTTP协议要求请求头和内容之间用CRLF分隔,使用单个
\n会触发请求头格式错误 - boundary字符串唯一:必须确保batch和changeset的边界字符串不会出现在请求体的任何内容中,建议用随机字符串生成
- 变更集事务性:每个changeset内的操作是原子性的,要么全部成功,要么全部回滚;如果不需要事务,可将每个操作放在独立的changeset中
- API版本匹配:确保使用的API版本与当前环境兼容(如v9.2)
内容的提问来源于stack exchange,提问作者RBK
相关产品推荐
相关产品推荐

