[英]How can i iterate mongoose returned documents array in loop using mongoose?
我有一個node.js(express based)
服務器,其中我有一個function
返回所有users
。 這是 function。
export async function findAllUser() {
let users = await User.find({}).exec()
return users
}
在我的node.js
應用程序中,我有兩個這樣的Users
和Referrals
人models(schema)
。
var User = mongoose.model( "users", new Schema({ first_name: String, last_name: String, name: String, email: String, password: String, roleId: { type: Number, default: 0 }, country: String, token: String, createdAt: String, updatedAt: String, tempToken: String, verificationCode: String, fbUserId: String, isFbUser: { type: Boolean, default: false }, isActive: { type: Boolean, default: true }, isEmailVerified: { type: Boolean, default: false }, rememberme: Boolean, }, { toJSON: { virtuals: true }, toObject: { virtuals: true } }) ); User.virtual("referrals", { ref: "referralLinks", foreignField: "userId", localField: "_id" });
export var ReferralLink = mongoose.model(
"referralLinks",
new Schema({
referral_link: String,
referral_code: String,
isLink: Number,
offer_name: String,
offer_desc: String,
user_email: String,
companyId: { type: Schema.Types.ObjectId, ref: 'companies' },
addedByAdmin: { type: Boolean, default: true },
number_of_clicks: Number,
referral_country: String,
link_status: String,
categoryId: { type: Schema.Types.ObjectId, ref: 'categories' },
number_of_clicks: { type: Number, default: 0 },
createdAt: String,
updatedAt: String,
userId: { type: Schema.Types.ObjectId, ref: 'users' }
})
);
我有我單獨的api.route.js
文件,其中我有所有用戶這樣的路由
router.get("/", log, getAllUsers);
我的api.controller.js
文件有這樣的getAllUsers
export async function getAllUsers(req, res) {
try {
let Users = await findAllUser()
if (Users) {
generateResponse(true, "All Users fetched", Users, res)
} else {
generateResponse(false, "No Users found", null, res)
}
} catch (err) {
generateResponse(false, 'Error occured, 404 not found!', err, res)
}
}
在我的api.handler.js
文件中,我有這樣的findAllUser
function
export async function findAllUser() { let users = await User.find({}).populate("referrals").exec() return users }
單個用戶可以擁有多個Referrals
人。 但不幸的是,我在Users
文檔中沒有“推薦人”參考_id
。 現在,我想讓所有用戶都有各自的Referrals
人
我正確地獲得了所有users
,但對於每個用戶,我也想獲取他們各自的referrals
。 因此,由於 mongoose find 的異步性質,我絕對不能使用for
或forEach
循環。 那么我應該使用什么來代替for
或forEach
循環呢?
我想要的結果
results = [ { first_name: "Fahad", last_name: "subzwari", email: "fahadsubzwari@gmail.com", password: "***", referrals: [ { //referral object 1 }, { //referral object 2... } ] }, { first_name: "Alex", last_name: "Hales", email: "alex@gmail.com", password: "***", referrals: [ { //referral object 1 }, { //referral object 2... }, { //referral object 3... } ] }, ]
為了能夠訪問用戶的推薦,您需要使用virtual populate 。
所以你的 userSchema 必須是這樣的:
const userSchema = new Schema(
{
first_name: String,
last_name: String,
name: String,
email: String,
password: String,
roleId: { type: Number, default: 0 },
country: String,
token: String,
createdAt: String,
updatedAt: String,
tempToken: String,
verificationCode: String,
fbUserId: String,
isFbUser: { type: Boolean, default: false },
isActive: { type: Boolean, default: true },
isEmailVerified: { type: Boolean, default: false },
rememberme: Boolean
},
{
toJSON: { virtuals: true },
toObject: { virtuals: true }
}
);
// Virtual populate
userSchema.virtual("referrals", {
ref: "referralLinks",
foreignField: "userId",
localField: "_id"
});
var User = mongoose.model("users", userSchema);
現在您可以使用此路由訪問用戶的推薦:
router.get("/", async (req, res) => {
const result = await User.find({}).populate("referrals");
res.send(result);
});
結果將是這樣的:(為簡單起見,我排除了一些字段)
[
{
"_id": "5dd6819201419f5930d02334",
"name": "User 1",
"email": "user1@gmail.com",
"password": "123123",
"__v": 0,
"referrals": [
{
"_id": "5dd6829831b95a6b2cd58fca",
"referral_link": "referral_link 1",
"userId": "5dd6819201419f5930d02334",
"__v": 0
},
{
"_id": "5dd682a031b95a6b2cd58fcb",
"referral_link": "referral_link 2",
"userId": "5dd6819201419f5930d02334",
"__v": 0
}
],
"id": "5dd6819201419f5930d02334"
},
{
"_id": "5dd681a101419f5930d02335",
"name": "User 2",
"email": "user2@gmail.com",
"password": "123123",
"__v": 0,
"referrals": [
{
"_id": "5dd682a731b95a6b2cd58fcc",
"referral_link": "referral_link 3",
"userId": "5dd681a101419f5930d02335",
"__v": 0
}
],
"id": "5dd681a101419f5930d02335"
}
]
更新:
以下是您的項目設置的步驟:
api.handler.js:
exports.findAllUser = async function() {
console.log("api handler inside");
let users = await User.find({})
.populate("referrals")
.exec();
console.log("in handler: ", users);
return users;
};
api.controller.js:
const handler = require("./api.handler");
exports.getAllUsers = async function(req, res) {
console.log("userController.getAllUsers");
try {
let Users = await handler.findAllUser();
if (Users) {
return res.send(Users);
generateResponse(true, "All Users fetched", Users, res);
} else {
generateResponse(false, "No Users found", null, res);
}
} catch (err) {
generateResponse(false, "Error occured, 404 not found!", err, res);
}
};
api.route.js
const apiController = require("../controllers/api.controller");
router.get("/", log, apiController.getAllUsers);
您說“我在用戶中沒有 'Referrals' 參考 _id”,所以我假設您在 Referrals 架構中有對用戶的參考?
否則,沒有辦法將它們聯系起來,恐怕你會迷失在海上...... :-(
如果你這樣做,那么你會在一個單獨的查詢中這樣做:
const userIds = users.map(user => user._id);
const referrals = await Referrals.find({ userId: { $in: userIds } })
$in 運算符將抓取數組中包含用戶 ID 的任何字段。
編輯:響應您的更新 - 是的,上面應該可以正常工作。 然后你可以用它們做你想做的事情,例如 map 對用戶對象的引用,或者單獨使用它們等等。
EDIT2:是的,這就是方式。 此時,您有一組用戶和一組推薦,因此您只需將它們放在一起。
users.map(user => ({
// add props from user obj
...user,
// add all referrals that with matching userId
referrals: referrals.filter(referral => referral.userId === user._id)
}))
請記住,當您處理異步調用和承諾時,您將需要使用 async/await 關鍵字,或者在 promise 回調中解析結果。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.