作者热门文章
- r - 以节省内存的方式增长 data.frame
- ruby-on-rails - ruby/ruby on rails 内存泄漏检测
- android - 无法解析导入android.support.v7.app
- UNIX 域套接字与共享内存(映射文件)
我们正在 Golang 中构建一个通过 SSL 打开 TCP 端口的服务器。
我们希望在客户端和服务器之间启用相互认证。但也会检测客户端何时尝试在没有有效客户端证书的情况下连接到我们的服务器,并通过 SSL 向他们返回错误消息 - 例如“检测到无效的客户端证书,请联系公司 ABC 寻求帮助”。
需要明确的是:我们坚持要求通过 SSL 将数据返回给未能与服务器相互验证的客户端。我们不想断开它们。
我们采用的方法是对 TLS 使用“VerifyClientCertIfGiven”配置设置。
因此,如果提供了客户端证书,我们将对其进行验证,但如果未提供,我们仍然允许建立 SSL 连接。
我们怎样才能知道:
下面是我们服务器的代码:
package main
import(
"fmt"
"io/ioutil"
"crypto/tls"
"crypto/x509"
)
func main(){
// Configure SSL
cert, err := tls.LoadX509KeyPair("server.crt", "server.key")
caCert, _ := ioutil.ReadFile("client.crt")
caCertPool := x509.NewCertPool()
caCertPool.AppendCertsFromPEM(caCert)
config := &tls.Config{
Certificates: []tls.Certificate{cert},
ClientCAs: caCertPool,
ClientAuth: tls.VerifyClientCertIfGiven,
}
config.BuildNameToCertificate()
// Listen on port 443
listener, _ := tls.Listen("tcp", ":443", config)
defer listener.Close()
// Accept incoming connection
conn, _ := listener.Accept()
defer conn.Close()
// Print ConnectionState
tlscon, _ := conn.(*tls.Conn)
fmt.Println(tlscon.ConnectionState())
}
下面是我们客户端的代码:
package main
import (
"io/ioutil"
"crypto/tls"
"crypto/x509"
)
func main(){
//Configure SSL
cert, _ := tls.LoadX509KeyPair("client.crt", "client.key"
caCert, _ := io.util.ReadFile("server.crt")
caCertPool := x509.NewCertPool()
caCertPool.AppendCertsFromPEM(caCert)
config := &tls.Config{
Certificates: []tls.Certificate{cert},
RootCAs: caCertPool,
}
config.BuildNameToCertificate()
// Connect to server
conn, _ := tls.Dial("tcp", "127.0.0.1:443", config)
defer conn.Close()
}
输出:
{0 false false 0 false [] [] [] [] []}
我们已经尝试在服务器上实现 conn.ConnectionState().PeerCertificates,但在我们所有的尝试中,它都是一个空字节数组。
提前致谢。感谢您花时间帮助我们。
亲切的问候,
朱利安
最佳答案
我也是在这上面度过了最美好的下午。
一旦服务器接受连接,您将需要显式调用 tlscon.Handshake()
以获取客户端的证书,否则 tls 程序包将在第一次 i/o 后自动执行此操作。 https://golang.org/pkg/crypto/tls/#Conn.Handshake
可以看一个例子here .
关于ssl - 如何在不强制断开连接的情况下使用 Go TLS 手动验证客户端证书?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42664156/
我是一名优秀的程序员,十分优秀!