프로그래밍/Node.js

Node.js 5장 패키지 매니저 npm

p-a-r-k 2019. 1. 11. 19:20
반응형

* 해당 글은 (주)길벗 `Node.js교과서` 내용을 바탕으로 복습 차 정리중입니다.



앞장에서 모듈없이 구현하거나 내부모듈만으로 구현해보면서 서비스를 직접 구현하기에는 벅참을 느꼈을 것입니다.

세상에는 많은 자바스크립트 개발자가 있고, 그들이 이미 많은 유용한 코드를 작성해놓았습니다. 그리고 공개했습니다.

그런 코드들이 공개되어있는 npm이라는 패키지매니저에대해 알아봅니다.


5.1 npm알아보기

node package manager의 약어로, 이름 그대로 노드 패키지 매니저 입니다.

npm에 업로드된 노드 모듈을 패키지라고 부릅니다. 모듈이 다른 모듈을 사용할 수 있는것처럼,

패키지가 다른 패키지를 사용할 수도 있습니다. 이를 의존 관계라고 부릅니다.

yarn

npm의 대체자로 yarn이 있습니다. 페이스북이 내놓은 패키지매니저 입니다.

npm과 비교해서 편한기능이 다소들어있지만, 따로 설치해야합니다.

npm서버가 느릴 경우 yarn으로 대신 설치할 수 있습니다.


5.2 package.json으로 패키지 관리하기

서비스에 필요한 패키지를 하나씩 추가하다보면 패키지수가 100개가 넘어가기 쉽습니다.

그리고 사용한 패키지마다 고유한 버전이 있으므로 어딘가에 기록해두어야합니다.

같은 패키지라도 버전별로 기능이 다를 수 있으므로 서비스 배포시동일한 버전을 설치하지않으면 문제가 생깁니다.

이렇게 설치한 패키지의 버전을 관리하는 파일이 package.json입니다.


npm은 package.json을 만드는 명령어를 제공합니다.

테스트 작업 폴더를 하나만들고 해당 경로로 콘솔에서 이동하여 npm init을 실행해봅니다.


프로젝트 이름과 버전, 설명 등을 입력하여 프로젝트 초기화를 할 수 있습니다.

순서대로 패키지이름/버전/설명/실행파일진입점/테스트명령어/git저장소주소/npm홈페이지에서의 검색키워드/만든사람/라이선스 입니다.

실행이 완료되면 해당 폴더 내에 package.json이 생성됩니다.

script부분은 npm명령어를 저장해두는 부분입니다. 

콘솔에서 npm run <스크립트명령어>를  입력하면 해당 스크립트가 실행됩니다.

예를들어 npm run test를 하면 위 파일에 정의된 echo ...부분이 실행됩니다.

test스크립트 외에도 script속성에 명령어 여러개를 등록하고 사용할 수 있습니다.

보통 start나 dev, build등을 사용합니다. start나 test는 run을 생략해도 됩니다.


npm install <패키지명>을 사용하여 6장에서 사용할 express를 설치해봅니다.

install은 "i"로 줄여 쓸 수 있습니다. 설치한 express가 package.json에 기록됩니다.


dependencies라는 속성이 생겼고, express라는 이름과 버전이 저장되었습니다.

버전앞의 ^는 특별한 의미가 있습니다. 다음절에서 알아봅니다.

--save 옵션

원래는 패키지 설치 시 npm install <패키지명> --save 옵션을 붙였습니다.

dependencies에 추가하라는 옵션이지만 npm@5부터는 기본값으로 저절로 추가됩니다.

추가로 node_modules라는 폴더도 생성되었습니다. express에 의존하는 패키지들이 설치 된 것입니다.

그많은 패키지들의 의존관계를 위해 package.json이 필요합니다.

package-lock.json이라는 파일도 볼 수 있는데, express외에도 내부의존관계를 이 파일에 저장합니다.


이번엔 모듈 여러개를 설치해봅니다.

패키지들이 dependencies속성에 추가 됩니다.

개발용 패키지도 있습니다. 실제 배포시에는 사용되지않고, 개발중에만 사용되는 패키지들입니다.

npm install --save-dev <패키지명> 으로 설치합니다. --save-dev는 -D로 줄여쓸 수 있습니다.


나중에 사용할 nodemon을 설치해봅니다.


"devDependencies" 속성이 생겼습니다. 개발용 패키지들만 따로 관리합니다.

package.json
1
2
3
"devDependencies": {
     "nodemon": "^1.18.9"
  }


npm엔 전역설치 라는 옵션도 있습니다. npm install --global <패키지명> (-g로 줄일 수 있습니다.)

현재폴더의 node_modules가 아닌 npm이 설치된 폴더(C://.../사용자/AppData/Roamng/npm)에 설치합니다.

해당 폴더의 경로는 시스템 환경 변수에 등록되어 있으므로 전역 설치 시 콘솔에서 커맨드로 사용할 수 있습니다.

전역 패키지 한개를 설치해봅니다.


리눅스나 macOS는 전역 설치 시 관리자 권한이 필요하므로 sudo를 앞에 붙여줍니다.

rimraf

리눅스나 macOS의 rm -rf 명령어를 윈도에서도 사용할 수 있게 해주는 패키지입니다.

rm -rf는 파일이나 폴더를 지우는 명령어입니다.

전역 설치한 패키지는 package.json에 기록되지않습니다.

설치한 rimraf를 사용해봅니다. node_modules폴더가 삭제됩니다.


express와 의존 파일들이 들어있는 node_modules가 삭제되어도 package.json파일만 있으면 다시 설치할 수 있습니다.

npm install 명령어를 사용하면 package.json을 기반으로 다시 설치됩니다.

중요한파일은 package.json 입니다.

npx 명령어

전역설치를 기피하는 개발자들도 있습니다. 전역 설치한 패키지는 package.json에 기록되지 않아서,

다른환경에서 설치할 때 어려움이 있을 수도 있기때문입니다. 이런 경우를위해 npx 가 있습니다.


위와같이 rimraf모듈을 devDependencies 속성에 기록한 후 npx명령어와 함께 실행하면 전역설치와 같은 효과를 얻습니다.

5.3 패키지 버전 이해하기

노드패키지 버전들을 보면 세자리로 이루어져 있습니다. 심지어 노드의 버전도 세 자리 입니다.

이유는 SemVer방식의 버전 넘버링을 따르기 때문입니다. Semantic Versioning(유의적버전)의 약어입니다.

버전을 구성하는 세자리가 모두 의미를 가지고 있다는 뜻 입니다.

각각 패키지는 모두 버전도다르고 의존관계도 복잡합니다.

만약 어떤 패키지의 버전업이 되었는데 그 패키지를 사용하는 다른 패키지에서 에러가 발생하면 문제가 됩니다.

따라서 버전 번호를 어떻게 정하고 올리는지를 명시하는 규칙이 등장했는데, 이것이 SemVer입니다.

SemVer

ex) 0.0.1

버전의 첫번째자리는 major 버전입니다. 주버전이 0이면 초기 개발 중 이라는 뜻입니다.

1부터는 정식버전이라는 뜻입니다. major버전은 하위호환이 안 될 정도로 내용이 수정었을 때 올립니다.

예를들어 1.5.0에서 2.0.0으로 올렸다는 것은,,,

1.5.0 버전 패키지를 사용하고 있던 사람들이 2.0.0으로 업데이트 했을 때 에러가 발생할 확률이 크다는 뜻입니다.


두번째자리는 minor 버전입니다. minor 버전은 하위 호환이 되는 기능 업데이트 시에 올립니다.

버전을 1.5.0에서 1.6.0으로 올렸다면 1.5.0사용자가 1.6.0으로 업데이트해도 아무런 문제가 없어야 합니다.


세번째자리는 patch 버전입니다. 새로운기능이 추가되었다기보다는 기존기능에 문제가 있어서 수정한 버전을 내놓습니다.

1.5.0에서 1.5.1 처럼요. 당연히 업데이트시에도 아무런 문제가 없어야 합니다.

package.json에는 SemVer식 세 자리 버전 외에도 버전 앞에 ^나 ~, >, <같은 문자가 붙어있습니다.

업데이트시 어떤 버전까지 설치할지 지정한 것 입니다. 가장 많이 보는 기호가 ^인데 minor버전까지만 설치또는 업데이트 합니다.

npm i express@^1.1.1 이면 1.1.1 <= 버전 < 2.0.0까지 설치됩니다. (1.x.x)

~ 기호는 patch 버전까지입니다. ~보단 ^가 많이 사용됩니다. minor버전까지는 하위호환이 보장되기 때문입니다.

추가로 @latest도 사용하는데, 최신버전의 패키지를 설치합니다. ex) npm i express@latest



5.4 기타 npm 명령어

npm으로 설치한 패키지를 사용하다 보면 새로운 기능이 추가되거나 버그를 고친 버전이 나옵니다.

npm outdated 명령어로 업데이트가능한 패키지가 있는지 확인 가능합니다.


current와 wanted가 다르면 업데이트가 필요한 경우입니다. 위 테스트는 제가 npm i 로 설치를 아직안해서 MISSING이 나오는것 같네요.

만약 업데이트가 가능한 목록이 있다면 npm update로 wanted에 적힌 버전으로 업데이트 됩니다.

npm uninstall <패키지명> 은 해당 패키지를 제거합니다. 또한, package.json과 node_modules폴더에서도 삭제됩니다. = npm rm <패키지명>

npm search <검색어>로 패키지를 검색할 수도 있습니다. package.json에 정의 된 keyword가 이 떄 사용됩니다.

검색결과가 적은 키워드로 검색해보겠습니다. 

npm info <패키지명>은 세부 정보를 파악할 때 사용합니다.

package.json의 내용과 의존관계, 설치가능한 버전정보 등이 표시됩니다.


npm adduser는 npm에서 가입한 계정으로 로그인을 위한 명령입니다. 패키지 배포 시 로그인이 필요합니다.

npm whoami : 로그인 한 사용자가 누구인지 확인. 로그인안되어 있으면 에러발생.

npm logout : adduser로 로그인한 계정을 로그아웃

npm version <버전> : package.json의 버전을 올려줌. major, minor, patch 문자열을 넣어서 해당부분을 1 증가도 가능.

npm deprecate <패키지명><버전> <메시지>: 해당패키지사용시 경고 메시지를 띄우게 할 수 있음.

npm publish : 자신이 만든 패키지를 배포할 때 사용

npm unpublish : 배포한 패키지를 제거할 때 사용. 24시간 이내에 배포한 패키지만 제거가능. (다른사람이 사용하는 의존성 관계때문)



5.5 패키지 배포하기

패키지를 배포하려면 일단 https://www.npmjs.com/ 에서 계정을 만들어야합니다.

그 후 콘솔에서 npm adduser 명령어를 입력하여 로그인합니다.

이제 패키지로 만들 코드를 작성합니다. package.json의 main부분의 파일명과 일치해야 진입점으로 인식합니다.

index.js
1
2
3
module.exports = () => {
   return 'hello package'
}

작성했다면, npm publish 를 사용하여 패키지를 배포해봅니다. 

저는 park_test라는 이름으로 패키지를 만들었기에 한번에 만들어졌지만, 흔한이름으로 한다면 중복이 생겨 에러가발생합니다.

npm은 패키지명이 겹치는 것을 허용하지 않습니다. npm info <패키지명>으로 원하는 패키지명이 있는지 체크할 수 있습니다.

package.json에서 원하는 이름으로 바꾼 후 다시 npm publish를 실행하면 아래처럼 진행됩니다.


배포가되고, 등록되었는지 확인해봅니다.

정보가 나오면 성공입니다.

원하는 이름이 사용중이라면..

해당 이름의 패키지가 활발하게 유지된다면 아쉽지만 다른이름을 사용해야합니다..

하지만 아무의미없이 이름만 차지하고 있다면 npm owner ls <패키지명>으로 해당 패키지 제작자의 이메일을 확인하고 메일을 보내보세요.

메일 보낼 때 CC(참조)로 support@npmjs.com 을 지정하면 npm 지원팀에게도 메일이 갑니다.

몇 주간 이름 분쟁이 해결되지않으면 npm팀에서 해결해줍니다.


24시간이 지나면 삭제할 수 없으므로 바로 삭제해보도록 합니다.

npm unpublish <패키지명> --force  입니다.


삭제 후 npm info로 404 에러발생을 확인했습니다. 지워졌습니다.




반응형