팀 프로젝트에서 필요한 라이브러리 설치 후, 프로젝트를 클론하는 과정에서 에러를 만났다. npm install
로 설치했을 때 다음과 같이 npm 에러가 나왔는데, 프로젝트에 필요한 에디터 라이브러리인 TOAST-UI의 의존성 문제였다. root project는 react@"^18.2.0"
인데, @toast-ui/react-editor@3.2.2
는 react@17.0.1
에 의존하고 있기 때문에 나타난 문제인 것 같다. (처음에 CRA를 했을 때, 최신 버전의 react로 설치가 되기 때문에)
(base) front|local⚡ ⇒ npm i
npm ERR! code ERESOLVE
npm ERR! ERESOLVE could not resolve
npm ERR!
npm ERR! While resolving: @toast-ui/react-editor@3.2.2
npm ERR! Found: react@18.2.0
npm ERR! node_modules/react
npm ERR! react@"^18.2.0" from the root project
npm ERR! peer react@"^18.0.0" from @testing-library/react@13.4.0
npm ERR! node_modules/@testing-library/react
npm ERR! @testing-library/react@"^13.4.0" from the root project
npm ERR! 6 more (react-dom, react-router, react-router-dom, ...)
npm ERR!
npm ERR! Could not resolve dependency:
npm ERR! peer react@"^17.0.1" from @toast-ui/react-editor@3.2.2
npm ERR! node_modules/@toast-ui/react-editor
npm ERR! @toast-ui/react-editor@"^3.2.2" from the root project
npm ERR!
npm ERR! Conflicting peer dependency: react@17.0.2
npm ERR! node_modules/react
npm ERR! peer react@"^17.0.1" from @toast-ui/react-editor@3.2.2
npm ERR! node_modules/@toast-ui/react-editor
npm ERR! @toast-ui/react-editor@"^3.2.2" from the root project
npm ERR!
npm ERR! Fix the upstream dependency conflict, or retry
npm ERR! this command with --force, or --legacy-peer-deps
npm ERR! to accept an incorrect (and potentially broken) dependency resolution.
npm ERR!
npm ERR! See /Users/mina/.npm/eresolve-report.txt for a full report.
npm ERR! A complete log of this run can be found in:
npm ERR! /Users/mina/.npm/_logs/2022-12-23T16_13_37_060Z-debug-0.log
에러 코드에서 제안하는 것처럼 충돌을 해결하기 위해 --force
나 --legacy-peer-deps
옵션을 추가해 설치하는 방법이 있고, 찾아보니 아예 React의 버전을 낮추어 재설치하는 방법이 있었다. 두번째 방법은 나중에 찾게된 방법이라 프로젝트 진행 중에는 npm install --legacy-peer-deps
로 설치하기로 정했었다.
패키지 모듈에 다른 버전의 의존성이 있을 때, node_modules는 root project에 dependency와 패키지의 하위에 peer dependency를 두는 구조로 형성된다.(관련)
node_modules/@toast-ui/react-editor/package.json에 peerDependencies 속성에
"react": "^17.0.1"
버전에서 동작한다고 명시되어 있다.
peerDependencies
In some cases, you want to express the compatibility of your package with a host tool or library, while not necessarily doing arequire
of this host. This is usually referred to as a plugin. Notably, your module may be exposing a specific interface, expected and specified by the host documentation.In npm versions 3 through 6, peerDependencies were not automatically installed, and would raise a warning if an invalid version of the peer dependency was found in the tree. As of npm v7, peerDependencies are installed by default. 여기
실제로 패키지에서 import하지 않지만 의존성을 가지는 경우 명시하는 dependency이다. npm3~6까지는 자동으로 설치되지 않고, 경고만 준다. 하지만 npm7부터는 기본으로 설치되며 버전이 맞지 않을 경우 에러가 발생한다.
검색하다보니 TOAST-UI를 설치하면서 같은 문제를 겪은 블로그들이 많아서 반가웠다(?) 그리고 당시 프로젝트 땐 --legacy-peer-deps
flag로 설치하라는 의견을 보고 해결했지만, --force
로 강제 설치가 더 낫다는 의견도 많았다.
둘의 차이는 무엇이고 어떤 상황에서 써야할까??
The -f or --force argument will force npm to fetch remote resources even if a local copy exists on disk.
You have the option to retry with --force to bypass the conflict or --legacy-peer-deps command to ignore peer dependencies entirely (this behavior is similar to versions 4-6).
--force
는 강제 설치로 충돌을 우회할 수 있다고 하고, --legacy-peer-deps
는 npm 버전 4-6처럼 peerDependencies가 자동으로 설치되는 기능을 무시한다고 한다. 결과적으로 npm7부터 자동 설치되는 업데이트에서 파생된 문제였다. 이전에 프로젝트에 적용했던 방식으로는 다행히 라이브러리에 사용에 문제는 없었지만, peerDependencies가 존재하는 이유는 분명하고 해당 라이브러리를 사용할 때 버전 또한 함께 고려해야 할 것 같다.
감사합니다!