HTTP healthcheck server minimal di Go
Server Go 30 baris yang expose /health dan /ready endpoint. Cocok untuk Kubernetes liveness probe atau Cloudflare Tunnel.
Dipublikasikan 21 Mei 2026
Kadang yang dibutuhkan hanya HTTP server kecil yang merespon 200 OK untuk monitoring. Service di belakang Cloudflare Tunnel, sidecar untuk Kubernetes, atau status-check internal. Go cocok karena binary-nya kecil (~6 MB) dan startup cepat.
Kode
// healthcheck/main.go
package main
import (
"encoding/json"
"fmt"
"log"
"net/http"
"os"
"runtime"
"time"
)
var startTime = time.Now()
type Status struct {
Status string `json:"status"`
Uptime string `json:"uptime"`
StartedAt string `json:"started_at"`
Memory uint64 `json:"memory_mb"`
Goroutines int `json:"goroutines"`
Version string `json:"version"`
}
func health(w http.ResponseWriter, r *http.Request) {
var m runtime.MemStats
runtime.ReadMemStats(&m)
status := Status{
Status: "ok",
Uptime: time.Since(startTime).Round(time.Second).String(),
StartedAt: startTime.UTC().Format(time.RFC3339),
Memory: m.Alloc / 1024 / 1024,
Goroutines: runtime.NumGoroutine(),
Version: os.Getenv("APP_VERSION"),
}
w.Header().Set("Content-Type", "application/json")
w.WriteHeader(http.StatusOK)
json.NewEncoder(w).Encode(status)
}
func ready(w http.ResponseWriter, r *http.Request) {
// Tambahkan check ke dependencies (DB, cache, dst) di sini
// Contoh: cek koneksi DB; kalau gagal, return 503
w.WriteHeader(http.StatusOK)
fmt.Fprintln(w, "ready")
}
func main() {
port := os.Getenv("PORT")
if port == "" {
port = "8080"
}
mux := http.NewServeMux()
mux.HandleFunc("/health", health)
mux.HandleFunc("/ready", ready)
srv := &http.Server{
Addr: ":" + port,
Handler: mux,
ReadTimeout: 5 * time.Second,
WriteTimeout: 10 * time.Second,
}
log.Printf("Healthcheck server listening on :%s", port)
if err := srv.ListenAndServe(); err != nil {
log.Fatal(err)
}
}
Build & run
go mod init healthcheck
go build -o healthcheck main.go
# Run
PORT=8080 APP_VERSION=v1.0.0 ./healthcheck
# Test
curl http://localhost:8080/health
# {"status":"ok","uptime":"1m23s","memory_mb":1,"goroutines":7,"version":"v1.0.0"}
Build untuk Docker
# Dockerfile
FROM golang:1.22-alpine AS build
WORKDIR /app
COPY . .
RUN CGO_ENABLED=0 go build -ldflags="-s -w" -o healthcheck
FROM scratch
COPY --from=build /app/healthcheck /healthcheck
EXPOSE 8080
ENTRYPOINT ["/healthcheck"]
Hasilnya: image Docker ~6 MB total.
Kapan dipakai
- Microservice yang butuh liveness/readiness probe Kubernetes.
- Status page sidecar — di-poll oleh Uptime Robot, Healthchecks.io, atau Bettercheck.
- Smoke test sebelum routing traffic ke deployment baru.
Catatan
- Tidak ada dependency external — pakai
net/httpstdlib. Tidak butuh framework seperti Echo atau Fiber untuk use case sederhana ini. runtime.MemStatsngecek heap saat ini, bukan keseluruhan memory process. Untuk metric yang akurat, pakai Prometheus client.- Cross-compile ke ARM (Raspberry Pi):
GOOS=linux GOARCH=arm64 go build. - Graceful shutdown tidak ada di snippet ini. Untuk production, tambahkan signal handling:
go func() {
if err := srv.ListenAndServe(); err != nil && err != http.ErrServerClosed {
log.Fatal(err)
}
}()
stop := make(chan os.Signal, 1)
signal.Notify(stop, os.Interrupt, syscall.SIGTERM)
<-stop
ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
defer cancel()
srv.Shutdown(ctx)
Untuk Cloudflare Tunnel,
cloudflaredbutuh service jalan di port yang ditentukan di config. Pakai snippet ini sebagai dummy service untuk test routing sebelum bikin app sungguhan.
# tags
healthcheckkubernetesuptimeminimal