MST

星途 面试题库

面试题:TypeScript 中 Partial 和 Readonly 在类型体操及项目架构中的深度应用

在一个大型前端项目中,存在多个模块需要共享一些基础数据结构。例如有一个基础用户信息类型:interface BaseUserInfo { id: number; name: string; email: string; }。有些模块需要对这个用户信息进行修改,有些模块只能读取。现在要求通过自定义工具类型,利用 Partial 和 Readonly 映射类型,实现一套灵活的类型系统,使得不同模块能方便地获取到符合需求的用户信息类型(如可修改的部分用户信息类型、只读的完整用户信息类型等),并且在类型定义层面要保证数据的一致性和类型安全。请阐述你的设计思路,并给出具体的类型定义代码。同时,分析这种类型设计在项目长期维护过程中的优势和可能遇到的挑战。
48.3万 热度难度
前端开发TypeScript

知识考点

AI 面试

面试题答案

一键面试

设计思路

  1. 可修改的部分用户信息类型:利用 Partial 映射类型将 BaseUserInfo 中的所有属性变为可选,这样就得到了可修改的部分用户信息类型。因为部分属性可以不存在,所以适合用于需要对用户信息进行修改的模块,且修改时可以只更新部分属性。
  2. 只读的完整用户信息类型:使用 Readonly 映射类型将 BaseUserInfo 所有属性变为只读,保证该类型的用户信息不能被修改,适用于只需要读取用户信息的模块。

具体类型定义代码

interface BaseUserInfo { 
    id: number; 
    name: string; 
    email: string; 
}

// 可修改的部分用户信息类型
type MutablePartialUserInfo = Partial<BaseUserInfo>;

// 只读的完整用户信息类型
type ReadonlyFullUserInfo = Readonly<BaseUserInfo>;

优势

  1. 类型安全:在编译阶段就能发现类型不匹配的错误,避免在运行时出现意外的错误,提高了代码的稳定性和可靠性。例如,如果一个模块尝试修改 ReadonlyFullUserInfo 类型的用户信息,TypeScript 编译器会报错。
  2. 代码清晰:通过自定义工具类型,不同模块获取的用户信息类型一目了然,增强了代码的可读性。比如 MutablePartialUserInfo 一看就知道是可修改且部分的用户信息类型。
  3. 灵活性:可以根据不同模块的需求,灵活地组合 PartialReadonly 来生成所需的类型,满足各种业务场景。例如,如果某个模块需要只读的部分用户信息类型,也可以很容易通过组合得到 Readonly<Partial<BaseUserInfo>>

可能遇到的挑战

  1. 类型复杂性增加:随着项目的发展,基础数据结构可能变得更加复杂,自定义工具类型的组合也会增多,导致类型定义变得冗长和难以理解。例如,如果 BaseUserInfo 嵌套了多层对象,组合出的类型会变得非常复杂。
  2. 升级维护成本:当 BaseUserInfo 发生变化时,所有依赖于它的自定义工具类型都需要检查和更新,可能会影响到多个模块。比如 BaseUserInfo 新增了一个属性,那么 MutablePartialUserInfoReadonlyFullUserInfo 都可能需要相应调整。
  3. 学习成本:对于新加入项目的开发人员,需要花费时间学习和理解这些自定义工具类型,尤其是复杂的组合类型,增加了上手的难度。