前端Nodejs-Day36
package.json属性:name为npm包名,version为包版本,main为文件入口,description为包介绍,keywords为搜索关键词,license为开源许可协议(一般为ISC)
发布包:cd到包的根目录下,利用npm publish命令上传
删除包:运行npm unpublish 包名 –force命令
注意:① 只能删除72小时内发布的包。② 已删除的包在24小时内不允许重复发布。
模块的加载机制:
① 模块优先从缓存中加载:多次调用require不会执行多次导入模块。
② 内置模块加载的优先级最高!
③ 在加载自定义模块时,必须以./或者../开头的路径标识符,否则node会当做内置模块或第三方模块进行加载。
④ 若当前加载模块不为内置模块也不以./和../开头,则Node会从当前模块的父目录开始,从/node_modules中加载第三方模块。若未找到,则会去上一层目录的node_modules中继续查找下去,直到文件系统的根目录。
Express:web开放框架,类似nodejs内置的http模块,用于创建web服务器
创建基本web服务器:
// 导入express
const express = require('express')
// 创建web服务器
const app = express()
// 启动web服务器
app.listen(8080, () => {
console.log('express server running at http://127.0.0.1:8080')
})
监听客户端GET请求:app.get
app.get('url', (req, res) => {})
// req:请求对象,包含了与请求相关的属性和方法
// res:响应对象,包含了与响应相关的属性和方法
监听客户端POST请求:app.post
app.post('url', (req, res)=>{})
将内容响应给客户端:res.send(res为get与post回调函数中的响应对象)
app.get('/user', (req, res) => {
// 向客户端发送JSON对象
res.send({name: 'lwh', age: 18})
})
app.post('/user', (req, res) => {
// 向客户端发送文本内容
res.send('请求成功!')
})
req.query、req.params用于get请求。req.body用于post请求。
获取URL中携带的查询参数(即地址的查询字符串):req.query(req为回调函数的请求对象)
app.get('/', (req, res)=> {
// 通过req.query可以获取到客户端发送的参数,默认为空对象!
console.log(req.query)
res.send(req.query)
})
获取URL中的动态参数:req.params获取URL中通过:匹配到的对象
app.get('/user/:id', (req, res)=> {
// req.params是动态匹配的URL参数,默认为空对象
console.log(req.params)
res.send(req.params)
})
获取请求体的数据:默认情况下如果不配置解析表单数据的中间件(即以json格式或者urlencoded格式解析数据),则req.body默认为undefined
除了错误级别的中间件,配置其他中间件必须在路由之前!!
// 必须在路由前配置中间件的解析表单格式此处为JSON格式
app.use(express.json())
app.post('/user', (req, res) => {
console.log(req.body)
res.send(req.body)
})
托管静态资源:app.use(express.static(’路径’))
express在指定目录里寻找静态资源,故存放静态资源的目录不会出现在地址中。
挂载路径前缀:app.use(‘路径前缀’,express.static(‘路径’))
nodemon:使用nodemon命令运行js文件,会监听js动态而变化。
Express路由:客户端请求和服务器处理函数间的映射关系,由请求类型、请求URL地址、处理函数三部分组成。
路由的匹配顺序:按照路由顺序进行匹配,当URL和请求类型同时匹配,Express才会转发此次请求到相应的函数处理。
模块化路由:方便对路由进行模块化管理,express不支持将路由挂载到app上,而是推荐将路由抽离为单独的模块。
① 创建路由相关js文件
② 调用express.Router()创建路由对象
③ 向路由对象上挂载路由
④ 利用module.exports共享路由对象
const express = require('express')
const router = express.Router()
router.get('/user/list', (req, res) => {
res.send('Get user list!')
})
router.post('user/add', (req, res) => {
res.send('add user success!')
})
module.exports = router
⑤ 使用app.use()注册路由模块:接受模块共享的router对象
app.use()用于注册全局中间件!!!
const express = require('express')
const userRouter = require('./router')
const app = express()
app.use(userRouter)
app.listen(8080, () => {
console.log('http://127.0.0.1:8080')
})
同样也可以为路由设置统一访问前缀,与给静态资源设置访问前缀相同,即app.use(‘前缀’, router)
Express中间件:
1.即业务处理过程的中间处理环节,且必须具有输出和输出!
2.当请求达到Express服务器后,可以连续调用多个中间件,对其进行预处理
3.中间件本质上是一个函数,包含req,res,next三个参数(路由只有req和res,这就是和中间件最大的区别)
中间件的next函数:将流转关系转交给下一个中间件或路由,是多个中间件连续调用的关键。
全局生效的中间件:即客户端发起的任意请求到达后都会触发的中间件
通过app.use(中间件)定义全局中间件。
中间件的作用:多个中间件间的req和res是共享的!可以给上游的中间件的res和req添加属性和方法,供下游的中间件使用。
const express = require('express')
const app = express()
app.use((req, res, next) => {
// 获取到请求到达服务器的时间
const time = Date.now()
// 为req挂载自定义属性,把时间共享给后面所有路由
req.startTime = time
console.log('全局中间件!')
next()
})
app.get('/', (req, res) => {
//每次响应都可以获取当前的时间
console.log(req.startTime)
res.send('Home page')
})
app.get('/user', (req, res) => {
console.log(req.startTime)
res.send('user page')
})
app.listen(8080, () => console.log('http://127.0.0.1:8080'))
局部生效的中间件:即不使用app.use定义的中间件,若想在某一路由使用、则将其作为路由的第二个参数加入。
const mw = function (req, res, next) {
console.log('局部中间件')
next()
}
// 只在该路由生效
app.get('/', mw, (req, res) => {
res.send('Home Page')
})
// 不生效
app.get('/user', (req, res) => {
res.send('User Page')
})
定义多个局部中间件:同时加入多个中间件参数或者以数组形式加入。