<?php
declare(strict_types=1);

namespace App\Modules\Temporary\Services;

use App\Core\App;
use App\Modules\Rules\Services\RuleEngine;

final class TemporaryFeeCalculator
{
    public static function calculate(int $memberId, array $tempData): array
    {
        $db = App::getInstance()->db();
        $member = $db->selectOne("SELECT * FROM members WHERE id = ? AND is_archived = 0", [$memberId]);
        if (!$member) {
            return ['fee' => '0.00', 'error' => 'العضو غير موجود'];
        }

        $membershipValue = $member['membership_value'] ?? '0.00';
        if (bccomp($membershipValue, '0.00', 2) <= 0) {
            return ['fee' => '0.00', 'error' => 'قيمة العضوية غير محددة'];
        }

        $hasChampionship = (bool) ($tempData['has_championship'] ?? false);
        $category = $tempData['category'] ?? '';

        // Championship exemption
        $exemptData = RuleEngine::get('TEMP_CHAMPIONSHIP_EXEMPT');
        $isExempt = $hasChampionship && ($exemptData['exempt'] ?? true);

        if ($isExempt) {
            return [
                'fee'          => '0.00',
                'percentage'   => '0.00',
                'rule_applied' => 'TEMP_CHAMPIONSHIP_EXEMPT',
                'exempt'       => true,
                'error'        => null,
            ];
        }

        $feeData = RuleEngine::get('TEMP_MEMBER_FEE');
        $pct = $feeData['percentage'] ?? '10.00';
        $fee = bcmul($membershipValue, bcdiv($pct, '100', 4), 2);

        // Form fee if post-creation
        $formFee = '0.00';
        if ($member['status'] !== 'potential') {
            $formFeeData = RuleEngine::get('FORM_ADDITION_FEE');
            $formFee = $formFeeData['amount'] ?? '570.00';
        }

        return [
            'membership_value' => $membershipValue,
            'fee'              => $fee,
            'percentage'       => $pct,
            'form_fee'         => $formFee,
            'total_fee'        => bcadd($fee, $formFee, 2),
            'rule_applied'     => 'TEMP_MEMBER_FEE',
            'exempt'           => false,
            'error'            => null,
        ];
    }

    public static function validateCategory(string $category, array $tempData, array $member): array
    {
        $errors = [];
        $age = (int) ($tempData['age_years'] ?? 0);

        switch ($category) {
            case 'parent':
                // No specific age limit for parents
                break;

            case 'special_needs':
                if ($age < 21) {
                    $errors[] = 'أبناء ذوي الاحتياجات الخاصة يجب أن يكونوا فوق 21 سنة';
                }
                if (empty($tempData['disability_documentation'])) {
                    $errors[] = 'يجب تقديم وثائق الإعاقة';
                }
                break;

            case 'unmarried_daughter':
                if (($tempData['gender'] ?? '') !== 'female') {
                    $errors[] = 'هذه الفئة للإناث فقط';
                }
                break;

            case 'sister':
                if ($age >= 25) {
                    $errors[] = 'شقيقة العضو يجب أن تكون أقل من 25 سنة';
                }
                if (($tempData['gender'] ?? '') !== 'female') {
                    $errors[] = 'هذه الفئة للإناث فقط';
                }
                break;

            case 'stepchild':
                if ($age >= 25) {
                    $errors[] = 'أبناء الزوج/الزوجة يجب أن تكون أعمارهم أقل من 25 سنة';
                }
                break;

            case 'orphan':
                if ($age >= 25) {
                    $errors[] = 'الطفل اليتيم يجب أن يكون أقل من 25 سنة';
                }
                break;

            case 'disabled_sibling':
                if (empty($tempData['disability_documentation'])) {
                    $errors[] = 'يجب تقديم وثائق الإعاقة';
                }
                break;

            case 'nanny':
                // Nanny — companion, no specific age rules
                break;

            default:
                $errors[] = 'فئة غير معروفة';
        }

        return $errors;
    }

    public static function canSeparate(string $category): bool
    {
        $noSeparation = ['orphan', 'disabled_sibling', 'nanny', 'parent'];
        return !in_array($category, $noSeparation, true);
    }

    public static function canGetIndependent(string $category): bool
    {
        $noIndependent = ['orphan', 'disabled_sibling', 'nanny'];
        return !in_array($category, $noIndependent, true);
    }
}