from django.conf import settings
from django.test import TestCase

from accounts.models import User
from companies.models import Company
from employers.forms import AdminJobPostForm
from subscriptions.access import ensure_platform_admin_subscriptions
from subscriptions.management.commands.seed_plans import PLANS
from subscriptions.models import CompanySubscription, SubscriptionPlan
from subscriptions.usage import company_has_ats_subscription, get_company_benefits


class PlatformAdminEnterpriseAccessTests(TestCase):
    @classmethod
    def setUpTestData(cls):
        for plan_data in PLANS:
            SubscriptionPlan.objects.update_or_create(
                slug=plan_data['slug'],
                defaults={**plan_data, 'is_active': True},
            )
        cls.admin = User.objects.create_superuser(
            username='enterprise_admin',
            email='enterprise-admin@test.com',
            password='testpass123',
        )
        cls.company = Company.objects.create(
            name='Admin Co',
            slug='admin-co',
            initials='AC',
            industry='Tech',
            location='Lusaka',
            description='Admin company',
            owner=cls.admin,
        )

    def test_ensure_admin_subscriptions_uses_enterprise_plan(self):
        ensure_platform_admin_subscriptions(self.admin)
        subscription = CompanySubscription.objects.get(company=self.company)
        self.assertEqual(subscription.plan.slug, settings.COMPANY_ENTERPRISE_PLAN_SLUG)
        self.assertTrue(subscription.is_valid)
        self.company.refresh_from_db()
        self.assertEqual(self.company.tier, Company.Tier.ENTERPRISE)

    def test_platform_admin_has_enterprise_benefits_and_ats(self):
        ensure_platform_admin_subscriptions(self.admin)
        benefits = get_company_benefits(self.company, user=self.admin)
        self.assertTrue(benefits.can_access_ats)
        self.assertIsNone(benefits.job_posts_per_month)
        self.assertTrue(company_has_ats_subscription(self.company, user=self.admin))

    def test_admin_job_form_allows_pezajob_applications(self):
        ensure_platform_admin_subscriptions(self.admin)
        form = AdminJobPostForm(company=self.company, user=self.admin)
        self.assertTrue(form.can_use_pezajob_ats)
        self.assertEqual(len(form.fields['application_methods'].choices), 2)
        self.assertEqual(len(list(form['application_methods'])), 2)

    def test_admin_can_select_both_application_methods(self):
        ensure_platform_admin_subscriptions(self.admin)
        from jobs.category_data import sync_pezajob_categories
        from jobs.models import JobCategory

        sync_pezajob_categories(deactivate_unknown=False)
        category = JobCategory.objects.get(slug='information-technology-software')
        data = {
            'company_name': 'Admin Co',
            'title': 'Dual Apply Role',
            'company_industry': 'Information Technology & Software',
            'category': category.pk,
            'location_scope': 'single',
            'location_country': 'ZM',
            'location_region': 'Lusaka Province',
            'location_city': 'Lusaka',
            'location_regions_multi': [],
            'location_city_text': '',
            'job_type': 'full_time',
            'experience_years_min': 3,
            'experience_years_max': 5,
            'positions_total': 1,
            'application_methods': ['ats', 'email'],
            'application_candidate_fields': ['full_name', 'phone', 'email', 'profile'],
            'application_documents': ['cv'],
            'use_screening_questions': 'no',
            'screening_questions_json': '[]',
            'how_to_apply': 'careers@adminco.com',
            'description': 'Role summary.',
            'responsibilities': 'Work',
            'requirements': 'Skills',
            'benefits': '',
            'ongoing_vacancy': 'on',
        }
        form = AdminJobPostForm(data, company=self.company, user=self.admin)
        self.assertTrue(form.is_valid(), form.errors)
        job = form.save(commit=False)
        self.assertEqual(set(job.application_methods), {'ats', 'email'})
