REST API implementation patterns. Use when building HTTP APIs.
This skill inherits all available tools. When active, it can use any tool Claude has access to.
REST API implementation patterns for Go.
Use when building HTTP APIs.
type Handler struct {
service *Service
logger *log.Logger
}
func NewHandler(service *Service) *Handler {
return &Handler{service: service, logger: log.Default()}
}
func (h *Handler) GetUser(w http.ResponseWriter, r *http.Request) {
ctx := r.Context()
// Parse ID
userID, err := strconv.Atoi(chi.URLParam(r, "id"))
if err != nil {
respondError(w, http.StatusBadRequest, "invalid user ID")
return
}
// Get user
user, err := h.service.GetUser(ctx, userID)
if err != nil {
respondError(w, http.StatusInternalServerError, err.Error())
return
}
respondJSON(w, http.StatusOK, user)
}
func respondJSON(w http.ResponseWriter, status int, data interface{}) {
w.Header().Set("Content-Type", "application/json")
w.WriteStatus(status)
json.NewEncoder(w).Encode(data)
}
func respondError(w http.ResponseWriter, status int, message string) {
respondJSON(w, status, map[string]string{"error": message})
}
// Logging middleware
func loggingMiddleware(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
start := time.Now()
next.ServeHTTP(w, r)
log.Printf("%s %s %v", r.Method, r.URL.Path, time.Since(start))
})
}
// Auth middleware
func authMiddleware(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
token := r.Header.Get("Authorization")
if !isValidToken(token) {
http.Error(w, "Unauthorized", http.StatusUnauthorized)
return
}
next.ServeHTTP(w, r)
})
}
func setupRoutes() http.Handler {
r := chi.NewRouter()
// Middleware
r.Use(middleware.Logger)
r.Use(middleware.Recoverer)
r.Use(corsMiddleware)
// Routes
r.Get("/health", healthHandler)
r.Route("/api/v1", func(r chi.Router) {
r.Use(authMiddleware)
r.Get("/users/{id}", handler.GetUser)
r.Post("/users", handler.CreateUser)
r.Put("/users/{id}", handler.UpdateUser)
r.Delete("/users/{id}", handler.DeleteUser)
})
return r
}
type CreateUserRequest struct {
Name string `json:"name" validate:"required,min=2,max=100"`
Email string `json:"email" validate:"required,email"`
}
func (h *Handler) CreateUser(w http.ResponseWriter, r *http.Request) {
var req CreateUserRequest
if err := json.NewDecoder(r.Body).Decode(&req); err != nil {
respondError(w, http.StatusBadRequest, "invalid JSON")
return
}
if err := validate.Struct(req); err != nil {
respondError(w, http.StatusBadRequest, err.Error())
return
}
// process request
}