<?php

namespace Modules\Bms\Entities;

use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;
use Illuminate\Database\Eloquent\Relations\BelongsToMany;
use Illuminate\Database\Eloquent\Relations\HasMany;

class BmsHall extends Model
{
    protected $table = 'bms_halls';

    protected $fillable = [
        'business_id', 'venue_id', 'location_id', 'area_id', 'name', 'name_ar',
        'code', 'capacity_min', 'capacity_max', 'venue_type', 'fnb_levels',
        'min_budget', 'base_price', 'area_sqm', 'hall_manager_id', 'hall_manager_ids',
        'features', 'description', 'description_ar', 'is_active', 'sort_order',
    ];

    protected $casts = [
        'fnb_levels'       => 'array',
        'features'         => 'array',
        'hall_manager_ids' => 'array',
        'capacity_min'     => 'integer',
        'capacity_max'     => 'integer',
        'min_budget'       => 'decimal:2',
        'base_price'       => 'decimal:2',
        'area_sqm'         => 'decimal:2',
        'is_active'        => 'boolean',
        'sort_order'       => 'integer',
    ];

    public function venue(): BelongsTo
    {
        return $this->belongsTo(BmsVenue::class, 'venue_id');
    }

    public function area(): BelongsTo
    {
        return $this->belongsTo(BmsArea::class, 'area_id');
    }

    public function media(): HasMany
    {
        return $this->hasMany(BmsHallMedia::class, 'hall_id')->orderBy('sort_order');
    }

    /**
     * Packages offered in this hall. A package may span several halls (1.8.1),
     * so this resolves through the bms_package_hall pivot rather than the
     * legacy single hall_id column.
     */
    public function packages(): BelongsToMany
    {
        return $this->belongsToMany(BmsPackage::class, 'bms_package_hall', 'hall_id', 'package_id')->withTimestamps();
    }

    public function addons(): BelongsToMany
    {
        return $this->belongsToMany(BmsAddon::class, 'bms_hall_addon', 'hall_id', 'addon_id')
            ->withPivot(['price_override', 'is_available'])
            ->withTimestamps();
    }

    public function availability(): HasMany
    {
        return $this->hasMany(BmsHallAvailability::class, 'hall_id');
    }

    /** Whether this hall supports a given F&B level. */
    public function supportsFnbLevel(?string $level): bool
    {
        if (empty($level)) {
            return true;
        }
        $levels = $this->fnb_levels ?? [];
        return in_array($level, $levels, true) || in_array('custom', $levels, true);
    }

    /** Whether this hall's type satisfies a requested venue preference. */
    public function matchesVenuePreference(?string $preference): bool
    {
        if (empty($preference) || $preference === 'both' || $this->venue_type === 'both') {
            return true;
        }
        return $this->venue_type === $preference;
    }

    /**
     * Derive min_budget / base_price from the hall's active packages — pricing
     * is owned by packages, not entered on the hall (called when packages change).
     */
    public static function recomputePricing(int $hallId): void
    {
        $hall = static::find($hallId);
        if (! $hall) {
            return;
        }
        $cheapest = (float) $hall->packages()->where('is_active', true)->min('price');
        $hall->forceFill(['min_budget' => $cheapest, 'base_price' => $cheapest ?: null])->save();
    }
}
