# Architecture of hnh-map ## Overview hnh-map is an automapper server for HnH: a Go backend with bbolt storage, sessions, and a Nuxt 3 SPA served at `/`. API, SSE, and tiles are served at `/map/api/`, `/map/updates`, `/map/grids/`. Grid and tile data is stored in the `grids/` directory and in the database. ``` ┌─────────────┐ HTTP/SSE ┌──────────────────────────────────────┐ │ Browser │ ◄────────────────► │ Go server (cmd/hnh-map) │ │ (Nuxt SPA │ /, /login, │ • bbolt (users, sessions, grids, │ │ at /) │ /map/api, │ markers, tiles, maps, config) │ │ │ /map/updates, │ • Frontend statics (frontend/) │ │ │ /map/grids/ │ • internal/app — all logic │ └─────────────┘ └──────────────────────────────────────┘ ``` ## Backend structure The backend follows a layered architecture: **Store → Services → Handlers**. - **cmd/hnh-map/main.go** — the single entry point (`package main`): parses flags (`-grids`, `-port`) and environment variables (`HNHMAP_PORT`), opens bbolt, runs migrations, creates `App`, wires services and handlers, registers routes, and starts the HTTP server. Paths to `frontend/` and `public/` are resolved relative to the working directory at startup. - **internal/app/** — package `app` with the `App` type and domain types: - **app.go** — `App` struct, domain types (`Character`, `Session`, `Coord`, `Position`, `Marker`, `User`, `MapInfo`, `GridData`, etc.), SPA serving (`ServeSPARoot`), character cleanup (`CleanChars`), constants. - **router.go** — route registration (`Router`), interface `APIHandler`. - **topic.go** — generic `Topic[T]` pub/sub for broadcasting tile and merge updates. - **migrations.go** — bbolt schema migrations; called from main via `RunMigrations(db)`. - **internal/app/store/** — database access layer: - **db.go** — `Store` struct with bucket helpers and CRUD operations for users, sessions, tokens, config, maps, grids, tiles, markers, and OAuth states. - **buckets.go** — bucket name constants. - **internal/app/services/** — business logic layer: - **auth.go** — `AuthService`: authentication, sessions, password hashing, token validation, OAuth (Google) login flow. - **map.go** — `MapService`: map data retrieval, tile save/get, zoom level processing, SSE watch, character/marker access. - **admin.go** — `AdminService`: user management, settings, map management, wipe, tile operations. - **client.go** — `ClientService`: game client operations (grid update, grid upload, position updates, marker uploads). - **export.go** — `ExportService`: data export (ZIP) and merge (import). - **internal/app/handlers/** — HTTP handlers (thin layer over services): - **handlers.go** — `Handlers` struct (dependency container), `HandleServiceError`. - **response.go** — JSON response helpers. - **api.go** — top-level API router (`APIRouter`). - **auth.go** — login, logout, me, setup, OAuth, token, and password handlers. - **map.go** — config, characters, markers, and maps handlers. - **client.go** — game client HTTP handlers (grid update/upload, positions, markers). - **admin.go** — admin HTTP handlers (users, settings, maps, wipe, tile ops, export, merge). - **tile.go** — tile image serving and SSE endpoint. - **internal/app/apperr/** — domain error types mapped to HTTP status codes by handlers. - **internal/app/response/** — shared JSON response utilities. Build from the repository root: ```bash go build -o hnh-map ./cmd/hnh-map ```