diff --git a/lib/reducers/master-reducer.js b/lib/reducers/master-reducer.js --- a/lib/reducers/master-reducer.js +++ b/lib/reducers/master-reducer.js @@ -85,7 +85,12 @@ // Only allow checkpoints to increase if we are connected // or if the action is a STATE_SYNC const { messageStoreOperations, messageStore: reducedMessageStore } = - reduceMessageStore(state.messageStore, action, threadInfos); + reduceMessageStore( + state.messageStore, + action, + threadInfos, + onStateDifferenceForStaff, + ); let messageStore = reducedMessageStore; let { keyserverStore, keyserverStoreOperations } = reduceKeyserverStore( diff --git a/lib/reducers/message-reducer.js b/lib/reducers/message-reducer.js --- a/lib/reducers/message-reducer.js +++ b/lib/reducers/message-reducer.js @@ -107,7 +107,9 @@ type ClientUpdateInfo, processUpdatesActionType, } from '../types/update-types.js'; +import { getMessageForException } from '../utils/errors.js'; import { translateClientDBThreadMessageInfos } from '../utils/message-ops-utils.js'; +import { assertObjectsAreEqual } from '../utils/objects.js'; const _mapValuesWithKeys = _mapValues.convert({ cap: false }); @@ -140,6 +142,31 @@ ); } +function assertMessageStoreLocalMessageInfosAreEqual( + processedMessageStore: MessageStore, + expectedMessageStore: MessageStore, + location: string, + onStateDifference?: (message: string) => mixed, +) { + try { + assertObjectsAreEqual( + processedMessageStore.local, + expectedMessageStore.local, + `MessageStore.local - ${location}`, + ); + } catch (e) { + console.log( + 'Error processing MessageStore local ops', + processedMessageStore.local, + expectedMessageStore.local, + ); + const message = `Error processing MessageStore local ops ${ + getMessageForException(e) ?? '{no exception message}' + }`; + onStateDifference?.(message); + } +} + const newThread = (): ThreadMessageInfo => ({ messageIDs: [], startReached: false, @@ -725,6 +752,7 @@ messageStore: MessageStore, action: BaseAction, newThreadInfos: RawThreadInfos, + onStateDifference?: (message: string) => mixed, ): ReduceMessageStoreResult { if ( action.type === legacyLogInActionTypes.success || @@ -1679,6 +1707,13 @@ payload: { threads: threadsToAdd }, }); + assertMessageStoreLocalMessageInfosAreEqual( + processedMessageStore, + messageStore, + action.type, + onStateDifference, + ); + return { messageStoreOperations, messageStore: processedMessageStore, diff --git a/lib/reducers/message-reducer.test.js b/lib/reducers/message-reducer.test.js --- a/lib/reducers/message-reducer.test.js +++ b/lib/reducers/message-reducer.test.js @@ -298,7 +298,7 @@ auxUserInfos: {}, threadActivityStore: {}, entries: {}, - messageStoreLocalMessageInfos: {}, + messageStoreLocalMessageInfos: [], }, }, { diff --git a/lib/types/store-ops-types.js b/lib/types/store-ops-types.js --- a/lib/types/store-ops-types.js +++ b/lib/types/store-ops-types.js @@ -11,7 +11,6 @@ import type { ThreadHashes } from './integrity-types.js'; import type { KeyserverInfos } from './keyserver-types.js'; import type { - MessageStoreLocalMessageInfos, ClientDBMessageInfo, ClientDBThreadMessageInfo, ClientDBLocalMessageInfo, @@ -139,5 +138,5 @@ +auxUserInfos: ?AuxUserInfos, +threadActivityStore: ?ThreadActivityStore, +entries: ?RawEntryInfos, - +messageStoreLocalMessageInfos: ?MessageStoreLocalMessageInfos, + +messageStoreLocalMessageInfos: ?$ReadOnlyArray, }; diff --git a/native/data/sqlite-data-handler.js b/native/data/sqlite-data-handler.js --- a/native/data/sqlite-data-handler.js +++ b/native/data/sqlite-data-handler.js @@ -244,6 +244,7 @@ auxUserInfos, threadActivityEntries, entries, + messageStoreLocalMessageInfos, } = await commCoreModule.getClientDBStore(); const threadInfosFromDB = threadStoreOpsHandlers.translateClientDBData(threads); @@ -285,6 +286,7 @@ auxUserInfos: auxUserInfosFromDB, threadActivityStore: threadActivityStoreFromDB, entries: entriesFromDB, + messageStoreLocalMessageInfos, }, }); } catch (setStoreException) {