【问题标题】:Typescript: Pattern for building an object one property at a time打字稿:一次构建一个对象的模式
【发布时间】:2021-09-01 01:18:44
【问题描述】:

在创建要插入数据库的复杂对象时,这种情况尤其常见。我可能有一个需要 20 个字段的对象,每个字段都来自其他地方。

interface Cat {hair: HairType, name: string, ...20 other properties}
function insertCatIntoDB(cat: Cat){...}

function createCatForUser(userType: UserType){
  const newCat: Partial<Cat> = {};
  newCat.name = getNewCatNameForUserType(userType);
  ...business logic involving the setting of the other properties
  insertCatIntoDB(newCat); // Problem: newCat is Partial<Cat> 
                           // instead of Cat despite having assigned all of the properties

}

我看到了一些处理这个问题的方法。

  1. 将每个属性的“获取”重构为一个新函数,然后调用类似
insertCatIntoDB({hair: getHairByUserType, name: getNameByUserType, ...})

但是,如果创建属性所需的业务逻辑相对简单,您将创建 20 个函数,每个函数可能 3 行代码,它们只会被调用一次,这不利于可读性。

  1. 类似,但无需创建新函数,您只需在选项“内部”执行,例如

insertCatIntoDB({name: userType === UserType.girl ? 'cookie' : (userType === userType.boy ? 'tiger' : 'persian'), ...}) 但即使在这个逻辑非常简单的例子中,这很快就会变得笨拙且难以阅读。

  1. 做类似insertCatIntoDB(newCat as Cat)的事情

但这没有类型检查。

我正在寻找有关处理这些情况的更好方法的建议。

【问题讨论】:

    标签: javascript node.js reactjs typescript types


    【解决方案1】:

    当我查看您界面中的属性数量并根据您的重构想法时,我对此有几个想法:

    • 根据Interface segregation principles将该接口拆分成更小的接口。我们可以使用Information experts principleHigh cohesion principle 来创建几个接口,这些接口包含几个高内聚属性的信息。这样就不用创建20个函数来按类型获取属性,只需要几个实例。

    • 使用工厂模式创建 getNameByUserType、getHairByUserType、getOtherAttributesByType 等 ...

    • 使用Builder模式初始化cat对象,并将上述工厂注入到builder中(参考:https://refactoring.guru/design-patterns/builder)。例如:

        const cat = new CatBuilder()
         .byUserType(userType)
         .withGetByUserTypeFactory(GetByUserTypeFactory)
         .withHair()
         .withName()
         .(...other attributes...)
         .build(); 
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-12-24
      • 2021-07-22
      • 2019-06-30
      • 2019-02-13
      • 2022-01-14
      • 2023-03-07
      • 2018-09-23
      相关资源
      最近更新 更多