mirror of
https://github.com/Swiftgram/Telegram-iOS.git
synced 2025-12-04 13:38:21 +00:00
Fix clear history
This commit is contained in:
parent
6696d6045c
commit
2a05628f97
@ -90,6 +90,7 @@ enum AccountStateMutationOperation {
|
||||
case UpdateCall(Api.PhoneCall)
|
||||
case UpdateLangPack(String, Api.LangPackDifference?)
|
||||
case UpdateMinAvailableMessage(MessageId)
|
||||
case UpdatePeerInclusionMinTimestamp(PeerId, Int32)
|
||||
}
|
||||
|
||||
struct AccountMutableState {
|
||||
@ -277,6 +278,10 @@ struct AccountMutableState {
|
||||
self.addOperation(.UpdateMinAvailableMessage(id))
|
||||
}
|
||||
|
||||
mutating func updatePeerInclusionMinTimestamp(peerId: PeerId, timestamp: Int32) {
|
||||
self.addOperation(.UpdatePeerInclusionMinTimestamp(peerId, timestamp))
|
||||
}
|
||||
|
||||
mutating func mergeUsers(_ users: [Api.User]) {
|
||||
self.addOperation(.MergeApiUsers(users))
|
||||
|
||||
@ -347,7 +352,7 @@ struct AccountMutableState {
|
||||
|
||||
mutating func addOperation(_ operation: AccountStateMutationOperation) {
|
||||
switch operation {
|
||||
case .DeleteMessages, .DeleteMessagesWithGlobalIds, .EditMessage, .UpdateMessagePoll, .UpdateMedia, .ReadOutbox, .ReadGroupFeedInbox, .MergePeerPresences, .UpdateSecretChat, .AddSecretMessages, .ReadSecretOutbox, .AddPeerInputActivity, .UpdateCachedPeerData, .UpdatePinnedItemIds, .ReadMessageContents, .UpdateMessageImpressionCount, .UpdateInstalledStickerPacks, .UpdateRecentGifs, .UpdateChatInputState, .UpdateCall, .UpdateLangPack, .UpdateMinAvailableMessage, .UpdatePeerChatUnreadMark, .UpdateIsContact:
|
||||
case .DeleteMessages, .DeleteMessagesWithGlobalIds, .EditMessage, .UpdateMessagePoll, .UpdateMedia, .ReadOutbox, .ReadGroupFeedInbox, .MergePeerPresences, .UpdateSecretChat, .AddSecretMessages, .ReadSecretOutbox, .AddPeerInputActivity, .UpdateCachedPeerData, .UpdatePinnedItemIds, .ReadMessageContents, .UpdateMessageImpressionCount, .UpdateInstalledStickerPacks, .UpdateRecentGifs, .UpdateChatInputState, .UpdateCall, .UpdateLangPack, .UpdateMinAvailableMessage, .UpdatePeerInclusionMinTimestamp, .UpdatePeerChatUnreadMark, .UpdateIsContact:
|
||||
break
|
||||
case let .AddMessages(messages, location):
|
||||
for message in messages {
|
||||
|
||||
@ -829,6 +829,13 @@ private func finalStateWithUpdatesAndServerTime(postbox: Postbox, network: Netwo
|
||||
}
|
||||
}
|
||||
updatedState.editMessage(messageId, message: message)
|
||||
for media in message.media {
|
||||
if let media = media as? TelegramMediaAction {
|
||||
if case .historyCleared = media.action {
|
||||
updatedState.readInbox(messageId)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
case let .updateNewChannelMessage(apiMessage, pts, ptsCount):
|
||||
if let message = StoreMessage(apiMessage: apiMessage) {
|
||||
@ -1885,7 +1892,7 @@ private func optimizedOperations(_ operations: [AccountStateMutationOperation])
|
||||
var currentAddMessages: OptimizeAddMessagesState?
|
||||
for operation in operations {
|
||||
switch operation {
|
||||
case .DeleteMessages, .DeleteMessagesWithGlobalIds, .EditMessage, .UpdateMessagePoll, .UpdateMedia, .MergeApiChats, .MergeApiUsers, .MergePeerPresences, .UpdatePeer, .ReadInbox, .ReadOutbox, .ReadGroupFeedInbox, .ResetReadState, .UpdatePeerChatUnreadMark, .ResetMessageTagSummary, .UpdateNotificationSettings, .UpdateGlobalNotificationSettings, .UpdateSecretChat, .AddSecretMessages, .ReadSecretOutbox, .AddPeerInputActivity, .UpdateCachedPeerData, .UpdatePinnedItemIds, .ReadMessageContents, .UpdateMessageImpressionCount, .UpdateInstalledStickerPacks, .UpdateRecentGifs, .UpdateChatInputState, .UpdateCall, .UpdateLangPack, .UpdateMinAvailableMessage, .UpdateIsContact:
|
||||
case .DeleteMessages, .DeleteMessagesWithGlobalIds, .EditMessage, .UpdateMessagePoll, .UpdateMedia, .MergeApiChats, .MergeApiUsers, .MergePeerPresences, .UpdatePeer, .ReadInbox, .ReadOutbox, .ReadGroupFeedInbox, .ResetReadState, .UpdatePeerChatUnreadMark, .ResetMessageTagSummary, .UpdateNotificationSettings, .UpdateGlobalNotificationSettings, .UpdateSecretChat, .AddSecretMessages, .ReadSecretOutbox, .AddPeerInputActivity, .UpdateCachedPeerData, .UpdatePinnedItemIds, .ReadMessageContents, .UpdateMessageImpressionCount, .UpdateInstalledStickerPacks, .UpdateRecentGifs, .UpdateChatInputState, .UpdateCall, .UpdateLangPack, .UpdateMinAvailableMessage, .UpdatePeerInclusionMinTimestamp, .UpdateIsContact:
|
||||
if let currentAddMessages = currentAddMessages, !currentAddMessages.messages.isEmpty {
|
||||
result.append(.AddMessages(currentAddMessages.messages, currentAddMessages.location))
|
||||
}
|
||||
@ -2104,6 +2111,14 @@ func replayFinalState(accountManager: AccountManager, postbox: Postbox, accountP
|
||||
deleteMessages(transaction: transaction, mediaBox: mediaBox, ids: ids)
|
||||
case let .UpdateMinAvailableMessage(id):
|
||||
transaction.deleteMessagesInRange(peerId: id.peerId, namespace: id.namespace, minId: 1, maxId: id.id)
|
||||
case let .UpdatePeerInclusionMinTimestamp(peerId, timestamp):
|
||||
let inclusion = transaction.getPeerChatListInclusion(peerId)
|
||||
switch inclusion {
|
||||
case .ifHasMessages, .ifHasMessagesOrOneOf:
|
||||
transaction.updatePeerChatListInclusion(peerId, inclusion: inclusion.withSetIfHasMessagesOrMaxMinTimestamp(timestamp))
|
||||
default:
|
||||
break
|
||||
}
|
||||
case let .EditMessage(id, message):
|
||||
transaction.updateMessage(id, update: { previousMessage in
|
||||
var updatedFlags = message.flags
|
||||
|
||||
@ -86,15 +86,18 @@ final class CloudChatRemoveChatOperation: PostboxCoding {
|
||||
final class CloudChatClearHistoryOperation: PostboxCoding {
|
||||
let peerId: PeerId
|
||||
let topMessageId: MessageId
|
||||
let type: InteractiveMessagesDeletionType
|
||||
|
||||
init(peerId: PeerId, topMessageId: MessageId) {
|
||||
init(peerId: PeerId, topMessageId: MessageId, type: InteractiveMessagesDeletionType) {
|
||||
self.peerId = peerId
|
||||
self.topMessageId = topMessageId
|
||||
self.type = type
|
||||
}
|
||||
|
||||
init(decoder: PostboxDecoder) {
|
||||
self.peerId = PeerId(decoder.decodeInt64ForKey("p", orElse: 0))
|
||||
self.topMessageId = MessageId(peerId: PeerId(decoder.decodeInt64ForKey("m.p", orElse: 0)), namespace: decoder.decodeInt32ForKey("m.n", orElse: 0), id: decoder.decodeInt32ForKey("m.i", orElse: 0))
|
||||
self.type = InteractiveMessagesDeletionType(rawValue: decoder.decodeInt32ForKey("type", orElse: 0)) ?? .forLocalPeer
|
||||
}
|
||||
|
||||
func encode(_ encoder: PostboxEncoder) {
|
||||
@ -102,6 +105,7 @@ final class CloudChatClearHistoryOperation: PostboxCoding {
|
||||
encoder.encodeInt64(self.topMessageId.peerId.toInt64(), forKey: "m.p")
|
||||
encoder.encodeInt32(self.topMessageId.namespace, forKey: "m.n")
|
||||
encoder.encodeInt32(self.topMessageId.id, forKey: "m.i")
|
||||
encoder.encodeInt32(self.type.rawValue, forKey: "type")
|
||||
}
|
||||
}
|
||||
|
||||
@ -113,7 +117,7 @@ func cloudChatAddRemoveChatOperation(transaction: Transaction, peerId: PeerId, r
|
||||
transaction.operationLogAddEntry(peerId: peerId, tag: OperationLogTags.CloudChatRemoveMessages, tagLocalIndex: .automatic, tagMergedIndex: .automatic, contents: CloudChatRemoveChatOperation(peerId: peerId, reportChatSpam: reportChatSpam, deleteGloballyIfPossible: deleteGloballyIfPossible, topMessageId: transaction.getTopPeerMessageId(peerId: peerId, namespace: Namespaces.Message.Cloud)))
|
||||
}
|
||||
|
||||
func cloudChatAddClearHistoryOperation(transaction: Transaction, peerId: PeerId, explicitTopMessageId: MessageId?) {
|
||||
func cloudChatAddClearHistoryOperation(transaction: Transaction, peerId: PeerId, explicitTopMessageId: MessageId?, type: InteractiveMessagesDeletionType) {
|
||||
let topMessageId: MessageId?
|
||||
if let explicitTopMessageId = explicitTopMessageId {
|
||||
topMessageId = explicitTopMessageId
|
||||
@ -121,6 +125,6 @@ func cloudChatAddClearHistoryOperation(transaction: Transaction, peerId: PeerId,
|
||||
topMessageId = transaction.getTopPeerMessageId(peerId: peerId, namespace: Namespaces.Message.Cloud)
|
||||
}
|
||||
if let topMessageId = topMessageId {
|
||||
transaction.operationLogAddEntry(peerId: peerId, tag: OperationLogTags.CloudChatRemoveMessages, tagLocalIndex: .automatic, tagMergedIndex: .automatic, contents: CloudChatClearHistoryOperation(peerId: peerId, topMessageId: topMessageId))
|
||||
transaction.operationLogAddEntry(peerId: peerId, tag: OperationLogTags.CloudChatRemoveMessages, tagLocalIndex: .automatic, tagMergedIndex: .automatic, contents: CloudChatClearHistoryOperation(peerId: peerId, topMessageId: topMessageId, type: type))
|
||||
}
|
||||
}
|
||||
|
||||
@ -9,9 +9,9 @@ import Foundation
|
||||
import MtProtoKitDynamic
|
||||
#endif
|
||||
|
||||
public enum InteractiveMessagesDeletionType {
|
||||
case forLocalPeer
|
||||
case forEveryone
|
||||
public enum InteractiveMessagesDeletionType: Int32 {
|
||||
case forLocalPeer = 0
|
||||
case forEveryone = 1
|
||||
}
|
||||
|
||||
public func deleteMessagesInteractively(postbox: Postbox, messageIds: [MessageId], type: InteractiveMessagesDeletionType) -> Signal<Void, NoError> {
|
||||
@ -57,21 +57,25 @@ public func deleteMessagesInteractively(postbox: Postbox, messageIds: [MessageId
|
||||
}
|
||||
}
|
||||
|
||||
public func clearHistoryInteractively(postbox: Postbox, peerId: PeerId) -> Signal<Void, NoError> {
|
||||
public func clearHistoryInteractively(postbox: Postbox, peerId: PeerId, type: InteractiveMessagesDeletionType) -> Signal<Void, NoError> {
|
||||
return postbox.transaction { transaction -> Void in
|
||||
if peerId.namespace == Namespaces.Peer.CloudUser || peerId.namespace == Namespaces.Peer.CloudGroup || peerId.namespace == Namespaces.Peer.CloudChannel {
|
||||
var topTimestamp: Int32?
|
||||
if let topIndex = transaction.getTopPeerMessageIndex(peerId: peerId, namespace: Namespaces.Message.Cloud) {
|
||||
topTimestamp = topIndex.timestamp
|
||||
cloudChatAddClearHistoryOperation(transaction: transaction, peerId: peerId, explicitTopMessageId: nil, type: type)
|
||||
var topIndex: MessageIndex?
|
||||
if let topMessageId = transaction.getTopPeerMessageId(peerId: peerId, namespace: Namespaces.Message.Cloud), let topMessage = transaction.getMessage(topMessageId) {
|
||||
topIndex = MessageIndex(topMessage)
|
||||
}
|
||||
cloudChatAddClearHistoryOperation(transaction: transaction, peerId: peerId, explicitTopMessageId: nil)
|
||||
clearHistory(transaction: transaction, mediaBox: postbox.mediaBox, peerId: peerId)
|
||||
if let cachedData = transaction.getPeerCachedData(peerId: peerId) as? CachedChannelData, let migrationReference = cachedData.migrationReference {
|
||||
cloudChatAddClearHistoryOperation(transaction: transaction, peerId: migrationReference.maxMessageId.peerId, explicitTopMessageId: MessageId(peerId: migrationReference.maxMessageId.peerId, namespace: migrationReference.maxMessageId.namespace, id: migrationReference.maxMessageId.id + 1))
|
||||
cloudChatAddClearHistoryOperation(transaction: transaction, peerId: migrationReference.maxMessageId.peerId, explicitTopMessageId: MessageId(peerId: migrationReference.maxMessageId.peerId, namespace: migrationReference.maxMessageId.namespace, id: migrationReference.maxMessageId.id + 1), type: type)
|
||||
clearHistory(transaction: transaction, mediaBox: postbox.mediaBox, peerId: migrationReference.maxMessageId.peerId)
|
||||
}
|
||||
if let topTimestamp = topTimestamp {
|
||||
updatePeerChatInclusionWithMinTimestamp(transaction: transaction, id: peerId, minTimestamp: topTimestamp)
|
||||
if let topIndex = topIndex {
|
||||
if peerId.namespace == Namespaces.Peer.CloudUser {
|
||||
let _ = transaction.addMessages([StoreMessage(id: topIndex.id, globallyUniqueId: nil, groupingKey: nil, timestamp: topIndex.timestamp, flags: StoreMessageFlags(), tags: [], globalTags: [], localTags: [], forwardInfo: nil, authorId: nil, text: "", attributes: [], media: [TelegramMediaAction(action: .historyCleared)])], location: .Random)
|
||||
} else {
|
||||
updatePeerChatInclusionWithMinTimestamp(transaction: transaction, id: peerId, minTimestamp: topIndex.timestamp)
|
||||
}
|
||||
}
|
||||
} else if peerId.namespace == Namespaces.Peer.SecretChat {
|
||||
clearHistory(transaction: transaction, mediaBox: postbox.mediaBox, peerId: peerId)
|
||||
|
||||
@ -6,6 +6,8 @@ import Foundation
|
||||
#endif
|
||||
|
||||
public struct LimitsConfiguration: Equatable, PreferencesEntry {
|
||||
public static let timeIntervalForever: Int32 = 0x7fffffff
|
||||
|
||||
public var maxGroupMemberCount: Int32
|
||||
public var maxSupergroupMemberCount: Int32
|
||||
public var maxMessageForwardBatchSize: Int32
|
||||
|
||||
@ -261,7 +261,7 @@ private func removeChat(transaction: Transaction, postbox: Postbox, network: Net
|
||||
}
|
||||
let deleteMessages: Signal<Void, NoError>
|
||||
if let inputPeer = apiInputPeer(peer), let topMessageId = operation.topMessageId ?? transaction.getTopPeerMessageId(peerId: peer.id, namespace: Namespaces.Message.Cloud) {
|
||||
deleteMessages = requestClearHistory(postbox: postbox, network: network, stateManager: stateManager, inputPeer: inputPeer, maxId: topMessageId.id, justClear: false)
|
||||
deleteMessages = requestClearHistory(postbox: postbox, network: network, stateManager: stateManager, inputPeer: inputPeer, maxId: topMessageId.id, justClear: false, type: operation.deleteGloballyIfPossible ? .forEveryone : .forLocalPeer)
|
||||
} else {
|
||||
deleteMessages = .complete()
|
||||
}
|
||||
@ -285,7 +285,7 @@ private func removeChat(transaction: Transaction, postbox: Postbox, network: Net
|
||||
} else {
|
||||
reportSignal = .complete()
|
||||
}
|
||||
return requestClearHistory(postbox: postbox, network: network, stateManager: stateManager, inputPeer: inputPeer, maxId: operation.topMessageId?.id ?? Int32.max - 1, justClear: false)
|
||||
return requestClearHistory(postbox: postbox, network: network, stateManager: stateManager, inputPeer: inputPeer, maxId: operation.topMessageId?.id ?? Int32.max - 1, justClear: false, type: operation.deleteGloballyIfPossible ? .forEveryone : .forLocalPeer)
|
||||
|> then(reportSignal)
|
||||
|> then(postbox.transaction { transaction -> Void in
|
||||
clearHistory(transaction: transaction, mediaBox: postbox.mediaBox, peerId: peer.id)
|
||||
@ -298,8 +298,15 @@ private func removeChat(transaction: Transaction, postbox: Postbox, network: Net
|
||||
}
|
||||
}
|
||||
|
||||
private func requestClearHistory(postbox: Postbox, network: Network, stateManager: AccountStateManager, inputPeer: Api.InputPeer, maxId: Int32, justClear: Bool) -> Signal<Void, NoError> {
|
||||
let signal = network.request(Api.functions.messages.deleteHistory(flags: justClear ? 1 : 0, peer: inputPeer, maxId: maxId))
|
||||
private func requestClearHistory(postbox: Postbox, network: Network, stateManager: AccountStateManager, inputPeer: Api.InputPeer, maxId: Int32, justClear: Bool, type: InteractiveMessagesDeletionType) -> Signal<Void, NoError> {
|
||||
var flags: Int32 = 0
|
||||
if justClear {
|
||||
flags |= 1 << 0
|
||||
}
|
||||
if case .forEveryone = type {
|
||||
flags |= 1 << 1
|
||||
}
|
||||
let signal = network.request(Api.functions.messages.deleteHistory(flags: flags, peer: inputPeer, maxId: maxId))
|
||||
|> map { result -> Api.messages.AffectedHistory? in
|
||||
return result
|
||||
}
|
||||
@ -330,7 +337,7 @@ private func requestClearHistory(postbox: Postbox, network: Network, stateManage
|
||||
private func clearHistory(transaction: Transaction, postbox: Postbox, network: Network, stateManager: AccountStateManager, peer: Peer, operation: CloudChatClearHistoryOperation) -> Signal<Void, NoError> {
|
||||
if peer.id.namespace == Namespaces.Peer.CloudGroup || peer.id.namespace == Namespaces.Peer.CloudUser {
|
||||
if let inputPeer = apiInputPeer(peer) {
|
||||
return requestClearHistory(postbox: postbox, network: network, stateManager: stateManager, inputPeer: inputPeer, maxId: operation.topMessageId.id, justClear: true)
|
||||
return requestClearHistory(postbox: postbox, network: network, stateManager: stateManager, inputPeer: inputPeer, maxId: operation.topMessageId.id, justClear: true, type: operation.type)
|
||||
} else {
|
||||
return .complete()
|
||||
}
|
||||
|
||||
@ -559,9 +559,6 @@ extension StoreMessage {
|
||||
case .messageEmpty:
|
||||
return nil
|
||||
case let .messageService(flags, id, fromId, toId, replyToMsgId, date, action):
|
||||
if case .messageActionHistoryClear = action {
|
||||
return nil
|
||||
}
|
||||
let peerId: PeerId
|
||||
var authorId: PeerId?
|
||||
switch toId {
|
||||
|
||||
@ -240,7 +240,7 @@ func telegramMediaActionFromApiAction(_ action: Api.MessageAction) -> TelegramMe
|
||||
return TelegramMediaAction(action: .channelMigratedFromGroup(title: title, groupId: PeerId(namespace: Namespaces.Peer.CloudGroup, id: chatId)))
|
||||
case let .messageActionChatAddUser(users):
|
||||
return TelegramMediaAction(action: .addedMembers(peerIds: users.map({ PeerId(namespace: Namespaces.Peer.CloudUser, id: $0) })))
|
||||
case let .messageActionChatCreate(title, userIds):
|
||||
case let .messageActionChatCreate(title, _):
|
||||
return TelegramMediaAction(action: .groupCreated(title: title))
|
||||
case .messageActionChatDeletePhoto:
|
||||
return TelegramMediaAction(action: .photoUpdated(image: nil))
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user