Node Express用法详解【安装、使用、路由、中间件、模板引擎等】


Posted in Javascript onMay 13, 2020

本文实例讲述了Node Express用法。分享给大家供大家参考,具体如下:

安装

npm install --save express

基本使用

//引用express
var express = require('express');

//创建app
var app = express();

//罗列中间件
app.get('/',function( req,res ){
  res.send('index');
});

app.get('/new/:id',function( req,res ){
  res.send('news'+ res.params.id);
});

//开启服务器,监听端口
app.listen(3000);

路由

express 路由

//路由小写和大写都可以。
var express = require('express');

var app = express();

app.get('/',function( req,res ) {
  res.send('get请求');
});
app.post('/',function( req,res ){  
  res.send('post请求');  
});
app.listen(1221);

get和post请求都可以

app.all('/',function( req,res ){
  res.send('get&post');
});
// 更推荐冒号写法
app.get('/student/:id',function( req,res ){});
app.get('/:username/:id',function( req,res ){ res.write(username); res.end(id) });

有字符串正则系统

// 匹配 acd 和 abcd
app.get('/ab?cd', function(req, res) {
 res.send('ab?cd');
});

// 匹配 abcd、abbcd、abbbcd等
app.get('/ab+cd', function(req, res) {
 res.send('ab+cd');
});

// 匹配 abcd、abxcd、abRABDOMcd、ab123cd等
app.get('/ab*cd', function(req, res) {
 res.send('ab*cd');
});

// 匹配 /abe 和 /abcde
app.get('/ab(cd)?e', function(req, res) {
 res.send('ab(cd)?e');
});

正则表达式

// 匹配任何路径中含有 a 的路径:
app.get(/a/, function(req, res) {
 res.send('/a/');
});
// 路由中的正则表达式,可以使用分组捕获,程序中使用req.params[0],req.params[1]来获取
app.get(/student([\d]{1})\/class([\d]{2})$/,function( req,res ){
  console.log( req.params[0],req.params[1] );
});

表单提交

表单提交到本身页面 // restful 路由设计

/* 
概念:
  /student 
    get // 读取学生信息  // app.get('/student/:id',function(){});
    add // 添加学生信息   // app.add('/student/:id',function(){});
    delete // 删除学生信息 // app.delete('/student/:id',function(){});
问题:web网页中,大部分处理get和psot请求处理。
其它的服务,可以是从软件,或者app发出请求。一般restful是提供给app。
*/
       
app.get('/',function( req,res ){
  res.render('form.ejs');
});
app.post('/',function( req,res ){
  res.send('form表单提交');
});

中间件

中间件middleware ,少了一层回调。
所有的中间件,都将作为http.createServer();的回调。

中间件特点:

app.js中的代码,程序执行的时候运行,用户来了之后,并不执行。中间件中的代码块,每个用户访问的时候都会执行一次。

具有跳楼现象,从上往下走,匹配一个就执行,而不会执行第二个。

app.get('/',function( req,res ){ res.send('A') });    
app.get('/',function( req,res ){ res.send('B') });   //执行A,而不会执行B

中间件的回调函数中有next参数,表示继续执行下一个匹配的中间件。 //利用next(),用两段小程序,来同时处理同一个请求。 把业务分开。 next() , 影响MVC。

app.get('/',function( req,res,next ){
  res.send( 'A' );
  next();
})

app.get('/',function( req,res,next ){
  res.send( 'B' );
})

//这两个路由,感觉没关系,实际上冲突了。
app.get('/:username/:id',function( req,res ){
  console.log(1);
  res.send('用户信息'+ req.params[username]);
});

app.get('/admin/login',function( req,res ){
  console.log(2);
  res.send('管理员登陆');
});

解决方法

方法1:
调整路由上下位置 //利用匹配就有跳楼现象。 express 中 所有的路由 都是中间件,具体的路由往上写,抽象的往下写

app.get('/admin/login',function( req,res ){ 
  console.log(2);
  res.send('管理员登陆');
});

app.get('/:username/:id',function( req,res ){
  console.log(1);
  res.send('用户信息'+ req.params[username]);
});

方法2: 匹配到最后,要有最终的路由来匹配于它。

//加上next()之后,匹配两次,已经被send()一次,会报错。通过数据的判断适当加next()

app.get('/:username/:id',function( req,res ){
  
  var username = req.paramse.username;
  //检索数据库,如果username不存在,那么才next()
  if( usernma ) {
    console.log(1);
    res.send('用户信息'+ req.params[username]);
  } else {
    next();
  }

});

app.get('/admin/login',function( req,res ){
  console.log(2);
  res.send('管理员登陆');
});

app.use()

此时并不会进行任何路由匹配,都是执行。一般处理404,和总体的返回编码和状态的使用。

// 多个路由都能够匹配
app.use('/admin',function( req,res ){
  console.log(req.originUrl); // '/admin/new'
  console.log(req.baseUrl); // 'admin'
  console.log(req.path); // '/new'
  next();
});
// 任何网址都是 '/' 的拓展
app.use('/',function( req,res ){});
app.use(function( req,res ){}); // 可以不用第一个参数 直接就是 '/',就是所有网址了。
app.use(); //增加一些特定功能的便利场所。
// 实际上app.use(); //基本上都从第三方能得到。 -- 路由顺序(落路)
app.use(user);
function user( req,res,next ){   
  var filePath = req.originalUrl;
  fs.readFile('./public/'+filePath,function( err,data ){
    if( err ){
      //文件不存在
      next()
      return ;
  }
    res.send(data.toSting());
  });
}
// 静态服务
app.use(express.static('./public'));

// 路由的上下关系,很有关系, 是否匹配第一个,是否需要next()

// 一般习惯把静态服务写在前头,后面的路由处理,一般不冲突。

 // 返回编码和状态
 app.use(function( req,res,next ){
  
  res.status(200);
  res.set('Content-Type','text/html;charset=utf-8');
  next();

});
//404 
app.use(function( req,res ){
  res.status(404);
  res.send('sorry');
});

render() & send()

大多数情况下,渲染内容用res.render(),将会根据views的模板文件进行渲染,如果不想使用views文件夹,使用其它名字,

app.set('views','static');

send(); //自动设置了Content-Type 头部和200状态码。和 mime类型。 send() 和 end() 一样。

get & post

get请求的参数在url中,在原生node中,需要使用url模块来识别参数字符串,在express中,不需要使用url模块。可以直接使用req.query对象。

post请求在express中不能直接获得,必须使用body-parser模块。使用后,将可用req.body得到参数。但是如果表单中含有文件上传,那么还是需要使用formidable模块

post使用到的第三方模块:body-parserformidable

var express = require('express');
var bodyParser = require('body-parser');
var app = express();

// 设置模板
app.set('view engine','ejs');
app.use(bodyParser.urlencoded({ extended: false }));

// router
app.get('/',function( req,res ){
 res.render('form.ejs');
});

app.post('/',function( req,res ){
 console.log(req.body);
});

静态化文件

利用expres.static(root); // root 参数指的是静态资源文件所在的根目录。

// app.use方法实际上是将中间件保存在一个数组中,注册路由时,依次将数组的元素取出
app.use(express.static('./static'));
app.use('page',epxress.static('./static')); // page/index.html

模板引擎

和 express 结合的模板是:jadeejs
(ejs)[https://www.npmjs.com/package/ejs%5D

var express = require('express');
var app = express();

// 设置模板引擎,设置为ejs
app.set('view engine','ejs');

// 路由
app.get('/',function( req,res ){
  //render: 第二个参数是,字典。
  res.render('index.ejs',{
    'name': [ting,daie]
  });
});  
app.listen(1221);

对应的模板为:

<ul>
  <%
    for( var i=0; i<name.length; i++ ){
  %>
    <li><%=name[i]%></li>
  <%
    }
  %>
</ul>

默认的视图文件夹,views。如果不想使用默认的 app.set('views','./shitu');

希望本文所述对大家node.js程序设计有所帮助。

Javascript 相关文章推荐
通过JavaScript使Div居中并随网页大小改变而改变
Jun 24 Javascript
jQuery下的动画处理总结
Oct 10 Javascript
jquery复选框全选/取消示例
Dec 30 Javascript
JavaScript实现数组在指定位置插入若干元素的方法
Apr 06 Javascript
jquery自定义插件开发之window的实现过程
May 06 Javascript
node.js实现博客小爬虫的实例代码
Oct 08 Javascript
js实现一个可以兼容PC端和移动端的div拖动效果实例
Dec 09 Javascript
vue2 中如何实现动态表单增删改查实例
Jun 09 Javascript
解决webpack打包速度慢的解决办法汇总
Jul 06 Javascript
js实现图片上传预览原理分析
Jul 13 Javascript
webpack中的热刷新与热加载的区别
Apr 09 Javascript
通过原生vue添加滚动加载更多功能
Nov 21 Javascript
Node 模块原理与用法详解
May 13 #Javascript
JavaScript oncopy事件用法实例解析
May 13 #Javascript
JavaScript 正则应用详解【模式、欲查、反向引用等】
May 13 #Javascript
JavaScript 引用类型实例详解【数组、对象、严格模式等】
May 13 #Javascript
Node.js API详解之 module模块用法实例分析
May 13 #Javascript
JS如何实现手机端输入验证码效果
May 13 #Javascript
vue-socket.io接收不到数据问题的解决方法
May 13 #Javascript
You might like
mysql 字段类型说明
2007/04/27 PHP
php fputcsv命令 写csv文件遇到的小问题(多维数组连接符)
2011/05/24 PHP
php设计模式之单例模式使用示例
2014/01/20 PHP
dedecms函数分享之获取某一栏目所有子栏目
2014/05/19 PHP
ThinkPHP提交表单时默认自动转义的解决方法
2014/11/25 PHP
php实现的RSS生成类实例
2015/04/23 PHP
PHP实现的链式队列结构示例
2017/09/15 PHP
js切换光标示例代码
2013/10/10 Javascript
JS小功能(列表页面隔行变色)简单实现
2013/11/28 Javascript
jQuery实现Tab菜单滚动切换的方法
2015/09/21 Javascript
js和jquery分别验证单选框、复选框、下拉框
2015/12/17 Javascript
EasyUI中在表单提交之前进行验证
2016/07/19 Javascript
js 将图片连接转换成base64格式的简单实例
2016/08/10 Javascript
JS中的一些常用的函数式编程术语
2019/06/15 Javascript
基于JavaScript实现贪吃蛇游戏
2020/03/16 Javascript
vue2.0 解决抽取公用js的问题
2020/07/31 Javascript
vue 数据遍历筛选 过滤 排序的应用操作
2020/11/17 Javascript
深入理解Python爬虫代理池服务
2018/02/28 Python
教你如何编写、保存与运行Python程序的方法
2019/07/12 Python
numpy.meshgrid()理解(小结)
2019/08/01 Python
Python3 合并二叉树的实现
2019/09/30 Python
python3实现单目标粒子群算法
2019/11/14 Python
Python3常见函数range()用法详解
2019/12/30 Python
Django后台管理系统的图文使用教学
2020/01/20 Python
解决Python3.8用pip安装turtle-0.0.2出现错误问题
2020/02/11 Python
基于OpenCV的路面质量检测的实现
2020/11/04 Python
基于PyInstaller各参数的含义说明
2021/03/04 Python
俄罗斯最大的隐形眼镜销售网站:Ochkov.Net
2021/02/07 全球购物
广告设计应届生求职信
2014/03/01 职场文书
贷款承诺书
2015/01/20 职场文书
委托公证书样本
2015/01/23 职场文书
2015年度个人思想工作总结
2015/04/08 职场文书
违纪开除通知书
2015/04/25 职场文书
项目投资意向书范本
2015/05/09 职场文书
幼儿园奖惩制度范本
2015/08/05 职场文书
Oracle11g r2 卸载干净重装的详细教程(亲测有效已重装过)
2021/06/04 Oracle