package.json是npm package的配置文件,存储当前项目相关的信息。如果下载npm中的包,包内会自带该文件。

具体属性

{
"name" : "underscore",  //当前包(项目)的名字
"description" : "JavaScript's functional programming helper library.",
"homepage" : "http://documentcloud.github.com/underscore/",
"keywords" : ["util", "functional", "server", "client", "browser"],
"author" : "Jeremy Ashkenas",
"contributors" : [],
"dependencies" : [],//生产依赖
"devDependencies”:[],//开发依赖
"repository" : {"type": "git", "url": "git://github.com/documentcloud/underscore.git"},
"scripts": {
"build": "node build.js"
}
"main" : "underscore.js",   //当前项目(包)的入口文件,该文件的导出对象作为该模块的导出对象 
"version" : "1.1.6"
}

main:the main entry point for the libary; when someone runs require(<library name>), require resolves this call to require(<package.json:main>).

dependencies :used to list all the dependencies of your project that are available on npm. When someone installs your project through npm, all the dependencies listed will be installed as well. Additionally, if someone runs npm install in the root directory of your project, it will install all the dependencies to ./node_modules.

devDependencies :these are dependencies not required for normal operation, but required/recommended if you want to patch or modify the project. If you built your unit tests using a testing framework, for example, it would be appropriate to put the testing framework you used in your devDependencies field. To install a project's devDependencies, simply pass the --dev option when you use npm install.

scripts:每一个属性,对应一段脚本。每当执行npm run xxx 时就会自动新建一个 Shell,在这个 Shell 里面执行指定的脚本命令。npm run新建的Shell会将当前目录的node_modules/.bin子目录append到PATH变量,执行结束后,再恢复原样。所以当前目录的node_modules/.bin子目录里面的所有脚本,都可以直接用脚本名调用,在没有全局安装时也不必加上路径。所以只要是 Shell可以运行的命令,都可以写在 npm 脚本里面。

  传入参数:npm run <command> [-- <args>] ,所以在scripts中要用 -- 双中线分隔传给npm命令的参数和传给脚本的参数。node server.js --port=8888 转换成  npm run server -- --port=8888 

  执行多个脚本:并行执行多个命令使用&符号,顺序执行(前一个任务成功才执行下一个任务)使用&&符号。

全局安装vs本地安装:

Global packages are for anything that you need to access from the shell. By contrast local packages are for using within your apps.

npm install xxx -g :属于全局安装将包安装在C:\Users\admin\AppData\Roaming\npm\node_modules目录下,同时在node_modules平级目录生成批处理文件,这样可以在任何地方执行xxx的CIL命令。否则需要cd到项目的cmd命令所在目录再执行/双引号包含可执行命令的全路径,很繁琐。全局安装时的包不可以通过 require() 来引入。

@IF EXIST "%~dp0\node.exe" (
"%~dp0\node.exe" "%~dp0\node_modules\gulp\bin\gulp.js" %*
) ELSE (
@SETLOCAL              //变量本地化
@SET PATHEXT=%PATHEXT:;.JS;=;% //删除js后缀的默认执行文件,不直接执行gulp.js
node "%~dp0\node_modules\gulp\bin\gulp.js" %* //在命令行输入gulp时,实际上调用的是这条命令:用node解释器调用批处理文件所在目录下的js文件
)
npm install xxx –save-dev :属于本地安装将包安装在项目根目录下的node_modules目录下的.bin目录下,生成对应的cmd命令,在项目根目录下可以直接运行。可以通过 require() 来引入本地安装的模块。


@IF EXIST "%~dp0\node.exe" (
"%~dp0\node.exe" "%~dp0\..\._gulp@3.9.1@gulp\bin\gulp.js" %* //"执行其他目录下的文件" "node执行的js文件地址" %*其他任意变量
) ELSE (
@SETLOCAL
@SET PATHEXT=%PATHEXT:;.JS;=;%
node "%~dp0\..\._gulp@3.9.1@gulp\bin\gulp.js" %* //%~dp0代表的是bat文件所在的文件目录,不可变;指向当前项目依赖的gulp模块的js
)
如果不安装全局包,则在pro目录下是不能执行对应的命令行命令,必须cd到.bin目录下,或者通过npm link命令或通过package.json的scripts字段设置:
"scripts" : {
"build" : "webpack ./entry.js bundle.js",
"deploy": "export NODE_ENV=production && `npm bin`/webpack --config webpack.config.production.js && npm start",
}

然后运行npm run build命令。

require()查找文件的顺序

当require一个文件模块时,先从当前执行文件平级的的node_modules目录中查找;然后查找上一级的node_modules目录;依次迭代,直到根目录下的node_modules目录。如果还没有查找到指定模块的话,就会去NODE_PATH注册的路径中查找

require绝对路径的文件,查找时不用去遍历每一个node_modules目录,其速度最快。

为什么要全局安装和本地安装两次?

本地安装可以让每个项目依赖独立的包,不受全局包的影响,保证不同版本的包之间的相互依赖,可以通过require()使用引入的模块。是npm的默认安装模式。

全局安装并不依赖引入的模块。它会在'C:\Users\admin\AppData\Roaming\npm'生成对应的cmd文件,保证在任何地方都可以通过命令行执行该程序,不用cd到项目目录执行。如全局安装gulp是为了在任何地方都可以执行gulp任务,本地安装gulp则是为了调用gulp插件的功能。

npm 常用命令

安装模块

npm install      //安装package.json中定义的所有依赖的包
npm install [<@scope>/]<name>@<version> //安装指定版本的包,如不指定版本,默认安装最新的包
alias: npm i
options:
-S|--save //保存版本信息到package.json文件的dep字段中
-D|--save-dev //保存版本信息到package.json文件的devDep字段中
npm install --production  # 添加了production参数后将仅仅安装package.json中dependencies 里面的包,不会安装devDependencies 里的模块,否则get all dependencies & devDependencies installed。一个模块不能同时在两种环境中安装。

卸载模块

npm uninstall <pkg>
aliases: remove, rm, r, un, unlink
options:
-S|--save //删除package.json中dev字段对应的信息
-D|--save-dev //删除package.json中devDep字段对应的信息

更新模块

npm outdated [<pkg>]    //列出所有过时的包
npm update [-g] [<pkg>...] //更新指定到包到最新版本;如果未指定,则更新所有包,包括全局和本地
aliases: up, upgrade
options:同上

其他命令

npm config get prefix              //获取全局模块安装路径;
where node //获取node所在路径;
npm <command> -h //查看该命令的所有使用帮助信息;
npm view package@2.3.1 [version|dependencies] //查看远程包内的package.json信息
npm config ls –l //查看npm内置的配置参数
npm install 或者 npm install –save-dev //自动将所在目录的package.json中的模块安装到node-modules文件夹下,不用一个一个安装模块。
npm ls xxx [–depth=0] //查看本地安装的模块版本信息,只看当前目录,不遍历子目录。注意:子模块的devdependency依赖包不会被安装,只安装dep包。

cnpm

因为npm是从国外服务器下载,经常出现异常,可以使用淘宝团队开发的镜像cnpm,cnpm跟npm用法一样。

安装命令:npm install cnpm -g --registry=https://registry.npm.taobao.org

create-react-app安装模块慢,可以设置永久使用cnpm:

$:npm config set registry https://registry.npm.taobao.org

$:npm config set registry http://registry.npmjs.org   #官方地址

使用nrm管理registry地址:

1.安装nrm:npm install -g nrm

2.注册registry地址:

  nrm add npm http://registry.npmjs.org

  nrm add cnpm https://registry.npm.taobao.org

3.切换registry地址

  nrm use npm/cnmp

依赖包版本管理 

包版本号为X.Y.Z三位,代表主版本号、次版本号和补丁版本号。当代码变更时,按以下原则更新版本号:
主版本号:有不兼容的API 修改时; 
次版本号:有向下兼容的功能性新增时;
补丁版本号:做了向下兼容的bug修正时。

依赖包版本号管理(固定写死需要手动更新):
~匹配最近的小版本依赖包,比如~1.2.3会匹配所有1.2.x的包,但是不包括1.3.0。

^匹配最新的大版本依赖包,比如^1.2.3会匹配所有1.x.x的包,但是不包括2.0.0。

配置npm仅安装精确版本号的模块: npm config set save-exact true

package-lock.json

npm 5.0新增特性。package-lock.json is automatically generated for any operations where npm modifies either the node_modules tree, or package.json. It describes the exact tree that was generated, such that subsequent installs are able to generate identical trees, regardless of intermediate dependency updates.如果package.json中使用了~或^指定版本,在重新npm i时会安装可用的最新版本,同时package-lock.json也会改变。但是如果之前的版本固定,package-lock.json也会固定。
It stores an exact, versioned dependency(including nested dependencies) tree rather than using starred versioning like package.json itself (e.g. 1.0.*). This means you can guarantee the dependencies for other developers or prod releases, etc. It also has a mechanism to lock the tree but generally will regenerate if package.json changes.
This is intended to lock down your full dependency tree. Let's say typescript v2.4.1 requires widget ~v1.0.0. When you npm install it grabs widget v1.0.0. Later on your fellow developer (or CI build) does an npm install and gets typescript v2.4.1 but widget has been updated to widget v1.0.1. Now your node module are out of sync. This is what package-lock.json prevents.(控制嵌套依赖包的版本)
忽略项目开发过程中有些依赖已经发生的更新而锁定当前项目所有依赖包的版本号,避免后来者新拉项目时因重新安装的依赖包版本不同而出现bug。(同事甲:为什么我的电脑上是正常的?!) 

前端工程之npm的更多相关文章

  1. 前端工程之CDN部署

    之前发的一篇文章<变态的静态资源缓存与更新>中提到了静态资源和页面部署之间的时间间隙问题,这个问题会迫使前端静态资源发布必须采用非覆盖式. 那篇文章中没有详细解释为什么会产生不可忍受的时间 ...

  2. 前端工程之node基础

    Node.exe是一个基于 Chrome V8 引擎的 JavaScript 运行环境. Nodejs定义了一个构造函数 Module,所有的模块(Node中一个文件即一个模块)都是 Module 的 ...

  3. VS2015前端工具:NPM和Web Essentials

    VS2015前端工具:NPM和Web Essentials 1.写作背景 想在5月份前换个工作环境了,“检讨”一下自己混饭的技术水平和处世的人脉关系,觉得很不给力!为人方面,人各有志也就不纠结了,但本 ...

  4. FrameWork逆向工程之MotioPI

    在BI项目建设的过程中我们一般都是有备份的,而且这个是必须有的!特别是例如ETL Model,还有Data Model这一类的元数据,这些东西如果我们没有备份,而恰好的我们的开发模型又在某一天离我们而 ...

  5. 逆向工程之App脱壳

    http://www.cnblogs.com/ludashi/p/5725743.html iOS逆向工程之App脱壳 本篇博客以微信为例,给微信脱壳."砸壳"在iOS逆向工程中是 ...

  6. 前端工程化 - 剖析npm的包管理机制

    转自https://juejin.im/post/5df789066fb9a0161f30580c 现如今,前端开发的同学已经离不开 npm 这个包管理工具,其优秀的包版本管理机制承载了整个繁荣发展的 ...

  7. 前端node.js npm i 报错Unexpected end of JSON input while parsing near

    清缓存 npm cache clean --force 重新安装 npm install

  8. [web前端] yarn和npm命令使用

    原文地址: https://blog.csdn.net/mjzhang1993/article/details/70092902/ 最初接触 yarn 还是在 0.17.10 版本,由于各种各样的原因 ...

  9. 前端自动化之npm

    npm——node依赖包管理工具 安装: 1.在nvm目录下复制npm和npm-cath文件夹 2.配置环境变量. 使用: 1.在项目文件夹,shift+右键打开命令窗口 2.npm init     ...

随机推荐

  1. 老李分享:持续集成学好jenkins之解答疑问

    老李分享:持续集成学好jenkins之解答疑问   poptest(www.poptest.cn)在培训的过程中使用jenkins搭建持续集成环境,让学员真正交流持续集成到底是什么,怎么去做的. Je ...

  2. Android实现网络多线程断点续传下载

    本示例介绍在Android平台下通过HTTP协议实现断点续传下载. 我们编写的是Andorid的HTTP协议多线程断点下载应用程序.直接使用单线程下载HTTP文件对我们来说是一件非常简单的事.那么,多 ...

  3. img 的 3px

    今天在做一个测试的时候碰到的问题:用一个 div 包裹一个 img ,代码如下: html代码: <div class="box"> <img src=" ...

  4. java多线程基本概述(四)——死锁

    package mytask; public class Task { public static void main(String[] args) { DeadThread thread = new ...

  5. CF #edu 11 C. Hard Process

    题目链接:http://codeforces.com/problemset/problem/660/C 大意是给一个01数组,至多可以将k个0变为1,问最后数组中最长能有多少个连续的1,并输出. 问题 ...

  6. (原)HashMap之java8新特性

    首先说一下HashMap存储结构,数组.链表.树这三种数据结构形成了hashMap.存储结构下图所示,根据key的hash与table长度确定table位置,同一个位置的key以链表形式存储,超过一定 ...

  7. 进程间通信系列 之 socket套接字实例

    进程间通信系列 之 概述与对比   http://blog.csdn.net/younger_china/article/details/15808685  进程间通信系列 之 共享内存及其实例   ...

  8. lxml简明教程

    最近要做下微信爬虫,之前写个小东西都是直接用正则提取数据就算了,如果需要更稳定的提取数据,还是使用 xpath 定位元素比较可靠.周末没事,从爬虫的角度研究了一下 python xml 相关的库. P ...

  9. MyEclipse(8.5以上的版本) 安装js的开发插件aptana

    最近在学习js,想在MyEclipse(MyEclipse 10) 上面安装一个js的开发的插件aptana. MyEclipse 8.5以后的版本的安装的方法: 1.下载aptana_update_ ...

  10. office web apps 部署-搭建域控服务器

    开始第一条先说注意事项:我所配置的环境是用了三台2012server虚拟机,三台虚拟机必须要加下域控,而且登录操作的时候必须以域账号登录,否则测试不通过!在笔记本上搭建了两个虚拟机(window se ...