Reputation: 53
I want to take each element of an array of documents I queried and check if it is in an other array of documents I queried
I have this model :
var dataTypeSchema = new Schema({
name : String,
description : String,
// Personnel || Professionel || Intime
category : String,
provenance : {
type : Schema.ObjectId,
ref : 'Service'
}
});
and this one :
var dataUseSchema = new Schema({
purpose : {
type : Schema.ObjectId,
ref : 'Purposes'
},
dataTypes : [{
type : Schema.ObjectId,
ref : 'DataType'
}],
description : String,
service : {
type : Schema.ObjectId,
ref : 'Service'
},
user : {
type : Schema.ObjectId,
ref : 'User'
}
});
I basically query an array of dataTypes and then want to check for each one if it is in a specific dataUse.data
I tried several methods of comparison : includes, indexOf, even comparing each elements _ids, it always returns false
I have checked that both arrays indeed contain documents and that they have some documents in common
Here is my code (one attempt) for comparing, I am first getting an array of DataUses and then for each one I want to check which values it shares with the dataTypesArray
const dataTypesArray = await Service.getServiceDataTypes(req.params.serviceName)
DataUse.find({service : serviceID, user : serviceID})
.populate('purpose dataTypes service user')
.exec()
.then(dataUses => {
for(let j = 0; j < dataUses.length; j++) {
for(let k = 0; k < dataTypesIDs.length; k++) {
if(dataUses[j].dataTypes.indexOf(dataTypesIDs[k])==-1) {
dataUses[j]["otherData"].push(dataTypesIDs[k])
}
}
}
return dataUseArray
})
.catch(console.log)
For the last if (condition)
, everything sets equal to -1
Both dataTypes
arrays are populated, but as I said I tried comparing just _id and still same result
thanks !
Upvotes: 1
Views: 1082
Reputation: 1789
Here is how you can do it...
To compare an array with other of Mongoose Array.
See the IDs your are getting are mongoose
ObjectID
which is an object
To compare an Array of ObjectID with other ObjectID:
// converting dataTypes to String,
// you can also convert it by using `lean`
// i.e Model.find().lean().exec()
// this would return JavascriptObject instead of MongooseModel
dataTypeIDs = dataTypes.map(i => i.toString()); // converting to plain
// Array of string
dataTypeIDs.indexOf(someDataTypeID.toString()); // returns -1 if not found
You can use the last line to convert it anyway you like in your if (condition)
Change this block of code like this:
.then(dataUses => {
// assuming its an Array of ObjectID
dataTypesIDsArray = dataTypesIDs.map(i => i.toString())
for(let j = 0; j < dataUses.length; j++) {
usesDataTypes = dataUses[j].dataTypes.map(i => i.toString())
for(let k = 0; k < dataTypesIDsArray.length; k++) {
if(usesDataTypes.indexOf(dataTypesIDsArray[k]) == -1) {
dataUses[j]["otherData"].push(dataTypesIDsArray[k])
// use ObjectID from mongoDB if you want to cast it to "ObjectId"
}
}
}
return dataUseArray;
})
Its not tested, but I have taken reference of an existing tested code from my project.
Upvotes: 2