Chapter 3.5.
Isolating the application routes
While we’re refactoring our code there’s one more change worth making.
Our main()
function is beginning to get a bit crowded, so to keep it clear and focused I’d like to move the route declarations for the application into a standalone routes.go
file, like so:
$ touch cmd/web/routes.go
package main import "net/http" // The routes() method returns a servemux containing our application routes. func (app *application) routes() *http.ServeMux { mux := http.NewServeMux() fileServer := http.FileServer(http.Dir("./ui/static/")) mux.Handle("GET /static/", http.StripPrefix("/static", fileServer)) mux.HandleFunc("GET /{$}", app.home) mux.HandleFunc("GET /snippet/view/{id}", app.snippetView) mux.HandleFunc("GET /snippet/create", app.snippetCreate) mux.HandleFunc("POST /snippet/create", app.snippetCreatePost) return mux }
We can then update the main.go
file to use this instead:
package main ... func main() { addr := flag.String("addr", ":4000", "HTTP network address") flag.Parse() logger := slog.New(slog.NewTextHandler(os.Stdout, nil)) app := &application{ logger: logger, } logger.Info("starting server", "addr", *addr) // Call the new app.routes() method to get the servemux containing our routes, // and pass that to http.ListenAndServe(). err := http.ListenAndServe(*addr, app.routes()) logger.Error(err.Error()) os.Exit(1) }
This is quite a bit neater. The routes for our application are now isolated and encapsulated in the app.routes()
method, and the responsibilities of our main()
function are limited to:
- Parsing the runtime configuration settings for the application;
- Establishing the dependencies for the handlers; and
- Running the HTTP server.