Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Make function param accepts only keys from variable object

Tags:

typescript

I have an object with defined type for value:

type Type = { [key: string]: ValueType }

const variable: Type = {
    key1: valueType,
    key2: valueType,
    key3: valueType,
}

And I have a function func, which I want to be accepting only string with values from variable's keys:

func('key1')     // OK
func('key2')     // OK
func('key3')     // OK
func('keyother') // Error
func(3)          // Error

And this is what I have done when making type for func:

type FuncType = (param: keyof typeof variable) => any
const func: FuncType = ...

But I can only achieve one:

  • typing for variable's value

or

  • typing for func's param accept only variable's key

Not both.

  • If I'm typing for variable's value const variable: Type = {, param has string type and I can pass any string to func call, which is wrong
  • If I'm not typing for variable's value const variable: Type = {, func now typing param correctly but it makes variable accept anything as value.

Another way I can think about is predefined Type with list of keys ([key1, key2, ...]). But I don't want to maintain two list of the same thing. How can I achieve both of them without doing this way.

Typescript playground for this problem, which has some comments to describe problem more clearfully.

like image 705
namgold Avatar asked Jul 19 '26 08:07

namgold


1 Answers

You have to use helper function that does nothing just validates type.

const makeType = <T extends Type = Type>(obj: T) => obj

const variable = makeType({
    key1: 0,
    key2: 0,
    key3: 0,
})

Playground

UPDATE: TypeScript 4.9 will make this possible with satisfies

Announcing TypeScript 4.9 Beta

const variable = {
    key1: valueType,
    key2: valueType,
    key3: valueType,
} satisfies Record<string, ValueType>
like image 59
BorisTB Avatar answered Jul 22 '26 01:07

BorisTB



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!