<?php
declare(strict_types=1);

namespace Itdatex\Rechnungseingang;

if ( ! defined( 'ABSPATH' ) ) { exit; }

/**
 * Aktivierung / Deaktivierung des Plugins.
 *
 * - Legt die drei Kerntabellen an (invoices, files, audit_log)
 * - Erzeugt geschuetzten Upload-Ordner unter uploads/itdatex-e-invoice-intake-{zufall}/
 * - Setzt Capability auf der Administrator-Rolle
 *
 * Die eigentliche Deinstallation (Tabellen + Dateien) passiert in uninstall.php
 * und ist absichtlich vorsichtig: 8-10 Jahre Aufbewahrungspflicht!
 */
final class Installer
{
    public const DB_VERSION_OPTION = 'reing_db_version';
    public const DB_VERSION        = '1';
    public const UPLOAD_DIR_OPTION = 'reing_upload_dir';

    public static function activate(): void
    {
        self::create_tables();
        self::create_upload_dir();
        self::add_capability();
        flush_rewrite_rules();
    }

    public static function deactivate(): void
    {
        flush_rewrite_rules();
    }

    public static function create_tables(): void
    {
        global $wpdb;
        $charset = $wpdb->get_charset_collate();
        $invoices  = $wpdb->prefix . 'reing_invoices';
        $files     = $wpdb->prefix . 'reing_files';
        $audit     = $wpdb->prefix . 'reing_audit_log';

        require_once ABSPATH . 'wp-admin/includes/upgrade.php';

        // dbDelta ist zickig: Spalten-Definitionen exakt formatieren,
        // KEINE doppelten Leerzeichen, Index-Definitionen mit korrekten Klammern.
        dbDelta( "CREATE TABLE $invoices (
            id BIGINT UNSIGNED NOT NULL AUTO_INCREMENT,
            file_id BIGINT UNSIGNED NOT NULL,
            direction VARCHAR(16) NOT NULL DEFAULT 'incoming',
            format VARCHAR(32) NOT NULL,
            invoice_number VARCHAR(190),
            issue_date DATE,
            due_date DATE,
            seller_name VARCHAR(190),
            seller_vat_id VARCHAR(32),
            buyer_name VARCHAR(190),
            buyer_reference VARCHAR(190),
            total_net DECIMAL(15,4),
            total_tax DECIMAL(15,4),
            total_gross DECIMAL(15,4),
            currency CHAR(3) DEFAULT 'EUR',
            line_count INT UNSIGNED NOT NULL DEFAULT 0,
            validation_status VARCHAR(16) NOT NULL DEFAULT 'unchecked',
            validation_errors INT UNSIGNED NOT NULL DEFAULT 0,
            validation_warnings INT UNSIGNED NOT NULL DEFAULT 0,
            validation_report LONGTEXT,
            payment_status VARCHAR(16) NOT NULL DEFAULT 'open',
            extracted_by VARCHAR(16) NOT NULL DEFAULT 'parser',
            raw_meta LONGTEXT,
            created_at DATETIME NOT NULL,
            updated_at DATETIME NOT NULL,
            PRIMARY KEY  (id),
            KEY file_id (file_id),
            KEY idx_due (payment_status, due_date),
            KEY idx_seller (seller_name(50))
        ) $charset;" );

        dbDelta( "CREATE TABLE $files (
            id BIGINT UNSIGNED NOT NULL AUTO_INCREMENT,
            stored_name VARCHAR(190) NOT NULL,
            original_name VARCHAR(190) NOT NULL,
            mime VARCHAR(64),
            size_bytes BIGINT UNSIGNED,
            sha256 CHAR(64) NOT NULL,
            chain_hash CHAR(64) NOT NULL,
            source VARCHAR(16) NOT NULL DEFAULT 'upload',
            created_at DATETIME NOT NULL,
            PRIMARY KEY  (id),
            UNIQUE KEY uq_sha (sha256)
        ) $charset;" );

        dbDelta( "CREATE TABLE $audit (
            id BIGINT UNSIGNED NOT NULL AUTO_INCREMENT,
            invoice_id BIGINT UNSIGNED,
            actor VARCHAR(64),
            action VARCHAR(64) NOT NULL,
            detail TEXT,
            created_at DATETIME NOT NULL,
            PRIMARY KEY  (id),
            KEY idx_inv (invoice_id)
        ) $charset;" );

        update_option( self::DB_VERSION_OPTION, self::DB_VERSION );
    }

    /**
     * Legt einen geschuetzten Upload-Ordner mit Zufallssuffix an.
     * Dateiname wird in Optionen gespeichert (idempotent).
     */
    public static function create_upload_dir(): void
    {
        $existing = (string) get_option( self::UPLOAD_DIR_OPTION, '' );
        if ( $existing && is_dir( $existing ) ) {
            return;
        }

        $uploads = wp_upload_dir();
        $rand    = bin2hex( random_bytes( 8 ) ); // 16 chars
        $dirname = 'itdatex-e-invoice-intake-' . $rand;
        $path    = trailingslashit( $uploads['basedir'] ) . $dirname;

        if ( ! wp_mkdir_p( $path ) ) {
            return; // Fehler wird beim ersten Upload sichtbar
        }

        // Apache/LiteSpeed-Schutz
        @file_put_contents( $path . '/.htaccess', "Require all denied\nDeny from all\n" );
        // PHP-Listing-Schutz + nginx-fallback
        @file_put_contents( $path . '/index.php', "<?php // Silence is golden.\n" );

        update_option( self::UPLOAD_DIR_OPTION, $path );
    }

    public static function add_capability(): void
    {
        $role = get_role( 'administrator' );
        if ( $role && ! $role->has_cap( Plugin::CAPABILITY ) ) {
            $role->add_cap( Plugin::CAPABILITY );
        }
    }
}
