'Sedan / Hatchback', 'suv' => 'SUV / Crossover', 'commercial' => 'Comercial (van/camion)', 'hybrid' => 'Hibrid', 'ev' => 'Electric (EV)', 'premium' => 'Premium / Lux', ]; public const URGENCY = [ 'normal' => 'Normal', 'urgent' => 'Urgent', 'express' => 'Express', ]; protected $fillable = [ 'company_id', 'name', 'multiplier', 'conditions', 'priority', 'stackable', 'is_active', ]; protected $casts = [ 'multiplier' => 'decimal:3', 'conditions' => 'array', 'stackable' => 'boolean', 'is_active' => 'boolean', ]; /** * Does this coefficient apply to the given pricing context? * * @param array{class?:?string, age?:?int, vip?:bool, urgency?:string} $ctx */ public function matches(array $ctx): bool { $c = (array) $this->conditions; // Vehicle class — if rule lists classes, context class must be among them. $classes = (array) ($c['classes'] ?? []); if (! empty($classes)) { if (empty($ctx['class']) || ! in_array($ctx['class'], $classes, true)) { return false; } } // Vehicle age range. if (isset($c['age_min']) && $c['age_min'] !== null && $c['age_min'] !== '') { if (($ctx['age'] ?? null) === null || $ctx['age'] < (int) $c['age_min']) return false; } if (isset($c['age_max']) && $c['age_max'] !== null && $c['age_max'] !== '') { if (($ctx['age'] ?? null) === null || $ctx['age'] > (int) $c['age_max']) return false; } // VIP requirement (true = only VIP, false/null = ignore). if (! empty($c['client_vip'])) { if (empty($ctx['vip'])) return false; } // Urgency — if rule lists urgencies, context must match. $urg = (array) ($c['urgency'] ?? []); if (! empty($urg)) { if (empty($ctx['urgency']) || ! in_array($ctx['urgency'], $urg, true)) { return false; } } return true; } }