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

如何在Go中配置http.Client通过Cloudflare SSL发送HTTPS请求

Go使用Cloudflare证书发起HTTPS请求时证书验证失败的解决

问题描述

我有一个基于Go语言运行的服务器,希望能通过SSL发送HTTP请求。我使用Cloudflare为域名提供的证书来实现SSL/TLS,以下是我尝试发起HTTPS请求的代码示例:

func makeHttpsRequest(w http.ResponseWriter, req *http.Request) {
   certs, _ := tls.LoadX509KeyPair("certificate.pem", "key.pem")
   rcert, _ := os.ReadFile("rootcert.pem")
   rpool := x509.NewCertPool()
   rpool.AppendCertsFromPEM(rcert)
   tlsConfig := &tls.Config{
      Certificates: []tls.Certificate{certs},
      RootCAs:      rpool,
   }
   tr := &http.Transport{
      TLSClientConfig: tlsConfig,
   }
   client := &http.Client{
      Transport: tr
   }
   request, _ := http.NewRequest("GET", "https://example.com", nil)
   response, err := client.do(request)
   if err != nil {
      log.Println(err)
   }
   // code to handle the response removed from code snippet
}

但调用该函数时出现错误:

tls: failed to verify certificate: x509: certificate signed by unknown authority

我确定错误源于certificate.pem、key.pem和rootcert.pem的配置问题。当前certificate.pem和key.pem是Cloudflare的Origin Certificate Authority证书及私钥,rootcert.pem是Cloudflare Origin Root CA证书。请问正确的配置应该是怎样的?


问题根源

你混淆了客户端证书和根证书信任池的作用:

  • Cloudflare Origin证书(certificate.pem/key.pem)是给你的服务器接收HTTPS请求时使用的,并非客户端发起请求需要携带的证书。
  • 发起HTTPS请求到外部站点时,客户端需要验证目标站点的证书是否被信任根CA签发,而非把自身的Origin证书加入客户端配置。

正确配置方案

场景1:普通HTTPS请求(访问公共站点如example.com)

直接使用Go默认的http.Client即可,它会自动调用系统内置的根CA信任池验证目标证书:

func makeHttpsRequest(w http.ResponseWriter, req *http.Request) {
    client := &http.Client{}
    request, err := http.NewRequest("GET", "https://example.com", nil)
    if err != nil {
        log.Println(err)
        return
    }
    response, err := client.Do(request)
    if err != nil {
        log.Println(err)
        return
    }
    defer response.Body.Close()
    // 处理响应的逻辑
}

场景2:访问使用Cloudflare Origin证书的内部站点

此时需要将Cloudflare Origin Root CA加入信任池,但不需要配置客户端证书(除非目标服务器要求双向认证):

func makeHttpsRequest(w http.ResponseWriter, req *http.Request) {
    // 读取Cloudflare Origin Root CA证书
    rcert, err := os.ReadFile("rootcert.pem")
    if err != nil {
        log.Println(err)
        return
    }
    // 初始化证书池并添加根CA
    rpool := x509.NewCertPool()
    ok := rpool.AppendCertsFromPEM(rcert)
    if !ok {
        log.Println("无法将根证书添加到信任池")
        return
    }
    // 配置TLS,仅指定信任的根CA
    tlsConfig := &tls.Config{
        RootCAs: rpool,
        // 只有当目标服务器要求客户端提供证书时,才需要设置Certificates字段
    }
    tr := &http.Transport{
        TLSClientConfig: tlsConfig,
    }
    client := &http.Client{
        Transport: tr,
    }
    // 发起请求到使用Cloudflare Origin证书的站点
    request, err := http.NewRequest("GET", "https://your-internal-cloudflare-site.com", nil)
    if err != nil {
        log.Println(err)
        return
    }
    response, err := client.Do(request)
    if err != nil {
        log.Println(err)
        return
    }
    defer response.Body.Close()
    // 处理响应的逻辑
}

关键注意事项

  • tls.Config.Certificates字段仅用于目标服务器要求客户端证书认证的场景,普通HTTPS请求不需要配置。
  • 你之前的错误是因为自定义的RootCAs只包含Cloudflare根CA,而example.com的证书由公共根CA签发,不在你的信任池内,导致验证失败。只有访问使用Cloudflare Origin证书加密的站点时,才需要用Cloudflare根CA做验证。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.12 02:33:36