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

如何在同一对象中使用某字段的参数类型作为另一字段的返回类型?

解决TypeScript中with函数返回类型与选中method参数类型严格匹配的问题

看起来你遇到的核心问题是:当在onSuccess里指定某个method时,with函数的返回类型没有被精确约束为该方法的参数类型,而是变成了所有方法参数类型的联合。这是因为原来的泛型设计让G默认是所有键的联合,导致类型推断范围太宽。

问题根源分析

原来的ReturnedObject泛型中,G extends keyof T = keyof T给G设置了默认值为所有方法键的联合,这就导致Parameters<...>会计算所有方法参数的联合类型。另外,你代码里的ReturnedObject<T>[G]是错误的引用——ReturnedObject的属性是property和onSuccess,你实际需要的是T[G]['q']的参数类型。

解决方案:用映射类型绑定method与with的类型

我们可以通过创建一个泛型的OnSuccess类型,让每个method和对应的with返回类型形成一一绑定的联合成员。这样TypeScript就能根据你指定的method自动窄化with的类型约束。

调整后的完整类型定义和使用示例如下:

// 定义辅助类型:提取指定方法的q函数的参数类型
type MethodParams<T, G extends keyof T> = Parameters<T[G]['q']>;

// 定义OnSuccess类型:让每个method和对应的with返回类型绑定
type OnSuccess<T> = {
  [G in keyof T]: {
    method: G;
    with: () => MethodParams<T, G>;
  };
}[keyof T];

interface ReturnedObject<T> {
  property: string;
  onSuccess: OnSuccess<T>;
}

interface Option<T> {
  [key: string]: {
    q: (...args: any[]) => string | ReturnedObject<T>;
  };
}

function fn<T extends Option<T>>() {}

测试验证

现在当你使用这个定义时,TypeScript会自动根据method的值约束with的返回类型:

fn({
  method1: {
    q: (name: string) => 'hello!' + name,
  },
  method2: {
    q: () => ({
      property: 'value',
      onSuccess: {
        method: 'method1',
        with: () => ['Mo'], // ✅ 合法,完全匹配method1的参数类型[string]
        // with: () => [], // ❌ 报错:类型'[]'不能赋值给类型'[string]'
      }
    })
  }
});

为什么这个方案有效?

OnSuccess<T>是一个映射类型的联合:我们遍历T的所有键,为每个键生成一个{ method: G; with: () => ... }的对象,然后通过[keyof T]把这些对象转换成联合类型。当你在onSuccess中指定method: 'method1'时,TypeScript会自动将联合类型窄化到对应的成员,从而with的返回类型就被精确约束为method1的参数类型,而不是所有方法的联合类型。

内容的提问来源于stack exchange,提问作者Chemss-Eddine BenHassine

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.01 02:04:06