正文

MongoDB中实现多表联查的实例教程(mongodb 表关联)深度揭秘

文章摘要

这篇文章主要介绍了如何利用MongoDB的聚合查询功能来实现复杂的字段过滤和数据处理。文章详细讨论了以下内容: 1. **字段过滤操作**:使用`$eq`和`$in`等操作符进行字段匹配,结合`$match`方法筛选符合条件的数据。 2. **日期范围过滤**:通过`$lte`和`$gte`操作符设置日期范围,结合`$in`方法过滤特定状态。 3. **连表操作**:使用`$lookup`方法连接其他表(如`coupons`表),并使用`$let`方法提取相关字段。 4. **聚合查询结构**:通过管道式结构组织查询,包括匹配、投影和分片操作,最终生成所需的结果集。 5. **结果分片和聚合**:利用`$facet`方法对结果进行分片和统计,提高查询效率。 文章通过实例展示了MongoDB聚合查询的高级功能,以及如何结合连表和分片操作实现高效的复杂查询。

// 每次必有的条件,当前表的字段用 `$$`,连表的字段用 `$` const filter=[{ $eq: [‘$$userId’, userId] }, { $eq: [‘$isDeleted’, false] }]; if (status===Expired) { dateOp=’$lte’; } else if (status===Normal) { dateOp=’$gte’; filter.push({ $in: [‘$$status’, [Normal, Shared]] }); } else { dateOp=’$gte’; filter.push({ $eq: [‘$$status’, status] }); } const results=await myModel.aggregate([ { $lookup: { from: ‘coupons’, // 当前表字段必须 `let` 之后才能用 let: { couponId: ‘$couponId’, userId: ‘$userId’, status: ‘$status’ }, // 在 pipeline 里完成筛选 pipeline: [ { $match: { $expr: { // `$toString` 是内建方法,可以把 `ObjectId` 转换成 `string` $and: [{ $eq: [{ $toString: ‘$_id’ }, ‘$$couponId’] }, …filter, { [dateOp]: [‘$endAt’, new Date()] }], }, }, }, // 只要某些字段,在这里筛选 { $project: couponFields, }, ], as: ‘source’, }, }, { // 这种筛选相当 LEFT JOIN,所以需要去掉没有连表内容的结果 $match: { source: { $ne: [] }, }, }, { // 为了一次查表出结果,要转换一下输出格式 $facet: { results: [{ $skip: size * (page – 1) }, { $limit: size }], count: [ { $count: ‘count’, }, ], }, }, ]);