/home2/mshostin/hall-management.ms-hostingladz.com/app/Services/BookingService.php
<?php
namespace App\Services;
use App\Models\Booking;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;
class BookingService
{
public function createBooking(array $bookingData): Booking
{
return DB::transaction(function () use ($bookingData) {
$bookingData['created_by'] = Auth::id();
$bookingData['updated_by'] = Auth::id();
$bookingData['booking_price'] = $bookingData['booking_price'] ?? $bookingData['quote_price'];
// Generate Booking Number
if (empty($bookingData['booking_number'])) {
$bookingData['booking_number'] = $this->generateBookingNumber($bookingData['hall_id']);
}
return Booking::create($bookingData);
});
}
private function generateBookingNumber($hallId)
{
$hall = \App\Models\Hall::find($hallId);
$hallName = $hall ? $hall->name : 'General';
// 1. Generate Hall Code (First letters of words, or first 2 chars)
$words = explode(' ', preg_replace('/[^a-zA-Z0-9\s]/', '', $hallName));
$code = '';
foreach ($words as $word) {
$code .= strtoupper(substr($word, 0, 1));
}
if (strlen($code) < 2) {
$code = strtoupper(substr(preg_replace('/[^a-zA-Z0-9]/', '', $hallName), 0, 2));
}
// Ensure at least 2 chars
if (strlen($code) < 2) {
$code = 'HL';
}
// 2. Generate Date Code (DDMMYY)
$dateCode = now()->format('dmy');
// 3. Find Sequence
$prefix = $code.$dateCode.'-';
$latestBooking = Booking::where('booking_number', 'like', $prefix.'%')
->orderBy('id', 'desc')
->first();
$sequence = 1;
if ($latestBooking && preg_match('/-(\d+)$/', $latestBooking->booking_number, $matches)) {
$sequence = intval($matches[1]) + 1;
}
return $prefix.str_pad($sequence, 4, '0', STR_PAD_LEFT);
}
public function updateBooking(Booking $booking, array $bookingData): Booking
{
return DB::transaction(function () use ($booking, $bookingData) {
$bookingData['updated_by'] = Auth::id();
$bookingData['booking_price'] = $bookingData['booking_price'] ?? $bookingData['quote_price'];
// Ensure booking number exists (for legacy records)
if (empty($booking->booking_number)) {
$hallId = $bookingData['hall_id'] ?? $booking->hall_id;
$bookingData['booking_number'] = $this->generateBookingNumber($hallId);
}
$booking->update($bookingData);
return $booking;
});
}
public function checkAvailability(int $lawnId, string $start, string $end, ?int $excludeId = null): bool
{
return ! Booking::where('lawn_id', $lawnId)
->when($excludeId, fn ($q) => $q->where('id', '!=', $excludeId))
->where(function ($q) use ($start, $end) {
$q->whereBetween('start_datetime', [$start, $end])
->orWhereBetween('end_datetime', [$start, $end])
->orWhere(function ($r) use ($start, $end) {
$r->where('start_datetime', '<=', $start)
->where('end_datetime', '>=', $end);
});
})
->exists();
}
}