Транзакция не терпит неудачу, но поля написаны неправильно - PullRequest
0 голосов
/ 18 сентября 2018

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

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

У меня два вопроса: является ли массив лучшей структурой в базе данных NoSql для этой проблемы?Почему элемент массива исчезает несмотря на транзакцию?

export const addImageToTag = functions.storage.object().onFinalize(async (object) => {
    try {
        const tag = object.metadata.Tag;
        const position = object.metadata.Position;

        const tagRef = db.collection(COLLECTION_TAGS).doc(tag)
        const tagSnapshot = await db.runTransaction(t => t.get(tagRef));

        const images = tagSnapshot.data().images;
        images[position] = object.name;

        let uploadCount = 0;
        for (let i = 0; i < tagSnapshot.data().imageCount; i++) {
            if (images[i].length > 0) {
                uploadCount++;
            } else {
                break;
            }
        }

        let state;
        if (tagSnapshot.data().imageCount === uploadCount) {
            state = STATE_ACTIVE;
        } else {
            state = STATE_UPLOADING;
        }

        await tagSnapshot.ref.update({
            images: images,
            state: state
        });

        console.log('Image ', position, ' of tag ', tag, 'added')
    } catch (error) {
        console.error('Call failed: ', error)
    }
});

1 Ответ

0 голосов
/ 18 сентября 2018

На второй вопрос ответили, фактически поместив код в блок транзакции, сделали свое дело.Я читал, что ссылки на документ тега с использованием tagSnapshot.ref было достаточно, что ложно.

export const addImageToTag = functions.storage.object().onFinalize(async (object) => {
    try {
        const tag = object.metadata.Tag;
        const position = object.metadata.Position;
        const tagRef = db.collection(COLLECTION_TAGS).doc(tag)

        await db.runTransaction(async transaction => {
            const tagSnapshot = await transaction.get(tagRef)

            const images = tagSnapshot.data().images;
            images[position] = object.name;

            let uploadCount = 0;
            for (let i = 0; i < tagSnapshot.data().imageCount; i++) {
                if (images[i].length > 0) {
                    uploadCount++;
                } else {
                    break;
                }
            }

            let state;
            if (tagSnapshot.data().imageCount === uploadCount) {
                state = STATE_ACTIVE;
            } else {
                state = STATE_UPLOADING;
            }

            transaction.update(tagRef, {
                images: images,
                state: state
            });

            if (state === STATE_ACTIVE) {
                console.log('All images of tag ', tag, ' were succesfully added')
            }
            });
    } catch (error) {
        console.error('Call failed: ', error)
    }
});
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...