package dev.lions.unionflow.server.entity;

import dev.lions.unionflow.server.api.enums.document.TypeDocument;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;

import java.time.LocalDateTime;
import java.util.UUID;

import static org.assertj.core.api.Assertions.assertThat;

@DisplayName("Document")
class DocumentTest {

    @Test
    @DisplayName("getters/setters")
    void gettersSetters() {
        Document d = new Document();
        d.setNomFichier("doc.pdf");
        d.setNomOriginal("MonDoc.pdf");
        d.setCheminStockage("/storage/doc.pdf");
        d.setTypeMime("application/pdf");
        d.setTailleOctets(1024L);
        d.setTypeDocument(TypeDocument.FACTURE);
        d.setHashMd5("abc123");
        d.setHashSha256("def456");
        d.setDescription("Facture");
        d.setNombreTelechargements(5);
        d.setDateDernierTelechargement(LocalDateTime.now());

        assertThat(d.getNomFichier()).isEqualTo("doc.pdf");
        assertThat(d.getNomOriginal()).isEqualTo("MonDoc.pdf");
        assertThat(d.getCheminStockage()).isEqualTo("/storage/doc.pdf");
        assertThat(d.getTypeMime()).isEqualTo("application/pdf");
        assertThat(d.getTailleOctets()).isEqualTo(1024L);
        assertThat(d.getTypeDocument()).isEqualTo(TypeDocument.FACTURE);
        assertThat(d.getHashMd5()).isEqualTo("abc123");
        assertThat(d.getHashSha256()).isEqualTo("def456");
        assertThat(d.getDescription()).isEqualTo("Facture");
        assertThat(d.getNombreTelechargements()).isEqualTo(5);
    }

    @Test
    @DisplayName("verifierIntegriteMd5: true quand hash égal (insensible casse)")
    void verifierIntegriteMd5() {
        Document d = new Document();
        d.setHashMd5("ABC123");
        assertThat(d.verifierIntegriteMd5("abc123")).isTrue();
        assertThat(d.verifierIntegriteMd5("autre")).isFalse();
        d.setHashMd5(null);
        assertThat(d.verifierIntegriteMd5("x")).isFalse();
    }

    @Test
    @DisplayName("verifierIntegriteSha256")
    void verifierIntegriteSha256() {
        Document d = new Document();
        d.setHashSha256("DEF456");
        assertThat(d.verifierIntegriteSha256("def456")).isTrue();
        assertThat(d.verifierIntegriteSha256("autre")).isFalse();
    }

    @Test
    @DisplayName("verifierIntegriteSha256: false si hashSha256 null")
    void verifierIntegriteSha256_hashNull_returnsFalse() {
        Document d = new Document();
        d.setHashSha256(null);
        assertThat(d.verifierIntegriteSha256("def456")).isFalse();
    }

    @Test
    @DisplayName("getTailleFormatee: B, KB, MB")
    void getTailleFormatee() {
        Document d = new Document();
        d.setNomFichier("x");
        d.setCheminStockage("/x");
        d.setTailleOctets(500L);
        assertThat(d.getTailleFormatee()).isEqualTo("500 B");
        d.setTailleOctets(2048L);
        assertThat(d.getTailleFormatee()).contains("KB");
        d.setTailleOctets(1024L * 1024 * 2);
        assertThat(d.getTailleFormatee()).contains("MB");
        d.setTailleOctets(null);
        assertThat(d.getTailleFormatee()).isEqualTo("0 B");
    }

    @Test
    @DisplayName("equals et hashCode")
    void equalsHashCode() {
        UUID id = UUID.randomUUID();
        Document a = new Document();
        a.setId(id);
        a.setNomFichier("a.pdf");
        a.setCheminStockage("/a");
        a.setTailleOctets(1L);
        Document b = new Document();
        b.setId(id);
        b.setNomFichier("a.pdf");
        b.setCheminStockage("/a");
        b.setTailleOctets(1L);
        assertThat(a).isEqualTo(b);
        assertThat(a.hashCode()).isEqualTo(b.hashCode());
    }

    @Test
    @DisplayName("toString non null")
    void toString_nonNull() {
        Document d = new Document();
        d.setNomFichier("x");
        d.setCheminStockage("/x");
        d.setTailleOctets(1L);
        assertThat(d.toString()).isNotNull().isNotEmpty();
    }
}
