Cloud Firestore 데이터 모델

Cloud Firestore는 NoSQL 문서 중심의 데이터베이스입니다. SQL 데이터베이스와 달리 테이블이나 행이 없으며, 컬렉션으로 정리되는 문서에 데이터를 저장합니다.

문서에는 키-값 쌍이 들어 있습니다. Cloud Firestore는 작은 문서가 많이 모인 컬렉션을 저장하는 데 최적화되어 있습니다.

모든 문서는 컬렉션에 저장되어야 합니다. 문서는 하위 컬렉션 및 중첩 개체를 포함할 수 있으며, 둘 다 문자열 같은 기본형 필드나 목록 같은 복합 개체를 포함할 수 있습니다.

컬렉션과 문서는 Cloud Firestore에서 암시적으로 생성됩니다. 사용자는 컬렉션 내의 문서에 데이터를 할당하기만 하면 됩니다. 컬렉션 또는 문서가 없으면 Cloud Firestore에서 자동으로 생성합니다.

문서

Cloud Firestore의 저장소 단위는 문서입니다. 문서는 값에 매핑되는 필드를 포함하는 간단한 레코드입니다. 각 문서는 이름으로 식별됩니다.

사용자 alovelace를 나타내는 문서는 다음과 같습니다.

  • class alovelace

    first : "Ada"
    last : "Lovelace"
    born : 1815

문서의 복잡한 중첩 개체를 맵이라고 합니다. 예를 들어 위의 예에서 사용자 이름을 다음과 같이 맵으로 구조화할 수 있습니다.

  • class alovelace

    name :
        first : "Ada"
        last : "Lovelace"
    born : 1815

문서가 JSON과 매우 비슷해졌는데, 사실은 기본적으로 JSON이 사용됩니다. 문서는 추가적인 데이터 유형을 지원하고 크기가 1MB로 제한되는 등의 몇 가지 차이점이 있기는 하지만, 일반적으로는 문서를 간단한 JSON 레코드로 취급해도 무방합니다.

컬렉션

문서는 컬렉션에 저장되며, 컬렉션은 단순히 문서의 컨테이너입니다. 예를 들어 users 컬렉션을 사용하여 각각 문서로 표현되는 여러 사용자를 포함할 수 있습니다.

  • collections_bookmark users

    • class alovelace

      first : "Ada"
      last : "Lovelace"
      born : 1815

    • class aturing

      first : "Alan"
      last : "Turing"
      born : 1912

Cloud Firestore는 스키마를 사용하지 않으므로 각 문서에 어떤 필드를 넣을 지와 각 필드에 어떤 유형의 데이터를 저장할 지는 완전히 사용자의 재량입니다. 같은 컬렉션에 포함된 여러 문서가 서로 다른 필드를 포함할 수 있고, 이러한 필드에 서로 다른 유형의 데이터를 저장할 수도 있습니다. 그러나 문서를 보다 쉽게 쿼리할 수 있도록 여러 문서에서 동일한 필드와 데이터 유형을 사용하는 것이 좋습니다.

컬렉션은 오로지 문서만 포함합니다. 값이 있는 원시 필드를 포함하거나 다른 컬렉션을 포함할 수는 없습니다. Cloud Firestore에서 보다 복잡한 데이터를 구조화하는 방법은 계층적 데이터를 참조하세요.

컬렉션 내의 문서 이름은 고유합니다. 사용자 ID와 같은 키를 직접 제공할 수도 있고, add() 등을 호출하여 Cloud Firestore에서 무작위 ID를 자동으로 만들도록 할 수도 있습니다.

컬렉션을 직접 '생성' 또는 '삭제'할 필요는 없습니다. 컬렉션에 첫 번째 문서를 만들면 컬렉션이 생성됩니다. 컬렉션의 모든 문서를 삭제하면 컬렉션도 삭제됩니다.

참조

Cloud Firestore의 모든 문서는 데이터베이스 내에서 위치에 따라 고유하게 식별됩니다. 앞의 예에 나왔던 alovelace 문서는 users 컬렉션에 속했습니다. 코드에서 이 위치를 참조하려면 위치를 가리키는 참조를 만듭니다.

var alovelaceDocumentRef = db.collection('users').doc('alovelace');
Swift
let alovelaceDocumentRef = db.collection("users").document("alovelace")
Objective-C
FIRDocumentReference *alovelaceDocumentRef =
    [[self.db collectionWithPath:@"users"] documentWithPath:@"alovelace"];
Android
DocumentReference alovelaceDocumentRef = db.collection("users").document("alovelace");
자바
// Reference to a document with id "alovelace" in the collection "users"
DocumentReference document = db.collection("users").document("alovelace");
Python
a_lovelace_ref = db.collection(u'users').document(u'alovelace')
Node.js
var alovelaceDocumentRef = db.collection('users').doc('alovelace');
Go
alovelaceRef := client.Collection("users").Doc("alovelace")
PHP
$document = $db->collection('users')->document('lovelace');

참조는 데이터베이스의 특정 위치를 가리키는 간단한 객체입니다. 해당 위치에 데이터가 있는지 여부에 관계없이 참조를 만들 수 있으며, 참조를 만들어도 네트워크 작업이 수행되지 않습니다.

컬렉션을 가리키는 참조를 만들 수도 있습니다.

var usersCollectionRef = db.collection('users');
Swift
let usersCollectionRef = db.collection("users")
Objective-C
FIRCollectionReference *usersCollectionRef = [self.db collectionWithPath:@"users"];
Android
CollectionReference usersCollectionRef = db.collection("users");
자바
// Reference to the collection "users"
CollectionReference collection = db.collection("users");
Python
users_ref = db.collection(u'users')
Node.js
var usersCollectionRef = db.collection('users');
Go
usersRef := client.Collection("users")
PHP
$collection = $db->collection('users');

편의상 경로 구성요소를 슬래시(/)로 구분한 문자열로 문서 또는 컬렉션의 경로를 지정해 참조를 만들 수도 있습니다. 예를 들어 alovelace 문서의 참조를 만드는 방법은 다음과 같습니다.

var alovelaceDocumentRef = db.doc('users/alovelace');
Swift
let aLovelaceDocumentReference = db.document("users/alovelace")
Objective-C
FIRDocumentReference *aLovelaceDocumentReference =
    [self.db documentWithPath:@"users/alovelace"];
Android
DocumentReference alovelaceDocumentRef = db.document("users/alovelace");
자바
// Reference to a document with id "alovelace" in the collection "users"
DocumentReference document = db.document("users/alovelace");
Python
a_lovelace_ref = db.document(u'users/alovelace')
Node.js
var alovelaceDocumentRef = db.doc('users/alovelace');
Go
alovelaceRef := client.Doc("users/alovelace")
PHP
$document = $db->document('users/lovelace');

계층적 데이터

Cloud Firestore의 계층적 데이터 구조를 이해하기 위해, 메시지와 채팅방을 갖춘 예제 채팅 앱을 가정해 보겠습니다.

다음과 같이 여러 채팅방을 저장하는 rooms라는 컬렉션을 만들 수 있습니다.

  • collections_bookmark rooms

    • class roomA

      name : "my chat room"

    • class roomB

      ...

이제 채팅방이 생겼으므로 메시지를 저장할 방법을 결정해야 합니다. 채팅방 문서에는 저장하지 않는 것이 좋습니다. Cloud Firestore의 문서는 가벼워야 하는데, 채팅방에 매우 많은 메시지가 포함될 수 있기 때문입니다. 그러나 채팅방 문서 안에 하위 컬렉션을 추가로 만들 수는 있습니다.

하위 컬렉션

이 시나리오에서 메시지를 저장하는 가장 좋은 방법은 하위 컬렉션을 사용하는 것입니다. 하위 컬렉션은 특정 문서와 관련된 컬렉션입니다.

rooms 컬렉션의 모든 채팅방 문서에 messages라는 하위 컬렉션을 만들 수 있습니다.

  • collections_bookmark rooms

    • class roomA

      name : "my chat room"

      • collections_bookmark messages

        • class message1

          from : "alex"
          msg : "Hello World!"

        • class message2

          ...

    • class roomB

      ...

이 예에서는 다음 코드를 사용하여 하위 컬렉션의 메시지에 대한 참조를 만들 수 있습니다.

var messageRef = db.collection('rooms').doc('roomA')
                .collection('messages').doc('message1');
Swift
let messageRef = db
    .collection("rooms").document("roomA")
    .collection("messages").document("message1")
Objective-C
FIRDocumentReference *messageRef =
    [[[[self.db collectionWithPath:@"rooms"] documentWithPath:@"roomA"]
    collectionWithPath:@"messages"] documentWithPath:@"message1"];
Android
DocumentReference messageRef = db
        .collection("rooms").document("roomA")
        .collection("messages").document("message1");
자바
// Reference to a document in subcollection "messages"
DocumentReference document =
    db.collection("rooms").document("roomA").collection("messages").document("message1");
Python
room_a_ref = db.collection(u'rooms').document(u'roomA')
message_ref = room_a_ref.collection(u'messages').document(u'message1')
Node.js
var messageRef = db.collection('rooms').doc('roomA')
    .collection('messages').doc('message1');
Go
messageRef := client.Collection("rooms").Doc("roomA").
	Collection("messages").Doc("message1")
PHP
$document = $db
    ->collection('rooms')
    ->document('roomA')
    ->collection('messages')
    ->document('message1');

컬렉션과 문서가 교대로 나타나는 패턴에 주목하세요. 컬렉션과 문서는 항상 이 패턴을 따라야 합니다. 컬렉션에 속한 컬렉션이나 문서에 속한 문서는 참조할 수 없습니다.

하위 컬렉션을 사용하여 데이터를 계층적으로 구조화하면 데이터에 쉽게 액세스할 수 있습니다. roomA의 모든 메시지를 가져오려면 간단히 db.collection('rooms').doc('roomA').collection('messages') 컬렉션에 액세스하면 됩니다.

하위 컬렉션의 문서도 하위 컬렉션을 포함할 수 있으므로 데이터를 더 중첩할 수 있습니다. 데이터를 중첩할 수 있는 최대 깊이는 100개 수준입니다.

다음에 대한 의견 보내기...

도움이 필요하시나요? 지원 페이지를 방문하세요.