<?php

namespace App\Console\Commands;

use Illuminate\Console\Command;
use Illuminate\Support\Str;
use Illuminate\Database\Eloquent\Model;

class AuditModelColumns extends Command
{
    /**
     * The name and signature of the console command.
     *
     * @var string
     */
    protected $signature = 'audit:model-columns';

    /**
     * The console command description.
     *
     * @var string
     */
    protected $description = 'Audit all Eloquent models for missing columns in their tables.';

    /**
     * Execute the console command.
     *
     * @return int
     */
    public function handle()
    {
        // Dynamically discover all model classes in app/ and app/Modules/
        $modelDirs = [
            app_path('Models'),
            app_path('Modules'),
        ];
        $models = [];
        foreach ($modelDirs as $dir) {
            if (!is_dir($dir)) continue;
            $rii = new \RecursiveIteratorIterator(new \RecursiveDirectoryIterator($dir));
            foreach ($rii as $file) {
                if ($file->isDir() || $file->getExtension() !== 'php') continue;
                $contents = file_get_contents($file->getPathname());
                // Extract namespace and class name
                $namespace = '';
                if (preg_match('/namespace\s+([^;]+);/', $contents, $nsMatch)) {
                    $namespace = trim($nsMatch[1]);
                }
                if (preg_match('/class\s+(\w+)\s+extends\s+(ValidationModel|Model)/', $contents, $classMatch)) {
                    $className = $classMatch[1];
                    $fqcn = $namespace ? ($namespace . '\\' . $className) : $className;
                    if (!class_exists($fqcn)) continue;
                    try {
                        $reflection = new \ReflectionClass($fqcn);
                        if ($reflection->isAbstract()) {
                            continue;
                        }
                        $models[] = $fqcn;
                    } catch (\Throwable $e) {
                        continue;
                    }
                }
            }
        }
        $models = array_unique($models);
        if (empty($models)) {
            $this->error('No models found for audit.');
            return 1;
        }
        foreach ($models as $modelClass) {
            try {
                /** @var \Illuminate\Database\Eloquent\Model $model */
                $model = new $modelClass;
                $table = $model->getTable();
                $expected = array_unique(array_merge($model->getFillable(), method_exists($model, 'getDates') ? $model->getDates() : []));
                $actual = \Schema::getColumnListing($table);
                $missing = array_diff($expected, $actual);
                if ($missing) {
                    $this->warn("Table '$table' is missing columns: " . implode(', ', $missing) . " (Model: $modelClass)");
                } else {
                    $this->info("Table '$table' is OK. (Model: $modelClass)");
                }
            } catch (\Throwable $e) {
                $this->error("Error auditing $modelClass: " . $e->getMessage());
            }
        }
        $this->info('Audit complete.');
        return 0;
    }

    private function getClassFullNameFromFile($filePath)
    {
        // Try to get the full class name
        $relPath = str_replace([app_path() . '/', '.php'], '', $filePath);
        $relPath = str_replace(DIRECTORY_SEPARATOR, '\\', $relPath);
        $namespace = '';
        if (preg_match('/namespace\\s+([^;]+);/', file_get_contents($filePath), $ns)) {
            $namespace = trim($ns[1]) . '\\';
        }
        $className = $namespace . basename($relPath, '.php');
        return class_exists($className) ? $className : null;
    }
} 