feat(httpclient): initial stable release v0.9.0
Resilient HTTP client with circuit breaking, exponential-backoff retry, X-Request-ID propagation, and a generic typed JSON helper. What's included: - Client interface with Do(req) method; New(logger, cfg) and NewWithDefaults(logger) constructors - Config struct with env-tag support for timeout, dial timeout, retry, and circuit breaker parameters - Retry via avast/retry-go/v4 with BackOffDelay; triggers only on network errors and HTTP 5xx - Circuit breaker via sony/gobreaker wrapping the full retry loop; open circuit → xerrors.ErrUnavailable - X-Request-ID header propagated automatically from context via logz.GetRequestID on every attempt - DoJSON[T](ctx, client, req) generic helper for typed JSON request/response with xerrors error mapping - MapStatusToError(code, msg) exported function mapping HTTP status codes to xerrors types Tested-via: todo-api POC integration Reviewed-against: docs/adr/
This commit is contained in:
57
README.md
Normal file
57
README.md
Normal file
@@ -0,0 +1,57 @@
|
||||
# httpclient
|
||||
|
||||
Resilient HTTP client with automatic retry and circuit breaking.
|
||||
|
||||
## Install
|
||||
|
||||
```
|
||||
go get code.nochebuena.dev/go/httpclient
|
||||
```
|
||||
|
||||
## Usage
|
||||
|
||||
```go
|
||||
client := httpclient.NewWithDefaults(logger)
|
||||
// or with custom config:
|
||||
client = httpclient.New(logger, httpclient.Config{
|
||||
Name: "payment-api",
|
||||
MaxRetries: 3,
|
||||
CBThreshold: 10,
|
||||
})
|
||||
|
||||
resp, err := client.Do(req)
|
||||
```
|
||||
|
||||
## Typed JSON helper
|
||||
|
||||
```go
|
||||
order, err := httpclient.DoJSON[Order](ctx, client, req)
|
||||
```
|
||||
|
||||
## Error mapping
|
||||
|
||||
```go
|
||||
httpclient.MapStatusToError(404, "not found") // → xerrors.ErrNotFound
|
||||
```
|
||||
|
||||
| HTTP status | xerrors code |
|
||||
|---|---|
|
||||
| 404 | `ErrNotFound` |
|
||||
| 400 | `ErrInvalidInput` |
|
||||
| 401 | `ErrUnauthorized` |
|
||||
| 403 | `ErrPermissionDenied` |
|
||||
| 409 | `ErrAlreadyExists` |
|
||||
| 429 | `ErrUnavailable` |
|
||||
| 5xx | `ErrInternal` |
|
||||
|
||||
## Configuration
|
||||
|
||||
| Env var | Default | Description |
|
||||
|---|---|---|
|
||||
| `HTTP_CLIENT_NAME` | `http` | Circuit breaker name |
|
||||
| `HTTP_TIMEOUT` | `30s` | Overall request timeout |
|
||||
| `HTTP_DIAL_TIMEOUT` | `5s` | TCP dial timeout |
|
||||
| `HTTP_MAX_RETRIES` | `3` | Retry attempts |
|
||||
| `HTTP_RETRY_DELAY` | `1s` | Base retry delay |
|
||||
| `HTTP_CB_THRESHOLD` | `10` | Consecutive failures before open |
|
||||
| `HTTP_CB_TIMEOUT` | `1m` | Time before half-open retry |
|
||||
Reference in New Issue
Block a user