Skip to content
🎉 httpz v1.1.0 released
DocsGuideCertralized Error Handling

Consider the following helloHandler, which returns an error:

func helloHandler(w http.ResponseWriter, r *http.Request) error {
	w.Write([]byte("hello httpz"))
	return nil
}

httpz simply writes an adapter to convert the above handler into the standard library handler below:

http.HandleFunc("GET /hello", func(w http.ResponseWriter, r *http.Request) {
	err := helloHandler(w, r)
 
	if err != nil {
      // Global error handling function
      ErrorHandlerFunc(w, err)
	}
})

This allows us to handle errors centrally. Consider the following example:

main.go
// ...
 
// mux.Get("/hello", helloHandler)
func helloHandler(w http.ResponseWriter, r *http.Request) error {
	name := r.URL.Query().Get("name")
 
	if name == "" {
		return httpz.NewHTTPError(http.StatusBadRequest, "name is required")
	}
 
	fmt.Fprintf(w, "hello %s", name)
	return nil
}

When we visit http://localhost:8080/hello, and name is an empty string, you will see: {"msg":"name is required"}, which is the response returned by our default error handling function.

Default Error Handling Function

// default centralized error handling function.
// only the *HTTPError will trigger error response.
func DefaultErrHandlerFunc(err error, w http.ResponseWriter) {
	if he, ok := err.(*HTTPError); ok {
		rw := NewHelperRW(w)
		rw.JSON(he.StatusCode, he)
	} else {
		slog.Error(err.Error())
	}
}

Note that the default error handling function only triggers a response for errors of type *HTTPError. Other types of errors will only log the error. The reason for this design is that when users return an HTTPError, they clearly know that the error will trigger a response, reducing the possibility of redundant response returns.

You can also customize your own global error handling function:

func main() {
	mux := httpz.NewServeMux()
 
	mux.ErrHandlerFunc = func(err error, w http.ResponseWriter) {
      // It has already been checked that err != nil
      http.Error(w, err.Error(), http.StatusInternalServerError)
	}
}

In this case, all non-nil errors will trigger a response.