<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;

class UnifiedNumberSequence extends Model
{
    protected $table = 'unified_number_sequences';
    
    protected $fillable = [
        'date',
        'type',
        'last_number',
        'prefix',
        'format'
    ];
    
    protected $casts = [
        'date' => 'date',
        'last_number' => 'integer'
    ];
    
    /**
     * Get or create today's sequence
     */
    public static function getTodaySequence(string $type = 'invoice_receipt'): self
    {
        $today = now()->format('Y-m-d');
        
        return self::firstOrCreate(
            [
                'date' => $today,
                'type' => $type
            ],
            [
                'last_number' => 0,
                'prefix' => 'INVRCP',
                'format' => '{prefix}-{date}-{sequence}'
            ]
        );
    }
    
    /**
     * Get the next unified number
     */
    public static function getNextNumber(string $type = 'invoice_receipt'): string
    {
        DB::beginTransaction();
        
        try {
            // Get or create sequence with lock
            $today = now()->format('Y-m-d');
            
            $sequence = self::where('date', $today)
                ->where('type', $type)
                ->lockForUpdate()
                ->first();
            
            if (!$sequence) {
                $sequence = self::create([
                    'date' => $today,
                    'type' => $type,
                    'last_number' => 0,
                    'prefix' => 'INVRCP',
                    'format' => '{prefix}-{date}-{sequence}'
                ]);
            }
            
            // Increment and save
            $sequence->last_number++;
            $sequence->save();
            
            DB::commit();
            
            // Format the number
            return self::formatNumber($sequence);
            
        } catch (\Exception $e) {
            DB::rollBack();
            Log::error('Failed to generate unified number: ' . $e->getMessage());
            throw $e;
        }
    }
    
    /**
     * Format the number according to the pattern
     */
    private static function formatNumber(self $sequence): string
    {
        $date = $sequence->date->format('Ymd');
        $number = str_pad($sequence->last_number, 4, '0', STR_PAD_LEFT);
        
        return "{$sequence->prefix}-{$date}-{$number}";
    }
    
    /**
     * Get current number without incrementing
     */
    public static function getCurrentNumber(string $type = 'invoice_receipt'): string
    {
        $sequence = self::getTodaySequence($type);
        return self::formatNumber($sequence);
    }
    
    /**
     * Reset sequences older than today
     */
    public static function cleanOldSequences(): void
    {
        $today = now()->format('Y-m-d');
        
        self::where('date', '<', $today)
            ->where('type', 'invoice_receipt')
            ->delete();
    }
    
    /**
     * Get statistics
     */
    public static function getStats(): array
    {
        $today = now()->format('Y-m-d');
        
        $todaySequence = self::where('date', $today)
            ->where('type', 'invoice_receipt')
            ->first();
        
        $totalSequences = self::count();
        
        return [
            'today_date' => $today,
            'today_number' => $todaySequence ? $todaySequence->last_number : 0,
            'total_sequences' => $totalSequences,
            'next_number' => $todaySequence ? self::formatNumber($todaySequence) : 'INVRCP-' . $today . '-0001'
        ];
    }
}