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

如何在Dialogflow中使用C# Webhook实现订阅用户广播消息

实现Dialogflow Webhook的广播消息功能(C#)

你已经搞定了用户订阅(保存PSID)的部分,接下来要实现广播消息其实核心是调用Facebook Messenger Send API(毕竟你用到的PSID是Facebook用户标识,说明你的Dialogflow对接了Messenger渠道),下面一步步给你讲怎么在C# Webhook里落地:

1. 准备必要的凭证

首先得从Facebook开发者后台拿到你的Page Access Token,这个令牌是调用Messenger API的关键,要确保它拥有pages_messaging权限。

2. 从数据库取出所有订阅用户的PSID

你已经用WebhookReceiverModelDataContext保存了用户PSID,现在只需要查询上下文里的订阅列表就行,假设你的实体类是SubscribedUser,包含Psid字段:

// 从数据库拉取所有订阅用户的PSID
var subscribedUsers = ctx.SubscribedUsers.Select(u => u.Psid).ToList();

3. 封装调用Messenger API的方法

写一个通用方法用来给单个用户发送消息,后续广播时直接循环调用即可:

private async Task SendMessageToUser(string pageAccessToken, string psid, string messageText)
{
    // 建议复用HttpClient,这里为示例简洁直接创建
    var client = new HttpClient();
    var requestUrl = $"https://graph.facebook.com/v18.0/me/messages?access_token={pageAccessToken}";

    // 构造Messenger API要求的请求体
    var payload = new
    {
        recipient = new { id = psid },
        message = new { text = messageText }
    };

    var jsonPayload = JsonConvert.SerializeObject(payload);
    var content = new StringContent(jsonPayload, Encoding.UTF8, "application/json");

    var response = await client.PostAsync(requestUrl, content);
    if (!response.IsSuccessStatusCode)
    {
        // 这里建议加日志记录,方便排查发送失败的情况
        var errorContent = await response.Content.ReadAsStringAsync();
        Console.WriteLine($"给用户 {psid} 发送消息失败: {errorContent}");
    }
}

提示:记得安装Newtonsoft.Json NuGet包来处理JSON序列化;生产环境里HttpClient最好全局复用,不要每次请求都实例化。

4. 在Webhook里触发广播逻辑

比如你可以新增一个broadcast.send意图,当管理员触发这个意图时(比如发送指令“发送广播”),执行广播逻辑。把这段逻辑加到你现有的Post方法里:

public async Task<ApiAiResponse> Post([FromBody]JObject jsonRequest)
{
    using (WebhookReceiverModelDataContext ctx = new WebhookReceiverModelDataContext())
    {
        ApiAiRequest request = jsonRequest.ToObject<ApiAiRequest>();
        var response = new ApiAiResponse();

        switch (request.Result.Action)
        {
            case "subscribe.about":
                // 你已有的保存PSID逻辑
                var psid = request.OriginalRequest.Data["sender"]["id"].ToString();
                ctx.SubscribedUsers.InsertOnSubmit(new SubscribedUser { Psid = psid });
                ctx.SubmitChanges();
                response.Speech = "订阅成功!";
                break;

            case "broadcast.send":
                // 广播消息逻辑
                string pageAccessToken = "你的Facebook Page Access Token";
                string broadcastContent = "这是一条给所有订阅用户的广播消息!";
                
                var subscribedUsers = ctx.SubscribedUsers.Select(u => u.Psid).ToList();
                foreach (var userPsid in subscribedUsers)
                {
                    await SendMessageToUser(pageAccessToken, userPsid, broadcastContent);
                }

                response.Speech = "广播消息已发起发送!";
                break;

            // 其他意图的处理逻辑...
        }

        return response;
    }
}

几个注意点

  • API版本:示例里用的是v18.0,记得根据Facebook的最新API版本调整,避免版本过期导致请求失败。
  • 限流问题:如果订阅用户数量多,不要一次性同步发送,建议用异步队列或者批量请求处理,避免触发Facebook的API调用频率限制。
  • 失效PSID处理:如果用户取消订阅,对应的PSID会失效,API返回错误时可以考虑从数据库移除这些无效的PSID。
  • 凭证安全:不要把Page Access Token硬编码在代码里,最好放在配置文件(比如appsettings.json)中,避免泄露。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.25 06:35:59