我的数据库在生产中的搜索很奇怪:如果我没有指定_id
,它就找不到对象。
当我仅使用_id
进行搜索时,它可以正常运行:
MongoDB shell version v3.6.2
connecting to: mongodb://127.0.0.1:hidevalue000/hidevalue001
MongoDB server version: 3.6.2
> hidevalue001:PRIMARY>
> hidevalue001:PRIMARY>
> hidevalue001:PRIMARY>
> hidevalue001:PRIMARY> db.trackings.find({_id:ObjectId('hidevalue002')}).pretty()
{
"_id" : ObjectId("hidevalue002"),
"public" : false,
"creation_date" : ISODate("2018-03-08T09:43:27.661Z"),
"user_id" : ObjectId("hidevalue003"),
"apikey" : "hidevalue004",
"type" : "autodiag",
"key" : "autodiag_data",
"value" : "hidevalue005",
"__v" : 0
}
> hidevalue001:PRIMARY>
> hidevalue001:PRIMARY>
当我在没有_id
的情况下进行搜索时,它不会向我返回任何内容:
> hidevalue001:PRIMARY> db.trackings.find(
... {
... "user_id" : ObjectId("hidevalue003"),
... "apikey" : "hidevalue004",
... "type": "autodiag",
... "key" : "autodiag_data"
... }).pretty()
> hidevalue001:PRIMARY>
> hidevalue001:PRIMARY>
当我使用_id
进行搜索时,它会很好地返回结果:
> hidevalue001:PRIMARY> db.trackings.find(
... {
... "_id" : ObjectId("hidevalue002"),
... "user_id" : ObjectId("hidevalue003"),
... "apikey" : "hidevalue004",
... "type": "autodiag",
... "key" : "autodiag_data",
... }).pretty()
{
"_id" : ObjectId("hidevalue002"),
"public" : false,
"creation_date" : ISODate("2018-03-08T09:43:27.661Z"),
"user_id" : ObjectId("hidevalue003"),
"apikey" : "hidevalue004",
"type" : "autodiag",
"key" : "autodiag_data",
"value" : "hidevalue005",
"__v" : 0
}
> hidevalue001:PRIMARY>
> hidevalue001:PRIMARY>
基数跟踪总数:
> hidevalue001:PRIMARY> db.trackings.find().count()
38330
MongoDB索引由Mongoose 5.0.1版(NodeJS)配置:
// Init
var trackingsSchema = new mongoose.Schema(
{
user_id: { type:mongoose.Schema.Types.ObjectId },
apikey: { type:String },
type: { type:String },
key: { type:String },
value: { type:String },
public: { type:Boolean, default:false },
creation_date: { type:Date, default:Date.now }
});
// Set index
trackingsSchema.index(
{
'user_id': 1,
'apikey': 1,
'type': 1,
'key': 1,
'value': 1,
'public': 1,
'creation_date':-1
}, { name: 'hidevalue006' });
编辑:
如果我在搜索中删除user_id
,那么我会找到我的文档。
> hidevalue001:PRIMARY> db.trackings.find(
... {
... "apikey" : "hidevalue004",
... "type": "autodiag",
... "key" : "autodiag_data",
... "creation_date" : ISODate("2018-03-08T09:43:27.661Z")
... }).pretty()
{
"_id" : ObjectId("hidevalue002"),
"public" : false,
"creation_date" : ISODate("2018-03-08T09:43:27.661Z"),
"user_id" : ObjectId("hidevalue003"),
"apikey" : "hidevalue004",
"type" : "autodiag",
"key" : "autodiag_data",
"value" : "hidevalue005",
"__v" : 0
}
> hidevalue001:PRIMARY>
> hidevalue001:PRIMARY>
db.trackings.validate ()
命令不会返回错误。
hidevalue001:PRIMARY> db.trackings.validate()
{
"ns" : "hidevalue000.hidevalue001",
"nInvalidDocuments" : NumberLong(0),
"nrecords" : 39024,
"nIndexes" : 2,
"keysPerIndex" : {
"hidevalue002.trackings.$_id_" : 39024,
"hidevalue002.trackings.$hidevalue003" : 38494
},
"valid" : true,
"warnings" : [
"Some checks omitted for speed. use {full:true} option to do more thorough scan."
],
"errors" : [ ],
"ok" : 1
}
编辑:
我尝试db.trackings.reIndex()
,结果相同。
编辑:
我创建了一个新的集合并重新索引我的所有文档,同样的结果,如果我指定user_id
,我找不到我的文档。
> db.createCollection('trackings_v2');
>
>
> db.trackings_v2.createIndex(
{
'user_id': 1
'apikey': 1
'type': 1
'key': 1
'value': 1
'ip': 1
'public': 1
'creation_date': 1
},
{ name: 'hidevalue010' });
>
>
> db.trackings.find({}).forEach(function(e)
{
delete e._id;
delete e.__v;
db.trackings_v2.update(e, e, {upsert:true});
})
>
>
编辑:
某些跟踪使用相同的user_id
,因此某些跟踪可能会被严格编入索引...
解决方案:
值字段的值大于1024字节,如果我们不指定它,mongoDB不喜欢大值...我不认为他不会对它进行任何记录...
更改跟踪索引:
trackingsSchema.index(
{
'user_id': 1,
'apikey': 1,
'type': 1,
'key': 1,
'value': 'text',
'public': 1,
'creation_date':-1
}, { name: 'hidevalue006' });
重新索引所有集合(或仅跟踪):
db.getCollectionNames().forEach(function(collname)
{
db.getCollection(collname).reIndex();
});
答案 0 :(得分:1)
我找到了解决方案......
值字段的值大于1024字节,如果我们不指定它,mongoDB不喜欢大值...我不认为他不会对它进行任何记录...
更改跟踪索引:
trackingsSchema.index(
{
'user_id': 1,
'apikey': 1,
'type': 1,
'key': 1,
'value': 'text',
'public': 1,
'creation_date':-1
}, { name: 'hidevalue006' });
重新索引所有集合(或仅跟踪):
db.getCollectionNames().forEach(function(collname)
{
db.getCollection(collname).reIndex();
});