Синхронизация контактов с друзьями - чат приложение Firebase - PullRequest
0 голосов
/ 02 ноября 2018

Мы работаем в приложении, которое включает чат в реальном времени, и мы используем Firebase и React-Native. Пользователь будет использовать свои номера телефонов для аутентификации, поэтому мы используем сервис аутентификации телефонных номеров.

Когда пользователи открывают приложение, мы извлекаем их контактную информацию и отправляем проанализированные / отфильтрованные телефонные номера в облачную функцию, эта функция должна обрабатывать все телефонные номера, отправленные в запросе, и помечать в качестве друзей тех пользователей, чей номер телефона соответствует один из контактных телефонов. Тот же процесс, что и WhatsApp.

Для этого мы попробовали два подхода:

  1. После того, как функция получает запрос, она перебирает массив телефонных номеров контакта и запрашивает коллекцию users в базе данных Cloud Firestore. Если запрос возвращает результат, функция извлекает эту информацию о пользователе и добавляет ее в подгруппу friends запрашивающего пользователя.

    /**
     * 
     * @param {string} userId - Firebase id of user that made the request
     * @param {Array<string>} contacts - Array of user's contacts phone numbers in E.164 format
     * @returns {Array<object>} Array containing registered contacts data 
     */
    exports.searchFriends = (userId, contacts) => {
      const registeredContacts = contacts.map(phoneNumber =>
        db.collection(constants.usersPublicCollection)
          .where('phoneNumber', '==', phoneNumber)
          .get()
          .then(snapshot => snapshot.docs.map((doc) => {
            if (doc.id !== userId) {
              return doc.data();
            }
            return null;
          })));
    
      return Promise.all(registeredContacts)
        .then(friends => friends.filter(friend => friend !== null));
        .then(friends => friends.reduce((prev, next) => [...prev, ...next], [])); // flatten array of arrays
    };
    
  2. Второй подход - тот же процесс, но он запрашивает службу аутентификации с помощью метода getUserByPhonenumber().

    /**
     * 
     * @param {string} userId - Firebase id of user that made the request
     * @param {Array<string>} contacts - Array of user's contacts phone numbers in E.164 format
     * @returns {Array<object>} Array containing registered contacts data 
     */        
    exports.searchFriends = (userId, contacts) => {
      const registeredContacts = contacts.map(phoneNumber =>
        admin.auth().getUserByPhoneNumber(phoneNumber)
          .then((user) => {
            if (user.uid !== userId) {
              return getUsersRef(user.uid).get();
            }
            return null;
          })
          .then((userProfile) => {
            if (!userProfile) {
              return null;
            }
            return userProfile.data();
          })
          .catch((err) => {
            if (err.code !== 'auth/user-not-found') {
              console.log(phoneNumber);
              console.error(err);
            }
            return null;
          }));
    
      return Promise.all(registeredContacts)
        .then(friends => friends.filter(friend => friend !== null));
    };
    

Первый подход не сработал, потому что, когда мы проводили тестирование с пользователем с контактами 2k, мы обнаружили, что этот метод, возможно (и один раз) потреблял все ограничения на чтение в облачном хранилище файлов в день (50k).
Итак, мы попробовали со вторым подходом. Этот метод, кажется, работает, но после пары вызовов функции мы получаем ошибку, указывающую, что мы достигли предела для SocketConnectNonbillable, мы попытались примерно через 2 часа, и он снова заработал, но после вызова произошел точно так же. Однако мы проверили страницу квот, и эта конкретная квота была хорошей, в то время мы выполняли только 30 подключений в день и только 0,3472 за 100 секунд.

Кто-нибудь знает решение этой проблемы?

Любая обратная связь приветствуется, если кто-либо обнаружит проблему с этими подходами или если у него есть идея решить проблему с контактами / друзьями (мы знаем, что они определенно не самые лучшие).

Спасибо!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...