I have a use case which I think would be perfect for Typescript's Pick types.
Here's a trimmed down example:
interface CreditCard {
name: string;
year: number;
expired: boolean;
}
function setValue(key: keyof CreditCard, value: Pick<CreditCard, typeof key>) {
// do stuff...
}
However, when I try calling this function:
setValue("name", "rick");
Typescript (2.3.4) gives the following error:
error TS2345: Argument of type '"rick"' is not assignable to parameter of type 'Pick<CreditCard, "name" | "year" | "expired">'.
Also, I do not have an instance of CreditCard
available to pass in as an argument, so changing the function to take a CreditCard
as a third parameter is not possible in my use case.
The "Type 'string' is not assignable to type" TypeScript error occurs when we try to assign a value of type string to something that expects a different type, e.g. a more specific string literal type or an enum. To solve the error use a const or a type assertion.
The error "Argument of type string | undefined is not assignable to parameter of type string" occurs when a possibly undefined value is passed to a function that expects a string . To solve the error, use a type guard to verify the value is a string before passing it to the function.
The "Type 'string | null' is not assignable to type string" error occurs when a possibly null value is assigned to something that expects a string . To solve the error, use a non-null assertion or a type guard to verify the value is a string before the assignment.
The "Type 'undefined' is not assignable to type" error occurs when a possibly undefined value is assigned to something that expects a different type. To solve the error, use the non-null assertion operator or a type guard to verify the value is of the specific type before the assignment.
Pick<Obj, Props>
creates a type that looks like Obj
with only the properties specified by Props
, whereas your example is trying to use it to get the type of a single property, which should instead be done like this: CreditCard[KeyType]
Your setValue function should look like this:
function setValue<K extends keyof CreditCard>(key: K, value: CreditCard[K]) {
// do stuff...
}
You set up a generic type K which is a string literal type for one or more of the keys of CreditCard
. Then you use that type to grab the type of a property off of CreditCard
. When the function is invoked, the type system will narrow K
as far as it can and use that to figure out a specific type for the value
argument.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With