Net
The net package provides utilities for HTTP response handling, concurrent file downloads, and pointer helper functions.
Installation
import "github.com/leoheung/go-patterns/net"API Reference
Concurrent Download
Download files using multiple goroutines with progress tracking.
// Concurrent download with 4 workers
err := net.DownloadFileByConcurrent("https://example.com/file.zip", "./downloads/", 4)Stream Download
Stream any io.Reader to HTTP response with proper headers. Supports both fixed-size and chunked transfer.
// Stream download with known file size
fileData := bytes.NewReader(fileBytes)
size := int64(len(fileBytes))
net.StreamDownloadHandler(w, fileData, "report.pdf", "application/pdf", &size)
// Stream download with unknown size (uses chunked transfer)
s3Reader := getS3ObjectReader(key)
net.StreamDownloadHandler(w, s3Reader, "backup.zip", "application/zip", nil)Parameters:
w: HTTP ResponseWriterreader: Any io.Reader (file, memory buffer, S3 object, etc.)filename: Download filename shown to usercontentType: MIME type (e.g., "application/pdf", "application/octet-stream")size: File size pointer (optional, pass nil for chunked transfer)
WebSocket Manager
A high-level WebSocket connection management framework. See WebSocket Documentation for details.
import "github.com/leoheung/go-patterns/net/wrapsocket"
// Create WebSocket handler
handler := wrapsocket.NewDefaultHandler(nil)
// Set callbacks
handler.SetOnConnect(func(conn *wrapsocket.Conn) {
fmt.Printf("Client connected: %s\n", conn.ID)
})
handler.SetOnMessage(func(conn *wrapsocket.Conn, msg *wrapsocket.Message) {
// Echo message back
conn.Write(ctx, msg.Type, msg.Data)
})
http.ListenAndServe(":8080", handler)Features:
- Connection lifecycle management
- Heartbeat detection
- Group broadcasting
- Metadata storage
HTTP Response Helpers
Standardized JSON and CSV response helpers for web services.
// Return a standardized JSON success response
net.ReturnJsonResponse(w, http.StatusOK, map[string]string{"message": "success"})
// Return a standardized JSON error response
net.ReturnErrorResponse(w, http.StatusBadRequest, "invalid input")
// Return a CSV file response
headers := []string{"ID", "Name"}
rows := [][]string{{"1", "Alice"}, {"2", "Bob"}}
net.ReturnCSVResponse(w, "users.csv", headers, rows)Chi Router Utilities
// Print all registered routes in a Chi mux
net.PrintCHIRoutes(r)Shared HTTP Client
Thread-safe reusable HTTP client with connection pooling. See Clients Documentation for details.
// Initialize shared HTTP client
clients.InitDefaultSharedHTTPClient()
// Make requests
resp, headers, code, err := clients.Request(req)Features:
- Connection pooling with configurable limits
- TLS and proxy configuration
- Built-in panic recovery
- Generic JSON response parsing
Pointer Helpers
Commonly used to create pointers for primitive types (useful for database models).
s := net.PtrString("hello")
i := net.PtrInt(100)
b := net.PtrBool(true)
t := net.PtrTime(time.Now())Safe Body Reading
Reads HTTP request/response body safely with size limit to prevent memory issues.
// Read body with size limit (in MB)
data, err := net.SafelyReadBody(r.Body, net.PtrInt(10))
if err != nil {
log.Fatal(err)
}
fmt.Printf("Read %d bytes\n", len(data))Deep Copy HTTP Request
Creates a complete deep copy of an HTTP request, including the body content.
// Deep copy a request with 10MB body limit
reqCopy, err := net.DeepCopyRequest(r, 10)
if err != nil {
log.Fatal(err)
}
// Now you can process reqCopy without affecting the original r.Body
process(reqCopy)
next.ServeHTTP(w, r) // Original request still has its body intactDeep Copy HTTP Response
Creates a complete deep copy of an HTTP response, including the body content.
// Deep copy a response with 10MB body limit
respCopy, err := net.DeepCopyResponse(resp, 10)
if err != nil {
log.Fatal(err)
}
// Now you can process respCopy without affecting the original
cacheResponse(respCopy)Complete Example
package main
import (
"net/http"
"github.com/go-chi/chi/v5"
"github.com/leoheung/go-patterns/net"
)
func main() {
r := chi.NewRouter()
r.Get("/api/data", func(w http.ResponseWriter, r *http.Request) {
data := struct {
ID int `json:"id"`
Name string `json:"name"`
}{ID: 1, Name: "Pattern"}
net.ReturnJsonResponse(w, http.StatusOK, data)
})
// Print routes for debugging
net.PrintCHIRoutes(r)
// Download a file concurrently
go net.DownloadFileByConcurrent("https://example.com/large-file.bin", "./tmp/", 8)
http.ListenAndServe(":8080", r)
}Features
- Concurrent Download: Multi-threaded downloading with automatic filename resolution.
- Standardized Responses: Consistent
UniversalResponsestructure for JSON APIs. - Route Debugging: Easily visualize Chi router structures.
- Pointer Utils: Convenient helpers for handling optional fields in structs.
- Safe Body Reading: Prevent memory issues by limiting body size.
- Deep Copy Request/Response: Complete deep copy of HTTP messages for middleware processing.