6

I have the following function:

    const infer = (...params: string[]): Record<string, string> => {
      const obj: Record<string, string> = {};
      // Put all params as keys with a random value to obj
      // [...]
      return obj;
    }

This function will take n strings and return an object containing exactly those strings as keys, with random values.

So infer("abc", "def") might return {"abc": "1337", "def":"1338"}.

Is there any way to infer the return type to get complete type-safety from this function? The code of the function guarantees that each key will be present in the returned object and that each value will be a string.

1 Answer 1

5

You could declare it like this:

const infer = <T extends string[]>(...params: T): Record<T[number], string> => {
  const obj: Record<string, string> = {};
  // Put all params as keys with a random value to obj
  // [...]
  return obj;
};

const t = infer("a", "b", "c") // const t: Record<"a" | "b" | "c", string>

Playground

Sign up to request clarification or add additional context in comments.

8 Comments

Amazing, can you explain what the T[number] part does exactly?
Sure. If you have type MyTuple = ["a", "b", "c"], you can use the lookup/index access operator to access item types by their numeric index value, e.g. MyTuple[0] has type "a". number in MyTuple[number] simply stands for all possible numeric index values, so MyTuple[number] is the union of all possible item types, which are your desired string values.
What if I pass the keys in as a single list? How can I get the same output?
@etarrowo You can drop the rest parameter from infer and let T extend string, like here
awesome thank you @ford04 this one has been puzzling me for a bit
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.