package.json을 사용하여 전역 및 로컬로 종속성을 설치하십시오.


189

npm을 사용하면 -g옵션을 사용하여 모듈을 전체적으로 설치할 수 있습니다 . package.json 파일에서 어떻게 할 수 있습니까?

package.json 파일의 종속성이라고 가정 해보십시오.

"dependencies": {
    "mongoose": "1.4.0",
    "node.io" : "0.3.3",
    "jquery"  : "1.5.1",
    "jsdom"   : "0.2.0",
    "cron"    : "0.1.2"
  }

내가 실행할 때 전역으로 npm installnode.io설치하고 나머지는 로컬로 설치해야합니다. 이것에 대한 옵션이 있습니까?


11
당신은 할 수 없습니다. 그러나 "preferGlobal": truepackage.json 내부에 모듈을 설정할 수 있습니다 .
Raynos 2016 년

예, <code> preferGlobal </ code>에 대해 알고 있지만 전 세계적으로 모든 종속성을 설치합니다 ... 어쨌든 감사합니다! 나는 그런 기능이 없다고 생각합니다 ...
Madhusudhan

3
나는 그렇게 생각하지 않습니다. 현재 모듈을 전체적으로 설치합니다. 개별 종속성이 true로 설정되어 있으면 전체적으로 설치 될 수도 있습니다. # node.js에서 @isaacs에게 물어봐야합니다
Raynos

3
전역 설치는 종속성 문제를 일으킬 수 있습니다. 패키지 A에 버전 0.3.3과 패키지 B 버전 0.3.4가 필요하고 둘 다 다른 버전과 작동하지 않는다고 가정하십시오. 그런 다음 두 패키지를 수용하려면 두 대의 컴퓨터가 필요합니다.
nalply

6
이 의견들 중 어느 것도이 문제에 도움이 "preferGlobal":true되지 않습니다 ... 코드가 나에게 더 많은 것을 보여 주면 좋을 것입니다 ... 실제로 package.json에 넣을 위치를 모르겠습니다. npmjs.org/doc/json.html NPM 문서에 preferGlobal은 고유 한 패키지 용이며,이를 설정하면 고유 한 패키지를 전역 패키지로 설치할 수 있습니다. 그래도 더 많은 가이드처럼 보입니다.
PPPaul

답변:


216

새로운 참고 : 아마도이 작업을 원하지 않거나 필요로하지 않을 것입니다. 아마도 당신이하고 싶은 devDependencies것은 package.json 섹션에 빌드 / 테스트 등에 대한 이러한 유형의 명령 의존성을 두는 것 입니다. package.json 에서 무언가를 사용할 때마다 scriptsnode_modules / .bin의 devDependencies 명령이 마치 경로에있는 것처럼 작동합니다.

예를 들면 다음과 같습니다.

npm i --save-dev mocha # Install test runner locally
npm i --save-dev babel # Install current babel locally

그런 다음 package.json에서 :

// devDependencies has mocha and babel now

"scripts": {
  "test": "mocha",
  "build": "babel -d lib src",
  "prepublish": "babel -d lib src"
}

그런 다음 명령 프롬프트에서 다음을 실행할 수 있습니다.

npm run build # finds babel
npm test # finds mocha

npm publish # will run babel first

그러나 당신이 경우 정말 세계적으로 설치하려면, 당신은 package.json의 스크립트 섹션에서 사전 설치를 추가 할 수 있습니다 :

"scripts": {
  "preinstall": "npm i -g themodule"
}

실제로 내 npm 설치는 npm install을 다시 실행합니다 .. 이상하지만 작동하는 것 같습니다.

참고 :npm 글로벌 노드 패키지 설치가 필요한 곳에 가장 일반적인 설정을 사용하는 경우 문제가있을 수 있습니다 sudo. 한 가지 옵션은 npm구성 을 변경하여 필요하지 않은 것입니다.

npm config set prefix ~/npm에 $ HOME / npm / bin을 $ PATH에 추가 export PATH=$HOME/npm/bin:$PATH하십시오 ~/.bashrc.


3
이 작업을 수행 할 수 없었습니다 npm i -g underscore-cli. wd가 잘못되었다는 경고를 표시합니다. wd는 작업 디렉토리를 의미합니다. 내가 수동으로 다음 일이 잘 갈 명령 줄에서이 작업을 수행 할 때, 그러나 나는 사용자가 간단하게 내 코드를 설치 처리 할 수 있다면 선호npm install
PPPaul

3
PPPaul-최근에이 트릭을 다시 시도했을 때도 같은 문제가있었습니다. 어쩌면 내 설정이 다르거 나 특정 모듈에서만 작동합니다. 그렇지 않으면 npm으로 변경된 것이 있다고 생각합니까?
Jason Livesay

9
또한 npm list module -g || npm install module -gnpm은 적절한 종료 값을 반환 하므로 패키지가 이미 설치되어 있는지 미리 확인할 수 있습니다 .
m90

3
@CMCDragonkai : 이것은 별도의 질문이어야합니다. 그러나 명령을 스크립트에 넣고 실행할 명령으로 스크립트를 지정하십시오 (예 "preinstall" : "scripts/preinstall.sh":).
우리 모두 모니카

1
@CMCDragonkai &&는 예를 들어 다음과 같이 연결합니다npm install -g bower && npm install -g grunt-cli
Matsemann

12

아래 설명 된 단점으로 인해 허용 된 답변을 따르는 것이 좋습니다 .

다음 npm install --save-dev [package_name]을 사용 하여 스크립트를 실행 하십시오 .

$ npm run lint
$ npm run build
$ npm test

내 원래이지만 권장되지 않는 답변은 다음과 같습니다.


전역 설치를 사용하는 대신 패키지를 devDependencies( --save-dev)에 추가 한 다음 프로젝트 내부 어디에서나 바이너리를 실행할 수 있습니다.

"$(npm bin)/<executable_name>" <arguments>...

귀하의 경우 :

"$(npm bin)"/node.io --help

이 엔지니어npm-exec별명을 바로 가기로 제공했습니다 . 이 엔지니어 는이라는 쉘 스크립트를 사용합니다 env.sh. 그러나 $(npm bin)추가 파일이나 설정을 피하기 위해 직접 사용하는 것을 선호합니다 .

각 호출을 약간 더 크게 만들지 만 작동 하지 않아야합니다 .

  • 글로벌 패키지와의 잠재적 인 종속성 충돌 (@nalply)
  • 에 대한 필요성 sudo
  • npm 접두사를 설정해야합니다 (어쨌든 하나를 사용하는 것이 좋습니다)

단점 :

  • $(npm bin) Windows에서는 작동하지 않습니다.
  • 개발 트리에서 더 깊은 도구는 npm bin폴더에 나타나지 않습니다 . ( npm-run 또는 npm을 설치하십시오 .)

Jason이 위에서 설명한 것처럼 일반적인 작업 (예 : 빌드 및 축소)을 '스크립트'섹션 에 배치 하는 것이 더 나은 솔루션 인 것 같습니다 .package.json


에 환경 변수에 디렉토리를 .bashrc쉽게 추가하려면에 별명을 추가하십시오 . 실행 한 다음 평소처럼 명령을 입력하면됩니다. bin/PATHalias nodebin='export PATH=$(npm bin)/:$PATH'nodebin
gitaarik

왜 팀에 효과가 없는지 모르겠습니다. 물론 설정해야하며 선택한 별칭을 사용하지 않으려는 경우. 그러나 팀에서 사용하는 것은 아프지 않습니다.
gitaarik

9

이것은 조금 낡았지만 요구 사항에 부딪 쳤으므로 여기에 내가 찾은 해결책이 있습니다.

문제 :

개발 팀은 AngularJS / Bootstrap으로 마이그레이션하는 많은 .NET 웹 응용 프로그램 제품을 유지 관리합니다. VS2010은 사용자 지정 빌드 프로세스에 쉽게 적합하지 않으며 개발자는 일상적으로 여러 제품 릴리스를 작업하고 있습니다. 우리의 VCS는 Subversion입니다 (저는 알고 있습니다. Git으로 이동하려고하지만 성가신 마케팅 직원이 너무 까다로워 요). 단일 VS 솔루션에는 여러 개의 별도 프로젝트가 포함됩니다. 직원들에게 동일한 노드 패키지 (걸프, 바우어 등)를 동일한 컴퓨터에 여러 번 설치할 필요없이 개발 환경을 초기화하는 일반적인 방법이 필요했습니다.

TL; DR :

  1. .NET 제품에 대한 모든 로컬 필수 패키지뿐만 아니라 글로벌 Node / Bower 개발 환경을 설치하려면 "npm install"이 필요합니다.

  2. 글로벌 패키지는 아직 설치되지 않은 경우에만 설치해야합니다.

  3. 글로벌 패키지에 대한 로컬 링크는 자동으로 작성되어야합니다.

해결책:

우리는 이미 모든 개발자와 모든 제품이 공유하는 공통 개발 프레임 워크를 가지고 있으므로 필요할 때 글로벌 패키지를 설치하고 로컬 링크를 작성하는 NodeJS 스크립트를 작성했습니다. 이 스크립트는 제품 기본 폴더와 관련하여 ".... \ SharedFiles"에 있습니다.

/*******************************************************************************
* $Id: npm-setup.js 12785 2016-01-29 16:34:49Z sthames $
* ==============================================================================
* Parameters: 'links' - Create links in local environment, optional.
* 
* <p>NodeJS script to install common development environment packages in global
* environment. <c>packages</c> object contains list of packages to install.</p>
* 
* <p>Including 'links' creates links in local environment to global packages.</p>
* 
* <p><b>npm ls -g --json</b> command is run to provide the current list of 
* global packages for comparison to required packages. Packages are installed 
* only if not installed. If the package is installed but is not the required 
* package version, the existing package is removed and the required package is 
* installed.</p>.
*
* <p>When provided as a "preinstall" script in a "package.json" file, the "npm
* install" command calls this to verify global dependencies are installed.</p>
*******************************************************************************/
var exec = require('child_process').exec;
var fs   = require('fs');
var path = require('path');

/*---------------------------------------------------------------*/
/* List of packages to install and 'from' value to pass to 'npm  */
/* install'. Value must match the 'from' field in 'npm ls -json' */
/* so this script will recognize a package is already installed. */
/*---------------------------------------------------------------*/
var packages = 
  {
  "bower"                      :                      "bower@1.7.2", 
  "event-stream"               :               "event-stream@3.3.2",
  "gulp"                       :                       "gulp@3.9.0",
  "gulp-angular-templatecache" : "gulp-angular-templatecache@1.8.0",
  "gulp-clean"                 :                 "gulp-clean@0.3.1", 
  "gulp-concat"                :                "gulp-concat@2.6.0",
  "gulp-debug"                 :                 "gulp-debug@2.1.2",
  "gulp-filter"                :                "gulp-filter@3.0.1",
  "gulp-grep-contents"         :         "gulp-grep-contents@0.0.1",
  "gulp-if"                    :                    "gulp-if@2.0.0", 
  "gulp-inject"                :                "gulp-inject@3.0.0", 
  "gulp-minify-css"            :            "gulp-minify-css@1.2.3",
  "gulp-minify-html"           :           "gulp-minify-html@1.0.5",
  "gulp-minify-inline"         :         "gulp-minify-inline@0.1.1",
  "gulp-ng-annotate"           :           "gulp-ng-annotate@1.1.0",
  "gulp-processhtml"           :           "gulp-processhtml@1.1.0",
  "gulp-rev"                   :                   "gulp-rev@6.0.1",
  "gulp-rev-replace"           :           "gulp-rev-replace@0.4.3",
  "gulp-uglify"                :                "gulp-uglify@1.5.1",
  "gulp-useref"                :                "gulp-useref@3.0.4",
  "gulp-util"                  :                  "gulp-util@3.0.7",
  "lazypipe"                   :                   "lazypipe@1.0.1",
  "q"                          :                          "q@1.4.1",
  "through2"                   :                   "through2@2.0.0",

  /*---------------------------------------------------------------*/
  /* fork of 0.2.14 allows passing parameters to main-bower-files. */
  /*---------------------------------------------------------------*/
  "bower-main"                 : "git+https://github.com/Pyo25/bower-main.git" 
  }

/*******************************************************************************
* run */
/**
* Executes <c>cmd</c> in the shell and calls <c>cb</c> on success. Error aborts.
* 
* Note: Error code -4082 is EBUSY error which is sometimes thrown by npm for 
* reasons unknown. Possibly this is due to antivirus program scanning the file 
* but it sometimes happens in cases where an antivirus program does not explain 
* it. The error generally will not happen a second time so this method will call 
* itself to try the command again if the EBUSY error occurs.
* 
* @param  cmd  Command to execute.
* @param  cb   Method to call on success. Text returned from stdout is input.
*******************************************************************************/
var run = function(cmd, cb)
  {
  /*---------------------------------------------*/
  /* Increase the maxBuffer to 10MB for commands */
  /* with a lot of output. This is not necessary */
  /* with spawn but it has other issues.         */
  /*---------------------------------------------*/
  exec(cmd, { maxBuffer: 1000*1024 }, function(err, stdout)
    {
    if      (!err)                   cb(stdout);
    else if (err.code | 0 == -4082) run(cmd, cb);
    else throw err;
    });
  };

/*******************************************************************************
* runCommand */
/**
* Logs the command and calls <c>run</c>.
*******************************************************************************/
var runCommand = function(cmd, cb)
  {
  console.log(cmd);
  run(cmd, cb);
  }

/*******************************************************************************
* Main line
*******************************************************************************/
var doLinks  = (process.argv[2] || "").toLowerCase() == 'links';
var names    = Object.keys(packages);
var name;
var installed;
var links;

/*------------------------------------------*/
/* Get the list of installed packages for   */
/* version comparison and install packages. */
/*------------------------------------------*/
console.log('Configuring global Node environment...')
run('npm ls -g --json', function(stdout)
  {
  installed = JSON.parse(stdout).dependencies || {};
  doWhile();
  });

/*--------------------------------------------*/
/* Start of asynchronous package installation */
/* loop. Do until all packages installed.     */
/*--------------------------------------------*/
var doWhile = function()
  {
  if (name = names.shift())
    doWhile0();
  }

var doWhile0 = function()
  {
  /*----------------------------------------------*/
  /* Installed package specification comes from   */
  /* 'from' field of installed packages. Required */
  /* specification comes from the packages list.  */
  /*----------------------------------------------*/
  var current  = (installed[name] || {}).from;
  var required =   packages[name];

  /*---------------------------------------*/
  /* Install the package if not installed. */
  /*---------------------------------------*/
  if (!current)
    runCommand('npm install -g '+required, doWhile1);

  /*------------------------------------*/
  /* If the installed version does not  */
  /* match, uninstall and then install. */
  /*------------------------------------*/
  else if (current != required)
    {
    delete installed[name];
    runCommand('npm remove -g '+name, function() 
      {
      runCommand('npm remove '+name, doWhile0);
      });
    }

  /*------------------------------------*/
  /* Skip package if already installed. */
  /*------------------------------------*/
  else
    doWhile1();
  };

var doWhile1 = function()
  {
  /*-------------------------------------------------------*/
  /* Create link to global package from local environment. */
  /*-------------------------------------------------------*/
  if (doLinks && !fs.existsSync(path.join('node_modules', name)))
    runCommand('npm link '+name, doWhile);
  else
    doWhile();
  };

이제 개발자를위한 전역 도구를 업데이트하려면 "packages"개체를 업데이트하고 새 스크립트를 체크인하십시오. 내 개발자는이를 확인하고 "노드 npm-setup.js"또는 개발중인 모든 제품에서 "npm install"로 실행하여 글로벌 환경을 업데이트합니다. 전부 5 분이 걸립니다.

또한 새 개발자를위한 환경을 구성하려면 먼저 NodeJS 및 GIT for Windows를 설치하고 컴퓨터를 재부팅 한 다음 "공유 파일"폴더 및 개발중인 모든 제품을 확인한 후 작업을 시작해야합니다.

.NET 제품의 "package.json"은 설치하기 전에이 스크립트를 호출합니다.

{ 
"name"                    : "Books",
"description"             : "Node (npm) configuration for Books Database Web Application Tools",
"version"                 : "2.1.1",
"private"                 : true,
"scripts":
  {
  "preinstall"            : "node ../../SharedFiles/npm-setup.js links",
  "postinstall"           : "bower install"
  },
"dependencies": {}
}

노트

  • 스크립트 참조는 Windows 환경에서도 슬래시가 필요합니다.

  • "npm ls"는 "package.json" "종속성"에 나열되어 있지 않기 때문에 로컬로 연결된 모든 패키지에 대해 "npm ERR! extraneous :"메시지를 제공합니다.

1/29/16 수정

npm-setup.js위 의 업데이트 된 스크립트는 다음과 같이 수정되었습니다.

  • "version"패키지 var packages는 이제 npm install명령 행에 전달 된 "package"값 입니다. 등록 된 리포지토리가 아닌 다른 곳에서 패키지를 설치할 수 있도록 변경되었습니다.

  • 패키지가 이미 설치되었지만 요청 된 패키지가 아닌 경우 기존 패키지가 제거되고 올바른 패키지가 설치됩니다.

  • 알 수없는 이유로 설치 또는 링크를 수행 할 때 npm은 주기적으로 EBUSY 오류 (-4082)를 발생시킵니다. 이 오류는 갇히고 명령이 다시 실행됩니다. 오류는 두 번째로 거의 발생하지 않으며 항상 정리되는 것 같습니다.


이것은 생명의 은인 @ sthames42입니다! 나는 이것을 정확히하는 방법을 알아 내려고 몇 시간 동안 트롤하고 있습니다. 명확하고 포괄적이며 일반적으로 굉장합니다. #points 질문 : (a) Bower가 이미 패키지 목록에있을 때 사후 설치에있는 이유는 무엇입니까? (b) 글로벌 패키지를 로컬로 링크하지 않는 방법은 무엇입니까? 명령에 "링크"를 포함시키지 않습니까?
MaxRocket

@MaxRocket : 도와 드리겠습니다. 나는 훨씬 더 잘 작동하는 최신을 포함하도록 답변을 업데이트했습니다. 답변 : (a) 'npm install'이후에 'bower install'명령이 실행되어 여기에 표시되지 않은 bower.json 파일에 나열된 Bower 구성 요소를 설치합니다. 나는 사람들이 'npm install'을 입력하고 다른 명령을 입력하지 않고도 환경을 완전히 설정하기를 원했습니다. (b) 예.
sthames42

이 스크립트의 현재 버전이 여기에 유지 됩니다 .
sthames42

6

npm_globals.txt대신에 와 같은 별도의 파일을 사용할 수 있습니다 package.json. 이 파일은 다음과 같이 새 줄에 각 모듈을 포함합니다.

mongoose@1.4.0
node.io@0.3.3
jquery@1.5.1
jsdom@0.2.0
cron@0.1.2

그런 다음 명령 행에서

< npm_globals.txt xargs npm install -g

제대로 설치되었는지 확인하십시오.

npm list -g --depth=0

작업을 수행 해야하는지 여부 는 사용 사례에 따라 다릅니다. 대부분의 프로젝트에는 필요하지 않습니다. 프로젝트가 package.json이러한 도구와 종속성을 캡슐화하는 것이 훨씬 바람직합니다.

그러나 요즘에는 create-react-app새 시스템으로 이동할 때 항상 전 세계적으로 항상 다른 CLI를 설치 하고 있음을 알았습니다 . 버전 관리가 중요하지 않은 경우 전역 도구와 해당 종속성을 쉽게 설치할 수있는 방법이 좋습니다.

요즘에는 npx , NPM 패키지 주자를 대신 전 세계적으로 패키지를 설치하는.


3

package.json의 모든 모듈은 ./node_modules/에 설치됩니다.

명시 적으로 이것을 찾을 수는 없지만 NPM에 대한 package.json 참조입니다 .


1

고유 한 스크립트를 작성하여 전역 종속성을 설치하십시오. 많이 걸리지 않습니다. package.json은 상당히 확장 가능합니다.

const {execSync} = require('child_process');

JSON.parse(fs.readFileSync('package.json'))
     .globalDependencies.foreach(
         globaldep => execSync('npm i -g ' + globaldep)
     );

위를 사용하면 아래의 인라인으로 만들 수도 있습니다!

아래 사전 설치를보십시오 :

{
  "name": "Project Name",
  "version": "0.1.0",
  "description": "Project Description",
  "main": "app.js",
  "scripts": {
    "preinstall": "node -e \"const {execSync} = require('child_process'); JSON.parse(fs.readFileSync('package.json')).globalDependencies.foreach(globaldep => execSync('npm i -g ' + globaldep));\"",
    "build": "your transpile/compile script",
    "start": "node app.js",
    "test": "./node_modules/.bin/mocha --reporter spec",
    "patch-release": "npm version patch && npm publish && git add . && git commit -m \"auto-commit\" && git push --follow-tags"
  },
  "dependencies": [
  },
  "globalDependencies": [
    "cordova@8.1.2",
    "ionic",
    "potato"
  ],
  "author": "author",
  "license": "MIT",
  "devDependencies": {
    "chai": "^4.2.0",
    "mocha": "^5.2.0"
  },
  "bin": {
    "app": "app.js"
  }
}

node의 저자는 package.json이 프로젝트 파일임을 인정하지 않을 수 있습니다. 하지만 그것은.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.