imroc / req

Simple Go HTTP client with Black Magic
https://req.cool
MIT License
4.3k stars 350 forks source link

KeyLogWriter不生效 #387

Closed 1992w closed 1 month ago

1992w commented 1 month ago

使用基础库的http client通过设置KeyLogWriter可以用来保存密钥,像下面这样:

    client := http.Client{
        Transport: &http.Transport{
            TLSClientConfig: &tls.Config{
                KeyLogWriter: file,
            },
        },
    }

使用req.Client设置KeyLogWriter,密钥不会保存到文件中:

    tc := c.GetTLSClientConfig()
    tc.KeyLogWriter = file
    c.SetTLSClientConfig(tc)
1992w commented 1 month ago

看了下源码,是设置指纹时没有设置KeyLogWriter这个参数,加上就正常了:

func (c *Client) SetTLSFingerprint(clientHelloID utls.ClientHelloID) *Client {
    fn := func(ctx context.Context, addr string, plainConn net.Conn) (conn net.Conn, tlsState *tls.ConnectionState, err error) {
        colonPos := strings.LastIndex(addr, ":")
        if colonPos == -1 {
            colonPos = len(addr)
        }
        hostname := addr[:colonPos]
        utlsConfig := &utls.Config{
            ServerName:         hostname,
            RootCAs:            c.GetTLSClientConfig().RootCAs,
            NextProtos:         c.GetTLSClientConfig().NextProtos,
            InsecureSkipVerify: c.GetTLSClientConfig().InsecureSkipVerify,
            KeyLogWriter:       c.GetTLSClientConfig().KeyLogWriter, //这里加上就好了
        }
        uconn := &uTLSConn{utls.UClient(plainConn, utlsConfig, clientHelloID)}
        err = uconn.HandshakeContext(ctx)
        if err != nil {
            return
        }
        cs := uconn.Conn.ConnectionState()
        conn = uconn
        tlsState = &tls.ConnectionState{
            Version:                     cs.Version,
            HandshakeComplete:           cs.HandshakeComplete,
            DidResume:                   cs.DidResume,
            CipherSuite:                 cs.CipherSuite,
            NegotiatedProtocol:          cs.NegotiatedProtocol,
            NegotiatedProtocolIsMutual:  cs.NegotiatedProtocolIsMutual,
            ServerName:                  cs.ServerName,
            PeerCertificates:            cs.PeerCertificates,
            VerifiedChains:              cs.VerifiedChains,
            SignedCertificateTimestamps: cs.SignedCertificateTimestamps,
            OCSPResponse:                cs.OCSPResponse,
            TLSUnique:                   cs.TLSUnique,
        }
        return
    }
    c.Transport.SetTLSHandshake(fn)
    return c
}
imroc commented 1 month ago

v3.46.1 已修复