Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 20 additions & 0 deletions client.go
Original file line number Diff line number Diff line change
Expand Up @@ -1225,6 +1225,10 @@ func (conn *uTLSConn) ConnectionState() tls.ConnectionState {
// which uses the specified clientHelloID to simulate the tls fingerprint.
// Note this is valid for HTTP1 and HTTP2, not HTTP3.
func (c *Client) SetTLSFingerprint(clientHelloID utls.ClientHelloID) *Client {
c.setTLSFingerprint(clientHelloID, nil)
return c
}
func (c *Client) setTLSFingerprint(clientHelloID utls.ClientHelloID, uTLSConnApply func(*uTLSConn) error) *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 {
Expand All @@ -1248,6 +1252,11 @@ func (c *Client) SetTLSFingerprint(clientHelloID utls.ClientHelloID) *Client {
KeyLogWriter: tlsConfig.KeyLogWriter,
}
uconn := &uTLSConn{utls.UClient(plainConn, utlsConfig, clientHelloID)}
if uTLSConnApply != nil {
if err = uTLSConnApply(uconn); err != nil {
return
}
}
err = uconn.HandshakeContext(ctx)
if err != nil {
return
Expand All @@ -1274,6 +1283,17 @@ func (c *Client) SetTLSFingerprint(clientHelloID utls.ClientHelloID) *Client {
return c
}

// SetTLSFingerprintSpec set the tls fingerprint for tls handshake, will use utls
// (https://github.com/refraction-networking/utls) to perform the tls handshake,
// which uses the specified clientHelloID to simulate the tls fingerprint.
func (c *Client) SetTLSFingerprintSpec(clientHelloID *utls.ClientHelloSpec) *Client {
c.setTLSFingerprint(utls.HelloCustom, func(conn *uTLSConn) error {
err := conn.ApplyPreset(clientHelloID)
return err
})
return c
}

// SetTLSHandshake set the custom tls handshake function, only valid for HTTP1 and HTTP2, not HTTP3,
// it specifies an optional dial function for tls handshake, it works even if a proxy is set, can be
// used to customize the tls fingerprint.
Expand Down
31 changes: 31 additions & 0 deletions client_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import (

"github.com/imroc/req/v3/internal/header"
"github.com/imroc/req/v3/internal/tests"
utls "github.com/refraction-networking/utls"
"golang.org/x/net/publicsuffix"
)

Expand Down Expand Up @@ -720,3 +721,33 @@ func TestCloneCookieJar(t *testing.T) {
tests.AssertEqual(t, true, c2.cookiejarFactory == nil)
tests.AssertEqual(t, true, c2.httpClient.Jar == nil)
}
func TestUTLSConnApply(t *testing.T) {
c1 := C()

c1.setTLSFingerprint(utls.HelloCustom, func(conn *uTLSConn) error {
tt, _ := utls.UTLSIdToSpec(utls.HelloQQ_Auto)
//"github.com/Danny-Dasilva/CycleTLS/cycletls"
//cycletls.StringToSpec("771,4865-4866-4867-49195-49199-49196-49200-52393-52392-49171-49172-156-157-47-53,0-5-10-11-13-16-18-21-23-27-35-43-45-51-17513-65281,29-23-24,0", "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:120.0) Gecko/20100101 Firefox/120.0", false)
err := conn.ApplyPreset(&tt)
return err
})

//c1.SetTLSFingerprintQQ()
bodyJson := &struct {
Ja3NText string `json:"ja3n_text"`
}{}
_ = c1.Get("https://tls.browserleaks.com/json").Do().Into(bodyJson)
//println(string(bodyJson.Ja3NText))
tests.AssertEqual(t, true, bodyJson.Ja3NText == "771,4865-4866-4867-49195-49199-49196-49200-52393-52392-49171-49172-156-157-47-53,0-5-10-11-13-16-18-21-23-27-35-43-45-51-17513-65281,29-23-24,0")
}
func TestSetTLSFingerprintSpec(t *testing.T) {
c1 := C()
tt, _ := utls.UTLSIdToSpec(utls.HelloQQ_Auto)
c1.SetTLSFingerprintSpec(&tt)
bodyJson := &struct {
Ja3NText string `json:"ja3n_text"`
}{}
_ = c1.Get("https://tls.browserleaks.com/json").Do().Into(bodyJson)
//println(string(bodyJson.Ja3NText))
tests.AssertEqual(t, true, bodyJson.Ja3NText == "771,4865-4866-4867-49195-49199-49196-49200-52393-52392-49171-49172-156-157-47-53,0-5-10-11-13-16-18-21-23-27-35-43-45-51-17513-65281,29-23-24,0")
}