The Requests library simplifies the way you make HTTP requests in Go. It provides an easy-to-use interface for sending requests and handling responses, reducing the boilerplate code typically associated with the net/http package.
Begin by installing the Requests library:
go get github.com/kaptinlin/requestsCreating a new HTTP client and making a request is straightforward:
package main
import (
"context"
"log"
"time"
"github.com/kaptinlin/requests"
)
func main() {
// Create a client with functional options (recommended)
client := requests.New(
requests.WithBaseURL("http://example.com"),
requests.WithTimeout(30 * time.Second),
)
// Perform a GET request
resp, err := client.Get("/resource").Send(context.Background())
if err != nil {
log.Fatal(err)
}
defer resp.Close()
log.Println(resp.String())
}The Client struct is your gateway to making HTTP requests. You can configure it to your needs, setting default headers, cookies, timeout durations, and more.
// Functional options (recommended)
client := requests.New(
requests.WithBaseURL("http://example.com"),
requests.WithTimeout(5 * time.Second),
requests.WithContentType("application/json"),
requests.WithBearerAuth("my-token"),
requests.WithMaxRetries(3),
)
// Short form for URL-only clients
client = requests.URL("http://example.com")
// Struct-based configuration (for HTTP/2 or full control)
client = requests.Create(&requests.Config{
BaseURL: "http://example.com",
Timeout: 5 * time.Second,
HTTP2: true,
})The New() constructor returns *Client in a single expression, making it easy to pass into other libraries:
scorer := NewVoyageScorer(
WithHTTPClient(requests.New(
requests.WithTimeout(60 * time.Second),
requests.WithMaxRetries(3),
requests.WithBearerAuth("token"),
)),
)For more details, see docs/client.md.
The library provides a RequestBuilder to construct and dispatch HTTP requests. Here are examples of performing various types of requests, including adding query parameters, setting headers, and attaching a body to your requests.
To retrieve data from a specific resource:
resp, err := client.Get("/path").
Query("search", "query").
Header("Accept", "application/json").
Send(context.Background())To submit data to be processed to a specific resource:
resp, err := client.Post("/path").
Header("Content-Type", "application/json").
JSONBody(map[string]any{"key": "value"}).
Send(context.Background())To replace all current representations of the target resource with the request payload:
resp, err := client.Put("/articles/{article_id}").
PathParam("article_id", "123456").
JSONBody(map[string]any{"updatedKey": "newValue"}).
Send(context.Background())To remove all current representations of the target resource:
resp, err := client.Delete("/articles/{article_id}").
PathParam("article_id", "123456").
Send(context.Background())For more details, visit docs/request.md.
Handling responses is crucial in determining the outcome of your HTTP requests. The Requests library makes it easy to check status codes, read headers, and parse the body content.
Parsing JSON response into a Go struct:
type APIResponse struct {
Data string `json:"data"`
}
var apiResp APIResponse
if err := resp.ScanJSON(&apiResp); err != nil {
log.Fatal(err)
}
log.Printf("Status Code: %d\n", resp.StatusCode())
log.Printf("Response Data: %s\n", apiResp.Data)This example demonstrates how to unmarshal a JSON response and check the HTTP status code.
Additional status helpers: IsSuccess(), IsError(), IsClientError(), IsServerError(), IsRedirect().
For more on handling responses, see docs/response.md.
Configure proxy settings with optional bypass rules:
// Single proxy
client.SetProxy("http://proxy:8080")
// Multiple proxies with round-robin rotation (retries auto-rotate)
client.SetProxies("http://proxy1:8080", "http://proxy2:8080", "socks5://proxy3:1080")
// Proxy with NO_PROXY bypass list
client.SetProxyWithBypass("http://proxy:8080", "localhost, .internal.com, 10.0.0.0/8")
// Use environment variables (HTTP_PROXY, HTTPS_PROXY, NO_PROXY)
client.SetProxyFromEnv()Control redirect behavior including browser-like method downgrade:
// Smart redirect: downgrades POST→GET on 301/302/303, strips sensitive headers cross-host
client.SetRedirectPolicy(requests.NewSmartRedirectPolicy(10))For more details, see docs/client.md.
Fine-grained control over request phases and connection pooling:
client := requests.Create(&requests.Config{
BaseURL: "https://api.example.com",
Timeout: 60 * time.Second, // overall deadline
DialTimeout: 5 * time.Second, // TCP connect
TLSHandshakeTimeout: 5 * time.Second, // TLS negotiation
ResponseHeaderTimeout: 10 * time.Second, // time to first byte
MaxIdleConnsPerHost: 10, // connection pool tuning
})Classify errors without manual type assertion chains:
_, err := client.Get("/resource").Send(ctx)
if requests.IsTimeout(err) {
// Handle timeout (context deadline, net timeout)
}
if requests.IsConnectionError(err) {
// Handle connection failure (DNS, TCP, TLS)
}- Logging: Learn how to configure logging for your requests. See docs/logging.md.
- Middleware: Extend functionality with custom middleware. See docs/middleware.md.
- Retry Mechanism: Implement retry strategies for transient errors. See docs/retry.md.
- Stream Support: Utilize streaming for real-time data processing. See docs/stream.md.
This library was inspired by and built upon the work of several other HTTP client libraries:
Contributions to the requests package are welcome. If you'd like to contribute, please follow the contribution guidelines.
This project is licensed under the MIT License - see the LICENSE file for details.