<?php
/**
 * BookiFlex Core
 *
 * @package    BookiFlex
 * @subpackage Core
 * @author     BookiFlex
 * @copyright  Copyright (c) 2025 BookiFlex
 * @license    GPL-2.0-or-later
 *
 * @link       https://bookiflex.com
 */

declare(strict_types=1);

namespace BookiFlex\Core\Admin\PersonalData;

use BookiFlex\Core\Contract\PluginInterface;
use BookiFlex\Core\Model\Reservation\Reservation;

defined( 'ABSPATH' ) || exit;

class DataExporter
{
    private readonly PluginInterface $plugin;

    public function __construct(PluginInterface $plugin)
    {
        $this->plugin = $plugin;
        $this->init();
    }

    private function init(): void
    {
        $this->plugin->addFilter('wp_privacy_personal_data_exporters', [$this, 'registerExporter']);
    }

    public function registerExporter(array $exporters): array
    {
        $exporters['bookiflex'] = [
            'exporter_friendly_name' => __('BookiFlex Plugin Data', 'bookiflex'),
            'callback'               => [__CLASS__, 'exportPersonalData'],
        ];
        return $exporters;
    }

    public static function exportPersonalData($email_address, $page = 1): array
    {
        if (!function_exists('bookiflex')) {
            return [];
        }

        // Get plugin instance
        $plugin = bookiflex();
        if (!$plugin) {
            return ['data' => [], 'done' => true];
        }

        $container = $plugin->getContainer();
        $customerRepo = $container->get(\BookiFlex\Core\Repository\CustomerRepository::class);

        // Find customer by email
        $customer = $customerRepo->findByEmail($email_address);
        if (!$customer) {
            return ['data' => [], 'done' => true];
        }

        $export_items = [];
        $items_per_page = 100;

        // Export customer profile (page 1 only)
        if ($page === 1) {
            $export_items[] = [
                'group_id'    => 'bookiflex-customer',
                'group_label' => __('BookiFlex Customer Profile', 'bookiflex'),
                'item_id'     => 'bookiflex-customer-' . $customer->getId(),
                'data'        => [
                    [
                        'name'  => __('First Name', 'bookiflex'),
                        'value' => $customer->getFirstName(),
                    ],
                    [
                        'name'  => __('Last Name', 'bookiflex'),
                        'value' => $customer->getLastName(),
                    ],
                    [
                        'name'  => __('Email', 'bookiflex'),
                        'value' => $customer->getEmail(),
                    ],
                    [
                        'name'  => __('Phone', 'bookiflex'),
                        'value' => $customer->getPhone(),
                    ],
                    [
                        'name'  => __('Address', 'bookiflex'),
                        'value' => $customer->getAddress(),
                    ],
                    [
                        'name'  => __('City', 'bookiflex'),
                        'value' => $customer->getCity(),
                    ],
                    [
                        'name'  => __('Country', 'bookiflex'),
                        'value' => $customer->getCountry(),
                    ],
                    [
                        'name'  => __('Postal Code', 'bookiflex'),
                        'value' => $customer->getPostalCode(),
                    ],
                    [
                        'name'  => __('Notes', 'bookiflex'),
                        'value' => $customer->getNotes(),
                    ],
                    [
                        'name'  => __('Created Date', 'bookiflex'),
                        'value' => $customer->getCreatedAt()->format('Y-m-d H:i:s'),
                    ],
                ],
            ];
        }

        // Export reservations with pagination
        $reservationRepo = $container->get(\BookiFlex\Core\Repository\ReservationRepository::class);
        $offset = ($page - 1) * $items_per_page;

        $reservations = $reservationRepo->select()
            ->where('customer_id', $customer->getId())
            ->limit($items_per_page)
            ->offset($offset)
            ->fetchAll();

        /** @var Reservation $reservation */
        foreach ($reservations as $reservation) {
            $reservationData = [
                [
                    'name'  => __('Reservation Number', 'bookiflex'),
                    'value' => $reservation->getNumber(),
                ],
                [
                    'name'  => __('Check-in Date', 'bookiflex'),
                    'value' => $reservation->getMinPossibleCheckInDateTime()->format('Y-m-d'),
                ],
                [
                    'name'  => __('Check-out Date', 'bookiflex'),
                    'value' => $reservation->getMaxPossibleCheckOutDateTime()->format('Y-m-d'),
                ],
                [
                    'name'  => __('Status', 'bookiflex'),
                    'value' => $reservation->getStatus()->getValue(),
                ],
                [
                    'name'  => __('Total Amount', 'bookiflex'),
                    'value' => $reservation->getTotalAmount()->formatTo('en_US'),
                ],
                [
                    'name'  => __('Special Request', 'bookiflex'),
                    'value' => $reservation->getSpecialRequest(),
                ],
                [
                    'name'  => __('Created Date', 'bookiflex'),
                    'value' => $reservation->getCreatedAt()->format('Y-m-d H:i:s'),
                ],
            ];

            $export_items[] = [
                'group_id'    => 'bookiflex-reservations',
                'group_label' => __('BookiFlex Reservations', 'bookiflex'),
                'item_id'     => 'bookiflex-reservation-' . $reservation->getId(),
                'data'        => $reservationData,
            ];
        }

        // Check if there are more reservations
        $totalReservations = $reservationRepo->select()
            ->where('customer_id', $customer->getId())
            ->count();

        $done = ($offset + $items_per_page) >= $totalReservations;

        return [
            'data' => $export_items,
            'done' => $done,
        ];
    }
}
