Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/node.js/39.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript sequelize.js自定义验证程序,检查唯一用户名/密码_Javascript_Node.js_Orm_Sequelize.js - Fatal编程技术网

Javascript sequelize.js自定义验证程序,检查唯一用户名/密码

Javascript sequelize.js自定义验证程序,检查唯一用户名/密码,javascript,node.js,orm,sequelize.js,Javascript,Node.js,Orm,Sequelize.js,假设我定义了以下自定义验证器函数: isUnique: function () { // This works as expected throw new Error({error:[{message:'Email address already in use!'}]}); } 但是,当我尝试查询数据库时,遇到了以下问题: isUnique: function (email) { // This doesn't work var User = seqeulize.import('/pa

假设我定义了以下自定义验证器函数:

isUnique: function () { // This works as expected
  throw new Error({error:[{message:'Email address already in use!'}]});
}
但是,当我尝试查询数据库时,遇到了以下问题:

isUnique: function (email) { // This doesn't work
  var User = seqeulize.import('/path/to/user/model');

  User.find({where:{email: email}})
    .success(function () { // This gets called
      throw new Error({error:[{message:'Email address already in use!'}]});  // But this isn't triggering a validation error.
    });
}

如何在自定义验证器中查询ORM并根据ORM的响应触发验证错误?

即使找不到用户,也会调用成功回调。您必须检查函数是否将用户作为参数传递:

isUnique: function (email) {
  var User = seqeulize.import('/path/to/user/model');

  User.find({where:{email: email}})
    .success(function (u) { // This gets called
      if(u){
        throw new Error({error:[{message:'Email address already in use!'}]});  // But this isn't triggering a validation error.
      }
    });
}

下面是一个功能正常的
isUnique
验证回调的简化示例(从SequelizeJS v2.0.0开始工作)。我添加了注释来解释重要的部分:

var UserModel = sequelize.define('User', {

    id: {
        type: Sequelize.INTEGER(11).UNSIGNED,
        autoIncrement: true,
        primaryKey: true
    },
    email: {
        type: Sequelize.STRING,
        validate: {
            isUnique: function(value, next) {

                UserModel.find({
                    where: {email: value},
                    attributes: ['id']
                })
                    .done(function(error, user) {

                        if (error)
                            // Some unexpected error occured with the find method.
                            return next(error);

                        if (user)
                            // We found a user with this email address.
                            // Pass the error to the next method.
                            return next('Email address already in use!');

                        // If we got this far, the email address hasn't been used yet.
                        // Call next with no arguments when validation is successful.
                        next();

                    });

            }
        }
    }

});

module.exports = UserModel;

使用Sequelize 2.0,您需要捕获验证错误

首先,使用自定义验证器定义用户模型:

var User = sequelize.define('User',
    {
        email: {
            type: Sequelize.STRING,
            allowNull: false,
            unique: true,
            validate: {
                isUnique: function (value, next) {
                    var self = this;
                    User.find({where: {email: value}})
                        .then(function (user) {
                            // reject if a different user wants to use the same email
                            if (user && self.id !== user.id) {
                                return next('Email already in use!');
                            }
                            return next();
                        })
                        .catch(function (err) {
                            return next(err);
                        });
                }
            }
        },
        other_field: Sequelize.STRING
    });

module.exports = User;
const { DataTypes } = require('sequelize');
const sequelize = require('../config/db');

const UserModel = sequelize.define('user', {
  id: {
    type: DataTypes.INTEGER(11).UNSIGNED,
    autoIncrement: true,
    primaryKey: true,
  },
  name: {
    type: DataTypes.STRING,
    allowNull: false,
  },
  email: {
    type: DataTypes.STRING,
    allowNull: false,
    validate: {
      isUnique: (value, next) => {
        UserModel.findAll({
          where: { email: value },
          attributes: ['id'],
        })
          .then((user) => {
            if (user.length != 0)
              next(new Error('Email address already in use!'));
            next();
          })
          .catch((onError) => console.log(onError));
      },
    },
  },
  password: {
    type: DataTypes.STRING,
    allowNull: false,
  },
  createdAt: {
    type: DataTypes.DATE,
    allowNull: false,
  },
  updatedAt: {
    type: DataTypes.DATE,
    allowNull: false,
  },
});

module.exports = UserModel;
然后,在控制器中捕获任何验证错误:

var Sequelize = require('sequelize'),
    _ = require('lodash'),
    User = require('./path/to/User.model');

exports.create = function (req, res) {
    var allowedKeys = ['email', 'other_field'];
    var attributes = _.pick(req.body, allowedKeys);
    User.create(attributes)
        .then(function (user) {
            res.json(user);
        })
        .catch(Sequelize.ValidationError, function (err) {
            // respond with validation errors
            return res.status(422).send(err.errors);
        })
        .catch(function (err) {
            // every other error
            return res.status(400).send({
                message: err.message
            });
        });

您可以验证电子邮件是否已经存在,如下所示:

email: {
  type: Sequelize.STRING,
  allowNull: false,
  validate: {
    isEmail:true
  },
  unique: {
      args: true,
      msg: 'Email address already in use!'
  }
}

使用自定义验证器定义用户模型:

var User = sequelize.define('User',
    {
        email: {
            type: Sequelize.STRING,
            allowNull: false,
            unique: true,
            validate: {
                isUnique: function (value, next) {
                    var self = this;
                    User.find({where: {email: value}})
                        .then(function (user) {
                            // reject if a different user wants to use the same email
                            if (user && self.id !== user.id) {
                                return next('Email already in use!');
                            }
                            return next();
                        })
                        .catch(function (err) {
                            return next(err);
                        });
                }
            }
        },
        other_field: Sequelize.STRING
    });

module.exports = User;
const { DataTypes } = require('sequelize');
const sequelize = require('../config/db');

const UserModel = sequelize.define('user', {
  id: {
    type: DataTypes.INTEGER(11).UNSIGNED,
    autoIncrement: true,
    primaryKey: true,
  },
  name: {
    type: DataTypes.STRING,
    allowNull: false,
  },
  email: {
    type: DataTypes.STRING,
    allowNull: false,
    validate: {
      isUnique: (value, next) => {
        UserModel.findAll({
          where: { email: value },
          attributes: ['id'],
        })
          .then((user) => {
            if (user.length != 0)
              next(new Error('Email address already in use!'));
            next();
          })
          .catch((onError) => console.log(onError));
      },
    },
  },
  password: {
    type: DataTypes.STRING,
    allowNull: false,
  },
  createdAt: {
    type: DataTypes.DATE,
    allowNull: false,
  },
  updatedAt: {
    type: DataTypes.DATE,
    allowNull: false,
  },
});

module.exports = UserModel;

好吧,这行不通,你可以试着简单地运行
.find()
,然后在回调中操纵查询结果并调用
响应。渲染
或其他任何东西来向用户发送消息。真的!?我试图编程到Sequelize接口,而不是一个可靠的实现。为什么上述方法不起作用?我只能想象.find在某个地方捕捉到了错误?只是为了澄清一下,User.find({where:{email:email}}).success()工作得非常好(如Sequelize文档中指定的)。问题是Sequelize没有捕捉到错误,或者在其他地方捕捉到错误。据我所知,
User.find()
返回一个事件,它会在发出事件时抛出一个错误,因此调用
是唯一的('example@example.com“
,甚至尝试
try..catch
也不行。好的,看来我还有很多工作要做才能让续集成型。它远没有我被引导去相信的那么强大……这!我不明白为什么其他人需要运行
用户。在插入之前查找
。@BaNz是的,你可以这样做&显然更好,但是如果你的表中有自动递增值,那么如果你的插入查询因唯一冲突而失败,那么你的自动递增id也会增加,是的,这是任何SQL的工作方式。我很困惑,您似乎使用了列
email
unique
属性(即不作为
validate
对象的属性)。假设
attributes.column.unique
的值可以是
String | Boolean
;但您的值是一个对象(不是字符串或布尔值),其值为:`{args:true,msg:''.'}`。如果将该值添加到
validate
对象中,则该值与使用
unique
的方式类似;但是在
email
(aka column)对象上直接有
unique
unique
参数接受对象,如果它有
args
作为“字符串”或“布尔”值。msg属性用作验证消息。我已将其更改为已接受的答案。它是在最初的问题出现将近4年后才被回答的,我只是刚刚注意到了它。我很不安的是,在被接受的答案中的代码包含了一条注释,上面写着“这不起作用”。特别是因为代码似乎依赖于可能不起作用的东西。这是因为我只是复制了问题中的代码,并添加了if语句,这样它就会起作用。我删除了误导性的注释谢谢你的回答。我使用上述方法进行查询,但无法捕获控制器上的验证错误。因为我使用的是wait User.create()而不是User.create().then()。我已尝试在try块中嵌套User.create(),并在catch块中捕获错误,但无法在catch块中获取这些验证错误。有什么建议吗?