

태그를 만들고 삭제하는 코드를 작성하던 중 이와 같은 문제가 발생했다.
그 외에도 event.target에 어떤 속성이 없다는 에러가 종종 발생했다.
이럴 때에는 event 파라미터에서 모든 타입을 해결하려고 하지 말고, event와 target을 분리해서 각각의 타입을 지정해주면 된다.
혹은 currentTarget을 이용해서 해결할 수 있었다.
const deleteTagItem = (e: React.MouseEvent<HTMLButtonElement>) => {
//여기서 에러 발생
const deleteTagItem = e.target.parentElement;
//'EventTarget' 형식에 'parentElement' 속성이 없습니다.ts(2339)
if (deleteTagItem.firstChild) {
const dItem = deleteTagItem.firstChild.textContent;
const filteredTagList = tagList.filter((tagItem) => tagItem !== dItem);
setTagList(filteredTagList);
}
};
event와 target을 분리해서 각각의 타입을 지정
const deleteTagItem = (e: React.MouseEvent<HTMLButtonElement>) => {
const target = e.target as HTMLButtonElement;
const deleteTagItem = target.parentElement
if (deleteTagItem && deleteTagItem.firstChild) {
const dItem = deleteTagItem.firstChild.textContent;
const filteredTagList = tagList.filter((tagItem) => tagItem !== dItem);
setTagList(filteredTagList);
}
};
currentTarget 사용
const deleteTagItem = (e: React.MouseEvent<HTMLButtonElement>) => {
const deleteTagItem = e.currentTarget.parentElement as Node;
if (deleteTagItem.firstChild) {
const dItem = deleteTagItem.firstChild.textContent;
const filteredTagList = tagList.filter((tagItem) => tagItem !== dItem);
setTagList(filteredTagList);
}
};
const handleSearchValue = (e: KeyboardEvent<HTMLInputElement>) => {
setSearchValue(e.currentTarget.value);
setSearchValue(e.target.value); // error 발생
};
Property 'value' does not exist on type 'EventTarget'. ts(2339)
위와 같은 에러가 나온다.
왜 그러냐면
e.target과 e.currentTarget의 type alias가 다르기 때문이다
위의 코드를 기준으로 살펴보면
currentTarget과 달리 EventTarget에 HTMLInputElement를 확장하지 않았다.
HTMLInputElement를 확장하지 않은 이유는 EventTarget이 될 수 있는 요소들에는 HTML Element 말고 다른 요소들도 있기 때문이라고 한다.
⇒XMLHttpRequest, FileReader, AudioNode, AudioContext 등등
currentTarget과 target이 동일할 경우는 currentTarget을 사용하자.
const handleSearchValue = (e: KeyboardEvent<HTMLInputElement>) => {
// 1. currentTarget과 target이 동일할 경우
setSearchValue(e.currentTarget.value);
// 2. n개의 DOM 구조일 경우 -> currentTarget 기준으로 value 찾기
const target = e.currentTarget;
const findId = target.querySelector('span').id
setSearchValue(findId);
const findValue = target.querySelector(span).value
setSearchValue(findValue);
};
불가피하게 target을 사용해야 되는 경우가 많다. 그럴 때는 currentTarget을 기준으로 DOM을 탐색해야 한다. 이 경우 currentTarget 밑으로 자식이 n개인 상태에서 자식들의 구조가 복잡한 상황에서 특정 자식을 찾는 경우 findChild(’childName’) 식으로 순차적으로 [자식 → 자식의 자식 → … ] 순으로 재귀 탐색을 해야 해서 비용이 큰 작업이 돼서 부담이 될 수 있기 때문에 아래와 같은 방법을 사용할 수도 있다.
const handleSearchValue = (e: KeyboardEvent<HTMLInputElement>) => {
setSearchValue((e.target as HTMLInputElement).value);
};
보통 타입 단언을 지양하지만, target이 되는 DOM이 문서에서 명확하게 정해져 있다면 이 경우는 타입 단언하는 방식을 사용해도 괜찮을 것 같다고 한다.
e: ChangeEvent<HTMLInputElement>로 타입을 줄 경우
ChangeEvent는 EventTarget을 확장하고 있어 해당 에러가 발생하지 않는다.
참고
좋은 글 감사합니다!