"""Tests for caffeinate_me.tracker."""

import json
from unittest.mock import patch

import pytest


@pytest.fixture()
def temp_tracker(tmp_path):
    """Redirect tracker storage to a temporary directory for each test."""
    temp_file = tmp_path / "tracker.json"
    with (
        patch("caffeinate_me.tracker.TRACKER_FILE", temp_file),
        patch("caffeinate_me.tracker.DATA_DIR", tmp_path),
    ):
        yield temp_file


# ---------------------------------------------------------------------------
# log_coffee
# ---------------------------------------------------------------------------


class TestLogCoffee:
    def test_creates_entry(self, temp_tracker):
        from caffeinate_me.tracker import _load_data, log_coffee

        log_coffee()
        data = _load_data()
        assert len(data["entries"]) == 1

    def test_entry_has_timestamp(self, temp_tracker):
        from caffeinate_me.tracker import _load_data, log_coffee

        log_coffee()
        entry = _load_data()["entries"][0]
        assert "timestamp" in entry

    def test_records_coffee_type(self, temp_tracker):
        from caffeinate_me.tracker import _load_data, log_coffee

        log_coffee(coffee_type="espresso")
        assert _load_data()["entries"][0]["coffee_type"] == "espresso"

    def test_records_mood(self, temp_tracker):
        from caffeinate_me.tracker import _load_data, log_coffee

        log_coffee(mood="energetic")
        assert _load_data()["entries"][0]["mood"] == "energetic"

    def test_multiple_entries_accumulate(self, temp_tracker):
        from caffeinate_me.tracker import _load_data, log_coffee

        log_coffee()
        log_coffee()
        log_coffee()
        assert len(_load_data()["entries"]) == 3

    def test_first_cup_achievement_unlocked(self, temp_tracker):
        from caffeinate_me.tracker import log_coffee

        newly = log_coffee()
        assert "first_cup" in newly

    def test_no_duplicate_achievement(self, temp_tracker):
        from caffeinate_me.tracker import log_coffee

        log_coffee()
        newly = log_coffee()
        assert "first_cup" not in newly

    def test_triple_shot_achievement(self, temp_tracker):
        from caffeinate_me.tracker import log_coffee

        log_coffee()
        log_coffee()
        newly = log_coffee()
        assert "triple_shot" in newly

    def test_variety_seeker_achievement(self, temp_tracker):
        from caffeinate_me.tracker import log_coffee

        types = ["espresso", "latte", "mocha", "cold-brew", "cappuccino"]
        newly_all: list = []
        for t in types:
            newly_all.extend(log_coffee(coffee_type=t))
        assert "variety_seeker" in newly_all

    def test_century_club_achievement(self, temp_tracker):
        from caffeinate_me.tracker import log_coffee

        newly_all: list = []
        for _ in range(100):
            newly_all.extend(log_coffee())
        assert "century_club" in newly_all


# ---------------------------------------------------------------------------
# get_stats
# ---------------------------------------------------------------------------


class TestGetStats:
    def test_empty_returns_zero_counts(self, temp_tracker):
        from caffeinate_me.tracker import get_stats

        stats = get_stats()
        assert stats["total"] == 0
        assert stats["today"] == 0
        assert stats["week"] == 0

    def test_total_after_logging(self, temp_tracker):
        from caffeinate_me.tracker import get_stats, log_coffee

        log_coffee()
        log_coffee()
        assert get_stats()["total"] == 2

    def test_today_count(self, temp_tracker):
        from caffeinate_me.tracker import get_stats, log_coffee

        log_coffee()
        assert get_stats()["today"] == 1

    def test_favourite_type(self, temp_tracker):
        from caffeinate_me.tracker import get_stats, log_coffee

        log_coffee(coffee_type="espresso")
        log_coffee(coffee_type="espresso")
        log_coffee(coffee_type="latte")
        assert get_stats()["favorite_type"] == "espresso"

    def test_avg_per_day(self, temp_tracker):
        from caffeinate_me.tracker import get_stats, log_coffee

        log_coffee()
        log_coffee()
        stats = get_stats()
        assert stats["avg_per_day"] >= 1.0

    def test_achievements_list_present(self, temp_tracker):
        from caffeinate_me.tracker import get_stats

        stats = get_stats()
        assert "achievements" in stats
        assert "all_achievements" in stats


# ---------------------------------------------------------------------------
# export_data
# ---------------------------------------------------------------------------


class TestExportData:
    def test_json_export_is_valid(self, temp_tracker):
        from caffeinate_me.tracker import export_data, log_coffee

        log_coffee()
        result = export_data("json")
        data = json.loads(result)
        assert "entries" in data

    def test_csv_export_header(self, temp_tracker):
        from caffeinate_me.tracker import export_data

        result = export_data("csv")
        assert result.splitlines()[0] == "timestamp,coffee_type,mood"

    def test_csv_export_has_data_row(self, temp_tracker):
        from caffeinate_me.tracker import export_data, log_coffee

        log_coffee(coffee_type="latte", mood="zen")
        lines = export_data("csv").splitlines()
        assert len(lines) == 2
        assert "latte" in lines[1]
        assert "zen" in lines[1]
