<?php

namespace App\Models\ScssCdn;

use App\Models\Auth\User;
use App\Models\Products\Product;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Str;

class ScssCdnFile extends Model
{
    use HasFactory;

    protected $table = 'scss_cdn_files';

    protected $fillable = [
        'scss_cdn_bundle_id',
        'relative_path',
        'filename',
        'is_servable',
        'secure_token',
        'created_by',
        'updated_by',
    ];

    protected $casts = [
        'is_servable' => 'boolean',
    ];

    /* -----------------------------
       Relaciones
    ------------------------------*/

    /**
     * Bundle al que pertenece el archivo
     */
    public function bundle()
    {
        return $this->belongsTo(ScssCdnBundle::class, 'scss_cdn_bundle_id');
    }

    /**
     * Producto al que pertenece el archivo (a través de bundle)
     */
    public function product()
    {
        return $this->hasOneThrough(Product::class, ScssCdnBundle::class, 'id', 'id', 'scss_cdn_bundle_id', 'product_id');
    }

    /**
     * Usuario que creó el archivo
     */
    public function creator()
    {
        return $this->belongsTo(User::class, 'created_by');
    }

    /**
     * Usuario que editó por última vez el archivo
     */
    public function updater()
    {
        return $this->belongsTo(User::class, 'updated_by');
    }

    /* -----------------------------
       Scopes
    ------------------------------*/

    /**
     * Scope para filtrar por bundle
     */
    public function scopeForBundle($query, $bundle)
    {
        $bundleId = $bundle instanceof ScssCdnBundle ? $bundle->id : $bundle;
        return $query->where('scss_cdn_bundle_id', $bundleId);
    }

    /**
     * Scope para filtrar archivos servibles
     */
    public function scopeServable($query)
    {
        return $query->where('is_servable', true);
    }

    /* -----------------------------
       Métodos de instancia
    ------------------------------*/

    /**
     * Obtiene el contenido del archivo desde storage físico
     *
     * @return string|null
     */
    public function getContent(): ?string
    {
        if (!$this->bundle) {
            $this->load('bundle');
        }
        
        if (!$this->bundle || !$this->bundle->product) {
            $this->bundle->load('product');
        }

        return \App\Services\ScssCdn\ScssCdnStorageService::getFile(
            $this->bundle->product,
            $this->bundle,
            $this->relative_path
        );
    }

    /**
     * Guarda el contenido del archivo en storage físico
     *
     * @param string $content
     * @return bool
     */
    public function setContent(string $content): bool
    {
        if (!$this->bundle) {
            $this->load('bundle');
        }
        
        if (!$this->bundle || !$this->bundle->product) {
            $this->bundle->load('product');
        }

        return \App\Services\ScssCdn\ScssCdnStorageService::saveFile(
            $this->bundle->product,
            $this->bundle,
            $this->relative_path,
            $content
        );
    }

    /**
     * Obtiene la ruta completa del archivo
     *
     * @return string
     */
    public function getFullPath(): string
    {
        return $this->relative_path;
    }

    /**
     * Obtiene el directorio del archivo (sin el nombre del archivo)
     *
     * @return string
     */
    public function getDirectoryPath(): string
    {
        $path = dirname($this->relative_path);
        return $path === '.' ? '' : $path;
    }

    /**
     * Genera un nuevo token seguro si no existe
     *
     * @return void
     */
    protected static function booted()
    {
        static::creating(function ($file) {
            if (empty($file->secure_token)) {
                $file->secure_token = Str::random(32);
            }
        });
    }
}

