Увеличьте существующее значение в пожарном депо - PullRequest
2 голосов
/ 18 марта 2019

Есть ли способ увеличить существующее значение в firestore ?

What i am trying

    FirebaseFirestore.getInstance()
            .collection("notifications")
            .document(response.getString("multicast_id"))
            .set(notificationData);
    FirebaseFirestore.getInstance()
            .collection("users")
            .document(post.userId)
            .get().addOnCompleteListener(new OnCompleteListener<DocumentSnapshot>() {
        @Override
        public void onComplete(@NonNull Task<DocumentSnapshot> task) {
            if (task.isSuccessful()) {
                int followers = Integer.valueOf(task.getResult().getData().get("followers").toString());
                FirebaseFirestore.getInstance()
                        .collection("users")
                        .document(post.userId).update("followers", followers++).addOnCompleteListener(new OnCompleteListener<Void>() {
                    @Override
                    public void onComplete(@NonNull Task<Void> task) {
                    }
                });
            }
        }
    });

Структура базы данных

users

  - data....
  - followers(number)

В соответствии с этим Ответ функция доступна для увеличения или уменьшения значений числовых полей

Версия 5.9.0 - 14 марта 2019

Добавлено FieldValue.increment(), который можно использовать в update () и установить (..., {merge: true}) для безопасного увеличения или уменьшения значений числового поля без транзакций.

https://firebase.google.com/support/release-notes/js


, так что, я думаю, есть ли какая-нибудь функция, доступная для увеличения существующего значения в firestore android?


1 Ответ

2 голосов
/ 18 марта 2019

Нет доступных FieldValue.increment(), но мы можем достичь Обновление данных с транзакциями

Обновление данных с транзакциями

Используя клиентские библиотеки Cloud Firestore, вы можете сгруппировать несколько операций в одну транзакцию.Транзакции полезны, когда вы хотите обновить значение поля на основе его текущего значения или значения какого-либо другого поля.Вы можете увеличить счетчик, создав транзакцию, которая считывает текущее значение счетчика, увеличивает его и записывает новое значение в Cloud Firestore.

Транзакция состоит из любого числа операций get (), за которыми следует любаяколичество операций записи, таких как set(), update() или delete().В случае одновременного редактирования Cloud Firestore снова запускает всю транзакцию.Например, если транзакция читает документы, а другой клиент изменяет какой-либо из этих документов, Cloud Firestore повторяет транзакцию.Эта функция гарантирует, что транзакция выполняется на актуальных и согласованных данных.

Транзакции никогда частично не применяют записи.Все операции записи выполняются в конце успешной транзакции.

При использовании транзакций обратите внимание, что:

  • Операции чтения должны предшествовать операциям записи.Функция, вызывающая
  • транзакция (функция транзакции), может запускаться более одного раза, если одновременное редактирование влияет на документ, который читает транзакция.
  • Функции транзакции не должны напрямую изменять состояние приложения.
  • Транзакции не будут выполнены, когда клиент находится в автономном режиме.

Передача информации из транзакций

Не изменяйте состояние приложения внутриваших транзакций функций.Это создаст проблемы параллелизма, потому что функции транзакций могут выполняться несколько раз и не гарантированно будут выполняться в потоке пользовательского интерфейса.Вместо этого, передавайте необходимую информацию из ваших транзакционных функций.Следующий пример основан на предыдущем примере и показывает, как передавать информацию из транзакции:

Example

final DocumentReference sfDocRef = db.collection("cities").document("SF");

db.runTransaction(new Transaction.Function<Double>() {
    @Override
    public Double apply(Transaction transaction) throws FirebaseFirestoreException {
        DocumentSnapshot snapshot = transaction.get(sfDocRef);
        double newPopulation = snapshot.getDouble("population") + 1;
        if (newPopulation <= 1000000) {
            transaction.update(sfDocRef, "population", newPopulation);
            return newPopulation;
        } else {
            throw new FirebaseFirestoreException("Population too high",
                    FirebaseFirestoreException.Code.ABORTED);
        }
    }
}).addOnSuccessListener(new OnSuccessListener<Double>() {
    @Override
    public void onSuccess(Double result) {
        Log.d(TAG, "Transaction success: " + result);
    }
})
.addOnFailureListener(new OnFailureListener() {
    @Override
    public void onFailure(@NonNull Exception e) {
        Log.w(TAG, "Transaction failure.", e);
    }
});

Редактировать 2

Благодаря последнему патчу Firestore (13 марта 2019 г.)

Класс Firestore FieldValue теперь содержит метод increment , который атомарно обновляет числовое значениеполе документа в базе данных пожарного магазина.Вы можете использовать эту опцию FieldValue с set (с истинным mergeOptions) или с update методами объекта DocumentReference.

Использование приведено ниже (из официальных документов это все, что есть).):

DocumentReference washingtonRef = db.collection("cities").document("DC");

// Atomically increment the population of the city by 50.
washingtonRef.update("population", FieldValue.increment(50));

Если вам интересно, он доступен с версии 18.2.0 firestore.Для вашего удобства конфигурация зависимостей Gradle составляет implementation 'com.google.firebase:firebase-firestore:18.2.0'

Примечание. Операции приращения полезны для реализации счетчиков, но имейте в виду, что вы можете обновлять один документ только один раз в секунду.Если вам нужно обновить свой счетчик выше этой нормы, см. Страницу Распределенные счетчики .


FieldValue.increment() является чисто "серверной" стороной (происходит в пожарном депо),поэтому вам не нужно показывать текущее значение клиенту (-ам).

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