- Domain (
internal/domain): Core entities, value objects, and Ports (interfaces). Must remain completely framework-agnostic. - Application (
internal/application): Use cases, strictly separated intocommand/andquery/to follow CQRS. Dependencies always point inward toward the Domain. - Infrastructure (
internal/infrastructure): Adapters for HTTP (gin), logging (zerolog), metrics (prometheus), and repositories. - Composition Root (
cmd/api): Responsible for wiring concrete adapters to application use cases.
- Test Suite:
make test(runs with-v -race -coverprofile). - Single Test:
go test -v -race -run ^TestName$ ./internal/path/to/pkg - Lint:
make lint(runsgolangci-lint). Always runmake lintandmake testbefore completing a task as CI enforces these. - Run Locally:
make run(listens on:3000by default). - Docker:
docker compose up -d --build(copy.env.exampleto.envfirst if overrides are needed).
- Testing (
testify): Userequirefor fatal setup/precondition checks (halts test immediately). Useassertfor value comparisons (allows test to continue and report multiple failures). - Logging: Do not use
fmtorlogin business logic. Injectport.Loggerand pass alternating key-value arguments (e.g.,logger.Info("msg", "key", "value")). SetLOG_PRETTY=1in your local environment for readable console output instead of JSON. - Metrics: Endpoints are automatically instrumented for Prometheus (
/metrics). If domain events need metric tracking, extendport.MetricsRecorderand implement it ininfrastructure/metrics.