IIS上的Webhook无法验证URL。回调验证失败,出现以下错误:curl_errno = 60

时间:2019-07-24 15:04:08

标签: facebook ssl https facebook-javascript-sdk facebook-webhooks

我用{#3}}中的C#创建了Facebook Webhook。在我的本地PC中创建pfx文件。 但是在Facebook上订阅时出现了错误:

  

无法验证URL。回调验证失败,原因是   错误如下:curl_errno = 60; curl_error = SSL证书   问题:无法获得本地发行者证书; HTTP状态代码=   200; HTTP消息=已建立连接

试图订阅发布在https://www.vnsppl.somee.com/api/webhooks上的消息 试图在我的PC上使用digicert util生成密钥,结果显示所有密钥都可以。

已从此处https://developers.facebook.com/apps/2442731462439849/webhooks/下载了代码

appsetting.json:

  

{“ FacebookOptions”:{       //在Facebook应用中配置WebHooks时,要求您输入验证令牌。       //在此处设置相同的值(任何随机字符串)       “ VerifyToken”:“ o / ERviEE / vt0 | https://developers.facebook.com/apps/)       “ AppSecret”:“ ”,       //您的应用令牌(从https://github.com/EtienneCoumont/FacebookWebHooks获取)       “ AppToken”:“ ”   },“ MailOptions”:{       “ FromName”:“ ”,       “ FromMail”:“ ”,       “ ToName”:“ ”,       “ ToMail”:“ ”,       “ SmtpHost”:“ ”,       “ SmtpPort”:587,       “ SmtpUseSsl”:否,       “ SmtpLogin”:“ ”,       “ SmtpPassword”:“ ***”},“记录”:{       “ IncludeScopes”:否,       “调试”:{         “ LogLevel”:{           “默认”:“警告”         }       },       “安慰”: {         “ LogLevel”:{           “默认”:“警告”         }       }}

WebHooksController.cs

...     [Route(“ api / [controller]”)]     公共类WebHooksController:控制器     {         FacebookOptions _fbOptions;         MailOptions _mailOptions;         ILogger _log;

    public WebHooksController(IOptions<FacebookOptions> fbOptions, IOptions<MailOptions> mailOptions,
        ILogger<WebHooksController> logger)
    {
        _fbOptions = fbOptions.Value;
        _mailOptions = mailOptions.Value;
        _log = logger;
    }

    // GET: api/webhooks
    [HttpGet]
    public string Get([FromQuery(Name = "hub.mode")] string hub_mode,
        [FromQuery(Name = "hub.challenge")] string hub_challenge,
        [FromQuery(Name = "hub.verify_token")] string hub_verify_token)
    {
        if (_fbOptions.VerifyToken == hub_verify_token)
        {
            _log.LogInformation("Get received. Token OK : {0}", hub_verify_token);
            return hub_challenge;
        }
        else
        {
            _log.LogError("Error. Token did not match. Got : {0}, Expected : {1}", hub_verify_token, _fbOptions.VerifyToken);
            return "error. no match";
        }
    }

    // POST api/values
    [HttpPost]
    public void Post()
    {
        string json;
        try
        {
            using (StreamReader sr = new StreamReader(this.Request.Body))
            {
                json = sr.ReadToEnd();
            }
        }
        catch (Exception ex)
        {
            _log.LogCritical("Error during body read.", ex);
            Mail.SendMail(_mailOptions, "Error during body read : " + ex.Message);
            return;
        }

        StringBuilder sb = new StringBuilder();
        bool errorRaised = false;
        try
        {
            if (_fbOptions.ShouldVerifySignature)
            {
                VerifySignature(json);
            }
            WriteStory(sb, json);
        }
        catch (Exception ex)
        {
            errorRaised = true;
            sb.AppendLine("Error during webhook processing : " + ex.Message);
        }

        WriteDebug(sb, json);

        string msg = sb.ToString();
        if (errorRaised)
            _log.LogError(msg);
        else
            _log.LogTrace(msg);

        try
        {
            Mail.SendMail(_mailOptions, msg);
        }
        catch (Exception ex)
        {
            _log.LogError("Can't send email", ex);
        }
    }

    private void VerifySignature(string json)
    {
        var signatures = this.Request.Headers.Where(h => h.Key == "X-Hub-Signature").ToArray();
        if (signatures.Length == 0)
            throw new Exception("X-Hub-Signature not found");
        if (signatures.Length >= 2)
            throw new Exception("Many X-Hub-Signature found");
        string headerHash = signatures[0].Value;
        if (headerHash == null)
            throw new Exception("X-Hub-Signature is null");
        if (!headerHash.StartsWith("sha1="))
            throw new Exception("Unexpected format of X-Hub-Signature : " + headerHash);
        headerHash = headerHash.Substring(5);

        string myHash = Hash.ComputeHash(_fbOptions.AppSecret, json);
        if (myHash == null)
            throw new Exception("Unexpected null hash");
        if (!myHash.Equals(headerHash, StringComparison.OrdinalIgnoreCase))
            throw new Exception($"Hash did not match. Expected {myHash}. But header was {headerHash}");
    }

    private void WriteDebug(StringBuilder sb, string json)
    {
        sb.AppendLine();
        sb.Append("<pre>");
        sb.Append(this.Request.QueryString.ToUriComponent());
        foreach (var header in this.Request.Headers)
        {
            sb.Append(header.Key + ": " + header.Value + "\r\n");
        }
        sb.Append("\r\n" + json + "\r\n\r\n" + Hash.ComputeHash(_fbOptions.AppSecret, json));
        sb.Append("</pre>");
    }

    private void WriteStory(StringBuilder sb, string json)
    {
        // alternative : var json = JToken.Parse(body);
        var updateObj = JsonConvert.DeserializeObject<UpdateObject>(json);

        switch (updateObj.Object)
        {
            case ObjectEnum.Page:
                if (updateObj.Entry == null)
                {
                    sb.AppendLine("Null Entry");
                    break;
                }
                foreach (var entry in updateObj.Entry)
                {
                    WriteEntry(sb, entry);
                }
                break;
            default:
                sb.AppendLine("Not implemented object : " + updateObj.Object);
                break;
        }
    }

    private void WriteEntry(StringBuilder sb, Entry entry)
    {
        if (entry.Changes == null)
        {
            sb.AppendLine($"Null Changes for entry {entry.Id}");
            return;
        }
        foreach (var change in entry.Changes)
        {
            WriteChange(sb, change);
        }
    }

    private void WriteChange(StringBuilder sb, Change change)
    {
        if (change.Field != "feed")
        {
            sb.AppendLine("Field updated : " + change.Field);
            return;
        }
        WriteValue(sb, change.Value);
    }

    private void WriteValue(StringBuilder sb, Value value)
    {
        if (value == null)
        {
            sb.AppendLine("Value null");
            return;
        }

        switch (value.Item)
        {
            case "share":
                sb.AppendLine($"{value.SenderName} shared the link {value.Link}<br/>");
                sb.AppendLine(value.Message);
                break;
            case "like":
                if (value.Verb != "add")
                {
                    sb.AppendLine($"Unknown verb for like {value.Verb}");
                }
                else if (value.PostId == null)
                {
                    sb.AppendLine($"{value.UserId} liked the page");
                }
                else
                {
                    sb.AppendLine($"{value.SenderName} liked the post {value.PostId}");
                }
                break;
            case "photo":
                if (value.Verb != "add")
                {
                    sb.AppendLine($"Unknown verb for photo {value.Verb}");
                }
                else
                {
                    sb.AppendLine($"{value.SenderName} posted a new photo:");
                    sb.AppendLine(value.Link);
                    sb.AppendLine($"<img src=\"{value.Link}\" style=\"width:100%;\"/>");
                    if (!string.IsNullOrEmpty(value.Message))
                        sb.AppendLine(value.Message);
                }
                break;
            case "status":
                if (value.Verb != "add")
                {
                    sb.AppendLine($"Unknown verb for status {value.Verb}");
                }
                else
                {
                    sb.AppendLine($"{value.SenderName} posted a new status:");
                    sb.AppendLine(value.Message);
                }
                break;
            default:
                sb.AppendLine($"Unknown item '{value.Item}'");
                break;
        }
    }
}

0 个答案:

没有答案