개발하는 앱 유형에 따라 어떠한 사용자 또는 기기가 현재 온라인 상태인지를 확인하면 유용할 수 있습니다. 이러한 기능을 '접속 상태' 감지라고 합니다.
예를 들어 소셜 네트워크와 같은 앱을 빌드하거나 여러 IoT 기기를 배포할 경우 이 정보를 사용하여 채팅 가능한 온라인 상태인 친구 목록을 표시하거나 IoT 기기를 '최종 접속 시간' 순으로 정렬할 수 있습니다.
Cloud Firestore에서 기본적으로 인기척을 지원하지 않지만 다음 방법을 사용할 수 있습니다. 다른 Firebase 제품을 활용하여 접속 상태 시스템 구축
솔루션: Cloud Functions 및 실시간 데이터베이스
Cloud Firestore를 Firebase 실시간 데이터베이스의 네이티브에 연결 Cloud Functions를 사용하세요
실시간 데이터베이스를 사용하여 연결 상태를 보고한 후 Cloud Functions를 사용하여 다음을 수행합니다. 이 데이터를 Cloud Firestore에 미러링합니다.
실시간 데이터베이스에서 접속 상태 사용
먼저 실시간 데이터베이스의 기본 접속 상태 시스템을 살펴보겠습니다.
웹
// Fetch the current user's ID from Firebase Authentication. var uid = firebase.auth().currentUser.uid; // Create a reference to this user's specific status node. // This is where we will store data about being online/offline. var userStatusDatabaseRef = firebase.database().ref('/status/' + uid); // We'll create two constants which we will write to // the Realtime database when this device is offline // or online. var isOfflineForDatabase = { state: 'offline', last_changed: firebase.database.ServerValue.TIMESTAMP, }; var isOnlineForDatabase = { state: 'online', last_changed: firebase.database.ServerValue.TIMESTAMP, }; // Create a reference to the special '.info/connected' path in // Realtime Database. This path returns `true` when connected // and `false` when disconnected. firebase.database().ref('.info/connected').on('value', function(snapshot) { // If we're not currently connected, don't do anything. if (snapshot.val() == false) { return; }; // If we are currently connected, then use the 'onDisconnect()' // method to add a set which will only trigger once this // client has disconnected by closing the app, // losing internet, or any other means. userStatusDatabaseRef.onDisconnect().set(isOfflineForDatabase).then(function() { // The promise returned from .onDisconnect().set() will // resolve as soon as the server acknowledges the onDisconnect() // request, NOT once we've actually disconnected: // https://firebase.google.com/docs/reference/js/firebase.database.OnDisconnect // We can now safely set ourselves as 'online' knowing that the // server will mark us as offline once we lose connection. userStatusDatabaseRef.set(isOnlineForDatabase); }); });
이 예시는 완전한 실시간 데이터베이스 접속 상태 시스템으로 여러 연결 해제, 비정상 종료 등을 처리합니다.
Cloud Firestore에 연결 중
Cloud Firestore에서 유사한 솔루션을 구현하려면 다음을 사용하세요. 실시간 데이터베이스 코드로 처리하고 Cloud Functions를 사용하여 실시간 데이터베이스 및 Cloud Firestore 동기화됨
프로젝트에 실시간 데이터베이스를 아직 추가하지 않았다면 지금 추가하고 위의 접속 상태 솔루션을 포함합니다.
다음으로 현재 상태를 Cloud Firestore에 동기화합니다. 다음과 같은 메서드를 지원합니다.
- 로컬에서 오프라인 기기의 Cloud Firestore 캐시에 저장 오프라인 상태임을 알 수 있습니다.
- 전역적으로 Cloud 함수를 사용하여 Cloud Firestore님은 이 기기가 오프라인 상태임을 알고 있습니다.
Cloud Firestore의 로컬 캐시 업데이트
첫 번째 문제인 Cloud Firestore의 로컬 캐시
웹
// ... var userStatusFirestoreRef = firebase.firestore().doc('/status/' + uid); // Firestore uses a different server timestamp value, so we'll // create two more constants for Firestore state. var isOfflineForFirestore = { state: 'offline', last_changed: firebase.firestore.FieldValue.serverTimestamp(), }; var isOnlineForFirestore = { state: 'online', last_changed: firebase.firestore.FieldValue.serverTimestamp(), }; firebase.database().ref('.info/connected').on('value', function(snapshot) { if (snapshot.val() == false) { // Instead of simply returning, we'll also set Firestore's state // to 'offline'. This ensures that our Firestore cache is aware // of the switch to 'offline.' userStatusFirestoreRef.set(isOfflineForFirestore); return; }; userStatusDatabaseRef.onDisconnect().set(isOfflineForDatabase).then(function() { userStatusDatabaseRef.set(isOnlineForDatabase); // We'll also add Firestore set here for when we come online. userStatusFirestoreRef.set(isOnlineForFirestore); }); });
이러한 변경을 통해 이제 로컬 Cloud Firestore 상태가 항상
기기의 온라인/오프라인 상태를 반영합니다. 즉, 사용자는
/status/{uid}
문서를 만들고 이 데이터를 사용하여 연결을 반영하도록 UI를 변경합니다.
있습니다.
웹
userStatusFirestoreRef.onSnapshot(function(doc) { var isOnline = doc.data().state == 'online'; // ... use isOnline });
전역적으로 Cloud Firestore 업데이트 중
애플리케이션이 온라인 상태를 올바르게 보고하지만 이 상태는
'오프라인'으로 인해 다른 Cloud Firestore 앱에서는 아직 정확하지 않습니다.
상태 쓰기는 로컬에서만 이루어지며 연결이 복원될 때 동기화되지 않습니다. 반론할 대상
status/{uid}
경로를 실시간으로 감시하는 Cloud 함수를 사용합니다.
데이터베이스. 실시간 데이터베이스 값이 변경되면 값이 Cloud Firestore에 동기화됩니다.
모든 사용자의 있는지 확인합니다.
Node.js
firebase.firestore().collection('status') .where('state', '==', 'online') .onSnapshot(function(snapshot) { snapshot.docChanges().forEach(function(change) { if (change.type === 'added') { var msg = 'User ' + change.doc.id + ' is online.'; console.log(msg); // ... } if (change.type === 'removed') { var msg = 'User ' + change.doc.id + ' is offline.'; console.log(msg); // ... } }); });
이 함수를 배포하면 완전한 접속 상태 시스템이 실행됩니다.
Cloud Firestore를 사용합니다. 다음은 PII를 사용하는 사용자를 모니터링하는
where()
쿼리를 사용하여 온라인 또는 오프라인으로 전환할 수 있습니다.
웹
firebase.firestore().collection('status') .where('state', '==', 'online') .onSnapshot(function(snapshot) { snapshot.docChanges().forEach(function(change) { if (change.type === 'added') { var msg = 'User ' + change.doc.id + ' is online.'; console.log(msg); // ... } if (change.type === 'removed') { var msg = 'User ' + change.doc.id + ' is offline.'; console.log(msg); // ... } }); });
제한사항
실시간 데이터베이스를 사용하여 Cloud Firestore 앱에 접속 상태를 추가하는 작업은 다음과 같습니다. 확장 가능하고 효과적이지만 몇 가지 제한사항이 있습니다.
- 디바운싱 - Cloud Firestore인 경우 이 솔루션은 여러 개의 있습니다. 이러한 변경사항으로 인해 이벤트가 너무 많이 트리거되는 경우 수동으로 Cloud Firestore 이벤트를 디바운싱합니다.
- 연결 - 이 구현은 Realtime에 대한 연결을 측정합니다. Cloud Firestore가 아닌 데이터베이스입니다. 각 데이터베이스에 대한 연결 상태가 동일하지 않으면 이 솔루션은 정확하지 않은 접속 상태를 보고할 수 있습니다.
- Android - Android에서 실시간 데이터베이스는 비활성 상태가 60초간 지속되면 백엔드에서 연결을 끊습니다. 비활성 상태란 열린 상태의 리스너나 대기 중인 작업이 없다는 의미입니다. 연결을 열린 상태로 유지하려면 값 이벤트 리스너를
.info/connected
외의 경로에 추가하는 것이 좋습니다. 예를 들어 각 세션 시작 시FirebaseDatabase.getInstance().getReference((new Date()).toString()).keepSynced()
를 실행하는 방법이 있습니다. 자세한 내용은 연결 상태 감지를 참조하세요.