Initial commit: Message Gateway project

- FastAPI приложение для отправки мониторинговых алертов в мессенджеры
- Поддержка Telegram и MAX/VK
- Интеграция с Grafana, Zabbix, AlertManager
- Автоматическое создание тикетов в Jira
- Управление группами мессенджеров через API
- Декораторы для авторизации и скрытия эндпоинтов
- Подробная документация в папке docs/

Автор: Сергей Антропов
Сайт: https://devops.org.ru
This commit is contained in:
2025-11-12 20:25:11 +03:00
commit b90def35ed
72 changed files with 10609 additions and 0 deletions

127
app/core/button_utils.py Normal file
View File

@@ -0,0 +1,127 @@
"""
Утилиты для работы с кнопками в различных мессенджерах.
Автор: Сергей Антропов
Сайт: https://devops.org.ru
"""
import logging
from typing import Optional, Dict, Any, List
from telegram import InlineKeyboardButton, InlineKeyboardMarkup
logger = logging.getLogger(__name__)
def convert_telegram_buttons_to_dict(buttons: Optional[InlineKeyboardMarkup]) -> Optional[Dict[str, Any]]:
"""
Преобразовать кнопки Telegram (InlineKeyboardMarkup) в универсальный формат Dict.
Args:
buttons: InlineKeyboardMarkup с кнопками или None.
Returns:
Словарь с кнопками в универсальном формате или None.
Формат:
{
"inline_keyboard": [
[
{"text": "Кнопка 1", "url": "https://example.com"},
{"text": "Кнопка 2", "url": "https://example2.com"}
],
[
{"text": "Кнопка 3", "url": "https://example3.com"}
]
]
}
"""
if buttons is None:
return None
if not isinstance(buttons, InlineKeyboardMarkup):
logger.warning(f"Неизвестный тип кнопок: {type(buttons)}")
return None
inline_keyboard = []
for row in buttons.inline_keyboard:
row_buttons = []
for button in row:
if isinstance(button, InlineKeyboardButton):
button_dict = {"text": button.text}
if button.url:
button_dict["url"] = button.url
if button.callback_data:
button_dict["callback_data"] = button.callback_data
row_buttons.append(button_dict)
if row_buttons:
inline_keyboard.append(row_buttons)
if not inline_keyboard:
return None
return {"inline_keyboard": inline_keyboard}
def convert_dict_to_telegram_buttons(buttons_dict: Optional[Dict[str, Any]]) -> Optional[InlineKeyboardMarkup]:
"""
Преобразовать универсальный формат Dict в кнопки Telegram (InlineKeyboardMarkup).
Args:
buttons_dict: Словарь с кнопками в универсальном формате или None.
Returns:
InlineKeyboardMarkup с кнопками или None.
"""
if buttons_dict is None:
return None
inline_keyboard_data = buttons_dict.get("inline_keyboard", [])
if not inline_keyboard_data:
return None
inline_keyboard = []
for row in inline_keyboard_data:
row_buttons = []
for button_data in row:
if isinstance(button_data, dict):
text = button_data.get("text")
url = button_data.get("url")
callback_data = button_data.get("callback_data")
if text:
if url:
row_buttons.append(InlineKeyboardButton(text=text, url=url))
elif callback_data:
row_buttons.append(InlineKeyboardButton(text=text, callback_data=callback_data))
if row_buttons:
inline_keyboard.append(row_buttons)
if not inline_keyboard:
return None
return InlineKeyboardMarkup(inline_keyboard)
def convert_dict_to_vk_buttons(buttons_dict: Optional[Dict[str, Any]]) -> Optional[str]:
"""
Преобразовать универсальный формат Dict в кнопки VK (JSON строка).
Args:
buttons_dict: Словарь с кнопками в универсальном формате или None.
Returns:
JSON строка с кнопками для VK API или None.
"""
if buttons_dict is None:
return None
inline_keyboard_data = buttons_dict.get("inline_keyboard", [])
if not inline_keyboard_data:
return None
# Формируем клавиатуру для VK API
# VK API использует другой формат клавиатуры
# Для простоты возвращаем None, так как VK API требует более сложной структуры
# В реальной реализации нужно преобразовать в формат VK Keyboard
logger.warning("Преобразование кнопок в формат VK пока не реализовано полностью")
return None