Excel Online Office Scripts在Microsoft Flow运行时报错:namedRanges.findAsync不是函数
解决Office Scripts在Power Automate中运行时的
namedRanges.findAsync is not a function错误 问题场景
编写的Office Scripts脚本在Excel Online中直接运行完全正常,但通过Power Automate(原Microsoft Flow)执行时,出现以下运行时错误:
无法运行脚本,请重试。运行时错误:
第19行:namedRanges.findAsync is not a function clientRequestId:
e0d62dd6-eada-4d04-b081-13e7c5400748
原脚本代码:
function main(workbook: ExcelScript.Workbook) { const names = ["EVMSChart", "AC", "EV", "PV"]; let outputRow = 0; let outputWs = workbook.getWorksheet("Graph Data"); if (!outputWs) { outputWs = workbook.addWorksheet("Graph Data"); } else { outputWs.getRange("A:BZ").clear(); } outputWs.getRange("A1:E1").setValues([["Sheet Name", "EVMSChart", "AC", "EV", "PV"]]); workbook.getWorksheets().forEach((ws) => { let max = 0; let hasData = false; for (let i = 0; i < names.length; i++) { const namedRanges = ws.getNames(); const namedRange = namedRanges.find(nr => nr.getName() === names[i]);//Line 19 if (namedRange) { const range = namedRange.getRange(); const data = range.getValues(); let outputData: (string[][]) = []; for (let j = 0; j < data.length; j++) { const row = data[j]; for (let k = 0; k < row.length; k++) { const value = row[k].toString(); outputData.push([value]); max = Math.max(max, k); } } if (outputData.length > 0) { outputWs.getRangeByIndexes(outputRow + 1, i + 1, outputData.length, 1).setValues(outputData); hasData = true; } } } if (hasData) { outputWs.getRangeByIndexes(outputRow + 1, 0, max + 1, 1).setValues(Array(max + 1).fill([ws.getName()])); outputRow += max + 1; } }); const tblDataRange = outputWs.getRange("A1").getSurroundingRegion(); const tbl = outputWs.addTable(tblDataRange, true); tbl.setName("data"); console.log("Done!"); }
错误原因分析
- Excel Online直接运行环境中,
ws.getNames()返回的对象会被适配为标准JavaScript数组,因此原生数组方法find()可以正常调用。 - 但在Power Automate执行环境中,
ws.getNames()返回的是类数组对象,而非标准数组,不具备原生find()方法。错误信息中的findAsync是Office Scripts底层尝试的异步 fallback 方法,因原生方法缺失触发了无效调用,导致报错。
修复方案
方案1:将类数组对象转为标准数组
使用Array.from()将ws.getNames()的返回值转换为标准数组,确保find()方法可用:
修改第19行附近的代码:
const namedRanges = Array.from(ws.getNames()); // 转换为标准数组 const namedRange = namedRanges.find(nr => nr.getName() === names[i]);
方案2:手动循环遍历查找
避免依赖数组原生方法,通过循环遍历类数组对象查找目标命名区域:
修改第19行附近的代码:
const namedRanges = ws.getNames(); let namedRange: ExcelScript.NamedItem | undefined; // 手动遍历查找 for (const nr of namedRanges) { if (nr.getName() === names[i]) { namedRange = nr; break; } }
完整修复后的脚本示例(方案1)
function main(workbook: ExcelScript.Workbook) { const names = ["EVMSChart", "AC", "EV", "PV"]; let outputRow = 0; let outputWs = workbook.getWorksheet("Graph Data"); if (!outputWs) { outputWs = workbook.addWorksheet("Graph Data"); } else { outputWs.getRange("A:BZ").clear(); } outputWs.getRange("A1:E1").setValues([["Sheet Name", "EVMSChart", "AC", "EV", "PV"]]); workbook.getWorksheets().forEach((ws) => { let max = 0; let hasData = false; for (let i = 0; i < names.length; i++) { const namedRanges = Array.from(ws.getNames()); // 转换为标准数组 const namedRange = namedRanges.find(nr => nr.getName() === names[i]); if (namedRange) { const range = namedRange.getRange(); const data = range.getValues(); let outputData: (string[][]) = []; for (let j = 0; j < data.length; j++) { const row = data[j]; for (let k = 0; k < row.length; k++) { const value = row[k].toString(); outputData.push([value]); max = Math.max(max, k); } } if (outputData.length > 0) { outputWs.getRangeByIndexes(outputRow + 1, i + 1, outputData.length, 1).setValues(outputData); hasData = true; } } } if (hasData) { outputWs.getRangeByIndexes(outputRow + 1, 0, max + 1, 1).setValues(Array(max + 1).fill([ws.getName()])); outputRow += max + 1; } }); const tblDataRange = outputWs.getRange("A1").getSurroundingRegion(); const tbl = outputWs.addTable(tblDataRange, true); tbl.setName("data"); console.log("Done!"); }
内容的提问来源于stack exchange,提问作者Dejan Dozet
相关产品推荐
相关产品推荐

