<?php
/**
 * BookiFlex Core
 *
 * @package    BookiFlex
 * @subpackage Core
 * @author     BookiFlex
 * @copyright  Copyright (c) 2025 BookiFlex
 * @license    GPL-2.0-or-later
 *
 * @link       https://bookiflex.com
 */

// File: DTO/ProlongDateUnits.php

declare(strict_types=1);

namespace BookiFlex\Core\Service\DateUnit\DTO;

use BookiFlex\Core\Model\AccommodationType\Accommodation\AccommodationType;
use BookiFlex\Core\Model\RatePlan\RatePlan;
use DateTimeImmutable;

defined( 'ABSPATH' ) || exit;

class ExtendDateUnits
{
    public const DAY_MON = 'mon';
    public const DAY_TUE = 'tue';
    public const DAY_WED = 'wed';
    public const DAY_THU = 'thu';
    public const DAY_FRI = 'fri';
    public const DAY_SAT = 'sat';
    public const DAY_SUN = 'sun';

    private const VALID_DAYS = [
        self::DAY_MON,
        self::DAY_TUE,
        self::DAY_WED,
        self::DAY_THU,
        self::DAY_FRI,
        self::DAY_SAT,
        self::DAY_SUN
    ];

    private RatePlan $ratePlan;
    /** @var AccommodationType[] */
    private array $accommodationTypes;
    private DateTimeImmutable $dateFrom;
    private DateTimeImmutable $dateTo;
    private array $activeDays;

    /**
     * @param RatePlan $ratePlan
     * @param AccommodationType[] $accommodationTypes
     * @param DateTimeImmutable $dateFrom
     * @param DateTimeImmutable $dateTo
     * @param array $activeDays
     */
    public function __construct(
        RatePlan $ratePlan,
        array $accommodationTypes,
        DateTimeImmutable $dateFrom,
        DateTimeImmutable $dateTo,
        array $activeDays
    ) {
        $this->ratePlan = $ratePlan;
        $this->accommodationTypes = $this->filterAccommodationTypes($accommodationTypes);
        $this->dateFrom = $dateFrom->setTime(0, 0);
        $this->dateTo = $dateTo->setTime(23, 59, 59);
        $this->activeDays = $this->normalizeActiveDays($activeDays);
    }

    public function getRatePlan(): RatePlan
    {
        return $this->ratePlan;
    }

    /**
     * @return AccommodationType[]
     */
    public function getAccommodationTypes(): array
    {
        return $this->accommodationTypes;
    }

    public function getDateFrom(): DateTimeImmutable
    {
        return $this->dateFrom;
    }

    public function getDateTo(): DateTimeImmutable
    {
        return $this->dateTo;
    }

    public function getActiveDays(): array
    {
        return $this->activeDays;
    }

    /**
     * Filter and validate accommodation types
     */
    private function filterAccommodationTypes(array $accommodationTypes): array
    {
        return array_values(
            array_filter(
                $accommodationTypes,
                fn($at) => $at instanceof AccommodationType
            )
        );
    }

    /**
     * Normalize and validate active days
     */
    private function normalizeActiveDays(array $activeDays): array
    {
        if (empty($activeDays)) {
            return [];
        }

        // Filter only valid day keys
        $validDays = array_filter(
            $activeDays,
            fn($key) => in_array($key, self::VALID_DAYS, true),
            ARRAY_FILTER_USE_KEY
        );

        // Convert all values to boolean
        return array_map(
            fn($value) => (bool)$value,
            $validDays
        );
    }
}
