跳到主要内容
ecdsa.com
Go crypto/tls clientGo

错误信息

remote error: tls: handshake failure

在 HTTP 客户端中,这一行的内容是“Get \"https://…\": remote error: tls: handshake failure”。当客户端发送告警时,Go 在服务器上也使用同样的“remote error: tls: <alert>”形式,出现在“http: TLS handshake error from …”日志行中。

Go crypto/tls client — the server sent TLS alert 40 (handshake_failure)

含义

“remote error”表示对方发送了 TLS 告警;这里是服务器向 Go 客户端发送了告警 40(handshake_failure)。服务器拒绝了 Go 提供的参数(密码套件、密钥交换组、签名算法),或者要求提供 Go 没有发送的客户端证书。Go 无法判断是哪一种;服务器日志可以。

原因

修复方法

  1. 1.

    比较密码套件

    tls.CipherSuites() 列出了 Go 认为安全并会提供的套件;将其与服务器的配置进行比较。

    go
    // What does this Go client offer by default?
    for _, s := range tls.CipherSuites() {
    	fmt.Println(s.Name)
    }
  2. 2.

    为双向 TLS 发送客户端证书

    用 tls.LoadX509KeyPair 加载证书和密钥,并将其配置到 tls.Config.Certificates 中。

    go
    // Mutual TLS: present a client certificate
    cert, err := tls.LoadX509KeyPair("client.pem", "client.key")
    if err != nil {
    	log.Fatal(err)
    }
    client := &http.Client{Transport: &http.Transport{TLSClientConfig: &tls.Config{
    	Certificates: []tls.Certificate{cert},
    }}}
  3. 3.

    服务器所有者:更新为现代的密码套件

    TLS 1.3 以及基于 ECDHE 的 TLS 1.2 套件适用于当前所有 Go 版本。

    text
    Server side: enable TLS 1.3 and TLS 1.2 ECDHE suites with AES-GCM or ChaCha20-Poly1305.

相关错误

浏览完整的签名错误库