package de.gecheckt.pdf.umbenenner.domain.model;

import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertNotNull;
import static org.junit.jupiter.api.Assertions.assertNotSame;

import org.junit.jupiter.api.Test;

/**
 * Unit tests for {@link ProcessingStatus} enumeration.
 * <p>
 * Verifies that all required status values are present and correctly defined
 * for the document processing pipeline.
 */
class ProcessingStatusTest {

    @Test
    void allRequiredStatusValuesExist() {
        // Verify all status values required by the architecture are present
        assertNotNull(ProcessingStatus.SUCCESS);
        assertNotNull(ProcessingStatus.FAILED_RETRYABLE);
        assertNotNull(ProcessingStatus.FAILED_FINAL);
        assertNotNull(ProcessingStatus.SKIPPED_ALREADY_PROCESSED);
        assertNotNull(ProcessingStatus.SKIPPED_FINAL_FAILURE);
        assertNotNull(ProcessingStatus.PROCESSING);
        assertNotNull(ProcessingStatus.READY_FOR_AI);
        assertNotNull(ProcessingStatus.PROPOSAL_READY);
    }

    @Test
    void successStatus_isDefinedAndAccessible() {
        ProcessingStatus status = ProcessingStatus.SUCCESS;
        assertEquals(ProcessingStatus.SUCCESS, status);
    }

    @Test
    void failedRetryableStatus_isDefinedAndAccessible() {
        ProcessingStatus status = ProcessingStatus.FAILED_RETRYABLE;
        assertEquals(ProcessingStatus.FAILED_RETRYABLE, status);
    }

    @Test
    void failedFinalStatus_isDefinedAndAccessible() {
        ProcessingStatus status = ProcessingStatus.FAILED_FINAL;
        assertEquals(ProcessingStatus.FAILED_FINAL, status);
    }

    @Test
    void skippedAlreadyProcessedStatus_isDefinedAndAccessible() {
        ProcessingStatus status = ProcessingStatus.SKIPPED_ALREADY_PROCESSED;
        assertEquals(ProcessingStatus.SKIPPED_ALREADY_PROCESSED, status);
    }

    @Test
    void skippedFinalFailureStatus_isDefinedAndAccessible() {
        ProcessingStatus status = ProcessingStatus.SKIPPED_FINAL_FAILURE;
        assertEquals(ProcessingStatus.SKIPPED_FINAL_FAILURE, status);
    }

    @Test
    void processingStatus_isDefinedAndAccessible() {
        ProcessingStatus status = ProcessingStatus.PROCESSING;
        assertEquals(ProcessingStatus.PROCESSING, status);
    }

    @Test
    void readyForAiStatus_isDefinedAndAccessible() {
        ProcessingStatus status = ProcessingStatus.READY_FOR_AI;
        assertEquals(ProcessingStatus.READY_FOR_AI, status);
    }

    @Test
    void proposalReadyStatus_isDefinedAndAccessible() {
        ProcessingStatus status = ProcessingStatus.PROPOSAL_READY;
        assertEquals(ProcessingStatus.PROPOSAL_READY, status);
    }

    @Test
    void statusEquality_worksByReference() {
        // Enums have identity-based equality
        assertNotSame(ProcessingStatus.SUCCESS, ProcessingStatus.FAILED_FINAL);
    }

    @Test
    void statusCanBeUsedInSwitch() {
        ProcessingStatus status = ProcessingStatus.FAILED_RETRYABLE;
        String result = "";

        switch (status) {
            case SUCCESS -> result = "success";
            case READY_FOR_AI -> result = "ready-for-ai";
            case PROPOSAL_READY -> result = "proposal-ready";
            case FAILED_RETRYABLE -> result = "retryable";
            case FAILED_FINAL -> result = "final";
            case SKIPPED_ALREADY_PROCESSED -> result = "skip-processed";
            case SKIPPED_FINAL_FAILURE -> result = "skip-failed";
            case PROCESSING -> result = "processing";
        }

        assertEquals("retryable", result);
    }

    @Test
    void statusValues_areEightInTotal() {
        ProcessingStatus[] values = ProcessingStatus.values();
        assertEquals(8, values.length, "ProcessingStatus should have exactly 8 values");
    }
}
