http

package
v1.2.3 Latest Latest
Warning

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

Go to latest
Published: Dec 23, 2025 License: Apache-2.0 Imports: 6 Imported by: 3

README

HTTP

Simplified HTTP client and server utilities for Go.

Overview

The http package provides convenient wrapper functions around Go's standard net/http and gorilla/mux packages. It simplifies making HTTP requests and managing HTTP servers with powerful routing capabilities while reducing boilerplate code.

Features

  • HTTP Client - Simplified request function with built-in authentication
  • HTTP Server - Easy server setup with gorilla/mux routing
  • Handler Registration - Multiple registration methods for different use cases
  • Path Prefix Routing - Route groups and static file serving
  • Middleware Support - Chain middleware functions
  • Graceful Shutdown - Proper server lifecycle management
  • Custom Transport - Configure HTTP client transport settings

Installation

go get -u github.com/common-library/go/http
go get -u github.com/gorilla/mux

Quick Start

HTTP Client
import "github.com/common-library/go/http"

func main() {
    resp, err := http.Request(
        "https://api.example.com/users",
        http.MethodGet,
        nil,  // headers
        "",   // body
        10,   // timeout in seconds
        "",   // username
        "",   // password
        nil,  // transport
    )
    if err != nil {
        log.Fatal(err)
    }
    
    fmt.Printf("Status: %d\n", resp.StatusCode)
    fmt.Printf("Body: %s\n", resp.Body)
}
HTTP Server
import (
    "net/http"
    "github.com/common-library/go/http"
)

func main() {
    var server http.Server
    
    // Register handlers
    server.RegisterHandlerFunc("/", func(w http.ResponseWriter, r *http.Request) {
        w.Write([]byte("Hello, World!"))
    })
    
    server.RegisterHandlerFunc("/api/users", usersHandler, http.MethodGet)
    
    // Start server
    err := server.Start(":8080", func(err error) {
        log.Fatal(err)
    })
    if err != nil {
        log.Fatal(err)
    }
    
    // Keep running
    select {}
}

HTTP Client

Request Function
func Request(
    url string,
    method string,
    header map[string][]string,
    body string,
    timeout time.Duration,
    username string,
    password string,
    transport *http.Transport,
) (Response, error)

Performs an HTTP request and returns the complete response.

Parameters:

  • url - Target URL
  • method - HTTP method (http.MethodGet, http.MethodPost, etc.)
  • header - HTTP headers as map[string][]string
  • body - Request body as string
  • timeout - Request timeout in seconds
  • username - Username for Basic Auth (empty for no auth)
  • password - Password for Basic Auth (empty for no auth)
  • transport - Custom HTTP transport (nil for default)

Returns:

  • Response - Response struct with Header, Body, and StatusCode
  • error - Error if request fails
Response Type
type Response struct {
    Header     http.Header
    Body       string
    StatusCode int
}
Client Examples
Simple GET Request
resp, err := http.Request(
    "https://api.example.com/users",
    http.MethodGet,
    nil,
    "",
    10,
    "", "",
    nil,
)
if err != nil {
    log.Fatal(err)
}

fmt.Printf("Status: %d\n", resp.StatusCode)
fmt.Printf("Body: %s\n", resp.Body)
POST Request with JSON
headers := map[string][]string{
    "Content-Type": {"application/json"},
}

body := `{
    "name": "Alice",
    "email": "alice@example.com"
}`

resp, err := http.Request(
    "https://api.example.com/users",
    http.MethodPost,
    headers,
    body,
    30,
    "", "",
    nil,
)

if err != nil {
    log.Fatal(err)
}

fmt.Printf("Created user, status: %d\n", resp.StatusCode)
Request with Authentication
resp, err := http.Request(
    "https://api.example.com/admin/stats",
    http.MethodGet,
    nil,
    "",
    10,
    "admin",      // username
    "password123", // password
    nil,
)

if err != nil {
    log.Fatal(err)
}

if resp.StatusCode == 401 {
    log.Println("Authentication failed")
} else {
    fmt.Println(resp.Body)
}
Request with Custom Headers
headers := map[string][]string{
    "Authorization": {"Bearer token123"},
    "X-API-Key":     {"secret456"},
    "Accept":        {"application/json"},
}

resp, err := http.Request(
    "https://api.example.com/data",
    http.MethodGet,
    headers,
    "",
    15,
    "", "",
    nil,
)
Request with Custom Transport
import "crypto/tls"

// Skip TLS verification (not recommended for production)
transport := &http.Transport{
    TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
}

resp, err := http.Request(
    "https://self-signed.example.com/api",
    http.MethodGet,
    nil,
    "",
    10,
    "", "",
    transport,
)

HTTP Server

Server Type
type Server struct {
    // Contains unexported fields
}
Handler Registration Methods
RegisterHandler
func (s *Server) RegisterHandler(path string, handler http.Handler, methods ...string)

Registers an HTTP handler for a specific path.

Example:

type MyHandler struct{}

func (h *MyHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
    w.Write([]byte("Hello from handler"))
}

var server http.Server

// All methods
server.RegisterHandler("/api", &MyHandler{})

// GET only
server.RegisterHandler("/users", &MyHandler{}, http.MethodGet)

// GET and POST
server.RegisterHandler("/items", &MyHandler{}, http.MethodGet, http.MethodPost)
RegisterHandlerFunc
func (s *Server) RegisterHandlerFunc(path string, handlerFunc http.HandlerFunc, methods ...string)

Registers an HTTP handler function for a specific path.

Example:

var server http.Server

// All methods
server.RegisterHandlerFunc("/ping", func(w http.ResponseWriter, r *http.Request) {
    w.Write([]byte("pong"))
})

// GET only
server.RegisterHandlerFunc("/users", func(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Content-Type", "application/json")
    w.Write([]byte(`[{"id": 1, "name": "Alice"}]`))
}, http.MethodGet)

// POST only
server.RegisterHandlerFunc("/users", func(w http.ResponseWriter, r *http.Request) {
    // Create user
    w.WriteHeader(http.StatusCreated)
}, http.MethodPost)
RegisterPathPrefixHandler
func (s *Server) RegisterPathPrefixHandler(prefix string, handler http.Handler, methods ...string)

Registers a handler for all paths matching the prefix.

Example:

// Serve static files
fileServer := http.FileServer(http.Dir("./static"))
server.RegisterPathPrefixHandler("/static/", http.StripPrefix("/static/", fileServer))

// API v1 endpoints
server.RegisterPathPrefixHandler("/api/v1/", apiV1Handler, http.MethodGet)
RegisterPathPrefixHandlerFunc
func (s *Server) RegisterPathPrefixHandlerFunc(prefix string, handlerFunc http.HandlerFunc, methods ...string)

Registers a handler function for paths matching the prefix.

Example:

server.RegisterPathPrefixHandlerFunc("/api/", func(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Content-Type", "application/json")
    w.Write([]byte(`{"status": "ok"}`))
})
Server Lifecycle
Start
func (s *Server) Start(address string, listenAndServeFailureFunc func(err error), middlewareFunc ...mux.MiddlewareFunc) error

Starts the HTTP server.

Example:

var server http.Server

// Simple start
err := server.Start(":8080", func(err error) {
    log.Fatal(err)
})

// With middleware
loggingMiddleware := func(next http.Handler) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        log.Printf("%s %s", r.Method, r.URL.Path)
        next.ServeHTTP(w, r)
    })
}

err = server.Start(":8080", nil, loggingMiddleware)
Stop
func (s *Server) Stop(shutdownTimeout time.Duration) error

Gracefully shuts down the server.

Example:

// Shutdown with 30 second timeout
err := server.Stop(30)
if err != nil {
    log.Printf("Shutdown error: %v", err)
}
SetRouter
func (s *Server) SetRouter(router *mux.Router)

Sets a custom router.

Example:

router := mux.NewRouter()
router.StrictSlash(true)
router.HandleFunc("/", homeHandler)

var server http.Server
server.SetRouter(router)
server.Start(":8080", nil)

Complete Examples

REST API Server
package main

import (
    "encoding/json"
    "log"
    "net/http"
    
    httplib "github.com/common-library/go/http"
)

type User struct {
    ID   int    `json:"id"`
    Name string `json:"name"`
}

var users = []User{
    {ID: 1, Name: "Alice"},
    {ID: 2, Name: "Bob"},
}

func main() {
    var server httplib.Server
    
    // GET /api/users - List all users
    server.RegisterHandlerFunc("/api/users", func(w http.ResponseWriter, r *http.Request) {
        w.Header().Set("Content-Type", "application/json")
        json.NewEncoder(w).Encode(users)
    }, http.MethodGet)
    
    // POST /api/users - Create user
    server.RegisterHandlerFunc("/api/users", func(w http.ResponseWriter, r *http.Request) {
        var user User
        if err := json.NewDecoder(r.Body).Decode(&user); err != nil {
            http.Error(w, err.Error(), http.StatusBadRequest)
            return
        }
        
        user.ID = len(users) + 1
        users = append(users, user)
        
        w.Header().Set("Content-Type", "application/json")
        w.WriteHeader(http.StatusCreated)
        json.NewEncoder(w).Encode(user)
    }, http.MethodPost)
    
    log.Println("Server starting on :8080")
    server.Start(":8080", func(err error) {
        log.Fatal(err)
    })
    
    select {}
}
Static File Server
package main

import (
    "log"
    "net/http"
    
    httplib "github.com/common-library/go/http"
)

func main() {
    var server httplib.Server
    
    // Serve static files from ./public directory
    fileServer := http.FileServer(http.Dir("./public"))
    server.RegisterPathPrefixHandler("/", fileServer)
    
    log.Println("Static file server on :8080")
    server.Start(":8080", nil)
    
    select {}
}
Server with Middleware
package main

import (
    "log"
    "net/http"
    "time"
    
    "github.com/gorilla/mux"
    httplib "github.com/common-library/go/http"
)

func loggingMiddleware(next http.Handler) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        start := time.Now()
        log.Printf("Started %s %s", r.Method, r.URL.Path)
        
        next.ServeHTTP(w, r)
        
        log.Printf("Completed in %v", time.Since(start))
    })
}

func authMiddleware(next http.Handler) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        apiKey := r.Header.Get("X-API-Key")
        if apiKey != "secret123" {
            http.Error(w, "Unauthorized", http.StatusUnauthorized)
            return
        }
        
        next.ServeHTTP(w, r)
    })
}

func main() {
    var server httplib.Server
    
    server.RegisterHandlerFunc("/api/data", func(w http.ResponseWriter, r *http.Request) {
        w.Write([]byte("Authenticated data"))
    })
    
    server.Start(":8080", nil, loggingMiddleware, authMiddleware)
    
    select {}
}
Server with Graceful Shutdown
package main

import (
    "log"
    "net/http"
    "os"
    "os/signal"
    "syscall"
    
    httplib "github.com/common-library/go/http"
)

func main() {
    var server httplib.Server
    
    server.RegisterHandlerFunc("/", func(w http.ResponseWriter, r *http.Request) {
        w.Write([]byte("Hello, World!"))
    })
    
    // Start server
    log.Println("Starting server on :8080")
    server.Start(":8080", func(err error) {
        log.Printf("Server error: %v", err)
    })
    
    // Wait for interrupt signal
    sigChan := make(chan os.Signal, 1)
    signal.Notify(sigChan, os.Interrupt, syscall.SIGTERM)
    <-sigChan
    
    log.Println("Shutting down server...")
    if err := server.Stop(30); err != nil {
        log.Printf("Shutdown error: %v", err)
    }
    
    log.Println("Server stopped gracefully")
}
API Client Wrapper
package main

import (
    "encoding/json"
    "fmt"
    "log"
    "net/http"
    
    httplib "github.com/common-library/go/http"
)

type APIClient struct {
    baseURL string
    apiKey  string
}

func NewAPIClient(baseURL, apiKey string) *APIClient {
    return &APIClient{
        baseURL: baseURL,
        apiKey:  apiKey,
    }
}

func (c *APIClient) GetUsers() ([]User, error) {
    headers := map[string][]string{
        "Authorization": {fmt.Sprintf("Bearer %s", c.apiKey)},
        "Accept":        {"application/json"},
    }
    
    resp, err := httplib.Request(
        c.baseURL+"/api/users",
        http.MethodGet,
        headers,
        "",
        10,
        "", "",
        nil,
    )
    if err != nil {
        return nil, err
    }
    
    if resp.StatusCode != 200 {
        return nil, fmt.Errorf("API error: %d", resp.StatusCode)
    }
    
    var users []User
    if err := json.Unmarshal([]byte(resp.Body), &users); err != nil {
        return nil, err
    }
    
    return users, nil
}

func (c *APIClient) CreateUser(user User) error {
    headers := map[string][]string{
        "Authorization": {fmt.Sprintf("Bearer %s", c.apiKey)},
        "Content-Type":  {"application/json"},
    }
    
    body, _ := json.Marshal(user)
    
    resp, err := httplib.Request(
        c.baseURL+"/api/users",
        http.MethodPost,
        headers,
        string(body),
        10,
        "", "",
        nil,
    )
    if err != nil {
        return err
    }
    
    if resp.StatusCode != 201 {
        return fmt.Errorf("API error: %d - %s", resp.StatusCode, resp.Body)
    }
    
    return nil
}

func main() {
    client := NewAPIClient("https://api.example.com", "secret123")
    
    users, err := client.GetUsers()
    if err != nil {
        log.Fatal(err)
    }
    
    for _, user := range users {
        fmt.Printf("User: %+v\n", user)
    }
}

Best Practices

1. Always Set Timeouts
// Good: Set reasonable timeout
resp, err := http.Request(url, http.MethodGet, nil, "", 30, "", "", nil)

// Avoid: Very long or no timeout
// May hang indefinitely
2. Handle Response Status Codes
// Good: Check status code
resp, err := http.Request(url, http.MethodGet, nil, "", 10, "", "", nil)
if err != nil {
    log.Fatal(err)
}

switch resp.StatusCode {
case 200:
    fmt.Println("Success:", resp.Body)
case 404:
    fmt.Println("Not found")
case 500:
    fmt.Println("Server error")
default:
    fmt.Printf("Unexpected status: %d\n", resp.StatusCode)
}

// Avoid: Ignoring status code
// resp, _ := http.Request(...)
// fmt.Println(resp.Body) // May not be what you expect
3. Use Proper HTTP Methods
// Good: Use correct method constants
http.Request(url, http.MethodGet, ...)
http.Request(url, http.MethodPost, ...)
http.Request(url, http.MethodPut, ...)

// Avoid: String literals
// http.Request(url, "GET", ...)
4. Set Content-Type Headers
// Good: Set Content-Type for POST/PUT
headers := map[string][]string{
    "Content-Type": {"application/json"},
}

resp, _ := http.Request(url, http.MethodPost, headers, jsonBody, 10, "", "", nil)

// Avoid: Missing Content-Type
// Server may not parse body correctly
5. Implement Graceful Shutdown
// Good: Graceful shutdown
sigChan := make(chan os.Signal, 1)
signal.Notify(sigChan, os.Interrupt, syscall.SIGTERM)
<-sigChan

server.Stop(30) // Wait for active connections

// Avoid: Abrupt termination
// os.Exit(0) // May interrupt active requests
6. Use Middleware for Cross-Cutting Concerns
// Good: Centralize logging, auth, CORS in middleware
server.Start(":8080", nil, loggingMiddleware, authMiddleware, corsMiddleware)

// Avoid: Repeating logic in every handler
// Each handler implements its own logging

Error Handling

Client Errors
resp, err := http.Request(url, http.MethodGet, nil, "", 10, "", "", nil)
if err != nil {
    // Network error, timeout, DNS failure, etc.
    log.Printf("Request failed: %v", err)
    return
}

// Check HTTP status
if resp.StatusCode >= 400 {
    log.Printf("HTTP error: %d - %s", resp.StatusCode, resp.Body)
}
Server Errors
server.RegisterHandlerFunc("/api/data", func(w http.ResponseWriter, r *http.Request) {
    data, err := fetchData()
    if err != nil {
        http.Error(w, "Internal server error", http.StatusInternalServerError)
        log.Printf("Error fetching data: %v", err)
        return
    }
    
    w.Header().Set("Content-Type", "application/json")
    json.NewEncoder(w).Encode(data)
})

Performance Tips

  1. Connection Reuse - HTTP client reuses connections automatically
  2. Timeouts - Set appropriate timeouts to prevent hanging requests
  3. Custom Transport - Use transport for connection pooling configuration
  4. Middleware Ordering - Order middleware from general to specific
  5. Graceful Shutdown - Allow active requests to complete

Testing

Unit Testing HTTP Handlers
func TestUserHandler(t *testing.T) {
    req := httptest.NewRequest(http.MethodGet, "/api/users", nil)
    rec := httptest.NewRecorder()
    
    userHandler(rec, req)
    
    if rec.Code != http.StatusOK {
        t.Errorf("Expected status 200, got %d", rec.Code)
    }
}
Integration Testing
func TestServer(t *testing.T) {
    var server httplib.Server
    
    server.RegisterHandlerFunc("/test", func(w http.ResponseWriter, r *http.Request) {
        w.Write([]byte("test response"))
    })
    
    server.Start(":8081", nil)
    defer server.Stop(5)
    
    time.Sleep(100 * time.Millisecond) // Wait for server
    
    resp, err := httplib.Request(
        "http://localhost:8081/test",
        http.MethodGet,
        nil, "", 5, "", "", nil,
    )
    
    if err != nil {
        t.Fatal(err)
    }
    
    if resp.StatusCode != 200 {
        t.Errorf("Expected 200, got %d", resp.StatusCode)
    }
    
    if resp.Body != "test response" {
        t.Errorf("Unexpected body: %s", resp.Body)
    }
}

Dependencies

  • net/http - Go standard library
  • github.com/gorilla/mux - HTTP router and dispatcher

Further Reading

Documentation

Overview

Package http provides simplified HTTP client and server utilities.

This package wraps Go's standard net/http and gorilla/mux packages, offering convenient functions for making HTTP requests and managing HTTP servers with routing capabilities.

Features:

  • Simplified HTTP client with authentication support
  • HTTP server with routing (powered by gorilla/mux)
  • Handler and middleware registration
  • Path prefix routing
  • Graceful server shutdown
  • Custom transport configuration

Example:

// Client
resp, _ := http.Request("http://api.example.com", http.MethodGet, nil, "", 10, "", "", nil)

// Server
var server http.Server
server.RegisterHandlerFunc("/api", handler)
server.Start(":8080", nil)

Package http provides simplified HTTP client and server utilities.

This package wraps Go's standard net/http and gorilla/mux packages, offering convenient functions for making HTTP requests and managing HTTP servers with routing capabilities.

Features:

  • Simplified HTTP client with authentication support
  • HTTP server with routing (powered by gorilla/mux)
  • Handler and middleware registration
  • Path prefix routing
  • Graceful server shutdown
  • Custom transport configuration

Example:

// Client
resp, _ := http.Request("http://api.example.com", http.MethodGet, nil, "", 10, "", "", nil)

// Server
var server http.Server
server.RegisterHandlerFunc("/api", handler)
server.Start(":8080", nil)

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type Response

type Response struct {
	Header     http.Header
	Body       string
	StatusCode int
}

Response is response information.

func Request

func Request(url, method string, header map[string][]string, body string, timeout time.Duration, username, password string, transport *http.Transport) (Response, error)

Request performs an HTTP request and returns the response.

Parameters:

  • url: Target URL for the HTTP request
  • method: HTTP method (http.MethodGet, http.MethodPost, etc.)
  • header: HTTP headers as a map of header names to value slices
  • body: Request body as a string
  • timeout: Request timeout in seconds
  • username: Username for HTTP Basic Authentication (empty string for no auth)
  • password: Password for HTTP Basic Authentication (empty string for no auth)
  • transport: Custom HTTP transport configuration (nil for default)

Returns:

  • Response: HTTP response containing headers, body, and status code
  • error: Error if request fails, nil on success

The function creates an HTTP client with the specified timeout and transport settings, performs the request, and returns the complete response. The response body is read entirely into memory.

Example:

// Simple GET request
resp, err := http.Request(
    "https://api.example.com/users",
    http.MethodGet,
    nil,  // no headers
    "",   // no body
    10,   // 10 second timeout
    "",   // no username
    "",   // no password
    nil,  // default transport
)
if err != nil {
    log.Fatal(err)
}
fmt.Printf("Status: %d\n", resp.StatusCode)
fmt.Printf("Body: %s\n", resp.Body)

// POST request with headers and authentication
headers := map[string][]string{
    "Content-Type": {"application/json"},
    "X-API-Key":    {"secret123"},
}
body := `{"name": "Alice", "email": "alice@example.com"}`
resp, err = http.Request(
    "https://api.example.com/users",
    http.MethodPost,
    headers,
    body,
    30,
    "admin",
    "password123",
    nil,
)

type Server

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

Server is a struct that provides server related methods.

func (*Server) RegisterHandler added in v1.1.8

func (s *Server) RegisterHandler(path string, handler http.Handler, methods ...string)

RegisterHandler registers an HTTP handler for the specified path.

Parameters:

  • path: URL path pattern to match (e.g., "/api/users")
  • handler: HTTP handler to handle requests
  • methods: Optional HTTP methods to restrict (e.g., http.MethodGet, http.MethodPost)

If no methods are specified, the handler accepts all HTTP methods. Multiple methods can be provided to restrict the handler to specific request types.

Example:

// Handle all methods
server.RegisterHandler("/api/health", healthHandler)

// Handle only GET requests
server.RegisterHandler("/api/users", usersHandler, http.MethodGet)

// Handle GET and POST requests
server.RegisterHandler("/api/items", itemsHandler, http.MethodGet, http.MethodPost)

func (*Server) RegisterHandlerFunc added in v1.1.6

func (s *Server) RegisterHandlerFunc(path string, handlerFunc http.HandlerFunc, methods ...string)

RegisterHandlerFunc registers an HTTP handler function for the specified path.

Parameters:

  • path: URL path pattern to match (e.g., "/api/users")
  • handlerFunc: HTTP handler function to handle requests
  • methods: Optional HTTP methods to restrict (e.g., http.MethodGet, http.MethodPost)

This is a convenience method for registering handler functions directly without wrapping them in a Handler type. If no methods are specified, accepts all HTTP methods.

Example:

// Handle all methods
server.RegisterHandlerFunc("/api/ping", func(w http.ResponseWriter, r *http.Request) {
    w.Write([]byte("pong"))
})

// Handle only GET requests
server.RegisterHandlerFunc("/api/users", getUsersHandler, http.MethodGet)

// Handle GET and POST requests
server.RegisterHandlerFunc("/api/data", dataHandler, http.MethodGet, http.MethodPost)

func (*Server) RegisterPathPrefixHandler added in v1.1.6

func (s *Server) RegisterPathPrefixHandler(prefix string, handler http.Handler, methods ...string)

RegisterPathPrefixHandler registers an HTTP handler for all paths matching the prefix.

Parameters:

  • prefix: URL path prefix to match (e.g., "/static/", "/api/v1/")
  • handler: HTTP handler to handle requests
  • methods: Optional HTTP methods to restrict (e.g., http.MethodGet, http.MethodPost)

This method matches all paths that start with the specified prefix. Useful for serving static files or grouping related endpoints. If no methods are specified, accepts all HTTP methods.

Example:

// Serve static files (all methods)
fileServer := http.FileServer(http.Dir("./static"))
server.RegisterPathPrefixHandler("/static/", fileServer)

// API v1 endpoints (GET only)
server.RegisterPathPrefixHandler("/api/v1/", apiV1Handler, http.MethodGet)

// Admin endpoints (GET and POST)
server.RegisterPathPrefixHandler("/admin/", adminHandler, http.MethodGet, http.MethodPost)

func (*Server) RegisterPathPrefixHandlerFunc added in v1.1.8

func (s *Server) RegisterPathPrefixHandlerFunc(prefix string, handlerFunc http.HandlerFunc, methods ...string)

RegisterPathPrefixHandlerFunc registers an HTTP handler function for paths matching the prefix.

Parameters:

  • prefix: URL path prefix to match (e.g., "/static/", "/api/v1/")
  • handlerFunc: HTTP handler function to handle requests
  • methods: Optional HTTP methods to restrict (e.g., http.MethodGet, http.MethodPost)

This is a convenience method for registering handler functions for path prefixes without wrapping them in a Handler type. Matches all paths starting with the prefix. If no methods are specified, accepts all HTTP methods.

Example:

// Handle all /api/ requests
server.RegisterPathPrefixHandlerFunc("/api/", func(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Content-Type", "application/json")
    w.Write([]byte(`{"status": "ok"}`))
})

// Handle /files/ with GET only
server.RegisterPathPrefixHandlerFunc("/files/", filesHandler, http.MethodGet)

func (*Server) SetRouter

func (s *Server) SetRouter(router *mux.Router)

SetRouter sets a custom router for the server.

Parameters:

  • router: gorilla/mux router instance, or nil to reset

This method allows using a pre-configured router instead of the default one. Setting the router to nil will reset it, and a new router will be created on the next operation. This is useful for advanced routing configurations or testing.

Example:

// Use custom router
router := mux.NewRouter()
router.StrictSlash(true)
router.HandleFunc("/", homeHandler)

var server http.Server
server.SetRouter(router)
server.Start(":8080", nil)

// Reset router
server.SetRouter(nil)

func (*Server) Start

func (s *Server) Start(address string, listenAndServeFailureFunc func(err error), middlewareFunc ...mux.MiddlewareFunc) error

Start starts the HTTP server on the specified address.

Parameters:

  • address: Address to bind the server to (e.g., ":8080", "localhost:8080")
  • listenAndServeFailureFunc: Optional callback function called if server fails to start
  • middlewareFunc: Optional middleware functions to apply to all requests

Returns:

  • error: Always returns nil (errors are reported via listenAndServeFailureFunc)

The server starts in a background goroutine, so this method returns immediately. If no middleware is provided, a pass-through middleware is added. Multiple middleware functions are executed in the order provided.

Example:

var server http.Server
server.RegisterHandlerFunc("/api", apiHandler)

// Start without middleware
err := server.Start(":8080", func(err error) {
    log.Fatal(err)
})

// Start with logging middleware
loggingMiddleware := func(next http.Handler) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        log.Printf("%s %s", r.Method, r.URL.Path)
        next.ServeHTTP(w, r)
    })
}
err = server.Start(":8080", nil, loggingMiddleware)

func (*Server) Stop

func (s *Server) Stop(shutdownTimeout time.Duration) error

Stop gracefully shuts down the HTTP server.

Parameters:

  • shutdownTimeout: Maximum duration in seconds to wait for active connections to complete

Returns:

  • error: Error if shutdown fails or times out, nil on successful shutdown

The server stops accepting new connections immediately and waits for active connections to complete within the timeout period. After the timeout, remaining connections are forcefully closed. The router is reset to nil after shutdown.

Example:

var server http.Server
server.Start(":8080", nil)

// Later, graceful shutdown with 30 second timeout
err := server.Stop(30)
if err != nil {
    log.Printf("Shutdown error: %v", err)
}
log.Println("Server stopped gracefully")

Jump to

Keyboard shortcuts

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