Node+Express+MongoDB实现登录注册功能实例


Posted in Javascript onApril 23, 2017

注入MongoDB 依赖

var mongoose = require("mongoose");

由于需要进行表单处理,需要用到bodyParser中间件

bodyParser模块来做文件解析,将表单里的数据进行格式化

var bodyParser = require("body-parser"); 
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));

登录后将用户信息保存下来,需要使用session中间件,它依赖cookieParser中间件

var cookieParser = require('cookie-parser');
var session = require('express-session');
ar mongoStore = require('connect-mongo')(session);
var dbUrl = 'mongodb://localhost/express';
app.use(cookieParser()); 
app.use(session({
 secret:'express',
 store: new mongoStore({
 url: dbUrl,
 collection: 'sessions'
 })
}));

使用jade模板

layout.jade

doctype html
html
 head
  meta(charset='utf-8')
  title #{title}
  include ./includes/head
 body
  include ./includes/header
  block content

head.jade

link(href='css/main.css', rel='stylesheet')
link(href="/libs/bootstrap/dist/css/bootstrap.min.css" rel="external nofollow" , rel="stylesheet")
script(src="/libs/jquery/dist/jquery.min.js")
script(src="/libs/bootstrap/dist/js/bootstrap.min.js")

header.jade

.container
 .row
  .page-header
   h1 #{title}
.navbar.navbar-default.navbar-fixed-bottom
 .container
  if user
   p.navbar-text.navbar-right
    span 欢迎你,#{user.name}
    span  | 
    a.navbar-link(href="/layout" rel="external nofollow" ) 退出登录
  else
   p.navbar-text.navbar-right
    a.navbar-link(href="/signup" rel="external nofollow" , data-toggle="modal", data-target="#signupModal") 注册
    span  | 
    a.navbar-link(href="/login" rel="external nofollow" , data-toggle="modal", data-target="#signinModal") 登录

signup.jade

include ../layout
 block content
  form.form-horizontal( role="form", method="POST", action='/user/signup')
   .form-group
    label.col-sm-2.control-label(for="signupName") 用户名
    .col-sm-10
     input#signupName.form-control(type="text", name="user[name]", placeholder="输入用户名")
   .form-group
    label.col-sm-2.control-label(for="signuppassword") 密码
    .col-sm-10
     input#signuppassword.form-control(type="password", name="user[password]", placeholder="输入密码")
   .form-group
    label.col-sm-2.control-label(for="signupemail") 邮箱
    .col-sm-10
     input#signupemail.form-control(type="email", name="user[email]", placeholder="输入邮箱")
   .form-group
    .col-sm-offset-2.col-sm-10
     button.btn.btn-default(type="submit") 完成注册

配置路由

登录注册页面

// 注册页面
app.get('/signup', function (req,res) {
 res.render('signup', {
 title: '注册'
 });
});
// 登录页面
app.get('/login', function (req,res) {
 res.render('login', {
 title: '登录'
 });
});

注册功能

// 注册表单
app.post('/user/signup', function (req,res) {
 var _user = req.body.user;
 User.findOne({name:_user.name}, function (err, user) {
 if(err){
  console.log(err);
 }
 if(user) {
  return res.redirect('/login');
 } else {
  var user = new User(_user);
  user.save(function (err, user) {
  if(err){
   console.log(err);
   res.redirect('/signup');
  }
  console.log('注册成功——用户名:' + user);
  res.redirect('/login'); 
  });
 }
 });
});

登录功能

// 登录表单
app.post('/user/login', function (req,res) {
 var _user = req.body.user;
 var name = _user.name;
 var password = _user.password;
 User.findOne({name:name}, function (err, user) {
 if(err){
  console.log(err);
 }
 if(!user) {
  return res.redirect('/signup');
 }
 user.comparePassword(password, function (err, isMatch) {
  if (err){
  console.log(err);
  }
  if (isMatch) {
  req.session.user = user; // 用户名存入session中
  console.log('登录成功——用户名: ' + user);
  return res.redirect('/');
  } else {
  return res.redirect('/lgoin');
  }
 });
 });
});

退出登录

app.get('/layout', function(req,res){
 delete req.session.user;
 //delete app.locals.user; // 删除全局变量user,否则点击退出登录,页面无变化
 res.redirect('/');
});

登录注册的数据库操作

连接数据库

mongoose.connect("mongodb://localhost/express"); // 连接数据库

schema模式定义

数据的更新和查找,以及密码加盐

//schemas/user.js
var mongoose = require('mongoose');
var bcrypt = require('bcrypt');
var SALT_WORK_FSCTOR = 10; // 计算强度,越大破解越困难
var UserSchema = new mongoose.Schema({
 name: {
 unique: true,
 type:String
 },
 password: String,
 email:String,
 meta: {
 createAt: {
  type: Date,
  default: Date.now()
 },
 updateAt: {
  type: Date,
  default: Date.now()
 }
 }
});
//每次存入数据时都进行判断
UserSchema.pre('save', function (next) {
 var user = this;
 if (this.isNew) { // 数据是新数据
 this.meta.createAt = this.meta.updateAt = Date.now();
 } else {
 this.meta.updateAt = Date.now();
 }
 //密码 加盐
 bcrypt.genSalt(SALT_WORK_FSCTOR, function (err, salt) {
 if (err) {
  return next(err);
 }
 bcrypt.hash(user.password, salt, function (err, hash) {
  if (err) {
  return next(err);
  }
  user.password = hash;
  next();
 });
 });
});
UserSchema.methods = {
 comparePassword: function (_password, cb) {
 bcrypt.compare(_password, this.password, function (err, isMatch) {
  if (err) {
  return cb(err);
  }
  cb(null, isMatch);
 })
 }
};
UserSchema.statics = {
 fetch: function (cb) {
 return this
  .find({})
  .sort('meta.updateAt')
  .exec(cb);
 },
 findById: function (id, cb) {
 return this
  .findOne({_id: id})
  .exec(cb)
 }
};
module.exports = UserSchema;

model编译模型

// models/user.js
var mongoose = require('mongoose');
//模式
var UserSchema = require('../schemas/user');
//编译模型
var User = mongoose.model('user',UserSchema);
module.exports = User;

入口文件注入

//app.js
var User = require('./models/user');
app.set('view engine', 'jade'); // jade模板引擎
app.set("views", "./views/pages/"); // 视图根目录
var serveStatic = require('serve-static'); // 静态文件处理
app.use(serveStatic('public')); // 路径:public

身份验证中间件

获取session的用户名,存入到locals中,暴露给视图使用,即header.jade中可以获取到user。

app.use(function (req, res, next) {
 var _user = req.session.user;
 app.locals.user = _user;
 return next();
});

以上所述是小编给大家介绍的Node+Express+MongoDB实现登录注册功能,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
Jquery 复选框取值兼容FF和IE8(测试有效)
Oct 29 Javascript
JS:window.onload的使用介绍
Nov 13 Javascript
用javascript关闭本窗口不弹出询问框的方法
Sep 12 Javascript
JavaScript编写简单的计算器
Nov 25 Javascript
详解JavaScript逻辑And运算符
Dec 04 Javascript
JS从一组数据中找到指定的单条数据的方法
Jun 02 Javascript
Bootstrap3 Grid system原理及应用详解
Sep 30 Javascript
深入理解JavaScript定时机制
Oct 27 Javascript
angular.js 路由及页面传参示例
Feb 24 Javascript
今天,小程序正式支持 SVG
Apr 20 Javascript
javascript实现搜索筛选功能实例代码
Nov 12 Javascript
JavaScript的function函数详细介绍
Nov 20 Javascript
使用jQuery ajaxupload插件实现无刷新上传文件
Apr 23 #jQuery
基于JavaScript实现类名的添加与移除
Apr 23 #Javascript
源码分析Vue.js的监听实现教程
Apr 23 #Javascript
Bootstrap进度条与AJAX后端数据传递结合使用实例详解
Apr 23 #Javascript
springMVC + easyui + $.ajaxFileUpload实现文件上传注意事项
Apr 23 #Javascript
Node.js中的require.resolve方法使用简介
Apr 23 #Javascript
AngularJS之ionic 框架下实现 Localstorage本地存储
Apr 22 #Javascript
You might like
全国FM电台频率大全 - 24 贵州省
2020/03/11 无线电
PHP学习 运算符与运算符优先级
2008/06/15 PHP
利用yahoo汇率接口实现实时汇率转换示例 汇率转换器
2014/01/14 PHP
PHP使用CURL获取302跳转后的地址实例
2014/05/04 PHP
php常用表单验证类用法实例
2015/06/18 PHP
TNC vs IO BO3 第一场2.13
2021/03/10 DOTA
用document.documentElement取代document.body的原因分析
2009/11/12 Javascript
奉献给JavaScript初学者的编写开发的七个细节
2011/01/11 Javascript
可以用鼠标拖动的DIV实现思路及代码
2013/10/21 Javascript
jQuery使用之标记元素属性用法实例
2015/01/19 Javascript
JS替换字符串中空格方法
2015/04/17 Javascript
jquery实现多屏多图焦点图切换特效的方法
2015/05/04 Javascript
JS右下角广告窗口代码(可收缩、展开及关闭)
2015/09/04 Javascript
Jquery时间轴特效(三种不同类型)
2015/11/02 Javascript
浏览器兼容的JS写法总结
2016/04/27 Javascript
jQuery中通过ajax调用webservice传递数组参数的问题实例详解
2016/05/20 Javascript
ES6新特性之Object的变化分析
2017/03/31 Javascript
Angular 4.0学习教程之架构详解
2017/09/12 Javascript
js使用xml数据载体实现城市省份二级联动效果
2017/11/08 Javascript
详解JavaScript 的变量
2019/03/08 Javascript
Python入门篇之条件、循环
2014/10/17 Python
Django框架中处理URLconf中特定的URL的方法
2015/07/20 Python
python编程开发之textwrap文本样式处理技巧
2015/11/13 Python
Python中文件I/O高效操作处理的技巧分享
2017/02/04 Python
速记Python布尔值
2017/11/09 Python
详解Python异常处理中的Finally else的功能
2017/12/29 Python
django 自定义filter 判断if var in list的例子
2019/08/20 Python
django创建超级用户过程解析
2019/09/18 Python
python由已知数组快速生成新数组的方法
2020/04/08 Python
Python gevent协程切换实现详解
2020/09/14 Python
Prometheus开发中间件Exporter过程详解
2020/11/30 Python
CSS中的字体大小设置属性总结
2016/05/24 HTML / CSS
ABOUT YOU罗马尼亚:超过600个时尚品牌
2019/09/19 全球购物
无工作经验者个人求职信范文
2013/12/22 职场文书
餐饮服务员岗位职责
2015/02/09 职场文书
2015年外联部工作总结
2015/04/03 职场文书