"""PRD §5.1 FRFA-CS005 — type-configured form template rules per call_type.

Assertions:
- Fellowship form surfaces fellowship fields and drops scholarship/challenge fields.
- Challenge form surfaces challenge fields and drops scholarship/fellowship fields.
- The clean() loop zeroes out per-type fields that aren't visible for the chosen call_type,
  preventing a scholarship-only flag from leaking into a fellowship row.
"""
import pytest

from apps.rims.grants.forms import GrantCallForm
from apps.rims.grants.models import GrantCall


@pytest.mark.django_db
def test_fellowship_form_clean_drops_scholarship_flags():
    """A fellowship submission that ALSO ticks scholarship_university_required must
    not persist that flag — the per-type clean loop nulls fields outside the
    fellowship visible_fields set."""
    from datetime import timedelta
    from django.utils import timezone

    form = GrantCallForm(
        data={
            "title": "Fellowship 2026",
            "call_type": GrantCall.CallType.FELLOWSHIP,
            "opens_at": timezone.now().strftime("%Y-%m-%dT%H:%M"),
            "closes_at": (timezone.now() + timedelta(days=30)).strftime("%Y-%m-%dT%H:%M"),
            "reviewers_per_application": 2,
            "review_deadline_days": 14,
            "tie_break_policy": GrantCall.TieBreakPolicy.MANAGER_REVIEW,
            "reviewer_workload_mode": GrantCall.ReviewerWorkloadMode.BALANCED,
            "verification_type": GrantCall.VerificationType.NONE,
            "verification_score_weight": "0.00",
            # Fellowship-applicable fields:
            "fellowship_host_institution_required": "on",
            "fellowship_term_months": "12",
            # Cross-contamination from another type — these must be zeroed by clean():
            "scholarship_university_required": "on",
            "scholarship_course_required": "on",
            "scholarship_cohort_year": "2027",
            "challenge_sector_focus": "agritech",
        }
    )
    assert form.is_valid(), form.errors
    cleaned = form.cleaned_data
    assert cleaned["call_type"] == GrantCall.CallType.FELLOWSHIP
    assert cleaned["fellowship_host_institution_required"] is True
    assert cleaned["fellowship_term_months"] == 12
    # Scholarship + challenge fields zeroed because they're not in fellowship's
    # visible_fields:
    assert cleaned["scholarship_university_required"] is False
    assert cleaned["scholarship_course_required"] is False
    assert cleaned["scholarship_cohort_year"] is None
    assert cleaned["challenge_sector_focus"] == ""


@pytest.mark.django_db
def test_challenge_form_keeps_challenge_fields_zeros_others():
    from datetime import timedelta
    from django.utils import timezone

    form = GrantCallForm(
        data={
            "title": "Innovation Challenge 2026",
            "call_type": GrantCall.CallType.CHALLENGE,
            "opens_at": timezone.now().strftime("%Y-%m-%dT%H:%M"),
            "closes_at": (timezone.now() + timedelta(days=30)).strftime("%Y-%m-%dT%H:%M"),
            "reviewers_per_application": 2,
            "review_deadline_days": 14,
            "tie_break_policy": GrantCall.TieBreakPolicy.MANAGER_REVIEW,
            "reviewer_workload_mode": GrantCall.ReviewerWorkloadMode.BALANCED,
            "verification_type": GrantCall.VerificationType.NONE,
            "verification_score_weight": "0.00",
            "challenge_innovation_stage": GrantCall.InnovationStage.PILOT,
            "challenge_sector_focus": "fintech",
            # Cross-contamination:
            "applicant_budget_required": "on",
            "fellowship_term_months": "24",
        }
    )
    assert form.is_valid(), form.errors
    cleaned = form.cleaned_data
    assert cleaned["challenge_innovation_stage"] == GrantCall.InnovationStage.PILOT
    assert cleaned["challenge_sector_focus"] == "fintech"
    # Grant + fellowship fields zeroed:
    assert cleaned["applicant_budget_required"] is False
    assert cleaned["fellowship_term_months"] is None


@pytest.mark.django_db
def test_grant_form_keeps_grant_fields_zeros_per_type_extras():
    from datetime import timedelta
    from django.utils import timezone

    form = GrantCallForm(
        data={
            "title": "Research Grant 2026",
            "call_type": GrantCall.CallType.GRANT,
            "opens_at": timezone.now().strftime("%Y-%m-%dT%H:%M"),
            "closes_at": (timezone.now() + timedelta(days=30)).strftime("%Y-%m-%dT%H:%M"),
            "reviewers_per_application": 2,
            "review_deadline_days": 14,
            "tie_break_policy": GrantCall.TieBreakPolicy.MANAGER_REVIEW,
            "reviewer_workload_mode": GrantCall.ReviewerWorkloadMode.BALANCED,
            "verification_type": GrantCall.VerificationType.NONE,
            "verification_score_weight": "0.00",
            "applicant_budget_required": "on",
            # Cross-contamination:
            "scholarship_cohort_year": "2027",
            "fellowship_term_months": "12",
            "challenge_sector_focus": "edtech",
        }
    )
    assert form.is_valid(), form.errors
    cleaned = form.cleaned_data
    assert cleaned["applicant_budget_required"] is True
    assert cleaned["scholarship_cohort_year"] is None
    assert cleaned["fellowship_term_months"] is None
    assert cleaned["challenge_sector_focus"] == ""


@pytest.mark.django_db
def test_grantcall_model_supports_fellowship_and_challenge_fields():
    """Round-trip the new model fields to confirm the migration applied."""
    from datetime import timedelta
    from django.utils import timezone

    GrantCall.objects.create(
        title="Fellowship",
        slug="fellowship-test",
        call_type=GrantCall.CallType.FELLOWSHIP,
        opens_at=timezone.now(),
        closes_at=timezone.now() + timedelta(days=30),
        fellowship_host_institution_required=True,
        fellowship_term_months=18,
    )
    fellowship = GrantCall.objects.get(slug="fellowship-test")
    assert fellowship.fellowship_host_institution_required is True
    assert fellowship.fellowship_term_months == 18

    GrantCall.objects.create(
        title="Challenge",
        slug="challenge-test",
        call_type=GrantCall.CallType.CHALLENGE,
        opens_at=timezone.now(),
        closes_at=timezone.now() + timedelta(days=30),
        challenge_innovation_stage=GrantCall.InnovationStage.SCALE,
        challenge_sector_focus="climatetech",
    )
    challenge = GrantCall.objects.get(slug="challenge-test")
    assert challenge.challenge_innovation_stage == GrantCall.InnovationStage.SCALE
    assert challenge.challenge_sector_focus == "climatetech"
