Turbopack이 기본 번들러가 되면서 바뀌는 것들
선택이 아니라 기본값이 됐다
Turbopack은 15까지는 next dev --turbo로 켜야 하는 옵션이었습니다. 16부터는 next dev와 next build 모두 Turbopack이 기본입니다. 공식 벤치마크는 프로덕션 빌드 2~5배, Fast Refresh는 최대 10배 빠르다고 말합니다. 체감상으로도 중대형 프로젝트에서 빌드 시간이 눈에 띄게 줄어듭니다.
빠른 건 반가운 일이지만, 여기서 짚어야 할 건 속도가 아니라 호환성입니다.
webpack 설정이 있다면 멈춰서 확인해야 한다
next.config.ts의 webpack() 커스텀 설정, 일부 webpack 전용 로더나 플러그인을 쓰고 있었다면 Turbopack에서 그대로 동작한다는 보장이 없습니다. Turbopack은 webpack 설정 형식을 이해하지 못합니다 — 별개의 번들러니까요. 자주 걸리는 지점은 다음과 같습니다.
- SVG를 컴포넌트로 불러오는
@svgr/webpack같은 커스텀 로더 webpack.DefinePlugin으로 직접 전역 상수를 주입하던 설정- 모노레포에서
resolve.alias를 손으로 건드려 패키지를 재매핑하던 설정
이런 프로젝트는 업그레이드 직후 next dev가 뜨더라도, 해당 로더가 처리하던 파일을 실제로 임포트하는 화면에서 에러가 납니다. 빌드 성공이 곧 정상 동작을 뜻하지 않는다는 걸 기억해야 합니다.
// next.config.ts — 여전히 webpack이 필요하다면 명시적으로 되돌릴 수 있다
const nextConfig = {
turbopack: {
// Turbopack 전용 옵션은 여기로
},
};
export default nextConfig;당장 Turbopack으로 옮기기 어려운 설정이 있다면, 알려진 webpack 전용 옵션이 남아 있는 동안은 기존 방식을 유지하고 별도 브랜치에서 Turbopack 전환을 검증한 뒤 옮기는 편이 안전합니다. "빌드가 빨라졌다"는 이유만으로 검증 없이 프로덕션에 바로 올릴 사안은 아닙니다.
에러 메시지를 읽는 법이 달라진다
webpack에서 익숙했던 에러 스택과 Turbopack의 에러 스택은 형식이 다릅니다. 특히 로더 관련 에러는 "어떤 파일을 처리하다 실패했는지"가 이전만큼 친절하게 나오지 않는 경우가 있습니다. 원인을 못 찾겠다면 해당 import 문을 지워보고 에러가 사라지는지 이분 탐색하듯 좁혀가는 게 실용적입니다 — 스택 트레이스만 보고 바로 원인을 짚기 어려운 상황을 몇 번 겪었습니다.
CI 환경에서만 재현되는 문제도 주의해야 합니다. 로컬 macOS/Linux에서는 멀쩡한데 CI의 Docker 이미지에서만 Turbopack 빌드가 실패하는 사례가 커뮤니티에 보고되어 있습니다. 대부분 네이티브 바이너리(Turbopack은 Rust로 작성되어 플랫폼별 바이너리를 받습니다) 캐시가 꼬였을 때 발생하므로, CI에서만 나는 실패라면 의존성 캐시를 지우고 다시 설치하는 것부터 시도해볼 만합니다.