<?php

namespace Modules\Booking\Services;

use Modules\Booking\Data\VehicleSelectionData;
use Modules\Booking\Exceptions\InvalidVehicleSelectionException;
use Modules\Shared\Enums\VehicleOption;

class BookingService
{
    /**
     * Enforces the only v1 inventory rule (max Front Seats per booking), the
     * blunt config toggles for Back Seat / Whole Vehicle availability, and
     * shape rules around combining options in one booking (no duplicate
     * option lines, Whole Vehicle can't be mixed with anything else since it
     * already covers the whole car).
     *
     * Deliberately does not check real capacity/availability — that's an
     * explicitly deferred future phase (domain.md §2, §7).
     *
     * @param  list<VehicleSelectionData>  $selections
     *
     * @throws InvalidVehicleSelectionException
     */
    public function validateSelections(array $selections): void
    {
        $seen = [];

        foreach ($selections as $selection) {
            if (isset($seen[$selection->vehicleOption->value])) {
                throw InvalidVehicleSelectionException::duplicateOption($selection->vehicleOption);
            }

            $seen[$selection->vehicleOption->value] = true;

            $this->validateOption($selection->vehicleOption, $selection->passengerCount);
        }

        if (isset($seen[VehicleOption::WholeVehicle->value]) && count($seen) > 1) {
            throw InvalidVehicleSelectionException::wholeVehicleCannotBeCombined();
        }
    }

    private function validateOption(VehicleOption $vehicleOption, int $passengerCount): void
    {
        match ($vehicleOption) {
            VehicleOption::FrontSeat => $this->validateFrontSeat($passengerCount),
            VehicleOption::BackSeat => $this->validateEnabled($vehicleOption, 'booking.back_seat_enabled'),
            VehicleOption::WholeVehicle => $this->validateEnabled($vehicleOption, 'booking.whole_vehicle_enabled'),
        };
    }

    private function validateFrontSeat(int $passengerCount): void
    {
        $max = config('booking.front_seat_max_per_booking');

        if ($passengerCount > $max) {
            throw InvalidVehicleSelectionException::frontSeatLimitExceeded($passengerCount, $max);
        }
    }

    private function validateEnabled(VehicleOption $vehicleOption, string $configKey): void
    {
        if (! config($configKey)) {
            throw InvalidVehicleSelectionException::optionDisabled($vehicleOption);
        }
    }
}
