httpclient

package
v2.0.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Feb 2, 2026 License: Apache-2.0 Imports: 15 Imported by: 0

Documentation

Overview

Package httpclient provides outbound HTTP clients with retry and tracing.

Index

Constants

This section is empty.

Variables

View Source
var ErrBreakerOpen = errors.New("circuit breaker open")

ErrBreakerOpen is returned when the circuit is open.

Functions

This section is empty.

Types

type Breaker

type Breaker interface {
	Execute(fn func() (*http.Response, error), isFailure FailureFunc) (*http.Response, error)
}

Breaker executes a function with circuit breaker semantics.

type Bulkhead

type Bulkhead interface {
	Acquire(ctx context.Context) (func(), error)
}

Bulkhead limits concurrency for outbound requests.

type CircuitBreaker

type CircuitBreaker struct {
	// contains filtered or unexported fields
}

CircuitBreaker provides a simple failure-count breaker.

func NewCircuitBreaker

func NewCircuitBreaker(opts CircuitBreakerOptions) *CircuitBreaker

NewCircuitBreaker creates a circuit breaker with sane defaults.

func (*CircuitBreaker) Execute

func (b *CircuitBreaker) Execute(fn func() (*http.Response, error), isFailure FailureFunc) (*http.Response, error)

Execute runs fn when the circuit allows it, updating breaker state afterward.

type CircuitBreakerOptions

type CircuitBreakerOptions struct {
	FailureThreshold    int
	SuccessThreshold    int
	OpenTimeout         time.Duration
	HalfOpenMaxInFlight int
	Now                 func() time.Time
}

CircuitBreakerOptions configures a circuit breaker.

type Client

type Client struct {
	// contains filtered or unexported fields
}

Client implements ports.HTTPClient.

func New

func New(opts Options) *Client

New constructs an outbound HTTP client with sane defaults.

func (*Client) Do

func (c *Client) Do(req *http.Request) (*http.Response, error)

Do issues the HTTP request with retry behavior when configured.

type FailureFunc

type FailureFunc func(*http.Response, error) bool

FailureFunc determines whether a response or error should count as a failure.

type Options

type Options struct {
	Timeout        time.Duration
	Transport      http.RoundTripper
	CheckRedirect  func(*http.Request, []*http.Request) error
	DisableTracing bool
	Sleep          func(time.Duration)
	Retry          RetryOptions
	Breaker        Breaker
	BreakerFailure FailureFunc
	Bulkhead       Bulkhead
}

Options configures the outbound HTTP client.

type Resolver

type Resolver interface {
	LookupIPAddr(ctx context.Context, host string) ([]net.IPAddr, error)
}

Resolver resolves hostnames for SSRF protection.

type RetryOptions

type RetryOptions struct {
	Disable              bool
	MaxRetries           int
	MaxElapsedTime       time.Duration
	MinBackoff           time.Duration
	MaxBackoff           time.Duration
	RetryableStatusCodes []int
	RetryableMethods     []string
	UseRetryAfter        bool
	RetryOn              func(*http.Response, error) bool
}

RetryOptions configures retry behavior.

type SSRFOptions

type SSRFOptions struct {
	Transport    *http.Transport
	Resolver     Resolver
	Dialer       *net.Dialer
	AllowedHosts []string
	AllowedPorts []int
	AllowedCIDRs []string
	// AllowRedirectSchemeChange permits http<->https redirects.
	AllowRedirectSchemeChange bool
}

SSRFOptions configures SSRF protection for outbound HTTP.

type SSRFTransport

type SSRFTransport struct {
	// contains filtered or unexported fields
}

SSRFTransport validates outbound targets before dialing and on redirects.

Threat model coverage: - Blocks private/reserved IPv4/IPv6 ranges (including link-local/metadata IPs). - Re-validates each redirect hop (host/port/scheme) via CheckRedirect. - Mitigates DNS rebinding by resolving once and dialing by IP.

Non-goals: - If you allowlist a host/CIDR, requests to that target are allowed. - It does not inspect application-level SSRF beyond host/port/scheme/IP.

Example:

guard, _ := httpclient.NewSSRFTransport(httpclient.SSRFOptions{
	AllowedHosts: []string{"api.example.com"},
	AllowedPorts: []int{443},
})
client := &http.Client{
	Transport:     guard,
	CheckRedirect: guard.CheckRedirect,
}

func NewSSRFTransport

func NewSSRFTransport(opts SSRFOptions) (*SSRFTransport, error)

NewSSRFTransport creates a transport that blocks private/reserved networks by default.

func (*SSRFTransport) CheckRedirect

func (t *SSRFTransport) CheckRedirect(req *http.Request, via []*http.Request) error

CheckRedirect validates redirect targets and enforces scheme-change rules.

func (*SSRFTransport) RoundTrip

func (t *SSRFTransport) RoundTrip(req *http.Request) (*http.Response, error)

RoundTrip validates the outbound request before dialing.

type SemaphoreBulkhead

type SemaphoreBulkhead struct {
	// contains filtered or unexported fields
}

SemaphoreBulkhead bounds concurrent requests using a semaphore.

func NewSemaphoreBulkhead

func NewSemaphoreBulkhead(limit int) (*SemaphoreBulkhead, error)

NewSemaphoreBulkhead creates a semaphore bulkhead with the given limit.

func (*SemaphoreBulkhead) Acquire

func (b *SemaphoreBulkhead) Acquire(ctx context.Context) (func(), error)

Acquire reserves capacity until the release function is called.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL