본문 바로가기

UIKIT/Firebase

❓ FireStore 내에 회원정보를 불러오는 데 왜 tryMap?

🔥 tryMap { try $0.data(as: MovieClipUser.self) }의 역할

 

func collectionUsers(retrieve id: String) -> AnyPublisher<MovieClipUser, Error> {
    db.collection(userPath)
        .document(id)
        .getDocument()
        .tryMap { try $0.data(as: MovieClipUser.self) } // 🔥 여기가 핵심
        .eraseToAnyPublisher()
}

🔹 각 단계별 동작

1️⃣ db.collection(userPath).document(id).getDocument()

  • Firestore에서 특정 문서(Document)를 가져오는 비동기 작업
  • 반환 타입: AnyPublisher<DocumentSnapshot, Error>
  • 성공하면 DocumentSnapshot이 반환됨

2️⃣ .tryMap { try $0.data(as: MovieClipUser.self) }

  • DocumentSnapshot을 MovieClipUser 모델로 변환
  • Firestore의 데이터를 MovieClipUser 타입의 객체로 변환하려고 시도
  • 변환이 실패하면 tryMap이 자동으로 에러를 throw

3️⃣ .eraseToAnyPublisher()

  • 반환 타입을 AnyPublisher<MovieClipUser, Error>로 변환하여 외부에서 사용하기 쉽게 만듦

 

.tryMap이 필요한 이유

🔹 1️⃣ .map과 .tryMap의 차이

.map은 단순한 변환만 할 수 있고, 에러를 throw할 수 없음
.tryMap은 변환 도중 오류가 발생하면 try를 사용하여 에러를 throw할 수 있음

🔹 2️⃣ Firestore 변환 시 tryMap이 필요한 이유

만약 Firestore에서 가져온 데이터가 MovieClipUser와 맞지 않는다면,
data(as:)가 에러를 발생시키는데, .map은 에러를 처리할 수 없음.

그래서 .tryMap을 사용해야 변환 실패 시 자동으로 Error를 throw하고, 스트림에서 이를 감지할 수 있음.

 

 data(as:) 변환 실패 예시

만약 Firestore에서 가져온 데이터가 MovieClipUser 모델과 다르면, 변환이 실패하고 tryMap이 Error를 throw함.

예를 들어, MovieClipUser 모델이 다음과 같다고 가정하자.

struct MovieClipUser: Codable {
    let id: String
    let name: String
    let age: Int
}

 

하지만 Firestore에 저장된 데이터가 다음과 같다면:

{
    "id": "abc123",
    "name": "John Doe"
    // "age" 필드가 없음!
}

 

그러면 MovieClipUser 모델에서 age: Int가 필수 필드인데 Firestore 데이터에 없으므로 변환이 실패함!
이 경우 .tryMap이 자동으로 DecodingError를 throw하고, Error로 변환됨.