TypeScript报错:Type 'null'不能用作索引类型求助
TypeScript错误:Type 'null' cannot be used as an index type 解决方案
问题描述
在前端CRM系统使用TypeScript执行基础计算时,遇到报错:TypeScript- Type 'null' cannot be used as an index type。尽管已通过IF语句判断分数选项是否为null,但错误仍出现在SectionAScore = scoreMap[ScoreOptionA];及类似的百分比赋值代码处。
原代码如下:
export async function CalculateAverageScore() { console.log(`CalculateAverage JS Triggered`); try { console.log(`Calculate Average Score JS try`); const ScoreOptionA: Xrm.Attributes.OptionSetAttribute = FORM_CONTEXT.getAttribute("dp_testweightedaverage"); const PercentageOptionA: Xrm.Attributes.OptionSetAttribute = FORM_CONTEXT.getAttribute("dp_percentagevalue"); const ScoreOptionB: Xrm.Attributes.OptionSetAttribute = FORM_CONTEXT.getAttribute("dp_average2"); const PercentageOptionB: Xrm.Attributes.OptionSetAttribute = FORM_CONTEXT.getAttribute("dp_percentagevalue2"); const ScoreOptionC: Xrm.Attributes.OptionSetAttribute = FORM_CONTEXT.getAttribute("dp_pickascorefirmwide"); const PercentageOptionC: Xrm.Attributes.OptionSetAttribute = FORM_CONTEXT.getAttribute("dp_percentagevaluefirmwide"); // Define Scoring & Percentages const scoreMap: { [Score: number]: number } = { 778180000: 1, 778180001: 2, 778180002: 3, 778180003: 4, 778180004: 5 }; const percentageMap: { [Percentage: number]: number } = { 778180000: 0.10, 778180001: 0.20, 778180002: 0.30, 778180003: 0.40, 778180004: 0.50 }; FORM_CONTEXT.getAttribute<Xrm.Attributes.OptionSetAttribute>('preferredcontactmethodcode')?.getValue(); var SectionAScore, SectionAPercentage, SectionBScore, SectionBPercentage, SectionCScore, SectionCPercentage; // Section A Score & Percentages if (ScoreOptionA != null && PercentageOptionA != null) { ScoreOptionA.getValue(); PercentageOptionA.getValue(); SectionAScore = scoreMap[ScoreOptionA]; SectionAPercentage = scoreMap[ScoreOptionB]; } //Section B Set Score & Percentages if (ScoreOptionB != null && PercentageOptionB != null) { var ScoreValueB = ScoreOptionB.getValue(); var valuePercentageB = PercentageOptionB.getValue(); SectionBScore = scoreMap[ScoreValueB]; SectionBPercentage = percentageMap[valuePercentageB]; } // Section C Score & Percentages if (ScoreOptionC != null && PercentageOptionC != null) { var ScoreValueC = ScoreOptionC.getValue(); var valuePercentageC = PercentageOptionC.getValue(); SectionCScore = scoreMap[ScoreValueC]; SectionCPercentage = percentageMap[valuePercentageC]; } // Calculations var Section1Score = (SectionAScore * SectionAPercentage); var Section2Score = (SectionBScore * SectionBPercentage); var Section3Score = (SectionCScore * SectionCPercentage); var averagescore = (Section1Score + Section2Score + Section3Score); // Set Average Score Value FORM_CONTEXT.getAttribute("dp_decimal").setValue(averagescore); } catch (error) { console.log(`exampleFunction error`, error); HELPERS.displayErrorMessage(error); } finally { console.log(`exampleFunction finally`); } }
错误原因分析
- 类型与使用不匹配:Section A代码中直接用
ScoreOptionA(OptionSetAttribute对象)作为索引访问scoreMap,且误用ScoreOptionB去赋值SectionAPercentage,完全不符合映射表的索引类型要求。 - getValue()返回值可能为null:即使OptionSetAttribute对象不为null,
getValue()方法在未选择选项时会返回null,TypeScript会识别这个潜在的null值,导致索引类型报错。 - 变量未初始化:分数、百分比变量未设置默认值,后续计算可能出现NaN问题。
修复后的代码
export async function CalculateAverageScore() { console.log(`CalculateAverage JS Triggered`); try { console.log(`Calculate Average Score JS try`); // 修正类型声明:getAttribute可能返回null const ScoreOptionA: Xrm.Attributes.OptionSetAttribute | null = FORM_CONTEXT.getAttribute("dp_testweightedaverage"); const PercentageOptionA: Xrm.Attributes.OptionSetAttribute | null = FORM_CONTEXT.getAttribute("dp_percentagevalue"); const ScoreOptionB: Xrm.Attributes.OptionSetAttribute | null = FORM_CONTEXT.getAttribute("dp_average2"); const PercentageOptionB: Xrm.Attributes.OptionSetAttribute | null = FORM_CONTEXT.getAttribute("dp_percentagevalue2"); const ScoreOptionC: Xrm.Attributes.OptionSetAttribute | null = FORM_CONTEXT.getAttribute("dp_pickascorefirmwide"); const PercentageOptionC: Xrm.Attributes.OptionSetAttribute | null = FORM_CONTEXT.getAttribute("dp_percentagevaluefirmwide"); // Define Scoring & Percentages const scoreMap: { [Score: number]: number } = { 778180000: 1, 778180001: 2, 778180002: 3, 778180003: 4, 778180004: 5 }; const percentageMap: { [Percentage: number]: number } = { 778180000: 0.10, 778180001: 0.20, 778180002: 0.30, 778180003: 0.40, 778180004: 0.50 }; // 初始化变量默认值,避免NaN let SectionAScore = 0, SectionAPercentage = 0, SectionBScore = 0, SectionBPercentage = 0, SectionCScore = 0, SectionCPercentage = 0; // Section A Score & Percentages if (ScoreOptionA != null && PercentageOptionA != null) { const scoreValueA = ScoreOptionA.getValue(); const percentageValueA = PercentageOptionA.getValue(); // 额外判断返回值不为null,确保索引是number类型 if (scoreValueA !== null && percentageValueA !== null) { SectionAScore = scoreMap[scoreValueA]; SectionAPercentage = percentageMap[percentageValueA]; } } //Section B Set Score & Percentages if (ScoreOptionB != null && PercentageOptionB != null) { const ScoreValueB = ScoreOptionB.getValue(); const valuePercentageB = PercentageOptionB.getValue(); if (ScoreValueB !== null && valuePercentageB !== null) { SectionBScore = scoreMap[ScoreValueB]; SectionBPercentage = percentageMap[valuePercentageB]; } } // Section C Score & Percentages if (ScoreOptionC != null && PercentageOptionC != null) { const ScoreValueC = ScoreOptionC.getValue(); const valuePercentageC = PercentageOptionC.getValue(); if (ScoreValueC !== null && valuePercentageC !== null) { SectionCScore = scoreMap[ScoreValueC]; SectionCPercentage = percentageMap[valuePercentageC]; } } // Calculations const Section1Score = SectionAScore * SectionAPercentage; const Section2Score = SectionBScore * SectionBPercentage; const Section3Score = SectionCScore * SectionCPercentage; const averagescore = Section1Score + Section2Score + Section3Score; // Set Average Score Value:先检查属性是否存在 const averageAttr = FORM_CONTEXT.getAttribute("dp_decimal"); if (averageAttr) { averageAttr.setValue(averagescore); } } catch (error) { console.log(`exampleFunction error`, error); HELPERS.displayErrorMessage(error); } finally { console.log(`exampleFunction finally`); } }
关键修复点
- 修正类型声明:给所有OptionSetAttribute变量添加
| null,匹配getAttribute()的实际返回值类型。 - 正确使用getValue()结果:将
getValue()的返回值赋值给变量,用该变量作为索引访问映射表,而非直接使用OptionSetAttribute对象。 - 增加null判断:在对象非空的基础上,额外检查
getValue()的结果是否为null,确保索引为有效number类型。 - 初始化变量默认值:给分数、百分比变量设置初始值0,避免计算出现NaN。
- 修正映射表误用:修复Section A中错误的映射表和变量引用问题。
- 安全设置属性值:获取目标属性后先判断是否存在,再调用
setValue()。
内容的提问来源于stack exchange,提问作者BenDev21
相关产品推荐
相关产品推荐

