<script setup>
/** @deprecated Внимание: старая версия (V1/V2). Используйте V3. */
import SegmentsChannelMatrixHeatmap from '@/components/marketing/SegmentsChannelMatrixHeatmap.vue';
import MarketingService from '@/service/MarketingService';
import MarketingAnalysisPptDashboard from '@/views/pages/MarketingAnalysis.vue';
import { marked } from 'marked';
import markedKatex from 'marked-katex-extension';
import Button from 'primevue/button';
import Chart from 'primevue/chart';
import Checkbox from 'primevue/checkbox';
import InputText from 'primevue/inputtext';
import MultiSelect from 'primevue/multiselect';
import ProgressSpinner from 'primevue/progressspinner';
import RadioButton from 'primevue/radiobutton';
import Tag from 'primevue/tag';
import Textarea from 'primevue/textarea';
import Toast from 'primevue/toast';
import { useToast } from 'primevue/usetoast';
import { computed, onBeforeUnmount, onMounted, ref } from 'vue';
import { useRoute, useRouter } from 'vue-router';

const toast = useToast();
const router = useRouter();
const route = useRoute();

let isKatexMarkedConfigured = false;

// Constants
const VALID_REGIONS = [
    'Алматы',
    'Астана',
    'Шымкент',
    'Караганда',
    'Актобе',
    'Тараз',
    'Павлодар',
    'Усть-Каменогорск',
    'Семей',
    'Костанай',
    'Кызылорда',
    'Уральск',
    'Петропавловск',
    'Атырау',
    'Актау',
    'Туркестан',
    'Кокшетау',
    'Талдыкорган',
    'Экибастуз',
    'Рудный'
];

const VALID_GENDERS = ['Женщины', 'Мужчины'];
const VALID_AGE_RANGES = ['20-40', '25-45', '18-25', '40-60', '60+'];
const VALID_AUDIENCE_TYPES = ['Семьи', 'Молодёжь', 'Все подряд'];
const VALID_ANALYSIS_TYPES = ['РЫНОК', 'КОНКУРЕНТЫ', 'ЦА', 'КАНАЛЫ', 'SWOT'];

const DETAIL_LEVELS = ['КРАТКО', 'СТАНДАРТНО', 'ПОДРОБНО'];

// Form data
const formData = ref({
    businessNiche: '',
    product: '',
    targetAudience: {
        genders: [],
        ageRanges: [],
        types: []
    },
    region: [],
    goal: '',
    detailLevel: 'СТАНДАРТНО',
    strongSide: '',
    weakSide: '',
    marketingBudget: null,
    analysisType: []
});

const analysisTypeOptions = [
    { label: 'РЫНОК - Анализ внешней среды', value: 'РЫНОК' },
    { label: 'КОНКУРЕНТЫ - Анализ конкурентов', value: 'КОНКУРЕНТЫ' },
    { label: 'ЦА - Анализ целевой аудитории', value: 'ЦА' },
    { label: 'КАНАЛЫ - Анализ рекламных каналов', value: 'КАНАЛЫ' },
    { label: 'SWOT - SWOT-анализ', value: 'SWOT' }
];

const submitting = ref(false);
const errors = ref({});

// Analysis state
const isAnalysisOpen = ref(false);
const analysisId = ref(null);
const status = ref(null);
const report = ref(null);
const currentAnalysisType = ref(null);
const estimatedCompletionTime = ref(null);
const pollingInterval = ref(null);
const pollingAttempts = ref(0);
const maxPollingAttempts = 60; // 10 minutes with 10 second intervals
const pollingIntervalMs = 10000; // 10 seconds
const downloadingPdf = ref(false);

// v2 dashboard state (loaded via start?generateV2=true + GET /analysis/v2/{id})
const v2AnalysisId = ref(null);
const v2Report = ref(null); // raw v2 payload from GET /api/marketing/analysis/v2/{id}
const v2Loading = ref(false);
const v2Error = ref(null);

const isV2ReportPayload = (payload) => {
    if (!payload || typeof payload !== 'object') return false;
    if (payload.report_title || payload.reportTitle) return true;
    if (payload.sections && typeof payload.sections === 'object') return true;
    return false;
};

const applyV2Report = (payload) => {
    v2Report.value = payload;
    v2Loading.value = false;
    v2Error.value = null;
};

const v2ReportNormalized = computed(() => {
    const root = v2Report.value;
    if (!root) return null;

    const title = root.reportTitle || root.report_title || '';
    const s = root.sections || {};
    const pick = (camel, snake) => s[camel] || s[snake] || null;

    return {
        report_title: title,
        sections: {
            market_overview: pick('marketOverview', 'market_overview'),
            target_audience: pick('targetAudience', 'target_audience'),
            competitive_environment: pick('competitiveEnvironment', 'competitive_environment'),
            demand_and_behavior: pick('demandAndBehavior', 'demand_and_behavior'),
            customer_journey: pick('customerJourney', 'customer_journey'),
            acquisition_channels: pick('acquisitionChannels', 'acquisition_channels'),
            marketing_economics: pick('marketingEconomics', 'marketing_economics'),
            bottlenecks: pick('bottlenecks', 'bottlenecks'),
            recommendations: pick('recommendations', 'recommendations')
        },
        sources: root.sources || []
    };
});

const drawBarValues = (chart) => {
    const ctx = chart.ctx;
    ctx.save();
    ctx.font = 'bold 14px "Inter", sans-serif'; // Шрифт покрупнее, как на фото
    ctx.textAlign = 'center';
    ctx.textBaseline = 'middle';

    chart.data.datasets.forEach((dataset, i) => {
        const meta = chart.getDatasetMeta(i);
        if (!meta.hidden) {
            meta.data.forEach((bar, index) => {
                const value = dataset.data[index];
                if (value !== null && value !== undefined && value != 0) {
                    let label = value.toLocaleString();
                    // Если это проценты, добавляем знак %
                    if (dataset.unit === '%' || (typeof dataset.data[index] === 'string' && String(dataset.data[index]).includes('%'))) {
                        label = String(value).replace('%', '') + '%';
                    }

                    const isHorizontal = meta.indexAxis === 'y';

                    if (isHorizontal) {
                        // Горизонтальный: цифра справа темная
                        ctx.fillStyle = document.documentElement.classList.contains('dark') ? '#ffffff' : '#1f2937';
                        ctx.textAlign = 'left';
                        ctx.fillText(label, bar.x + 8, bar.y);
                    } else {
                        // === ВЕРТИКАЛЬНЫЙ (КАК НА ФОТО) ===
                        const barHeight = Math.abs(bar.base - bar.y);

                        // Если столбец достаточно высокий (>25px), рисуем цифру ВНУТРИ белым цветом
                        if (barHeight > 25) {
                            ctx.fillStyle = '#ffffff';
                            // bar.y - это верхушка столбца. Добавляем 15px, чтобы спустить цифру чуть ниже верха
                            ctx.fillText(label, bar.x, bar.y + 15);
                        } else {
                            // Если столбец мелкий, рисуем цифру СВЕРХУ темным цветом
                            ctx.fillStyle = document.documentElement.classList.contains('dark') ? '#ffffff' : '#1f2937';
                            ctx.fillText(label, bar.x, bar.y - 12);
                        }
                    }
                }
            });
        }
    });
    ctx.restore();
};

// Опции: Дизайн "Как на фото" (С цифрами внутри)
const photoStyleBarOptions = {
    responsive: true,
    maintainAspectRatio: false,
    layout: { padding: { top: 25 } }, // Отступ сверху для тултипов
    animation: {
        duration: 500,
        onComplete: (animation) => drawBarValues(animation.chart)
    },
    plugins: {
        legend: { display: false }, // Легенда не нужна
        tooltip: {
            enabled: true,
            callbacks: { label: (ctx) => `${ctx.formattedValue}%` }
        }
    },
    scales: {
        y: {
            display: true, // Ось Y оставляем (как на фото 0, 10, 20...), но можно поставить false, если надо скрыть
            beginAtZero: true,
            grid: { display: true, drawBorder: false, color: 'rgba(0,0,0,0.05)' },
            ticks: { font: { size: 10 } }
        },
        x: {
            grid: { display: false }, // Вертикальные линии убираем
            ticks: {
                font: { size: 12, weight: '600' },
                color: '#64748b'
            }
        }
    }
};

// Опции: Горизонтальные бары
const horizontalBarChartOptions = {
    indexAxis: 'y',
    responsive: true,
    maintainAspectRatio: false,
    layout: { padding: { right: 40 } },
    animation: {
        duration: 500,
        onComplete: (animation) => drawBarValues(animation.chart)
    },
    plugins: { legend: { display: false } },
    scales: {
        x: { display: false, beginAtZero: true },
        y: {
            grid: { display: false },
            ticks: { font: { size: 12, weight: '500' }, crossAlign: 'far' }
        }
    }
};

// Опции: Круговая диаграмма
const pieChartOptions = {
    responsive: true,
    maintainAspectRatio: false,
    plugins: {
        legend: { display: true, position: 'bottom', align: 'center' },
        tooltip: {
            callbacks: { label: (context) => context.label + ': ' + context.parsed + '%' }
        }
    }
};

// Опции: Линейный график (Сезонность)
const seasonalityChartOptions = {
    responsive: true,
    maintainAspectRatio: false,
    plugins: { legend: { display: true, position: 'bottom' } },
    scales: { y: { beginAtZero: true } }
};

// Опции: Воронка
const conversionFunnelChartOptions = {
    responsive: true,
    maintainAspectRatio: false,
    plugins: { legend: { display: true, position: 'bottom' } },
    scales: {
        y: { beginAtZero: true, title: { display: true, text: 'Пользователи' } }
    }
};

// Опции: Потенциал каналов
const channelsPotentialChartOptions = {
    responsive: true,
    maintainAspectRatio: false,
    plugins: { legend: { display: false } },
    scales: { y: { beginAtZero: true, max: 100 } }
};

// Хелпер для цветов
const MARKETING_COLORS = ['#4F46E5', '#10B981', '#F59E0B', '#EF4444', '#8B5CF6', '#EC4899'];
const getMarketingColors = (count, offset = 0) => {
    const safeCount = Math.max(0, Number(count) || 0);
    if (safeCount === 0) return [];
    return Array.from({ length: safeCount }, (_, i) => MARKETING_COLORS[(i + offset) % MARKETING_COLORS.length]);
};

const parsePercentageData = (obj) => {
    if (!obj || typeof obj !== 'object') return { labels: [], values: [] };
    const labels = Object.keys(obj).map((k) => k.replace(/_/g, ' '));
    const values = Object.values(obj).map((v) => {
        if (typeof v === 'string') return parseFloat(v.replace('%', ''));
        return v;
    });
    return { labels, values };
};

const refreshV2 = async () => {
    if (!v2AnalysisId.value) return;
    v2Loading.value = true;
    v2Error.value = null;
    try {
        const data = await MarketingService.getAnalysisV2ById(v2AnalysisId.value);
        v2Report.value = data;
    } catch (e) {
        v2Error.value = e?.message || 'Не удалось загрузить v2 отчёт';
        toast.add({
            severity: 'warn',
            summary: 'v2 недоступен',
            detail: v2Error.value,
            life: 4000
        });
    } finally {
        v2Loading.value = false;
    }
};

// Validation
const validateForm = () => {
    errors.value = {};

    // BusinessNiche validation
    if (!formData.value.businessNiche || formData.value.businessNiche.trim().length < 3) {
        errors.value.businessNiche = 'Ниша бизнеса должна содержать минимум 3 символа';
    } else if (formData.value.businessNiche.trim().length > 200) {
        errors.value.businessNiche = 'Ниша бизнеса не должна превышать 200 символов';
    }

    // Product validation
    if (!formData.value.product || formData.value.product.trim().length < 3) {
        errors.value.product = 'Название продукта должно содержать минимум 3 символа';
    } else if (formData.value.product.trim().length > 200) {
        errors.value.product = 'Название продукта не должно превышать 200 символов';
    }

    // TargetAudience validation
    const hasGenders = formData.value.targetAudience.genders && formData.value.targetAudience.genders.length > 0;
    const hasAgeRanges = formData.value.targetAudience.ageRanges && formData.value.targetAudience.ageRanges.length > 0;
    const hasTypes = formData.value.targetAudience.types && formData.value.targetAudience.types.length > 0;

    if (!hasGenders && !hasAgeRanges && !hasTypes) {
        errors.value.targetAudience = 'Выберите хотя бы одну опцию для целевой аудитории (гендер, возраст или тип)';
    } else {
        // Валидация значений
        if (formData.value.targetAudience.genders) {
            const invalidGenders = formData.value.targetAudience.genders.filter((g) => !VALID_GENDERS.includes(g));
            if (invalidGenders.length > 0) {
                errors.value.targetAudience = `Недопустимые значения гендера: ${invalidGenders.join(', ')}`;
            }
        }
        if (formData.value.targetAudience.ageRanges) {
            const invalidAges = formData.value.targetAudience.ageRanges.filter((a) => !VALID_AGE_RANGES.includes(a));
            if (invalidAges.length > 0) {
                errors.value.targetAudience = `Недопустимые значения возраста: ${invalidAges.join(', ')}`;
            }
        }
        if (formData.value.targetAudience.types) {
            const invalidTypes = formData.value.targetAudience.types.filter((t) => !VALID_AUDIENCE_TYPES.includes(t));
            if (invalidTypes.length > 0) {
                errors.value.targetAudience = `Недопустимые значения типа: ${invalidTypes.join(', ')}`;
            }
        }
    }

    // Region validation
    if (!formData.value.region || formData.value.region.length === 0) {
        errors.value.region = 'Выберите хотя бы один регион';
    } else {
        const invalidRegions = formData.value.region.filter((r) => !VALID_REGIONS.includes(r));
        if (invalidRegions.length > 0) {
            errors.value.region = `Недопустимые регионы: ${invalidRegions.join(', ')}`;
        }
    }

    // Goal validation
    if (!formData.value.goal || formData.value.goal.trim().length < 10) {
        errors.value.goal = 'Цель должна содержать минимум 10 символов';
    } else if (formData.value.goal.trim().length > 500) {
        errors.value.goal = 'Цель не должна превышать 500 символов';
    }

    // DetailLevel validation
    if (!formData.value.detailLevel || !DETAIL_LEVELS.includes(formData.value.detailLevel)) {
        errors.value.detailLevel = 'Пожалуйста, выберите уровень детализации';
    }

    // StrongSide validation (optional)
    if (formData.value.strongSide && formData.value.strongSide.trim().length > 500) {
        errors.value.strongSide = 'Сильная сторона не должна превышать 500 символов';
    }

    // WeakSide validation (optional)
    if (formData.value.weakSide && formData.value.weakSide.trim().length > 500) {
        errors.value.weakSide = 'Слабая сторона не должна превышать 500 символов';
    }

    // AnalysisType validation
    if (!formData.value.analysisType || formData.value.analysisType.length === 0) {
        errors.value.analysisType = 'Выберите хотя бы один тип анализа';
    } else {
        const invalidTypes = formData.value.analysisType.filter((t) => !VALID_ANALYSIS_TYPES.includes(t));
        if (invalidTypes.length > 0) {
            errors.value.analysisType = `Недопустимые типы анализа: ${invalidTypes.join(', ')}`;
        }
    }

    return Object.keys(errors.value).length === 0;
};

// Start polling for analysis status
const startPolling = (id) => {
    pollingAttempts.value = 0;
    pollingInterval.value = setInterval(async () => {
        pollingAttempts.value++;

        if (pollingAttempts.value > maxPollingAttempts) {
            stopPolling();
            toast.add({
                severity: 'warn',
                summary: 'Таймаут',
                detail: 'Превышено время ожидания анализа. Попробуйте проверить результат позже.',
                life: 5000
            });
            return;
        }

        try {
            const result = await MarketingService.getAnalysisResult(id);
            if (!result) return;
            if (isV2ReportPayload(result)) {
                stopPolling();
                applyV2Report(result);
                status.value = 'completed';
                return;
            }
            status.value = result.status;

            if (result.status === 'completed' && result.report) {
                stopPolling();
                report.value = result.report;
                // Сохраняем тип анализа из результата, если он есть
                if (result.analysisType) {
                    currentAnalysisType.value = result.analysisType;
                }
                toast.add({
                    severity: 'success',
                    summary: 'Анализ завершен',
                    detail: 'Маркетинговый анализ успешно завершен',
                    life: 3000
                });
            } else if (result.status === 'failed') {
                stopPolling();
                toast.add({
                    severity: 'error',
                    summary: 'Ошибка анализа',
                    detail: 'Анализ завершился с ошибкой',
                    life: 5000
                });
            }
        } catch (error) {
            console.error('Ошибка при проверке статуса анализа:', error);
            // Continue polling on error, but log it
        }
    }, pollingIntervalMs);
};

// Stop polling
const stopPolling = () => {
    if (pollingInterval.value) {
        clearInterval(pollingInterval.value);
        pollingInterval.value = null;
    }
};

// Handle form submit
const handleSubmit = async () => {
    if (!validateForm()) {
        toast.add({
            severity: 'error',
            summary: 'Ошибка валидации',
            detail: 'Пожалуйста, исправьте ошибки в форме',
            life: 3000
        });
        return;
    }

    submitting.value = true;
    v2Report.value = null;
    v2AnalysisId.value = null;
    v2Error.value = null;

    try {
        // Формируем объект targetAudience (удаляем пустые массивы)
        const targetAudience = {};
        if (formData.value.targetAudience.genders && formData.value.targetAudience.genders.length > 0) {
            targetAudience.genders = formData.value.targetAudience.genders;
        }
        if (formData.value.targetAudience.ageRanges && formData.value.targetAudience.ageRanges.length > 0) {
            targetAudience.ageRanges = formData.value.targetAudience.ageRanges;
        }
        if (formData.value.targetAudience.types && formData.value.targetAudience.types.length > 0) {
            targetAudience.types = formData.value.targetAudience.types;
        }

        const requestData = {
            businessNiche: formData.value.businessNiche.trim(),
            product: formData.value.product.trim(),
            targetAudience: targetAudience,
            region: formData.value.region,
            goal: formData.value.goal.trim(),
            detailLevel: formData.value.detailLevel,
            analysisType: formData.value.analysisType
        };

        // Добавляем опциональные поля только если они заполнены
        if (formData.value.strongSide && formData.value.strongSide.trim()) {
            requestData.strongSide = formData.value.strongSide.trim();
        }
        if (formData.value.weakSide && formData.value.weakSide.trim()) {
            requestData.weakSide = formData.value.weakSide.trim();
        }
        if (formData.value.marketingBudget !== null && formData.value.marketingBudget !== undefined) {
            requestData.marketingExpenses = formData.value.marketingBudget;
        }

        const result = await MarketingService.startAnalysis(requestData, { generateV2: true });

        // Обработка ответа: может быть массив или один объект
        if (Array.isArray(result)) {
            // Множественные анализы
            const firstAnalysis = result[0];
            analysisId.value = firstAnalysis.analysisId;
            status.value = firstAnalysis.status;
            estimatedCompletionTime.value = firstAnalysis.estimatedCompletion;
            v2AnalysisId.value = firstAnalysis.v2AnalysisId || null;
            router.replace({ query: { ...route.query, analysisId: analysisId.value, v2AnalysisId: v2AnalysisId.value || undefined } });

            // Сохраняем типы анализов
            currentAnalysisType.value = formData.value.analysisType.length === 1 ? formData.value.analysisType[0] : null;

            toast.add({
                severity: 'success',
                summary: 'Анализы запущены',
                detail: `Создано ${result.length} анализов. Они будут обработаны параллельно.`,
                life: 5000
            });

            // Запускаем polling для первого анализа (можно расширить для всех)
            startPolling(firstAnalysis.analysisId);

            // v2: загрузка сохраненного отчёта (если есть)
            if (v2AnalysisId.value) {
                await refreshV2();
            }
        } else {
            // Один анализ
            analysisId.value = result.analysisId;
            status.value = result.status;
            currentAnalysisType.value = formData.value.analysisType.length === 1 ? formData.value.analysisType[0] : null;
            estimatedCompletionTime.value = result.estimatedCompletion;
            v2AnalysisId.value = result.v2AnalysisId || null;
            router.replace({ query: { ...route.query, analysisId: analysisId.value, v2AnalysisId: v2AnalysisId.value || undefined } });

            toast.add({
                severity: 'success',
                summary: 'Анализ запущен',
                detail: result.message || 'Анализ успешно запущен. Результаты будут готовы в течение 5-10 минут.',
                life: 5000
            });

            // Start polling
            startPolling(result.analysisId);

            // v2: загрузка сохраненного отчёта (если есть)
            if (v2AnalysisId.value) {
                await refreshV2();
            }
        }
    } catch (error) {
        console.error('Ошибка при запуске анализа:', error);
        toast.add({
            severity: 'error',
            summary: 'Ошибка',
            detail: error.message || 'Не удалось запустить анализ. Пожалуйста, попробуйте снова.',
            life: 5000
        });
    } finally {
        submitting.value = false;
    }
};

// Handle PDF download
const handleDownloadPdf = async () => {
    if (!analysisId.value) return;

    downloadingPdf.value = true;

    try {
        await MarketingService.downloadPdfFile(analysisId.value);
        toast.add({
            severity: 'success',
            summary: 'PDF скачан',
            detail: 'PDF отчет успешно скачан',
            life: 3000
        });
    } catch (error) {
        console.error('Ошибка при скачивании PDF:', error);
        toast.add({
            severity: 'error',
            summary: 'Ошибка',
            detail: error.message || 'Не удалось скачать PDF отчет',
            life: 5000
        });
    } finally {
        downloadingPdf.value = false;
    }
};

// Reset analysis and form
const resetAnalysis = () => {
    stopPolling();
    analysisId.value = null;
    status.value = null;
    report.value = null;
    currentAnalysisType.value = null;
    estimatedCompletionTime.value = null;
    pollingAttempts.value = 0;
    v2AnalysisId.value = null;
    v2Report.value = null;
    v2Loading.value = false;
    v2Error.value = null;
    formData.value = {
        businessNiche: '',
        product: '',
        targetAudience: {
            genders: [],
            ageRanges: [],
            types: []
        },
        region: [],
        goal: '',
        detailLevel: 'СТАНДАРТНО',
        strongSide: '',
        weakSide: '',
        analysisType: []
    };
    errors.value = {};
};

// Render markdown to HTML
// Helper function to extract JSON from rendered HTML (after markdown rendering)
const extractJsonFromRenderedHtml = (html) => {
    if (!html || typeof html !== 'string') {
        return { htmlSegments: [html], chartSegments: [] };
    }

    const chartSegments = [];
    const htmlSegments = [];
    let processedHtml = html;
    const processedMatches = new Set();

    // Find all <pre><code> blocks that might contain JSON
    const codeBlockRegex = /<pre[^>]*><code[^>]*>([\s\S]*?)<\/code><\/pre>/gi;
    let match;

    while ((match = codeBlockRegex.exec(html)) !== null) {
        const [fullMatch, codeContent] = match;
        if (processedMatches.has(fullMatch)) continue;

        // Try to extract and parse JSON from code content
        const jsonSegment = tryParseJsonSegment(codeContent);
        if (jsonSegment) {
            processedMatches.add(fullMatch);
            chartSegments.push(jsonSegment);
            // Remove the code block from HTML
            processedHtml = processedHtml.replace(fullMatch, '');
        }
    }

    // Also check for standalone <code> blocks
    const standaloneCodeRegex = /<code[^>]*>([\s\S]*?)<\/code>/gi;
    while ((match = standaloneCodeRegex.exec(processedHtml)) !== null) {
        const [fullMatch, codeContent] = match;
        if (processedMatches.has(fullMatch)) continue;

        const jsonSegment = tryParseJsonSegment(codeContent);
        if (jsonSegment) {
            processedMatches.add(fullMatch);
            chartSegments.push(jsonSegment);
            processedHtml = processedHtml.replace(fullMatch, '');
        }
    }

    // Also try to find JSON in plain text (not in code blocks)
    // Look for JSON objects/arrays in the remaining HTML text
    const findJsonInHtmlText = (text) => {
        const results = [];
        let depth = 0;
        let start = -1;
        let inString = false;
        let stringChar = '';
        let inTag = false;

        for (let i = 0; i < text.length; i++) {
            const char = text[i];
            const prevChar = i > 0 ? text[i - 1] : '';

            // Skip HTML tags
            if (char === '<') inTag = true;
            if (char === '>') inTag = false;
            if (inTag) continue;

            // Handle string escaping
            if (prevChar === '\\') continue;

            // Handle string boundaries
            if ((char === '"' || char === "'") && !inString) {
                inString = true;
                stringChar = char;
            } else if (char === stringChar && inString) {
                inString = false;
                stringChar = '';
            }

            if (inString) continue;

            // Track bracket depth
            if (char === '[' || char === '{') {
                if (depth === 0) {
                    start = i;
                }
                depth++;
            } else if (char === ']' || char === '}') {
                depth--;
                if (depth === 0 && start !== -1) {
                    const jsonText = text.substring(start, i + 1);
                    const jsonSegment = tryParseJsonSegment(jsonText);
                    if (jsonSegment) {
                        results.push({ text: jsonText, index: start, segment: jsonSegment });
                    }
                    start = -1;
                }
            }
        }

        return results;
    };

    const jsonMatches = findJsonInHtmlText(processedHtml);
    // Process matches from end to start to preserve indices
    jsonMatches.reverse().forEach(({ text, segment }) => {
        if (!processedMatches.has(text)) {
            processedMatches.add(text);
            chartSegments.push(segment);
            // Remove JSON from HTML
            const index = processedHtml.indexOf(text);
            if (index !== -1) {
                processedHtml = processedHtml.substring(0, index) + processedHtml.substring(index + text.length);
            }
        }
    });

    // Split remaining HTML by removed code blocks and add as segments
    if (processedHtml.trim()) {
        // Split by multiple newlines to create separate segments
        const parts = processedHtml.split(/\n\s*\n/).filter((p) => p.trim());
        htmlSegments.push(...parts);
    }

    return { htmlSegments, chartSegments };
};

// Helper function to extract JSON from markdown before rendering
const extractJsonFromMarkdown = (markdown) => {
    if (!markdown || typeof markdown !== 'string') {
        return { processedText: markdown, jsonSegments: [] };
    }

    const jsonSegments = [];
    let processedText = markdown;
    const processedMatches = new Set();

    // Find all code blocks that might contain JSON
    // Match ```json, ```json:identifier, or plain ``` blocks
    const codeBlockRegex = /```(?:json(?::(\w+))?)?\r?\n([\s\S]*?)\r?\n```/g;
    let match;

    while ((match = codeBlockRegex.exec(markdown)) !== null) {
        const [fullMatch, identifier, codeContent] = match;
        const jsonSegment = tryParseJsonSegment(codeContent);

        if (jsonSegment && !processedMatches.has(fullMatch)) {
            processedMatches.add(fullMatch);
            jsonSegments.push(jsonSegment);
            // Replace the code block with empty string (we'll add the segment separately)
            processedText = processedText.replace(fullMatch, '');
        }
    }

    // Also check for JSON objects/arrays that are not in code blocks
    // Look for JSON at the end of text or standalone
    // Use a more sophisticated approach: find balanced brackets
    const findJsonInText = (text) => {
        const results = [];
        let depth = 0;
        let start = -1;
        let inString = false;
        let stringChar = '';

        for (let i = 0; i < text.length; i++) {
            const char = text[i];
            const prevChar = i > 0 ? text[i - 1] : '';

            // Handle string escaping
            if (prevChar === '\\') continue;

            // Handle string boundaries
            if ((char === '"' || char === "'") && !inString) {
                inString = true;
                stringChar = char;
            } else if (char === stringChar && inString) {
                inString = false;
                stringChar = '';
            }

            if (inString) continue;

            // Track bracket depth
            if (char === '[' || char === '{') {
                if (depth === 0) {
                    start = i;
                }
                depth++;
            } else if (char === ']' || char === '}') {
                depth--;
                if (depth === 0 && start !== -1) {
                    const jsonText = text.substring(start, i + 1);
                    const jsonSegment = tryParseJsonSegment(jsonText);
                    if (jsonSegment) {
                        results.push({ text: jsonText, index: start, segment: jsonSegment });
                    }
                    start = -1;
                }
            }
        }

        return results;
    };

    const jsonMatches = findJsonInText(processedText);

    // Process matches from end to start to preserve indices
    jsonMatches.reverse().forEach(({ text, segment }) => {
        if (!processedMatches.has(text)) {
            processedMatches.add(text);
            jsonSegments.push(segment);
            // Use a more precise replacement to avoid partial matches
            processedText = processedText.substring(0, processedText.indexOf(text)) + processedText.substring(processedText.indexOf(text) + text.length);
        }
    });

    // Also check if the entire remaining text is JSON (common case when JSON is at the end)
    // This handles cases where JSON is at the very end of the text
    const finalTrimmed = processedText.trim();
    if (finalTrimmed && (finalTrimmed.startsWith('[') || finalTrimmed.startsWith('{'))) {
        const finalJsonSegment = tryParseJsonSegment(finalTrimmed);
        if (finalJsonSegment && !processedMatches.has(finalTrimmed)) {
            jsonSegments.push(finalJsonSegment);
            processedText = '';
        }
    }

    // Also check for JSON that might be at the end but after some whitespace/newlines
    // Look for JSON patterns at the end of the text (after removing trailing whitespace)
    const lines = processedText.split('\n');
    let jsonStartLine = -1;
    for (let i = lines.length - 1; i >= 0; i--) {
        const line = lines[i].trim();
        if (line.startsWith('[') || line.startsWith('{')) {
            jsonStartLine = i;
            break;
        }
        if (line && !line.match(/^[\[\]{}:,\s"']+$/)) {
            // Not a JSON line, stop searching
            break;
        }
    }

    if (jsonStartLine >= 0) {
        const jsonText = lines.slice(jsonStartLine).join('\n').trim();
        const finalJsonSegment = tryParseJsonSegment(jsonText);
        if (finalJsonSegment && !processedMatches.has(jsonText)) {
            jsonSegments.push(finalJsonSegment);
            processedText = lines.slice(0, jsonStartLine).join('\n').trim();
        }
    }

    return { processedText: processedText.trim(), jsonSegments };
};

const renderMarkdown = (markdown) => {
    if (!markdown || typeof markdown !== 'string') {
        return '';
    }
    try {
        // Support LaTeX blocks written as \[ ... \] by normalizing to $$ ... $$ (what KaTeX/marked extension expects).
        // We apply this only outside fenced code blocks to avoid mangling JSON/code.
        const normalizeLatexMathDelimiters = (input) => {
            if (!input || typeof input !== 'string') return input;

            // Split into "fenced code blocks" and "everything else".
            // Fence pattern: ```lang?\n ... \n```
            const fenceRe = /```[^\n]*\n[\s\S]*?\n```/g;
            let out = '';
            let lastIndex = 0;
            let m;

            const normalizeChunk = (chunk) => {
                // Block math: \[ ... \]  ->  $$ ... $$
                // Use non-greedy match across newlines.
                let s = chunk.replace(/\\\[([\s\S]*?)\\\]/g, (_full, body) => `\n\n$$\n${body.trim()}\n$$\n\n`);
                // Inline math: \( ... \) -> $ ... $ (optional but useful)
                s = s.replace(/\\\(([\s\S]*?)\\\)/g, (_full, body) => `$${body.trim()}$`);
                return s;
            };

            while ((m = fenceRe.exec(input)) !== null) {
                const before = input.slice(lastIndex, m.index);
                out += normalizeChunk(before);
                out += m[0]; // keep fenced code blocks unchanged
                lastIndex = m.index + m[0].length;
            }
            out += normalizeChunk(input.slice(lastIndex));
            return out;
        };

        // Register KaTeX extension once (idempotent-ish in practice, but we guard to be safe).
        // We avoid throwing on invalid LaTeX so markdown rendering never crashes the report.
        if (!isKatexMarkedConfigured) {
            marked.use(
                markedKatex({
                    throwOnError: false,
                    strict: 'ignore'
                })
            );
            isKatexMarkedConfigured = true;
        }

        // В marked v17 используется marked.parse() с опциями вторым параметром
        const normalized = normalizeLatexMathDelimiters(markdown);
        return marked.parse(normalized, { breaks: true, gfm: true });
    } catch (error) {
        console.error('Error rendering markdown:', error);
        // В случае ошибки возвращаем исходный текст
        return markdown;
    }
};

/**
 * Split markdown into block-level segments so charts/code blocks can be rendered strictly in-flow
 * between the exact neighboring blocks (paragraphs, lists, headings, etc.).
 *
 * Important: we keep rendering via `renderMarkdown()` for compatibility, but use `marked.lexer()`
 * to determine block boundaries and to mark token type for safer pairing logic.
 */
const pushMarkdownTokens = (segments, markdownChunk) => {
    if (!markdownChunk || typeof markdownChunk !== 'string') return;

    const trimmed = markdownChunk.trim();
    if (!trimmed) return;

    let tokens = [];
    try {
        tokens = marked.lexer(markdownChunk, { breaks: true, gfm: true }) || [];
    } catch (e) {
        // If lexer fails, fall back to a single segment (still in-flow, just less granular).
        segments.push({ type: 'markdown', html: renderMarkdown(markdownChunk), mdTokenType: 'raw' });
        return;
    }

    for (const token of tokens) {
        if (!token || token.type === 'space') continue;
        const raw = typeof token.raw === 'string' ? token.raw : '';
        if (!raw.trim()) continue;
        segments.push({
            type: 'markdown',
            html: renderMarkdown(raw),
            mdTokenType: token.type
        });
    }
};

const buildSeasonalityChartData = (seasonality) => {
    if (!seasonality || typeof seasonality !== 'object') return null;

    // New backend format: Chart.js data shape { labels: [...], datasets: [...] }
    if (isChartJsData(seasonality)) return normalizeChartJsData(seasonality, 'line');

    // Chart.js-like (labels exist) but datasets missing/empty -> return safe shape so UI can show placeholder
    if (Array.isArray(seasonality.labels)) {
        return {
            labels: seasonality.labels,
            datasets: Array.isArray(seasonality.datasets) ? seasonality.datasets : []
        };
    }

    // Legacy format: object map { "Январь": 80, ... }
    return {
        labels: Object.keys(seasonality),
        datasets: [
            {
                label: 'Индекс спроса',
                data: Object.values(seasonality),
                borderColor: '#3B82F6',
                backgroundColor: 'rgba(59, 130, 246, 0.2)',
                fill: true,
                tension: 0.4
            }
        ]
    };
};

const buildConversionFunnelChartData = (funnel) => {
    if (!Array.isArray(funnel) || funnel.length === 0) return null;
    return {
        labels: funnel.map((item) => item.stage),
        datasets: [
            {
                label: 'Пользователей',
                data: funnel.map((item) => item.value),
                backgroundColor: getMarketingColors(funnel.length),
                borderColor: '#ffffff',
                borderWidth: 2,
                borderRadius: 4
            }
        ]
    };
};

const buildChannelsPotentialChartData = (channels) => {
    if (!Array.isArray(channels) || channels.length === 0) return null;

    return {
        labels: channels.map((ch) => ch.name),
        datasets: [
            {
                label: 'Потенциал канала',
                data: channels.map((ch) => ch.potential),
                backgroundColor: (ctx) => {
                    const val = ctx.raw;
                    return val >= 80 ? '#10B981' : val >= 50 ? '#F59E0B' : '#EF4444';
                },
                borderRadius: 4
            }
        ]
    };
};

const buildAudienceSegmentationChartData = (segmentation) => {
    if (!segmentation || !segmentation.ageGroups) return { ageGroupsChartData: null, gendersChartData: null };

    // Build chart data for age groups (primary chart)
    const ageLabels = segmentation.ageGroups.map((i) => i.label);
    const ageValues = segmentation.ageGroups.map((i) => parseFloat(i.value));

    const ageGroupsChartData = {
        labels: ageLabels,
        datasets: [
            {
                data: ageValues,
                backgroundColor: getMarketingColors(ageValues.length),
                borderColor: '#ffffff',
                borderWidth: 2
            }
        ]
    };

    // Keep genders chart for backward compatibility if needed
    const gendersChartData =
        Array.isArray(segmentation.genders) && segmentation.genders.length > 0
            ? {
                  labels: segmentation.genders.map((g) => g?.label || ''),
                  datasets: [
                      {
                          data: segmentation.genders.map((g) => {
                              const value = g?.value;
                              return value != null ? parseFloat(value) : 0;
                          }),
                          backgroundColor: getMarketingColors(segmentation.genders.length),
                          borderColor: '#ffffff',
                          borderWidth: 2
                      }
                  ]
              }
            : null;

    return { ageGroupsChartData, gendersChartData };
};

// Build segments channel matrix data for heatmap
const buildSegmentsChannelMatrix = (matrix) => {
    if (!Array.isArray(matrix) || matrix.length === 0) return null;

    // Extract all unique channels from matrix
    const channels = new Set();
    matrix.forEach((row) => {
        Object.keys(row).forEach((key) => {
            if (key !== 'segmentName') {
                channels.add(key);
            }
        });
    });

    return {
        segments: matrix.map((row) => row.segmentName),
        channels: Array.from(channels),
        data: matrix
    };
};

// Build market share chart data
const buildMarketShareChartData = (marketShareChart) => {
    if (!Array.isArray(marketShareChart) || marketShareChart.length === 0) return null;
    return {
        labels: marketShareChart.map((item) => item.name),
        datasets: [
            {
                data: marketShareChart.map((item) => item.value),
                backgroundColor: getMarketingColors(marketShareChart.length),
                borderColor: '#ffffff',
                borderWidth: 2
            }
        ]
    };
};

// Build competitors bar chart data for reach and followers
const buildCompetitorsBarChartData = (competitors, metricType = 'reach') => {
    if (!Array.isArray(competitors) || competitors.length === 0) return null;

    return {
        labels: competitors.map((comp) => comp.name),
        datasets: [
            {
                label: metricType === 'reach' ? 'Охват аудитории' : 'Подписчики',
                // Check nested structure digitalMetrics!
                data: competitors.map((comp) => (comp.digitalMetrics ? comp.digitalMetrics[metricType] || 0 : comp[metricType] || 0)),
                backgroundColor: getMarketingColors(competitors.length, metricType === 'reach' ? 0 : 1),
                borderColor: '#ffffff',
                borderWidth: 2,
                borderRadius: 4
            }
        ]
    };
};

// Build competitors visibility score chart data (horizontal bar chart)
const buildCompetitorsVisibilityChartData = (competitors) => {
    if (!Array.isArray(competitors) || competitors.length === 0) return null;

    // Sort by visibility_score descending for better visualization
    const sortedCompetitors = [...competitors].sort((a, b) => (b.visibility_score || 0) - (a.visibility_score || 0));

    return {
        labels: sortedCompetitors.map((comp) => comp.name),
        datasets: [
            {
                label: 'Видимость (score)',
                data: sortedCompetitors.map((comp) => comp.visibility_score || 0),
                backgroundColor: sortedCompetitors.map((comp) => {
                    const score = comp.visibility_score || 0;
                    // Color coding: high (green), medium (yellow), low (red)
                    if (score >= 70) return '#10B981'; // green-500
                    if (score >= 40) return '#F59E0B'; // amber-500
                    return '#EF4444'; // red-500
                }),
                borderColor: '#ffffff',
                borderWidth: 2,
                borderRadius: 4
            }
        ]
    };
};

// Process competitive environment data into segment format
const processCompetitiveEnvironmentData = (competitiveEnv) => {
    if (!competitiveEnv || typeof competitiveEnv !== 'object') return null;

    const competitors = competitiveEnv.competitors || [];
    if (!Array.isArray(competitors) || competitors.length === 0) return null;

    // Build visibility chart data
    const visibilityChartData = buildCompetitorsVisibilityChartData(competitors);

    return {
        type: 'competitiveEnvironment',
        title: competitiveEnv.title || 'Конкурентная среда',
        metrics: competitiveEnv.metrics || {},
        competitors: competitors,
        visibilityChart: visibilityChartData
            ? {
                  chartType: 'bar',
                  data: visibilityChartData,
                  options: {
                      indexAxis: 'y',
                      responsive: true,
                      maintainAspectRatio: false,
                      layout: { padding: { right: 40 } },
                      animation: {
                          duration: 500,
                          onComplete: (animation) => drawBarValues(animation.chart)
                      },
                      plugins: {
                          legend: { display: false },
                          tooltip: {
                              callbacks: {
                                  label: (context) => `Видимость: ${context.parsed.x}%`
                              }
                          }
                      },
                      scales: {
                          x: {
                              display: true,
                              beginAtZero: true,
                              max: 100,
                              ticks: {
                                  callback: function (value) {
                                      return value + '%';
                                  },
                                  font: { size: 12 }
                              },
                              grid: {
                                  display: true,
                                  drawBorder: false,
                                  color: 'rgba(0,0,0,0.05)'
                              }
                          },
                          y: {
                              grid: { display: false },
                              ticks: {
                                  font: { size: 12, weight: '500' },
                                  crossAlign: 'far'
                              }
                          }
                      }
                  },
                  title: 'Видимость конкурентов',
                  chartHeight: 'height: 400px'
              }
            : null,
        conclusion: competitiveEnv.conclusion || ''
    };
};

// Build competitors heatmap data
const buildCompetitorsHeatmapData = (competitors) => {
    if (!Array.isArray(competitors) || competitors.length === 0) return null;

    const channels = new Set();
    competitors.forEach((comp) => {
        if (comp.channelsHeatmap && typeof comp.channelsHeatmap === 'object') {
            Object.keys(comp.channelsHeatmap).forEach((channel) => channels.add(channel));
        }
    });

    return {
        competitors: competitors.map((comp) => comp.name),
        channels: Array.from(channels),
        data: competitors.map((comp) => ({
            name: comp.name,
            channelsHeatmap: comp.channelsHeatmap || {}
        }))
    };
};

// --- ВСТАВИТЬ СЮДА ---

// Сборка данных для ДОХОДА (Фото 2)
const buildIncomeChartData = (targetAudience) => {
    // Данные могут быть в snake_case или camelCase
    const incomeData = targetAudience?.income_by_age || targetAudience?.incomeByAge;
    if (!incomeData || typeof incomeData !== 'object') return null;

    const labels = Object.keys(incomeData);
    const values = Object.values(incomeData);

    return {
        labels: labels,
        datasets: [
            {
                label: 'Средний доход (KZT)',
                data: values,
                backgroundColor: getMarketingColors(values.length),
                borderRadius: 4
            }
        ]
    };
};

const buildChannelsChartData = (acquisitionChannels) => {
    const shares = acquisitionChannels?.channel_shares || acquisitionChannels?.channelShares;
    if (!shares || typeof shares !== 'object') return null;

    // Превращаем ключи "instagram_target" в "Instagram Target"
    const labels = Object.keys(shares).map((key) =>
        key
            .split('_')
            .map((w) => w.charAt(0).toUpperCase() + w.slice(1))
            .join(' ')
    );

    // Чистим значения от знака % для графика
    const values = Object.values(shares).map((val) => (typeof val === 'string' ? parseFloat(val.replace('%', '')) : val));

    return {
        labels: labels,
        datasets: [
            {
                label: 'Доля',
                data: values,
                unit: '%', // Маркер, чтобы рисовать %
                backgroundColor: getMarketingColors(values.length, 2),
                borderRadius: 6
            }
        ]
    };
};

// Get heatmap color intensity based on value (0-100)
const getHeatmapColor = (value) => {
    if (value >= 80) return 'rgba(16, 185, 129, 0.9)'; // green-500
    if (value >= 60) return 'rgba(245, 158, 11, 0.9)'; // amber-500
    if (value >= 40) return 'rgba(251, 191, 36, 0.9)'; // yellow-500
    if (value >= 20) return 'rgba(249, 115, 22, 0.9)'; // orange-500
    return 'rgba(239, 68, 68, 0.9)'; // red-500
};

// Helper: detect Chart.js "data" shape (labels + datasets)
const isChartJsData = (value) => {
    return !!(value && typeof value === 'object' && !Array.isArray(value) && Array.isArray(value.labels) && Array.isArray(value.datasets));
};

// Helper: normalize Chart.js datasets to have sane colors
// - For pie/doughnut/bar we default to per-item colors (arrays) + white borders
// - If backgroundColor is already an array or function, we keep it (custom colors)
const normalizeChartJsData = (raw, chartType) => {
    if (!isChartJsData(raw)) return null;
    const type = String(chartType || raw.chartType || '').toLowerCase();
    const wantsPerItemColors = type === 'pie' || type === 'doughnut' || type === 'bar';

    return {
        labels: Array.isArray(raw.labels) ? raw.labels : [],
        datasets: raw.datasets.map((dataset, idx) => {
            const data = Array.isArray(dataset?.data) ? dataset.data : [];

            const hasCustomBgArray = Array.isArray(dataset?.backgroundColor);
            const hasCustomBgFn = typeof dataset?.backgroundColor === 'function';

            const backgroundColor = wantsPerItemColors && !hasCustomBgArray && !hasCustomBgFn ? getMarketingColors(data.length, idx) : dataset?.backgroundColor;

            // Keep existing borderColor if provided; otherwise apply white borders for separation on partitioned charts
            const borderColor = dataset?.borderColor ?? (wantsPerItemColors ? '#ffffff' : undefined);
            const borderWidth = dataset?.borderWidth ?? (wantsPerItemColors ? 2 : undefined);

            // For non-partitioned charts, keep old behavior: if colors are missing, use a reasonable fallback
            const fallbackColor = getMarketingColors(1, idx)[0];
            const resolvedBg = typeof backgroundColor === 'undefined' ? dataset?.borderColor || fallbackColor : backgroundColor;
            const resolvedBorder = typeof borderColor === 'undefined' ? dataset?.borderColor || resolvedBg : borderColor;

            return {
                ...dataset,
                data,
                backgroundColor: resolvedBg,
                borderColor: resolvedBorder,
                ...(typeof borderWidth !== 'undefined' ? { borderWidth } : {}),
                borderRadius: dataset.borderRadius ?? 4
            };
        })
    };
};

// Helper: check if chart has any renderable data (avoid crashing when datasets is missing/empty)
const hasRenderableChartData = (chartData) => {
    if (!chartData || typeof chartData !== 'object') return false;
    const datasets = Array.isArray(chartData.datasets) ? chartData.datasets : [];
    if (datasets.length === 0) return false;
    return datasets.some((ds) => Array.isArray(ds?.data) && ds.data.length > 0);
};

// Main function to map chartsData to segments
const mapChartsDataToSegments = (chartsData) => {
    if (!chartsData || typeof chartsData !== 'object') return [];

    const segments = [];
    const sections = chartsData.sections || chartsData;

    // --- 1. СПРОС И ПОВЕДЕНИЕ ---
    const demandSection = sections.demand_and_behavior || sections.demandAndBehavior;
    if (demandSection) {
        // Причины отказов (Оранжевые, как на фото 1)
        const refusals = demandSection.reasons_for_refusal || demandSection.reasonsForRefusal;
        if (refusals) {
            const { labels, values } = parsePercentageData(refusals);
            segments.push({
                type: 'chart',
                key: 'refusalReasons',
                title: 'Причины отказов',
                chartType: 'bar',
                data: {
                    labels,
                    datasets: [
                        {
                            data: values,
                            backgroundColor: '#fb923c', // Оранжевый
                            borderRadius: 8,
                            barPercentage: 0.7,
                            unit: '%'
                        }
                    ]
                },
                options: photoStyleBarOptions, // <-- Стиль как на фото (цифры внутри)
                chartHeight: 'height: 300px'
            });
        }

        // Факторы принятия решения (Сиреневые, стиль фото 6)
        const factors = demandSection.decision_factors || demandSection.decisionFactors;
        if (factors) {
            const { labels, values } = parsePercentageData(factors);
            segments.push({
                type: 'chart',
                key: 'decisionFactors',
                title: 'Факторы принятия решения',
                chartType: 'bar',
                data: {
                    labels,
                    datasets: [
                        {
                            data: values,
                            backgroundColor: '#818cf8', // Сиреневый
                            borderRadius: 8,
                            barPercentage: 0.7,
                            unit: '%'
                        }
                    ]
                },
                options: photoStyleBarOptions,
                chartHeight: 'height: 300px'
            });
        }
    }

    // --- 2. ЦЕЛЕВАЯ АУДИТОРИЯ ---
    const audienceSection = sections.target_audience || sections.targetAudience;
    if (audienceSection) {
        // ВОЗРАСТНАЯ СТРУКТУРА (ФОТО 3 - СИНИЙ ЦВЕТ)
        const ageStruct = audienceSection.age_structure || audienceSection.ageStructure;
        if (ageStruct) {
            const { labels, values } = parsePercentageData(ageStruct);
            segments.push({
                type: 'chart',
                key: 'ageStructure',
                title: 'Возрастная структура',
                chartType: 'bar',
                data: {
                    labels,
                    datasets: [
                        {
                            data: values,
                            // !!! ЦВЕТ КАК НА ФОТО (СИНИЙ) !!!
                            backgroundColor: '#60a5fa',
                            borderRadius: 8, // Скругление
                            barPercentage: 0.65,
                            unit: '%'
                        }
                    ]
                },
                options: photoStyleBarOptions, // Белые цифры внутри
                chartHeight: 'height: 300px'
            });
        }

        // Доход (Фото 5 - Мятный цвет)
        const incomeData = audienceSection.income_by_age || audienceSection.incomeByAge;
        if (incomeData || audienceSection.metrics?.above_average_income_share) {
            let labels = [],
                values = [];
            if (incomeData) {
                const parsed = parsePercentageData(incomeData);
                labels = parsed.labels;
                values = parsed.values;
            } else {
                labels = ['Низкий', 'Средний', 'Высокий'];
                values = [20, 50, 30];
            }

            segments.push({
                type: 'chart',
                key: 'incomeLevel',
                title: 'Уровень дохода аудитории',
                chartType: 'bar',
                data: {
                    labels,
                    datasets: [
                        {
                            data: values,
                            backgroundColor: '#34d399', // Мятный
                            borderRadius: 8,
                            barPercentage: 0.65,
                            unit: '%'
                        }
                    ]
                },
                options: photoStyleBarOptions,
                chartHeight: 'height: 300px'
            });
        }
    }

    // --- 3. КАНАЛЫ (Фото 4 - Разноцветные) ---
    const acquisitionSection = sections.acquisition_channels || sections.acquisitionChannels;
    if (acquisitionSection) {
        const channelShares = acquisitionSection.channel_shares || acquisitionSection.channelShares;
        if (channelShares) {
            const { labels, values } = parsePercentageData(channelShares);
            // Убираем нули
            const filteredIndices = values.map((v, i) => (v > 0 ? i : -1)).filter((i) => i !== -1);
            const finalLabels = filteredIndices.map((i) => labels[i]);
            const finalValues = filteredIndices.map((i) => values[i]);

            if (finalValues.length > 0) {
                segments.push({
                    type: 'chart',
                    key: 'acquisitionChannels',
                    title: 'Доли каналов привлечения',
                    chartType: 'bar',
                    data: {
                        labels: finalLabels,
                        datasets: [
                            {
                                data: finalValues,
                                backgroundColor: getMarketingColors(finalValues.length), // Разноцветные
                                borderRadius: 8,
                                barPercentage: 0.6,
                                unit: '%'
                            }
                        ]
                    },
                    options: photoStyleBarOptions,
                    chartHeight: 'height: 300px'
                });
            }
        }
    }

    // --- 4. СЕЗОННОСТЬ (Line) ---
    const marketSection = sections.market_overview || sections.marketOverview;
    if (marketSection) {
        const seasonalData = marketSection.monthly_online_index || marketSection.monthlyOnlineIndex;
        if (seasonalData) {
            segments.push({
                type: 'chart',
                key: 'seasonality',
                title: 'Динамика спроса',
                chartType: 'line',
                data: {
                    labels: Object.keys(seasonalData),
                    datasets: [
                        {
                            label: 'Индекс',
                            data: Object.values(seasonalData),
                            borderColor: '#6366f1',
                            backgroundColor: 'rgba(99, 102, 241, 0.2)',
                            fill: true,
                            tension: 0.4
                        }
                    ]
                },
                options: seasonalityChartOptions,
                chartHeight: 'height: 350px'
            });
        }
    }

    // --- LEGACY (Старый код, просто чтобы не ломалось, если придет старый JSON) ---
    if (Array.isArray(chartsData)) {
        if (chartsData.length > 0 && chartsData[0]?.name) {
            const reachData = chartsData.map((c) => c.reach || 0);
            return [
                {
                    type: 'chart',
                    title: 'Охват конкурентов',
                    chartType: 'bar',
                    data: { labels: chartsData.map((c) => c.name), datasets: [{ data: reachData, backgroundColor: '#60a5fa' }] },
                    options: photoStyleBarOptions
                }
            ];
        }
        return [];
    }

    return segments;
};
const mapJsonBlockToSegment = (identifier, data, rawText) => {
    const key = identifier?.toLowerCase();
    switch (key) {
        case 'audienceage': {
            const chartData = normalizeChartJsData(data, 'bar');
            if (!chartData) return null;
            return {
                type: 'chart',
                key: 'audienceAge',
                title: 'Распределение по возрасту',
                chartType: 'bar',
                data: chartData,
                options: horizontalBarChartOptions,
                chartHeight: 'height: 350px'
            };
        }
        case 'audiencegender': {
            const chartData = normalizeChartJsData(data, 'pie');
            if (!chartData) return null;
            return {
                type: 'chart',
                key: 'audienceGender',
                title: 'Распределение по полу',
                chartType: 'pie',
                data: chartData,
                options: pieChartOptions,
                chartHeight: 'height: 350px'
            };
        }
        case 'seasonality': {
            const chartData = isChartJsData(data) ? normalizeChartJsData(data, 'line') : buildSeasonalityChartData(data);
            if (!chartData) return null;
            return {
                type: 'chart',
                key: 'seasonality',
                title: 'Сезонность спроса',
                chartType: 'line',
                data: chartData,
                options: seasonalityChartOptions,
                chartHeight: 'height: 300px'
            };
        }
        case 'funnel':
        case 'conversionfunnel': {
            const chartData = isChartJsData(data) ? normalizeChartJsData(data, 'bar') : buildConversionFunnelChartData(data);
            if (!chartData) return null;
            return {
                type: 'chart',
                key: 'funnel',
                title: 'Воронка конверсии',
                chartType: 'bar',
                data: chartData,
                options: conversionFunnelChartOptions,
                chartHeight: 'height: 400px'
            };
        }
        case 'channelspotential': {
            const chartData = isChartJsData(data) ? normalizeChartJsData(data, 'bar') : buildChannelsPotentialChartData(data);
            if (!chartData) return null;
            return {
                type: 'chart',
                key: 'channelsPotential',
                title: 'Потенциал каналов продвижения',
                chartType: 'bar',
                data: chartData,
                options: channelsPotentialChartOptions,
                chartHeight: 'height: 300px',
                channels: Array.isArray(data) ? data : []
            };
        }
        case 'marketsharechart': {
            const chartData = isChartJsData(data) ? normalizeChartJsData(data, 'pie') : null;
            if (!chartData) return null;
            return {
                type: 'marketShareChart',
                title: 'Доли рынка',
                chartType: 'pie',
                data: chartData,
                options: pieChartOptions,
                chartHeight: 'height: 300px'
            };
        }
        case 'comparisontable': {
            if (!Array.isArray(data) || data.length === 0) return null;
            return {
                type: 'comparisonTable',
                data
            };
        }
        case 'audiencesegmentation': {
            const { ageGroupsChartData, gendersChartData } = buildAudienceSegmentationChartData(data || {});
            if (!ageGroupsChartData && !gendersChartData) return null;
            return {
                type: 'audienceSegmentation',
                ageGroupsChartData,
                gendersChartData
            };
        }
        case 'competitiveenvironment':
        case 'competitive_environment': {
            // New structure: { title, metrics, competitors, conclusion }
            const processed = processCompetitiveEnvironmentData(data);
            if (processed) return processed;
            // Fallback to old structure if processing fails
            return null;
        }
        case 'competitors': {
            // Check if it's new structure (has metrics, competitors array with visibility_score)
            if (data && typeof data === 'object' && !Array.isArray(data)) {
                if (data.metrics && Array.isArray(data.competitors)) {
                    const processed = processCompetitiveEnvironmentData(data);
                    if (processed) return processed;
                }
            }
            // Old structure: array of competitors
            if (!Array.isArray(data) || data.length === 0) return null;
            const reachChartData = buildCompetitorsBarChartData(data, 'reach');
            const followersChartData = buildCompetitorsBarChartData(data, 'followers');

            return {
                type: 'competitors',
                competitors: data,
                competitorsHeatmap: buildCompetitorsHeatmapData(data),
                reachChart: reachChartData
                    ? {
                          chartType: 'bar',
                          data: reachChartData,
                          options: horizontalBarChartOptions,
                          title: 'Охват конкурентов'
                      }
                    : null,
                followersChart: followersChartData
                    ? {
                          chartType: 'bar',
                          data: followersChartData,
                          options: horizontalBarChartOptions,
                          title: 'Подписчики конкурентов'
                      }
                    : null
            };
        }
        case 'swot': {
            if (!data || typeof data !== 'object') return null;
            return {
                type: 'swot',
                data: {
                    strengths: data.strengths || [],
                    weaknesses: data.weaknesses || [],
                    opportunities: data.opportunities || [],
                    threats: data.threats || []
                }
            };
        }
        case 'segmentschannelmatrix': {
            const matrix = buildSegmentsChannelMatrix(data);
            if (!matrix || !Array.isArray(matrix.data) || matrix.data.length === 0) return null;
            return {
                type: 'segmentsChannelMatrix',
                title: 'Матрица каналов по сегментам',
                matrix
            };
        }
        default:
            // Unknown block type: render raw markdown so nothing is lost
            return {
                type: 'markdown',
                html: renderMarkdown(rawText || '')
            };
    }
};

// Helper function to get chart segment by placeholder
const getChartSegmentByPlaceholder = (placeholder, chartsData) => {
    if (!chartsData) return null;

    switch (placeholder) {
        case 'CHART_AUDIENCE':
            if (chartsData.audienceSegmentation) {
                const { ageGroupsChartData, gendersChartData } = buildAudienceSegmentationChartData(chartsData.audienceSegmentation);
                if (ageGroupsChartData || gendersChartData) {
                    return {
                        type: 'audienceSegmentation',
                        ageGroupsChartData,
                        gendersChartData,
                        segmentsChannelMatrix: buildSegmentsChannelMatrix(chartsData.audienceSegmentation.segmentsChannelMatrix),
                        keyTakeaways: chartsData.audienceSegmentation.keyTakeaways || []
                    };
                }
            }
            return null;

        case 'CHART_COMPETITORS':
        case 'CHART_COMPETITIVE_ENVIRONMENT': {
            // Check for new competitive environment structure first
            if (chartsData.competitiveEnvironment || chartsData.competitive_environment) {
                const competitiveEnv = chartsData.competitiveEnvironment || chartsData.competitive_environment;
                const processed = processCompetitiveEnvironmentData(competitiveEnv);
                if (processed) return processed;
            }
            // Fallback to old competitors structure
            const competitorsArray = Array.isArray(chartsData.competitors) ? chartsData.competitors : chartsData.competitors?.competitors || [];

            if (competitorsArray.length > 0) {
                // Check if it's new structure (has visibility_score)
                if (competitorsArray[0]?.visibility_score !== undefined) {
                    const processed = processCompetitiveEnvironmentData({
                        competitors: competitorsArray,
                        metrics: chartsData.metrics || {},
                        title: chartsData.title || 'Конкурентная среда',
                        conclusion: chartsData.conclusion || ''
                    });
                    if (processed) return processed;
                }
                // Old structure
                const reachChartData = buildCompetitorsBarChartData(competitorsArray, 'reach');
                const followersChartData = buildCompetitorsBarChartData(competitorsArray, 'followers');

                const segment = {
                    type: 'competitors',
                    competitors: competitorsArray,
                    competitorsHeatmap: buildCompetitorsHeatmapData(competitorsArray),
                    reachChart: reachChartData
                        ? {
                              chartType: 'bar',
                              data: reachChartData,
                              options: horizontalBarChartOptions,
                              title: 'Охват конкурентов'
                          }
                        : null,
                    followersChart: followersChartData
                        ? {
                              chartType: 'bar',
                              data: followersChartData,
                              options: horizontalBarChartOptions,
                              title: 'Подписчики конкурентов'
                          }
                        : null
                };

                // Add marketShareChart if exists
                if (chartsData.marketShareChart && Array.isArray(chartsData.marketShareChart)) {
                    const marketShareChartData = buildMarketShareChartData(chartsData.marketShareChart);
                    if (marketShareChartData) {
                        segment.marketShareChart = {
                            type: 'marketShareChart',
                            title: 'Доли рынка',
                            chartType: 'pie',
                            data: marketShareChartData,
                            options: pieChartOptions,
                            chartHeight: 'height: 300px'
                        };
                    }
                }

                // Add comparisonTable if exists
                if (chartsData.comparisonTable && Array.isArray(chartsData.comparisonTable) && chartsData.comparisonTable.length > 0) {
                    segment.comparisonTable = {
                        type: 'comparisonTable',
                        data: chartsData.comparisonTable
                    };
                }

                return segment;
            }
            return null;
        }

        case 'CHART_SWOT':
            // Check for swotCompetitors first
            if (chartsData.swotCompetitors && typeof chartsData.swotCompetitors === 'object') {
                return {
                    type: 'swotCompetitors',
                    data: {
                        strengths: chartsData.swotCompetitors.strengths || [],
                        weaknesses: chartsData.swotCompetitors.weaknesses || []
                    }
                };
            }
            // Fallback to swot
            if (chartsData.swot && typeof chartsData.swot === 'object') {
                return {
                    type: 'swot',
                    data: {
                        strengths: chartsData.swot.strengths || [],
                        weaknesses: chartsData.swot.weaknesses || [],
                        opportunities: chartsData.swot.opportunities || [],
                        threats: chartsData.swot.threats || []
                    }
                };
            }
            return null;

        case 'CHART_CHANNELS':
            if (chartsData.channelsPotential && Array.isArray(chartsData.channelsPotential)) {
                const chartData = buildChannelsPotentialChartData(chartsData.channelsPotential);
                if (chartData) {
                    return {
                        type: 'chart',
                        key: 'channelsPotential',
                        title: 'Потенциал каналов продвижения',
                        chartType: 'bar',
                        data: chartData,
                        options: channelsPotentialChartOptions,
                        chartHeight: 'height: 300px',
                        channels: chartsData.channelsPotential
                    };
                }
            }
            return null;

        case 'CHART_FUNNEL':
            if (chartsData.conversionFunnel && Array.isArray(chartsData.conversionFunnel)) {
                const chartData = buildConversionFunnelChartData(chartsData.conversionFunnel);
                if (chartData) {
                    return {
                        type: 'chart',
                        key: 'funnel',
                        title: 'Воронка конверсии',
                        chartType: 'bar',
                        data: chartData,
                        options: conversionFunnelChartOptions,
                        chartHeight: 'height: 400px'
                    };
                }
            }
            return null;

        default:
            return null;
    }
};

// Helper function to get chart segment by JSON block identifier
const getChartSegmentByIdentifier = (identifier, chartsData) => {
    if (!chartsData) return null;
    const key = identifier?.toLowerCase();

    switch (key) {
        case 'audienceage': {
            const chartData = normalizeChartJsData(chartsData.audienceAge, 'bar');
            if (!chartData) return null;
            return {
                type: 'chart',
                key: 'audienceAge',
                title: 'Распределение по возрасту',
                chartType: 'bar',
                data: chartData,
                options: horizontalBarChartOptions,
                chartHeight: 'height: 350px'
            };
        }
        case 'audiencegender': {
            const chartData = normalizeChartJsData(chartsData.audienceGender, 'pie');
            if (!chartData) return null;
            return {
                type: 'chart',
                key: 'audienceGender',
                title: 'Распределение по полу',
                chartType: 'pie',
                data: chartData,
                options: pieChartOptions,
                chartHeight: 'height: 350px'
            };
        }
        case 'audiencesegmentation':
            if (chartsData.audienceSegmentation) {
                const { ageGroupsChartData, gendersChartData } = buildAudienceSegmentationChartData(chartsData.audienceSegmentation);
                if (ageGroupsChartData || gendersChartData) {
                    return {
                        type: 'audienceSegmentation',
                        ageGroupsChartData,
                        gendersChartData,
                        segmentsChannelMatrix: buildSegmentsChannelMatrix(chartsData.audienceSegmentation.segmentsChannelMatrix),
                        keyTakeaways: chartsData.audienceSegmentation.keyTakeaways || []
                    };
                }
            }
            return null;

        case 'competitiveenvironment':
        case 'competitive_environment': {
            const competitiveEnv = chartsData.competitiveEnvironment || chartsData.competitive_environment;
            if (competitiveEnv) {
                const processed = processCompetitiveEnvironmentData(competitiveEnv);
                if (processed) return processed;
            }
            return null;
        }
        case 'competitors': {
            const competitorsArray = Array.isArray(chartsData.competitors) ? chartsData.competitors : chartsData.competitors?.competitors || [];
            if (competitorsArray.length > 0) {
                // Check if it's new structure (has visibility_score)
                if (competitorsArray[0]?.visibility_score !== undefined) {
                    const processed = processCompetitiveEnvironmentData({
                        competitors: competitorsArray,
                        metrics: chartsData.metrics || {},
                        title: chartsData.title || 'Конкурентная среда',
                        conclusion: chartsData.conclusion || ''
                    });
                    if (processed) return processed;
                }
                // Old structure
                const reachChartData = buildCompetitorsBarChartData(competitorsArray, 'reach');
                const followersChartData = buildCompetitorsBarChartData(competitorsArray, 'followers');

                const segment = {
                    type: 'competitors',
                    competitors: competitorsArray,
                    competitorsHeatmap: buildCompetitorsHeatmapData(competitorsArray),
                    reachChart: reachChartData
                        ? {
                              chartType: 'bar',
                              data: reachChartData,
                              options: horizontalBarChartOptions,
                              title: 'Охват конкурентов'
                          }
                        : null,
                    followersChart: followersChartData
                        ? {
                              chartType: 'bar',
                              data: followersChartData,
                              options: horizontalBarChartOptions,
                              title: 'Подписчики конкурентов'
                          }
                        : null
                };

                // Add marketShareChart if exists
                if (chartsData.marketShareChart && Array.isArray(chartsData.marketShareChart)) {
                    const marketShareChartData = buildMarketShareChartData(chartsData.marketShareChart);
                    if (marketShareChartData) {
                        segment.marketShareChart = {
                            type: 'marketShareChart',
                            title: 'Доли рынка',
                            chartType: 'pie',
                            data: marketShareChartData,
                            options: pieChartOptions,
                            chartHeight: 'height: 300px'
                        };
                    }
                }

                // Add comparisonTable if exists
                if (chartsData.comparisonTable && Array.isArray(chartsData.comparisonTable) && chartsData.comparisonTable.length > 0) {
                    segment.comparisonTable = {
                        type: 'comparisonTable',
                        data: chartsData.comparisonTable
                    };
                }

                return segment;
            }
            return null;
        }

        case 'swot':
            // Check for swotCompetitors first
            if (chartsData.swotCompetitors && typeof chartsData.swotCompetitors === 'object') {
                return {
                    type: 'swotCompetitors',
                    data: {
                        strengths: chartsData.swotCompetitors.strengths || [],
                        weaknesses: chartsData.swotCompetitors.weaknesses || []
                    }
                };
            }
            // Fallback to swot
            if (chartsData.swot && typeof chartsData.swot === 'object') {
                return {
                    type: 'swot',
                    data: {
                        strengths: chartsData.swot.strengths || [],
                        weaknesses: chartsData.swot.weaknesses || [],
                        opportunities: chartsData.swot.opportunities || [],
                        threats: chartsData.swot.threats || []
                    }
                };
            }
            return null;

        case 'marketsharechart': {
            const marketShareChartData = Array.isArray(chartsData.marketShareChart) ? buildMarketShareChartData(chartsData.marketShareChart) : normalizeChartJsData(chartsData.marketShareChart, 'pie');
            if (!marketShareChartData) return null;
            return {
                type: 'marketShareChart',
                title: 'Доли рынка',
                chartType: 'pie',
                data: marketShareChartData,
                options: pieChartOptions,
                chartHeight: 'height: 300px'
            };
        }
        case 'comparisontable': {
            if (Array.isArray(chartsData.comparisonTable) && chartsData.comparisonTable.length > 0) {
                return {
                    type: 'comparisonTable',
                    data: chartsData.comparisonTable
                };
            }
            return null;
        }
        case 'channelspotential':
        case 'channels':
            if (chartsData.channelsPotential) {
                const chartData = isChartJsData(chartsData.channelsPotential) ? normalizeChartJsData(chartsData.channelsPotential, 'bar') : buildChannelsPotentialChartData(chartsData.channelsPotential);
                if (chartData) {
                    return {
                        type: 'chart',
                        key: 'channelsPotential',
                        title: 'Потенциал каналов продвижения',
                        chartType: 'bar',
                        data: chartData,
                        options: channelsPotentialChartOptions,
                        chartHeight: 'height: 300px',
                        channels: Array.isArray(chartsData.channelsPotential) ? chartsData.channelsPotential : []
                    };
                }
            }
            return null;

        case 'funnel':
        case 'conversionfunnel':
            if (chartsData.conversionFunnel) {
                const chartData = isChartJsData(chartsData.conversionFunnel) ? normalizeChartJsData(chartsData.conversionFunnel, 'bar') : buildConversionFunnelChartData(chartsData.conversionFunnel);
                if (chartData) {
                    return {
                        type: 'chart',
                        key: 'funnel',
                        title: 'Воронка конверсии',
                        chartType: 'bar',
                        data: chartData,
                        options: conversionFunnelChartOptions,
                        chartHeight: 'height: 400px'
                    };
                }
            }
            return null;

        case 'seasonality':
            if (chartsData.seasonality && typeof chartsData.seasonality === 'object') {
                const chartData = buildSeasonalityChartData(chartsData.seasonality);
                if (chartData) {
                    return {
                        type: 'chart',
                        key: 'seasonality',
                        title: 'Сезонность спроса',
                        chartType: 'line',
                        data: chartData,
                        options: seasonalityChartOptions,
                        chartHeight: 'height: 300px'
                    };
                }
            }
            return null;

        default:
            return null;
    }
};

// Helper function to check if text is a JSON object that should be processed
const tryParseJsonSegment = (text) => {
    if (!text || typeof text !== 'string') return null;

    let trimmed = text.trim();

    // Remove HTML tags if present (from rendered markdown code blocks)
    if (trimmed.includes('<pre>') || trimmed.includes('<code>') || trimmed.includes('<')) {
        // Try to extract JSON from HTML code blocks - handle nested tags
        let codeContent = trimmed;
        // Remove all HTML tags recursively
        while (codeContent.includes('<') && codeContent.includes('>')) {
            codeContent = codeContent.replace(/<[^>]+>/g, '');
        }
        // Decode common HTML entities
        codeContent = codeContent
            .replace(/&quot;/g, '"')
            .replace(/&#39;/g, "'")
            .replace(/&lt;/g, '<')
            .replace(/&gt;/g, '>')
            .replace(/&amp;/g, '&');
        trimmed = codeContent.trim();
    }

    // Also try to extract JSON if it's wrapped in HTML but not in code tags
    // Look for JSON-like patterns in the text
    if (!trimmed.startsWith('{') && !trimmed.startsWith('[')) {
        // Try to find JSON object/array in the text
        const jsonMatch = trimmed.match(/\{[\s\S]*\}|\[[\s\S]*\]/);
        if (jsonMatch) {
            trimmed = jsonMatch[0].trim();
        }
    }

    // Check if it's a JSON object or array
    if ((!trimmed.startsWith('{') || !trimmed.endsWith('}')) && (!trimmed.startsWith('[') || !trimmed.endsWith(']'))) {
        return null;
    }

    try {
        const parsedJson = JSON.parse(trimmed);

        // Check if it's new competitive environment structure
        if (parsedJson && typeof parsedJson === 'object' && !Array.isArray(parsedJson)) {
            if (parsedJson.competitors && Array.isArray(parsedJson.competitors) && parsedJson.metrics) {
                const processed = processCompetitiveEnvironmentData(parsedJson);
                if (processed) return processed;
            }
        }

        // Check if it's an array of competitors
        if (Array.isArray(parsedJson) && parsedJson.length > 0) {
            // Check if it's new structure (has visibility_score)
            if (parsedJson[0]?.visibility_score !== undefined) {
                const processed = processCompetitiveEnvironmentData({
                    competitors: parsedJson,
                    metrics: {},
                    title: 'Конкурентная среда',
                    conclusion: ''
                });
                if (processed) return processed;
            }
            // Check if it looks like old competitors data
            if (parsedJson[0]?.name && (parsedJson[0]?.channelsHeatmap || parsedJson[0]?.reach || parsedJson[0]?.followers)) {
                return {
                    type: 'competitors',
                    competitors: parsedJson,
                    competitorsHeatmap: buildCompetitorsHeatmapData(parsedJson)
                };
            }
        }

        // Check if it's Chart.js format (datasets and labels)
        if (parsedJson && typeof parsedJson === 'object' && !Array.isArray(parsedJson)) {
            if (parsedJson.datasets && Array.isArray(parsedJson.datasets) && parsedJson.labels && Array.isArray(parsedJson.labels)) {
                // Determine chart type based on dataset type or default to bar
                const chartType = parsedJson.chartType || 'bar';

                // Use appropriate options based on chart type
                const options = chartType === 'pie' || chartType === 'doughnut' ? pieChartOptions : chartType === 'line' ? seasonalityChartOptions : horizontalBarChartOptions;

                // Normalize chart data (colors/borders, safety)
                const chartData = normalizeChartJsData(parsedJson, chartType);
                if (!chartData) return null;

                // Get title from label or use default
                const title = parsedJson.datasets[0]?.label || 'График';

                return {
                    type: 'chart',
                    chartType: chartType,
                    data: chartData,
                    options: options,
                    title: title,
                    chartHeight: 'height: 400px'
                };
            }
        }

        // Check if it's an audienceSegmentation object
        if (parsedJson && typeof parsedJson === 'object' && !Array.isArray(parsedJson)) {
            if (parsedJson.genders || parsedJson.ageGroups || parsedJson.segments) {
                const { ageGroupsChartData, gendersChartData } = buildAudienceSegmentationChartData(parsedJson);
                if (ageGroupsChartData || gendersChartData) {
                    return {
                        type: 'audienceSegmentation',
                        ageGroupsChartData,
                        gendersChartData,
                        segmentsChannelMatrix: buildSegmentsChannelMatrix(parsedJson.segmentsChannelMatrix),
                        keyTakeaways: parsedJson.keyTakeaways || []
                    };
                }
            }
        }
    } catch (e) {
        // Not valid JSON
        console.debug('Failed to parse JSON segment:', e);
    }
    return null;
};

// Parse fullAnalysis and replace placeholders and JSON blocks with charts from chartsData
const parseFullAnalysisWithCharts = (fullAnalysis, chartsData) => {
    if (!fullAnalysis) return [];

    const segments = [];
    // Combined regex for both placeholders [[CHART_*]], JSON blocks ```json:identifier, and plain ```json blocks
    const combinedRegex = /(\[\[CHART_(\w+)\]\]|```json:(\w+)\r?\n([\s\S]*?)\r?\n```|```json\r?\n([\s\S]*?)\r?\n```|```\r?\n([\s\S]*?)\r?\n```)/g;
    let lastIndex = 0;
    let match;

    while ((match = combinedRegex.exec(fullAnalysis)) !== null) {
        const [fullMatch, , chartTypePlaceholder, jsonIdentifier, jsonBlockWithId, jsonBlockPlain, codeBlock] = match;

        // Add markdown before match
        if (match.index > lastIndex) {
            const textBefore = fullAnalysis.slice(lastIndex, match.index);
            if (textBefore.trim()) {
                // IMPORTANT: keep markdown strictly in-flow.
                // JSON/Chart blocks are handled by the main regex loop and must appear exactly where they are in fullAnalysis.
                pushMarkdownTokens(segments, textBefore);
            }
        }

        // Handle code blocks that might contain JSON
        if (codeBlock || jsonBlockPlain) {
            const jsonContent = codeBlock || jsonBlockPlain;
            // Try to parse as JSON and process
            const jsonSegment = tryParseJsonSegment(jsonContent);
            if (jsonSegment) {
                segments.push(jsonSegment);
            } else {
                // If not JSON, add as markdown code block
                segments.push({ type: 'markdown', html: renderMarkdown(fullMatch), mdTokenType: 'code' });
            }
            lastIndex = combinedRegex.lastIndex;
            continue;
        }

        // Handle placeholder [[CHART_*]]
        if (chartTypePlaceholder) {
            const chartSegment = getChartSegmentByPlaceholder(chartTypePlaceholder, chartsData);
            if (chartSegment) {
                segments.push(chartSegment);
            }
        }
        // Handle JSON block ```json:identifier
        else if (jsonIdentifier) {
            const chartSegment = getChartSegmentByIdentifier(jsonIdentifier, chartsData);
            if (chartSegment) {
                segments.push(chartSegment);
            } else {
                // If no chart found, try to parse JSON and use old logic as fallback
                try {
                    const parsedData = JSON.parse(jsonBlockWithId);
                    const segment = mapJsonBlockToSegment(jsonIdentifier, parsedData, fullMatch);
                    if (segment) {
                        segments.push(segment);
                    } else {
                        // If segment is null, don't add anything - the JSON block will be ignored
                        // This prevents raw JSON from being displayed
                        console.warn(`Не удалось обработать JSON блок ${jsonIdentifier}`);
                    }
                } catch (error) {
                    console.error(`Не удалось распарсить блок ${jsonIdentifier}:`, error);
                    // Don't add raw JSON block to segments - it will be ignored
                }
            }
        }

        lastIndex = combinedRegex.lastIndex;
    }

    // Add remaining markdown
    const remaining = fullAnalysis.slice(lastIndex);
    if (remaining.trim()) {
        // Keep tail markdown in-flow; chart blocks already handled by regex matches above.
        pushMarkdownTokens(segments, remaining);
    }

    return segments;
};

// New computed property for chartsData
const chartsDataSegments = computed(() => {
    if (!report.value?.chartsData) return [];

    const chartsData = report.value.chartsData;

    // Handle case when chartsData is an array directly (shouldn't happen, but handle it)
    if (Array.isArray(chartsData)) {
        // If it's an array of competitors, process it
        if (chartsData.length > 0 && chartsData[0]?.name && (chartsData[0]?.channelsHeatmap || chartsData[0]?.reach || chartsData[0]?.followers)) {
            const reachChartData = buildCompetitorsBarChartData(chartsData, 'reach');
            const followersChartData = buildCompetitorsBarChartData(chartsData, 'followers');

            return [
                {
                    type: 'competitors',
                    competitors: chartsData,
                    competitorsHeatmap: buildCompetitorsHeatmapData(chartsData),
                    reachChart: reachChartData
                        ? {
                              chartType: 'bar',
                              data: reachChartData,
                              options: horizontalBarChartOptions,
                              title: 'Охват конкурентов'
                          }
                        : null,
                    followersChart: followersChartData
                        ? {
                              chartType: 'bar',
                              data: followersChartData,
                              options: horizontalBarChartOptions,
                              title: 'Подписчики конкурентов'
                          }
                        : null
                }
            ];
        }
        // If it's an array with audienceSegmentation-like structure, process it
        if (chartsData.length > 0 && (chartsData[0]?.genders || chartsData[0]?.ageGroups)) {
            const { ageGroupsChartData, gendersChartData } = buildAudienceSegmentationChartData(chartsData[0]);
            if (ageGroupsChartData || gendersChartData) {
                return [
                    {
                        type: 'audienceSegmentation',
                        ageGroupsChartData,
                        gendersChartData,
                        segmentsChannelMatrix: buildSegmentsChannelMatrix(chartsData[0].segmentsChannelMatrix),
                        keyTakeaways: chartsData[0].keyTakeaways || []
                    }
                ];
            }
        }
        return [];
    }

    // Handle case when chartsData is an audienceSegmentation object directly
    // (has genders, ageGroups, segments, etc. but no audienceSegmentation property)
    if (chartsData.genders || chartsData.ageGroups || chartsData.segments) {
        const { ageGroupsChartData, gendersChartData } = buildAudienceSegmentationChartData(chartsData);
        if (ageGroupsChartData || gendersChartData) {
            return [
                {
                    type: 'audienceSegmentation',
                    ageGroupsChartData,
                    gendersChartData,
                    segmentsChannelMatrix: buildSegmentsChannelMatrix(chartsData.segmentsChannelMatrix),
                    keyTakeaways: chartsData.keyTakeaways || []
                }
            ];
        }
    }

    return mapChartsDataToSegments(chartsData);
});

// Main parsedContent that combines fullAnalysis with chartsData
const parsedContent = computed(() => {
    let segments = [];

    // Check for v2ReportNormalized competitive_environment first
    if (v2ReportNormalized.value?.sections?.competitive_environment) {
        const competitiveEnv = v2ReportNormalized.value.sections.competitive_environment;
        const processed = processCompetitiveEnvironmentData(competitiveEnv);
        if (processed) {
            segments.push(processed);
        }
    }

    // If we have both fullAnalysis and chartsData, parse fullAnalysis and inject charts
    if (report.value?.fullAnalysis && report.value?.chartsData) {
        const parsedSegments = parseFullAnalysisWithCharts(report.value.fullAnalysis, report.value.chartsData);
        segments = [...segments, ...parsedSegments];
    }
    // If only chartsData exists, use it
    else if (report.value?.chartsData) {
        const chartSegments = chartsDataSegments.value;
        segments = [...segments, ...chartSegments];
    }
    // Otherwise, fall back to parsing fullAnalysis with JSON blocks (for old data)
    else if (report.value?.fullAnalysis) {
        const content = report.value.fullAnalysis;
        // Regex for both ```json:identifier and plain ```json or ``` code blocks
        const regex = /```json:(\w+)\r?\n([\s\S]*?)\r?\n```|```json\r?\n([\s\S]*?)\r?\n```|```\r?\n([\s\S]*?)\r?\n```/g;
        let lastIndex = 0;
        let match;

        while ((match = regex.exec(content)) !== null) {
            const [fullMatch, identifier, jsonBlockWithId, jsonBlockPlain, codeBlock] = match;

            if (match.index > lastIndex) {
                const textBefore = content.slice(lastIndex, match.index);
                if (textBefore.trim()) {
                    // Keep text strictly in place; JSON blocks are handled by the regex loop.
                    pushMarkdownTokens(segments, textBefore);
                }
            }

            // Handle code blocks that might contain JSON
            if (codeBlock || jsonBlockPlain) {
                const jsonContent = codeBlock || jsonBlockPlain;
                // Try to parse as JSON and process
                const jsonSegment = tryParseJsonSegment(jsonContent);
                if (jsonSegment) {
                    segments.push(jsonSegment);
                } else {
                    // If not JSON, add as markdown code block
                    segments.push({ type: 'markdown', html: renderMarkdown(fullMatch), mdTokenType: 'code' });
                }
                lastIndex = regex.lastIndex;
                continue;
            }

            // Handle ```json:identifier blocks
            if (identifier && jsonBlockWithId) {
                let parsedData = null;
                try {
                    parsedData = JSON.parse(jsonBlockWithId);
                } catch (error) {
                    console.error(`Не удалось распарсить блок ${identifier}:`, error);
                }

                const segment = mapJsonBlockToSegment(identifier, parsedData, fullMatch);
                if (segment) {
                    segments.push(segment);
                }
            }

            lastIndex = regex.lastIndex;
        }

        const remaining = content.slice(lastIndex);
        if (remaining.trim()) {
            pushMarkdownTokens(segments, remaining);
        }
    }

    // Filter out any segments without a valid type and ensure all segments are properly formatted
    return segments.filter((segment) => {
        // If segment doesn't have a type, try to process it
        if (!segment || !segment.type) {
            // Check if it's new competitive environment structure
            if (segment && typeof segment === 'object' && !Array.isArray(segment)) {
                if (segment.competitors && Array.isArray(segment.competitors) && segment.metrics) {
                    const processed = processCompetitiveEnvironmentData(segment);
                    if (processed) {
                        segments[segments.indexOf(segment)] = processed;
                        return true;
                    }
                }
            }
            // If it's an array (like competitors), process it
            if (Array.isArray(segment) && segment.length > 0 && segment[0]?.name) {
                // Check if it's new structure (has visibility_score)
                if (segment[0]?.visibility_score !== undefined) {
                    const processed = processCompetitiveEnvironmentData({
                        competitors: segment,
                        metrics: {},
                        title: 'Конкурентная среда',
                        conclusion: ''
                    });
                    if (processed) {
                        segments[segments.indexOf(segment)] = processed;
                        return true;
                    }
                }
                // Old structure
                const processed = {
                    type: 'competitors',
                    competitors: segment,
                    competitorsHeatmap: buildCompetitorsHeatmapData(segment)
                };
                segments[segments.indexOf(segment)] = processed;
                return true;
            }
            // If it's an object with audienceSegmentation-like structure, process it
            if (segment && typeof segment === 'object' && (segment.genders || segment.ageGroups || segment.segments)) {
                const { ageGroupsChartData, gendersChartData } = buildAudienceSegmentationChartData(segment);
                if (ageGroupsChartData || gendersChartData) {
                    const processed = {
                        type: 'audienceSegmentation',
                        ageGroupsChartData,
                        gendersChartData,
                        segmentsChannelMatrix: buildSegmentsChannelMatrix(segment.segmentsChannelMatrix),
                        keyTakeaways: segment.keyTakeaways || []
                    };
                    segments[segments.indexOf(segment)] = processed;
                    return true;
                }
            }
            return false;
        }
        return true;
    });
});

// Layout segments: group adjacent "paragraph markdown" + (chart/marketShareChart/comparisonTable) into a two-column container.
const isParagraphMarkdownSegment = (segment) => {
    return segment?.type === 'markdown' && segment?.mdTokenType === 'paragraph';
};

const isPairableMediaSegment = (segment) => {
    return segment?.type === 'chart' || segment?.type === 'marketShareChart' || segment?.type === 'comparisonTable';
};

const displayContent = computed(() => {
    const input = parsedContent.value || [];
    const out = [];

    for (let i = 0; i < input.length; i++) {
        const cur = input[i];
        const next = input[i + 1];

        // Text then media
        if (isParagraphMarkdownSegment(cur) && isPairableMediaSegment(next)) {
            // Pull subsequent paragraph tokens into the same left column so text can continue
            // alongside a tall right-column chart/table (no float, still strictly in-flow).
            const texts = [cur];
            let j = i + 2;
            while (j < input.length && isParagraphMarkdownSegment(input[j])) {
                texts.push(input[j]);
                j++;
            }
            out.push({
                type: 'paired',
                texts,
                media: next,
                order: 'text-media'
            });
            i = j - 1; // consumed media + following paragraph(s)
            continue;
        }

        // Media then text
        if (isPairableMediaSegment(cur) && isParagraphMarkdownSegment(next)) {
            // IMPORTANT: do NOT pull many paragraphs when media is on the left.
            // Otherwise right column grows tall and leaves a visible blank area under left media (table/chart).
            const texts = [next];
            const j = i + 2;
            out.push({
                type: 'paired',
                texts,
                media: cur,
                order: 'media-text'
            });
            i = j - 1; // consumed media + single adjacent paragraph
            continue;
        }

        out.push(cur);
    }

    return out;
});

const toCompactChartOptions = (options) => {
    const base = options && typeof options === 'object' ? options : {};

    const basePlugins = base.plugins && typeof base.plugins === 'object' ? base.plugins : {};
    const baseLegend = basePlugins.legend && typeof basePlugins.legend === 'object' ? basePlugins.legend : {};
    const baseLegendLabels = baseLegend.labels && typeof baseLegend.labels === 'object' ? baseLegend.labels : {};

    // Keep "legend.display: false" if it was explicitly turned off
    const legendDisplay = typeof baseLegend.display === 'boolean' ? baseLegend.display : true;

    const compact = {
        ...base,
        responsive: true,
        // For this request: keep aspect ratio behavior, but make it visually compact via aspectRatio + CSS max-height
        maintainAspectRatio: true,
        aspectRatio: typeof base.aspectRatio === 'number' ? base.aspectRatio : 3,
        layout: {
            ...(base.layout && typeof base.layout === 'object' ? base.layout : {}),
            padding: 0
        },
        plugins: {
            ...basePlugins,
            legend: {
                ...baseLegend,
                display: legendDisplay,
                // Avoid legend eating vertical space in compact mode
                position: 'bottom',
                align: 'center',
                labels: {
                    ...baseLegendLabels,
                    padding: 6,
                    boxWidth: 10,
                    boxHeight: 10,
                    usePointStyle: true,
                    font: {
                        ...(baseLegendLabels.font && typeof baseLegendLabels.font === 'object' ? baseLegendLabels.font : {}),
                        size: 10
                    }
                }
            }
        }
    };

    // Compact axis labels/ticks if scales exist
    if (compact.scales && typeof compact.scales === 'object') {
        const nextScales = { ...compact.scales };
        for (const axisKey of Object.keys(nextScales)) {
            const axis = nextScales[axisKey];
            if (!axis || typeof axis !== 'object') continue;
            const ticks = axis.ticks && typeof axis.ticks === 'object' ? axis.ticks : {};
            const title = axis.title && typeof axis.title === 'object' ? axis.title : {};

            nextScales[axisKey] = {
                ...axis,
                ticks: {
                    ...ticks,
                    autoSkip: typeof ticks.autoSkip === 'boolean' ? ticks.autoSkip : true,
                    maxRotation: typeof ticks.maxRotation === 'number' ? ticks.maxRotation : 0,
                    padding: 4,
                    font: {
                        ...(ticks.font && typeof ticks.font === 'object' ? ticks.font : {}),
                        size: 10
                    }
                },
                title: {
                    ...title,
                    padding: typeof title.padding !== 'undefined' ? title.padding : 4,
                    font: {
                        ...(title.font && typeof title.font === 'object' ? title.font : {}),
                        size: 11
                    }
                }
            };
        }
        compact.scales = nextScales;
    }

    return compact;
};

// Get analysis type label
const getAnalysisTypeLabel = (type) => {
    const labels = {
        РЫНОК: 'Анализ внешней среды',
        КОНКУРЕНТЫ: 'Анализ конкурентов',
        ЦА: 'Анализ целевой аудитории',
        КАНАЛЫ: 'Анализ рекламных каналов',
        SWOT: 'SWOT-анализ'
    };
    return labels[type] || type;
};

// Format date time
const formatDateTime = (dateString) => {
    if (!dateString) return '';
    const date = new Date(dateString);
    date.setHours(date.getHours() + 5);
    return date.toLocaleString('ru-RU', {
        year: 'numeric',
        month: 'long',
        day: 'numeric',
        hour: '2-digit',
        minute: '2-digit'
    });
};

// Navigate to strategy page
const goToStrategy = () => {
    if (analysisId.value) {
        router.push({
            name: 'marketing-promotion',
            query: { analysisId: analysisId.value }
        });
    } else {
        toast.add({
            severity: 'warn',
            summary: 'Предупреждение',
            detail: 'ID анализа не найден',
            life: 3000
        });
    }
};

// Competitive Environment: Chart and Table Synchronization
const highlightedRowIndex = ref(null);
const visibilityChartRef = ref(null);

const highlightRow = (index) => {
    highlightedRowIndex.value = index;
    // Highlight corresponding bar in chart if chart is available
    if (visibilityChartRef.value && visibilityChartRef.value.chart && index !== null) {
        const chart = visibilityChartRef.value.chart;
        const meta = chart.getDatasetMeta(0);
        if (meta && meta.data[index]) {
            // Reset all bars
            meta.data.forEach((bar) => {
                bar._model.backgroundColor = bar._view.backgroundColor;
            });
            // Highlight the hovered bar
            const hoveredBar = meta.data[index];
            if (hoveredBar) {
                const originalColor = hoveredBar._view.backgroundColor;
                hoveredBar._model.backgroundColor = originalColor + 'CC'; // Add transparency
                chart.update('none');
            }
        }
    }
};

const onChartHover = (event, elements) => {
    if (elements && elements.length > 0) {
        const elementIndex = elements[0].index;
        highlightedRowIndex.value = elementIndex;
    }
};

const onChartClick = (event, elements) => {
    if (elements && elements.length > 0) {
        const elementIndex = elements[0].index;
        // Could trigger some action on click
    }
};

const handleRowClick = (competitor) => {
    if (competitor.website) {
        let url = competitor.website.trim();
        // If URL doesn't start with http:// or https://, add https://
        if (!url.match(/^https?:\/\//i)) {
            url = 'https://' + url;
        }
        window.open(url, '_blank', 'noopener,noreferrer');
    }
};

const getFullUrl = (url) => {
    if (!url) return '';
    const trimmed = url.trim();
    // If URL doesn't start with http:// or https://, add https://
    if (!trimmed.match(/^https?:\/\//i)) {
        return 'https://' + trimmed;
    }
    return trimmed;
};

const formatWebsite = (url) => {
    if (!url) return '';
    const trimmed = url.trim();
    try {
        // If it's already a full URL, parse it
        if (trimmed.match(/^https?:\/\//i)) {
            const urlObj = new URL(trimmed);
            return urlObj.hostname.replace('www.', '');
        }
        // Otherwise, just return the domain part (before first /)
        const domain = trimmed.split('/')[0];
        return domain.replace('www.', '');
    } catch {
        // If parsing fails, return as is (might be just domain name)
        return trimmed.split('/')[0].replace('www.', '');
    }
};

const getScoreClass = (score) => {
    if (score >= 70) return 'competitive-env-score-high';
    if (score >= 40) return 'competitive-env-score-medium';
    return 'competitive-env-score-low';
};

const getPriceSegmentSeverity = (segment) => {
    const segmentLower = (segment || '').toLowerCase();
    if (segmentLower.includes('premium') || segmentLower.includes('высок') || segmentLower.includes('премиум')) {
        return 'danger';
    }
    if (segmentLower.includes('low') || segmentLower.includes('низк')) {
        return 'success';
    }
    return 'warning';
};

// Load analysis from query params
onMounted(async () => {
    const queryAnalysisId = route.query.analysisId;
    const queryV2AnalysisId = route.query.v2AnalysisId;
    if (queryAnalysisId) {
        // Try to load existing analysis
        try {
            analysisId.value = queryAnalysisId;
            const result = await MarketingService.getAnalysisResult(queryAnalysisId);
            const isV2 = isV2ReportPayload(result);
            if (isV2) {
                applyV2Report(result);
                status.value = 'completed';
            } else if (result) {
                status.value = result.status;

                // Сохраняем тип анализа, если он есть
                if (result.analysisType) {
                    currentAnalysisType.value = result.analysisType;
                }

                if (result.status === 'completed' && result.report) {
                    report.value = result.report;
                } else if (result.status === 'processing' || result.status === 'queued') {
                    estimatedCompletionTime.value = result.estimatedCompletionTime;
                    startPolling(queryAnalysisId);
                }

                // v2 restore:
                // 1) from query param
                // 2) fallback to /analysis/my lookup (docs say v2AnalysisId is present there)
                if (queryV2AnalysisId) {
                    v2AnalysisId.value = String(queryV2AnalysisId);
                    await refreshV2();
                } else {
                    try {
                        const list = await MarketingService.getMyAnalyses();
                        const found = Array.isArray(list) ? list.find((a) => a?.analysisId === queryAnalysisId) : null;
                        if (found?.v2AnalysisId) {
                            v2AnalysisId.value = found.v2AnalysisId;
                            router.replace({ query: { ...route.query, v2AnalysisId: v2AnalysisId.value } });
                            await refreshV2();
                        }
                    } catch (_) {
                        // ignore v2 restore errors; old analysis page must keep working
                    }
                }
            }
        } catch (error) {
            console.error('Ошибка при загрузке анализа:', error);
            toast.add({
                severity: 'error',
                summary: 'Ошибка',
                detail: error.message || 'Не удалось загрузить анализ',
                life: 5000
            });
        }
    }
});

// Cleanup on unmount
onBeforeUnmount(() => {
    stopPolling();
});
</script>

<template>
    <div class="marketing-analysis-page bg-surface-50 dark:bg-surface-900 min-h-screen p-6">
        <Toast />
        <div class="max-w-[1200px] mx-auto">
            <Message severity="warn" class="mb-4" :closable="false">
                <strong>Внимание:</strong> Эта версия маркетингового анализа (V1/V2) устарела. Рекомендуется использовать <router-link to="/marketing-analysis/v3" class="font-bold underline text-primary">версию V3</router-link> для получения более
                точных и современных данных.
            </Message>
            <!-- Форма запуска анализа -->
            <div v-if="!analysisId" class="card">
                <div class="card-header mb-4">
                    <h2 class="text-2xl font-bold text-surface-900 dark:text-surface-0">Запуск анализа</h2>
                </div>
                <div class="card-content">
                    <form @submit.prevent="handleSubmit" class="space-y-4 max-w-2xl">
                        <div class="field">
                            <label for="businessNiche" class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Ниша бизнеса * </label>
                            <InputText id="businessNiche" v-model="formData.businessNiche" placeholder="Например: E-commerce платформы" class="w-full" :class="{ 'p-invalid': errors.businessNiche }" />
                            <small v-if="errors.businessNiche" class="p-error">{{ errors.businessNiche }}</small>
                        </div>

                        <div class="field">
                            <label for="product" class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Что вы продаете? * </label>
                            <InputText id="product" v-model="formData.product" placeholder="Введите название продукта или услуги" class="w-full" :class="{ 'p-invalid': errors.product }" />
                            <small v-if="errors.product" class="p-error">{{ errors.product }}</small>
                        </div>

                        <div class="field">
                            <label class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Целевая аудитория * </label>

                            <!-- Гендер -->
                            <div class="mb-3">
                                <label class="block text-sm font-medium mb-2 text-surface-600 dark:text-surface-400">Гендер:</label>
                                <div class="flex gap-4 flex-wrap">
                                    <div v-for="gender in VALID_GENDERS" :key="gender" class="flex align-items-center">
                                        <Checkbox :inputId="`gender-${gender}`" :value="gender" v-model="formData.targetAudience.genders" />
                                        <label :for="`gender-${gender}`" class="ml-2 cursor-pointer">{{ gender }}</label>
                                    </div>
                                </div>
                            </div>

                            <!-- Возраст -->
                            <div class="mb-3">
                                <label class="block text-sm font-medium mb-2 text-surface-600 dark:text-surface-400">Возраст:</label>
                                <div class="flex gap-4 flex-wrap">
                                    <div v-for="age in VALID_AGE_RANGES" :key="age" class="flex align-items-center">
                                        <Checkbox :inputId="`age-${age}`" :value="age" v-model="formData.targetAudience.ageRanges" />
                                        <label :for="`age-${age}`" class="ml-2 cursor-pointer">{{ age }}</label>
                                    </div>
                                </div>
                            </div>

                            <!-- Тип -->
                            <div class="mb-3">
                                <label class="block text-sm font-medium mb-2 text-surface-600 dark:text-surface-400">Тип:</label>
                                <div class="flex gap-4 flex-wrap">
                                    <div v-for="type in VALID_AUDIENCE_TYPES" :key="type" class="flex align-items-center">
                                        <Checkbox :inputId="`type-${type}`" :value="type" v-model="formData.targetAudience.types" />
                                        <label :for="`type-${type}`" class="ml-2 cursor-pointer">{{ type }}</label>
                                    </div>
                                </div>
                            </div>

                            <!-- Отображение выбранных значений -->
                            <div v-if="formData.targetAudience.genders.length > 0 || formData.targetAudience.ageRanges.length > 0 || formData.targetAudience.types.length > 0" class="mt-2 p-2 border-round bg-surface-100 dark:bg-surface-800">
                                <small class="text-surface-600 dark:text-surface-400">
                                    <strong>Выбрано:</strong>
                                    <span v-if="formData.targetAudience.genders.length > 0"> Гендер: {{ formData.targetAudience.genders.join(', ') }}</span>
                                    <span v-if="formData.targetAudience.ageRanges.length > 0"> Возраст: {{ formData.targetAudience.ageRanges.join(', ') }}</span>
                                    <span v-if="formData.targetAudience.types.length > 0"> Тип: {{ formData.targetAudience.types.join(', ') }}</span>
                                </small>
                            </div>

                            <small v-if="errors.targetAudience" class="p-error">{{ errors.targetAudience }}</small>
                            <small class="text-surface-500 dark:text-surface-400 mt-1 block">Выберите хотя бы одну опцию для целевой аудитории</small>
                        </div>

                        <div class="field">
                            <label for="region" class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Регион (город Казахстана) * </label>
                            <MultiSelect id="region" v-model="formData.region" :options="VALID_REGIONS" placeholder="Выберите регионы" class="w-full" display="chip" :class="{ 'p-invalid': errors.region }" />
                            <small v-if="errors.region" class="p-error">{{ errors.region }}</small>
                            <small class="text-surface-500 dark:text-surface-400 mt-1 block">Выберите один или несколько регионов</small>
                        </div>

                        <div class="field">
                            <label for="goal" class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Цель на 6-12 месяцев * </label>
                            <Textarea id="goal" v-model="formData.goal" placeholder="Опишите вашу цель на ближайшие 6-12 месяцев" rows="3" class="w-full" :class="{ 'p-invalid': errors.goal }" />
                            <small v-if="errors.goal" class="p-error">{{ errors.goal }}</small>
                        </div>

                        <div class="field">
                            <label class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Уровень детализации анализа * </label>
                            <div class="flex gap-4">
                                <div v-for="level in DETAIL_LEVELS" :key="level" class="flex align-items-center">
                                    <RadioButton :inputId="`detailLevel-${level}`" v-model="formData.detailLevel" :value="level" :class="{ 'p-invalid': errors.detailLevel }" />
                                    <label :for="`detailLevel-${level}`" class="ml-2 cursor-pointer">
                                        {{ level === 'КРАТКО' ? 'Кратко' : level === 'СТАНДАРТНО' ? 'Стандартно' : 'Подробно' }}
                                    </label>
                                </div>
                            </div>
                            <small v-if="errors.detailLevel" class="p-error">{{ errors.detailLevel }}</small>
                            <small class="text-surface-500 dark:text-surface-400 mt-1 block">Выберите уровень детализации анализа</small>
                        </div>

                        <div class="field">
                            <label for="strongSide" class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Сильная сторона бизнеса </label>
                            <Textarea id="strongSide" v-model="formData.strongSide" placeholder="Опишите сильные стороны вашего бизнеса (опционально)" rows="2" class="w-full" :class="{ 'p-invalid': errors.strongSide }" />
                            <small v-if="errors.strongSide" class="p-error">{{ errors.strongSide }}</small>
                        </div>

                        <div class="field">
                            <label for="weakSide" class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Слабая сторона бизнеса </label>
                            <Textarea id="weakSide" v-model="formData.weakSide" placeholder="Опишите слабые стороны вашего бизнеса (опционально)" rows="2" class="w-full" :class="{ 'p-invalid': errors.weakSide }" />
                            <small v-if="errors.weakSide" class="p-error">{{ errors.weakSide }}</small>
                        </div>

                        <!-- <div class="field">
                            <label for="marketingBudget" class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Бюджет на маркетинг </label>
                            <InputNumber id="marketingBudget" v-model="formData.marketingBudget" :min="0" placeholder="Введите бюджет в тенге" class="w-full" :class="{ 'p-invalid': errors.marketingBudget }" />
                            <small v-if="errors.marketingBudget" class="p-error">{{ errors.marketingBudget }}</small>
                            <small class="text-surface-500 dark:text-surface-400 mt-1 block">Укажите ваш бюджет на маркетинг (опционально)</small>
                        </div> -->

                        <div class="field">
                            <label for="analysisType" class="block text-sm font-medium mb-2 text-surface-700 dark:text-surface-300"> Тип анализа * </label>
                            <MultiSelect id="analysisType" v-model="formData.analysisType" :options="VALID_ANALYSIS_TYPES" placeholder="Выберите типы анализа" class="w-full" display="chip" :class="{ 'p-invalid': errors.analysisType }">
                                <template #value="slotProps">
                                    <div v-if="slotProps.value && slotProps.value.length > 0" class="flex flex-wrap gap-2">
                                        <Tag v-for="type in slotProps.value" :key="type" :value="getAnalysisTypeLabel(type)" severity="info" />
                                    </div>
                                    <span v-else class="text-surface-400">{{ slotProps.placeholder }}</span>
                                </template>
                                <template #option="slotProps">
                                    <div class="flex align-items-center">
                                        <span>{{ getAnalysisTypeLabel(slotProps.option) }}</span>
                                    </div>
                                </template>
                            </MultiSelect>
                            <small v-if="errors.analysisType" class="p-error">{{ errors.analysisType }}</small>
                            <small class="text-surface-500 dark:text-surface-400 mt-1 block">Выберите один или несколько типов анализа. При выборе нескольких типов будут созданы отдельные анализы для каждого типа.</small>
                        </div>

                        <Button type="submit" label="Начать анализ" icon="pi pi-send" class="w-full p-button-primary" :loading="submitting" />

                        <p class="text-sm text-surface-500 dark:text-surface-400 mt-3 text-center">На основе ваших ответов будет создан подробный и полезный маркетинговый отчет</p>
                    </form>
                </div>
            </div>

            <!-- Единая страница: v2 dashboard сверху + старый анализ ниже -->
            <div v-else class="space-y-4">
                <!-- v2 Dashboard (показываем первым) -->
                <div v-if="v2Loading || v2ReportNormalized" class="card">
                    <div class="card-content">
                        <MarketingAnalysisPptDashboard embedded :report="v2ReportNormalized" :loading="v2Loading" :error="v2Error" />
                    </div>
                </div>

                <!-- Статус обработки (старый анализ) -->
                <div v-if="status === 'processing' || status === 'queued'" class="space-y-4">
                    <!-- Заголовок с кнопкой -->
                    <div class="card">
                        <div class="card-header mb-4">
                            <div class="flex flex-wrap justify-content-between align-items-center gap-3">
                                <div class="flex-1 min-w-0">
                                    <h2 class="text-2xl font-bold text-surface-900 dark:text-surface-0">Анализ выполняется</h2>
                                </div>
                                <div class="flex gap-2 align-items-center flex-shrink-0">
                                    <Button :label="isAnalysisOpen ? 'Скрыть анализ' : 'Показать анализ'" :icon="isAnalysisOpen ? 'pi pi-chevron-up' : 'pi pi-chevron-down'" severity="secondary" outlined @click="isAnalysisOpen = !isAnalysisOpen" />
                                </div>
                            </div>
                        </div>
                    </div>

                    <div v-show="isAnalysisOpen" class="card">
                        <div class="card-content">
                            <div class="text-center py-6">
                                <ProgressSpinner size="50" />
                                <p class="mt-4 text-lg text-surface-700 dark:text-surface-300">Анализ обрабатывается...</p>
                                <p class="mt-2 text-sm text-surface-500 dark:text-surface-400">Это может занять 5-10 минут. Пожалуйста, подождите.</p>
                                <p v-if="estimatedCompletionTime" class="mt-2 text-sm text-surface-500 dark:text-surface-400">Ожидаемое время завершения: {{ formatDateTime(estimatedCompletionTime) }}</p>
                                <Button label="Отменить" icon="pi pi-times" severity="secondary" class="mt-4" @click="resetAnalysis" />
                            </div>
                        </div>
                    </div>
                </div>

                <!-- Ошибка -->
                <div v-else-if="status === 'failed'" class="card">
                    <div class="card-header mb-4">
                        <h2 class="text-2xl font-bold text-surface-900 dark:text-surface-0">Ошибка анализа</h2>
                    </div>
                    <div class="card-content">
                        <div class="text-center py-6">
                            <i class="pi pi-exclamation-triangle text-6xl text-red-500 mb-3"></i>
                            <p class="mt-4 text-lg text-surface-700 dark:text-surface-300">Анализ завершился с ошибкой</p>
                            <p class="mt-2 text-sm text-surface-500 dark:text-surface-400">Попробуйте запустить анализ снова или обратитесь в поддержку.</p>
                            <Button label="Попробовать снова" icon="pi pi-refresh" class="mt-4" @click="resetAnalysis" />
                        </div>
                    </div>
                </div>

                <!-- Результаты анализа -->
                <div v-else-if="status === 'completed' && report" class="space-y-4">
                    <!-- Заголовок с кнопкой скачивания -->
                    <div class="card">
                        <div class="card-header mb-4">
                            <div class="flex flex-wrap justify-content-between align-items-center gap-3">
                                <div class="flex-1 min-w-0">
                                    <h2 class="text-2xl font-bold text-surface-900 dark:text-surface-0">Результаты анализа</h2>
                                    <div v-if="currentAnalysisType" class="mt-2">
                                        <Tag :value="getAnalysisTypeLabel(currentAnalysisType)" severity="info" />
                                    </div>
                                </div>
                                <div class="flex gap-2 align-items-center flex-shrink-0">
                                    <Button :label="isAnalysisOpen ? 'Скрыть анализ' : 'Показать анализ'" :icon="isAnalysisOpen ? 'pi pi-chevron-up' : 'pi pi-chevron-down'" severity="secondary" outlined @click="isAnalysisOpen = !isAnalysisOpen" />
                                    <Button label="Скачать PDF" icon="pi pi-download" @click="handleDownloadPdf" :loading="downloadingPdf" />
                                </div>
                            </div>
                        </div>
                    </div>

                    <div v-show="isAnalysisOpen" class="space-y-4">
                        <!-- Краткое резюме (Summary) -->
                        <div v-if="report.summary" class="card">
                            <div class="card-header mb-4">
                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-file-edit mr-2"></i>Краткое резюме</h3>
                            </div>
                            <div class="card-content">
                                <div class="markdown-content" v-html="renderMarkdown(report.summary)"></div>
                            </div>
                        </div>

                        <!-- Динамическое содержимое отчета (в одном контейнере) -->
                        <div v-if="parsedContent.length" class="card">
                            <div class="card-content">
                                <div class="space-y-6">
                                    <div v-for="(segment, index) in displayContent" :key="index">
                                        <!-- Two-column pair: paragraph text + adjacent json-chart/table -->
                                        <div v-if="segment.type === 'paired'" class="report-pair">
                                            <!-- IMPORTANT: preserve original markdown order in DOM -->
                                            <template v-if="segment.order === 'text-media'">
                                                <div class="report-pair__text">
                                                    <div class="report-pair__textStack">
                                                        <div v-for="(t, tIdx) in segment.texts || []" :key="tIdx" class="markdown-content" v-html="t.html"></div>
                                                    </div>
                                                </div>

                                                <div class="report-pair__media">
                                                    <div v-if="segment.media.type === 'chart'">
                                                        <div class="report-pair__mediaChart">
                                                            <div class="chart-container report-pair__chart-container">
                                                                <Chart v-if="hasRenderableChartData(segment.media.data)" :type="segment.media.chartType" :data="segment.media.data" :options="toCompactChartOptions(segment.media.options)" />
                                                                <div v-else class="p-3 border-round text-center text-surface-500 dark:text-surface-400">Нет данных для отображения</div>
                                                            </div>
                                                            <div v-if="segment.media.title" class="chart-caption text-surface-700 dark:text-surface-300">{{ segment.media.title }}</div>
                                                        </div>
                                                        <div v-if="segment.media.key === 'channelsPotential' && segment.media.channels?.length" class="mt-4 space-y-2">
                                                            <div v-for="channel in segment.media.channels" :key="channel.name" class="p-3 border-round bg-surface-50 dark:bg-surface-800">
                                                                <div class="flex justify-content-between align-items-center mb-2">
                                                                    <span class="font-semibold text-surface-900 dark:text-surface-0">{{ channel.name }}</span>
                                                                    <Tag :value="`Потенциал: ${channel.potential}`" :severity="channel.potential >= 80 ? 'success' : channel.potential >= 60 ? 'warning' : 'info'" />
                                                                </div>
                                                                <p class="text-sm text-surface-600 dark:text-surface-400">{{ channel.justification }}</p>
                                                            </div>
                                                        </div>
                                                    </div>

                                                    <div v-else-if="segment.media.type === 'marketShareChart'">
                                                        <div class="report-pair__mediaChart">
                                                            <div class="chart-container report-pair__chart-container">
                                                                <Chart v-if="hasRenderableChartData(segment.media.data)" :type="segment.media.chartType" :data="segment.media.data" :options="toCompactChartOptions(segment.media.options)" />
                                                                <div v-else class="p-3 border-round text-center text-surface-500 dark:text-surface-400">Нет данных для отображения</div>
                                                            </div>
                                                            <div v-if="segment.media.title" class="chart-caption text-surface-700 dark:text-surface-300">{{ segment.media.title }}</div>
                                                        </div>
                                                    </div>

                                                    <div v-else-if="segment.media.type === 'comparisonTable'">
                                                        <div class="mb-4">
                                                            <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-table mr-2"></i>Сравнительная таблица</h3>
                                                        </div>
                                                        <div class="overflow-x-auto border-round" style="border: 1px solid var(--surface-border)">
                                                            <table class="comparison-table w-full border-collapse">
                                                                <thead>
                                                                    <tr>
                                                                        <th class="comparison-table-th">Характеристика</th>
                                                                        <th class="comparison-table-th text-center">Мы</th>
                                                                        <th class="comparison-table-th text-center">Конкурент A</th>
                                                                        <th class="comparison-table-th text-center">Конкурент B</th>
                                                                    </tr>
                                                                </thead>
                                                                <tbody>
                                                                    <tr v-for="(row, idx) in segment.media.data" :key="idx" class="comparison-table-tr">
                                                                        <td class="comparison-table-td font-semibold">{{ row.feature }}</td>
                                                                        <td class="comparison-table-td text-center">
                                                                            <Tag :value="row.us" severity="info" />
                                                                        </td>
                                                                        <td class="comparison-table-td text-center">
                                                                            <Tag :value="row.compA" :severity="row.compA === 'Высокая' || row.compA === 'Премиум' ? 'danger' : row.compA === 'Низкая' ? 'success' : 'warning'" />
                                                                        </td>
                                                                        <td class="comparison-table-td text-center">
                                                                            <Tag :value="row.compB" :severity="row.compB === 'Высокая' || row.compB === 'Премиум' ? 'danger' : row.compB === 'Низкая' ? 'success' : 'warning'" />
                                                                        </td>
                                                                    </tr>
                                                                </tbody>
                                                            </table>
                                                        </div>
                                                    </div>
                                                </div>
                                            </template>

                                            <template v-else>
                                                <div class="report-pair__media">
                                                    <div v-if="segment.media.type === 'chart'">
                                                        <div class="report-pair__mediaChart">
                                                            <div class="chart-container report-pair__chart-container">
                                                                <Chart v-if="hasRenderableChartData(segment.media.data)" :type="segment.media.chartType" :data="segment.media.data" :options="toCompactChartOptions(segment.media.options)" />
                                                                <div v-else class="p-3 border-round text-center text-surface-500 dark:text-surface-400">Нет данных для отображения</div>
                                                            </div>
                                                            <div v-if="segment.media.title" class="chart-caption text-surface-700 dark:text-surface-300">{{ segment.media.title }}</div>
                                                        </div>
                                                        <div v-if="segment.media.key === 'channelsPotential' && segment.media.channels?.length" class="mt-4 space-y-2">
                                                            <div v-for="channel in segment.media.channels" :key="channel.name" class="p-3 border-round bg-surface-50 dark:bg-surface-800">
                                                                <div class="flex justify-content-between align-items-center mb-2">
                                                                    <span class="font-semibold text-surface-900 dark:text-surface-0">{{ channel.name }}</span>
                                                                    <Tag :value="`Потенциал: ${channel.potential}`" :severity="channel.potential >= 80 ? 'success' : channel.potential >= 60 ? 'warning' : 'info'" />
                                                                </div>
                                                                <p class="text-sm text-surface-600 dark:text-surface-400">{{ channel.justification }}</p>
                                                            </div>
                                                        </div>
                                                    </div>

                                                    <div v-else-if="segment.media.type === 'marketShareChart'">
                                                        <div class="report-pair__mediaChart">
                                                            <div class="chart-container report-pair__chart-container">
                                                                <Chart v-if="hasRenderableChartData(segment.media.data)" :type="segment.media.chartType" :data="segment.media.data" :options="toCompactChartOptions(segment.media.options)" />
                                                                <div v-else class="p-3 border-round text-center text-surface-500 dark:text-surface-400">Нет данных для отображения</div>
                                                            </div>
                                                            <div v-if="segment.media.title" class="chart-caption text-surface-700 dark:text-surface-300">{{ segment.media.title }}</div>
                                                        </div>
                                                    </div>

                                                    <div v-else-if="segment.media.type === 'comparisonTable'">
                                                        <div class="mb-4">
                                                            <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-table mr-2"></i>Сравнительная таблица</h3>
                                                        </div>
                                                        <div class="overflow-x-auto border-round" style="border: 1px solid var(--surface-border)">
                                                            <table class="comparison-table w-full border-collapse">
                                                                <thead>
                                                                    <tr>
                                                                        <th class="comparison-table-th">Характеристика</th>
                                                                        <th class="comparison-table-th text-center">Мы</th>
                                                                        <th class="comparison-table-th text-center">Конкурент A</th>
                                                                        <th class="comparison-table-th text-center">Конкурент B</th>
                                                                    </tr>
                                                                </thead>
                                                                <tbody>
                                                                    <tr v-for="(row, idx) in segment.media.data" :key="idx" class="comparison-table-tr">
                                                                        <td class="comparison-table-td font-semibold">{{ row.feature }}</td>
                                                                        <td class="comparison-table-td text-center">
                                                                            <Tag :value="row.us" severity="info" />
                                                                        </td>
                                                                        <td class="comparison-table-td text-center">
                                                                            <Tag :value="row.compA" :severity="row.compA === 'Высокая' || row.compA === 'Премиум' ? 'danger' : row.compA === 'Низкая' ? 'success' : 'warning'" />
                                                                        </td>
                                                                        <td class="comparison-table-td text-center">
                                                                            <Tag :value="row.compB" :severity="row.compB === 'Высокая' || row.compB === 'Премиум' ? 'danger' : row.compB === 'Низкая' ? 'success' : 'warning'" />
                                                                        </td>
                                                                    </tr>
                                                                </tbody>
                                                            </table>
                                                        </div>
                                                    </div>
                                                </div>

                                                <div class="report-pair__text">
                                                    <div class="report-pair__textStack">
                                                        <div v-for="(t, tIdx) in segment.texts || []" :key="tIdx" class="markdown-content" v-html="t.html"></div>
                                                    </div>
                                                </div>
                                            </template>
                                        </div>

                                        <div v-else-if="segment.type === 'markdown'">
                                            <div class="markdown-content" v-html="segment.html"></div>
                                        </div>

                                        <div v-else-if="segment.type === 'chart'">
                                            <div class="chart-container" :style="segment.chartHeight">
                                                <Chart v-if="hasRenderableChartData(segment.data)" :type="segment.chartType" :data="segment.data" :options="segment.options" />
                                                <div v-else class="p-3 border-round text-center text-surface-500 dark:text-surface-400">Нет данных для отображения</div>
                                            </div>
                                            <div v-if="segment.title" class="chart-caption text-surface-700 dark:text-surface-300">{{ segment.title }}</div>
                                            <div v-if="segment.key === 'channelsPotential' && segment.channels?.length" class="mt-4 space-y-2">
                                                <div v-for="channel in segment.channels" :key="channel.name" class="p-3 border-round bg-surface-50 dark:bg-surface-800">
                                                    <div class="flex justify-content-between align-items-center mb-2">
                                                        <span class="font-semibold text-surface-900 dark:text-surface-0">{{ channel.name }}</span>
                                                        <Tag :value="`Потенциал: ${channel.potential}`" :severity="channel.potential >= 80 ? 'success' : channel.potential >= 60 ? 'warning' : 'info'" />
                                                    </div>
                                                    <p class="text-sm text-surface-600 dark:text-surface-400">{{ channel.justification }}</p>
                                                </div>
                                            </div>
                                        </div>

                                        <div v-else-if="segment.type === 'audienceSegmentation'">
                                            <div class="mb-4">
                                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-users mr-2"></i>Сегментация целевой аудитории</h3>
                                            </div>
                                            <div class="grid">
                                                <div v-if="segment.ageGroupsChartData" class="col-12 md:col-6 mb-4">
                                                    <div class="flex align-items-center mb-3">
                                                        <i class="pi pi-calendar text-primary-500 mr-2"></i>
                                                        <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">По возрасту</h4>
                                                    </div>
                                                    <div class="chart-container" style="height: 300px">
                                                        <Chart type="pie" :data="segment.ageGroupsChartData" :options="pieChartOptions" />
                                                    </div>
                                                </div>
                                                <div v-if="segment.gendersChartData" class="col-12 md:col-6 mb-4">
                                                    <div class="flex align-items-center mb-3">
                                                        <i class="pi pi-user text-primary-500 mr-2"></i>
                                                        <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">По полу</h4>
                                                    </div>
                                                    <div class="chart-container" style="height: 300px">
                                                        <Chart type="pie" :data="segment.gendersChartData" :options="pieChartOptions" />
                                                    </div>
                                                </div>
                                            </div>

                                            <!-- Segments Channel Matrix (Heatmap) -->
                                            <SegmentsChannelMatrixHeatmap v-if="segment.segmentsChannelMatrix" :matrix="segment.segmentsChannelMatrix" />

                                            <!-- Key Takeaways -->
                                            <div v-if="segment.keyTakeaways && segment.keyTakeaways.length > 0" class="mt-6">
                                                <div class="flex align-items-center mb-3">
                                                    <i class="pi pi-lightbulb text-primary-500 mr-2"></i>
                                                    <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">Ключевые выводы</h4>
                                                </div>
                                                <div class="p-4 border-round bg-primary-50 dark:bg-primary-900 border-1 border-primary-200 dark:border-primary-700">
                                                    <ul class="list-none p-0 m-0">
                                                        <li v-for="(takeaway, idx) in segment.keyTakeaways" :key="idx" class="flex align-items-start mb-3">
                                                            <i class="pi pi-check-circle text-primary-500 mr-2 mt-1 flex-shrink-0"></i>
                                                            <span class="text-surface-700 dark:text-surface-300">{{ takeaway }}</span>
                                                        </li>
                                                    </ul>
                                                </div>
                                            </div>
                                        </div>

                                        <div v-else-if="segment.type === 'segmentsChannelMatrix'">
                                            <HeatmapTable :matrix="segment.matrix" :title="segment.title || 'Матрица каналов по сегментам'" />
                                        </div>

                                        <!-- New Competitive Environment Component -->
                                        <div v-else-if="segment.type === 'competitiveEnvironment'">
                                            <div class="mb-6">
                                                <h3 class="text-2xl font-semibold text-surface-900 dark:text-surface-0 mb-4"><i class="pi pi-chart-line mr-2 text-primary-500"></i>{{ segment.title || 'Конкурентная среда' }}</h3>

                                                <!-- Metrics KPI Cards -->
                                                <div v-if="segment.metrics" class="grid mb-6">
                                                    <div class="col-12 md:col-3 mb-3">
                                                        <div class="p-4 border-round bg-surface-0 dark:bg-surface-800 border-1 border-surface-200 dark:border-surface-700 h-full">
                                                            <div class="flex align-items-center mb-2">
                                                                <i class="pi pi-sitemap text-primary-500 mr-2 text-xl"></i>
                                                                <span class="text-sm font-medium text-surface-600 dark:text-surface-400">Доля лидера</span>
                                                            </div>
                                                            <div class="text-2xl font-bold text-surface-900 dark:text-surface-0">
                                                                {{ segment.metrics.leader_market_share || '—' }}
                                                            </div>
                                                            <div v-if="segment.metrics.market_leader_name" class="text-xs text-surface-500 dark:text-surface-400 mt-1">
                                                                {{ segment.metrics.market_leader_name }}
                                                            </div>
                                                        </div>
                                                    </div>
                                                    <div class="col-12 md:col-3 mb-3">
                                                        <div class="p-4 border-round bg-surface-0 dark:bg-surface-800 border-1 border-surface-200 dark:border-surface-700 h-full">
                                                            <div class="flex align-items-center mb-2">
                                                                <i class="pi pi-chart-bar text-green-500 mr-2 text-xl"></i>
                                                                <span class="text-sm font-medium text-surface-600 dark:text-surface-400">Уровень конкуренции</span>
                                                            </div>
                                                            <div class="text-2xl font-bold text-surface-900 dark:text-surface-0">
                                                                {{ segment.metrics.competition_level || '—' }}
                                                            </div>
                                                        </div>
                                                    </div>
                                                    <div class="col-12 md:col-3 mb-3">
                                                        <div class="p-4 border-round bg-surface-0 dark:bg-surface-800 border-1 border-surface-200 dark:border-surface-700 h-full">
                                                            <div class="flex align-items-center mb-2">
                                                                <i class="pi pi-wallet text-orange-500 mr-2 text-xl"></i>
                                                                <span class="text-sm font-medium text-surface-600 dark:text-surface-400">Давление рекламы</span>
                                                            </div>
                                                            <div class="text-2xl font-bold text-surface-900 dark:text-surface-0">
                                                                {{ segment.metrics.ad_pressure || '—' }}
                                                            </div>
                                                        </div>
                                                    </div>
                                                </div>

                                                <!-- Visibility Chart -->
                                                <div v-if="segment.visibilityChart" class="mb-6">
                                                    <div class="flex align-items-center mb-3">
                                                        <i class="pi pi-chart-bar text-primary-500 mr-2"></i>
                                                        <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">{{ segment.visibilityChart.title }}</h4>
                                                    </div>
                                                    <div class="p-4 border-round bg-surface-0 dark:bg-surface-800 border-1 border-surface-200 dark:border-surface-700">
                                                        <div class="chart-container" :style="segment.visibilityChart.chartHeight">
                                                            <Chart
                                                                v-if="hasRenderableChartData(segment.visibilityChart.data)"
                                                                :type="segment.visibilityChart.chartType"
                                                                :data="segment.visibilityChart.data"
                                                                :options="segment.visibilityChart.options"
                                                                @chart:click="onChartClick"
                                                                @chart:hover="onChartHover"
                                                                ref="visibilityChartRef"
                                                            />
                                                            <div v-else class="p-3 border-round text-center text-surface-500 dark:text-surface-400">Нет данных для отображения</div>
                                                        </div>
                                                    </div>
                                                </div>

                                                <!-- Competitors Table -->
                                                <div v-if="segment.competitors && segment.competitors.length > 0" class="mb-6">
                                                    <div class="flex align-items-center mb-3">
                                                        <i class="pi pi-table text-primary-500 mr-2"></i>
                                                        <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">Таблица конкурентов</h4>
                                                    </div>
                                                    <div class="overflow-x-auto border-round" style="border: 1px solid var(--surface-border)">
                                                        <table class="competitive-environment-table w-full border-collapse">
                                                            <thead>
                                                                <tr>
                                                                    <th class="competitive-env-th">Название</th>
                                                                    <th class="competitive-env-th">Сайт</th>
                                                                    <th class="competitive-env-th text-center">Видимость</th>
                                                                    <th class="competitive-env-th">Ключевые преимущества</th>
                                                                    <th class="competitive-env-th text-center">Ценовой сегмент</th>
                                                                </tr>
                                                            </thead>
                                                            <tbody>
                                                                <tr
                                                                    v-for="(competitor, idx) in segment.competitors"
                                                                    :key="competitor.name || idx"
                                                                    :class="['competitive-env-tr', { 'competitive-env-tr-highlighted': highlightedRowIndex === idx }]"
                                                                    @mouseenter="highlightRow(idx)"
                                                                    @mouseleave="highlightRow(null)"
                                                                    @click="handleRowClick(competitor)"
                                                                >
                                                                    <td class="competitive-env-td font-semibold"><i class="pi pi-building text-primary-500 mr-2"></i>{{ competitor.name }}</td>
                                                                    <td class="competitive-env-td">
                                                                        <a
                                                                            v-if="competitor.website"
                                                                            :href="getFullUrl(competitor.website)"
                                                                            target="_blank"
                                                                            rel="noopener noreferrer"
                                                                            class="text-primary-500 hover:text-primary-700 dark:hover:text-primary-400 flex align-items-center"
                                                                            @click.stop
                                                                        >
                                                                            <i class="pi pi-external-link mr-1"></i>
                                                                            <span class="text-sm">{{ formatWebsite(competitor.website) }}</span>
                                                                        </a>
                                                                        <span v-else class="text-surface-400">—</span>
                                                                    </td>
                                                                    <td class="competitive-env-td text-center">
                                                                        <div class="flex align-items-center justify-content-center">
                                                                            <span class="competitive-env-score-badge" :class="getScoreClass(competitor.visibility_score)"> {{ competitor.visibility_score || 0 }}% </span>
                                                                        </div>
                                                                    </td>
                                                                    <td class="competitive-env-td">
                                                                        <div v-if="competitor.key_strengths && competitor.key_strengths.length > 0" class="flex flex-wrap gap-1">
                                                                            <Tag v-for="(strength, sIdx) in competitor.key_strengths" :key="sIdx" :value="strength" severity="success" class="text-xs" />
                                                                        </div>
                                                                        <span v-else class="text-surface-400">—</span>
                                                                    </td>
                                                                    <td class="competitive-env-td text-center">
                                                                        <Tag v-if="competitor.price_segment" :value="competitor.price_segment" :severity="getPriceSegmentSeverity(competitor.price_segment)" />
                                                                        <span v-else class="text-surface-400">—</span>
                                                                    </td>
                                                                </tr>
                                                            </tbody>
                                                        </table>
                                                    </div>
                                                </div>

                                                <!-- Conclusion -->
                                                <div v-if="segment.conclusion" class="mt-6">
                                                    <div class="p-4 border-round bg-primary-50 dark:bg-primary-900 border-1 border-primary-200 dark:border-primary-700">
                                                        <div class="flex align-items-start">
                                                            <i class="pi pi-info-circle text-primary-500 mr-2 mt-1 flex-shrink-0"></i>
                                                            <div>
                                                                <h4 class="text-lg font-semibold text-primary-700 dark:text-primary-300 mb-2">Заключение</h4>
                                                                <p class="text-surface-700 dark:text-surface-300 m-0">{{ segment.conclusion }}</p>
                                                            </div>
                                                        </div>
                                                    </div>
                                                </div>
                                            </div>
                                        </div>

                                        <div v-else-if="segment.type === 'competitors'">
                                            <div class="mb-4">
                                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-chart-line mr-2"></i>Анализ конкурентов</h3>
                                            </div>
                                            <!-- Market Share Chart (if included in competitors segment) -->
                                            <div v-if="segment.marketShareChart" class="mb-6">
                                                <div class="flex align-items-center mb-3">
                                                    <i class="pi pi-chart-pie text-primary-500 mr-2"></i>
                                                    <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">{{ segment.marketShareChart.title }}</h4>
                                                </div>
                                                <div class="chart-container" :style="segment.marketShareChart.chartHeight">
                                                    <Chart v-if="hasRenderableChartData(segment.marketShareChart.data)" :type="segment.marketShareChart.chartType" :data="segment.marketShareChart.data" :options="segment.marketShareChart.options" />
                                                    <div v-else class="p-3 border-round text-center text-surface-500 dark:text-surface-400">Нет данных для отображения</div>
                                                </div>
                                            </div>

                                            <!-- Comparison Table (if included in competitors segment) -->
                                            <div v-if="segment.comparisonTable" class="mb-6">
                                                <div class="flex align-items-center mb-3">
                                                    <i class="pi pi-table text-primary-500 mr-2"></i>
                                                    <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">Сравнительная таблица</h4>
                                                </div>
                                                <div class="overflow-x-auto border-round" style="border: 1px solid var(--surface-border)">
                                                    <table class="comparison-table w-full border-collapse">
                                                        <thead>
                                                            <tr>
                                                                <th class="comparison-table-th">Характеристика</th>
                                                                <th class="comparison-table-th text-center">Мы</th>
                                                                <th class="comparison-table-th text-center">Конкурент A</th>
                                                                <th class="comparison-table-th text-center">Конкурент B</th>
                                                            </tr>
                                                        </thead>
                                                        <tbody>
                                                            <tr v-for="(row, idx) in segment.comparisonTable.data" :key="idx" class="comparison-table-tr">
                                                                <td class="comparison-table-td font-semibold">{{ row.feature }}</td>
                                                                <td class="comparison-table-td text-center">
                                                                    <Tag :value="row.us" severity="info" />
                                                                </td>
                                                                <td class="comparison-table-td text-center">
                                                                    <Tag :value="row.compA" :severity="row.compA === 'Высокая' || row.compA === 'Премиум' ? 'danger' : row.compA === 'Низкая' ? 'success' : 'warning'" />
                                                                </td>
                                                                <td class="comparison-table-td text-center">
                                                                    <Tag :value="row.compB" :severity="row.compB === 'Высокая' || row.compB === 'Премиум' ? 'danger' : row.compB === 'Низкая' ? 'success' : 'warning'" />
                                                                </td>
                                                            </tr>
                                                        </tbody>
                                                    </table>
                                                </div>
                                            </div>
                                            <div class="grid">
                                                <div v-for="competitor in segment.competitors" :key="competitor.name" class="col-12 md:col-6 lg:col-4 mb-4">
                                                    <div class="p-4 border-round bg-surface-0 dark:bg-surface-800 border-1 border-surface-200 dark:border-surface-700 h-full flex flex-column">
                                                        <h4 class="text-lg font-semibold mb-3 text-surface-900 dark:text-surface-0 flex align-items-center"><i class="pi pi-building text-primary-500 mr-2"></i>{{ competitor.name }}</h4>
                                                        <div class="space-y-2 mb-3 flex-grow-1">
                                                            <div class="flex justify-content-between align-items-center">
                                                                <span class="text-surface-600 dark:text-surface-400 flex align-items-center"> <i class="pi pi-eye mr-1"></i>Охват: </span>
                                                                <span class="font-semibold text-surface-900 dark:text-surface-0">{{ competitor.reach?.toLocaleString() || 0 }}</span>
                                                            </div>
                                                            <div v-if="competitor.followers" class="flex justify-content-between align-items-center">
                                                                <span class="text-surface-600 dark:text-surface-400 flex align-items-center"> <i class="pi pi-users mr-1"></i>Подписчики: </span>
                                                                <span class="font-semibold text-surface-900 dark:text-surface-0">{{ competitor.followers?.toLocaleString() || 0 }}</span>
                                                            </div>
                                                            <div class="flex justify-content-between align-items-center">
                                                                <span class="text-surface-600 dark:text-surface-400 flex align-items-center"> <i class="pi pi-chart-bar mr-1"></i>Активность: </span>
                                                                <span class="font-semibold text-surface-900 dark:text-surface-0">{{ competitor.activity }}%</span>
                                                            </div>
                                                            <div v-if="competitor.priceStrategy" class="flex justify-content-between align-items-center">
                                                                <span class="text-surface-600 dark:text-surface-400 flex align-items-center"> <i class="pi pi-tag mr-1"></i>Ценовая стратегия: </span>
                                                                <Tag
                                                                    :value="competitor.priceStrategy"
                                                                    :severity="competitor.priceStrategy === 'Высокая' || competitor.priceStrategy === 'Премиум' ? 'danger' : competitor.priceStrategy === 'Низкая' ? 'success' : 'warning'"
                                                                />
                                                            </div>
                                                        </div>
                                                        <div v-if="competitor.strengths?.length" class="mb-3">
                                                            <p class="text-sm font-semibold mb-2 text-green-600 dark:text-green-400 flex align-items-center"><i class="pi pi-arrow-up mr-1"></i>Сильные стороны:</p>
                                                            <ul class="list-none p-0 m-0">
                                                                <li v-for="(strength, idx) in competitor.strengths" :key="idx" class="text-sm text-surface-700 dark:text-surface-300 mb-1 flex align-items-start">
                                                                    <i class="pi pi-check-circle text-green-500 mr-2 mt-1 flex-shrink-0"></i>
                                                                    <span>{{ strength }}</span>
                                                                </li>
                                                            </ul>
                                                        </div>
                                                        <div v-if="competitor.weaknesses?.length">
                                                            <p class="text-sm font-semibold mb-2 text-red-600 dark:text-red-400 flex align-items-center"><i class="pi pi-arrow-down mr-1"></i>Слабые стороны:</p>
                                                            <ul class="list-none p-0 m-0">
                                                                <li v-for="(weakness, idx) in competitor.weaknesses" :key="idx" class="text-sm text-surface-700 dark:text-surface-300 mb-1 flex align-items-start">
                                                                    <i class="pi pi-times-circle text-red-500 mr-2 mt-1 flex-shrink-0"></i>
                                                                    <span>{{ weakness }}</span>
                                                                </li>
                                                            </ul>
                                                        </div>
                                                    </div>
                                                </div>
                                            </div>

                                            <!-- Competitors Heatmap -->
                                            <div v-if="segment.competitorsHeatmap" class="mt-6">
                                                <div class="flex align-items-center mb-3">
                                                    <i class="pi pi-map text-primary-500 mr-2"></i>
                                                    <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">Тепловая карта каналов конкурентов</h4>
                                                </div>
                                                <div class="overflow-x-auto border-round" style="border: 1px solid var(--surface-border)">
                                                    <table class="competitors-heatmap-table w-full border-collapse">
                                                        <thead>
                                                            <tr>
                                                                <th class="competitors-heatmap-th">Конкурент</th>
                                                                <th v-for="channel in segment.competitorsHeatmap.channels" :key="channel" class="competitors-heatmap-th text-center">
                                                                    {{ channel }}
                                                                </th>
                                                            </tr>
                                                        </thead>
                                                        <tbody>
                                                            <tr v-for="(compData, idx) in segment.competitorsHeatmap.data" :key="idx" class="competitors-heatmap-tr">
                                                                <td class="competitors-heatmap-td font-semibold">{{ compData.name }}</td>
                                                                <td v-for="channel in segment.competitorsHeatmap.channels" :key="channel" class="competitors-heatmap-td text-center">
                                                                    <span class="competitors-heatmap-badge" :style="{ backgroundColor: getHeatmapColor(compData.channelsHeatmap[channel] || 0) }">
                                                                        {{ compData.channelsHeatmap[channel] || 0 }}
                                                                    </span>
                                                                </td>
                                                            </tr>
                                                        </tbody>
                                                    </table>
                                                </div>
                                            </div>
                                        </div>

                                        <!-- Market Share Chart -->
                                        <div v-else-if="segment.type === 'marketShareChart'">
                                            <div class="mb-4" v-if="segment.title">
                                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-chart-pie mr-2"></i>{{ segment.title }}</h3>
                                            </div>
                                            <div class="chart-container" :style="segment.chartHeight">
                                                <Chart v-if="hasRenderableChartData(segment.data)" :type="segment.chartType" :data="segment.data" :options="segment.options" />
                                                <div v-else class="p-3 border-round text-center text-surface-500 dark:text-surface-400">Нет данных для отображения</div>
                                            </div>
                                        </div>

                                        <!-- Comparison Table -->
                                        <div v-else-if="segment.type === 'comparisonTable'">
                                            <div class="mb-4">
                                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-table mr-2"></i>Сравнительная таблица</h3>
                                            </div>
                                            <div class="overflow-x-auto border-round" style="border: 1px solid var(--surface-border)">
                                                <table class="comparison-table w-full border-collapse">
                                                    <thead>
                                                        <tr>
                                                            <th class="comparison-table-th">Характеристика</th>
                                                            <th class="comparison-table-th text-center">Мы</th>
                                                            <th class="comparison-table-th text-center">Конкурент A</th>
                                                            <th class="comparison-table-th text-center">Конкурент B</th>
                                                        </tr>
                                                    </thead>
                                                    <tbody>
                                                        <tr v-for="(row, idx) in segment.data" :key="idx" class="comparison-table-tr">
                                                            <td class="comparison-table-td font-semibold">{{ row.feature }}</td>
                                                            <td class="comparison-table-td text-center">
                                                                <Tag :value="row.us" severity="info" />
                                                            </td>
                                                            <td class="comparison-table-td text-center">
                                                                <Tag :value="row.compA" :severity="row.compA === 'Высокая' || row.compA === 'Премиум' ? 'danger' : row.compA === 'Низкая' ? 'success' : 'warning'" />
                                                            </td>
                                                            <td class="comparison-table-td text-center">
                                                                <Tag :value="row.compB" :severity="row.compB === 'Высокая' || row.compB === 'Премиум' ? 'danger' : row.compB === 'Низкая' ? 'success' : 'warning'" />
                                                            </td>
                                                        </tr>
                                                    </tbody>
                                                </table>
                                            </div>
                                        </div>

                                        <!-- SWOT Competitors -->
                                        <div v-else-if="segment.type === 'swotCompetitors'">
                                            <div class="mb-4">
                                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-sitemap mr-2"></i>SWOT-анализ конкурентов</h3>
                                            </div>
                                            <div class="grid">
                                                <div class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-green-50 dark:bg-green-900 border-1 border-green-200 dark:border-green-700 h-full">
                                                        <h4 class="text-lg font-semibold mb-3 text-green-700 dark:text-green-300 flex align-items-center"><i class="pi pi-arrow-up mr-2"></i>Сильные стороны</h4>
                                                        <ul class="list-none p-0 m-0">
                                                            <li v-for="(strength, idx) in segment.data.strengths" :key="idx" class="text-surface-700 dark:text-surface-300 mb-2 flex align-items-start">
                                                                <i class="pi pi-check-circle text-green-500 mr-2 mt-1 flex-shrink-0"></i>
                                                                <span>{{ strength }}</span>
                                                            </li>
                                                        </ul>
                                                    </div>
                                                </div>
                                                <div class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-red-50 dark:bg-red-900 border-1 border-red-200 dark:border-red-700 h-full">
                                                        <h4 class="text-lg font-semibold mb-3 text-red-700 dark:text-red-300 flex align-items-center"><i class="pi pi-arrow-down mr-2"></i>Слабые стороны</h4>
                                                        <ul class="list-none p-0 m-0">
                                                            <li v-for="(weakness, idx) in segment.data.weaknesses" :key="idx" class="text-surface-700 dark:text-surface-300 mb-2 flex align-items-start">
                                                                <i class="pi pi-times-circle text-red-500 mr-2 mt-1 flex-shrink-0"></i>
                                                                <span>{{ weakness }}</span>
                                                            </li>
                                                        </ul>
                                                    </div>
                                                </div>
                                            </div>
                                        </div>

                                        <!-- Market -->
                                        <div v-else-if="segment.type === 'market'">
                                            <div class="mb-4">
                                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0"><i class="pi pi-globe mr-2"></i>Анализ рынка</h3>
                                            </div>
                                            <div class="grid mb-4">
                                                <div class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-surface-0 dark:bg-surface-800 border-1 border-surface-200 dark:border-surface-700">
                                                        <div class="flex align-items-center mb-2">
                                                            <i class="pi pi-chart-bar text-primary-500 mr-2"></i>
                                                            <h4 class="text-sm font-semibold text-surface-600 dark:text-surface-400 m-0">Размер рынка</h4>
                                                        </div>
                                                        <p class="text-lg font-bold text-surface-900 dark:text-surface-0 mt-2">{{ segment.data.size || 'Не указано' }}</p>
                                                    </div>
                                                </div>
                                                <div class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-surface-0 dark:bg-surface-800 border-1 border-surface-200 dark:border-surface-700">
                                                        <div class="flex align-items-center mb-2">
                                                            <i class="pi pi-arrow-up-right text-primary-500 mr-2"></i>
                                                            <h4 class="text-sm font-semibold text-surface-600 dark:text-surface-400 m-0">Темп роста</h4>
                                                        </div>
                                                        <p class="text-lg font-bold text-surface-900 dark:text-surface-0 mt-2">{{ segment.data.growthRate || 'Не указано' }}</p>
                                                    </div>
                                                </div>
                                            </div>

                                            <div v-if="segment.data.trends && segment.data.trends.length > 0" class="mb-4">
                                                <div class="flex align-items-center mb-3">
                                                    <i class="pi pi-trending-up text-primary-500 mr-2"></i>
                                                    <h4 class="text-lg font-semibold text-surface-700 dark:text-surface-300 m-0">Тренды</h4>
                                                </div>
                                                <div class="p-4 border-round bg-blue-50 dark:bg-blue-900 border-1 border-blue-200 dark:border-blue-700">
                                                    <ul class="list-none p-0 m-0">
                                                        <li v-for="(trend, idx) in segment.data.trends" :key="idx" class="flex align-items-start mb-2">
                                                            <i class="pi pi-arrow-up-right text-blue-500 mr-2 mt-1 flex-shrink-0"></i>
                                                            <span class="text-surface-700 dark:text-surface-300">{{ trend }}</span>
                                                        </li>
                                                    </ul>
                                                </div>
                                            </div>

                                            <div class="grid">
                                                <div v-if="segment.data.opportunities && segment.data.opportunities.length > 0" class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-blue-50 dark:bg-blue-900 border-1 border-blue-200 dark:border-blue-700">
                                                        <h4 class="text-lg font-semibold mb-3 text-blue-700 dark:text-blue-300">Возможности</h4>
                                                        <ul class="list-none p-0 m-0">
                                                            <li v-for="(opportunity, idx) in segment.data.opportunities" :key="idx" class="text-surface-700 dark:text-surface-300 mb-2">
                                                                <i class="pi pi-arrow-up-circle text-blue-500 mr-2"></i>{{ opportunity }}
                                                            </li>
                                                        </ul>
                                                    </div>
                                                </div>
                                                <div v-if="segment.data.threats && segment.data.threats.length > 0" class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-orange-50 dark:bg-orange-900 border-1 border-orange-200 dark:border-orange-700">
                                                        <h4 class="text-lg font-semibold mb-3 text-orange-700 dark:text-orange-300">Угрозы</h4>
                                                        <ul class="list-none p-0 m-0">
                                                            <li v-for="(threat, idx) in segment.data.threats" :key="idx" class="text-surface-700 dark:text-surface-300 mb-2">
                                                                <i class="pi pi-exclamation-triangle text-orange-500 mr-2"></i>{{ threat }}
                                                            </li>
                                                        </ul>
                                                    </div>
                                                </div>
                                            </div>
                                        </div>

                                        <div v-else-if="segment.type === 'swot'">
                                            <div class="mb-4">
                                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0">SWOT-анализ</h3>
                                            </div>
                                            <div class="grid">
                                                <div class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-green-50 dark:bg-green-900 border-1 border-green-200 dark:border-green-700">
                                                        <h4 class="text-lg font-semibold mb-3 text-green-700 dark:text-green-300">Сильные стороны</h4>
                                                        <ul class="list-none p-0 m-0">
                                                            <li v-for="(strength, idx) in segment.data.strengths" :key="idx" class="text-surface-700 dark:text-surface-300 mb-2"><i class="pi pi-check-circle text-green-500 mr-2"></i>{{ strength }}</li>
                                                        </ul>
                                                    </div>
                                                </div>
                                                <div class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-red-50 dark:bg-red-900 border-1 border-red-200 dark:border-red-700">
                                                        <h4 class="text-lg font-semibold mb-3 text-red-700 dark:text-red-300">Слабые стороны</h4>
                                                        <ul class="list-none p-0 m-0">
                                                            <li v-for="(weakness, idx) in segment.data.weaknesses" :key="idx" class="text-surface-700 dark:text-surface-300 mb-2"><i class="pi pi-times-circle text-red-500 mr-2"></i>{{ weakness }}</li>
                                                        </ul>
                                                    </div>
                                                </div>
                                                <div class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-blue-50 dark:bg-blue-900 border-1 border-blue-200 dark:border-blue-700">
                                                        <h4 class="text-lg font-semibold mb-3 text-blue-700 dark:text-blue-300">Возможности</h4>
                                                        <ul class="list-none p-0 m-0">
                                                            <li v-for="(opportunity, idx) in segment.data.opportunities" :key="idx" class="text-surface-700 dark:text-surface-300 mb-2">
                                                                <i class="pi pi-arrow-up-circle text-blue-500 mr-2"></i>{{ opportunity }}
                                                            </li>
                                                        </ul>
                                                    </div>
                                                </div>
                                                <div class="col-12 md:col-6 mb-3">
                                                    <div class="p-4 border-round bg-orange-50 dark:bg-orange-900 border-1 border-orange-200 dark:border-orange-700">
                                                        <h4 class="text-lg font-semibold mb-3 text-orange-700 dark:text-orange-300">Угрозы</h4>
                                                        <ul class="list-none p-0 m-0">
                                                            <li v-for="(threat, idx) in segment.data.threats" :key="idx" class="text-surface-700 dark:text-surface-300 mb-2">
                                                                <i class="pi pi-exclamation-triangle text-orange-500 mr-2"></i>{{ threat }}
                                                            </li>
                                                        </ul>
                                                    </div>
                                                </div>
                                            </div>
                                        </div>
                                        <!-- Fallback for unrecognized segment types - don't display raw JSON -->
                                        <div v-else-if="segment && segment.type">
                                            <p class="text-surface-600 dark:text-surface-400">Неизвестный тип сегмента: {{ segment.type }}</p>
                                        </div>
                                    </div>
                                </div>
                            </div>
                        </div>

                        <!-- Рекомендации -->
                        <div v-if="report.recommendations?.length" class="card">
                            <div class="card-header mb-4">
                                <h3 class="text-xl font-semibold text-surface-900 dark:text-surface-0">Рекомендации</h3>
                            </div>
                            <div class="card-content">
                                <ul class="list-none p-0 m-0">
                                    <li v-for="(recommendation, index) in report.recommendations" :key="index" class="flex align-items-start mb-3">
                                        <i class="pi pi-check-circle text-green-500 mr-2 mt-1"></i>
                                        <span class="text-surface-700 dark:text-surface-300">{{ recommendation }}</span>
                                    </li>
                                </ul>
                            </div>
                        </div>
                    </div>
                </div>

                <!-- Кнопки действий (всегда видны, когда есть анализ) -->
                <div v-if="(status === 'completed' && report) || v2ReportNormalized" class="card">
                    <div class="card-content text-center">
                        <div class="flex gap-3 justify-content-center flex-wrap">
                            <Button label="Создать стратегию на основе анализа" icon="pi pi-magic" severity="success" @click="goToStrategy" />
                            <Button label="Создать новый анализ" icon="pi pi-plus" severity="secondary" @click="resetAnalysis" />
                        </div>
                    </div>
                </div>
            </div>
        </div>
    </div>
</template>

<style scoped>
.v2-glow :deep(canvas) {
    filter: drop-shadow(0 0 14px rgba(59, 130, 246, 0.22));
}

.marketing-analysis-page {
    font-family: var(--font-family);
}

.card {
    background: var(--surface-card);
    border-radius: 12px;
    box-shadow:
        0 1px 3px rgba(0, 0, 0, 0.12),
        0 1px 2px rgba(0, 0, 0, 0.24);
    padding: 1.5rem;
}

.card-header {
    border-bottom: 1px solid var(--surface-border);
    padding-bottom: 1rem;
    margin-bottom: 1rem;
}

.card-content {
    padding-top: 0;
}

.markdown-content {
    line-height: 1.7;
    color: var(--text-color);
    font-size: 0.95rem;
}

.markdown-content :deep(h1) {
    font-size: 1.75rem;
    font-weight: 700;
    margin-top: 1.5rem;
    margin-bottom: 1rem;
    color: var(--text-color);
    line-height: 1.3;
}

.markdown-content :deep(h1:first-child) {
    margin-top: 0;
}

.markdown-content :deep(h2) {
    font-size: 1.5rem;
    font-weight: 600;
    margin-top: 1.5rem;
    margin-bottom: 0.75rem;
    color: var(--text-color);
    line-height: 1.3;
}

.markdown-content :deep(h3) {
    font-size: 1.25rem;
    font-weight: 600;
    margin-top: 1.25rem;
    margin-bottom: 0.75rem;
    color: var(--text-color);
    line-height: 1.4;
}

.markdown-content :deep(h4) {
    font-size: 1.1rem;
    font-weight: 600;
    margin-top: 1rem;
    margin-bottom: 0.5rem;
    color: var(--text-color);
    line-height: 1.4;
}

.markdown-content :deep(h5),
.markdown-content :deep(h6) {
    font-size: 1rem;
    font-weight: 600;
    margin-top: 0.75rem;
    margin-bottom: 0.5rem;
    color: var(--text-color);
    line-height: 1.4;
}

.markdown-content :deep(p) {
    margin-bottom: 1rem;
    color: var(--text-color);
    line-height: 1.7;
}

.markdown-content :deep(p:last-child) {
    margin-bottom: 0;
}

.markdown-content :deep(ul),
.markdown-content :deep(ol) {
    margin-top: 0.5rem;
    margin-bottom: 1rem;
    padding-left: 2rem;
    color: var(--text-color);
}

.markdown-content :deep(ul) {
    list-style-type: disc;
}

.markdown-content :deep(ol) {
    list-style-type: decimal;
}

.markdown-content :deep(li) {
    margin-bottom: 0.5rem;
    line-height: 1.7;
    color: var(--text-color);
}

.markdown-content :deep(li > p) {
    margin-bottom: 0.5rem;
}

.markdown-content :deep(li > ul),
.markdown-content :deep(li > ol) {
    margin-top: 0.5rem;
    margin-bottom: 0.5rem;
}

.markdown-content :deep(strong) {
    font-weight: 600;
    color: var(--text-color);
}

.markdown-content :deep(em) {
    font-style: italic;
}

.markdown-content :deep(code) {
    background-color: var(--surface-100);
    padding: 0.125rem 0.375rem;
    border-radius: 0.25rem;
    font-size: 0.875em;
    font-family: 'Courier New', monospace;
}

.markdown-content :deep(pre) {
    background-color: var(--surface-100);
    padding: 1rem;
    border-radius: 0.5rem;
    overflow-x: auto;
    margin-bottom: 1rem;
}

.markdown-content :deep(pre code) {
    background-color: transparent;
    padding: 0;
}

.markdown-content :deep(table) {
    width: 100%;
    border-collapse: collapse;
    margin-top: 1rem;
    margin-bottom: 1rem;
    border: 1px solid var(--surface-border);
    border-radius: 0.5rem;
    overflow: hidden;
}

.markdown-content :deep(thead) {
    background-color: var(--surface-100);
}

.markdown-content :deep(th) {
    padding: 0.75rem 1rem;
    text-align: left;
    font-weight: 600;
    color: var(--text-color);
    border-bottom: 2px solid var(--surface-border);
}

.markdown-content :deep(td) {
    padding: 0.75rem 1rem;
    border-bottom: 1px solid var(--surface-border);
    color: var(--text-color);
}

.markdown-content :deep(tr:last-child td) {
    border-bottom: none;
}

.markdown-content :deep(tr:hover) {
    background-color: var(--surface-50);
}

.report-pair {
    /* Keep everything strictly in normal flow; no float/absolute positioning */
    display: grid;
    grid-template-columns: minmax(0, 1fr) minmax(260px, 40%);
    gap: 1.5rem;
    align-items: start;
}

.report-pair__text,
.report-pair__media {
    min-width: 0;
}

.report-pair__textStack {
    display: flex;
    flex-direction: column;
    gap: 1rem;
}

.report-pair__media {
    width: 100%;
    align-self: start;
}

.report-pair__mediaChart {
    width: 100%;
}

.report-pair__chart-container {
    width: 100%;
    /* Keep charts compact without forcing wrapper height */
    max-height: 250px;
    height: auto;
    overflow: hidden;
}

/* Remove top/bottom margins inside paired markdown so text starts flush with chart title/area */
.report-pair__text .markdown-content :deep(> *:first-child) {
    margin-top: 0 !important;
}
.report-pair__text .markdown-content :deep(> *:last-child) {
    margin-bottom: 0 !important;
}

/* Ensure Chart.js canvas doesn't add extra whitespace and respects container width */
.report-pair__chart-container :deep(canvas) {
    width: 100% !important;
    height: auto !important;
    max-height: 250px;
    display: block;
}

.chart-caption {
    margin-top: 0.5rem;
    text-align: center;
    font-size: 0.95rem;
    font-weight: 600;
    line-height: 1.25rem;
}

@media (max-width: 768px) {
    .report-pair {
        grid-template-columns: 1fr;
    }
}

.chart-container {
    position: relative;
}

/* Competitors Heatmap Table Styles */
.competitors-heatmap-table {
    border: 1px solid var(--surface-border);
    border-radius: 0.5rem;
    overflow: hidden;
}

.competitors-heatmap-th {
    padding: 0.75rem 1rem;
    text-align: left;
    font-weight: 600;
    color: var(--text-color);
    background-color: var(--surface-100);
    border-bottom: 2px solid var(--surface-border);
    white-space: nowrap;
}

.competitors-heatmap-td {
    padding: 0.75rem 1rem;
    border-bottom: 1px solid var(--surface-border);
    color: var(--text-color);
}

.competitors-heatmap-tr:last-child .competitors-heatmap-td {
    border-bottom: none;
}

.competitors-heatmap-tr:hover {
    background-color: var(--surface-50);
}

.competitors-heatmap-badge {
    display: inline-block;
    padding: 0.5rem 0.875rem;
    border-radius: 0.375rem;
    color: white;
    font-weight: 600;
    font-size: 0.875rem;
    min-width: 55px;
    text-align: center;
    box-shadow: 0 1px 2px rgba(0, 0, 0, 0.1);
}

/* Comparison Table Styles */
.comparison-table {
    border: 1px solid var(--surface-border);
    border-radius: 0.5rem;
    overflow: hidden;
}

.comparison-table-th {
    padding: 0.75rem 1rem;
    text-align: left;
    font-weight: 600;
    color: var(--text-color);
    background-color: var(--surface-100);
    border-bottom: 2px solid var(--surface-border);
}

.comparison-table-td {
    padding: 0.75rem 1rem;
    border-bottom: 1px solid var(--surface-border);
    color: var(--text-color);
}

.comparison-table-tr:last-child .comparison-table-td {
    border-bottom: none;
}

.comparison-table-tr:hover {
    background-color: var(--surface-50);
}

/* Competitive Environment Table Styles */
.competitive-environment-table {
    font-size: 0.9rem;
}

.competitive-env-th {
    padding: 1rem;
    text-align: left;
    font-weight: 600;
    color: var(--text-color);
    background-color: var(--surface-50);
    border-bottom: 2px solid var(--surface-border);
    white-space: nowrap;
}

.competitive-env-td {
    padding: 1rem;
    border-bottom: 1px solid var(--surface-border);
    color: var(--text-color);
    vertical-align: middle;
}

.competitive-env-tr {
    transition: all 0.2s ease;
    cursor: pointer;
}

.competitive-env-tr:hover {
    background-color: var(--surface-hover);
    transform: translateX(2px);
}

.competitive-env-tr-highlighted {
    background-color: var(--primary-50);
    border-left: 3px solid var(--primary-500);
}

.competitive-env-score-badge {
    display: inline-block;
    padding: 0.375rem 0.75rem;
    border-radius: 0.5rem;
    font-weight: 600;
    font-size: 0.875rem;
    min-width: 3rem;
    text-align: center;
}

.competitive-env-score-high {
    background-color: rgba(16, 185, 129, 0.1);
    color: #10b981;
}

.competitive-env-score-medium {
    background-color: rgba(245, 158, 11, 0.1);
    color: #f59e0b;
}

.competitive-env-score-low {
    background-color: rgba(239, 68, 68, 0.1);
    color: #ef4444;
}

.dark .competitive-env-score-high {
    background-color: rgba(16, 185, 129, 0.2);
    color: #34d399;
}

.dark .competitive-env-score-medium {
    background-color: rgba(245, 158, 11, 0.2);
    color: #fbbf24;
}

.dark .competitive-env-score-low {
    background-color: rgba(239, 68, 68, 0.2);
    color: #f87171;
}
</style>
