如何在TypeScript中正确为IdTokenData函数组件及关联的createClaimsTable函数添加类型定义?
如何在TypeScript中正确为IdTokenData函数组件及关联的createClaimsTable函数添加类型定义?
嘿,这个TypeScript类型问题我熟,咱们一步步来搞定它!
一、先搞定IdTokenData组件的idTokenClaims Prop类型
首先,你的idTokenClaims是MSAL返回的ID Token声明,其实不用自己瞎定义类型——MSAL的包已经给咱们准备好了现成的类型!
方案1:用MSAL内置类型(推荐)
从@azure/msal-browser包里导入IdTokenClaims类型,直接用它来定义props:
import { IdTokenClaims } from "@azure/msal-browser"; // 定义组件的Props接口 interface IdTokenDataProps { idTokenClaims: IdTokenClaims; } // 组件使用这个Props类型,替换掉原来的any export const IdTokenData = (props: IdTokenDataProps) => { // ... 你的组件逻辑 };
这个类型包含了ID Token所有标准声明的类型定义,完全贴合实际返回的数据结构,省心又准确。
方案2:自定义类型(如果不想依赖MSAL类型)
要是你不想引入MSAL的类型包,也可以自己写一个接口,覆盖常用的声明字段,再用索引签名兼容其他未知字段:
interface CustomIdTokenClaims { sub?: string; // 用户唯一标识 name?: string; // 用户名 email?: string; // 用户邮箱 iat?: number; // 签发时间戳 exp?: number; // 过期时间戳 // 加上你业务里用到的其他声明字段 [key: string]: string | number | undefined; // 兼容其他未知的string/number类型声明 } interface IdTokenDataProps { idTokenClaims: CustomIdTokenClaims; } export const IdTokenData = (props: IdTokenDataProps) => { // ... 你的组件逻辑 };
二、给createClaimsTable函数加类型
看原函数的逻辑,它是把ID Token里的string/number类型声明,转换成一个“键对应[声明名, 声明值]数组”的对象,那咱们就给它明确参数和返回类型:
完整的TypeScript版本函数
// 导入刚才的类型(用MSAL的IdTokenClaims或者自定义的CustomIdTokenClaims都行) import { IdTokenClaims } from "@azure/msal-browser"; // 定义函数的参数和返回类型 export const createClaimsTable = (claims: IdTokenClaims): Record<string, [string, string | number]> => { // 初始化返回对象,指定类型 const claimsObj: Record<string, [string, string | number]> = {}; Object.keys(claims).forEach((key) => { // 用类型断言把key转换成IdTokenClaims的键类型,避免类型报错 const value = claims[key as keyof IdTokenClaims]; // 原函数的过滤逻辑:只处理string/number类型的声明 if (typeof value !== 'string' && typeof value !== 'number') return; // 原函数里的switch逻辑可以保留,这里省略示例... // 核心逻辑:把声明名和值组成数组存入对象 claimsObj[key] = [key, value]; }); return claimsObj; };
三、修正IdTokenData组件里的类型报错
现在tokenClaims的类型已经明确了,组件里的map逻辑就不会再报“implicit any”的错了,甚至可以优化一下key的唯一性(避免React警告):
export const IdTokenData = (props: IdTokenDataProps) => { const tokenClaims = createClaimsTable(props.idTokenClaims); const tableRow = Object.keys(tokenClaims).map((key) => { return ( <tr key={key}> {/* 现在claimItem的类型自动推断为string | number,不会报错 */} {tokenClaims[key].map((claimItem, itemIndex) => ( {/* 用key+索引做唯一key,避免重复值导致的React警告 */} <td key={`${key}-${itemIndex}`}>{claimItem}</td> ))} </tr> ); }); // ... 剩下的渲染逻辑 };
这样一来,所有的TypeScript类型报错就都解决啦,代码也更健壮了!
备注:内容来源于stack exchange,提问作者nop
相关产品推荐
相关产品推荐

