Automation_Threads_EU / settings_manager.py
FincH12's picture
Deploy Dynamic Dashboard, Analytics and Prompts Editor
fd40f81 verified
Raw History Blame Contribute Delete
10.4 kB
import json
import os
SETTINGS_PATH = os.path.join(os.path.dirname(os.path.abspath(__file__)), "settings.json")
DEFAULT_SETTINGS = {
# Расписание
"MORNING_SLOT_START": "08:30",
"MORNING_SLOT_END": "10:00",
"EVENING_SLOT_START": "18:30",
"EVENING_SLOT_END": "20:00",
"DAILY_CAROUSELS_LIMIT": 1,
"DAILY_SINGLE_POSTS_LIMIT": 1,
"CAROUSEL_SLIDE_COUNT": 5,
# Промпты
"PROMPT_SINGLE": """Використовуючи наступний новинний контекст:
\"\"\"{news_context}\"\"\"
{exclude_str}
Створи 1 одиночний пост для Threads українською мовою. Вибери одну найцікавішу новину з фокусом на одну з тем: ІІ-безпека/етика, DeFi/криптовалюти, або стартапи/тех-сектор.
⚡ ТВОЇ СУПЕРСИЛИ (SKILLS) & КРИТИЧНІ ПРАВИЛА:
1. РОЛЬ: SENIOR SOCIAL MEDIA COPYWRITER (Текст посту)
- Психологія: Пиши максимально живим, людським стилем (як реальний експерт у Threads), уникаючи будь-якого ШІ-жаргону. Тон: {tone}.
- Позиція та думка: КАТЕГОРИЧНО ЗАБОРОНЕНО використовувати шаблон "[Факт]. [Риторичний вопрос]. Деталі...". Замість цього додай власну чітку експертну думку/позицію перед будь-яким запитанням (наприклад: "Я вважаю X, тому що Y. А як до цього ставитесь ви?"). Позиція має бути до запитання, а не замість неї. Уникай пустих риторичних питань.
- Самодостатність: Пост має бути повністю самодостатнім і нести цінність одразу в тексті. Посилання або картинка — лише доповнення, а не привід клікати.
- Заголовки: Пиши заголовки-крючки (hook), що чіпляють увагу, а не нудні заголовки-новини.
- Посилання: КАТЕГОРИЧНО ЗАБОРОНЕНО вставляти будь-які URL або посилання в полі description. Посилання на джерело має повертатися виключно окремо в ключі source_url.
- Хештеги: КАТЕГОРИЧНО ЗАБОРОНЕНО використовувати масові теги (#AI, #Crypto, #ШІ, #Технології). Використовуй лише 1-2 вузьких тега максимум (наприклад, #DeFiУкраїна, #LLMбезпека, #ХарківTech). Розташовуй теги строго в самому кінці тексту.
2. РОЛЬ: ART DIRECTOR & UI/UX DESIGNER (Візуал)
- Дизайн фону: Ти створюєш преміальні промпти для генерації зображень (Flux.1). Ти ідеально відчуваєш композицію, тому завжди вимагаєш "clean negative space" для читабельності тексту.
- Копірайт для карток: Заголовок картки — до 4 слів (punchy). Тези — до 8 слів, тільки саме "м'ясо".
Поверни результат строго у форматі JSON із наступними ключами:
{
"category": "одна з трьох категорій: 'AI', 'Business' або 'Crypto'",
"bg_prompt": "англійською мовою детальний промпт для генерації фону (Flux.1). Premium dark aesthetics, volumetric lighting, glowing elements, background only, smooth clean negative space, absolutely no text",
"card_title": "короткий заголовок (до 4 слів, без води)",
"card_bullets": [
"теза 1 (чіткий факт до 8 слів)",
"теза 2 (висновок або інсайт до 8 слів)"
],
"description": "Супровідний текст посту (до 400 символів). Жива мова з власною позицією, без шаблонів. Жодних посилань/URL у цьому тексті! Строго 1-2 вузьких тега в самому кінці.",
"source_url": "коротке посилання на першоджерело новини (обов'язково)"
}
Повертай ТІЛЬКИ чистий JSON-об'єкт.""",
"PROMPT_CAROUSEL": """Використовуючи наступний новинний контекст:
\"\"\"{news_context}\"\"\"
{exclude_str}
Створи глибокий розбір однієї з новин у вигляді каруселі з {slide_count} слайдів для Threads українською мовою з фокусом на теми: безпека/етика ІІ, DeFi/криптовалюти, або стартапи/тех-сфера.
⚡ ТВОЇ СУПЕРСИЛИ (SKILLS) & КРИТИЧНІ ПРАВИЛА:
1. РОЛЬ: SENIOR SOCIAL MEDIA COPYWRITER
- Сюжет: Будуй карусель як історію (Curiosity Gap). Кожен слайд змушує свайпнути далі. Тон: {tone}.
- Текст посту: Напиши коментар автора до каруселі. Він має бути повністю самодостатнім, нести самостійну цінність та містити твою чітку експертну думку/позицію перед питанням до аудиторії.
- Заборонені шаблони: КАТЕГОРИЧНО ЗАБОРОНЕНО використовувати шаблони на кшталт "[Факт]. [Риторичне питання]. Деталі в каруселі. Джерело". Натомість використовуй заголовок-крючок (hook).
- Заборонені фрази: Уникай типових ШІ-фразочок ("безумовно", "у сучасному світі", "у світі технологій"). Пиши як реальний живий експерт.
- Посилання: КАТЕГОРИЧНО ЗАБОРОНЕНО вставляти будь-які URL або посилання в полі description. Посилання на джерело має повертатися виключно окремо в ключі source_url.
- Хештеги: КАТЕГОРИЧНО ЗАБОРОНЕНО використовувати масові теги (#AI, #Crypto, #ШІ, #Технології). Використовуй лише 1-2 вузьких тега максимум. Розташовуй теги строго в самому кінці тексту.
2. РОЛЬ: ART DIRECTOR & UI/UX DESIGNER
- Фонова динаміка: Ти пишеш промпти для фонів так, щоб вони еволюціонували від слайду до слайду, зберігаючи загальну кінематографічную стилістику (premium dark aesthetics, neon, volumetric lighting).
- Читабельність: Завжди гарантуй вільний простір для тексту ('smooth clean negative space, absolutely no text').
Поверни результат строго у форматі JSON із наступними ключами:
{
"category": "одна з трьох категорій: 'AI', 'Business' або 'Crypto'",
"description": "Супровідний текст посту (до 350 символів). Жива людська мова, що виражає твою позицію та інтригує переглянути карусель. Жодних посилань/URL у цьому полі! Строго 1-2 вузьких тега в самому кінці.",
"source_url": "коротке посилання на першоджерело новини (обов'язково)",
"slides": [ масив з {slide_count} об'єктів слайдів: { "title": "...", "bullets": ["...", "..."], "bg_prompt": "..." } ]
}
Повертай ТІЛЬКИ чистий JSON-об'єкт.""",
"PROMPT_PREDICTOR": """Ты — AI-редактор и эксперт по виральному контенту в соцсетях.
Твоя задача — оценить черновик поста для Threads перед его публикацией.
{context}
Черновик поста:
--- {post_text} ---
Оцени потенциал этого поста по 10-балльной шкале (где 10 — абсолютный хит, а 1 — скучная новостная сводка, которую никто не лайкнет).
Пост должен иметь мощный 'крючок' (hook) в первом предложении, вызывать эмоции (шок, интерес, несогласие) и стимулировать дискуссию в комментариях.
Верни СТРОГО JSON:
{
"score": 8,
"criticism": "оставь пустым, если балл >= 7, иначе напиши 1-2 предложения, что именно изменить"
}
Возвращай только чистый JSON без markdown."""
}
def load_settings():
if not os.path.exists(SETTINGS_PATH):
return DEFAULT_SETTINGS.copy()
try:
with open(SETTINGS_PATH, "r", encoding="utf-8") as f:
data = json.load(f)
# Merge with defaults to ensure all keys exist
merged = DEFAULT_SETTINGS.copy()
merged.update(data)
return merged
except Exception as e:
print(f"[SettingsManager] Ошибка чтения settings.json: {e}")
return DEFAULT_SETTINGS.copy()
def save_settings(new_settings):
try:
current = load_settings()
current.update(new_settings)
with open(SETTINGS_PATH, "w", encoding="utf-8") as f:
json.dump(current, f, ensure_ascii=False, indent=2)
return True
except Exception as e:
print(f"[SettingsManager] Ошибка записи settings.json: {e}")
return False