<?php

namespace App\Http\Requests\Mentorship;

use Illuminate\Foundation\Http\FormRequest;
use Illuminate\Validation\Rule;

class ProgrammeRequest extends FormRequest
{
    /**
     * Determine if the user is authorized to make this request.
     */
    public function authorize(): bool
    {
        return true;
    }

    /**
     * Get the validation rules that apply to the request.
     */
    public function rules(): array
    {
        $programmeId = $this->route('programme')?->id;

        $rules = [
            'title' => [
                'required',
                'string',
                'max:191',
                'min:3',
            ],
            'slug' => [
                'nullable',
                'string',
                'max:191',
                Rule::unique('mentorship_programmes', 'slug')->ignore($programmeId),
            ],
            'description' => [
                'nullable',
                'string',
                'max:10000',
            ],
            'objectives' => [
                'nullable',
                'string',
                'max:10000',
            ],
            'requirements' => [
                'nullable',
                'string',
                'max:10000',
            ],
            'target_audience' => [
                'nullable',
                'string',
                'max:2000',
            ],
            'category_id' => [
                'nullable',
                'exists:mentorship_categories,id',
            ],
            'is_free' => [
                'boolean',
            ],
            'fee_amount' => [
                'required_if:is_free,false',
                'numeric',
                'min:0',
                'max:999999999.99',
            ],
            'currency' => [
                'required',
                'string',
                'size:3',
            ],
            'fee_description' => [
                'nullable',
                'string',
                'max:1000',
            ],
            'certificate_enabled' => [
                'boolean',
            ],
            'certificate_orientation' => [
                'required',
                'in:portrait,landscape',
            ],
            'certificate_template' => [
                'nullable',
                'string',
                'max:191',
            ],
            'duration_weeks' => [
                'nullable',
                'integer',
                'min:1',
                'max:104',
            ],
            'sessions_count' => [
                'nullable',
                'integer',
                'min:0',
                'max:365',
            ],
            'max_mentees' => [
                'nullable',
                'integer',
                'min:0',
                'max:10000',
            ],
            'max_mentors' => [
                'nullable',
                'integer',
                'min:0',
                'max:10000',
            ],
            'programme_type' => [
                'required',
                'in:one_on_one,group,hybrid',
            ],
            'session_type' => [
                'required',
                'in:online,in_person,both',
            ],
            'venue' => [
                'nullable',
                'string',
                'max:500',
            ],
            'is_active' => [
                'boolean',
            ],
            'is_featured' => [
                'boolean',
            ],
            'registration_start' => [
                'nullable',
                'date',
                'before_or_equal:registration_end',
            ],
            'registration_end' => [
                'nullable',
                'date',
                'after_or_equal:registration_start',
            ],
            'programme_start' => [
                'nullable',
                'date',
                'before_or_equal:programme_end',
            ],
            'programme_end' => [
                'nullable',
                'date',
                'after_or_equal:programme_start',
            ],
            'featured_image' => [
                'nullable',
                'string',
                'max:500',
            ],
            'gallery_images' => [
                'nullable',
                'array',
                'max:10',
            ],
            'gallery_images.*' => [
                'string',
                'max:500',
            ],
            'banner_image' => [
                'nullable',
                'string',
                'max:500',
            ],
            'meta_title' => [
                'nullable',
                'string',
                'max:191',
            ],
            'meta_description' => [
                'nullable',
                'string',
                'max:500',
            ],
        ];

        return $rules;
    }

    /**
     * Get custom messages for validator errors.
     */
    public function messages(): array
    {
        return [
            'title.required' => 'The programme title is required.',
            'title.min' => 'The programme title must be at least 3 characters.',
            'title.max' => 'The programme title may not be greater than 191 characters.',
            'slug.unique' => 'This slug is already in use. Please choose a different one.',
            'category_id.exists' => 'The selected category does not exist.',
            'fee_amount.required_if' => 'The fee amount is required when the programme is not free.',
            'fee_amount.min' => 'The fee amount must be at least 0.',
            'currency.size' => 'The currency must be a 3-letter code (e.g., UGX, USD).',
            'certificate_orientation.in' => 'The certificate orientation must be either portrait or landscape.',
            'duration_weeks.max' => 'The duration cannot exceed 104 weeks (2 years).',
            'sessions_count.max' => 'The sessions count cannot exceed 365.',
            'programme_type.in' => 'The programme type must be one-on-one, group, or hybrid.',
            'session_type.in' => 'The session type must be online, in-person, or both.',
            'registration_start.before_or_equal' => 'Registration start date must be before or equal to end date.',
            'registration_end.after_or_equal' => 'Registration end date must be after or equal to start date.',
            'programme_start.before_or_equal' => 'Programme start date must be before or equal to end date.',
            'programme_end.after_or_equal' => 'Programme end date must be after or equal to start date.',
            'gallery_images.max' => 'You can upload a maximum of 10 gallery images.',
        ];
    }

    /**
     * Prepare the data for validation.
     */
    protected function prepareForValidation(): void
    {
        $this->merge([
            'is_free' => $this->boolean('is_free'),
            'certificate_enabled' => $this->boolean('certificate_enabled'),
            'is_active' => $this->boolean('is_active'),
            'is_featured' => $this->boolean('is_featured'),
        ]);

        // Set default currency if not provided
        if (!$this->has('currency')) {
            $this->merge(['currency' => 'UGX']);
        }

        // Set fee amount to 0 if programme is free
        if ($this->boolean('is_free')) {
            $this->merge(['fee_amount' => 0]);
        }
    }

    /**
     * Get validated data with additional processing.
     */
    public function validated($key = null, $default = null): array
    {
        $validated = parent::validated($key, $default);

        // XSS Prevention
        $textFields = ['title', 'description', 'objectives', 'requirements', 'target_audience', 'fee_description', 'venue'];
        foreach ($textFields as $field) {
            if (isset($validated[$field])) {
                $validated[$field] = strip_tags($validated[$field], '<p><br><strong><em><u><ol><ul><li><a>');
            }
        }

        return $validated;
    }
}
