<?php

namespace WPSN\Modules\Onboarding\Admin;

use WPSN\Admin\SettingsRepository;
use WPSN\Core\Branding;
use WPSN\Core\Container;
use WPSN\Core\Capabilities;
use WPSN\Core\Logger;
use WPSN\Core\Settings;
use WPSN\Modules\Onboarding\OnboardingChecklistRuntime;
use WPSN\Modules\Onboarding\OnboardingChecklistStateRepository;
use WPSN\Modules\TasksHub\SetupTasksProvider;

defined('ABSPATH') || exit;

final class OnboardingAdmin
{
    private const PAGE_SLUG = 'wpsn-setup-wizard';

    private const OPT_COMPLETED = 'wpsn_onboarding_completed';
    private const OPT_DISMISSED = 'wpsn_onboarding_dismissed';

    private Container $container;
    private Settings $settings;
    private Logger $logger;

    public function __construct(Container $container, Settings $settings, Logger $logger)
    {
        $this->container = $container;
        $this->settings = $settings;
        $this->logger = $logger;
    }

    public function register(): void
    {
        add_action('admin_menu', [$this, 'addMenu']);

        add_action('admin_notices', [$this, 'maybeNotice']);

        add_action('admin_post_wpsn_onboarding_apply_preset', [$this, 'handleApplyPreset']);
        add_action('admin_post_wpsn_onboarding_complete', [$this, 'handleComplete']);
        add_action('admin_post_wpsn_onboarding_dismiss', [$this, 'handleDismiss']);
        add_action('admin_post_wpsn_onboarding_setup_task_state', [$this, 'handleSetupTaskState']);
    }

    public function addMenu(): void
    {
        add_management_page(
            __('SEO Setup Wizard', 'wp-seo-next'),
            __('SEO Setup Wizard', 'wp-seo-next'),
            Capabilities::CAP_TOOLS,
            self::PAGE_SLUG,
            [$this, 'renderPage']
        );
    }

    public function maybeNotice(): void
    {
        if (!current_user_can(Capabilities::CAP_TOOLS)) {
            return;
        }

        // Trust/Privacy policy: disable setup notices (no nags).
        if ((bool) $this->settings->get('privacy.no_nags', false)) {
            return;
        }

        // Already completed.
        if (!empty(get_option(self::OPT_COMPLETED))) {
            return;
        }

        // Dismissed.
        if (!empty(get_option(self::OPT_DISMISSED))) {
            return;
        }

        // Show only on dashboard + our plugin pages to avoid annoyance.
        $screen = function_exists('get_current_screen') ? get_current_screen() : null;
        $base = is_object($screen) && isset($screen->base) ? (string) $screen->base : '';
        $allowedBases = [
            'dashboard',
            'settings_page_wp-seo-next',
            'tools_page_wpsn-bulk-table',
            'tools_page_wpsn-import-export',
            'tools_page_wpsn-indexnow',
            'tools_page_wpsn-search-console',
            'tools_page_wpsn-setup-wizard',
        ];
        if ($base !== '' && !in_array($base, $allowedBases, true)) {
            return;
        }

        $brand = Branding::brand($this->settings);
        $brandSafe = $brand !== '' ? $brand : __('SEO', 'wp-seo-next');

        $url = $this->pageUrl(['step' => 1]);
        $dismissUrl = wp_nonce_url(admin_url('admin-post.php?action=wpsn_onboarding_dismiss'), 'wpsn_onboarding_dismiss');

        echo '<div class="notice notice-info is-dismissible">';
        echo '<p><strong>' . esc_html($brandSafe) . ':</strong> ' . esc_html__('Run the quick setup wizard to apply a preset, migrate from another SEO plugin, and verify key settings.', 'wp-seo-next') . '</p>';
        echo '<p>';
        echo '<a class="button button-primary" href="' . esc_url($url) . '">' . esc_html__('Open Setup Wizard', 'wp-seo-next') . '</a> ';
        echo '<a class="button button-secondary" href="' . esc_url($dismissUrl) . '">' . esc_html__('Dismiss', 'wp-seo-next') . '</a>';
        echo '</p>';
        echo '</div>';
    }

    public function renderPage(): void
    {
        if (!current_user_can(Capabilities::CAP_TOOLS)) {
            wp_die(esc_html__('You do not have permission to access this page.', 'wp-seo-next'));
        }

        $step = isset($_GET['step']) ? (int) $_GET['step'] : 1;
        if ($step < 1 || $step > 3) {
            $step = 1;
        }

        $brand = Branding::brand($this->settings);
        $brandSafe = $brand !== '' ? $brand : __('SEO', 'wp-seo-next');

        echo '<div class="wrap">';
        echo '<h1>' . esc_html(sprintf(__('SEO Setup Wizard — %s', 'wp-seo-next'), $brandSafe)) . '</h1>';

        // Steps nav.
        echo '<div style="margin:12px 0;">';
        $steps = [
            1 => __('Welcome', 'wp-seo-next'),
            2 => __('Choose a preset', 'wp-seo-next'),
            3 => __('Next steps', 'wp-seo-next'),
        ];
        foreach ($steps as $n => $label) {
            $url = $this->pageUrl(['step' => $n]);
            $style = $n === $step ? 'font-weight:600;' : 'opacity:0.85;';
            echo '<a href="' . esc_url($url) . '" style="margin-right:14px;' . esc_attr($style) . '">' . esc_html($n . '. ' . $label) . '</a>';
        }
        echo '</div>';

        $this->renderNotice();

        if ($step === 1) {
            $this->renderStepWelcome($brandSafe);
        } elseif ($step === 2) {
            $this->renderStepPreset();
        } else {
            $this->renderStepNext($brandSafe);
        }

        echo '</div>';
    }

    private function renderStepWelcome(string $brandSafe): void
    {
        echo '<p>' . esc_html__('This wizard is optional. It helps you configure the plugin quickly and safely.', 'wp-seo-next') . '</p>';

        echo '<ol style="max-width:760px;">';
        echo '<li>' . esc_html__('Apply a preset (safe defaults for a typical site).', 'wp-seo-next') . '</li>';
        echo '<li>' . esc_html__('Migrate SEO overrides from Yoast / Rank Math / AIOSEO (optional).', 'wp-seo-next') . '</li>';
        echo '<li>' . esc_html__('Verify essentials: sitemap, social image, schema, IndexNow/GSC tools.', 'wp-seo-next') . '</li>';
        echo '</ol>';

        echo '<p>';
        echo '<a class="button button-primary" href="' . esc_url($this->pageUrl(['step' => 2])) . '">' . esc_html__('Start', 'wp-seo-next') . '</a> ';
        echo '<a class="button button-secondary" href="' . esc_url(admin_url('admin.php?page=wp-seo-next')) . '">' . esc_html(Branding::settingsLinkText($this->settings)) . '</a>';
        echo '</p>';

        echo '<hr />';
        echo '<p class="description">' . esc_html__('Tip: if you already have SEO data in another plugin, migrate it first. Then you can disable the old plugin to avoid duplicate tags.', 'wp-seo-next') . '</p>';
    }

    private function renderStepPreset(): void
    {
        $presets = $this->presets();

        echo '<p>' . esc_html__('Choose a preset. This will only change a small, curated set of settings (you can review and edit later).', 'wp-seo-next') . '</p>';

        echo '<form method="post" action="' . esc_url(admin_url('admin-post.php')) . '">';
        echo '<input type="hidden" name="action" value="wpsn_onboarding_apply_preset" />';
        wp_nonce_field('wpsn_onboarding_apply_preset');

        echo '<table class="widefat" style="max-width:920px;">';
        echo '<thead><tr><th>' . esc_html__('Preset', 'wp-seo-next') . '</th><th>' . esc_html__('What it changes', 'wp-seo-next') . '</th></tr></thead>';
        echo '<tbody>';

        foreach ($presets as $id => $p) {
            $label = isset($p['label']) ? (string) $p['label'] : $id;
            $desc = isset($p['desc']) ? (string) $p['desc'] : '';

            echo '<tr>';
            echo '<td style="width:260px;">';
            echo '<label>';
            echo '<input type="radio" name="preset" value="' . esc_attr($id) . '" ' . checked($id, 'default', false) . ' /> ';
            echo '<strong>' . esc_html($label) . '</strong>';
            echo '</label>';
            echo '</td>';
            echo '<td>' . esc_html($desc) . '</td>';
            echo '</tr>';
        }

        echo '</tbody></table>';

        submit_button(__('Apply preset', 'wp-seo-next'), 'primary', 'submit', false);
        echo ' <a class="button button-secondary" href="' . esc_url($this->pageUrl(['step' => 3])) . '">' . esc_html__('Skip', 'wp-seo-next') . '</a>';

        echo '</form>';

        echo '<p class="description" style="max-width:920px;">' . esc_html__('Presets never touch per-post overrides. They only adjust global settings/modules.', 'wp-seo-next') . '</p>';
    }

    private function renderStepNext(string $brandSafe): void
    {
        $runtime = new OnboardingChecklistRuntime($this->settings);
        $snapshot = $runtime->snapshot();
        $items = isset($snapshot['items']) && is_array($snapshot['items']) ? $snapshot['items'] : [];
        $summary = isset($snapshot['summary']) && is_array($snapshot['summary']) ? $snapshot['summary'] : [];

        echo '<p>' . esc_html__('Below is the current setup checklist. It reflects your actual plugin state and helps you finish the essentials before moving on.', 'wp-seo-next') . '</p>';

        $this->renderChecklistSummary($summary);
        $this->renderChecklistTables($items);

        echo '<h2 style="margin-top:22px;">' . esc_html__('Quick links', 'wp-seo-next') . '</h2>';
        echo '<p>' . esc_html__('Here are the most common next actions:', 'wp-seo-next') . '</p>';

        $links = [
            [
                'label' => __('Review plugin settings', 'wp-seo-next'),
                'url'   => admin_url('admin.php?page=wp-seo-next'),
                'desc'  => __('Templates, modules, social defaults, schema org/local, privacy policies.', 'wp-seo-next'),
            ],
            [
                'label' => __('Migrate from another SEO plugin', 'wp-seo-next'),
                'url'   => admin_url('tools.php?page=wpsn-import-export'),
                'desc'  => __('Yoast / Rank Math / AIOSEO migration + report.', 'wp-seo-next'),
            ],
            [
                'label' => __('Bulk SEO tables', 'wp-seo-next'),
                'url'   => admin_url('tools.php?page=wpsn-bulk-table'),
                'desc'  => __('Posts/Terms/Media bulk edits and Apply-All with progress.', 'wp-seo-next'),
            ],
            [
                'label' => __('Tasks Hub → Setup', 'wp-seo-next'),
                'url'   => admin_url('tools.php?page=wpsn-tasks&tab=setup'),
                'desc'  => __('Work through the same setup checklist inside the unified Tasks Hub.', 'wp-seo-next'),
            ],
            [
                'label' => __('IndexNow tools', 'wp-seo-next'),
                'url'   => admin_url('tools.php?page=wpsn-indexnow'),
                'desc'  => __('Submit URL, bulk sitemap submit, ping sitemaps after migrations.', 'wp-seo-next'),
            ],
        ];

        // Optional modules.
        if ($this->settings->moduleEnabled('search_console', false)) {
            $links[] = [
                'label' => __('Search Console Hub', 'wp-seo-next'),
                'url'   => admin_url('tools.php?page=wpsn-search-console'),
                'desc'  => __('Fetch queries/pages, opportunities, internal linking suggestions.', 'wp-seo-next'),
            ];
        }

        echo '<ul style="max-width:920px;">';
        foreach ($links as $l) {
            echo '<li style="margin:6px 0;">';
            echo '<a href="' . esc_url($l['url']) . '"><strong>' . esc_html($l['label']) . '</strong></a>';
            if (!empty($l['desc'])) {
                echo '<div class="description">' . esc_html($l['desc']) . '</div>';
            }
            echo '</li>';
        }
        echo '</ul>';

        echo '<hr />';

        echo '<form method="post" action="' . esc_url(admin_url('admin-post.php')) . '">';
        echo '<input type="hidden" name="action" value="wpsn_onboarding_complete" />';
        wp_nonce_field('wpsn_onboarding_complete');
        submit_button(__('Mark wizard as completed', 'wp-seo-next'), 'primary', 'submit', false);
        echo '</form>';

        echo '<p class="description">' . esc_html__('You can re-open this wizard any time from Tools → SEO Setup Wizard.', 'wp-seo-next') . '</p>';
    }

    /**
     * @param array<string,int> $summary
     */
    private function renderChecklistSummary(array $summary): void
    {
        $essDone = (int) ($summary['essentials_done'] ?? 0);
        $essTotal = (int) ($summary['essentials_total'] ?? 0);
        $recDone = (int) ($summary['recommended_done'] ?? 0);
        $recTotal = (int) ($summary['recommended_total'] ?? 0);
        $intDone = (int) ($summary['integrations_done'] ?? 0);
        $intTotal = (int) ($summary['integrations_total'] ?? 0);

        echo '<div class="notice notice-info inline"><p><strong>' . esc_html__('Checklist progress:', 'wp-seo-next') . '</strong> ';
        echo esc_html(sprintf(__('%1$d/%2$d essentials done', 'wp-seo-next'), $essDone, $essTotal));
        if ($recTotal > 0) {
            echo ' · ' . esc_html(sprintf(__('%1$d/%2$d recommended items done', 'wp-seo-next'), $recDone, $recTotal));
        }
        if ($intTotal > 0) {
            echo ' · ' . esc_html(sprintf(__('%1$d/%2$d optional integrations done', 'wp-seo-next'), $intDone, $intTotal));
        }
        echo '</p></div>';
    }

    /**
     * @param array<int,array<string,mixed>> $items
     */
    private function renderChecklistTables(array $items): void
    {
        $provider = $this->setupTasksProvider();

        echo '<style>'
            . '.wpsn-setup-pill{display:inline-block;padding:2px 8px;border-radius:999px;font-size:11px;font-weight:600;line-height:1.7;}'
            . '.wpsn-setup-pill.done{background:#e7f6ea;color:#0a5c2f;}'
            . '.wpsn-setup-pill.todo{background:#fff4d6;color:#8a5b00;}'
            . '.wpsn-setup-pill.info{background:#eef2f7;color:#35516b;}'
            . '.wpsn-setup-pill.state{background:#eef2ff;color:#3858a6;}'
            . '.wpsn-setup-pill.state-hidden{background:#f1f1f1;color:#50575e;}'
            . '.wpsn-setup-checklist td{vertical-align:top;}'
            . '</style>';

        $sections = [
            'essentials' => __('Essentials', 'wp-seo-next'),
            'recommended' => __('Recommended', 'wp-seo-next'),
            'integrations' => __('Optional integrations', 'wp-seo-next'),
        ];

        foreach ($sections as $section => $label) {
            $rows = array_values(array_filter($items, static function (array $item) use ($section): bool {
                return isset($item['section']) && (string) $item['section'] === $section;
            }));

            if (empty($rows)) {
                continue;
            }

            echo '<h2 style="margin-top:18px;">' . esc_html($label) . '</h2>';
            echo '<table class="widefat striped wpsn-setup-checklist" style="max-width:980px;">';
            echo '<thead><tr>';
            echo '<th style="width:110px;">' . esc_html__('Status', 'wp-seo-next') . '</th>';
            echo '<th style="width:260px;">' . esc_html__('Task', 'wp-seo-next') . '</th>';
            echo '<th>' . esc_html__('Details', 'wp-seo-next') . '</th>';
            echo '<th style="width:180px;">' . esc_html__('Action', 'wp-seo-next') . '</th>';
            echo '</tr></thead><tbody>';

            foreach ($rows as $row) {
                $status = isset($row['status']) ? (string) $row['status'] : 'info';
                $title = isset($row['title']) ? (string) $row['title'] : '';
                $details = isset($row['summary']) ? (string) $row['summary'] : '';
                $taskState = isset($row['task_state']) ? sanitize_key((string) $row['task_state']) : 'open';
                $actions = $provider->actionsForItem($row);

                echo '<tr>';
                echo '<td>' . $this->checklistPillHtml($status) . '</td>';
                echo '<td><strong>' . esc_html($title) . '</strong>';
                if ($status === 'todo' && in_array($taskState, ['done', 'hidden'], true)) {
                    echo '<div style="margin-top:6px;">' . $this->taskStatePillHtml($taskState) . '</div>';
                }
                echo '</td>';
                echo '<td>' . esc_html($details);
                if ($status === 'todo' && $taskState === 'done') {
                    echo '<div class="description" style="margin-top:6px;">' . esc_html__('This reminder was marked as done and is hidden from open task lists until you reopen it or the underlying setup state changes.', 'wp-seo-next') . '</div>';
                } elseif ($status === 'todo' && $taskState === 'hidden') {
                    echo '<div class="description" style="margin-top:6px;">' . esc_html__('This reminder is hidden from open task lists until you reopen it or the underlying setup state changes.', 'wp-seo-next') . '</div>';
                }
                echo '</td>';
                echo '<td>';
                if (!empty($actions)) {
                    foreach ($actions as $action) {
                        if (!is_array($action)) {
                            continue;
                        }
                        $label = isset($action['label']) ? (string) $action['label'] : '';
                        $url = isset($action['url']) ? (string) $action['url'] : '';
                        if ($label === '' || $url === '') {
                            continue;
                        }
                        echo '<a class="button button-secondary button-small" style="margin:0 6px 6px 0;" href="' . esc_url($url) . '">' . esc_html($label) . '</a>';
                    }
                } else {
                    echo '&ndash;';
                }
                echo '</td>';
                echo '</tr>';
            }

            echo '</tbody></table>';
        }
    }

    private function checklistPillHtml(string $status): string
    {
        $status = sanitize_key($status);
        $label = __('Info', 'wp-seo-next');
        if ($status === 'done') {
            $label = __('Done', 'wp-seo-next');
        } elseif ($status === 'todo') {
            $label = __('To do', 'wp-seo-next');
        }
        if (!in_array($status, ['done', 'todo', 'info'], true)) {
            $status = 'info';
        }

        return '<span class="wpsn-setup-pill ' . esc_attr($status) . '">' . esc_html($label) . '</span>';
    }

    private function checklistActionUrl(string $action): string
    {
        switch ($action) {
            case 'settings':
                return admin_url('admin.php?page=wp-seo-next');

            case 'search_console':
                return admin_url('tools.php?page=wpsn-search-console');

            case 'indexnow':
                return admin_url('tools.php?page=wpsn-indexnow');
        }

        return '';
    }

    private function taskStatePillHtml(string $taskState): string
    {
        $taskState = sanitize_key($taskState);
        if ($taskState === 'done') {
            return '<span class="wpsn-setup-pill state">' . esc_html__('Marked done', 'wp-seo-next') . '</span>';
        }

        if ($taskState === 'hidden') {
            return '<span class="wpsn-setup-pill state state-hidden">' . esc_html__('Hidden', 'wp-seo-next') . '</span>';
        }

        return '';
    }

    private function renderNotice(): void
    {
        if (empty($_GET['wpsn_notice'])) {
            return;
        }

        $notice = sanitize_key((string) wp_unslash($_GET['wpsn_notice']));
        $map = [
            'preset_applied' => ['type' => 'success', 'text' => __('Preset applied.', 'wp-seo-next')],
            'wizard_done' => ['type' => 'success', 'text' => __('Wizard completed.', 'wp-seo-next')],
            'setup_task_done' => ['type' => 'success', 'text' => __('Setup task marked as done.', 'wp-seo-next')],
            'setup_task_hidden' => ['type' => 'warning', 'text' => __('Setup task hidden from the open list.', 'wp-seo-next')],
            'setup_task_reopened' => ['type' => 'info', 'text' => __('Setup task reopened.', 'wp-seo-next')],
        ];

        if (!isset($map[$notice])) {
            return;
        }

        $type = isset($map[$notice]['type']) ? (string) $map[$notice]['type'] : 'success';
        $text = isset($map[$notice]['text']) ? (string) $map[$notice]['text'] : '';
        $class = 'notice-success';
        if ($type === 'warning') {
            $class = 'notice-warning';
        } elseif ($type === 'info') {
            $class = 'notice-info';
        }

        echo '<div class="notice ' . esc_attr($class) . ' is-dismissible"><p>' . esc_html($text) . '</p></div>';
    }

    private function setupTasksProvider(): SetupTasksProvider
    {
        return new SetupTasksProvider($this->settings);
    }

    public function handleSetupTaskState(): void
    {
        if (!current_user_can(Capabilities::CAP_TOOLS)) {
            wp_die(esc_html__('You do not have permission to do this action.', 'wp-seo-next'));
        }

        $task = isset($_GET['task']) ? sanitize_key((string) wp_unslash($_GET['task'])) : '';
        $state = isset($_GET['state']) ? sanitize_key((string) wp_unslash($_GET['state'])) : '';

        if ($task === '' || !in_array($state, ['done', 'hidden', 'open'], true)) {
            wp_die(esc_html__('Invalid setup task action.', 'wp-seo-next'));
        }

        check_admin_referer('wpsn_onboarding_setup_task_state_' . $task . '_' . $state);

        $runtime = new OnboardingChecklistRuntime($this->settings);
        $snapshot = $runtime->snapshot();
        $items = isset($snapshot['items']) && is_array($snapshot['items']) ? $snapshot['items'] : [];

        $repo = new OnboardingChecklistStateRepository();
        $notice = 'setup_task_reopened';

        if ($state === 'open') {
            $repo->clearState($task);
        } elseif ($state === 'done') {
            $repo->setState($task, 'done', $items);
            $notice = 'setup_task_done';
        } else {
            $repo->setState($task, 'hidden', $items);
            $notice = 'setup_task_hidden';
        }

        $target = $this->safeReturnUrl($this->currentRefererUrl(), $this->pageUrl(['step' => 3]));
        $target = add_query_arg('wpsn_notice', $notice, $target);

        wp_safe_redirect($target);
        exit;
    }

    private function currentRefererUrl(): string
    {
        if (function_exists('wp_get_referer')) {
            $ref = (string) wp_get_referer();
            if ($ref !== '') {
                return $ref;
            }
        }

        if (!empty($_SERVER['HTTP_REFERER'])) {
            return (string) $_SERVER['HTTP_REFERER'];
        }

        return '';
    }

    private function safeReturnUrl(string $url, string $fallback): string
    {
        $url = trim($url);
        if ($url === '') {
            return $fallback;
        }

        $adminBase = rtrim((string) admin_url(), '/');
        if (strpos($url, $adminBase) === 0) {
            return $url;
        }

        return $fallback;
    }

    public function handleApplyPreset(): void
    {
        if (!current_user_can(Capabilities::CAP_TOOLS)) {
            wp_die(esc_html__('You do not have permission to do this action.', 'wp-seo-next'));
        }

        check_admin_referer('wpsn_onboarding_apply_preset');

        $preset = isset($_POST['preset']) ? sanitize_key((string) wp_unslash($_POST['preset'])) : 'default';
        $presets = $this->presets();
        if (!isset($presets[$preset])) {
            $preset = 'default';
        }

        $changes = isset($presets[$preset]['changes']) && is_array($presets[$preset]['changes']) ? $presets[$preset]['changes'] : [];

        // Multisite policies: don't mutate enforced groups in DB.
        if ($this->settings->networkPolicyIsEnforced('modules')) {
            unset($changes['modules']);
        }
        if ($this->settings->networkPolicyIsEnforced('white_label')) {
            unset($changes['white_label']);
        }
        if ($this->settings->networkPolicyIsEnforced('integrations')) {
            unset($changes['integrations']);
        }

        /** @var SettingsRepository $repo */
        $repo = $this->container->get('settings_repo');

        $current = $repo->getAll();
        $merged = array_replace_recursive($current, $changes);

        try {
            $repo->update($merged);
        } catch (\Throwable $e) {
            $this->logger->error('Onboarding preset apply failed: ' . $e->getMessage());
        }

        // Ensure runtime cache sees the update.
        $this->settings->flush();

        wp_safe_redirect($this->pageUrl([
            'step' => 3,
            'wpsn_notice' => 'preset_applied',
        ]));
        exit;
    }

    public function handleComplete(): void
    {
        if (!current_user_can(Capabilities::CAP_TOOLS)) {
            wp_die(esc_html__('You do not have permission to do this action.', 'wp-seo-next'));
        }

        check_admin_referer('wpsn_onboarding_complete');

        update_option(self::OPT_COMPLETED, 1);
        delete_option(self::OPT_DISMISSED);

        wp_safe_redirect($this->pageUrl([
            'step' => 1,
            'wpsn_notice' => 'wizard_done',
        ]));
        exit;
    }

    public function handleDismiss(): void
    {
        if (!current_user_can(Capabilities::CAP_TOOLS)) {
            wp_die(esc_html__('You do not have permission to do this action.', 'wp-seo-next'));
        }

        check_admin_referer('wpsn_onboarding_dismiss');

        update_option(self::OPT_DISMISSED, 1);

        wp_safe_redirect(admin_url());
        exit;
    }

    /**
     * Presets are intentionally conservative.
     *
     * @return array<string,array{label:string,desc:string,changes:array<string,mixed>}>
     */
    private function presets(): array
    {
        return [
            'default' => [
                'label' => __('Default', 'wp-seo-next'),
                'desc'  => __('No changes. Use your current settings.', 'wp-seo-next'),
                'changes' => [],
            ],
            'sitemap_only' => [
                'label' => __('Sitemap-only preset', 'wp-seo-next'),
                'desc'  => __('Enable XML sitemaps + virtual robots.txt only (disable other SEO output modules).', 'wp-seo-next'),
                'changes' => [
                    'modules' => [
                        'sitemap' => true,
                        'robots' => true,

                        // Disable typical output / heavy modules.
                        'meta_tags' => false,
                        'schema' => false,
                        'social' => false,
                        'breadcrumbs' => false,
                        'local_seo' => false,
                        'woocommerce' => false,

                        'search_console' => false,
                        'site_kit' => false,

                        'audit' => false,
                        'issues' => false,
                        'tasks_hub' => false,
                        'site_crawl' => false,
                        'content_clusters' => false,
                        'crawl_budget' => false,
                        'drift_monitor' => false,
                        'indexation_risk' => false,

                        'redirects' => false,
                        'serp_gap' => false,
                        'media' => false,

                        'ai' => false,
                        'ai_readiness' => false,
                        'autopilot' => false,

                        'bulk' => false,
                        'bulk_table' => false,
                        'editor' => false,
                        'custom_fields' => false,
                        'author_seo' => false,
                        'schema_validator' => false,
                        'saas_dashboard' => false,
                        'saas_sync' => false,
                        'licensing' => false,
                    ],
                    'ui' => [
                        'mode' => 'simple',
                    ],
                ],
            ],

            'privacy_local_only' => [
                'label' => __('Privacy: Local-only mode', 'wp-seo-next'),
                'desc'  => __('Disables external services (OpenAI, scheduled GSC sync, IndexNow pings) via runtime policy. Great for regulated environments.', 'wp-seo-next'),
                'changes' => [
                    'privacy' => [
                        'local_only' => true,
                    ],
                ],
            ],
            'agency' => [
                'label' => __('Agency preset', 'wp-seo-next'),
                'desc'  => __('Enables Automation SDK + Config Sync + Bulk tables.', 'wp-seo-next'),
                'changes' => [
                    'modules' => [
                        'automation' => true,
                        'config_sync' => true,
                        'bulk_table' => true,
                    ],
                ],
            ],
            'local_business' => [
                'label' => __('Local business', 'wp-seo-next'),
                'desc'  => __('Enables Locations (Local SEO) module and turns on home LocalBusiness schema.', 'wp-seo-next'),
                'changes' => [
                    'modules' => [
                        'local_seo' => true,
                    ],
                    'local' => [
                        'schema' => [
                            'enabled' => true,
                            'show_on_home' => true,
                        ],
                    ],
                ],
            ],
            'publisher' => [
                'label' => __('Publisher / Content site', 'wp-seo-next'),
                'desc'  => __('Enables Search Console Hub (for opportunities + internal linking).', 'wp-seo-next'),
                'changes' => [
                    'modules' => [
                        'search_console' => true,
                    ],
                ],
            ],
        ];
    }

    /**
     * @param array<string, mixed> $args
     */
    private function pageUrl(array $args = []): string
    {
        $base = admin_url('tools.php?page=' . self::PAGE_SLUG);
        if (empty($args)) {
            return $base;
        }
        return add_query_arg($args, $base);
    }
}
