Gorilla mux optional query values

If you register query parameters they are required doc:

All variables defined in the route are required, and their values must conform to the corresponding patterns.

Because those parameters are optional you just need to check for them inside of a handler function: id, found := mux.Vars(r)["id"]. Where found will show if the parameter in the query or not.


Seems like the best way to handle optional URL parameters is to define your router as normal without them, then parse the optional params out like this:

urlParams := request.URL.Query()

This returns a map that contains the URL parameters as Key/Value pairs.


I would just register your handler twice.

router.Path("/articles/{id:[0-9]+}").
    Queries("key", "{[0-9]*?}").
    HandlerFunc(YourHandler).
    Name("YourHandler")

router.Path("/articles/{id:[0-9]+}").HandlerFunc(YourHandler)

Here is a working program to demonstrate. Notice that I am using r.FormValue to get the query parameter.

Note: make sure you have an up to date version go get -u github.com/gorilla/mux since a bug of query params not getting added the built URLs was fixed recently.

package main

import (
    "fmt"
    "log"
    "net/http"

    "github.com/gorilla/mux"
)

var router = mux.NewRouter()

func main() {
    router.Path("/articles/{id:[0-9]+}").Queries("key", "{key}").HandlerFunc(YourHandler).Name("YourHandler")
    router.Path("/articles/{id:[0-9]+}").HandlerFunc(YourHandler)

    if err := http.ListenAndServe(":9000", router); err != nil {
        log.Fatal(err)
    }
}

func YourHandler(w http.ResponseWriter, r *http.Request) {
    id := mux.Vars(r)["id"]
    key := r.FormValue("key")

    u, err := router.Get("YourHandler").URL("id", id, "key", key)
    if err != nil {
        http.Error(w, err.Error(), 500)
        return
    }

    // Output:
    // /articles/10?key=[key]
    w.Write([]byte(u.String()))
}

Tags:

Go

Mux

Gorilla