Typescript - TS7053

clean·2022년 6월 30일
0

Typescript 는 string 타입의 key 를 허용하지 않는다. (String Literal 또는 number 타입만 허용된다.)
따라서 아래 코드의 경우 Type 에러가 발생한다.

const friends = {
  peach: 'peach',
  neo: 'chico',
  lion: 'lion',
};

for (const key in friends) {
  // TS7053: Element implicitly has an 'any' type because expression of type 'string' can't be used to index type '{ peach: string; neo: string; lion: string; }'.
  // No index signature with a parameter of type 'string' was found on type '{ peach: string; neo: string; lion: string; }'.
  console.log(charctors[key]); // Compile Error
}

객체에 동적으로 속성을 할당하거나 key로 접근하려는 경우 객체의 형태에 따라 아래와 같이 적용할 수 있다.

key 값이 문자열이라는 것 외에 정해진 바가 없을 때 (index signiture 사용)

  • for loop 를 통해 접근하려는 객체 자체를 서버에서 받아 사용하는 경우 등 key 값에 대해 미리 정의해둘 수 없을 때
  • index signiture를 통해 key, value 의 타입만 정의해두고 사용하는 방법
interface Friends {
  [key: string]: string; // key 의 타입, value 의 타입만 정의
}

for (const key in friends) {
  console.log(friends[key]);
}

key 값이 명확하게 정해져 있을 때 (1)

type nameTypes = 'peach' | 'neo' | 'lion'; // 이렇게 key 값이 정해져있을 때
type Friends = {
  [name in nameTypes]: string;
};
const friends: Friends = {
  peach: 'peach',
  neo: 'neo',
  lion: 'lion',
};
for (const key in friends) {
  const name = key as nameTypes; // Type Assertion 필요함
  console.log(friends[name]);
}

key 값이 명확하게 정해져 있을 때 (2)

type nameTypes = 'peach' | 'neo' | 'lion';
type Friends = Record<nameTypes, string>; // key:nameTypes, value:string
const friends: Friends = {
  peach: 'peach',
  neo: 'neo',
  lion: 'lion',
};
for (const key in friends) {
  const name = key as nameTypes; // Type Assertion 필요함
  console.log(friends[name]);
}

다른 속성 값과 함께 사용하고 싶다면...?

// 예를 들어 이런 형태로 정의하고 싶음
interface Firends {
	type: string; 
	count: number; 
    // union으로 정의된 유형들
    peach: string; 
  	neo: string;
    lion: string;
}

// 방법(1) 활용 방식: 이렇게는 불가~!
type Friends = {
  type: string; // TS7061: A mapped type may not declare properties or methods.
  count: number;
  [name in nameTypes]: string;
};

// 방법(2) 활용 방식:  이렇게는 가능!
type nameTypes = 'peach' | 'neo' | 'lion';
type FriendsRecord = Record<nameTypes, string>;
interface Friends extends FriendsRecord {
  type: string;
  count: number;
}

참고 페이지

0개의 댓글