Architecture
Lore is a layered Go monolith. It runs as one process with one PostgreSQL database, while package dependencies point inward so HTTP and persistence details stay out of application behavior.
The normal request path is:
HTTP -> routes/middleware -> handler -> service -> repository contract -> store -> PostgreSQL
| |
+------------> domain <------------+
Main layers
cmdis the minimal process entry point.internal/clidefines the TinyFlags command tree (serve,build) and binds command-line configuration to application operations.internal/appis the server composition root. It receives resolved runtime values, loads assets, opens PostgreSQL, constructs services/authentication/views, and builds the router.internal/routesregisters routes and applies authentication/role policies to already-constructed dependencies.internal/handler,internal/middleware, andinternal/authare inbound HTTP adapters.internal/serviceowns application use cases and mutation policy.internal/domainowns persistence-agnostic domain records and shared errors.internal/storeowns SQL, migrations, transactions, and PostgreSQL row mapping.- focused packages such as
internal/markdown,internal/navigation,internal/revision,internal/pdf,internal/icons, andinternal/httpresponseprovide narrow capabilities. internal/siteis the filesystem/static publishing adapter. It uses the same Markdown/navigation/theme capabilities but does not construct the server, authentication, services, or store.webandthemescontain browser assets and theme resources.
Boundaries
Handlers do not import the concrete store. Services and authenticators declare the persistence capabilities they consume. internal/app is the place where concrete store implementations satisfy those contracts. SQL and pgx stay in internal/store.
The static builder is intentionally outside the server composition path. lore build reads files, renders them, and writes static output without opening PostgreSQL.