MongoDB 데이터 변환하기

MongoDBBeginner
지금 연습하기

소개

이 랩에서는 MongoDB 의 강력한 집계 파이프라인 (aggregation pipeline) 을 사용하여 데이터를 변환하는 방법을 배우게 됩니다. 집계 파이프라인을 사용하면 일련의 단계를 거쳐 데이터를 처리하여 복잡한 변환, 분석 및 보고를 수행할 수 있습니다. 샘플 데이터셋을 설정하는 것으로 시작하여 필드 선택 및 이름 변경, 기존 데이터에서 새 필드 계산, 출력 형식 지정, 특정 기준에 따른 문서 필터링을 포함한 몇 가지 주요 변환 기법을 진행합니다. 이 랩이 끝나면 MongoDB 내에서 데이터를 조작하는 탄탄한 기반을 갖추게 될 것입니다.

설정 및 기본 필드 선택

첫 번째 단계에서는 MongoDB 서버에 연결하고, 데이터베이스와 컬렉션을 생성한 후 샘플 데이터를 삽입합니다. 그런 다음 문서에서 특정 필드를 선택하고 이름을 변경하여 첫 번째 데이터 변환을 수행합니다.

먼저 터미널을 열고 MongoDB Shell (mongosh) 을 실행합니다. 이 대화형 쉘은 MongoDB 인스턴스와 상호 작용하는 주요 방법입니다. 랩의 나머지 부분에서는 이 쉘 내에서 모든 데이터베이스 작업을 수행합니다.

mongosh

MongoDB Shell 에 접속하면 프롬프트가 변경됩니다. 이제 bookstore라는 새 데이터베이스를 생성하고 해당 데이터베이스로 전환합니다. 데이터베이스가 존재하지 않으면 이 명령이 생성합니다.

use bookstore

다음으로 books라는 컬렉션을 생성하고 insertMany 명령을 사용하여 세 개의 샘플 문서를 삽입합니다. 컬렉션은 SQL 데이터베이스의 테이블과 유사하게 문서들의 그룹입니다.

db.books.insertMany([
  {
    title: "MongoDB Basics",
    author: "Jane Smith",
    price: 29.99,
    pages: 250,
    categories: ["Database", "Programming"]
  },
  {
    title: "Python Deep Dive",
    author: "John Doe",
    price: 39.99,
    pages: 450,
    categories: ["Programming", "Python"]
  },
  {
    title: "Data Science Handbook",
    author: "Alice Johnson",
    price: 49.99,
    pages: 600,
    categories: ["Data Science", "Programming"]
  }
]);

이제 데이터가 준비되었으므로 집계 파이프라인을 사용하여 데이터를 변환해 보겠습니다. aggregate 메서드는 스테이지 (stage) 의 배열을 받으며, 각 스테이지는 데이터에 대한 작업을 수행합니다. 첫 번째 스테이지는 문서를 재구성하는 $project입니다.

titleauthor 필드만 선택하고 각각 bookTitlebookAuthor로 이름을 변경하려면 다음 명령을 실행합니다.

db.books.aggregate([
  {
    $project: {
      _id: 0,
      bookTitle: "$title",
      bookAuthor: "$author"
    }
  }
]);

다음과 같은 출력을 볼 수 있습니다.

[
  { "bookTitle": "MongoDB Basics", "bookAuthor": "Jane Smith" },
  { "bookTitle": "Python Deep Dive", "bookAuthor": "John Doe" },
  { "bookTitle": "Data Science Handbook", "bookAuthor": "Alice Johnson" }
]

$project 스테이지를 자세히 살펴보겠습니다.

  • _id: 0은 기본 _id 필드를 출력에서 제외합니다. 기본적으로 항상 포함됩니다.
  • bookTitle: "$title"bookTitle이라는 새 필드를 생성하고 원래 title 필드의 값을 할당합니다. $ 접두사는 필드의 값을 참조하고 있음을 나타냅니다.
  • bookAuthor: "$author"는 유사하게 author 필드를 bookAuthor로 이름을 변경합니다.

새 필드 계산

이전 단계에서는 기존 필드를 선택하고 이름을 변경했습니다. 이제 기존 데이터에 대한 계산을 수행하여 완전히 새로운 필드를 만드는 방법을 배우게 됩니다. 이를 위해 $addFields 스테이지를 사용하며, 이 스테이지는 원본 필드를 제거하지 않고 문서에 새 필드를 추가합니다.

책 가격에 10% 세금을 포함한 priceWithTax라는 새 필드를 추가해 보겠습니다.

db.books.aggregate([
  {
    $addFields: {
      priceWithTax: { $multiply: ["$price", 1.1] }
    }
  }
]);

출력에는 각 문서에 대해 모든 원본 필드와 새로운 priceWithTax 필드가 포함됩니다.

[
  {
    _id: ObjectId("..."),
    title: 'MongoDB Basics',
    author: 'Jane Smith',
    price: 29.99,
    pages: 250,
    categories: [ 'Database', 'Programming' ],
    priceWithTax: 32.989
  },
  {
    _id: ObjectId("..."),
    title: 'Python Deep Dive',
    author: 'John Doe',
    price: 39.99,
    pages: 450,
    categories: [ 'Programming', 'Python' ],
    priceWithTax: 43.989
  },
  {
    _id: ObjectId("..."),
    title: 'Data Science Handbook',
    author: 'Alice Johnson',
    price: 49.99,
    pages: 600,
    categories: [ 'Data Science', 'Programming' ],
    priceWithTax: 54.989
  }
]

이 파이프라인에서:

  • $addFields는 새 필드를 추가하는 데 사용되는 스테이지입니다.
  • priceWithTax는 생성하려는 새 필드의 이름입니다.
  • $multiply는 두 개의 숫자로 이루어진 배열을 받아 곱하는 집계 연산자입니다. 여기서는 price 필드의 값을 1.1로 곱합니다.

출력 데이터 형식 지정

데이터는 적절하게 형식화될 때 더 유용합니다. 이 단계에서는 $project 스테이지 내의 다양한 집계 연산자를 사용하여 문자열 및 숫자 데이터 형식을 지정하는 방법을 배우게 됩니다. 이는 애플리케이션이나 보고서에 데이터를 표시하기 위해 준비하는 데 유용합니다.

책 제목을 대문자로 변환하고 가격을 통화 문자열로 형식화하여 더 읽기 쉬운 출력을 만들어 보겠습니다.

db.books.aggregate([
  {
    $project: {
      _id: 0,
      titleUpperCase: { $toUpper: "$title" },
      formattedPrice: {
        $concat: [{ $literal: "$" }, { $toString: "$price" }]
      }
    }
  }
]);

예상 출력은 변환된 데이터를 보여줍니다.

[
  {
    "titleUpperCase": "MONGODB BASICS",
    "formattedPrice": "$29.99"
  },
  {
    "titleUpperCase": "PYTHON DEEP DIVE",
    "formattedPrice": "$39.99"
  },
  {
    "titleUpperCase": "DATA SCIENCE HANDBOOK",
    "formattedPrice": "$49.99"
  }
]

$project 스테이지에서 사용된 연산자를 살펴보겠습니다.

  • $toUpper: 이 연산자는 문자열을 대문자로 변환합니다. title 필드에 적용했습니다.
  • $concat: 이 연산자는 문자열 배열을 연결합니다. 가격 앞에 달러 기호 $ 접두사를 추가하는 데 사용했습니다.
  • $literal: 이 연산자는 그렇지 않으면 표현식으로 해석될 수 있는 리터럴 값을 나타내는 데 사용됩니다. 여기서는 리터럴 달러 기호 문자를 나타내기 위해 { $literal: "$" }를 사용합니다.
  • $toString: $concat은 문자열만 작동하므로 먼저 $toString 연산자를 사용하여 숫자 price 필드를 문자열로 변환해야 했습니다.

$match 를 사용한 결과 필터링

마지막으로 배울 기본적인 기술은 필터링입니다. $match 스테이지는 SQL 의 WHERE 절과 유사하게 특정 기준을 충족하는 문서만 선택할 수 있게 해줍니다. 이는 집계 파이프라인에서 가장 흔하게 사용되는 스테이지 중 하나입니다.

가격이 35 달러를 초과하는 모든 책을 찾아보겠습니다.

db.books.aggregate([
  {
    $match: {
      price: { $gt: 35 }
    }
  }
]);

출력에는 필터와 일치하는 두 권의 책만 포함됩니다.

[
  {
    _id: ObjectId("..."),
    title: 'Python Deep Dive',
    author: 'John Doe',
    price: 39.99,
    pages: 450,
    categories: [ 'Programming', 'Python' ]
  },
  {
    _id: ObjectId("..."),
    title: 'Data Science Handbook',
    author: 'Alice Johnson',
    price: 49.99,
    pages: 600,
    categories: [ 'Data Science', 'Programming' ]
  }
]

$match 스테이지는 표준 MongoDB 쿼리 구문을 사용합니다.

  • price: { $gt: 35 }는 필터 조건을 지정합니다. price 필드가 35 보다 큰 ($gt) 문서를 선택합니다.

스테이지를 연결하여 더 복잡한 파이프라인을 만들 수도 있습니다. 예를 들어, 먼저 문서를 필터링한 다음 해당 결과에서 사용자 지정 출력을 투영할 수 있습니다.

db.books.aggregate([
  {
    $match: {
      price: { $gt: 35 }
    }
  },
  {
    $project: {
      _id: 0,
      title: 1,
      price: 1
    }
  }
]);

이 파이프라인은 먼저 $match를 사용하여 비싼 책을 필터링한 다음, 해당 결과에 대해 $project를 사용하여 titleprice만 표시합니다. $projecttitle: 1 구문은 필드를 포함하는 간결한 방법입니다.

최종 출력은 필터링되고 투영된 결과입니다.

[
  { "title": "Python Deep Dive", "price": 39.99 },
  { "title": "Data Science Handbook", "price": 49.99 }
]

MongoDB 셸을 종료하려면 exit를 입력하거나 Ctrl+D를 누르면 됩니다.

요약

이 실습에서는 MongoDB 집계 파이프라인의 기본 연산을 배웠습니다. 데이터를 삽입하는 것으로 시작하여 일련의 스테이지를 사용하여 데이터를 변환했습니다. $project를 사용하여 필드를 선택하고 이름을 바꾸고, $addFields를 사용하여 새 계산 필드를 만들고, $toUpper$concat과 같은 형식 지정 연산자를 사용하여 데이터 모양을 변경하고, $match를 사용하여 문서를 필터링하는 연습을 했습니다. 이러한 스테이지를 결합하면 데이터베이스 내에서 직접 데이터를 분석하고 재구성하는 정교한 데이터 처리 파이프라인을 구축할 수 있으며, 이는 데이터 조작에 강력하고 효율적인 접근 방식입니다.