Para agentes de IA: hay un índice de documentación disponible en https://www.mongodb.com/es/docs/llms.txt — versiones en markdown de todas las páginas están disponibles agregando .md a cualquier ruta URL.
Docs Menu

$lookup (etapa de agregación)

$lookup

Cambiado en la versión 8.0.

Performs a left outer join to a collection in the same database to filter in documents from the foreign collection for processing. The $lookup stage adds a new array field to each input document. The new array field contains the matching documents from the foreign collection. The $lookup stage passes these reshaped documents to the next stage.

A partir de MongoDB,5.1 puede usar con colecciones $lookup fragmentadas.

Para combinar elementos de dos colecciones diferentes, utiliza la plataforma de $unionWith del pipeline.

Importante

$lookup performance, as with any other query performance, depends on the operation type and whether the foreign field is indexed. Unindexed or correlated-subquery $lookup operations on large collections can slow down query performance. To reduce reliance on $lookup, consider an embedded data model to store related data in a single collection.

For details on $lookup performance by operation type, see Performance Considerations.

Puedes usar $lookup para implementaciones alojadas en los siguientes entornos:

  • MongoDB Atlas: El servicio totalmente gestionado para implementaciones de MongoDB en la nube
  • MongoDB Enterprise: La versión basada en suscripción y autogestionada de MongoDB

  • MongoDB Community: La versión de MongoDB con código fuente disponible, de uso gratuito y autogestionada.

The $lookup stage syntax:

{
$lookup:
{
from: <collection to join>,
localField: <field from the input documents>,
foreignField: <field from the documents of the "from" collection>,
let: { <var_1>: <expression>, …, <var_n>: <expression> },
pipeline: [ <pipeline to run> ],
as: <output array field>
}
}

The $lookup accepts a document with these fields:

Campo
Necesidad
Descripción

Requerido

Especifica la colección foránea en la misma base de datos para unirse a la colección local.

Es posible en algunos casos extremos sustituir from por pipeline usando $documents como la primera etapa. Para un ejemplo, consulta Usar una etapa $documents en una etapa $lookup.

A partir de MongoDB 5.1, la colección from se puede fragmentar.

Opcional si se especifica pipeline

Specifies the field from the documents input to the $lookup stage. $lookup performs an equality match on the localField to the foreignField from the documents of the from collection. If an input document does not contain the localField, the $lookup treats the field as having a value of null for matching purposes.

Opcional si se especifica pipeline

Especifica los foreignField de los documentos foráneos para realizar una coincidencia exacta con los localField de los documentos locales.

If a foreign document does not contain a foreignField value, the $lookup uses a null value for the match.

Opcional

Specifies variables to use in the pipeline stages. Use the variable expressions to access the fields from the local collection's documents that are input to the pipeline.

To reference variables in pipeline stages, use the "$$<variable>" syntax.

The let variables can be accessed by the stages in the pipeline, including additional $lookup stages nested in the pipeline.

  • Una etapa $match requiere el uso de un operador $expr para acceder a las variables. El operador $expr permite el uso de expresiones de agregación dentro de la sintaxis de $match.

    The $eq, $lt, $lte, $gt, and $gte comparison operators placed in an $expr operator can use an index on the from collection referenced in a $lookup stage. Limitations:

    • Los índices solo pueden utilizarse para comparaciones entre campos y constantes, por lo que el operando let debe resolverse en una constante.

      Por ejemplo, una comparación entre $a y un valor constante puede utilizar un índice, pero una comparación entre $a y $b no puede.

    • Los índices no se utilizan para comparaciones donde el operando let se resuelve en un valor vacío o faltante.

    • No se utilizan índices multiclave, parciales o dispersos.

  • Other (non-$match) stages in the pipeline do not require an $expr operator to access the variables.

Opcional si se especifican localField y foreignField

Especifica el pipeline que se ejecutará en la colección foránea. El pipeline devuelve documentos de la colección externa. Para devolver todos los documentos, especifica un pipeline: [] vacío.

El pipeline no puede incluir las etapas ni. A partir de $out $merge la6.0 versión, el pipeline puede contener la etapa de MongoDB Search $search como la primera etapa dentro de la canalización. Para obtener más información, consulte la sección de compatibilidad con MongoDB Search.

The pipeline cannot access fields from input documents. Instead, define variables for the document fields using the let option and then reference the variables in the pipeline stages.

To reference variables in pipeline stages, use the "$$<variable>" syntax.

The let variables can be accessed by the stages in the pipeline, including additional $lookup stages nested in the pipeline.

  • Una etapa $match requiere el uso de un operador $expr para acceder a las variables. El operador $expr permite el uso de expresiones de agregación dentro de la sintaxis de $match.

    The $eq, $lt, $lte, $gt, and $gte comparison operators placed in an $expr operator can use an index on the from collection referenced in a $lookup stage. Limitations:

    • Los índices solo pueden utilizarse para comparaciones entre campos y constantes, por lo que el operando let debe resolverse en una constante.

      Por ejemplo, una comparación entre $a y un valor constante puede utilizar un índice, pero una comparación entre $a y $b no puede.

    • Los índices no se utilizan para comparaciones donde el operando let se resuelve en un valor vacío o faltante.

    • No se utilizan índices multiclave, parciales o dispersos.

  • Other (non-$match) stages in the pipeline do not require an $expr operator to access the variables.

Requerido

Especifica el nombre del nuevo campo de arreglo que se añadirá a los documentos de entrada. El nuevo campo de arreglo contiene los documentos coincidentes de la colección from. Si el nombre especificado ya existe en el documento de entrada, el campo existente se sobrescribe.

To perform an equality match between a field from the input documents with a field from the documents of the foreign collection, the $lookup stage has this syntax:

{
$lookup:
{
from: <collection to join>,
localField: <field from the input documents>,
foreignField: <field from the documents of the "from" collection>,
pipeline: [ <pipeline to run> ],
as: <output array field>
}
}

Nota

En este ejemplo, pipeline es opcional y se ejecuta después de la etapa de igualdad local y foránea.

La operación corresponde a esta instrucción pseudo-SQL:

SELECT *, (
SELECT ARRAY_AGG(*)
FROM <collection to join>
WHERE <foreignField> = <collection.localField>
) AS <output array field>
FROM collection;

Nota

Las instrucciones SQL de esta página se incluyen para compararlas con la sintaxis de la pipeline de agregación de MongoDB. Las instrucciones SQL no son ejecutables.

Para ejemplos de MongoDB, consulte estas páginas:

MongoDB admite:

  • Ejecución de una pipeline en una colección externa.

  • Múltiples condiciones de combinación.

  • Subconsultas correlacionadas y no correlacionadas.

In MongoDB, an uncorrelated subquery means that every input document returns the same result. A correlated subquery is a pipeline in a $lookup stage that uses the local or input collection's fields to return results correlated to each incoming document.

Nota

A partir de MongoDB 5.0, para una subconsulta no correlacionada en una etapa de canalización$lookupque contiene una etapa$sample, el operador$sampleRateo el operador$rand, la subconsulta siempre se ejecuta de nuevo si se repite. Anteriormente, dependiendo del tamaño de la salida de la subconsulta, esta se almacenaba en caché o se volvía a ejecutar.

Las sub-query correlacionadas de MongoDB son comparables a las sub-query correlacionadas de SQL, donde la query interna hace referencia a los valores externos de la query. Una sub-query no correlacionada de SQL no hace referencia a valores de la query externa.

MongoDB 5.0 también soporta a los subquery correlacionados concisos.

To perform correlated and uncorrelated subqueries with two collections, and perform other join conditions besides a single equality match, use this $lookup syntax:

{
$lookup:
{
from: <foreign collection>,
let: { <var_1>: <expression>, …, <var_n>: <expression> },
pipeline: [ <pipeline to run on foreign collection> ],
as: <output array field>
}
}

La operación corresponde a esta instrucción pseudo-SQL:

SELECT *, <output array field>
FROM collection
WHERE <output array field> IN (
SELECT <documents as determined from the pipeline>
FROM <collection to join>
WHERE <pipeline>
);

Vea los siguientes ejemplos:

Nuevo en la versión 5.0.

A partir de MongoDB 5.0, puedes usar una sintaxis concisa para una sub-query correlacionada. Las sub-query correlacionadas hacen referencia a campos de documentos de una colección foránea y de la colección "local" en la que se ejecutó el método aggregate().

The following new concise syntax removes the requirement for an equality match on the foreign and local fields inside an $expr operator:

{
$lookup:
{
from: <foreign collection>,
localField: <field from local collection's documents>,
foreignField: <field from foreign collection's documents>,
let: { <var_1>: <expression>, …, <var_n>: <expression> },
pipeline: [ <pipeline to run> ],
as: <output array field>
}
}

La operación corresponde a esta instrucción pseudo-SQL:

SELECT *, <output array field>
FROM localCollection
WHERE <output array field> IN (
SELECT <documents as determined from the pipeline>
FROM <foreignCollection>
WHERE <foreignCollection.foreignField> = <localCollection.localField>
AND <pipeline match condition>
);

Vea este ejemplo:

A partir de MongoDB,8.1 puede hacer referencia a varias colecciones cifradas en una etapa. Sin $lookup embargo, $lookup no admite:

  • Utilizando un campo cifrado como campo de unión en el localField o foreignField.

    Nota

    Para los controladores que usan cifrado a nivel de campo del lado del cliente, puedes usar un campo cifrado como campo de unión solo si estás realizando una operación de unión automática.

  • Usar cualquier campo en un arreglo cifrado. Un arreglo se considera cifrado si contiene algún elemento cifrado.

    • For example, you can't use any field within the resulting as array of the $lookup operation, unless you're using Client-Side Field Level Encryption and $unwind the as field.

If performing an aggregation that involves multiple views, such as with $lookup or $graphLookup, the views must have the same collation.

You cannot include the $out or the $merge stage in the $lookup stage. That is, when specifying a pipeline for the foreign collection, you cannot include either stage in the pipeline field.

{
$lookup:
{
from: <collection to join>,
let: { <var_1>: <expression>, …, <var_n>: <expression> },
pipeline: [ <pipeline to execute on the foreign collection> ], // Cannot include $out or $merge
as: <output array field>
}
}

A partir de MongoDB,6.0 puede especificar la etapa MongoDB Search $search o en $searchMeta la $lookup canalización para buscar colecciones en el clúster Atlas. La $search etapa o debe ser la primera etapa dentro de la $searchMeta $lookup canalización.

For example, when you Join Conditions and Subqueries on a Foreign Collection or run Correlated Subqueries Using Concise Syntax, you can specify $search or $searchMeta inside the pipeline as shown below:

[{
"$lookup": {
"from": <foreign collection>,
localField: <field from the input documents>,
foreignField: <field from the documents of the "from" collection>,
"as": <output array field>,
"pipeline": [{
"$search": {
"<operator>": {
<operator-specification>
}
},
...
}]
}
}]
[{
"$lookup": {
"from": <foreign collection>,
localField: <field from the input documents>,
foreignField: <field from the documents of the "from" collection>,
"as": <output array field>,
"pipeline": [{
"$searchMeta": {
"<collector>": {
<collector-specification>
}
},
...
}]
}
}]

To see an example of $lookup with $search, see the MongoDB Search tutorial Run a MongoDB Search $search Query Using $lookup.

Starting in MongoDB 5.1, you can specify sharded collections in the from parameter of $lookup stages.

A partir de MongoDB 8.0, puedes usar la etapa $lookup dentro de una transacción mientras apunta a una colección fragmentada.

A partir de la 6.0 versión, MongoDB puede usar el motor de consulta de ejecución basado en ranuras para ejecutar $lookup etapas si todas las etapas anteriores en la canalización también pueden ser ejecutadas por el motor de ejecución basado en ranuras y ninguna de las siguientes condiciones es verdadera:

  • La operación $lookup ejecuta una pipeline en una colección foránea. Para ver un ejemplo de este tipo de operación, consulta Condiciones de unión y subconsultas en una colección foránea.

  • Los localField o foreignField de $lookup especifican componentes numéricos. Por ejemplo: { localField: "restaurant.0.review" }.

  • El campo from de cualquier $lookup en el pipeline especifica una vista o una colección fragmentada.

Para obtener más información, consulta $lookupOptimización.

$lookup el rendimiento depende del tipo de operación que se realice. Consulta la siguiente tabla para las consideraciones de rendimiento de las diferentes operaciones de $lookup.

$lookup Operación
Consideraciones sobre el rendimiento
  • $lookup Las operaciones que realizan coincidencias exactas con una sola unión funcionan mejor cuando la colección externa contiene un índice en el foreignField.

    IMPORTANT: If a supporting index on the foreignField does not exist, a $lookup operation that performs an equality match with a single join likely has poor performance.

  • $lookup operaciones que contienen subqueries no correlacionadas funcionan mejor cuando el pipeline interno puede acceder a un índice de la colección externa.

  • MongoDB solo necesita ejecutar una vez la subquery $lookup antes de almacenar en caché la query porque no hay relación entre las colecciones de origen y las externas. La subquery no se basa en ningún valor de la colección de origen. Este comportamiento mejora el rendimiento para las ejecuciones posteriores de la operación $lookup.

  • $lookup las operaciones que contienen subconsultas correlacionadas tienen un mejor rendimiento cuando la colección externa contiene un índice en el foreignField.

  • Si tu pipeline pasa una gran cantidad de documentos a la query$lookup, las siguientes estrategias pueden mejorar el rendimiento:

    • Reduce el número de documentos que MongoDB pasa a la query $lookup. Por ejemplo, establece un filtro más estricto durante la etapa $match.

    • Reconsidere el esquema de los datos para asegurarse de que sea óptimo para el caso de uso.

Para estrategias generales de rendimiento, consulta las Estrategias de indexación y Optimización de query.

Los ejemplos de esta página utilizan datos del conjunto de datos de muestra sample_mflix. Para obtener más información sobre cómo cargar este conjunto de datos en la implementación autogestionada de MongoDB, consultar Cargar el conjunto de datos de muestra. Si se realizó alguna modificación en las bases de datos de muestra, es posible que se deban descartar y volver a crear las bases de datos para ejecutar los ejemplos de esta página.

La siguiente operación de agregación primero filtra la colección movies para películas con un runtime superior a 1000, y luego se une con la colección comments en los campos _id y movie_id:

db.movies.aggregate( [
{ $match: { runtime: { $gt: 1000 } } },
{
$lookup: {
from: "comments",
localField: "_id",
foreignField: "movie_id",
as: "movie_comments"
}
},
{
$project: {
_id: 0,
title: 1,
year: 1,
"movie_comments.name": 1,
"movie_comments.text": 1,
"movie_comments.date": 1
}
}
] )
[
{
title: 'Centennial',
year: 1978,
movie_comments: [
{
name: 'Ellaria Sand',
text: 'Excepturi nam nam eum possimus aspernatur autem. Quis nulla optio praesentium ut distinctio explicabo.',
date: ISODate('1995-08-18T03:01:50.000Z')
}
]
},
{ title: 'Baseball', year: 1994, movie_comments: [] }
]

La operación corresponde a esta instrucción pseudo-SQL:

SELECT *, movie_comments
FROM movies
WHERE movie_comments IN (
SELECT *
FROM comments
WHERE movie_id = movies._id
);

Para obtener más información, consulta Consideraciones sobre el rendimiento de la coincidencia exacta.

Si el localField es un arreglo, puedes comparar los elementos del arreglo contra un escalar foreignField sin una etapa de $unwind.

La siguiente operación de agregación une la colección movies con la colección users, emparejando el campo de arreglo cast de movies con el campo escalar name de users:

db.movies.aggregate( [
{
$match: {
title: {
$in: [ "Roger & Me", "The Sum of Us",
"Centennial" ]
}
}
},
{
$lookup: {
from: "users",
localField: "cast",
foreignField: "name",
as: "cast_users"
}
},
{
$project: {
_id: 0,
title: 1,
year: 1,
cast: 1,
"cast_users.name": 1,
"cast_users.email": 1
}
},
{ $sort: { year: 1 } }
] )
[
{
cast: [
'Raymond Burr',
'Barbara Carrera',
'Richard Chamberlain',
'Robert Conrad'
],
title: 'Centennial',
year: 1978,
cast_users: []
},
{
cast: [
'Michael Moore',
'Roger B. Smith',
'Rhonda Britton',
'Fred Ross'
],
title: 'Roger & Me',
year: 1989,
cast_users: [ { name: 'Michael Moore', email: 'michael_moore@fakegmail.com' } ]
},
{
cast: [
'Jack Thompson',
'Russell Crowe',
'John Polson',
'Deborah Kennedy'
],
title: 'The Sum of Us',
year: 1994,
cast_users: [
{
name: 'Deborah Kennedy',
email: 'deborah_kennedy@fakegmail.com'
}
]
}
]

El $mergeObjects operador combina múltiples documentos en un único documento.

The following operation uses $lookup to join the movies collection with the comments collection, then uses $mergeObjects in $replaceRoot to merge the first comment document with the movie document:

db.movies.aggregate( [
{ $match: { runtime: { $gt: 1000 } } },
{
$lookup: {
from: "comments",
localField: "_id",
foreignField: "movie_id",
as: "movie_comments"
}
},
{
$replaceRoot: {
newRoot: {
$mergeObjects: [
{ $arrayElemAt: [ "$movie_comments", 0 ] },
"$$ROOT"
]
}
}
},
{
$project: {
_id: 0,
title: 1,
year: 1,
genres: 1,
name: 1,
email: 1,
text: 1,
date: 1
}
}
] )
[
{
name: 'Ellaria Sand',
email: 'indira_varma@gameofthron.es',
text: 'Excepturi nam nam eum possimus aspernatur autem. Quis nulla optio praesentium ut distinctio explicabo.',
date: ISODate('1995-08-18T03:01:50.000Z'),
genres: [ 'Action', 'Adventure', 'Drama' ],
title: 'Centennial',
year: 1978
},
{
genres: [ 'Documentary', 'History', 'Sport' ],
title: 'Baseball',
year: 1994
}
]

Las pipelines pueden ejecutarse en una colección externa e incluir múltiples condiciones de unión. El operador $expr permite condiciones de unión más complejas, incluidas las conjunciones y las coincidencias inexactas.

Una condición de unión puede referirse a un campo en la colección local en la que se ejecutó el método aggregate() y referirse a un campo en la colección extranjera. Esto permite una sub-query correlacionada entre ambas colecciones.

MongoDB 5.0 soporta los subquery correlacionados concisos.

El siguiente ejemplo:

  • Une las colecciones movies y comments usando los campos _id y movie_id.

  • Filtra los comentarios para incluir únicamente aquellos publicados después del año de estreno de la película.

db.movies.aggregate( [
{
$match: {
title: {
$in: [ "Class Action", "Kafka", "Corpse Bride" ]
}
}
},
{
$lookup: {
from: "comments",
localField: "_id",
foreignField: "movie_id",
let: { movie_year: "$year" },
pipeline: [
{
$match: {
$expr: {
$gt: [
{ $year: "$date" }, "$$movie_year"
]
}
}
},
{ $project: { _id: 0, name: 1, date: 1 } }
],
as: "post_release_comments"
}
},
{
$project: {
_id: 0,
title: 1,
year: 1,
post_release_comments: 1
}
}
] )
[
{
year: 1991,
title: 'Class Action',
post_release_comments: [
{ name: 'Khal Drogo', date: ISODate('2016-12-06T07:17:03.000Z') }
]
},
{
year: 1991,
title: 'Kafka',
post_release_comments: [
{ name: 'Khal Drogo', date: ISODate('1998-05-10T03:10:20.000Z') }
]
},
{ year: 2005, title: 'Corpse Bride', post_release_comments: [] }
]

La operación corresponde a esta instrucción pseudo-SQL:

SELECT *, post_release_comments
FROM movies
WHERE post_release_comments IN (
SELECT name, date
FROM comments
WHERE movie_id = movies._id
AND YEAR(date) > movies.year
);

The $eq, $lt, $lte, $gt, and $gte comparison operators placed in an $expr operator can use an index on the from collection referenced in a $lookup stage. Limitations:

  • Los índices solo pueden utilizarse para comparaciones entre campos y constantes, por lo que el operando let debe resolverse en una constante.

    Por ejemplo, una comparación entre $a y un valor constante puede utilizar un índice, pero una comparación entre $a y $b no puede.

  • Los índices no se utilizan para comparaciones donde el operando let se resuelve en un valor vacío o faltante.

  • No se utilizan índices multiclave, parciales o dispersos.

Por ejemplo, si el índice { movie_id: 1 } existe en la colección comments:

  • La coincidencia exacta en el campo comments.movie_id utiliza el índice.

An aggregation pipeline $lookup stage can execute a pipeline on the foreign collection, which allows uncorrelated subqueries. An uncorrelated subquery does not reference the local document fields.

Nota

Starting in MongoDB 5.0, for an uncorrelated subquery in a $lookup pipeline stage containing a $sample stage, the $sampleRate operator, or the $rand operator, the subquery is always run again if repeated. Previously, depending on the subquery output size, either the subquery output was cached or the subquery was run again.

La siguiente operación une la colección users con las películas que tienen una duración superior a 1000 minutos, pertenecientes a la colección movies:

db.users.aggregate( [
{
$match: {
email: { $in: [
"mark_addy@gameofthron.es",
"lena_headey@gameofthron.es"
] }
}
},
{
$lookup: {
from: "movies",
pipeline: [
{ $match: { runtime: { $gt: 1000 } } },
{ $project: { _id: 0, title: 1, year: 1 } }
],
as: "long_movies"
}
},
{
$project: {
_id: 0, name: 1, email: 1, long_movies: 1
}
}
] )
[
{
name: 'Robert Baratheon',
email: 'mark_addy@gameofthron.es',
long_movies: [
{ title: 'Centennial', year: 1978 },
{ title: 'Baseball', year: 1994 }
]
},
{
name: 'Cersei Lannister',
email: 'lena_headey@gameofthron.es',
long_movies: [
{ title: 'Centennial', year: 1978 },
{ title: 'Baseball', year: 1994 }
]
}
]

La operación corresponde a esta instrucción pseudo-SQL:

SELECT *, long_movies
FROM users
WHERE long_movies IN (
SELECT title, year
FROM movies
WHERE runtime > 1000
);

Para obtener más información, consulta Consideraciones sobre el rendimiento de subquery no correlacionado.

Nuevo en la versión 5.0.

A partir de MongoDB,5.0 una etapa de canalización de $lookup agregación admite una sintaxis de subconsulta correlacionada concisa que mejora las uniones entre colecciones. La nueva sintaxis concisa elimina el requisito de una coincidencia de igualdad en los campos foráneos y locales dentro de un operador $expr $match en una etapa.

El siguiente ejemplo:

  • Joins the movies and comments collections by matching the localField _id with the foreignField movie_id. The match is performed before the pipeline is run.

  • Filtra los comentarios para incluir solo aquellos publicados después del año de estreno de la película, accediendo respectivamente mediante $$movie_year y $date.

db.movies.aggregate( [
{
$match: {
title: { $in: [
"I Don't Kiss",
"Lucky Luke",
"Mississippi Masala"
] }
}
},
{
$lookup: {
from: "comments",
localField: "_id",
foreignField: "movie_id",
let: { movie_year: "$year" },
pipeline: [
{
$match: {
$expr: {
$gt: [
{ $year: "$date" }, "$$movie_year"
]
}
}
},
{ $project: { _id: 0, name: 1, date: 1 } }
],
as: "post_release_comments"
}
},
{
$project: {
_id: 0,
title: 1,
year: 1,
post_release_comments: 1
}
}
] )
[
{
title: "I Don't Kiss",
year: 1991,
post_release_comments: [
{
name: 'Brandon Hardy',
date: ISODate('2016-09-18T11:11:34.000Z')
}
]
},
{
title: 'Lucky Luke',
year: 1991,
post_release_comments: [
{
name: 'Kelsey Smith',
date: ISODate('2010-01-13T17:55:01.000Z')
}
]
},
{
title: 'Mississippi Masala',
year: 1991,
post_release_comments: [
{
name: 'Phillip Collins',
date: ISODate('2010-05-13T08:04:22.000Z')
}
]
}
]

Este ejemplo utiliza la sintaxis detallada de las versiones de MongoDB anteriores a la 5.0 y arroja los mismos resultados que el ejemplo conciso anterior:

db.movies.aggregate( [
{
$match: {
title: { $in: [
"I Don't Kiss",
"Lucky Luke",
"Mississippi Masala"
] }
}
},
{
$lookup: {
from: "comments",
let: { movie_id: "$_id", movie_year: "$year" },
pipeline: [
{
$match: {
$expr: {
$and: [
{ $eq: [ "$movie_id", "$$movie_id" ] },
{ $gt: [
{ $year: "$date" }, "$$movie_year"
] }
]
}
}
},
{ $project: { _id: 0, name: 1, date: 1 } }
],
as: "post_release_comments"
}
},
{
$project: {
_id: 0,
title: 1,
year: 1,
post_release_comments: 1
}
}
] )
[
{
title: "I Don't Kiss",
year: 1991,
post_release_comments: [
{
name: 'Brandon Hardy',
date: ISODate('2016-09-18T11:11:34.000Z')
}
]
},
{
title: 'Lucky Luke',
year: 1991,
post_release_comments: [
{
name: 'Kelsey Smith',
date: ISODate('2010-01-13T17:55:01.000Z')
}
]
},
{
title: 'Mississippi Masala',
year: 1991,
post_release_comments: [
{
name: 'Phillip Collins',
date: ISODate('2010-05-13T08:04:22.000Z')
}
]
}
]

Los ejemplos anteriores corresponden a esta instrucción pseudo-SQL:

SELECT *, post_release_comments
FROM movies
WHERE post_release_comments IN (
SELECT *
FROM comments
WHERE comments.movie_id = movies._id
AND YEAR(comments.date) > movies.year
);

Para obtener más información, consulta Consideraciones sobre el rendimiento de los subquery correlacionados.

A partir de MongoDB 8.0, namespaces en subpipelines dentro de $lookup y $unionWith se validan para asegurar el uso correcto de los campos from y coll:

  • Para $lookup, omite el campo from si utilizas una subpipeline con una etapa que no requiera una colección especificada. Por ejemplo, una etapa $documents.

  • De manera similar, para $unionWith, omite el campo coll.

Comportamiento sin cambio:

  • Para un $lookup que comienza con una etapa para una colección, por ejemplo, una sub-etapa $match o $collStats, debes incluir el campo from y especificar la colección.

  • De manera similar, para $unionWith, incluye el campo coll y especifica la colección.

El siguiente escenario muestra un ejemplo.

Cree una colección cakeFlavors:

db.cakeFlavors.insertMany( [
{ _id: 1, flavor: "chocolate" },
{ _id: 2, flavor: "strawberry" },
{ _id: 3, flavor: "cherry" }
] )

Los ejemplos de C# en esta página utilizan la base de datos sample_mflix de los conjuntos de datos de muestra de Atlas. Para aprender a crear un clúster gratuito de MongoDB Atlas y cargar los conjuntos de datos de muestra, consulta Primeros pasos en la documentación del controlador de MongoDB .NET/C#.

La siguiente clase Movie modela los documentos en la colección sample_mflix.movies:

[BsonIgnoreExtraElements]
public class Movie
{
[BsonId]
public ObjectId Id { get; set; }
[BsonElement("title")]
public string Title { get; set; } = null!;
[BsonElement("year")]
public int? Year { get; set; }
[BsonElement("runtime")]
public int? Runtime { get; set; }
[BsonElement("rated")]
public string? Rated { get; set; }
[BsonElement("metacritic")]
public int Metacritic { get; set; }
[BsonElement("plot")]
public string? Plot { get; set; }
[BsonElement("type")]
public string? Type { get; set; }
[BsonElement("cast")]
public string[]? Cast { get; set; }
[BsonElement("directors")]
public string[]? Directors { get; set; }
[BsonElement("writers")]
public string[]? Writers { get; set; }
[BsonElement("imdb")]
public ImdbData? Imdb { get; set; }
}

La siguiente clase Comment modela los documentos en la colección sample_mflix.comments:

[BsonIgnoreExtraElements]
public class Comment
{
[BsonId]
public ObjectId Id { get; set; }
[BsonElement("movie_id")]
public ObjectId MovieId { get; set; }
[BsonElement("text")]
public string Text { get; set; } = null!;
}

La siguiente clase LookupResult almacena la salida de la etapa $lookup:

[BsonIgnoreExtraElements]
public class LookupResult
{
[BsonId]
public ObjectId Id { get; set; }
[BsonElement("title")]
public string Title { get; set; } = null!;
public List<Comment> Comments { get; set; } = [];
}

To use the MongoDB .NET/C# driver to add a $lookup stage to an aggregation pipeline, call the UnionWith() method on a PipelineDefinition object.

El siguiente ejemplo crea una etapa de pipeline que realiza una unión externa izquierda entre las colecciones movies y comments. El código une el campo Id de cada documento Movie al campo MovieId en los documentos Comment. Los comentarios de cada película se almacenan en un campo llamado Comments en cada documento LookupResult.

var commentCollection = _client
.GetDatabase("sample_mflix")
.GetCollection<Comment>("comments");
var pipeline = new EmptyPipelineDefinition<Movie>()
.Lookup<Movie, Movie, Comment, LookupResult>(
foreignCollection: commentCollection,
localField: m => m.Id,
foreignField: c => c.MovieId,
@as: r => r.Comments);

Los ejemplos de Node.js en esta página utilizan la base de datos sample_mflix de los conjuntos de datos de muestra de Atlas. Para aprender a crear un clúster gratuito de MongoDB Atlas y cargar los conjuntos de datos de muestra, consulte Primeros pasos en la documentación del controlador de MongoDB Node.js.

Para utilizar el controlador de MongoDB Node.js para agregar una etapa de $lookup a una canalización de agregación, utilice el Operador $lookup en un objeto de canalización.

El siguiente ejemplo crea una etapa de pipeline que realiza una unión externa izquierda entre las colecciones movies y comments. El código une el campo _id de cada documento movie al campo movie_id en los documentos comment. El campo comments almacena los comentarios de cada película en cada documento movie. A continuación, el ejemplo ejecuta la pipeline de agregación:

const pipeline = [
{
$lookup: {
from: "comments",
localField: "_id",
foreignField: "movie_id",
as: "comments"
}
}
];
const cursor = collection.aggregate(pipeline);
return cursor;