<?php

declare(strict_types=1);

namespace App\Framework\Database\Backup;

/**
 * Configuration options for database backups
 */
final readonly class BackupOptions
{
    public function __construct(
        public bool $includeStructure = true,
        public bool $includeData = true,
        public bool $compress = true,
        public bool $encrypt = false,
        public ?array $includeTables = null,
        public ?array $excludeTables = null,
        public bool $singleTransaction = true,
        public bool $routines = true,
        public bool $triggers = true,
        public bool $events = false,
        public int $maxMemory = 256 * 1024 * 1024, // 256MB
    ) {
    }

    /**
     * Create options for structure-only backup
     */
    public static function structureOnly(): self
    {
        return new self(
            includeStructure: true,
            includeData: false,
            compress: true,
            encrypt: false
        );
    }

    /**
     * Create options for data-only backup
     */
    public static function dataOnly(): self
    {
        return new self(
            includeStructure: false,
            includeData: true,
            compress: true,
            encrypt: false
        );
    }

    /**
     * Create options for secure encrypted backup
     */
    public static function encrypted(): self
    {
        return new self(
            includeStructure: true,
            includeData: true,
            compress: true,
            encrypt: true
        );
    }

    /**
     * Create options for quick uncompressed backup
     */
    public static function quick(): self
    {
        return new self(
            includeStructure: true,
            includeData: true,
            compress: false,
            encrypt: false,
            singleTransaction: false,
            routines: false,
            triggers: false
        );
    }

    /**
     * Create options with specific table inclusion
     */
    public function withTables(array $tables): self
    {
        return new self(
            includeStructure: $this->includeStructure,
            includeData: $this->includeData,
            compress: $this->compress,
            encrypt: $this->encrypt,
            includeTables: $tables,
            excludeTables: $this->excludeTables,
            singleTransaction: $this->singleTransaction,
            routines: $this->routines,
            triggers: $this->triggers,
            events: $this->events,
            maxMemory: $this->maxMemory
        );
    }

    /**
     * Create options excluding specific tables
     */
    public function excludingTables(array $tables): self
    {
        return new self(
            includeStructure: $this->includeStructure,
            includeData: $this->includeData,
            compress: $this->compress,
            encrypt: $this->encrypt,
            includeTables: $this->includeTables,
            excludeTables: $tables,
            singleTransaction: $this->singleTransaction,
            routines: $this->routines,
            triggers: $this->triggers,
            events: $this->events,
            maxMemory: $this->maxMemory
        );
    }

    /**
     * Enable encryption
     */
    public function withEncryption(): self
    {
        return new self(
            includeStructure: $this->includeStructure,
            includeData: $this->includeData,
            compress: $this->compress,
            encrypt: true,
            includeTables: $this->includeTables,
            excludeTables: $this->excludeTables,
            singleTransaction: $this->singleTransaction,
            routines: $this->routines,
            triggers: $this->triggers,
            events: $this->events,
            maxMemory: $this->maxMemory
        );
    }

    /**
     * Convert to array for serialization
     */
    public function toArray(): array
    {
        return [
            'includeStructure' => $this->includeStructure,
            'includeData' => $this->includeData,
            'compress' => $this->compress,
            'encrypt' => $this->encrypt,
            'includeTables' => $this->includeTables,
            'excludeTables' => $this->excludeTables,
            'singleTransaction' => $this->singleTransaction,
            'routines' => $this->routines,
            'triggers' => $this->triggers,
            'events' => $this->events,
            'maxMemory' => $this->maxMemory,
        ];
    }

    /**
     * Create from array
     */
    public static function fromArray(array $data): self
    {
        return new self(
            includeStructure: $data['includeStructure'] ?? true,
            includeData: $data['includeData'] ?? true,
            compress: $data['compress'] ?? true,
            encrypt: $data['encrypt'] ?? false,
            includeTables: $data['includeTables'] ?? null,
            excludeTables: $data['excludeTables'] ?? null,
            singleTransaction: $data['singleTransaction'] ?? true,
            routines: $data['routines'] ?? true,
            triggers: $data['triggers'] ?? true,
            events: $data['events'] ?? false,
            maxMemory: $data['maxMemory'] ?? 256 * 1024 * 1024,
        );
    }
}
