Skip to content

Combine을 활용한 데이터 전달

SeungJae Son edited this page Dec 4, 2024 · 1 revision

배경

알쏭달쏭은 멀티플레이어 게임으로, 모든 기기에서 동일한 데이터를 실시간으로 동기화해야 하는 요구사항이 있었습니다. 이를 해결하기 위해 Firebase를 도입하여 서버 역할을 대신하고, Firebase에서 Firestore를 통해 데이터의 변경사항을 감지하고, Combine을 통해 데이터의 변경을 실시간으로 뷰모델과 View에 전달하는 구조를 구현하였습니다.

구조

22

Combine을 사용한 이유

Combine을 사용한 주요 이유는 Firebase의 실시간 데이터 리스닝 기능과 원활하게 통합하기 위함이었습니다.

Firebase의 Firestore와 Realtime Database는 실시간으로 데이터 변경 사항을 감지할 수 있는 리스닝 기능을 제공합니다.

이러한 실시간 데이터 변경 사항에 대한 비동기 이벤트를 뷰까지 전달이 필요했습니다.

이 사이에 stream 이라는걸만들어서 연결시키고 데이터를 거기다가 흘려보내고 싶었고,

Combine 프레임워크를 사용하여 각기 다른 시간에 발생하는 비동기이벤트를 처리하기 위해 사용했습니다.

메인 레포지토리와 하위 레포지토리로 나눈 이유

Firebase는 데이터를 Collection -> Document -> Field 계층 구조로 관리합니다.

그러나 Firebase SDK에서는 Document의 변경사항만을 감지할 수 있으며,

Field 단위의 변경사항은 직접적으로 감지할 수 없습니다.

저희 알쏭달쏭에서는 특정 필드의 변경사항을 실시간으로 감지하여

뷰모델과 하위 컴포넌트에 전달해야 하는 요구사항이 있었습니다.

이를 해결하기 위해 MainRepository하위 레포지토리로 구조를 분리하였습니다

  • MainRepository: Firestore의 Document 변경사항을 감지하고, 전체 Document 데이터를 MainRepository의 CurrentValueSubject에 업데이트합니다.
  • 하위 레포지토리: MainRepository의 데이터를 구독하며, 특정 필드의 변경을 감지하여 필요한 컴포넌트에 전달하는 역할을 담당합니다. 이를 통해 Field 단위의 세밀한 변경사항을 관리할 수 있게 되었습니다.

아쉬웠던 점

  • 비슷한 구독 로직이 여러 ViewModel이나 Repository에 중복될 수 있습니다.
  • 여러 Publisher가 조합된 복잡한 데이터 흐름에서 문제가 발생했었 을 때, 데이터가 어떻게 흘러가는지 디버깅하기 어려웠습니다.
  • 뷰 컴포넌트에서 Publisher만 bind할 수있도록 만들었는데, 항상 Published 데이터만 받아서 유연성이 조금 떨어짐

iOS07 프로젝트 일지

📚 문서

🫶🏻 팀 기록

🎤 프로젝트

💡 핵심 경험

🚨 트러블 슈팅

📔 학습 정리

🪄 QA

Clone this wiki locally