This commit is contained in:
arys
2026-02-22 13:18:23 +05:00
parent 5b5dcdd8cf
commit 08a891c614
2 changed files with 66 additions and 55 deletions
@@ -138,9 +138,10 @@ public class MarketingAnalysisV3Result {
@Data
public static class UserPositioning {
private RadarMetrics radarChart;
private String status;
private List<String> gaps;
private RadarMetrics marketMetrics;
private RadarMetrics userMetrics;
private String mode;
private List<String> strategicFocus;
}
@Data
@@ -236,16 +236,18 @@ public class MarketingAnalysisV3Service {
private String buildKazakhstanSystemPrompt() {
return """
РОЛЬ: Ты — Chief Data Officer и Стратег Big 4 (PwC, BCG) по рынку Казахстана.
ЗАДАЧА: Сгенерировать глубокий, Data-Driven "Marketing Analysis v4.0" в строгом JSON формате.
РОЛЬ: Ты — Chief Data Officer и Senior Стратег Big 4 (PwC, McKinsey), эксперт по рынку Казахстана.
Твоя задача — не просто сгенерировать JSON, а подготовить ИДЕАЛЬНЫЙ датасет для интерактивного аналитического дашборда на фронтенде (React/Vue).
От твоих данных будут строиться реальные графики (Radar, Scatter, Pie, Line charts). Данные должны быть математически корректны и логически связаны.
КРИТИЧЕСКИЕ ПРАВИЛА (ANTI-HALLUCINATION PROTOCOL):
1. ТОЛЬКО РЕАЛЬНЫЕ ДАННЫЕ: Вся аналитика строится на переданном SEARCH EVIDENCE.
2. РЕАЛЬНЫЕ КОНКУРЕНТЫ: В блоке `3_competitor_map` ОБЯЗАНО быть строго от 5 до 10 РЕАЛЬНЫХ компаний из предоставленных данных. Ровно 3 — ЗАПРЕЩЕНО.
3. ПОЛНАЯ РУСИФИКАЦИЯ: Все текстовые значения статусов, уровней и трендов (businessStage, competitionLevel, demandTrend, intensityLabel, status) СТРОГО на русском языке. Запрещено копировать английские слова (JUST_STARTING, HIGH, STABLE, NONE) из DTO. Переводи их по смыслу (Например: 'На старте', 'Высокая', 'Стабильный', 'Отсутствует').
4. ОЦИФРОВКА И ТИПЫ ДАННЫХ: Возвращай строго те типы данных, которые указаны в шаблоне. Если указано число (0 или 0.0), возвращай число, а не строку.
5. СВЯЗЬ СО СТРАТЕГИЕЙ: Твой анализ — это фундамент для будущего SMM-Scoring Model.
6. НИКАКИХ NULL: Заполни абсолютно все поля JSON. Если точной цифры нет, примени метод Ферми и сделай экстраполяцию, характерную для рынка РК.
1. АБСОЛЮТНАЯ РУСИФИКАЦИЯ: Все статусы, уровни, тренды и перечисления (businessStage, competitionLevel, demandTrend, intensityLabel) СТРОГО НА РУССКОМ ЯЗЫКЕ. Никаких 'JUST_STARTING', 'HIGH', 'NONE'.
2. ГЕОГРАФИЯ И ГОРОДА: Ты ОБЯЗАН включить КАЖДЫЙ город, переданный в запросе, в блоки аналитики (1_market_landscape и 2_geo_structure). Пропуск даже одного города — критический провал системы.
3. КОНКУРЕНТЫ: В блоке `3_competitor_map` ОБЯЗАНО быть строго от 5 до 10 реально существующих компаний из SEARCH EVIDENCE. Ровно 3 — ЗАПРЕЩЕНО.
4. ЧИСЛА, А НЕ СЛОВА: Если фронт ждет int или double (например, avgMonthlySearches, avgCycleDays), выдавай СТРОГО числа. Никаких слов "высокая" или "короткий".
5. НИКАКИХ NULL И ПУСТОТ: Заполни абсолютно все поля. Используй экстраполяцию рынка РК (Kaspi, 2GIS, менталитет), если точных данных нет.
6. ЛОГИКА ГРАФИКОВ: Суммы процентов (например, в content_profile или starDistribution) должны давать ровно 100%.
7. РЕАЛИСТИЧНОСТЬ ДАННЫХ (КРИТИЧНО): Избегай круглых чисел и ленивых средних значений (типа ровно 50% или везде 0). Генерируй реалистичный математический разброс для показателей, основываясь на данных парсинга.
""";
}
@@ -271,42 +273,55 @@ public class MarketingAnalysisV3Service {
РАЗВЕДДАННЫЕ (SEARCH EVIDENCE):
%s
ИНСТРУКЦИИ ПО СЕКЦИЯМ (СТРОГО):
СТРОГО ИСПОЛЬЗУЙ ВСЕ ГОРОДА, КОТОРЫЕ ТЕБЕ ОТПРАВЛЯЮТ, ПРЯМ ВСЕ
[0_executive_summary]
- Все статусы СТРОГО на русском.
- averageNicheEr: Верни число (double, например 0.05).
ОБЯЗАТЕЛЬНЫЕ ЦЕЛЕВЫЕ ГОРОДА (СТРОГО ИСПОЛЬЗУЙ ВСЕ ГОРОДА В АНАЛИЗЕ!): %s
[1_market_landscape] и [2_geo_structure]
- ОБЯЗАТЕЛЬНО выведи метрики распределения для КАЖДОГО из этих городов: %s. Пропуск любого города — критическая ошибка.
ИНСТРУКЦИИ ДЛЯ ПОДГОТОВКИ ДАННЫХ К ДАШБОРДУ (СТРОГО):
[3_competitor_map]
- ОБЯЗАНО быть строго от 5 до 10 РЕАЛЬНЫХ компаний.
- Рассчитай реалистичный ER (от 0.01 до 0.08).
[0_executive_summary] -> Виджеты KPI
- Все текстовые поля (businessStage, geography, competitionLevel, demandTrend) СТРОГО НА РУССКОМ.
- averageNicheEr: верни реалистичное число (double, например 0.045).
[4_content_profile]
- Сумма всех ContentPercent должна быть ровно 100.0.
- avgTextLengthCharacters: Верни конкретное число символов (int, например 400).
- ctaUsagePercent: Верни процент использования призывов (double, например 85.0).
[1_market_landscape] -> Pie Chart (Платформы) и Heatmap (Города)
- Распредели игроков по платформам адекватно.
- В cityDistribution ОБЯЗАТЕЛЬНО укажи распределение по КАЖДОМУ целевому городу.
[6_reputation_analysis]
- avgOwnerResponseTimeHours: Верни среднее время ответа в часах (int, например 2 или 24).
[2_geo_structure] -> Сравнительная гистограмма
- В cityComparison ОБЯЗАНЫ быть ВСЕ целевые города с метриками.
[7_behavioral_pattern]
- Все показатели верни в процентах (double, например 45.0).
- avgCycleDays: Верни цикл сделки в днях (int, например 7).
[3_competitor_map] -> Scatter Plot (Пузырьковая диаграмма)
- СТРОГО 5-10 РЕАЛЬНЫХ конкурентов. Меньше 5 недопустимо.
- ER, followers, postsPerMonth должны быть числовыми и реалистичными.
[8_search_demand]
- avgMonthlySearches: Верни число поисковых запросов в месяц (int, например 15000).
- seasonality: 12 объектов. Поле "period" СТРОГО на русском (Январь, Февраль...).
[4_content_profile] -> Donut Chart
- Сумма всех Percent строго 100.0. Сделай реалистичный разброс (например 35, 20, 15, 25, 5).
- avgTextLengthCharacters: верни число символов (int, например 350).
- ctaUsagePercent: процент постов с призывом (double, например 85.5).
[9_user_positioning]
- status: СТРОГО на русском (например 'Отсутствует', 'Действующий').
[5_competition_intensity] -> Gauge Chart (Спидометр)
- ciiIndex: 0-100.
- intensityLabel: СТРОГО НА РУССКОМ (например "Высокая", "Свободный рынок").
[11_smm_strategy_rationale]
- МИНИМУМ 50 СЛОВ. Обоснуй стратегию на основе реальных данных из блоков 5 и 7.
[6_reputation_analysis] -> Bar Chart (Рейтинги)
- starDistribution: сумма долей строго 100.0. Имитируй реальные отзывы (много 5, немного 1, почти нет 2 и 3).
- avgOwnerResponseTimeHours: часы (int, например 2 или 24).
ЭТАЛОННЫЙ JSON:
[7_behavioral_pattern] -> Горизонтальный Bar Chart и Карточки
- Показатели (promoUsagePercent и т.д.) верни в процентах (double, 0.0 - 100.0). Сделай цифры разными и реалистичными.
- avgCycleDays: цикл сделки в днях (int, например 7).
[8_search_demand] -> Line Chart (Сезонность)
- avgMonthlySearches: точное число запросов (int, например 15000). Никаких слов!
- seasonality: ровно 12 объектов. Периоды строго на русском (Январь, Февраль...).
[9_user_positioning] -> Radar Chart (Паутинка) - ВАЖНАЯ ЛОГИКА:
- Если DTO smmStatus == "NONE": поле mode СТРОГО "BENCHMARK". userMetrics везде 0. marketMetrics заполни РЕАЛЬНЫМИ средними требованиями ниши (от 0 до 100, с разбросом, например activity 75, engagement 45, reputation 80).
- Если DTO smmStatus != "NONE": поле mode СТРОГО "COMPARISON". Оцени userMetrics на основе данных, marketMetrics — реалистичное среднее по рынку.
- strategicFocus: Напиши 3 конкретных шага (стратегический фокус).
[10_structured_conclusions] & [11_smm_strategy_rationale] -> Текстовые выводы
- МИНИМУМ 50 СЛОВ в блоке 11. Обоснуй SMM стратегию глубоко, опираясь на конкретные числа из графиков.
ЭТАЛОННЫЙ JSON (СТРОГО СОБЛЮДАЙ ФОРМАТ, КЛЮЧИ И ТИПЫ ДАННЫХ):
%s
""".formatted(requestJson, evidenceJson, targetCities, schemaTemplate);
} catch (Exception e) {
@@ -318,18 +333,18 @@ public class MarketingAnalysisV3Service {
return """
{
"0_executive_summary": {
"businessStage": "СТРОГО НА РУССКОМ",
"geography": "СТРОГО НА РУССКОМ",
"businessStage": "СТРОГО НА РУССКОМ (например: 'На этапе запуска', 'Действующий бизнес')",
"geography": "СТРОГО НА РУССКОМ (например: 'Один город', 'Вся страна')",
"activeCompetitors": 0,
"competitionLevel": "СТРОГО НА РУССКОМ",
"competitionLevel": "СТРОГО НА РУССКОМ (например: 'Высокий', 'Средний')",
"averageNicheEr": 0.0,
"averageRating": 0.0,
"demandTrend": "СТРОГО НА РУССКОМ",
"demandTrend": "СТРОГО НА РУССКОМ (например: 'Растущий', 'Стабильный')",
"keyFigures": ["string", "string", "string"]
},
"1_market_landscape": {
"activePlayersByPlatform": {"Instagram": 0, "TikTok": 0, "GoogleMaps": 0},
"cityDistribution": {"Almaty": 0},
"cityDistribution": {"Город 1": 0, "Город 2": 0},
"nicheReputationLevel": 0.0
},
"2_geo_structure": {
@@ -361,7 +376,7 @@ public class MarketingAnalysisV3Service {
},
"5_competition_intensity": {
"ciiIndex": 0,
"intensityLabel": "СТРОГО НА РУССКОМ",
"intensityLabel": "СТРОГО НА РУССКОМ (например: 'Высокая плотность')",
"contributingFactors": ["string"]
},
"6_reputation_analysis": {
@@ -398,18 +413,13 @@ public class MarketingAnalysisV3Service {
"relatedQueries": ["string"]
},
"9_user_positioning": {
"radarChart": {
"activity": 0,
"engagement": 0,
"video": 0,
"reputation": 0,
"frequency": 0
},
"status": "СТРОГО НА РУССКОМ",
"gaps": ["string"]
"marketMetrics": {"activity": 0, "engagement": 0, "video": 0, "reputation": 0, "frequency": 0},
"userMetrics": {"activity": 0, "engagement": 0, "video": 0, "reputation": 0, "frequency": 0},
"mode": "BENCHMARK или COMPARISON",
"strategicFocus": ["string", "string", "string"]
},
"10_structured_conclusions": ["string", "string", "string"],
"11_smm_strategy_rationale": "string"
"11_smm_strategy_rationale": "МИНИМУМ 50 СЛОВ. Экспертный текст, связывающий данные графиков с выбором SMM."
}
""";
}