main
lzf 2025-07-11 16:57:24 +08:00
parent 27ccc2a080
commit 1cb7943903
2 changed files with 113 additions and 34 deletions

View File

@ -3,7 +3,6 @@ package httpc
import (
"bytes"
"context"
"crypto/tls"
"errors"
"fmt"
"git.makemake.in/kzkzzzz/mycommon/mylog"
@ -21,18 +20,34 @@ var (
)
func init() {
defaultClient = NewWithRedirect(false)
noRedirectClient = NewWithRedirect(true)
defaultClient = New()
noRedirectClient = New(WithNoRedirect())
}
func NewTransport() *http.Transport {
func Client() *HttpClient {
return defaultClient
}
func NoRedirectClient() *HttpClient {
return noRedirectClient
}
func NewTransport(maxConn int, idleTimeout time.Duration) *http.Transport {
if maxConn <= 0 {
panic("max connection <= 0")
}
if idleTimeout <= 0 {
panic("idle timeout <= 0")
}
tr := http.DefaultTransport.(*http.Transport).Clone()
tr.MaxIdleConns = 0
tr.MaxConnsPerHost = 0
tr.MaxIdleConnsPerHost = 2048
tr.IdleConnTimeout = time.Second * 90
tr.MaxIdleConnsPerHost = maxConn
tr.IdleConnTimeout = idleTimeout
tr.DisableKeepAlives = false
tr.TLSClientConfig = &tls.Config{InsecureSkipVerify: false}
//tr.TLSClientConfig = &tls.Config{InsecureSkipVerify: false}
return tr
}
@ -46,24 +61,43 @@ type Request struct {
}
type HttpClient struct {
config *Config
client *http.Client
}
func NewWithRedirect(noRedirect bool) *HttpClient {
tr := NewTransport()
func New(opts ...ConfigOpt) *HttpClient {
config := &Config{}
for _, opt := range opts {
opt(config)
}
if config.timeout <= 0 {
config.timeout = time.Second * 6
}
if config.transport == nil {
config.transport = NewTransport(3072, time.Second*90)
}
if config.client == nil {
client := &http.Client{
Transport: tr,
Timeout: time.Second * 6,
Transport: config.transport,
Timeout: config.timeout,
}
if noRedirect {
client.CheckRedirect = func(req *http.Request, via []*http.Request) error {
return http.ErrUseLastResponse
}
if config.redirectFn != nil {
client.CheckRedirect = config.redirectFn
}
h := &HttpClient{client: client}
return h
config.client = client
}
hc := &HttpClient{
config: config,
client: config.client,
}
return hc
}
func NewWithClient(httpClient *http.Client) *HttpClient {
@ -81,7 +115,7 @@ func (h *HttpClient) SetProxy(pr string) *HttpClient {
return h
}
func (h *HttpClient) Request(ctx context.Context) *Request {
func (h *HttpClient) NewRequest(ctx context.Context) *Request {
r := &Request{
ctx: ctx,
header: nil,
@ -91,22 +125,26 @@ func (h *HttpClient) Request(ctx context.Context) *Request {
return r
}
func PcRequest(ctx context.Context) *Request {
return defaultClient.PcRequest(ctx)
func NewRequest(ctx context.Context) *Request {
return defaultClient.NewRequest(ctx)
}
func MobileRequest(ctx context.Context) *Request {
return defaultClient.MobileRequest(ctx)
func NewPcRequest(ctx context.Context) *Request {
return defaultClient.NewPcRequest(ctx)
}
func (h *HttpClient) PcRequest(ctx context.Context) *Request {
r := h.Request(ctx)
func NewMobileRequest(ctx context.Context) *Request {
return defaultClient.NewMobileRequest(ctx)
}
func (h *HttpClient) NewPcRequest(ctx context.Context) *Request {
r := h.NewRequest(ctx)
r.SetHeaderPcAgent()
return r
}
func (h *HttpClient) MobileRequest(ctx context.Context) *Request {
r := h.Request(ctx)
func (h *HttpClient) NewMobileRequest(ctx context.Context) *Request {
r := h.NewRequest(ctx)
r.SetHeaderMobileAgent()
return r
}
@ -223,14 +261,6 @@ func (r *Request) Do(method, rawUrl string) (*Response, error) {
return resp, nil
}
func Client() *HttpClient {
return defaultClient
}
func NoRedirectClient() *HttpClient {
return noRedirectClient
}
func (r *Request) SetHeaderPcAgent() *Request {
r.SetHeader(HeaderUserAgent, PcUserAgent)
return r

49
myhttp/httpc/option.go Normal file
View File

@ -0,0 +1,49 @@
package httpc
import (
"net/http"
"time"
)
type (
Config struct {
timeout time.Duration
client *http.Client
transport *http.Transport
redirectFn func(req *http.Request, via []*http.Request) error
}
ConfigOpt func(c *Config)
)
func WithTimout(v time.Duration) ConfigOpt {
return func(c *Config) {
c.timeout = v
}
}
func WithClient(v *http.Client) ConfigOpt {
return func(c *Config) {
c.client = v
}
}
func WithTransport(v *http.Transport) ConfigOpt {
return func(c *Config) {
c.transport = v
}
}
func WithRedirectFn(v func(req *http.Request, via []*http.Request) error) ConfigOpt {
return func(c *Config) {
c.redirectFn = v
}
}
func WithNoRedirect() ConfigOpt {
return func(c *Config) {
c.redirectFn = func(req *http.Request, via []*http.Request) error {
return http.ErrUseLastResponse
}
}
}