diff --git a/Postbox/InitialMessageHistoryData.swift b/Postbox/InitialMessageHistoryData.swift index 178b92fda9..4c3c7d6e83 100644 --- a/Postbox/InitialMessageHistoryData.swift +++ b/Postbox/InitialMessageHistoryData.swift @@ -3,4 +3,5 @@ import Foundation public struct InitialMessageHistoryData { public let peer: Peer? public let chatInterfaceState: PeerChatInterfaceState? + public let associatedMessages: [MessageId: Message] } diff --git a/Postbox/MessageHistoryView.swift b/Postbox/MessageHistoryView.swift index 27c41fc3a1..0f7d05d94c 100644 --- a/Postbox/MessageHistoryView.swift +++ b/Postbox/MessageHistoryView.swift @@ -17,6 +17,8 @@ public enum AdditionalMessageHistoryViewData { case totalUnreadState case peerNotificationSettings(PeerId) case cacheEntry(ItemCacheEntryId) + case peer(PeerId) + case peerIsContact(PeerId) } public enum AdditionalMessageHistoryViewDataEntry { @@ -27,6 +29,8 @@ public enum AdditionalMessageHistoryViewDataEntry { case totalUnreadState(ChatListTotalUnreadState) case peerNotificationSettings(PeerNotificationSettings?) case cacheEntry(ItemCacheEntryId, PostboxCoding?) + case peerIsContact(PeerId, Bool) + case peer(PeerId, Peer?) } public enum MessageHistoryViewHole: Hashable { @@ -463,7 +467,7 @@ private func clipMessages(peerIds: MessageHistoryViewPeerIds, entries: [MutableM switch entry { case let .MessageEntry(message, _, _): if message.id.peerId == associatedId.peerId { - if message.id.namespace == associatedId.namespace && message.id.id <= associatedId.id { + if message.id.namespace == associatedId.namespace && message.id.id < associatedId.id { result.append(entry) } } else { @@ -471,7 +475,7 @@ private func clipMessages(peerIds: MessageHistoryViewPeerIds, entries: [MutableM } case let .IntermediateMessageEntry(message, _, _): if message.id.peerId == associatedId.peerId { - if message.id.namespace == associatedId.namespace && message.id.id <= associatedId.id { + if message.id.namespace == associatedId.namespace && message.id.id < associatedId.id { result.append(entry) } } else { @@ -1065,7 +1069,25 @@ final class MutableMessageHistoryView { self.additionalDatas[i] = .cacheEntry(entryId, postbox.retrieveItemCacheEntry(id: entryId)) hasChanges = true } - break + case let .peerIsContact(peerId, value): + if let replacedPeerIds = transaction.replaceContactPeerIds { + let updatedValue: Bool + if let contactPeer = postbox.peerTable.get(peerId), let associatedPeerId = contactPeer.associatedPeerId { + updatedValue = replacedPeerIds.contains(associatedPeerId) + } else { + updatedValue = replacedPeerIds.contains(peerId) + } + + if value != updatedValue { + self.additionalDatas[i] = .peerIsContact(peerId, value) + hasChanges = true + } + } + case let .peer(peerId, _): + if let peer = transaction.currentUpdatedPeers[peerId] { + self.additionalDatas[i] = .peer(peerId, peer) + hasChanges = true + } } } if let cachedData = currentCachedPeerData, !cachedData.messageIds.isEmpty { diff --git a/Postbox/PeerChatInterfaceState.swift b/Postbox/PeerChatInterfaceState.swift index 04c1d99af4..eb395081d0 100644 --- a/Postbox/PeerChatInterfaceState.swift +++ b/Postbox/PeerChatInterfaceState.swift @@ -8,6 +8,7 @@ public protocol PeerChatListEmbeddedInterfaceState: PostboxCoding { public protocol PeerChatInterfaceState: PostboxCoding { var chatListEmbeddedState: PeerChatListEmbeddedInterfaceState? { get } var historyScrollMessageIndex: MessageIndex? { get } + var associatedMessageIds: [MessageId] { get } func isEqual(to: PeerChatInterfaceState) -> Bool } diff --git a/Postbox/Postbox.swift b/Postbox/Postbox.swift index c4c1b67c0a..2ac6cdfeeb 100644 --- a/Postbox/Postbox.swift +++ b/Postbox/Postbox.swift @@ -87,9 +87,9 @@ public final class Transaction { self.postbox?.replaceChatListHole(groupId: groupId, index: index, hole: hole) } - public func resetChatList(keepPeerNamespaces: Set, replacementHole: ChatListHole?) { + public func resetChatList(keepPeerNamespaces: Set, replacementHole: ChatListHole?) -> [PeerId] { assert(!self.disposed) - self.postbox?.resetChatList(keepPeerNamespaces: keepPeerNamespaces, replacementHole: replacementHole) + return self.postbox?.resetChatList(keepPeerNamespaces: keepPeerNamespaces, replacementHole: replacementHole) ?? [] } public func deleteMessages(_ messageIds: [MessageId]) { @@ -2468,6 +2468,16 @@ public final class Postbox { additionalDataEntries.append(.peerNotificationSettings(self.peerNotificationSettingsTable.getEffective(peerId))) case let .cacheEntry(entryId): additionalDataEntries.append(.cacheEntry(entryId, self.retrieveItemCacheEntry(id: entryId))) + case let .peerIsContact(peerId): + let value: Bool + if let contactPeer = self.peerTable.get(peerId), let associatedPeerId = contactPeer.associatedPeerId { + value = self.contactsTable.isContact(peerId: associatedPeerId) + } else { + value = self.contactsTable.isContact(peerId: peerId) + } + additionalDataEntries.append(.peerIsContact(peerId, value)) + case let .peer(peerId): + additionalDataEntries.append(.peer(peerId, self.peerTable.get(peerId))) } } @@ -2516,7 +2526,7 @@ public final class Postbox { case let .associated(peerId, _): initialData = self.initialMessageHistoryData(peerId: peerId) case .group: - initialData = InitialMessageHistoryData(peer: nil, chatInterfaceState: nil) + initialData = InitialMessageHistoryData(peer: nil, chatInterfaceState: nil, associatedMessages: [:]) } subscriber.putNext((MessageHistoryView(mutableView), initialUpdateType, initialData)) @@ -2534,7 +2544,16 @@ public final class Postbox { } private func initialMessageHistoryData(peerId: PeerId) -> InitialMessageHistoryData { - return InitialMessageHistoryData(peer: self.peerTable.get(peerId), chatInterfaceState: self.peerChatInterfaceStateTable.get(peerId)) + let chatInterfaceState = self.peerChatInterfaceStateTable.get(peerId) + var associatedMessages: [MessageId: Message] = [:] + if let chatInterfaceState = chatInterfaceState { + for id in chatInterfaceState.associatedMessageIds { + if let message = self.getMessage(id) { + associatedMessages[message.id] = message + } + } + } + return InitialMessageHistoryData(peer: self.peerTable.get(peerId), chatInterfaceState: chatInterfaceState, associatedMessages: associatedMessages) } public func messageIndexAtId(_ id: MessageId) -> Signal { @@ -3204,7 +3223,7 @@ public final class Postbox { return nil } - fileprivate func resetChatList(keepPeerNamespaces: Set, replacementHole: ChatListHole?) { + fileprivate func resetChatList(keepPeerNamespaces: Set, replacementHole: ChatListHole?) -> [PeerId] { let entries = self.chatListTable.allEntries(groupId: nil) for entry in entries { switch entry { @@ -3222,6 +3241,14 @@ public final class Postbox { if let replacementHole = replacementHole { self.chatListTable.addHole(groupId: nil, hole: replacementHole, operations: &self.currentChatListOperations) } + return entries.compactMap { entry -> PeerId? in + switch entry { + case let .message(index, _): + return index.messageIndex.id.peerId + default: + return nil + } + } } public func isMasterClient() -> Signal {