#!/usr/bin/env python

# Copyright (C) 2018 Visual Collaboration Technologies Inc.
# All Rights Reserved.
#
# This file is a property of Visual Collaboration Technologies Inc.
# Unauthorized access, reproduction or redistribution of any kind is prohibited.
"""Tests for custom level logger functionality."""

import logging

import pytest

from vcti.logging import create_logging_config, logger, setup_logging
from vcti.logging.custom_level import CustomLogLevel


@pytest.fixture
def log_file(tmp_path):
    """Fixture providing a temporary log file path."""
    return tmp_path / "test.log"


@pytest.fixture
def log_config(log_file):
    """Fixture providing logging configuration with TRACE level to capture all logs."""
    return create_logging_config(
        enable_console_log=True, log_file_path=log_file, log_level="trace"
    )


@pytest.fixture(autouse=True)
def setup_teardown_logging(log_config):
    """Setup and teardown logging for each test."""
    # Setup
    setup_logging(log_config)
    yield
    # Teardown
    for handler in logger.handlers[:]:
        handler.close()
        logger.removeHandler(handler)


class TestCustomLevelLogger:
    """Tests for custom logging level functionality."""

    def test_custom_log_level_methods_exist(self):
        """Verify that custom log level methods are available and callable."""
        assert hasattr(logger, "trace")
        assert hasattr(logger, "verbose")
        assert callable(logger.trace)
        assert callable(logger.verbose)

    def test_trace_logging(self, log_file):
        """Test TRACE level logging."""
        trace_message = "Trace message"
        logger.trace(trace_message)

        assert log_file.exists()
        log_content = log_file.read_text()
        assert trace_message in log_content

    def test_verbose_logging(self, log_file):
        """Test VERBOSE level logging."""
        verbose_message = "Verbose message"
        logger.verbose(verbose_message)

        assert log_file.exists()
        log_content = log_file.read_text()
        assert verbose_message in log_content

    def test_custom_levels_numeric_values(self):
        """Verify that custom log levels have correct numeric values."""
        assert CustomLogLevel.TRACE == 5
        assert CustomLogLevel.VERBOSE == 15

    def test_custom_levels_registered(self):
        """Verify that custom levels are registered with logging module."""
        assert logging.getLevelName(CustomLogLevel.TRACE) == "TRACE"
        assert logging.getLevelName(CustomLogLevel.VERBOSE) == "VERBOSE"

    def test_all_log_levels_work(self, log_file):
        """Test all log levels (standard + custom) work correctly."""
        test_messages = {
            "trace": "Trace message",
            "debug": "Debug message",
            "verbose": "Verbose message",
            "info": "Info message",
            "warning": "Warning message",
            "error": "Error message",
            "fatal": "Fatal message",
        }

        for level, message in test_messages.items():
            getattr(logger, level)(message)

        log_content = log_file.read_text()
        for message in test_messages.values():
            assert message in log_content

    def test_log_level_hierarchy(self, tmp_path):
        """Test that log level hierarchy is respected."""
        # Create a logger with INFO level (should not log TRACE, DEBUG, or VERBOSE)
        info_log_file = tmp_path / "info.log"
        info_config = create_logging_config(
            enable_console_log=False, log_file_path=info_log_file, log_level="info"
        )
        setup_logging(info_config)

        logger.trace("Trace message - should not appear")
        logger.debug("Debug message - should not appear")
        logger.verbose("Verbose message - should not appear")
        logger.info("Info message - should appear")
        logger.warning("Warning message - should appear")

        log_content = info_log_file.read_text()
        assert "Trace message" not in log_content
        assert "Debug message" not in log_content
        assert "Verbose message" not in log_content
        assert "Info message" in log_content
        assert "Warning message" in log_content

    def test_logger_name(self):
        """Verify that logger has correct name."""
        assert logger.name == "vcti"

    def test_custom_levels_accessible_via_logging_module(self):
        """Verify that custom level names are registered with the logging module."""
        assert logging.getLevelName(CustomLogLevel.TRACE) == "TRACE"
        assert logging.getLevelName(CustomLogLevel.VERBOSE) == "VERBOSE"
        assert logging.getLevelName("TRACE") == CustomLogLevel.TRACE
        assert logging.getLevelName("VERBOSE") == CustomLogLevel.VERBOSE
