"""End-to-end tests for flat-fhir."""

import json
import os
import tempfile
from pathlib import Path

import pytest

from flat_fhir import flatten, unflatten, merge, FlatFHIR

FIXTURES = Path(__file__).parent / "fixtures"
SAMPLE = FIXTURES / "sample_bundle.json"


def test_flatten_produces_xlsx():
    with tempfile.NamedTemporaryFile(suffix=".xlsx", delete=False) as f:
        out = f.name
    try:
        ff = flatten(str(SAMPLE), output=out)
        assert os.path.exists(out)
        assert "patient" in ff.sheets()
        assert "vitals" in ff.sheets()
        assert "labs" in ff.sheets()
        assert "medications" in ff.sheets()
        assert "conditions" in ff.sheets()
        assert "allergies" in ff.sheets()
        assert "encounters" in ff.sheets()
    finally:
        os.unlink(out)


def test_patient_extraction():
    ff = FlatFHIR(str(SAMPLE))
    p = ff.patient
    assert len(p) == 1
    row = p.iloc[0]
    assert row["family_name"] == "Doe"
    assert row["given_name"] == "Jane"
    assert row["gender"] == "male"
    assert row["birth_date"] == "1990-05-15"


def test_vitals_extraction():
    ff = FlatFHIR(str(SAMPLE))
    v = ff.vitals
    assert not v.empty
    assert "blood_pressure_systolic_mmhg" in v.columns
    assert "heart_rate_bpm" in v.columns
    assert "body_weight_kg" in v.columns


def test_labs_extraction():
    ff = FlatFHIR(str(SAMPLE))
    labs = ff.labs
    assert not labs.empty
    assert "hba1c_pct" in labs.columns
    assert "blood_glucose_fasting_mg_dl" in labs.columns


def test_medications_extraction():
    ff = FlatFHIR(str(SAMPLE))
    meds = ff.medications
    assert len(meds) == 2
    names = set(meds["medication_name"])
    assert "Metformin 500 MG Oral Tablet" in names or "Metformin 500 MG" in names


def test_conditions_extraction():
    ff = FlatFHIR(str(SAMPLE))
    conds = ff.conditions
    assert len(conds) == 2
    assert any("diabetes" in str(n).lower() for n in conds["condition_name"])


def test_allergies_extraction():
    ff = FlatFHIR(str(SAMPLE))
    allergy = ff.allergies
    assert len(allergy) == 1
    assert allergy.iloc[0]["substance"] == "Penicillin"


def test_to_prompt():
    ff = FlatFHIR(str(SAMPLE))
    prompt = ff.to_prompt()
    assert "Jane Doe" in prompt
    assert "diabetes" in prompt.lower()
    assert "Penicillin" in prompt


def test_round_trip(tmp_path):
    """Test FHIR → XLSX → FHIR round-trip."""
    xlsx_path = str(tmp_path / "roundtrip.xlsx")
    json_path = str(tmp_path / "roundtrip.json")

    flatten(str(SAMPLE), output=xlsx_path)
    bundle = unflatten(xlsx_path, output=json_path)

    assert bundle["resourceType"] == "Bundle"
    rtypes = [e["resource"]["resourceType"] for e in bundle["entry"]]
    assert "Patient" in rtypes
    assert "Observation" in rtypes
    assert "MedicationRequest" in rtypes
    assert "Condition" in rtypes


def test_merge():
    ff = merge([str(SAMPLE), str(SAMPLE)])
    # Should have double the observations
    assert not ff.vitals.empty


def test_to_json():
    ff = FlatFHIR(str(SAMPLE))
    with tempfile.NamedTemporaryFile(suffix=".json", delete=False, mode="w") as f:
        out = f.name
    try:
        ff.to_json(out)
        with open(out) as f:
            data = json.load(f)
        assert "patient" in data
        assert "vitals" in data
    finally:
        os.unlink(out)
