Search code examples
typescripttypeerror

Can not properly set value of object field


I need to set values of fields of person object which exists in employee object. But I can't do it properly without type errors

Here is my code:

interface IPerson {
   name: string;
   age: number;
}

interface IEmployee extends IPerson {
   salary: number;
}

const PersonTemplate: IPerson = {
  name: '',
  age: 0
}

const employee: IEmployee = {name: 'Name', age: 18, salary: 1000};
const person: IPerson = {...PersonTemplate};

for (const key in PersonTemplate) {
  const keyName = key as keyof IPerson;

  if (keyName in employee) person[keyName] = employee[keyName];
}

console.log(person);

The problem on line person[keyName] = employee[keyName]. Error text:

Type 'string | number' is not assignable to type 'never'.

Type 'string' is not assignable to type 'never'.

I tried to fix this by changing the line to person[keyName] = employee[keyName] typeof person[keyName] but I get new errors:

Type 'keyName' is not assignable to type 'never'.

Type 'keyName' cannot be used as an index type.

'keyName' refers to a value, but is being used as a type here. Did you mean 'typeof keyName'?

and when I hover mouse on keyName in typeof person[keyName] TS shows me that type keyName = /*unresolved*/ any

Please show how to solve this problem properly

P.S. in real there is more fields than given 3


Solution

  • If you want to answer why, I don't know excatly why TS lost track of typings in this case.

    If you want to make it works :

    function copyValue<T>(k: keyof T, target: T, source: T) {
      target[k] = source[k];
    }
    
    for (const key in PersonTemplate) {
      const keyName = key as keyof IPerson;
    
      if (keyName in employee) {
        copyValue(keyName, person, employee);
      }
    }