You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何为函数处理器结果的泛型聚合定义TypeScript类型?

TypeScript 链式处理器的类型推导方案

问题场景

需要实现一个configure生成器函数,通过链式添加处理器(processor)合并配置结果,要求TypeScript自动推导done()返回值的类型——即默认处理器返回的BaseConfig与所有后续添加的处理器返回类型的交集。原示例代码及使用方式如下:

原实现代码

function configure() {
  // 内部复杂嵌套配置
  const config = {
    root: true,
    basic: true,
    value: 10,
  };

  const processors = [ // 默认处理器,返回BaseConfig
    function(data) {
      return {
        isRoot: data.root,
        isBasic: data.basic,
        value: data.value * 5
      };
    }
  ];

  return {
    addProcessor(handler) { // 需要为该方法定义类型
      processors.push(handler);
      return this;
    },

    done() { // 返回类型应为BaseConfig & 所有处理器返回类型的交集
      return Object.assign({}, ...processors.map((p) => p(config)));
    }
  }
}

使用方式

const res = configure()
  .addProcessor(function(data) {
    return {
      isBasic: false,
      value: data.value * 10,
    }
  })
  .done();

// 期望res类型自动推导为 { isRoot: boolean; isBasic: boolean; value: number; }
// 实际值为 { isRoot: true, isBasic: false, value: 100 }

核心需求:无法提前预知后续处理器的返回类型,需通过泛型链式跟踪所有类型,最终合并为交叉类型。

解决方案

通过泛型对象类型跟踪处理器的返回类型集合,结合TypeScript的ReturnType工具类型和交叉类型实现自动合并。

完整实现代码

// 定义输入配置的固定类型
type InputConfig = {
  root: boolean;
  basic: boolean;
  value: number;
};

// 提取默认处理器并推导其返回类型
const defaultProcessor = (data: InputConfig) => ({
  isRoot: data.root,
  isBasic: data.basic,
  value: data.value * 5
});
type BaseConfig = ReturnType<typeof defaultProcessor>;

// 泛型生成器类型,T用于累积所有扩展处理器的返回类型交叉
type ConfigureGenerator<T = {}> = {
  addProcessor<U>(handler: (data: InputConfig) => U): ConfigureGenerator<T & U>;
  done(): BaseConfig & T;
};

function configure(): ConfigureGenerator {
  const config: InputConfig = {
    root: true,
    basic: true,
    value: 10,
  };

  const processors: ((data: InputConfig) => unknown)[] = [defaultProcessor];

  return {
    addProcessor(handler) {
      processors.push(handler);
      // 类型断言修正链式调用的泛型跟踪
      return this as unknown as ConfigureGenerator<
        BaseConfig & ReturnType<typeof handler>
      >;
    },

    done() {
      return Object.assign({}, ...processors.map(p => p(config))) as BaseConfig & ReturnType<typeof processors[number]>;
    }
  };
}

关键细节说明

  1. 泛型链式跟踪:
    ConfigureGenerator<T>中的T用于累积每次addProcessor添加的处理器返回类型交叉。每次调用addProcessor<U>,都会返回新的ConfigureGenerator<T & U>,实现类型的链式累积。

  2. 自动类型提取与合并:

    • 用ReturnType<typeof handler>自动提取处理器的返回类型,无需手动声明。
    • done()的返回类型为BaseConfig & T,自动合并默认类型与所有扩展类型,重复属性的类型会按交叉规则自动覆盖。
  3. 类型断言的作用:
    由于JS中this的运行时特性,TypeScript无法自动推导链式调用中this的泛型变化,因此需要用类型断言手动修正类型。

使用验证

const res = configure()
  .addProcessor(data => ({
    isBasic: false,
    value: data.value * 10,
    extraProp: "hello"
  }))
  .addProcessor(data => ({
    isRoot: false,
    anotherProp: 123
  }))
  .done();

// 自动推导res类型为:
// { isRoot: boolean; isBasic: boolean; value: number; extraProp: string; anotherProp: number; }

内容的提问来源于stack exchange,提问作者Andrey Popov

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 02:57:44