AI 에이전트의 경우: 문서 인덱스는 https://www.mongodb.com/ko-kr/docs/llms.txt에서 사용할 수 있으며, 모든 페이지의 마크다운 버전은 어떤 URL 경로에 .md를 추가하여 사용할 수 있습니다.
Docs Menu

$lookup (집계 단계)

$lookup

버전 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.

MongoDB 부터는 샤딩된 5.1 컬렉션과 함께 를 $lookup 사용할 수 있습니다.

서로 다른 두 컬렉션의 요소를 결합하려면 $unionWith 파이프라인 단계를 사용합니다.

중요

$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.

다음 환경에서 호스팅되는 배포에 $lookup 사용할 수 있습니다.

  • MongoDB Atlas: 클라우드에서의 MongoDB 배포를 위한 완전 관리형 서비스

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:

필드
필요성
설명

필수 사항

동일한 데이터베이스에서 로컬 컬렉션에 조인할 외부 컬렉션을 지정합니다.

일부 경우에는 첫 번째 단계로 $documents 를 사용하여 frompipeline 로 대체하는 것이 가능합니다. 예시는 $lookup 단계에서 $documents 단계 사용하기를 참조하세요.

MongoDB 5.1부터 from 컬렉션을 샤딩할 수 있습니다.

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.

pipeline이 지정된 경우, 선택 사항

로컬 문서의 localField와 동등성 매치를 수행하도록 외부 문서의 foreignField를 지정합니다.

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

옵션

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.

  • $match 단계에서는 $expr 연산자를 사용하여 변수에 액세스해야 합니다. $expr 연산자를 사용하면 $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:

    • 인덱스는 필드와 상수 간의 비교에만 사용할 수 있으므로 let 피연산자는 상수로 해결되어야 합니다.

      예를 들어 $a 및 상수 값 간의 비교에는 인덱스를 사용할 수 있지만, $a$b 간의 비교에는 인덱스를 사용할 수 없습니다.

    • let 피연산자가 비어 있거나 누락된 값으로 확인되는 비교에는 인덱스가 사용되지 않습니다.

    • 멀티키, 부분 또는 희소 인덱스는 사용되지 않습니다.

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

localFieldforeignField가 지정된 경우, 선택 사항

외부 컬렉션에서 실행할 pipeline을 지정합니다. pipeline은 외부 컬렉션에서 문서를 반환합니다. 모든 문서를 반환하려면 빈 pipeline: []을 지정합니다.

pipeline 에는$out또는$merge단계를 포함할 수 없습니다. v6.0부터 pipeline는 Atlas Search$search단계를 파이프라인 내부의 첫 번째 단계로 포함할 수 있습니다. 자세히 학습 Atlas 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.

  • $match 단계에서는 $expr 연산자를 사용하여 변수에 액세스해야 합니다. $expr 연산자를 사용하면 $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:

    • 인덱스는 필드와 상수 간의 비교에만 사용할 수 있으므로 let 피연산자는 상수로 해결되어야 합니다.

      예를 들어 $a 및 상수 값 간의 비교에는 인덱스를 사용할 수 있지만, $a$b 간의 비교에는 인덱스를 사용할 수 없습니다.

    • let 피연산자가 비어 있거나 누락된 값으로 확인되는 비교에는 인덱스가 사용되지 않습니다.

    • 멀티키, 부분 또는 희소 인덱스는 사용되지 않습니다.

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

필수 사항

입력 문서에 추가할 새 배열 필드의 이름을 지정합니다. 새 배열 필드에는 from 컬렉션에서 매칭되는 문서가 포함됩니다. 지정된 이름이 입력 문서에 이미 존재하는 경우 기존 필드를 덮어씁니다.

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>
}
}

참고

이 예시 에서 pipeline 은 선택 사항이며 로컬 및 외부 동일성 단계 이후에 실행됩니다.

이 작업은 다음과 같은 유사 SQL 문장에 해당합니다.

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

참고

이 페이지의 SQL 문은 MongoDB 집계 파이프라인 구문과 비교할 수 있도록 포함되어 있습니다. SQL 문을 실행할 수 없습니다.

MongoDB 예시는 이 페이지를 참조하세요.

MongoDB는 다음을 지원합니다.

  • 외부 컬렉션에서 파이프라인 실행하기.

  • 여러 조인 조건.

  • 상관관계가 있는 하위 쿼리와 상관관계가 없는 하위 쿼리.

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.

참고

MongoDB 5.0부터$sample단계, $sampleRate연산자 또는$rand연산자 포함하는$lookup파이프라인 단계에서 상관관계가 없는 하위 쿼리의 경우, 하위 쿼리가 반복되면 항상 다시 실행 됩니다. 이전에는 하위 쿼리 출력 크기에 따라 하위 쿼리 출력이 캐시되거나 하위 쿼리가 다시 실행 되었습니다.

MongoDB 상관 서브쿼리는 내부 쿼리가 외부 쿼리 값을 참조하는 SQL 상관 서브쿼리와 유사합니다. SQL 비연관 서브쿼리는 외부 쿼리 값을 참조하지 않습니다.

MongoDB 5.0은 상관관계가 있는 간결한 하위 쿼리도 지원합니다.

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>
}
}

이 작업은 다음과 같은 유사 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>
);

다음 예시를 참조하세요.

버전 5.0의 신규 항목입니다.

MongoDB 5.0부터는 상관 하위 쿼리에 간결한 구문을 사용할 수 있습니다. 상관 하위 쿼리는 외부 컬렉션 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>
}
}

이 작업은 다음과 같은 유사 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>
);

이 예시를 참조하세요.

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>
}
}

MongoDB 6.0 부터는 파이프라인 에서 Atlas Search $search 또는 $searchMeta 단계를 지정하여 $lookup Atlas cluster 에서 컬렉션을 검색 할 $search 수 있습니다.$searchMeta 또는 단계는 $lookup 파이프라인 내의 첫 번째 단계여야 합니다.

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 Atlas Search tutorial Run an Atlas Search $search Query Using $lookup.

MongoDB 5.1 부터는 from 단계의 $lookup 매개 변수에서 샤딩된 컬렉션을 지정할 수 있습니다.

MongoDB 8.0부터 샤딩된 컬렉션을 대상으로 하는 트랜잭션 내에서 $lookup 단계를 사용할 수 있습니다.

버전 부터 파이프라인 6.0 의 모든 이전 단계가 슬롯 기반 실행 엔진에서도 실행될 수 있고 다음 조건 중 어느 하나에도 해당하지 않는 $lookup 경우, MongoDB 슬롯 기반 실행 쿼리 엔진 엔진 하여 단계를 실행할 수 있습니다.

  • $lookup 작업은 외부 컬렉션에서 파이프라인을 실행합니다. 이러한 종류의 작업 예시를 보려면 외부 컬렉션의 조인 조건 및 하위 쿼리를 참조하세요.

  • $lookuplocalField 또는 foreignField는 숫자 구성 요소를 지정합니다. 예시: { localField: "restaurant.0.review" }

  • 파이프라인에서 $lookupfrom 필드는 뷰 또는 샤드 컬렉션을 지정합니다.

자세한 내용은 $lookup 최적화를 참조하세요.

$lookup 성능은 수행되는 작업 유형에 따라 달라집니다. 다양한 $lookup 작업에 대한 성능 고려 사항은 다음 표를 참조하세요.

$lookup 작업
성능 고려 사항
  • $lookup 연산은 단일 조인으로 동등성 매치를 수행하고, 외부 컬렉션에 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 연산은 관련 없는 하위 쿼리를 포함하며, 내부 파이프라인이 외부 컬렉션의 인덱스를 참조할 수 있을 때 성능이 더 우수합니다.

  • MongoDB는 소스 컬렉션과 외부 컬렉션 사이에 관계가 없기 때문에 쿼리를 캐싱하기 전에 $lookup 하위 쿼리를 한 번만 실행하면 됩니다. 하위 쿼리는 소스 컬렉션의 값을 기반으로 하지 않습니다. 이 동작은 $lookup 작업의 후속 실행에 대한 성능을 향상시킵니다.

  • $lookup operations that contain correlated subqueries perform better when the foreign collection contains an index on the foreignField.

  • 파이프라인이 많은 수의 문서를 $lookup 쿼리에 전달하는 경우 다음 전략을 사용하면 성능이 향상될 수 있습니다.

    • MongoDB가 $lookup 쿼리에 전달하는 문서 수를 줄입니다. 예를 들어 $match 단계에서 더 엄격한 필터를 설정합니다.

    • 데이터의 스키마를 재검토하여 사용 사례에 적합한지 확인합니다.

일반적인 성능 전략은 인덱싱 전략쿼리 최적화를 참조하세요.

이 페이지의 예시에서는 sample_mflix 샘플 데이터 세트의 데이터를 사용합니다. 이 데이터 세트를 자체 관리형 MongoDB 배포서버에 로드하는 방법에 대한 자세한 내용은 샘플 데이터 세트 로드를 참조하세요. 샘플 데이터베이스를 수정한 경우 이 페이지의 예시를 실행 하려면 데이터베이스를 제거하고 다시 만들어야 할 수 있습니다.

다음 집계 작업은 먼저 movies 컬렉션 1000보다 큰 runtime 를 가진 영화로 필터링한 다음 _idmovie_id 필드에서 comments 컬렉션 과 조인합니다.

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: [] }
]

이 작업은 다음과 같은 유사 SQL 문장에 해당합니다.

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

자세한 내용은 동등성 매치 성능 고려 사항을 참조하세요.

localField가 배열인 경우 $unwind 단계 없이 스칼라 foreignField에 일치시킬 수 있습니다.

다음 집계 작업은 movies 컬렉션 users 컬렉션 과 조인하여 moviescast 배열 필드 users의 스칼라 name 필드 와 일치시킵니다.

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'
}
]
}
]

$mergeObjects 연산자는 여러 문서를 단일 문서로 결합합니다.

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
}
]

파이프라인은 외부 컬렉션에서 실행할 수 있으며 여러 조인 조건을 포함할 수 있습니다. $expr 연산자를 사용하면 접속사 및 비동등성 매치를 포함한 더 복잡한 조인 조건이 가능합니다.

조인 조건은 aggregate() 메서드가 실행된 로컬 컬렉션의 필드를 참조하고 외부 컬렉션의 필드를 참조할 수 있습니다. 이렇게 하면 두 컬렉션 간에 상관 하위 쿼리가 가능합니다.

MongoDB 5.0은 상관관계가 있는 간결한 하위 쿼리를 지원합니다.

다음 예제입니다.

  • _idmovie_id 필드를 사용하여 moviescomments 컬렉션을 조인합니다.

  • 영화 출시하다 연도 이후에 게시된 댓글만 포함하도록 댓글을 필터링합니다.

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: [] }
]

이 작업은 다음과 같은 유사 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:

  • 인덱스는 필드와 상수 간의 비교에만 사용할 수 있으므로 let 피연산자는 상수로 해결되어야 합니다.

    예를 들어 $a 및 상수 값 간의 비교에는 인덱스를 사용할 수 있지만, $a$b 간의 비교에는 인덱스를 사용할 수 없습니다.

  • let 피연산자가 비어 있거나 누락된 값으로 확인되는 비교에는 인덱스가 사용되지 않습니다.

  • 멀티키, 부분 또는 희소 인덱스는 사용되지 않습니다.

예를 들어 comments 컬렉션에 인덱스 { movie_id: 1 }가 존재하는 경우입니다.

  • comments.movie_id 필드의 동등성 매치는 인덱스를 사용합니다.

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.

참고

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.

다음 작업은 movies 컬렉션 에서 런타임이 1000 분보다 긴 영화와 users 컬렉션 조인합니다.

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 }
]
}
]

이 작업은 다음과 같은 유사 SQL 문장에 해당합니다.

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

자세한 내용은 상관관계가 없는 하위 쿼리 성능 고려 사항을참조하세요.

버전 5.0의 신규 항목입니다.

MongoDB 부터 5.0 집계 파이프라인 단계는 컬렉션 $lookup 간의 조인을 개선하는 간결한 상관관계 하위 쿼리 구문을 지원합니다. 새로운 간결한 구문은 단계에서 연산자 내부의 외래 및 로컬 $expr $match 필드에 대한 동등성 매치 요구 사항을 제거합니다.

다음 예제입니다.

  • 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.

  • 댓글을 필터링하여 영화 출시하다 연도 이후에 게시된 댓글만 포함하며, 각각 $$movie_year$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')
}
]
}
]

이 예에서는 5.0 이전 버전의 구형 MongoDB 구문을 사용하며 버전에서 앞의 간결한 예와 동일한 결과를 반환합니다.

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')
}
]
}
]

이전 예시는 다음 유사 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
);

자세한 내용은 상관관계가 있는 하위 쿼리 성능 고려 사항을 참조하세요.

MongoDB 8.0부터 $lookup$unionWith 내의 서브파이프라인의 네임스페이스가 fromcoll 필드의 올바른 사용을 보장하기 위해 검증됩니다.

  • $lookup의 경우 지정된 컬렉션이 필요하지 않은 단계를 사용하는 서브파이프라인을 사용할 때는 from 필드를 생략합니다. 예를 들어 $documents 단계입니다.

  • 마찬가지로, $unionWith의 경우 coll 필드를 생략합니다.

변경되지 않은 동작:

  • 예를 들어 $match 또는 $collStats서브파이프라인과 같이 컬렉션을 위한 단계로 시작하는 $lookup의 경우 from 필드를 포함하고 컬렉션을 지정해야 합니다.

  • 마찬가지로 $unionWith의 경우 coll 필드를 포함하고 컬렉션을 지정합니다.

다음 시나리오는 한 가지 예시를 보여줍니다.

컬렉션 cakeFlavors을 만듭니다:

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

이 페이지의 C# 예제에서는 Atlas 샘플 데이터 세트sample_mflix 데이터베이스 사용합니다. 무료 MongoDB Atlas cluster 생성하고 샘플 데이터 세트를 로드하는 방법을 학습하려면 MongoDB .NET/ C# 드라이버 문서에서 시작하기 를 참조하세요.

다음 Movie 클래스는 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; }
}

다음 Comment 클래스는 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!;
}

다음 LookupResult 클래스에는 $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.

다음 예시 movies 컬렉션과 comments 컬렉션 간의 왼쪽 외부 조인을 수행하는 파이프라인 단계를 만듭니다. 이 코드는 각 Movie 문서 의 Id 필드 Comment 문서의 MovieId 필드 에 조인합니다. 각 영화에 대한 댓글은 각 LookupResult 문서 의 Comments 필드 에 저장됩니다.

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);

이 페이지의 Node.js 예제에서는 Atlas 샘플 데이터 세트sample_mflix 데이터베이스 사용합니다. 무료 MongoDB Atlas cluster 생성하고 샘플 데이터 세트를 로드하는 방법을 학습하려면 MongoDB Node.js 운전자 설명서에서 시작하기 를 참조하세요.

MongoDB Node.js 운전자 사용하여 집계 파이프라인 에 $lookup 단계를 추가하려면 파이프라인 객체 에서 $lookup 연산자 사용합니다.

다음 예시에서는 movies 컬렉션과 comments 컬렉션 간의 왼쪽 외부 조인을 수행하는 파이프라인 단계를 만듭니다. 코드는 각 movie 문서의 _id 필드를 comment 문서의 movie_id 필드와 조인합니다. comments 필드는 각 movie 문서에 개별 영화의 댓글을 저장합니다. 그리고 집계 파이프라인을 실행합니다.

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