Node.js E11000 mongodb mongoose中的重复密钥错误索引

Node.js E11000 mongodb mongoose中的重复密钥错误索引,node.js,mongodb,mongoose,Node.js,Mongodb,Mongoose,下面是我在user.js模型中的user模式- var userSchema = new mongoose.Schema({ local: { name: { type: String }, email : { type: String, require: true, unique: true }, password: { type: String, require:true }, }, facebook: {

下面是我在
user.js
模型中的
user
模式-

var userSchema = new mongoose.Schema({
    local: {
        name: { type: String },
        email : { type: String, require: true, unique: true },
        password: { type: String, require:true },
    },
    facebook: {
        id           : { type: String },
        token        : { type: String },
        email        : { type: String },
        name         : { type: String }
    }
});

var User = mongoose.model('User',userSchema);

module.exports = User;
这就是我在控制器中使用它的方式-

var user = require('./../models/user.js');
这就是我在db中保存它的方式-

user({'local.email' : req.body.email, 'local.password' : req.body.password}).save(function(err, result){
    if(err)
        res.send(err);
    else {
        console.log(result);
        req.session.user = result;
        res.send({"code":200,"message":"Record inserted successfully"});
    }
});
错误-

{"name":"MongoError","code":11000,"err":"insertDocument :: caused by :: 11000 E11000 duplicate key error index: mydb.users.$email_1  dup key: { : null }"} 
我检查了数据库集合,但不存在此类重复条目,请告诉我我做错了什么

仅供参考-
req.body.email
req.body.password
都是获取值

我也查看了这篇文章,但没有任何帮助


如果我完全删除了,那么它会插入文档,否则它会抛出错误“重复”错误,即使我在本地有一个条目。电子邮件

错误消息是说已经有一条记录将
null
作为电子邮件。换句话说,您已经有一个没有电子邮件地址的用户

相关文件如下:

如果文档在唯一索引中没有索引字段的值,索引将为此文档存储空值。由于唯一约束,MongoDB将只允许一个缺少索引字段的文档。如果有多个文档没有索引字段的值或缺少索引字段,则索引生成将失败,并出现重复键错误

您可以将唯一约束与稀疏索引相结合,从唯一索引中过滤这些空值并避免错误

稀疏索引仅包含具有索引字段的文档的条目,即使索引字段包含空值也是如此

换句话说,对于所有具有
null
值的多个文档,稀疏索引是可以的


从评论中:


您的错误显示密钥名为
mydb.users.$email_1
,这使我怀疑您在
users.email
users.local.email
上都有索引(前者目前已过时且未使用)。从Mongoose模型中删除字段不会影响数据库。如果是这种情况,请检查
mydb.users.getIndexes()
,并使用
mydb.users.dropIndex()

手动删除不需要的索引。错误消息表示电子邮件中已有一条记录为
null
。换句话说,您已经有一个没有电子邮件地址的用户

相关文件如下:

如果文档在唯一索引中没有索引字段的值,索引将为此文档存储空值。由于唯一约束,MongoDB将只允许一个缺少索引字段的文档。如果有多个文档没有索引字段的值或缺少索引字段,则索引生成将失败,并出现重复键错误

您可以将唯一约束与稀疏索引相结合,从唯一索引中过滤这些空值并避免错误

稀疏索引仅包含具有索引字段的文档的条目,即使索引字段包含空值也是如此

换句话说,对于所有具有
null
值的多个文档,稀疏索引是可以的


从评论中:


您的错误显示密钥名为
mydb.users.$email_1
,这使我怀疑您在
users.email
users.local.email
上都有索引(前者目前已过时且未使用)。从Mongoose模型中删除字段不会影响数据库。如果是这种情况,请检查mydb.users.getIndexes(),并使用mydb.users.dropIndex()手动删除不需要的索引

在“User”模式中,我将“name”设置为唯一键,然后运行一些执行,我认为这设置了数据库结构

然后我将唯一键更改为“username”,并在将数据保存到数据库时不再传递“name”值。因此mongodb可以自动将新记录的“name”值设置为null,这是重复的密钥。我尝试将“name”键设置为“User”架构中的非唯一键
{name:{unique:false,type:String}}
,以覆盖原始设置。然而,它没有起作用

最后,我提出了自己的解决方案:


在保存数据记录时,只需设置一个随机键值,该值不可能与“name”键重复。简单的数学方法
“”+Math.random()+Math.random()
生成一个随机字符串。

这是我的相关经验:

在“User”模式中,我将“name”设置为唯一键,然后运行一些执行,我认为这设置了数据库结构

然后我将唯一键更改为“username”,并在将数据保存到数据库时不再传递“name”值。因此mongodb可以自动将新记录的“name”值设置为null,这是重复的密钥。我尝试将“name”键设置为“User”架构中的非唯一键
{name:{unique:false,type:String}}
,以覆盖原始设置。然而,它没有起作用

最后,我提出了自己的解决方案:


在保存数据记录时,只需设置一个随机键值,该值不可能与“name”键重复。简单的数学方法
“”+Math.random()+Math.random()
生成一个随机字符串。

检查集合索引

我有这个问题是因为字段集合中的索引过时了,这些索引应该通过不同的新路径存储


当您将字段指定为唯一字段时,Mongoose会添加索引。

检查集合索引

我有这个问题是因为字段集合中的索引过时了,这些索引应该通过不同的新路径存储


当您将字段指定为唯一字段时,Mongoose会添加索引。

如果您仍在开发环境中,我会删除整个数据库,并使用新模式重新开始

从命令行

➜ mongo
use dbName;
db.dropDatabase();
exit

如果您仍在开发环境中,我将删除整个数据库,并使用新模式重新开始

从命令行

➜ mongo
use dbName;
db.dropDatabase();
exit
我有一个sim卡
module.exports.models = {
  connection: 'mongodb',
  migrate: 'safe'
}
db.users.drop();
unique: true
➜ mongo
use dbName;
db.dropDatabase();
exit
facebookId: {
    type: String,
    index:true
  },
  facebookId: {
    type: String,
    index:true,
    unique:true,
    sparse:true
  },
index:true,
unique:true,
sparse:true