the node before which the new node is to be inserted is not a child of this node 에러를 해결해 보자
2025-06-02어느 날 외국 유저가 CS 채널에 문의를 남겼는데, 특정 페이지에서만 항상 이런 오류가 발생한다는 것이었습니다:
the node before which the new node is to be inserted is not a child of this node
1. 문제 발견
처음에는 재현이 어려워 정확한 원인을 파악하기가 쉽지 않았습니다. 하지만 다양한 테스트 케이스를 시도해본 결과, 브라우저 자동 번역 기능이 활성화된 상태에서 해당 페이지로 접근했을 때 발생한다는 사실을 발견했습니다.
프로젝트 배경
현재 회사 플랫폼은 웹과 앱(웹뷰)로 구성되어 있으며, 외국 유저는 모두 웹으로만 접근 가능합니다. 아직 다국어를 지원하지 않아 외국 유저는 한글을 그대로 보거나 브라우저 자동 번역을 사용해야 합니다.
2. 원인 분석
정확한 원인을 파악하기 위해 문제가 되는 페이지의 컴포넌트들을 하나하나 주석 처리하면서 분석한 결과, 문제가 되는 코드를 찾았습니다.
문제의 코드
<span>{productValue} 개</span>
이 코드는 React에서 다음과 같이 해석됩니다:
productValue는 숫자 등의 동적 값" 개"는 정적인 문자열
따라서 React는 두 개의 텍스트 노드로 분리해서 렌더링합니다:
<span>
#text: "3"
#text: " 개"
</span>
브라우저 자동 번역의 동작
하지만 브라우저 자동 번역 기능은 이 구조를 그대로 유지하지 않습니다.
예를 들어 "3 개"를 "3 pcs"로 번역할 경우:
- 두 개의 텍스트 노드를 하나의 번역된 문자열로 통합하거나
- DOM 구조를 변경하게 됩니다
오류 발생 메커니즘
- React가 초기 렌더링 시 두 개의 텍스트 노드를 생성합니다
- 브라우저 자동 번역이 DOM 구조를 변경합니다
- React가 이후 업데이트 과정에서 노드를 특정 위치에 삽입하려 합니다
- 기존의 참조 노드가 이미 DOM에서 분리되었거나 위치가 달라진 상태입니다
- DOMException 발생: "the node before which the new node is to be inserted is not a child of this node"
3. 해결 방법
해결 방법은 간단합니다. 두 개로 나눠진 텍스트 노드를 React가 하나의 노드로 처리하게 만드는 것이죠.
AS-IS (문제 코드)
<span>{productValue} 개</span>
<!-- React가 두 개의 텍스트 노드로 분리 -->
TO-BE (해결 코드)
<span>{`${productValue} 개`}</span>
<!-- React가 하나의 텍스트 노드로 처리 -->
이렇게 작성하면:
- React는 전체 문자열을 하나의 텍스트 노드로 처리합니다
- 브라우저 자동 번역도 이 텍스트를 한 번에 번역합니다
- DOM 구조의 변경 없이 안정적으로 동작합니다
4. 일반화된 해결 패턴
비슷한 문제를 예방하려면 다음 패턴을 따르세요:
// ❌ 피해야 할 패턴
<div>{count}개</div>
<div>{price}원</div>
<div>{name}님</div>
// ✅ 권장 패턴
<div>{`${count}개`}</div>
<div>{`${price}원`}</div>
<div>{`${name}님`}</div>
정리
문제의 핵심:
- React가 동적 값과 정적 문자열을 별도의 텍스트 노드로 렌더링합니다
- 브라우저 자동 번역이 DOM 구조를 변경합니다
- React의 재조정(reconciliation) 과정에서 오류가 발생합니다
해결책:
- 템플릿 리터럴을 사용해 하나의 텍스트 노드로 통합합니다
배운 점: 사실 그동안 자동 번역을 많이 사용했지만 이로 인해 발생할 수 있는 문제점은 생각하지 않았습니다. 이번 이슈 덕분에 브라우저가 자동 번역을 어떻게 처리하는지 이해할 수 있었고, 실무에서 유용한 경험이 되었습니다.
다국어를 지원하지 않는 서비스라면 이런 문제를 미리 예방하는 것이 좋겠죠!