Home > Software design >  Typing with keyof and template literal
Typing with keyof and template literal

Time:05-21

For each arbitrary object, e.g.

{
  name: string;
  age: number;
}

I'd like to have a type e.g.:

type ConsumerFn<T> = (value: T) => void;
type Consumer = {
  nameConsumer: ConsumerFn<string>;
  ageConsumer: ConsumerFn<number>;
}

How can I make this typing generic? I'm imaging:

type Consumer<T> = {
  [`${K in keyof T}Consumer`]: ConsumerFn<K>
}

but that does not work.

CodePudding user response:

The following mapping type should work, transforming the properties into your template literals is a bit verbose

type ConsumerFn<T> = (value: T) => void;

type Consumer<Type> = {
    [Property in keyof Type as `${string & Property}Consumer`]: ConsumerFn<Type[Property]>
};

type Foo = {
  name: string;
  age: number;
}

type FooConsumer = Consumer<Foo>;

Results in

type FooConsumer = {
   nameConsumer: ConsumerFn<string>;
   ageConsumer: ConsumerFn<number>;
}

CodePudding user response:

type ConsumerGeneric<T> = keyof T extends string ? {
  [K in keyof T as `${K}Consumer`]: ConsumerFn<T>
} : never;
  • Related