From 27f92894b50ffc2058c1b2f0db4d78d47a48c843 Mon Sep 17 00:00:00 2001 From: Alan Pearce Date: Wed, 24 Apr 2024 13:36:57 +0200 Subject: split code into separate files --- cmd/server/server.go | 146 ++------------------------------------------------- 1 file changed, 4 insertions(+), 142 deletions(-) (limited to 'cmd/server/server.go') diff --git a/cmd/server/server.go b/cmd/server/server.go index 9c9911a..10144bb 100644 --- a/cmd/server/server.go +++ b/cmd/server/server.go @@ -2,98 +2,27 @@ package main import ( "fmt" - "hash/fnv" "io" - "io/fs" "log" "log/slog" "mime" "net" "net/http" "os" - "path/filepath" "strings" "time" cfg "website/internal/config" - "github.com/ardanlabs/conf/v3" "github.com/getsentry/sentry-go" sentryhttp "github.com/getsentry/sentry-go/http" - "github.com/pkg/errors" "github.com/shengyanli1982/law" ) -type Config struct { - Production bool `conf:"default:false"` - ListenAddress string `conf:"default:localhost"` - Port uint16 `conf:"default:3000,short:p"` - BaseURL cfg.URL `conf:"default:http://localhost:3000,short:b"` - RedirectOtherHostnames bool `conf:"default:false"` -} - var Commit string var config *cfg.Config -type File struct { - filename string - etag string -} - -var files = map[string]File{} - -func hashFile(filename string) (string, error) { - f, err := os.Open(filename) - if err != nil { - return "", err - } - defer f.Close() - hash := fnv.New64a() - if _, err := io.Copy(hash, f); err != nil { - return "", err - } - return fmt.Sprintf(`W/"%x"`, hash.Sum(nil)), nil -} - -func registerFile(urlpath string, filepath string) error { - if files[urlpath] != (File{}) { - log.Printf("registerFile called with duplicate file, urlPath: %s", urlpath) - return nil - } - hash, err := hashFile(filepath) - if err != nil { - return err - } - files[urlpath] = File{ - filename: filepath, - etag: hash, - } - return nil -} - -func registerContentFiles(root string) error { - err := filepath.WalkDir(root, func(filePath string, f fs.DirEntry, err error) error { - if err != nil { - return errors.WithMessagef(err, "failed to access path %s", filePath) - } - relPath, err := filepath.Rel(root, filePath) - if err != nil { - return errors.WithMessagef(err, "failed to make path relative, path: %s", filePath) - } - urlPath, _ := strings.CutSuffix(relPath, "index.html") - if !f.IsDir() { - slog.Debug("registering file", "urlpath", "/"+urlPath) - return registerFile("/"+urlPath, filePath) - } - return nil - }) - if err != nil { - return err - } - return nil -} - type HTTPError struct { Error error Message string @@ -116,7 +45,7 @@ func serveFile(w http.ResponseWriter, r *http.Request) *HTTPError { http.Redirect(w, r, urlPath, 302) return nil } - file := files[urlPath] + file := GetFile(urlPath) if file == (File{}) { return &HTTPError{ Message: "File not found", @@ -166,81 +95,14 @@ func fixupMIMETypes() { } } -type loggingResponseWriter struct { - http.ResponseWriter - statusCode int -} - -func (lrw *loggingResponseWriter) WriteHeader(code int) { - lrw.statusCode = code - // avoids warning: superfluous response.WriteHeader call - if lrw.statusCode != http.StatusOK { - lrw.ResponseWriter.WriteHeader(code) - } -} - -func NewLoggingResponseWriter(w http.ResponseWriter) *loggingResponseWriter { - return &loggingResponseWriter{w, http.StatusOK} -} - -type wrappedHandlerOptions struct { - defaultHostname string - logger io.Writer -} - -func wrapHandlerWithLogging(wrappedHandler http.Handler, opts wrappedHandlerOptions) http.Handler { - return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - scheme := r.Header.Get("X-Forwarded-Proto") - if scheme == "" { - scheme = "http" - } - host := r.Header.Get("Host") - if host == "" { - host = opts.defaultHostname - } - lw := NewLoggingResponseWriter(w) - wrappedHandler.ServeHTTP(lw, r) - statusCode := lw.statusCode - fmt.Fprintf( - opts.logger, - "%s %s %d %s %s %s\n", - scheme, - r.Method, - statusCode, - host, - r.URL.Path, - lw.Header().Get("Location"), - ) - }) -} - -func main() { - if os.Getenv("DEBUG") != "" { - slog.SetLogLoggerLevel(slog.LevelDebug) - } - +func startServer(runtimeConfig *Config) { fixupMIMETypes() - runtimeConfig := Config{} - help, err := conf.Parse("", &runtimeConfig) - if err != nil { - if errors.Is(err, conf.ErrHelpWanted) { - fmt.Println(help) - os.Exit(1) - } - log.Panicf("parsing runtime configuration: %v", err) - } - - config, err = cfg.GetConfig() + c, err := cfg.GetConfig() if err != nil { log.Panicf("parsing configuration file: %v", err) } - - cwd, err := os.Getwd() - if err != nil { - log.Panicf("don't know where I am") - } - slog.Debug("starting at", "wd", cwd) + config = c prefix := "website/public" slog.Debug("registering content files", "prefix", prefix) -- cgit 1.4.1