首页 > 解决方案 > 注册功能错误(TypeError:newUser.encryptPassword 不是函数)

问题描述

我正在尝试实现注册功能,但它在护照中显示类型错误,但找不到确切的错误以及如何修复它。如果我太傻了,对不起,因为我真的是 js 新手。我在这里附上我的代码...

//错误在passport.js的配置文件夹中

var passport = require('passport');
var User = require('../models/user');
var LocalStrategy = require('passport-local').Strategy;

passport.serializeUser(function(user, done) {
  done(null, user.id);
});

passport.deserializeUser(function(id, done) {
  User.findByID(id, function(err, user) {
    done(err, user);
  });
});

passport.use('local.signup', new LocalStrategy({
  usernameField: 'email',
  passwordField: 'password',
  passReqToCallback: true
}, function(req, email, password, done) {
  User.findOne({
    'email': email
  }, function(err, user) {
    if (err) {
      return done(err);
    }
    if (user) {
      return done(null, false, {
        message: 'Email is already in use.'
      });
    }
    var newUser = new User();
    newUser.email = email;
    newUser.password = newUser.encryptPassword(password);
    newUser.save(function(err, result) {
      if (err) {
        return done(err);
      }
      return done(null, newUser);
    });

  });
}));

// 这是用户模式,模块内的 user.js

var mongoose = require('mongoose');
var Schema = mongoose.Schema;
var bcrypt = require('bcrypt-nodejs');


var userSchema = new Schema({
  email: {
    type: String,
    required: true
  },
  password: {
    type: String,
    required: true
  },

});

userSchema.method.encryptPassword = function(password) {
  return bcrypt.hashSync(password, bcrypt.genSaltSync(5), null);
};

userSchema.method.validPassword = function(password) {
  return bcrypt.compareSync(password, this.password);
};
module.exports = mongoose.model('User', userSchema);

//这是路由文件夹中的路由器,index.js

var express = require('express');
var router = express.Router();
var csrf = require('csurf');
var passport = require('passport');

var Boi = require('../models/boi');

var csrfProtection = csrf();
router.use(csrfProtection);

/* GET home page. */
router.get('/', function(req, res, next) {
  var boi = Boi.find(function(err, docs) {
    var boiChunks = [];
    var chunkSize = 3;
    for (var i = 0; i < docs.length; i += chunkSize) {
      boiChunks.push(docs.slice(i, i + chunkSize));
    }
    res.render('library/index', {
      title: 'Boipoka',
      boi: docs
    });
  });
});

router.get('/user/signup', function(req, res, next) {
  var messages = req.flash('error');
  res.render('user/signup', {
    csrfToken: req.csrfToken(),
    messages: messages,
    hasErrors: messages.length > 0
  });
});
router.post('/user/signup', passport.authenticate('local.signup', {
  successRedirect: '/user/profile',
  failureRedirect: '/user/signup',
  failureFlash: true
}));

router.get('/user/profile', function(req, res, next) {
  res.render('user/profile');
});

module.exports = router;

//这里是主应用,app.js

var express = require('express');
var path = require('path');
var favicon = require('serve-favicon');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');
var expressHbs = require('express-handlebars');
var mongoose = require('mongoose');
var session = require('express-session');
var passport = require('passport');
var flash = require('connect-flash');


var routes = require('./routes/index');


var app = express();
mongoose.connect('mongodb://localhost:27017/boipoka', {
  useNewUrlParser: true
});
require('./config/passport');

// view engine setup
app.engine('.hbs', expressHbs({
  defaultLayout: 'layout',
  extname: '.hbs'
}));
app.set('view engine', '.hbs');

app.use(logger('dev'));
app.use(express.json());
app.use(express.urlencoded({
  extended: false
}));
app.use(cookieParser());
app.use(session({
  secret: 'mysupersecret',
  resave: false,
  saveUninitailized: false
}));
app.use(flash());
app.use(passport.initialize());
app.use(passport.session());
app.use(express.static(path.join(__dirname, 'public')));

app.use('/', routes);




// catch 404 and forward to error handler
app.use(function(req, res, next) {
  var err = new Error('Not Found');
  err.status = 404;
  next(err);
});

// error handler
app.use(function(err, req, res, next) {
  // set locals, only providing error in development
  res.locals.message = err.message;
  res.locals.error = req.app.get('env') === 'development' ? err : {};

  // render the error page
  res.status(err.status || 500);
  res.render('error');
});

module.exports = app;

错误信息是

events.js:174 抛出错误;// 未处理的“错误”事件 ^

TypeError:newUser.encryptPassword 不是函数

标签: node.jsmongodbexpresshandlebars.js

解决方案


看起来您对模式方法使用了不正确的 Mongoose 语法。

Schema.prototype.method()是一个函数,因此您要么需要传递一个方法对象,要么单独传递每个方法,并将字符串作为键。

您需要将模型更改为:

userSchema.method('encryptPassword', function(password) {
  return bcrypt.hashSync(password, bcrypt.genSaltSync(5), null);
};

userSchema.method('validPassword', function(password) {
  return bcrypt.compareSync(password, this.password);
};

或者:

userSchema.method({
  encryptPassword: function(password) {
    return bcrypt.hashSync(password, bcrypt.genSaltSync(5), null);
  },
  validPassword: function(password) {
    return bcrypt.compareSync(password, this.password);
  }
})

推荐阅读