MongoDB使用Node.js进行查找
$lookup 操作符是一个聚合操作符或者聚合阶段,它用于根据一些查询条件将一个集合中的文档连接到同一数据库的另一个集合中的文档。这两个集合应该属于同一个数据库。
在MongoDB中,聚合操作 是将多个文档的值进行分组的操作,并可以对分组的数据执行各种操作以返回单个结果。而 $lookup 就是聚合操作之一。
$lookup的工作原理
我们有两个集合,一个是 输入集合 (对应$lookup操作的集合),另一个是 from集合 (我们从中获取文档来与输入集合的文档进行连接)。
$lookup 根据一些查询条件从 from集合 中选择文档,并将它们附加到 输入集合 的文档中的一个单独的数组字段中。它就像SQL中的左外连接一样。
使用相等匹配进行$lookup操作:
在相等匹配中,对于每个文档,将输入集合文档的任何特定字段的值与from集合文档的任何特定字段的值进行比较,如果它们匹配,则将特定的from集合文档附加到输入集合文档的一个单独的数组字段中。
语法:$lookup操作符
{
$lookup:
{
from: < "from collection" >,
localField: < any field from "input collection" >,
foreignField: < any field from "from collection" >,
as: < attached array field >
}
}
- from: 这是一个包含“from collection”名称的字段,从这个集合中取出的文档将与输入集合的文档进行连接。
- localField: 它是输入集合中的任何字段,其值将与foreignField的值进行比较。
- foreignField: 它是“from collection”中的任何字段,其值将与localField的值进行比较。
- as: 这是用于存储与“from collection”中匹配的文档的数组字段。
安装Mongoose:
步骤1: 您可以访问链接Install mongoose来安装mongoose模块。您可以使用以下命令安装此包。
npm install mongoose
步骤2: 现在你可以通过以下方式在你的文件中导入mongoose模块:
const mongoose = require('mongoose');
数据库: 我们已经在我们的GFG数据库中创建了名为orders和customers的集合,以下为图像中显示的条目:
创建一个Node应用程序:
步骤1: 使用以下命令创建 package.json 文件:
npm init
步骤2: 创建文件 model.js ,其中包含 orders 和 customers 集合的模式和模型。
步骤3: 创建文件 main.js,并使用以下代码。
运行命令 main.js :
node main.js
解释 :在这里,每个customers集合文档的_id字段值与每个orders集合文档的customerId字段进行比较,如果它们匹配,则将该orders集合文档附加到customers集合文档的orders_info数组字段中。
注意: 在这里使用 $unwind
将“orders_info”数组字段从输入文档中拆分,以便为每个元素输出一个文档。通过这样做,我们将能够看到每个附加的文档。
输出: 在控制台中,我们得到了使用$lookup
从collection文档中将它们与input collection文档连接后的文档。
当我们从代码中删除 $unwind 操作符时,我们将得到以下输出:
使用多个连接条件执行$lookup:
语法:$lookup
运算符
{ $lookup: { from: <"来源集合">, let: { <变量_1>: <字段_1>, <变量_2>: <字段_2>, …… }, pipeline: <要在“来源”集合上执行的不同管道阶段>, as: <附加的数组字段> } }
- from: 这是包含“来源集合”名称的字段,从中获取文档以将其与输入集合的文档连接。
- let: 这是一个可选字段。管道不能直接访问“输入”文档字段,因此在let变量中,我们定义要在管道中使用的输入文档字段的名称来执行查询。
- pipeline: 这是在“来源”集合的文档上运行不同管道阶段的字段,并返回结果文档到数组字段中。
- as: 这是存储来自“来源”集合的匹配文档的数组字段。
注意:
- 要使用在
$let
字段中定义的变量,我们像这样引用它$$<变量>
。 - 在$match中使用
$expr
运算符,以访问$let
字段中的变量。
按照下面给出的方式更改 main.js 文件并运行以获取结果:
使用命令运行 main.js :
node main.js
解释: 在上面的代码中,我们正在将来自订单集合的文档连接起来,其中 customerId 的值与 customers 集合的 _id
值匹配,并且 itemName 的值为 “Watch” 。为了在管道中使用 customers 集合的 _id
字段,我们在 let 字段中将其定义为 custId。
注意: 这里使用了 $unwind
来解构输入文档中的 “orders_info” 数组字段,以便为每个元素输出一个文档。通过这样做,我们将能够看到每个附加的文档。
输出: 在控制台上,我们得到了如下所示的匹配文档:
当我们从代码中去除 $unwind
运算符时,我们将得到如下所示的输出: