[WIP] Topics

This commit is contained in:
Ali 2022-10-20 02:44:34 +04:00
parent a645b57563
commit a6c4a2ac9b
20 changed files with 290 additions and 170 deletions

View File

@ -1258,7 +1258,7 @@ public final class ChatListSearchContainerNode: SearchDisplayControllerContentNo
attributes.append(ForwardOptionsMessageAttribute(hideNames: forwardOptions?.hideNames == true, hideCaptions: forwardOptions?.hideCaptions == true))
result.append(contentsOf: messageIds.map { messageId -> EnqueueMessage in
return .forward(source: messageId, grouping: .auto, attributes: attributes, correlationId: nil)
return .forward(source: messageId, threadId: nil, grouping: .auto, attributes: attributes, correlationId: nil)
})
var displayPeers: [EnginePeer] = []
@ -1320,7 +1320,7 @@ public final class ChatListSearchContainerNode: SearchDisplayControllerContentNo
(strongSelf.navigationController?.topViewController as? ViewController)?.present(UndoOverlayController(presentationData: presentationData, content: .forward(savedMessages: savedMessages, text: text), elevatedLayout: false, animateInAsReplacement: true, action: { _ in return false }), in: .current)
}
peerSelectionController.peerSelected = { [weak self, weak peerSelectionController] peer, _ in
peerSelectionController.peerSelected = { [weak self, weak peerSelectionController] peer, threadId in
let peerId = peer.id
if let strongSelf = self, let _ = peerSelectionController {
if peerId == strongSelf.context.account.peerId {
@ -1328,7 +1328,7 @@ public final class ChatListSearchContainerNode: SearchDisplayControllerContentNo
(strongSelf.navigationController?.topViewController as? ViewController)?.present(UndoOverlayController(presentationData: presentationData, content: .forward(savedMessages: true, text: messages.count == 1 ? presentationData.strings.Conversation_ForwardTooltip_SavedMessages_One : presentationData.strings.Conversation_ForwardTooltip_SavedMessages_Many), elevatedLayout: false, animateInAsReplacement: true, action: { _ in return false }), in: .window(.root))
let _ = (enqueueMessages(account: strongSelf.context.account, peerId: peerId, messages: messageIds.map { id -> EnqueueMessage in
return .forward(source: id, grouping: .auto, attributes: [], correlationId: nil)
return .forward(source: id, threadId: threadId, grouping: .auto, attributes: [], correlationId: nil)
})
|> deliverOnMainQueue).start(next: { [weak self] messageIds in
if let strongSelf = self {

View File

@ -188,6 +188,26 @@ final class MessageHistoryThreadHoleIndexTable: Table {
return result
}
func latest(peerId: PeerId, threadId: Int64, namespace: MessageId.Namespace, space: MessageHistoryHoleSpace) -> ClosedRange<MessageId.Id>? {
self.ensureInitialized(peerId: peerId, threadId: threadId)
var result: ClosedRange<MessageId.Id>?
self.valueBox.range(self.table, start: self.upperBound(peerId: peerId, threadId: threadId, namespace: namespace, space: space), end: self.lowerBound(peerId: peerId, threadId: threadId, namespace: namespace, space: space), values: { key, value in
let (keyThreadId, upperId, keySpace) = decomposeKey(key)
assert(keyThreadId == threadId)
assert(keySpace == space)
assert(upperId.peerId == peerId)
assert(upperId.namespace == namespace)
let lowerId = decodeValue(value: value, peerId: peerId, namespace: namespace)
result = lowerId.id ... upperId.id
return false
}, limit: 1)
return result
}
func closest(peerId: PeerId, threadId: Int64, namespace: MessageId.Namespace, space: MessageHistoryHoleSpace, range: ClosedRange<MessageId.Id>) -> IndexSet {
self.ensureInitialized(peerId: peerId, threadId: threadId)

View File

@ -112,6 +112,40 @@ class MessageHistoryThreadsTable: Table {
return maxIndex
}
func holeLowerBoundForTopValidRange(peerId: PeerId, threadId: Int64, namespace: MessageId.Namespace, space: MessageHistoryHoleSpace, holeIndexTable: MessageHistoryThreadHoleIndexTable) -> MessageId.Id {
let topHole = holeIndexTable.latest(peerId: peerId, threadId: threadId, namespace: namespace, space: space)
if let topHole = topHole {
let maxInHole = topHole.upperBound
var messageNotInHole: MessageId?
self.valueBox.range(self.table, start: self.upperBound(threadId: threadId, peerId: peerId, namespace: namespace), end: self.lowerBound(threadId: threadId, peerId: peerId, namespace: namespace), keys: { key in
let index = extractKey(key)
if index.id.id > maxInHole {
messageNotInHole = index.id
return false
}
return true
}, limit: 32000)
if let messageNotInHole = messageNotInHole {
return messageNotInHole.id + 1
} else {
return topHole.lowerBound
}
} else {
var messageNotInHole: MessageId?
self.valueBox.range(self.table, start: self.upperBound(threadId: threadId, peerId: peerId, namespace: namespace), end: self.lowerBound(threadId: threadId, peerId: peerId, namespace: namespace), keys: { key in
let index = extractKey(key)
messageNotInHole = index.id
return false
}, limit: 1)
if let messageNotInHole = messageNotInHole {
return messageNotInHole.id + 1
} else {
return 1
}
}
}
func getMessageCountInRange(threadId: Int64, peerId: PeerId, namespace: MessageId.Namespace, lowerBound: MessageIndex?, upperBound: MessageIndex?) -> Int {
if let lowerBound = lowerBound {
precondition(lowerBound.id.namespace == namespace)

View File

@ -1163,6 +1163,11 @@ public final class Transaction {
return self.postbox!.messageHistoryThreadsTable.getTop(peerId: peerId, threadId: threadId, namespaces: namespaces)
}
public func holeLowerBoundForTopValidRange(peerId: PeerId, threadId: Int64, namespace: MessageId.Namespace, space: MessageHistoryHoleSpace) -> MessageId.Id {
assert(!self.disposed)
return self.postbox!.messageHistoryThreadsTable.holeLowerBoundForTopValidRange(peerId: peerId, threadId: threadId, namespace: namespace, space: space, holeIndexTable: self.postbox!.messageHistoryThreadHoleIndexTable)
}
public func getMessageHistoryThreadInfo(peerId: PeerId, threadId: Int64) -> StoredMessageHistoryThreadInfo? {
assert(!self.disposed)
return self.postbox!.messageHistoryThreadIndexTable.get(peerId: peerId, threadId: threadId)

View File

@ -678,8 +678,10 @@ public final class ShareController: ViewController {
case let .messages(messages):
for peerId in peerIds {
var replyToMessageId: MessageId?
var threadId: Int64?
if let topicId = topicIds[peerId] {
replyToMessageId = MessageId(peerId: peerId, namespace: Namespaces.Message.Cloud, id: Int32(clamping: topicId))
threadId = topicId
}
var messagesToEnqueue: [EnqueueMessage] = []
@ -687,7 +689,7 @@ public final class ShareController: ViewController {
messagesToEnqueue.append(.message(text: text, attributes: [], inlineStickers: [:], mediaReference: nil, replyToMessageId: replyToMessageId, localGroupingKey: nil, correlationId: nil, bubbleUpEmojiOrStickersets: []))
}
for message in messages {
messagesToEnqueue.append(.forward(source: message.id, grouping: .auto, attributes: [], correlationId: nil))
messagesToEnqueue.append(.forward(source: message.id, threadId: threadId, grouping: .auto, attributes: [], correlationId: nil))
}
messagesToEnqueue = transformMessages(messagesToEnqueue, showNames: showNames, silently: silently)
shareSignals.append(enqueueMessages(account: strongSelf.currentAccount, peerId: peerId, messages: messagesToEnqueue))

View File

@ -1045,7 +1045,8 @@ fileprivate let parsers: [Int32 : (BufferReader) -> Any?] = {
dict[1404185519] = { return Api.messages.SearchResultsPositions.parse_searchResultsPositions($0) }
dict[-1802240206] = { return Api.messages.SentEncryptedMessage.parse_sentEncryptedFile($0) }
dict[1443858741] = { return Api.messages.SentEncryptedMessage.parse_sentEncryptedMessage($0) }
dict[1705297877] = { return Api.messages.SponsoredMessages.parse_sponsoredMessages($0) }
dict[-907141753] = { return Api.messages.SponsoredMessages.parse_sponsoredMessages($0) }
dict[406407439] = { return Api.messages.SponsoredMessages.parse_sponsoredMessagesEmpty($0) }
dict[1846886166] = { return Api.messages.StickerSet.parse_stickerSet($0) }
dict[-738646805] = { return Api.messages.StickerSet.parse_stickerSetNotModified($0) }
dict[904138920] = { return Api.messages.StickerSetInstallResult.parse_stickerSetInstallResultArchive($0) }

View File

@ -576,14 +576,17 @@ public extension Api.messages {
}
public extension Api.messages {
enum SponsoredMessages: TypeConstructorDescription {
case sponsoredMessages(messages: [Api.SponsoredMessage], chats: [Api.Chat], users: [Api.User])
case sponsoredMessages(flags: Int32, postsBetween: Int32?, messages: [Api.SponsoredMessage], chats: [Api.Chat], users: [Api.User])
case sponsoredMessagesEmpty
public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
switch self {
case .sponsoredMessages(let messages, let chats, let users):
case .sponsoredMessages(let flags, let postsBetween, let messages, let chats, let users):
if boxed {
buffer.appendInt32(1705297877)
buffer.appendInt32(-907141753)
}
serializeInt32(flags, buffer: buffer, boxed: false)
if Int(flags) & Int(1 << 0) != 0 {serializeInt32(postsBetween!, buffer: buffer, boxed: false)}
buffer.appendInt32(481674261)
buffer.appendInt32(Int32(messages.count))
for item in messages {
@ -599,40 +602,57 @@ public extension Api.messages {
for item in users {
item.serialize(buffer, true)
}
break
case .sponsoredMessagesEmpty:
if boxed {
buffer.appendInt32(406407439)
}
break
}
}
public func descriptionFields() -> (String, [(String, Any)]) {
switch self {
case .sponsoredMessages(let messages, let chats, let users):
return ("sponsoredMessages", [("messages", String(describing: messages)), ("chats", String(describing: chats)), ("users", String(describing: users))])
case .sponsoredMessages(let flags, let postsBetween, let messages, let chats, let users):
return ("sponsoredMessages", [("flags", String(describing: flags)), ("postsBetween", String(describing: postsBetween)), ("messages", String(describing: messages)), ("chats", String(describing: chats)), ("users", String(describing: users))])
case .sponsoredMessagesEmpty:
return ("sponsoredMessagesEmpty", [])
}
}
public static func parse_sponsoredMessages(_ reader: BufferReader) -> SponsoredMessages? {
var _1: [Api.SponsoredMessage]?
var _1: Int32?
_1 = reader.readInt32()
var _2: Int32?
if Int(_1!) & Int(1 << 0) != 0 {_2 = reader.readInt32() }
var _3: [Api.SponsoredMessage]?
if let _ = reader.readInt32() {
_1 = Api.parseVector(reader, elementSignature: 0, elementType: Api.SponsoredMessage.self)
_3 = Api.parseVector(reader, elementSignature: 0, elementType: Api.SponsoredMessage.self)
}
var _2: [Api.Chat]?
var _4: [Api.Chat]?
if let _ = reader.readInt32() {
_2 = Api.parseVector(reader, elementSignature: 0, elementType: Api.Chat.self)
_4 = Api.parseVector(reader, elementSignature: 0, elementType: Api.Chat.self)
}
var _3: [Api.User]?
var _5: [Api.User]?
if let _ = reader.readInt32() {
_3 = Api.parseVector(reader, elementSignature: 0, elementType: Api.User.self)
_5 = Api.parseVector(reader, elementSignature: 0, elementType: Api.User.self)
}
let _c1 = _1 != nil
let _c2 = _2 != nil
let _c2 = (Int(_1!) & Int(1 << 0) == 0) || _2 != nil
let _c3 = _3 != nil
if _c1 && _c2 && _c3 {
return Api.messages.SponsoredMessages.sponsoredMessages(messages: _1!, chats: _2!, users: _3!)
let _c4 = _4 != nil
let _c5 = _5 != nil
if _c1 && _c2 && _c3 && _c4 && _c5 {
return Api.messages.SponsoredMessages.sponsoredMessages(flags: _1!, postsBetween: _2, messages: _3!, chats: _4!, users: _5!)
}
else {
return nil
}
}
public static func parse_sponsoredMessagesEmpty(_ reader: BufferReader) -> SponsoredMessages? {
return Api.messages.SponsoredMessages.sponsoredMessagesEmpty
}
}
}
@ -1390,53 +1410,3 @@ public extension Api.payments {
}
}
public extension Api.payments {
enum ValidatedRequestedInfo: TypeConstructorDescription {
case validatedRequestedInfo(flags: Int32, id: String?, shippingOptions: [Api.ShippingOption]?)
public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
switch self {
case .validatedRequestedInfo(let flags, let id, let shippingOptions):
if boxed {
buffer.appendInt32(-784000893)
}
serializeInt32(flags, buffer: buffer, boxed: false)
if Int(flags) & Int(1 << 0) != 0 {serializeString(id!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 1) != 0 {buffer.appendInt32(481674261)
buffer.appendInt32(Int32(shippingOptions!.count))
for item in shippingOptions! {
item.serialize(buffer, true)
}}
break
}
}
public func descriptionFields() -> (String, [(String, Any)]) {
switch self {
case .validatedRequestedInfo(let flags, let id, let shippingOptions):
return ("validatedRequestedInfo", [("flags", String(describing: flags)), ("id", String(describing: id)), ("shippingOptions", String(describing: shippingOptions))])
}
}
public static func parse_validatedRequestedInfo(_ reader: BufferReader) -> ValidatedRequestedInfo? {
var _1: Int32?
_1 = reader.readInt32()
var _2: String?
if Int(_1!) & Int(1 << 0) != 0 {_2 = parseString(reader) }
var _3: [Api.ShippingOption]?
if Int(_1!) & Int(1 << 1) != 0 {if let _ = reader.readInt32() {
_3 = Api.parseVector(reader, elementSignature: 0, elementType: Api.ShippingOption.self)
} }
let _c1 = _1 != nil
let _c2 = (Int(_1!) & Int(1 << 0) == 0) || _2 != nil
let _c3 = (Int(_1!) & Int(1 << 1) == 0) || _3 != nil
if _c1 && _c2 && _c3 {
return Api.payments.ValidatedRequestedInfo.validatedRequestedInfo(flags: _1!, id: _2, shippingOptions: _3)
}
else {
return nil
}
}
}
}

View File

@ -1,3 +1,53 @@
public extension Api.payments {
enum ValidatedRequestedInfo: TypeConstructorDescription {
case validatedRequestedInfo(flags: Int32, id: String?, shippingOptions: [Api.ShippingOption]?)
public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
switch self {
case .validatedRequestedInfo(let flags, let id, let shippingOptions):
if boxed {
buffer.appendInt32(-784000893)
}
serializeInt32(flags, buffer: buffer, boxed: false)
if Int(flags) & Int(1 << 0) != 0 {serializeString(id!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 1) != 0 {buffer.appendInt32(481674261)
buffer.appendInt32(Int32(shippingOptions!.count))
for item in shippingOptions! {
item.serialize(buffer, true)
}}
break
}
}
public func descriptionFields() -> (String, [(String, Any)]) {
switch self {
case .validatedRequestedInfo(let flags, let id, let shippingOptions):
return ("validatedRequestedInfo", [("flags", String(describing: flags)), ("id", String(describing: id)), ("shippingOptions", String(describing: shippingOptions))])
}
}
public static func parse_validatedRequestedInfo(_ reader: BufferReader) -> ValidatedRequestedInfo? {
var _1: Int32?
_1 = reader.readInt32()
var _2: String?
if Int(_1!) & Int(1 << 0) != 0 {_2 = parseString(reader) }
var _3: [Api.ShippingOption]?
if Int(_1!) & Int(1 << 1) != 0 {if let _ = reader.readInt32() {
_3 = Api.parseVector(reader, elementSignature: 0, elementType: Api.ShippingOption.self)
} }
let _c1 = _1 != nil
let _c2 = (Int(_1!) & Int(1 << 0) == 0) || _2 != nil
let _c3 = (Int(_1!) & Int(1 << 1) == 0) || _3 != nil
if _c1 && _c2 && _c3 {
return Api.payments.ValidatedRequestedInfo.validatedRequestedInfo(flags: _1!, id: _2, shippingOptions: _3)
}
else {
return nil
}
}
}
}
public extension Api.phone {
enum ExportedGroupCallInvite: TypeConstructorDescription {
case exportedGroupCallInvite(link: String)
@ -1374,55 +1424,3 @@ public extension Api.updates {
}
}
public extension Api.updates {
enum State: TypeConstructorDescription {
case state(pts: Int32, qts: Int32, date: Int32, seq: Int32, unreadCount: Int32)
public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
switch self {
case .state(let pts, let qts, let date, let seq, let unreadCount):
if boxed {
buffer.appendInt32(-1519637954)
}
serializeInt32(pts, buffer: buffer, boxed: false)
serializeInt32(qts, buffer: buffer, boxed: false)
serializeInt32(date, buffer: buffer, boxed: false)
serializeInt32(seq, buffer: buffer, boxed: false)
serializeInt32(unreadCount, buffer: buffer, boxed: false)
break
}
}
public func descriptionFields() -> (String, [(String, Any)]) {
switch self {
case .state(let pts, let qts, let date, let seq, let unreadCount):
return ("state", [("pts", String(describing: pts)), ("qts", String(describing: qts)), ("date", String(describing: date)), ("seq", String(describing: seq)), ("unreadCount", String(describing: unreadCount))])
}
}
public static func parse_state(_ reader: BufferReader) -> State? {
var _1: Int32?
_1 = reader.readInt32()
var _2: Int32?
_2 = reader.readInt32()
var _3: Int32?
_3 = reader.readInt32()
var _4: Int32?
_4 = reader.readInt32()
var _5: Int32?
_5 = reader.readInt32()
let _c1 = _1 != nil
let _c2 = _2 != nil
let _c3 = _3 != nil
let _c4 = _4 != nil
let _c5 = _5 != nil
if _c1 && _c2 && _c3 && _c4 && _c5 {
return Api.updates.State.state(pts: _1!, qts: _2!, date: _3!, seq: _4!, unreadCount: _5!)
}
else {
return nil
}
}
}
}

View File

@ -1,3 +1,55 @@
public extension Api.updates {
enum State: TypeConstructorDescription {
case state(pts: Int32, qts: Int32, date: Int32, seq: Int32, unreadCount: Int32)
public func serialize(_ buffer: Buffer, _ boxed: Swift.Bool) {
switch self {
case .state(let pts, let qts, let date, let seq, let unreadCount):
if boxed {
buffer.appendInt32(-1519637954)
}
serializeInt32(pts, buffer: buffer, boxed: false)
serializeInt32(qts, buffer: buffer, boxed: false)
serializeInt32(date, buffer: buffer, boxed: false)
serializeInt32(seq, buffer: buffer, boxed: false)
serializeInt32(unreadCount, buffer: buffer, boxed: false)
break
}
}
public func descriptionFields() -> (String, [(String, Any)]) {
switch self {
case .state(let pts, let qts, let date, let seq, let unreadCount):
return ("state", [("pts", String(describing: pts)), ("qts", String(describing: qts)), ("date", String(describing: date)), ("seq", String(describing: seq)), ("unreadCount", String(describing: unreadCount))])
}
}
public static func parse_state(_ reader: BufferReader) -> State? {
var _1: Int32?
_1 = reader.readInt32()
var _2: Int32?
_2 = reader.readInt32()
var _3: Int32?
_3 = reader.readInt32()
var _4: Int32?
_4 = reader.readInt32()
var _5: Int32?
_5 = reader.readInt32()
let _c1 = _1 != nil
let _c2 = _2 != nil
let _c3 = _3 != nil
let _c4 = _4 != nil
let _c5 = _5 != nil
if _c1 && _c2 && _c3 && _c4 && _c5 {
return Api.updates.State.state(pts: _1!, qts: _2!, date: _3!, seq: _4!, unreadCount: _5!)
}
else {
return nil
}
}
}
}
public extension Api.upload {
enum CdnFile: TypeConstructorDescription {
case cdnFile(bytes: Buffer)

View File

@ -4015,9 +4015,9 @@ public extension Api.functions.messages {
}
}
public extension Api.functions.messages {
static func forwardMessages(flags: Int32, fromPeer: Api.InputPeer, id: [Int32], randomId: [Int64], toPeer: Api.InputPeer, scheduleDate: Int32?, sendAs: Api.InputPeer?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse<Api.Updates>) {
static func forwardMessages(flags: Int32, fromPeer: Api.InputPeer, id: [Int32], randomId: [Int64], toPeer: Api.InputPeer, topMsgId: Int32?, scheduleDate: Int32?, sendAs: Api.InputPeer?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse<Api.Updates>) {
let buffer = Buffer()
buffer.appendInt32(-869258997)
buffer.appendInt32(-966673468)
serializeInt32(flags, buffer: buffer, boxed: false)
fromPeer.serialize(buffer, true)
buffer.appendInt32(481674261)
@ -4031,9 +4031,10 @@ public extension Api.functions.messages {
serializeInt64(item, buffer: buffer, boxed: false)
}
toPeer.serialize(buffer, true)
if Int(flags) & Int(1 << 9) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 10) != 0 {serializeInt32(scheduleDate!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 13) != 0 {sendAs!.serialize(buffer, true)}
return (FunctionDescription(name: "messages.forwardMessages", parameters: [("flags", String(describing: flags)), ("fromPeer", String(describing: fromPeer)), ("id", String(describing: id)), ("randomId", String(describing: randomId)), ("toPeer", String(describing: toPeer)), ("scheduleDate", String(describing: scheduleDate)), ("sendAs", String(describing: sendAs))]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.Updates? in
return (FunctionDescription(name: "messages.forwardMessages", parameters: [("flags", String(describing: flags)), ("fromPeer", String(describing: fromPeer)), ("id", String(describing: id)), ("randomId", String(describing: randomId)), ("toPeer", String(describing: toPeer)), ("topMsgId", String(describing: topMsgId)), ("scheduleDate", String(describing: scheduleDate)), ("sendAs", String(describing: sendAs))]), buffer, DeserializeFunctionResponse { (buffer: Buffer) -> Api.Updates? in
let reader = BufferReader(buffer)
var result: Api.Updates?
if let signature = reader.readInt32() {
@ -5955,11 +5956,11 @@ public extension Api.functions.messages {
public extension Api.functions.messages {
static func sendInlineBotResult(flags: Int32, peer: Api.InputPeer, replyToMsgId: Int32?, topMsgId: Int32?, randomId: Int64, queryId: Int64, id: String, scheduleDate: Int32?, sendAs: Api.InputPeer?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse<Api.Updates>) {
let buffer = Buffer()
buffer.appendInt32(363928691)
buffer.appendInt32(-738468661)
serializeInt32(flags, buffer: buffer, boxed: false)
peer.serialize(buffer, true)
if Int(flags) & Int(1 << 0) != 0 {serializeInt32(replyToMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 8) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 9) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
serializeInt64(randomId, buffer: buffer, boxed: false)
serializeInt64(queryId, buffer: buffer, boxed: false)
serializeString(id, buffer: buffer, boxed: false)
@ -5978,11 +5979,11 @@ public extension Api.functions.messages {
public extension Api.functions.messages {
static func sendMedia(flags: Int32, peer: Api.InputPeer, replyToMsgId: Int32?, topMsgId: Int32?, media: Api.InputMedia, message: String, randomId: Int64, replyMarkup: Api.ReplyMarkup?, entities: [Api.MessageEntity]?, scheduleDate: Int32?, sendAs: Api.InputPeer?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse<Api.Updates>) {
let buffer = Buffer()
buffer.appendInt32(-1561796130)
buffer.appendInt32(1967638886)
serializeInt32(flags, buffer: buffer, boxed: false)
peer.serialize(buffer, true)
if Int(flags) & Int(1 << 0) != 0 {serializeInt32(replyToMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 8) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 9) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
media.serialize(buffer, true)
serializeString(message, buffer: buffer, boxed: false)
serializeInt64(randomId, buffer: buffer, boxed: false)
@ -6007,11 +6008,11 @@ public extension Api.functions.messages {
public extension Api.functions.messages {
static func sendMessage(flags: Int32, peer: Api.InputPeer, replyToMsgId: Int32?, topMsgId: Int32?, message: String, randomId: Int64, replyMarkup: Api.ReplyMarkup?, entities: [Api.MessageEntity]?, scheduleDate: Int32?, sendAs: Api.InputPeer?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse<Api.Updates>) {
let buffer = Buffer()
buffer.appendInt32(1684017487)
buffer.appendInt32(482476935)
serializeInt32(flags, buffer: buffer, boxed: false)
peer.serialize(buffer, true)
if Int(flags) & Int(1 << 0) != 0 {serializeInt32(replyToMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 8) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 9) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
serializeString(message, buffer: buffer, boxed: false)
serializeInt64(randomId, buffer: buffer, boxed: false)
if Int(flags) & Int(1 << 2) != 0 {replyMarkup!.serialize(buffer, true)}
@ -6035,11 +6036,11 @@ public extension Api.functions.messages {
public extension Api.functions.messages {
static func sendMultiMedia(flags: Int32, peer: Api.InputPeer, replyToMsgId: Int32?, topMsgId: Int32?, multiMedia: [Api.InputSingleMedia], scheduleDate: Int32?, sendAs: Api.InputPeer?) -> (FunctionDescription, Buffer, DeserializeFunctionResponse<Api.Updates>) {
let buffer = Buffer()
buffer.appendInt32(1749432857)
buffer.appendInt32(-1225713124)
serializeInt32(flags, buffer: buffer, boxed: false)
peer.serialize(buffer, true)
if Int(flags) & Int(1 << 0) != 0 {serializeInt32(replyToMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 8) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
if Int(flags) & Int(1 << 9) != 0 {serializeInt32(topMsgId!, buffer: buffer, boxed: false)}
buffer.appendInt32(481674261)
buffer.appendInt32(Int32(multiMedia.count))
for item in multiMedia {

View File

@ -10,7 +10,7 @@ public enum EnqueueMessageGrouping {
public enum EnqueueMessage {
case message(text: String, attributes: [MessageAttribute], inlineStickers: [MediaId: Media], mediaReference: AnyMediaReference?, replyToMessageId: MessageId?, localGroupingKey: Int64?, correlationId: Int64?, bubbleUpEmojiOrStickersets: [ItemCollectionId])
case forward(source: MessageId, grouping: EnqueueMessageGrouping, attributes: [MessageAttribute], correlationId: Int64?)
case forward(source: MessageId, threadId: Int64?, grouping: EnqueueMessageGrouping, attributes: [MessageAttribute], correlationId: Int64?)
public func withUpdatedReplyToMessageId(_ replyToMessageId: MessageId?) -> EnqueueMessage {
switch self {
@ -25,8 +25,8 @@ public enum EnqueueMessage {
switch self {
case let .message(text, attributes, inlineStickers, mediaReference, replyToMessageId, localGroupingKey, correlationId, bubbleUpEmojiOrStickersets):
return .message(text: text, attributes: f(attributes), inlineStickers: inlineStickers, mediaReference: mediaReference, replyToMessageId: replyToMessageId, localGroupingKey: localGroupingKey, correlationId: correlationId, bubbleUpEmojiOrStickersets: bubbleUpEmojiOrStickersets)
case let .forward(source, grouping, attributes, correlationId):
return .forward(source: source, grouping: grouping, attributes: f(attributes), correlationId: correlationId)
case let .forward(source, threadId, grouping, attributes, correlationId):
return .forward(source: source, threadId: threadId, grouping: grouping, attributes: f(attributes), correlationId: correlationId)
}
}
@ -43,8 +43,8 @@ public enum EnqueueMessage {
switch self {
case let .message(text, attributes, inlineStickers, mediaReference, replyToMessageId, localGroupingKey, _, bubbleUpEmojiOrStickersets):
return .message(text: text, attributes: attributes, inlineStickers: inlineStickers, mediaReference: mediaReference, replyToMessageId: replyToMessageId, localGroupingKey: localGroupingKey, correlationId: value, bubbleUpEmojiOrStickersets: bubbleUpEmojiOrStickersets)
case let .forward(source, grouping, attributes, _):
return .forward(source: source, grouping: grouping, attributes: attributes, correlationId: value)
case let .forward(source, threadId, grouping, attributes, _):
return .forward(source: source, threadId: threadId, grouping: grouping, attributes: attributes, correlationId: value)
}
}
@ -62,7 +62,7 @@ private extension EnqueueMessage {
switch self {
case let .message(_, _, _, _, _, _, correlationId, _):
return correlationId
case let .forward(_, _, _, correlationId):
case let .forward(_, _, _, _, correlationId):
return correlationId
}
}
@ -298,7 +298,7 @@ public func resendMessages(account: Account, messageIds: [MessageId]) -> Signal<
func enqueueMessages(transaction: Transaction, account: Account, peerId: PeerId, messages: [(Bool, EnqueueMessage)], disableAutoremove: Bool = false, transformGroupingKeysWithPeerId: Bool = false) -> [MessageId?] {
var forwardedMessageIds = Set<MessageId>()
for (_, message) in messages {
if case let .forward(sourceId, _, _, _) = message {
if case let .forward(sourceId, _, _, _, _) = message {
forwardedMessageIds.insert(sourceId)
}
}
@ -329,10 +329,10 @@ func enqueueMessages(transaction: Transaction, account: Account, peerId: PeerId,
}
}
if canBeForwarded {
updatedMessages.append((true, .forward(source: replyToMessageId, grouping: .none, attributes: attributes, correlationId: nil)))
updatedMessages.append((true, .forward(source: replyToMessageId, threadId: nil, grouping: .none, attributes: attributes, correlationId: nil)))
}
}
case let .forward(sourceId, _, _, _):
case let .forward(sourceId, threadId, _, _, _):
if let sourceMessage = forwardedMessageToBeReuploaded(transaction: transaction, id: sourceId) {
var mediaReference: AnyMediaReference?
if sourceMessage.id.peerId.namespace == Namespaces.Peer.SecretChat {
@ -340,7 +340,7 @@ func enqueueMessages(transaction: Transaction, account: Account, peerId: PeerId,
mediaReference = .standalone(media: media)
}
}
updatedMessages.append((transformedMedia, .message(text: sourceMessage.text, attributes: sourceMessage.attributes, inlineStickers: [:], mediaReference: mediaReference, replyToMessageId: nil, localGroupingKey: nil, correlationId: nil, bubbleUpEmojiOrStickersets: [])))
updatedMessages.append((transformedMedia, .message(text: sourceMessage.text, attributes: sourceMessage.attributes, inlineStickers: [:], mediaReference: mediaReference, replyToMessageId: threadId.flatMap { MessageId(peerId: peerId, namespace: Namespaces.Message.Cloud, id: Int32(clamping: $0)) }, localGroupingKey: nil, correlationId: nil, bubbleUpEmojiOrStickersets: [])))
continue outer
}
}
@ -571,7 +571,7 @@ func enqueueMessages(transaction: Transaction, account: Account, peerId: PeerId,
}
storeMessages.append(StoreMessage(peerId: peerId, namespace: messageNamespace, globallyUniqueId: randomId, groupingKey: localGroupingKey, threadId: threadId, timestamp: effectiveTimestamp, flags: flags, tags: tags, globalTags: globalTags, localTags: localTags, forwardInfo: nil, authorId: authorId, text: text, attributes: attributes, media: mediaList))
case let .forward(source, grouping, requestedAttributes, _):
case let .forward(source, threadId, grouping, requestedAttributes, _):
let sourceMessage = transaction.getMessage(source)
if let sourceMessage = sourceMessage, let author = sourceMessage.author ?? sourceMessage.peers[sourceMessage.id.peerId] {
var messageText = sourceMessage.text
@ -731,7 +731,7 @@ func enqueueMessages(transaction: Transaction, account: Account, peerId: PeerId,
var entitiesAttribute: TextEntitiesMessageAttribute?
var effectiveTimestamp = timestamp
var sendAsPeer: Peer?
var threadId: Int64?
var threadId: Int64? = threadId
for attribute in attributes {
if let attribute = attribute as? TextEntitiesMessageAttribute {
entitiesAttribute = attribute

View File

@ -2661,6 +2661,7 @@ private func pollChannel(postbox: Postbox, network: Network, peer: Peer, state:
updatedState.mergeUsers(users)
updatedState.setNeedsHoleFromPreviousState(peerId: peer.peerId, namespace: Namespaces.Message.Cloud, validateChannelPts: pts)
updatedState.resetForumTopicLists[peer.peerId] = []
for apiMessage in messages {
if var message = StoreMessage(apiMessage: apiMessage) {
@ -4029,6 +4030,20 @@ func replayFinalState(
Logger.shared.log("State", "not adding hole for peer \(messageId.peerId), \(upperId) >= \(messageId.id) = false")
}
}
for (peerId, _) in finalState.state.resetForumTopicLists {
for item in transaction.getMessageHistoryThreadIndex(peerId: peerId, limit: 10000) {
let holeLowerBound = transaction.holeLowerBoundForTopValidRange(peerId: peerId, threadId: item.threadId, namespace: Namespaces.Message.Cloud, space: .everywhere)
transaction.addHole(peerId: peerId, threadId: item.threadId, namespace: Namespaces.Message.Cloud, space: .everywhere, range: holeLowerBound ... (Int32.max - 1))
for tag in MessageTags.all {
transaction.addHole(peerId: peerId, threadId: item.threadId, namespace: Namespaces.Message.Cloud, space: .tag(tag), range: holeLowerBound ... (Int32.max - 1))
}
}
transaction.setPeerThreadCombinedState(peerId: peerId, state: nil)
}
//TODO Please do not forget fix holes space.
// could be the reason for unbounded slowdown, needs investigation

View File

@ -1512,7 +1512,7 @@ public final class AccountViewTracker {
}
}
func wrappedMessageHistorySignal(chatLocation: ChatLocationInput, signal: Signal<(MessageHistoryView, ViewUpdateType, InitialMessageHistoryData?), NoError>, addHoleIfNeeded: Bool) -> Signal<(MessageHistoryView, ViewUpdateType, InitialMessageHistoryData?), NoError> {
func wrappedMessageHistorySignal(chatLocation: ChatLocationInput, signal: Signal<(MessageHistoryView, ViewUpdateType, InitialMessageHistoryData?), NoError>, fixedCombinedReadStates: MessageHistoryViewReadState?, addHoleIfNeeded: Bool) -> Signal<(MessageHistoryView, ViewUpdateType, InitialMessageHistoryData?), NoError> {
var signal = signal
if let postbox = self.account?.postbox, let peerId = chatLocation.peerId, let threadId = chatLocation.threadId {
let viewKey: PostboxViewKey = .messageHistoryThreadInfo(peerId: peerId, threadId: threadId)
@ -1523,11 +1523,16 @@ public final class AccountViewTracker {
if let threadInfo = additionalViews.views[viewKey] as? MessageHistoryThreadInfoView, let data = threadInfo.info?.data.get(MessageHistoryThreadData.self) {
let readState = CombinedPeerReadState(states: [(Namespaces.Message.Cloud, .idBased(maxIncomingReadId: data.maxIncomingReadId, maxOutgoingReadId: data.maxOutgoingReadId, maxKnownId: data.maxKnownMessageId, count: data.incomingUnreadCount, markedUnread: false))])
let fixed = fixedReadStates.modify { current in
if let current = current {
return current
} else {
return .peer([peerId: readState])
let fixed: MessageHistoryViewReadState?
if let fixedCombinedReadStates = fixedCombinedReadStates {
fixed = fixedCombinedReadStates
} else {
fixed = fixedReadStates.modify { current in
if let current = current {
return current
} else {
return .peer([peerId: readState])
}
}
}
@ -1733,7 +1738,7 @@ public final class AccountViewTracker {
} else {
signal = account.postbox.aroundMessageOfInterestHistoryViewForChatLocation(chatLocation, ignoreMessagesInTimestampRange: ignoreMessagesInTimestampRange, count: count, topTaggedMessageIdNamespaces: [Namespaces.Message.Cloud], tagMask: tagMask, appendMessagesFromTheSameGroup: appendMessagesFromTheSameGroup, namespaces: .not(Namespaces.Message.allScheduled), orderStatistics: orderStatistics, customUnreadMessageId: nil, additionalData: wrappedHistoryViewAdditionalData(chatLocation: chatLocation, additionalData: additionalData))
}
return wrappedMessageHistorySignal(chatLocation: chatLocation, signal: signal, addHoleIfNeeded: true)
return wrappedMessageHistorySignal(chatLocation: chatLocation, signal: signal, fixedCombinedReadStates: nil, addHoleIfNeeded: true)
} else {
return .never()
}
@ -1742,7 +1747,7 @@ public final class AccountViewTracker {
public func aroundIdMessageHistoryViewForLocation(_ chatLocation: ChatLocationInput, ignoreMessagesInTimestampRange: ClosedRange<Int32>? = nil, count: Int, ignoreRelatedChats: Bool, messageId: MessageId, tagMask: MessageTags? = nil, appendMessagesFromTheSameGroup: Bool = false, orderStatistics: MessageHistoryViewOrderStatistics = [], additionalData: [AdditionalMessageHistoryViewData] = []) -> Signal<(MessageHistoryView, ViewUpdateType, InitialMessageHistoryData?), NoError> {
if let account = self.account {
let signal = account.postbox.aroundIdMessageHistoryViewForLocation(chatLocation, ignoreMessagesInTimestampRange: ignoreMessagesInTimestampRange, count: count, ignoreRelatedChats: ignoreRelatedChats, messageId: messageId, topTaggedMessageIdNamespaces: [Namespaces.Message.Cloud], tagMask: tagMask, appendMessagesFromTheSameGroup: appendMessagesFromTheSameGroup, namespaces: .not(Namespaces.Message.allScheduled), orderStatistics: orderStatistics, additionalData: wrappedHistoryViewAdditionalData(chatLocation: chatLocation, additionalData: additionalData))
return wrappedMessageHistorySignal(chatLocation: chatLocation, signal: signal, addHoleIfNeeded: false)
return wrappedMessageHistorySignal(chatLocation: chatLocation, signal: signal, fixedCombinedReadStates: nil, addHoleIfNeeded: false)
} else {
return .never()
}
@ -1760,7 +1765,7 @@ public final class AccountViewTracker {
inputAnchor = .index(index)
}
let signal = account.postbox.aroundMessageHistoryViewForLocation(chatLocation, anchor: inputAnchor, ignoreMessagesInTimestampRange: ignoreMessagesInTimestampRange, count: count, clipHoles: clipHoles, ignoreRelatedChats: ignoreRelatedChats, fixedCombinedReadStates: fixedCombinedReadStates, topTaggedMessageIdNamespaces: [Namespaces.Message.Cloud], tagMask: tagMask, appendMessagesFromTheSameGroup: appendMessagesFromTheSameGroup, namespaces: .not(Namespaces.Message.allScheduled), orderStatistics: orderStatistics, additionalData: wrappedHistoryViewAdditionalData(chatLocation: chatLocation, additionalData: additionalData))
return wrappedMessageHistorySignal(chatLocation: chatLocation, signal: signal, addHoleIfNeeded: false)
return wrappedMessageHistorySignal(chatLocation: chatLocation, signal: signal, fixedCombinedReadStates: fixedCombinedReadStates, addHoleIfNeeded: false)
} else {
return .never()
}

View File

@ -737,7 +737,7 @@ public final class PendingMessageManager {
let sendMessageRequest: Signal<Api.Updates, MTRpcError>
if isForward {
if messages.contains(where: { $0.0.groupingKey != nil }) {
flags |= (1 << 9)
flags |= (1 << 8)
}
if hideSendersNames {
flags |= (1 << 11)
@ -774,6 +774,13 @@ public final class PendingMessageManager {
return .complete()
}
}
var topMsgId: Int32?
if let threadId = messages[0].0.threadId {
flags |= Int32(1 << 9)
topMsgId = Int32(clamping: threadId)
}
let forwardPeerIds = Set(forwardIds.map { $0.0.peerId })
if forwardPeerIds.count != 1 {
assertionFailure()
@ -781,7 +788,7 @@ public final class PendingMessageManager {
} else if let inputSourcePeerId = forwardPeerIds.first, let inputSourcePeer = transaction.getPeer(inputSourcePeerId).flatMap(apiInputPeer) {
let dependencyTag = PendingMessageRequestDependencyTag(messageId: messages[0].0.id)
sendMessageRequest = network.request(Api.functions.messages.forwardMessages(flags: flags, fromPeer: inputSourcePeer, id: forwardIds.map { $0.0.id }, randomId: forwardIds.map { $0.1 }, toPeer: inputPeer, scheduleDate: scheduleTime, sendAs: sendAsInputPeer), tag: dependencyTag)
sendMessageRequest = network.request(Api.functions.messages.forwardMessages(flags: flags, fromPeer: inputSourcePeer, id: forwardIds.map { $0.0.id }, randomId: forwardIds.map { $0.1 }, toPeer: inputPeer, topMsgId: topMsgId, scheduleDate: scheduleTime, sendAs: sendAsInputPeer), tag: dependencyTag)
} else {
assertionFailure()
sendMessageRequest = .fail(MTRpcError(errorCode: 400, errorDescription: "Invalid forward source"))
@ -842,7 +849,7 @@ public final class PendingMessageManager {
var topMsgId: Int32?
if let threadId = messages[0].0.threadId {
flags |= Int32(1 << 8)
flags |= Int32(1 << 9)
topMsgId = Int32(clamping: threadId)
}
@ -1076,7 +1083,7 @@ public final class PendingMessageManager {
var topMsgId: Int32?
if let threadId = message.threadId {
flags |= Int32(1 << 8)
flags |= Int32(1 << 9)
topMsgId = Int32(clamping: threadId)
}
@ -1088,15 +1095,21 @@ public final class PendingMessageManager {
var topMsgId: Int32?
if let threadId = message.threadId {
flags |= Int32(1 << 8)
flags |= Int32(1 << 9)
topMsgId = Int32(clamping: threadId)
}
sendMessageRequest = network.request(Api.functions.messages.sendMedia(flags: flags, peer: inputPeer, replyToMsgId: replyMessageId, topMsgId: topMsgId, media: inputMedia, message: text, randomId: uniqueId, replyMarkup: nil, entities: messageEntities, scheduleDate: scheduleTime, sendAs: sendAsInputPeer), tag: dependencyTag)
|> map(NetworkRequestResult.result)
case let .forward(sourceInfo):
var topMsgId: Int32?
if let threadId = message.threadId {
flags |= Int32(1 << 9)
topMsgId = Int32(clamping: threadId)
}
if let forwardSourceInfoAttribute = forwardSourceInfoAttribute, let sourcePeer = transaction.getPeer(forwardSourceInfoAttribute.messageId.peerId), let sourceInputPeer = apiInputPeer(sourcePeer) {
sendMessageRequest = network.request(Api.functions.messages.forwardMessages(flags: flags, fromPeer: sourceInputPeer, id: [sourceInfo.messageId.id], randomId: [uniqueId], toPeer: inputPeer, scheduleDate: scheduleTime, sendAs: sendAsInputPeer), tag: dependencyTag)
sendMessageRequest = network.request(Api.functions.messages.forwardMessages(flags: flags, fromPeer: sourceInputPeer, id: [sourceInfo.messageId.id], randomId: [uniqueId], toPeer: inputPeer, topMsgId: topMsgId, scheduleDate: scheduleTime, sendAs: sendAsInputPeer), tag: dependencyTag)
|> map(NetworkRequestResult.result)
} else {
sendMessageRequest = .fail(MTRpcError(errorCode: 400, errorDescription: "internal"))
@ -1108,7 +1121,7 @@ public final class PendingMessageManager {
var topMsgId: Int32?
if let threadId = message.threadId {
flags |= Int32(1 << 8)
flags |= Int32(1 << 9)
topMsgId = Int32(clamping: threadId)
}

View File

@ -406,7 +406,9 @@ private class AdMessagesHistoryContextImpl {
return account.postbox.transaction { transaction -> [Message] in
switch result {
case let .sponsoredMessages(messages, chats, users):
case let .sponsoredMessages(_, postsBetween, messages, chats, users):
let _ = postsBetween
var peers: [Peer] = []
var peerPresences: [PeerId: Api.User] = [:]
@ -504,6 +506,8 @@ private class AdMessagesHistoryContextImpl {
return parsedMessages.compactMap { message -> Message? in
return message.toMessage(peerId: peerId, transaction: transaction)
}
case .sponsoredMessagesEmpty:
return []
}
}
}

View File

@ -14,7 +14,7 @@ func _internal_forwardGameWithScore(account: Account, messageId: MessageId, to p
flags |= (1 << 13)
}
return account.network.request(Api.functions.messages.forwardMessages(flags: flags, fromPeer: fromInputPeer, id: [messageId.id], randomId: [Int64.random(in: Int64.min ... Int64.max)], toPeer: toInputPeer, scheduleDate: nil, sendAs: sendAsInputPeer))
return account.network.request(Api.functions.messages.forwardMessages(flags: flags, fromPeer: fromInputPeer, id: [messageId.id], randomId: [Int64.random(in: Int64.min ... Int64.max)], toPeer: toInputPeer, topMsgId: nil, scheduleDate: nil, sendAs: sendAsInputPeer))
|> map(Optional.init)
|> `catch` { _ -> Signal<Api.Updates?, NoError> in
return .single(nil)

View File

@ -6683,12 +6683,12 @@ public final class ChatControllerImpl: TelegramBaseController, ChatController, G
var forwardedMessages: [[EnqueueMessage]] = []
var forwardSourcePeerIds = Set<PeerId>()
for message in transformedMessages {
if case let .forward(source, _, _, _) = message {
if case let .forward(source, _, _, _, _) = message {
forwardSourcePeerIds.insert(source.peerId)
var added = false
if var last = forwardedMessages.last {
if let currentMessage = last.first, case let .forward(currentSource, _, _, _) = currentMessage, currentSource.peerId == source.peerId {
if let currentMessage = last.first, case let .forward(currentSource, _, _, _, _) = currentMessage, currentSource.peerId == source.peerId {
last.append(message)
added = true
}
@ -14994,7 +14994,7 @@ public final class ChatControllerImpl: TelegramBaseController, ChatController, G
attributes.append(ForwardOptionsMessageAttribute(hideNames: forwardOptions?.hideNames == true, hideCaptions: forwardOptions?.hideCaptions == true))
result.append(contentsOf: messages.map { message -> EnqueueMessage in
return .forward(source: message.id, grouping: .auto, attributes: attributes, correlationId: nil)
return .forward(source: message.id, threadId: nil, grouping: .auto, attributes: attributes, correlationId: nil)
})
let commit: ([EnqueueMessage]) -> Void = { result in
@ -15116,7 +15116,7 @@ public final class ChatControllerImpl: TelegramBaseController, ChatController, G
}), in: .current)
let _ = (enqueueMessages(account: strongSelf.context.account, peerId: peerId, messages: messages.map { message -> EnqueueMessage in
return .forward(source: message.id, grouping: .auto, attributes: [], correlationId: nil)
return .forward(source: message.id, threadId: nil, grouping: .auto, attributes: [], correlationId: nil)
})
|> deliverOnMainQueue).start(next: { messageIds in
if let strongSelf = self {

View File

@ -3188,7 +3188,7 @@ class ChatControllerNode: ASDisplayNode, UIScrollViewDelegate {
attributes.append(ForwardOptionsMessageAttribute(hideNames: self.chatPresentationInterfaceState.interfaceState.forwardOptionsState?.hideNames == true, hideCaptions: self.chatPresentationInterfaceState.interfaceState.forwardOptionsState?.hideCaptions == true))
for id in forwardMessageIds.sorted() {
messages.append(.forward(source: id, grouping: .auto, attributes: attributes, correlationId: nil))
messages.append(.forward(source: id, threadId: nil, grouping: .auto, attributes: attributes, correlationId: nil))
}
}

View File

@ -7234,7 +7234,7 @@ final class PeerInfoScreenNode: ViewControllerTracingNode, UIScrollViewDelegate
attributes.append(ForwardOptionsMessageAttribute(hideNames: forwardOptions?.hideNames == true, hideCaptions: forwardOptions?.hideCaptions == true))
result.append(contentsOf: messageIds.map { messageId -> EnqueueMessage in
return .forward(source: messageId, grouping: .auto, attributes: attributes, correlationId: nil)
return .forward(source: messageId, threadId: nil, grouping: .auto, attributes: attributes, correlationId: nil)
})
var displayPeers: [Peer] = []
@ -7308,7 +7308,7 @@ final class PeerInfoScreenNode: ViewControllerTracingNode, UIScrollViewDelegate
strongSelf.headerNode.navigationButtonContainer.performAction?(.selectionDone, nil, nil)
let _ = (enqueueMessages(account: strongSelf.context.account, peerId: peerId, messages: messageIds.map { id -> EnqueueMessage in
return .forward(source: id, grouping: .auto, attributes: [], correlationId: nil)
return .forward(source: id, threadId: nil, grouping: .auto, attributes: [], correlationId: nil)
})
|> deliverOnMainQueue).start(next: { [weak self] messageIds in
if let strongSelf = self {

View File

@ -217,7 +217,7 @@ final class WatchSendMessageHandler: WatchRequestHandler {
} else if let args = subscription as? TGBridgeSendForwardedMessageSubscription {
let peerId = makePeerIdFromBridgeIdentifier(args.targetPeerId)
if let forwardPeerId = makePeerIdFromBridgeIdentifier(args.peerId) {
messageSignal = .single((.forward(source: MessageId(peerId: forwardPeerId, namespace: Namespaces.Message.Cloud, id: args.messageId), grouping: .none, attributes: [], correlationId: nil), peerId))
messageSignal = .single((.forward(source: MessageId(peerId: forwardPeerId, namespace: Namespaces.Message.Cloud, id: args.messageId), threadId: nil, grouping: .none, attributes: [], correlationId: nil), peerId))
}
}