在 TypeScript 中使用解构和剩余类型的函数参数

Typed function parameters using destructuring and rest in TypeScript

我有一个功能:

export default ({
  input: { name, onChange, value, ...restInput },
  meta,
  ...rest
}) => (
  ...
);

鉴于 'name' 是一个字符串,'onChange' 是一个函数,'value' 是一个字符串,'meta' 是一个对象,我如何为这些添加类型参数? 我最好的猜测是这样的:

export default ({
  input: { (name: String), (onChange: function), (value: String), ...restInput },
  (meta: Object),
  ...rest
}) => (
  ...
);

不过好像有语法错误。甚至我不知道如何向剩余参数添加类型。

要向解构参数添加类型声明,您需要声明包含 对象 的类型。

来自typescript documentation

... Confusingly, the colon here does not indicate the type. The type, if you specify it, still needs to be written after the entire destructuring...

let { a, b }: { a: string, b: number } = o;

关于深度嵌套解构的 PSA:

Use destructuring with care. As the previous example demonstrates, anything but the simplest destructuring expression is confusing. This is especially true with deeply nested destructuring, which gets really hard to understand even without piling on renaming, default values, and type annotations. Try to keep destructuring expressions small and simple. You can always write the assignments that destructuring would generate yourself.

解构函数参数

在函数中,这是为解构参数声明类型的方式:

export default ({ a, b }: {a: string, b: number}) => (
  ...
);

虽然在更长的示例中这看起来很糟糕:

export default ({
  input: { name, onChange, value, ...restInput },
  meta,
  ...rest
}: {
  input: { 
    name: string, onChange: ()=>void, value:string, ...restInput 
  }, meta: object
}) => (
  ...
);

看起来很糟糕,所以你在这里能做的最好的事情就是为你的参数声明一个接口并使用它而不是内联类型:

interface Params {
  input: { 
    name: string;
    onChange: ()=>void;
    value: string;
  }; 
  meta: object;
}

export default ({
  input: { name, onChange, value, ...restInput },
  meta,
  ...rest
}: Params) => {};

Playground

Article with much more

其余参数

对于其余参数,根据您对这些类型的期望,您可以使用 index signature:

interface Params {
  // This needs to match the other declared keys and values
  [key: string]: object;
  input: { 
    [key: string]: string | (() => void);
    name: string;
    onChange: ()=>void;
    value: string;
  }; 
  meta: object;

}

export default ({
    input: { name, onChange, value, ...restInput },
    meta,
    ...rest
}: Params) => { };

这会给 ...rest 一个类型 {[key: string]: object} 例如。

Rest parameter playground