node概念
前端运行环境(浏览器)
后端的运行环境(Node.js)
nodejs是一个基于chrome V8引擎的的运行环境
终端常用
FS文件系统模块
提供一系列方法和属性来满足用户对文件的操作需求。
使用时需要导入
const fs=require('fs') //类似头文件
1、fs.readFile()读取文件
fs.readFile ( path ,options , callback( err, dataStr) )
参数1:必选参数,字符串表示文件路径
参数2:可选参数,表示读取文件的编码格式
参数3:必选参数,读取成功后通过回调来拿读取结果(读取成功 err=null , 读取失败err为错误对象,dataStr为undefined)
2、fs.writeFile()写入文件
fs.writeFile ( path ,data ,options , callback( err) )
参数1:必选参数,字符串表示文件路径
参数2:必选参数,写入内容
参数3:可选参数,以什么格式写入
参数3:必选参数,读取成功后通过回调来拿读取结果(写入成功 err=null , 写入失败err为错误对象)
path路径模块
1、path.join():把多个路径片段拼接为完整路径
2、path.basename():从路径中获取文件名
第一个参数:必选路径名
第二个参数:要删除的文件扩展名
3、path.extname():获取路径中的文件扩展名
http模块
在网络节点中,负责消费资源的电脑叫做客户端,负责对外提供网络资源的电脑叫做服务器。
http模块,可以用来创建web服务器,把一台电脑变为web服务器,向外部提供web服务。
1、创建web服务器
1、导入http模块
2、创建web服务器实例
3、为服务器实例绑定request事件,监听客户端请求
4、启动服务器
2、req请求对象(客户端相关)
3、res响应对象(服务端相关)
4、根据url响应不同的html
1、获取请求的url地址
2、设置默认的相应内容为404
3、判断用户请求的是否为/或/index.html首页
4、判断用户请求的是否为/about.html关于页面
5、设置content-type响应头,防止乱码
6、使用res.end()把内容相应给客户端
模块化
优点
- 提高代码复用性
- 提高代码可维护性
- 实现按需加载
分类
- 内置模块
- node提供的,包裹fs,path,http等
- 自定义模块
- 用户自己定义的js文件
- 第三方模块
- 需要下载的模块集合
ps:使用require加载模块,加载过程会执行模块中的代码
共享模块作用域中的成员(暴露)
module对象:每个自定义模块中都有一个module对象,存储了和当前模块有关的信息。
module.exports对象:将模块的成员共享出去,使用require引入模块时得到的时module。exports所指定的对象。
exports对象:是module.exports的简化写法
require得到的永远是module.exports指向的对象
npm与包
第三方模块又叫做包。
npm:包管理工具,用于下载管理包
npm使用
1、安装
npm i 完整的包名
安装完成后,项目下会多了node_modules的文件夹和package-lock.json配置文件
node_modules:存放所有已安装到项目中的包
package-lock.json:记录node_module目录下每一个包的下载信息。
2、卸载
npm unistall 包名
卸载的同时package.json中会同步消失
3、包管理配置文件
由于node_module太大,不适合git管理,因此不上传node_module,而是用package.json来记录用了那些包,这时使用npm i可以下载所有依赖
package.json:包管理配置文件,用来记录与项目有关的一些配置信息
项目的名称,版本,描述
项目都用到了那些包
4、创建package.json这个包管理配置文件
npm init -y
5、devDependecies(开发依赖包)与dependecies(核心依赖包)
某些包只在开发阶段会用到,在项目上线后不会用到,可以将其放在devDepencies中
npm i 包名 -D
6、镜像
直接下载外国服务器很慢,因此可以用淘宝镜像服务器下载。
镜像:一种资源的完全复制
使用镜像源
npm config get registry :查看服务器地址
npm config set registry=https://registry.npm.taobao.org/
模块的加载机制
模块在第一次加载后会缓存,加载后再次使用不会重复执行。
自定义模块的加载机制
第三方模块的加载
若require()的模块不是一个内置模块,也没有以路径开头。Node.js会从当前模块的父目录开始尝试从/node_module中加载
express
本质是一个第三方包,是http模块的扩展
创建基本的web服务器
1、导入express
2、创建web服务器
3、调用app.lisite(端口号,启动成功后的回调),启动服务器
监听get请求
监听post请求
响应客户端
获取url中携带的query参数
获取url中的动态参数
托管静态资源
express.static(),可以创建一个静态资源服务器
app.use(express.static( "public " ))
通过以上代码可以将public下的文件对外开放了
app.use( '/public' , express.static( "public" ) ) //加了访问前缀
nodemon
动态监听 node变化,自动重启,不必要每次都重启
Express路由
在Express,路由指的是客户端的请求与服务器处理函数之间的映射关系
Expresss中的路由有三部分组成,分别是请求的类型,请求的url地址,处理函数
模块化路由
- 将路由抽离为单独模块
- 创建路由模块对应的js文件
- 调用express.router创建路由对象
- 想路由对象上挂在具体的路由
- 使用module.exports向外共享路由对象
- 使用app.use()函数注册路由模块
使用
1、导入路由模块
2、使用app.use注册路由模块
中间件
有输入输出的中间处理环节,类似一个过滤的管道
express中间件的调用流程
当请求到达express的服务器之后,可以连续调用多个中间件,从而对这次请求进行预处理
中间件的格式
next函数: 调用next()向后流转
定义一个全局中间件
定义多个
多次使用app.use()
定义局部生效的中间件
不使用app.use()定义,在app.get中间增加参数
定义多个![](https://img-blog.csdnimg.cn/b2274ca901a643b59082eb48363d72c1.png)
小TIPS
- 中间件要在路由之前
- 客户端发送过来的请求,可以连续调用多个中间件进行处理、
- 执行完中间件的业务之后,不要忘记调用next
- 防止代码混乱,next后不要再写其他
- 多个中间件共享res,req对象
中间件分类
应用级别的中间件
通过app.use或者app.get绑定在app上的中间件
路由级别的中间件
绑定在express.Router上的中间件
错误级别的中间件
用于捕获错误,function包含四个参数,(err,req,res,next)
先有抛出错误,后又错误中间件捕获错误
express内置中间件
例子
express.static:托管静态资源
express.json:解析json格式的数据请求
express.urlencoded: 解析url-encoded格式的请求体数据
第三方的中间件
第三方开发的中间件,例如body-parser,使用步骤如下
1、npm i body-parser
2、使用require导入中间件
3、使用app.use()注册并使用中间件
Cors
使用cors中间件解决跨域问题
1、npm i cors
2、const cors = require( " cors " )//导入中间件
3、在路由之前调用app.use( cors )//配置中间件
什么是cors
跨域资源共享,有一些列HTTP响应头组成,这些HTTP响应头决定浏览器是否能阻止前端js代码跨域获取资源。配置了CORS相关的HTTP响应头就可以解决跨域限制。
Access-Control-Allow-Origin
origin指定了允许访问该资源的url ,那些网页可以访问资源
Access-Control-Allow-Headers
cors仅支持9个请求头,Access-Control-Allow-Headers允许对额外的请求头声明
Access-Control-Allow-Methods
默认情况,cors仅支持客户端发起GET、POST、HEAD请求
若希望发起PUT、DDELETE等请求,需要Access-Control-Allow-Methods设置支持的方法
cors的两种请求
简单请求
1、get 、head、post之一
2、头信息不得超过九种字段。。。。
预检请求
1、请求为get、head、post之外
2、超出九种字段,包含自定义字段
3、发送了application/json格式的数据
发送请求前,浏览器会发送option进行预检,以获知服务器是否允许请求。请求通过后才发送真正的请求。
数据库
数据组织机构
数据库、数据表、数据行、字段
1、每个项目都有对应的单独数据库
2、不同的数据,存储在数据库的不同表中,例如用户存储到users表中,图书存储在books表中
3、每个表中存储那些信息由字段决定,例如user中由id 、name、password
4、表中的行代表每一条具体的数据
字段属性
PK(Primary Key):主键唯一标识
NN(Not Null):值不为空
UQ(Unique):值唯一
AI(Auto Increment):值自动增长
在项目中使用mySQL
1、安装mysql模块
2、通过mysql连接MySql数据库
3、通过mysql模块执行SQL语句
如何使用
增
1、用?占位符,紧接在语句之后加入数组
2、通过res的对象affectedRows可判断是否成功
简化写法
删
改
简化
查![](https://img-blog.csdnimg.cn/d7f169171551403581750fb8179cf3ac.png)
身份认证
服务端渲染,推荐使用session认证
对于前后端分离,推荐使用JWT认证机制
Session认证(非跨域)
将用户信息存储在服务器内存中,同时生成对应的cookie。发送给浏览器,浏览器再次发送时携带cookie。
cookie
cookie是存储在用户浏览器中一段不超过4kb的字符串,它由Name,Value何以他控制字段组成。
每个域名的cookie各自独立。每当发起请求会将当前域名未过期的cookie全部发送。
在Express中使用Session验证
配置成功后可以通过req.session来访问和使用session对象,从而存储用户的关键信息。
JWT认证机制(跨域)
服务器将用户信息加密为token返回给客户端,客户端再次发送时将Authorization字段发送给服务其,服务器解密在认证
jwt组成部分
Header:安全性,
Payload:用户信息加密后的字符串,
Signature:安全性
Express中使用JWT
导入包
jsonwebtoken:生成jwt字符串
express-jwt:将jwt字符串解析为json字符串
登录成功后发送token
sign():三个参数
1、用户的信息对象
2、加密的密钥(任意字符串)
3、配置对象,配置当前token的有效期
将jwt字符串返回为json对象
使用user获取用户信息![](https://img-blog.csdnimg.cn/b1b9fac08b5b4ca69da600539d0292ab.png)
捕获解析失败的错误
通过错误中间件捕获错误
-
中间件顺序中,错误中间件为倒数第一位,路由中间件为倒数第二位。其他随意,因为路由中间件要使用其他中间件添加的对象,错误中间件要捕获所有的错误。