# Makefile for building and pushing multi-arch Docker images

IMAGE_REPO = git.coopcloud.tech/wiki-cafe/member-console
DATE_TAG = $(shell date -u +%Y-%m-%dT%H-%MZ)
# PLATFORMS = linux/arm64,linux/amd64
PLATFORMS = linux/amd64

.PHONY: docker-push

docker-push:
	docker buildx build \
	  --platform $(PLATFORMS) \
	  -t $(IMAGE_REPO):latest \
	  -t $(IMAGE_REPO):$(DATE_TAG) \
	  --push .

# Database migration targets
.PHONY: sqlc-generate

# The nine package directories that carry their own sqlc.yaml (six core
# packages + three integration stores); see docs/database-management.md.
SQLC_DIRS = internal/identity \
	internal/organization \
	internal/billing \
	internal/entitlements \
	internal/integration \
	internal/domains \
	internal/integrations/fedwiki/store \
	internal/integrations/stripe/store \
	internal/integrations/discourse/store

sqlc-generate:
	@for dir in $(SQLC_DIRS); do \
		echo "sqlc generate: $$dir"; \
		(cd $$dir && sqlc generate) || exit 1; \
	done

# Build the application
.PHONY: build
build:
	go build -o member-console .

# Run the test suite against pristine test databases. reset-test-db.sh drops,
# recreates, and migrates the tests' own databases (never the app's), so the
# suite starts from migrations only and a running app cannot perturb it.
# Requires the stack up: cd test && ./bootstrap-stack.sh && docker compose up -d.
#
# -count=1 because Go's test cache keys on code and env, not database state:
# after a reset, a cached "ok" would be reporting on a database that no
# longer exists.
#
# -p 1 because several packages commit rows that other packages read: the
# org-type-change suites set and restore personal.default_plan_ladder_id
# while internal/provisioning asserts it is unset; the discourse operator and
# webhook suites commit group mappings that the reconcile suite's fake forum
# has never heard of. Serializing packages closes that whole class. It is not
# a stand-in for the separate e2e database — serialization orders commits, it
# does not undo them — the two fixes cover different vectors.
.PHONY: test
test:
	@cd test && ./reset-test-db.sh && set -a && . ./.env && set +a && cd .. && go test -count=1 -p 1 ./...

# Respin the test stack from scratch: teardown (drops volumes), regenerate
# per-worktree ports/secrets, bring compose back up. The app and demo seed
# stay manual because migrations run at app boot (see test/AGENTS.md,
# "Browser walkthroughs (e2e) and stack age"). Suite freshness does not need
# this — `make test` resets the test databases on its own; respin when the
# *app* database or another service's state needs clearing.
#
# Composes the core stack. Teardown drops test/.env, so a composition carries
# over only if you pass it back in:
#   make stack-fresh COMPOSE_PROFILES=fedwiki,discourse
.PHONY: stack-fresh
stack-fresh:
	cd test && ./teardown-stack.sh && COMPOSE_PROFILES="$(COMPOSE_PROFILES)" ./bootstrap-stack.sh && docker compose up -d
	@echo ""
	@echo "Stack is fresh. For a full-exercise browser-walkthrough run:"
	@echo "  1. cd test && set -a && . ./.env && set +a && go run .. start --config mc-config.yaml   # boots + migrates"
	@echo "  2. ./test/seed-demo.sh   # walkthrough subjects (demo catalog + one active grant)"
	@echo "  3. go test ./test/e2e/operator-walkthroughs/ -count=1"
	@echo ""
	@echo "Integration walkthroughs skip unless their compose profile is on AND"
	@echo "the matching MC_* block in test/.env is uncommented (see test/AGENTS.md)."
	@echo ""
	@echo "The Go suite needs none of that: make test"

# Lint: ensure no handler bypasses SafeTemplates by writing directly to ResponseWriter.
# All template rendering must go through h.Templates.Render() — see internal/server/render.go.
.PHONY: lint-templates
lint-templates:
	@if grep -rn '\.ExecuteTemplate(w,' internal/server/; then \
		echo "ERROR: Direct ExecuteTemplate on ResponseWriter found. Use h.Templates.Render() instead."; \
		exit 1; \
	else \
		echo "OK: No direct ExecuteTemplate on ResponseWriter detected."; \
	fi
