什么是node.js
定义:基于chrome v8引擎的javascript 运行环境
特点:事件驱动,非阻塞式I/O的模型,轻量和高效,单线程、单进程
nodejs能做什么?
可以解析js代码(没有浏览器安全级别的限制)
提供很多系统级别的API:
文件的读写
进程的管理
网络的通信...
v8
谷歌开源的一个高性能 JavaScript 引擎 采用 C++ 编写 Google Chrome 浏览器用的就是这个引擎 V8 可以单独运行,也可以嵌入 C++ 应用当中 V8 会编译、执行 JavaScript 代码,并一样会管理内存、垃圾回收 V8 的高性能以及跨平台等特性,所以它也是 Node.js 的 JavaScript 引擎 JIT 编译出即时机器码,极大提高效率 借鉴java vm 垃圾回收,精确垃圾回收
安装nodemon 实时监测文件的变化
npm install -g nodemon //全局安装
模块包/CommonJS规范
www.commonjs.org javascript.ruanyifeng.com/nodejs/modu…
每个文件就是一个模块,在模块里面定义的变量、函数、类都是私有的
module 代表的当前模块 ,exports属性,代表向外提供接口
require加载模块,读取并执行一个js文件,然后返回该模块的exports对象
模块加载的顺序,按照代码中出现的顺序
模块可以多次加载,第一次加载运行之后,会被缓存
require内部处理流程
模块内容导出:
module.exports = "字符串";//可以的
module.exports.msg = '字符串'//可以的
exports.msg = '字符串'//可以的
exports = '字符串'//不行的
检查Moducle._cache, 是否缓存了指定模块
如果缓存没有的话,就创建一个新的module实例将它保存到缓存
module.load()去加载指定的模块
如果解析的过程中,出现异常,就从缓存中删除该模块
返回该模块的module.exports
node.js官网:nodejs.cn/api/
在 Node.js 模块系统中,每个文件都被视为一个独立的模块。
常用内置js模块
const http = require('http');
const path = require('path');
const qs = require('querystring');
const fs = require('fs')
const url = require('url');
const crypto = require('crypto');
版本号命名规则
GNU 风格的版本号命名格式
语义版本号分为X.Y.Z三位, 分别代表主版本号、次版本号和补丁版本号。当代码变更时,版本号按以下原则更新。
- 如果只是修复bug,需要更新Z位。
- 如果是新增了功能,但是向下兼容,需要更新Y位。
- 如果有大变动,向下不兼容,需要更新X位。
软件阶段说明
- Base:此版本表示该软件仅仅是一个假页面链接,通常包括所有的功能和页面布局,但是页面中的功能都没有做完整的实现,只是做为整体网站的一个基础架构。
- Alpha :软件的初级版本,表示该软件在此阶段以实现软件功能为主,通常只在软件开发者内部交流,一般而言,该版本软件的Bug较多,需要继续修改,是测试版本。测试人员提交Bug经开发人员修改确认之后,发布到测试网址让测试人员测试,此时可将软件版本标注为alpha版。
- Beta :该版本相对于Alpha 版已经有了很大的进步,消除了严重错误,但还需要经过多次 测试来进一步消除,此版本主要的修改对象是软件的UI。修改的的Bug 经测试人员测试确认后可发布到外网上,此时可将软件版本标注为 beta版。
- RC :该版本已经相当成熟了,基本上不存在导致错误的Bug,与即将发行的正式版本相差无几。
- Release:该版本意味“最终版本”,在前面版本的一系列测试版之后,终归会有一个正式的版本,是最终交付用户使用的一个版本。该版本有时也称标准版。
Package.json版本号规则
- npm install
- npm install @version
- 波浪符号(~) ~1.15.2 >=1.15.2 <1.16.0
- 插入符号(^) ^3.3.4 >=3.3.4 <4.0.0
socket
websocket
WebSocket 是 HTML5 开始提供的一种在单个 TCP 连接上进行全双工通讯的协议。
WebSocket 使得客户端和服务器之间的数据交换变得更加简单,允许服务端主动向客户端推送数据。在 WebSocket API 中,浏览器和服务器只需要完成一次握手,两者之间就直接可以创建持久性的连接,并进行双向数据传输。
在 WebSocket API 中,浏览器和服务器只需要做一个握手的动作,然后,浏览器和服务器之间就形成了一条快速通道。两者之间就直接可以数据互相传送。
现在,很多网站为了实现推送技术,所用的技术都是 Ajax 轮询。轮询是在特定的的时间间隔(如每1秒),由浏览器对服务器发出HTTP请求,然后由服务器返回最新的数据给客户端的浏览器。这种传统的模式带来很明显的缺点,即浏览器需要不断的向服务器发出请求,然而HTTP请求可能包含较长的头部,其中真正有效的数据可能只是很小的一部分,显然这样会浪费很多的带宽等资源。
HTML5 定义的 WebSocket 协议,能更好的节省服务器资源和带宽,并且能够更实时地进行通讯。
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<style>
#msglist {
width: 400px;
height: 500px;
background: #eeeeee;
}
</style>
</head>
<body>
<div id="msglist">
</div>
<textarea id="msg" rows="5" cols="10">
</textarea>
<button id="btn">留言</button>
<script>
var $btn = document.querySelector("#btn");
var $msg = document.querySelector("#msg")
var $list = document.querySelector('#msglist')
//http => new WebSocket('ws://***')
//https => new WebSocket('wss://***') 不能是ip
var ws = new WebSocket('ws://localhost:8099')
function wsEvent() {
//用于指定当从服务器接受到信息时的回调函数
ws.onmessage = (msg) => {
console.log(msg.data)
$list.innerHTML += msg.data + '<br>';
}
//用于连接成功之后的回调函数
ws.onopen = () => {
console.log('open ...')
}
//用于指定连接关闭后的回调函数
ws.onclose = () => {
console.log('close')
reconnect()
}
ws.onerror = () => {
console.log('error')
reconnect()
}
}
wsEvent();
$btn.addEventListener('click', () => {
//数据的发送
ws.send($msg.value)
})
//重连
function reconnect() {
if (ws.readyState === 2 || ws.readyState === 3) {
ws = new WebSocket('ws://localhost:8099');
wsEvent();
}
}
</script>
</body>
</html>
websocketServer.js
const ws = require('ws');
var websocketServer = new ws.Server({ port: 8099 });
//所有的客户端列表
var clientlist = {}
var id = 0;
websocketServer.on('connection', (client) => {
client.id = id++;
clientlist[id] = client;
console.log('connection...')
client.send('welcome to back')
client.on('message', (msg) => {
console.log(msg)
boardcast(client.id + ":" + msg);
})
//client退出时的事件
client.on('close', () => {
boardcast(client.id + " 下线了");
delete clientlist[client.id];
})
})
//广博通知,所有客户端
function boardcast(message) {
for (let o in clientlist) {
clientlist[o].send(message)
}
}