indieauth-server/internal/server/router.go
Dan Anglin 9cb1f8ed4b
feat: add an ID for every request
- Add a middleware to add an ID for every request for the purpose of
  cross referencing requests and errors.
- Add functions for handling client and server errors.
2024-10-17 18:25:43 +01:00

56 lines
1.7 KiB
Go

package server
import (
"crypto/rand"
"encoding/hex"
"fmt"
"log/slog"
"net/http"
"codeflow.dananglin.me.uk/apollo/indieauth-server/internal/config"
)
func newMux(cfg config.Config) *http.ServeMux {
mux := http.NewServeMux()
mux.Handle("GET /.well-known/oauth-authorization-server", setRequestID(metadataHandler(cfg.Domain)))
return mux
}
func setRequestID(next http.Handler) http.Handler {
return http.HandlerFunc(func(writer http.ResponseWriter, request *http.Request) {
requestID := "UNKNOWN"
id := make([]byte, 16)
if _, err := rand.Read(id); err != nil {
slog.Error("unable to create the request ID.", "error", err.Error())
} else {
requestID = hex.EncodeToString(id)
}
writer.Header().Set("X-Request-ID", requestID)
next.ServeHTTP(writer, request)
})
}
func metadataHandler(domain string) http.Handler {
return http.HandlerFunc(func(writer http.ResponseWriter, _ *http.Request) {
metadata := struct {
Issuer string `json:"issuer"`
AuthorizationEndpoint string `json:"authorization_endpoint"`
TokenEndpoint string `json:"token_endpoint"`
ServiceDocumentation string `json:"service_documentation"`
CodeChallengeMethodsSupported []string `json:"code_challenge_methods_supported"`
}{
Issuer: fmt.Sprintf("https://%s/", domain),
AuthorizationEndpoint: fmt.Sprintf("https://%s/auth", domain),
TokenEndpoint: fmt.Sprintf("https://%s/token", domain),
ServiceDocumentation: "https://indieauth.spec.indieweb.org",
CodeChallengeMethodsSupported: []string{"S256"},
}
sendResponse(writer, http.StatusOK, metadata)
})
}