"""Citation export service tests"""

import pytest


@pytest.fixture
def sample_article():
    return {
        "pmid": 12345678,
        "title": "Test Article About Cancer Treatment",
        "authors": [
            {"family": "Smith", "given": "J"},
            {"family": "Doe", "given": "A"},
        ],
        "journal": "Journal of Clinical Oncology",
        "pub_year": 2024,
        "volume": "42",
        "issue": "3",
        "pages": "100-110",
        "doi": "10.1000/j.jco.2024.01.001",
        "pmc_id": "PMC1234567",
        "keywords": ["cancer", "treatment"],
    }


@pytest.mark.asyncio
async def test_export_bibtex(sample_article):
    """BibTeX export produces correct @article format"""
    from app.services.citation_export import export_single

    result = export_single(sample_article, "bibtex")
    assert "@article{" in result
    # _bibtex_key: author first 4 chars of each title word => smith2024TestArti
    assert "smith2024TestArti" in result
    assert "Smith, J and Doe, A" in result
    assert "Test Article About Cancer Treatment" in result
    assert "Journal of Clinical Oncology" in result
    assert "pmid = {12345678}" in result
    assert "doi = {10.1000/j.jco.2024.01.001}" in result


@pytest.mark.asyncio
async def test_export_ris(sample_article):
    """RIS export produces correct tagged format"""
    from app.services.citation_export import export_single

    result = export_single(sample_article, "ris")
    assert "TY  - JOUR" in result
    assert "TI  - Test Article About Cancer Treatment" in result
    assert "JO  - Journal of Clinical Oncology" in result
    assert "PY  - 2024" in result
    assert "VL  - 42" in result
    assert "IS  - 3" in result
    assert "SP  - 100-110" in result
    assert "DO  - 10.1000/j.jco.2024.01.001" in result
    assert "AU  - Smith, J" in result
    assert "AU  - Doe, A" in result
    assert "UR  - https://pubmed.ncbi.nlm.nih.gov/12345678/" in result
    assert "ER  - " in result


@pytest.mark.asyncio
async def test_export_endnote(sample_article):
    """EndNote export produces correct %-tagged format"""
    from app.services.citation_export import export_single

    result = export_single(sample_article, "endnote")
    assert "%0 Journal Article" in result
    assert "%T Test Article About Cancer Treatment" in result
    assert "%A Smith, J and Doe, A" in result
    assert "%J Journal of Clinical Oncology" in result
    assert "%D 2024" in result
    assert "%V 42" in result
    assert "%P 100-110" in result
    assert "%@ 10.1000/j.jco.2024.01.001" in result
    assert "%U https://pubmed.ncbi.nlm.nih.gov/12345678/" in result


@pytest.mark.asyncio
async def test_export_csv(sample_article):
    """CSV export produces header + row"""
    from app.services.citation_export import export_single

    result = export_single(sample_article, "csv")
    assert "Title,Authors,Journal,Year,Volume,Pages,DOI,PMID" in result
    assert '"Test Article About Cancer Treatment"' in result
    assert '"Smith, J and Doe, A"' in result
    assert '"Journal of Clinical Oncology"' in result
    assert "12345678" in result


@pytest.mark.asyncio
async def test_export_bibtex_batch(sample_article):
    """Batch BibTeX export produces multiple entries"""
    from app.services.citation_export import export_batch

    result = export_batch([sample_article, sample_article], "bibtex")
    assert result.count("@article{") == 2
    assert "smith2024TestArti" in result


@pytest.mark.asyncio
async def test_export_csv_batch(sample_article):
    """Batch CSV export produces header once + multiple rows"""
    from app.services.citation_export import export_batch

    result = export_batch([sample_article, sample_article], "csv")
    assert result.count("Title,Authors,Journal,Year,Volume,Pages,DOI,PMID") == 1
    assert result.count("12345678") == 2


@pytest.mark.asyncio
async def test_export_unknown_format(sample_article):
    """Unknown format returns empty string"""
    from app.services.citation_export import export_single

    result = export_single(sample_article, "unknown")
    assert result == ""


@pytest.mark.asyncio
async def test_export_single_missing_fields():
    """Article with minimal fields (no authors) still exports"""
    # Omit 'authors' key entirely so _bibtex_key falls back to its default
    minimal = {
        "pmid": 99999999,
        "title": "Minimal Article",
        "journal": None,
        "pub_year": None,
        "doi": None,
    }
    from app.services.citation_export import export_single

    result = export_single(minimal, "bibtex")
    assert "@article{" in result
    # None values render as the string "None" in BibTeX output
    assert "pmid = {99999999}" in result


# ── MLA Format Tests ──


@pytest.mark.asyncio
async def test_export_mla(sample_article):
    """MLA export produces 9th Edition format"""
    from app.services.citation_export import export_single

    result = export_single(sample_article, "mla")
    assert "Smith, J" in result
    assert '"Test Article About Cancer Treatment."' in result
    assert "Journal of Clinical Oncology" in result
    assert "vol. 42, no. 3" in result
    assert "2024" in result
    assert "pp. 100-110" in result
    assert "doi:10.1000/j.jco.2024.01.001" in result


@pytest.mark.asyncio
async def test_export_mla_three_authors():
    """MLA with 3+ authors uses first author et al."""
    from app.services.citation_export import export_single

    article = {
        "pmid": 1,
        "title": "Multi-Author Study",
        "authors": [
            {"family": "Smith", "given": "J"},
            {"family": "Doe", "given": "A"},
            {"family": "Lee", "given": "K"},
        ],
        "journal": "Nature",
        "pub_year": 2024,
        "volume": "600",
        "pages": "1-10",
        "doi": "10.1000/nature",
    }
    result = export_single(article, "mla")
    assert "Smith, J" in result
    assert "et al." in result


@pytest.mark.asyncio
async def test_export_mla_single_author():
    """MLA with single author"""
    from app.services.citation_export import export_single

    article = {
        "pmid": 1,
        "title": "Single Author Study",
        "authors": [{"family": "Wang", "given": "L"}],
        "journal": "Nature",
        "pub_year": 2024,
        "volume": "600",
        "pages": "1-10",
        "doi": "10.1000/nature",
    }
    result = export_single(article, "mla")
    assert "Wang, L" in result
    assert "et al." not in result


@pytest.mark.asyncio
async def test_export_mla_no_doi(sample_article):
    """MLA without DOI uses period instead of doi suffix"""
    from app.services.citation_export import export_single

    no_doi = {k: v for k, v in sample_article.items() if k != "doi"}
    result = export_single(no_doi, "mla")
    assert "doi:" not in result
    assert result.strip().endswith(".")


@pytest.mark.asyncio
async def test_export_mla_no_volume_issue():
    """MLA without volume/issue omits those parts"""
    from app.services.citation_export import export_single

    article = {
        "pmid": 2,
        "title": "Minimal MLA",
        "authors": [{"family": "Li", "given": "X"}],
        "journal": "Science",
        "pub_year": 2025,
        "doi": "10.1000/science",
    }
    result = export_single(article, "mla")
    assert "vol." not in result
    assert "Science 2025" in result
    assert "doi:10.1000/science" in result


@pytest.mark.asyncio
async def test_export_mla_batch(sample_article):
    """Batch MLA export produces multiple entries"""
    from app.services.citation_export import export_batch

    result = export_batch([sample_article, sample_article], "mla")
    lines = result.strip().split("\n")
    assert len(lines) >= 2
    assert "Smith, J" in result


__all__ = []
