Computer >> 컴퓨터 >  >> 프로그래밍 >> MongoDB

MongoDB에서 $addFields 파이프라인과 $filter 연산자를 활용하는 방법

MongoDB에서 $addFields 애그리게이션 단계와 $filter 연산자를 함께 사용하면 배열 필드의 요소들을 조건에 따라 걸러낸 새로운 필드를 만들 수 있습니다. 이 글에서는 실제 예제를 통해 두 기능을 조합하여 사용하는 방법을 단계별로 살펴보겠습니다.

1. 컬렉션 생성 및 문서 삽입하기

먼저 예제로 사용할 컬렉션을 생성하고 문서를 삽입합니다. 아래 명령어는 학생 정보와 과목 목록, 그리고 세부 정보(Details) 배열을 포함한 문서를 저장합니다.

> db.demo118.insertOne(
...    {
...       "Id" : "101",
...       "Name" : "Chris",
...       "Subjects" : [
...          "MySQL",
...          "MongoDB",
...          "Java"
...       ],
...       "Details" : [
...          {
...             "Name" : "David",
...             S:"MongoDB"
...          },
...          {
...             "Name" : "Bob",
...             S:"Python"
...          }
...       ]
...    }
... );
{
   "acknowledged" : true,
   "insertedId" : ObjectId("5e2f0c0cd8f64a552dae6364")
}

2. find() 메서드로 전체 문서 확인하기

find() 메서드를 사용하면 컬렉션에 저장된 모든 문서를 조회할 수 있습니다.

> db.demo118.find();

위 쿼리를 실행하면 다음과 같은 결과가 출력됩니다.

{ "_id" : ObjectId("5e2f0c0cd8f64a552dae6364"), "Id" : "101", "Name" : "Chris", "Subjects" : [ "MySQL", "MongoDB", "Java" ], "Details" : [ { "Name" : "David", "S" : "MongoDB" }, { "Name" : "Bob", "S" : "Python" } ] }

3. $addFields와 $filter를 활용한 쿼리 작성하기

이제 핵심인 $addFields 파이프라인 쿼리를 살펴보겠습니다. 이 쿼리는 Details 배열에서 각 요소의 S 값이 Subjects 배열에 포함되어 있는지 확인하고, 조건을 만족하는 요소만 남겨서 Details 필드를 새롭게 정의합니다.

  • $addFields: 기존 필드를 덮어쓰거나 새로운 필드를 추가하는 애그리게이션 단계입니다.
  • $filter: input으로 지정한 배열을 순회하면서 cond 조건을 통과하는 요소만 반환합니다.
  • $in: 특정 값($$out.S)이 대상 배열($Subjects) 안에 존재하는지 검사합니다.
> db.demo118.aggregate([
...    {
...       "$addFields": {
...          "Details": {
...             "$filter": {
...                "input": "$Details",
...                "as": "out",
...                "cond": { "$in": ["$$out.S", "$Subjects"] }
...             }
...          }
...       }
...    }
... ]).pretty();

4. 실행 결과 확인하기

쿼리를 실행하면 다음과 같은 결과가 출력됩니다.

{
   "_id" : ObjectId("5e2f0c0cd8f64a552dae6364"),
   "Id" : "101",
   "Name" : "Chris",
   "Subjects" : [
      "MySQL",
      "MongoDB",
      "Java"
   ],
   "Details" : [
      {
         "Name" : "David",
         "S" : "MongoDB"
      }
   ]
}

결과 분석

원본 데이터의 Details 배열에는 David(MongoDB)와 Bob(Python) 두 개의 요소가 있었습니다. 그러나 Subjects 배열에는 MySQL, MongoDB, Java만 포함되어 있고 Python은 없기 때문에, $in 조건을 통과하지 못한 Bob의 정보는 결과에서 제외되었습니다. 이처럼 $addFields와 $filter를 조합하면 원본 문서를 수정하지 않고도 읽기 작업 시점에 배열 데이터를 유연하게 가공할 수 있습니다.