You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何让WTelegramClient跨频道同步消息时显示原生回复样式

实现WTelegramClient原生引用回复同步频道消息

我正在使用WTelegramClient监听某频道更新并同步消息至另一频道。目前通过拼接原消息与回复消息的方式处理回复,但希望实现Telegram原生的带引用回复预览样式。原频道原生回复样式如图所示,目标频道当前显示效果不符合预期,以下是当前使用的代码片段:

private async Task<Task> DisplayMessage(MessageBase messageBase, bool edit = false)
{
    if (edit) Console.Write("(Edit): ");
    switch (messageBase)
    {
        case TL.Message m:
            if (m.Peer.ID == from.ID)
            {
                string message = $"{m.message}";
                Console.WriteLine(message);

                if (messageBase.ReplyTo != null)
                {
                    var chats = await Client.Messages_GetAllChats();
                    InputPeer peer = chats.chats[from.ID];
                    Messages_MessagesBase repMessage = await Client.Messages_GetHistory(peer);

                    TL.Message repliee = (TL.Message)repMessage.Messages[0];
                    if (repMessage.Messages.Length > 0)
                    {
                        foreach (var msg in repMessage.Messages)
                        {
                            if (msg.ID == m.reply_to.reply_to_msg_id)
                            {
                                repliee = (TL.Message)msg;
                            }
                        }
                    }

                    TargetLog(repliee.message + Environment.NewLine + Environment.NewLine + 
                    "UPDATE:" + Environment.NewLine + message);
                }
                else
                {
                    await Client.Messages_ForwardMessages(from, new[] { messageBase.ID }, new[] { 
                    WTelegram.Helpers.RandomLong() }, to, drop_author: true);
                }
            }
    }
}

private async Task TargetLog(string txt)
{
    await Client.SendMessageAsync(to, txt);
}

修改方案

要实现原生引用回复,不能直接拼接文本,需利用Telegram API的reply_to_msg_id参数指定目标频道中被引用消息的ID。以下是修改后的代码:

// 缓存原频道消息ID与目标频道消息ID的映射,避免重复转发
private readonly Dictionary<int, long> _sourceToTargetMsgMap = new Dictionary<int, long>();

private async Task DisplayMessage(MessageBase messageBase, bool edit = false)
{
    if (edit) Console.Write("(Edit): ");
    switch (messageBase)
    {
        case TL.Message m:
            if (m.Peer.ID == from.ID)
            {
                string message = m.message;
                Console.WriteLine(message);

                if (m.ReplyTo != null)
                {
                    // 直接获取指定ID的被引用消息,替代遍历历史的低效方式
                    var referencedMsgResult = await Client.Messages_GetMessages(
                        new[] { new InputMessageID { id = m.reply_to.reply_to_msg_id } });
                    if (referencedMsgResult.Messages.Length == 0) break;
                    var referencedMsg = (TL.Message)referencedMsgResult.Messages[0];

                    long targetReferencedMsgId;
                    // 检查是否已同步过该被引用消息到目标频道
                    if (!_sourceToTargetMsgMap.TryGetValue(referencedMsg.ID, out targetReferencedMsgId))
                    {
                        // 未同步则先转发,获取目标频道的消息ID
                        var forwardResult = await Client.Messages_ForwardMessages(
                            from, new[] { referencedMsg.ID }, new[] { WTelegram.Helpers.RandomLong() }, to, drop_author: true);
                        
                        if (forwardResult is Messages_AffectedMessages affected)
                            targetReferencedMsgId = affected.id[0];
                        else
                        {
                            // 转发失败时 fallback 直接发送文本消息
                            var sentMsg = await Client.SendMessageAsync(to, referencedMsg.message);
                            targetReferencedMsgId = sentMsg.ID;
                        }
                        // 缓存映射关系
                        _sourceToTargetMsgMap[referencedMsg.ID] = targetReferencedMsgId;
                    }

                    // 发送当前消息,并指定引用目标频道的对应消息
                    await Client.SendMessageAsync(to, message, reply_to_msg_id: targetReferencedMsgId);
                }
                else
                {
                    // 非回复消息直接转发,并缓存ID映射
                    var forwardResult = await Client.Messages_ForwardMessages(
                        from, new[] { m.ID }, new[] { WTelegram.Helpers.RandomLong() }, to, drop_author: true);
                    if (forwardResult is Messages_AffectedMessages affected)
                        _sourceToTargetMsgMap[m.ID] = affected.id[0];
                }
            }
            break;
    }
}

关键说明

  • 高效获取被引用消息:用Messages_GetMessages直接按ID获取消息,替代原代码遍历历史的低效操作。
  • ID映射缓存:通过字典记录原频道消息到目标频道消息的ID对应关系,避免重复转发同一消息。
  • 原生引用实现:调用SendMessageAsync时传入reply_to_msg_id参数,指定目标频道中被引用消息的ID,即可触发Telegram原生引用样式。
  • 容错处理:针对转发失败的情况,增加了直接发送文本消息的 fallback 逻辑,确保同步流程不中断。

内容的提问来源于stack exchange,提问作者Rjoy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 17:10:35