为什么学习Node?
- IO优势
- 对于文件读写,Node采用的是非阻塞IO
- 传统IO在读写文件的时候CPU来处理,而代码执行也处于等待中,浪费性能
- 非阻塞IO将读写操作交给CPU,而代码正常执行,减少等待浪费的性能
- 应用场景
- 实际应用: webpack/gulp/npm/http-server/json-server
- 服务器中负责IO读写的中间层服务器(天猫中间层IO服务器)
NodeJS特点
- 其移植了chrome V8 引擎,解析和执行代码机制和浏览器js相同
- 其沿用了JavaScript语法、另外扩展了自己需要的功能
- 总结: nodejs 是一个后端语言 , 其具备操作文件的能力, 可以具备服务器的创建和操作能力
- 其语法是JavaScript语法,代码运行在chrome V8 引擎之上
基本使用
- 官网上下载 node-v-xx.msi 傻瓜式的安装包 一路下一步,就ok
- 检测是否安装成功 node -v
- 运行程序 node ./xxx.js
内置对象介绍
分类
- 全局对象: 何时何处都能访问
- 核心对象: 向系统索要,引入即可使用
- 自定义对象: 按路径引入即可
process(全局对象)
-
每个系统的环境变量几乎都不一样,可以利用环境变量中的具体某个特定的值来区分不同的机器
-
process.env 是一个对象,我们可以通过其.属性名来获取具体的环境变量值
- 设置一个特定的环境变量,以达到简单区分不同的机器,从而针对生产/开发环境运行不同的效果
-
process.argv 获取命令行参数
filename/dirname(全局对象)
- __filename 获取当前运行文件的目录,绝对路径
- __dirname 当前运行文件的绝对路径
nodejs实现规范
- CommonJS : 规范JavaScript语言作为后端语言运行的标准
- 具备什么能力,该怎么做 ,比如: 具备服务器的功能/ 可以操作文件 …..
- 模块应该怎么写: Module :
- 依赖一个模块 require(‘模块名(id)')
- 需要被模块依赖 module.exports = 给外部的数据
- 一个文件是一个模块
核心对象path
const path = require('path');
- 路径 -> 在处理路径的时候很擅长,但是,其不负责判断路径是否存在文件
- 拼接并修正路径
path.join(__dirname,'a','b');
以当前目录/a/b path.resovle('./xxx') 相对转绝对
- 接收一个合法的路径字符串,转换成一个对象
let pathObj = path.parse(mypath);
- 接收一个路径对象,转换成一个字符串路径
let str = path.format(pathObj);
{
root: 'C:\\',
dir: 'C:\\Users\\孙悟空',
base: '金箍棒.txt', // 该属性可以用于修改文件名和后缀
ext: '.txt',
name: '金箍棒'
}
- 注意:path对象是方便我们操作路径的,对于获取来讲: parse解析成对象,format转换成字符串.join拼接并修正…. 对于修改路径对象来讲,可以用base属性更改,不能用name,ext更改
模块
- 弊端
- 在js中要涉及到逻辑,还要在html中,为逻辑对象考虑引用顺序
- 所有对象默认都是全局对象,命名冲突
- commonjs规范
- 一个文件就是一个模块
- 导入用require(’./xxx.js');
- 导出用module.exports = xxx;
- 在每一个模块内声明的变量属于模块内的作用域
fs文件模块
- 文件读写
- 其他功能
- 扩展介绍
操作文件对象
-
IO
- I :input输入
- O:output 输出
- 文件的操作就是IO
-
复制文件的过程, I: 通过计算机,存储文件到剪切板
- 粘贴到指定目录: O: 通过计算机,将剪切板上的数据,写出到 指定目录
-
node中有两种IO的操作
-
同步IO
- 一行代码(读文件)不执行完毕…后续代码不能执行
-
异步IO (建议)
- 一行代码(读写文件) 不执行完毕(正在读写中) … 后续代码也可以执行
-
代码体验:
-
读写文件
-
const fs = require('fs'); //必须这个名称 //读 fs.readFile(路径,回调函数); //写 fs.writeFile(路径,数据,回调函数);
-
总结: 异步的读/写文件 参数1:都是路径,可以相对可以绝对,最后一个参数都是回调函数,回调函数的参数中错误对象优先
-
-
-
同步和异步IO的区别: 同步IO会阻塞后续代码执行,异步IO不会阻塞后续代码执行
遍历文件夹下的文件
-
读取文件夹,获取其中所有文件的资源
-
stat 获取文件状态
-
readdir 读取文件夹数据
-
access 判断文件或文件夹是否存在
包(文件夹)
- 多个文件,有效的被组织与管理的一个单位
- 留一个入口
- 包就是一个:文件夹
npm|| yarn
- 自己先有一个包描述文件(package.json)
- 创建一个包描述文件
npm init [-y]
- 会根据当前的文件夹来自动生成包名(不允许中文,不允许大写英文字母)
- 默认生成
npm init [-y]
- 下载一个包
npm install art-template jquery@1.5.1 --save
- 记录依赖
--save
- 记录依赖
- 根据package.json文件中的
dependencies
属性恢复依赖- 恢复包
npm install
简单:npm i
- 恢复包
- 卸载一个包
npm uninstall jquery@1.5.1 --save
- 简写```npm un jquery@1.5.1 –S`
- 下载简单些:
npm i 包名
- 下载简单些:
- 小结:以上简写: uninstall -> un ,install -> i , –save -> -S
- 查看包的信息
npm info jquery
- 查看包的信息中的某个字段(版本)(掌握)
npm info jquery versions
- 查看包的文档
npm docs jquery
- 安装全局命令行工具
npm install -g http-server
- 卸载全局命令行工具
npm uninstall -g http-server
- 查看全局包的下载路径
npm root -g
- 修改存储目录
npm config set prefix "D:\xxx"
- 不要node_modules
- 接着,修改环境变量中的path属性
- 添加或改为
D:\xxx
- 目的就是为了在任意目录启动 xxx.cmd
- 添加或改为
- 重启命令行
nrm是npm的镜像源管理工具
- 1:全局安装
npm install -g nrm
- 2:查看当前可选的镜像源
nrm ls
- 3:切换镜像源
nrm use taobao
- 添加自己公司私有源
nrm add name http://www.xxx.xxx/
包的加载机制
- 我们未来可能需要辨识一个包中,入口是否是我们想要的启动程序
- 逐级向上查找node_module,直到盘符根目录
- 1:查找node_modules下的包名文件夹中的main属性(常用)
- 2:不常用:查找node_modules下的包名.js
- 3:查找node_modules下的包名文件夹中的index.js(常用)
- 逐级向上,node_modules,要么main属性,要么index.js
事件队列
- 主线程–同步任务
- event loop–异步任务(宏,微)
- 微任务的优先级高于宏任务
- process.nextTick()优先于promise.then();
console.log('script start');//主线程
setTimeout(function() {
setTimeout(function() {
console.log('setTimeout1');//推入主线程
}, 0);//推入event loop(宏)
}, 0);//推入event loop(宏)
new Promise(resolve => {
console.log('promise start');//主线程
setTimeout(() => {
console.log('setTimeout2');//推入主线程
resolve();//将then推入event loop(微)
}, 0);//推入event loop(宏)
}).then(function() {
console.log('promise1');//推入主线程
}).then(function() {
console.log('promise2');//推入主线程
});
console.log('script end');//主线程