.POSIX:
.SUFFIXES:
.DEFAULT_GOAL := help

# --- SETTINGS ---
CORE_DIR = brain
IMAGE_NAME = agent_media
PYTHON_VERSION = 3.12.7
PYTHON_VERSION_SHORT = $(shell echo $(PYTHON_VERSION) | cut -d. -f1,2)
# Change to 'uv' when ready.
RUNNER ?= poetry
SERVICE_NAME = agent_media

export IMAGE_NAME
export PYTHON_VERSION
export PYTHON_VERSION_SHORT
export RUNNER

# --- ADAPTERS ---
# UV uses "sync", Poetry uses "install". Both install DEV deps by default.
INSTALL_CMD = $(if $(filter uv,$(RUNNER)),sync,install)

# --- MACROS ---
ARGS           = $(filter-out $@,$(MAKECMDGOALS))
BUMP_CMD       = cd $(CORE_DIR) && $(RUNNER) run bump-my-version bump
COMPOSE_CMD    = docker-compose
DOCKER_CMD     = docker build \
 --build-arg PYTHON_VERSION=$(PYTHON_VERSION) \
 --build-arg PYTHON_VERSION_SHORT=$(PYTHON_VERSION_SHORT) \
 --build-arg RUNNER=$(RUNNER) \
 -f $(CORE_DIR)/Dockerfile \
 -t $(IMAGE_NAME):latest .

RUNNER_ADD     = cd $(CORE_DIR) && $(RUNNER) add
RUNNER_HOOKS   = cd $(CORE_DIR) && $(RUNNER) run pre-commit install -c ../.pre-commit-config.yaml
RUNNER_INSTALL = cd $(CORE_DIR) && $(RUNNER) $(INSTALL_CMD)
RUNNER_RUN     = cd $(CORE_DIR) && $(RUNNER) run
RUNNER_UPDATE  = cd $(CORE_DIR) && $(RUNNER) update

# --- STYLES ---
B = \033[1m
G = \033[32m
T = \033[36m
R = \033[0m

# --- TARGETS ---
.PHONY: add build build-test check-docker check-runner clean coverage down format help init-dotenv install install-hooks lint logs major minor patch prune ps restart run shell test up update _check_branch _ci-dump-config _ci-run-tests _push_tag

# Catch-all for args
%:
	@:

add: check-runner
	@echo "$(T)➕ Adding dependency ($(RUNNER)): $(ARGS)$(R)"
	$(RUNNER_ADD) $(ARGS)

build: check-docker
	@echo "$(T)🐳 Building Docker image...$(R)"
	$(DOCKER_CMD)
	@echo "✅ Image $(IMAGE_NAME):latest ready."

build-test: check-docker
	@echo "$(T)🐳 Building test image (with dev deps)...$(R)"
	docker build \
		--build-arg RUNNER=$(RUNNER) \
		--build-arg PYTHON_VERSION=$(PYTHON_VERSION) \
		--build-arg PYTHON_VERSION_SHORT=$(PYTHON_VERSION_SHORT) \
		-f $(CORE_DIR)/Dockerfile \
		--target test \
		-t $(IMAGE_NAME):test .
	@echo "✅ Test image $(IMAGE_NAME):test ready."

check-docker:
	@command -v docker >/dev/null 2>&1 || { echo "$(R)❌ Docker not installed$(R)"; exit 1; }
	@docker info >/dev/null 2>&1 || { echo "$(R)❌ Docker daemon not running$(R)"; exit 1; }

check-runner:
	@command -v $(RUNNER) >/dev/null 2>&1 || { echo "$(R)❌ $(RUNNER) not installed$(R)"; exit 1; }

clean:
	@echo "$(T)🧹 Cleaning caches...$(R)"
	cd $(CORE_DIR) && rm -rf .ruff_cache __pycache__ .pytest_cache
	find $(CORE_DIR) -type d -name "__pycache__" -exec rm -rf {} + 2>/dev/null || true
	find $(CORE_DIR) -type d -name ".pytest_cache" -exec rm -rf {} + 2>/dev/null || true
	find $(CORE_DIR) -type f -name "*.pyc" -delete 2>/dev/null || true
	@echo "✅ Caches cleaned."

coverage: check-runner
	@echo "$(T)📊 Running tests with coverage...$(R)"
	$(RUNNER_RUN) pytest --cov=. --cov-report=html --cov-report=term $(ARGS)
	@echo "✅ Report generated in htmlcov/"

down: check-docker
	@echo "$(T)🛑 Stopping containers...$(R)"
	$(COMPOSE_CMD) down
	@echo "✅ System stopped."

format: check-runner
	@echo "$(T)✨ Formatting with Ruff...$(R)"
	$(RUNNER_RUN) ruff format .
	$(RUNNER_RUN) ruff check --fix .
	@echo "✅ Code cleaned."

help:
	@echo "$(B)Available commands:$(R)"
	@echo ""
	@echo "$(G)Setup:$(R)"
	@echo "  $(T)check-docker 		$(R)  Verify Docker is installed and running."
	@echo "  $(T)check-runner 		$(R)  Verify package manager ($(RUNNER))."
	@echo "  $(T)init-dotenv  		$(R)  Create .env from .env.example with generated secrets."
	@echo "  $(T)install      		$(R)  Install ALL dependencies (Prod + Dev)."
	@echo "  $(T)install-hooks		$(R)  Install git pre-commit hooks."
	@echo ""
	@echo "$(G)Docker:$(R)"
	@echo "  $(T)build        		$(R)  Build the docker image (production)."
	@echo "  $(T)build-test   		$(R)  Build the docker image (with dev deps for testing)."
	@echo "  $(T)down         		$(R)  Stop and remove containers."
	@echo "  $(T)logs         		$(R)  Follow logs."
	@echo "  $(T)prune        		$(R)  Clean Docker system."
	@echo "  $(T)ps           		$(R)  Show container status."
	@echo "  $(T)restart      		$(R)  Restart all containers."
	@echo "  $(T)shell        		$(R)  Open shell in container."
	@echo "  $(T)up           		$(R)  Start the agent."
	@echo ""
	@echo "$(G)Development:$(R)"
	@echo "  $(T)add ...      		$(R)  Add dependency (use --group dev or --dev if needed)."
	@echo "  $(T)clean        		$(R)  Clean caches."
	@echo "  $(T)coverage     		$(R)  Run tests with coverage."
	@echo "  $(T)format       		$(R)  Format code (Ruff)."
	@echo "  $(T)lint         		$(R)  Lint code without fixing."
	@echo "  $(T)test ...     		$(R)  Run tests (local with $(RUNNER))."
	@echo "  $(T)update       		$(R)  Update dependencies."
	@echo ""
	@echo "$(G)Versioning:$(R)"
	@echo "  $(T)major/minor/patch	$(R)  Bump version and push tag (triggers CI/CD)."

init-dotenv:
	@echo "$(T)🔑 Initializing .env file...$(R)"
	@if [ -f .env ]; then \
		echo "$(R)⚠️  .env already exists. Skipping.$(R)"; \
		exit 0; \
	fi
	@if [ ! -f .env.example ]; then \
		echo "$(R)❌ .env.example not found$(R)"; \
		exit 1; \
	fi
	@if ! command -v openssl >/dev/null 2>&1; then \
		echo "$(R)❌ openssl not found. Please install it first.$(R)"; \
		exit 1; \
	fi
	@echo "$(T)  → Copying .env.example...$(R)"
	@cp .env.example .env
	@echo "$(T)  → Generating secrets...$(R)"
	@sed -i.bak "s|JWT_SECRET=.*|JWT_SECRET=$$(openssl rand -base64 32)|" .env
	@sed -i.bak "s|JWT_REFRESH_SECRET=.*|JWT_REFRESH_SECRET=$$(openssl rand -base64 32)|" .env
	@sed -i.bak "s|CREDS_KEY=.*|CREDS_KEY=$$(openssl rand -hex 16)|" .env
	@sed -i.bak "s|CREDS_IV=.*|CREDS_IV=$$(openssl rand -hex 8)|" .env
	@sed -i.bak "s|MEILI_MASTER_KEY=.*|MEILI_MASTER_KEY=$$(openssl rand -base64 32)|" .env
	@sed -i.bak "s|AGENT_BRAIN_API_KEY=.*|AGENT_BRAIN_API_KEY=$$(openssl rand -base64 24)|" .env
	@rm -f .env.bak
	@echo "$(G)✅ .env created with generated secrets!$(R)"
	@echo "$(T)⚠️  Don't forget to add your API keys:$(R)"
	@echo "   - OPENAI_API_KEY"
	@echo "   - DEEPSEEK_API_KEY"
	@echo "   - TMDB_API_KEY (optional)"

install: check-runner
	@echo "$(T)📦 Installing FULL environment ($(RUNNER))...$(R)"
	$(RUNNER_INSTALL)
	@echo "✅ Environment ready (Prod + Dev)."

install-hooks: check-runner
	@echo "$(T)🔧 Installing hooks...$(R)"
	$(RUNNER_HOOKS)
	@echo "✅ Hooks ready."

lint: check-runner
	@echo "$(T)🔍 Linting code...$(R)"
	$(RUNNER_RUN) ruff check .

logs: check-docker
	@echo "$(T)📋 Following logs...$(R)"
	$(COMPOSE_CMD) logs -f

major: _check_branch
	@echo "$(T)💥 Bumping major...$(R)"
	SKIP=all $(BUMP_CMD) major
	@$(MAKE) -s _push_tag

minor: _check_branch
	@echo "$(T)✨ Bumping minor...$(R)"
	SKIP=all $(BUMP_CMD) minor
	@$(MAKE) -s _push_tag

patch: _check_branch
	@echo "$(T)🚀 Bumping patch...$(R)"
	SKIP=all $(BUMP_CMD) patch
	@$(MAKE) -s _push_tag

prune: check-docker
	@echo "$(T)🗑️  Pruning Docker resources...$(R)"
	docker system prune -af
	@echo "✅ Docker cleaned."

ps: check-docker
	@echo "$(T)📋 Container status:$(R)"
	@$(COMPOSE_CMD) ps

restart: check-docker
	@echo "$(T)🔄 Restarting containers...$(R)"
	$(COMPOSE_CMD) restart
	@echo "✅ Containers restarted."

run: check-runner
	$(RUNNER_RUN) $(ARGS)

shell: check-docker
	@echo "$(T)🐚 Opening shell in $(SERVICE_NAME)...$(R)"
	$(COMPOSE_CMD) exec $(SERVICE_NAME) /bin/sh

test: check-runner
	@echo "$(T)🧪 Running tests...$(R)"
	$(RUNNER_RUN) pytest $(ARGS)

up: check-docker
	@echo "$(T)🚀 Starting Agent Media...$(R)"
	$(COMPOSE_CMD) up -d
	@echo "✅ System is up."

update: check-runner
	@echo "$(T)🔄 Updating dependencies...$(R)"
	$(RUNNER_UPDATE)
	@echo "✅ All packages up to date."

_check_branch:
	@curr=$$(git rev-parse --abbrev-ref HEAD); \
	if [ "$$curr" != "main" ]; then \
	   echo "❌ Error: not on the main branch"; exit 1; \
	fi

_ci-dump-config:
	@echo "image_name=$(IMAGE_NAME)"
	@echo "python_version=$(PYTHON_VERSION)"
	@echo "python_version_short=$(PYTHON_VERSION_SHORT)"
	@echo "runner=$(IMAGE_NAME)"
	@echo "service_name=$(SERVICE_NAME)"

_ci-run-tests: build-test
	@echo "$(T)🧪 Running tests in Docker...$(R)"
	docker run --rm \
		-e DEEPSEEK_API_KEY \
		-e TMDB_API_KEY \
		$(IMAGE_NAME):test pytest
	@echo "✅ Tests passed."

_push_tag:
	@echo "$(T)📦 Pushing tag...$(R)"
	git push --tags
	@echo "✅ Tag pushed. Check CI for build status."
