diff --git a/README.md b/README.md index ad2834b..3d4eb87 100644 --- a/README.md +++ b/README.md @@ -1,228 +1 @@ -# 🎲 GM-Relay: TTRPG Session Scheduling Bot & Web Dashboard - -**GM-Relay** β€” это комплСксноС Ρ€Π΅ΡˆΠ΅Π½ΠΈΠ΅ для ΠœΠ°ΡΡ‚Π΅Ρ€ΠΎΠ² ПодзСмСлий (Π“ΠœΠΎΠ²), состоящСС ΠΈΠ· Π²Ρ‹ΡΠΎΠΊΠΎΠΏΡ€ΠΎΠΈΠ·Π²ΠΎΠ΄ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎΠ³ΠΎ Telegram-Π±ΠΎΡ‚Π° ΠΈ ΡƒΠ΄ΠΎΠ±Π½ΠΎΠ³ΠΎ Π²Π΅Π±-интСрфСйса. ΠŸΡ€Π΅Π΄Π½Π°Π·Π½Π°Ρ‡Π΅Π½ΠΎ для Π°Π²Ρ‚ΠΎΠΌΠ°Ρ‚ΠΈΠ·Π°Ρ†ΠΈΠΈ записи ΠΈΠ³Ρ€ΠΎΠΊΠΎΠ² Π½Π° сСссии, управлСния расписаниСм ΠΈ провСдСния ΠΈΠ³Ρ€. - -ΠŸΡ€ΠΎΠ΅ΠΊΡ‚ Ρ€Π°Π·Ρ€Π°Π±ΠΎΡ‚Π°Π½ с ΡƒΠΏΠΎΡ€ΠΎΠΌ Π½Π° ΠΏΡ€ΠΎΠΈΠ·Π²ΠΎΠ΄ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎΡΡ‚ΡŒ, Π°Ρ€Ρ…ΠΈΡ‚Π΅ΠΊΡ‚ΡƒΡ€Ρƒ Vertical Slice, Native AOT (для Π±ΠΎΡ‚Π°) ΠΈ удобство развСртывания с использованиСм .NET Aspire. - -**ВСкущая вСрсия:** `v1.9.9`. - ---- - -## ✨ ΠšΠ»ΡŽΡ‡Π΅Π²Ρ‹Π΅ возмоТности - -### πŸ€– Telegram Π‘ΠΎΡ‚ -- **πŸ“… Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ расписаний (Batch Sessions)**: Π‘ΠΎΠ·Π΄Π°Π²Π°ΠΉΡ‚Π΅ сразу нСсколько ΠΈΠ³Ρ€ ΠΎΠ΄Π½ΠΈΠΌ сообщСниСм (Π½Π° нСдСлю ΠΈΠ»ΠΈ мСсяц Π²ΠΏΠ΅Ρ€Π΅Π΄). -- **πŸ–Ό ОблоТки расписаний**: К batch-посту ΠΌΠΎΠΆΠ½ΠΎ ΠΏΡ€ΠΈΠΊΡ€Π΅ΠΏΠΈΡ‚ΡŒ Ρ„ΠΎΡ‚ΠΎ ΠΊ `/newsession` ΠΈΠ»ΠΈ ΡƒΠΊΠ°Π·Π°Ρ‚ΡŒ строку `ΠšΠ°Ρ€Ρ‚ΠΈΠ½ΠΊΠ°: https://...`; Π±ΠΎΡ‚ ΠΎΡ‚ΠΏΡ€Π°Π²ΠΈΡ‚ ΠΎΠ±Π»ΠΎΠΆΠΊΡƒ ΠΏΠ΅Ρ€Π΅Π΄ сообщСниСм записи. -- **⚑ БыстрыС ΠΏΠΎΠ²Ρ‚ΠΎΡ€Ρ‹ расписания**: Для рСгулярной ΠΊΠ°ΠΌΠΏΠ°Π½ΠΈΠΈ ΠΌΠΎΠΆΠ½ΠΎ ΡƒΠΊΠ°Π·Π°Ρ‚ΡŒ ΠΎΠ΄Π½Ρƒ Π΄Π°Ρ‚Ρƒ, количСство ΠΈΠ³Ρ€ ΠΈ ΠΈΠ½Ρ‚Π΅Ρ€Π²Π°Π», Π° Π±ΠΎΡ‚ сам Ρ€Π°Π·Π²Π΅Ρ€Π½Ρ‘Ρ‚ ΠΏΠΎΠ²Ρ‚ΠΎΡ€ΡΡŽΡ‰ΠΈΠΉΡΡ batch. -- **βœ‹ Π˜Π½Ρ‚Π΅Ρ€Π°ΠΊΡ‚ΠΈΠ²Π½Π°Ρ запись ΠΈ Π²Ρ‹Ρ…ΠΎΠ΄**: Π˜Π³Ρ€ΠΎΠΊΠΈ Π·Π°ΠΏΠΈΡΡ‹Π²Π°ΡŽΡ‚ΡΡ Π½Π° ΠΊΠΎΠ½ΠΊΡ€Π΅Ρ‚Π½Ρ‹Π΅ Π΄Π°Ρ‚Ρ‹ ΠΈ ΡΠ°ΠΌΠΎΡΡ‚ΠΎΡΡ‚Π΅Π»ΡŒΠ½ΠΎ ΡΠ½ΠΈΠΌΠ°ΡŽΡ‚ запись Π½Π°ΠΆΠ°Ρ‚ΠΈΠ΅ΠΌ ΠΎΠ΄Π½ΠΎΠΉ ΠΊΠ½ΠΎΠΏΠΊΠΈ. -- **πŸ‘₯ Π›ΠΈΠΌΠΈΡ‚ мСст ΠΈ лист оТидания**: Π“Πœ Π·Π°Π΄Π°Ρ‘Ρ‚ ΠΌΠ°ΠΊΡΠΈΠΌΠ°Π»ΡŒΠ½Ρ‹ΠΉ состав, Π±ΠΎΡ‚ Π½Π΅ пСрСполняСт сСссию, автоматичСски Π²Π΅Π΄Ρ‘Ρ‚ ΠΎΡ‡Π΅Ρ€Π΅Π΄ΡŒ оТидания ΠΈ освобоТдённоС мСсто ΠΎΡ‚Π΄Π°Ρ‘Ρ‚ ΠΏΠ΅Ρ€Π²ΠΎΠΌΡƒ ΠΎΠΆΠΈΠ΄Π°ΡŽΡ‰Π΅ΠΌΡƒ. -- **πŸ“ ΠŸΠΎΠ΄Π΄Π΅Ρ€ΠΆΠΊΠ° Π€ΠΎΡ€ΡƒΠΌΠΎΠ² (Telegram Topics)**: Π‘ΠΎΡ‚ автоматичСски создаСт Ρ‚Π΅ΠΌΡƒ Π²ΠΎ Π²Π»ΠΎΠΆΠ΅Π½Π½Ρ‹Ρ… Ρ‡Π°Ρ‚Π°Ρ… Telegram ΠΏΠΎΠ΄ ΠΊΠ°ΠΆΠ΄ΡƒΡŽ Π½ΠΎΠ²ΡƒΡŽ ΠΏΠ°Ρ‡ΠΊΡƒ ΠΈΠ³Ρ€. -- **❌ Π£ΠΏΡ€Π°Π²Π»Π΅Π½ΠΈΠ΅ сСссиями**: Owner ΠΈ Π½Π°Π·Π½Π°Ρ‡Π΅Π½Π½Ρ‹Π΅ co-GM ΠΌΠΎΠ³ΡƒΡ‚ ΡΠΎΠ·Π΄Π°Π²Π°Ρ‚ΡŒ, ΠΎΡ‚ΠΌΠ΅Π½ΡΡ‚ΡŒ, ΡƒΠ΄Π°Π»ΡΡ‚ΡŒ ΠΈ ΠΏΠ΅Ρ€Π΅Π½ΠΎΡΠΈΡ‚ΡŒ ΠΈΠ³Ρ€Ρ‹ ΠΈΠ· Telegram Ρ‡Π΅Ρ€Π΅Π· `/listsessions`; ΠΏΡƒΠ±Π»ΠΈΡ‡Π½Ρ‹ΠΉ пост записи ΠΏΠΎΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ ΠΊΠ½ΠΎΠΏΠΊΠΈ ΠΈΠ³Ρ€ΠΎΠΊΠΎΠ². -- **πŸ”„ ГолосованиС Π·Π° пСрСнос**: ΠŸΡ€ΠΈ пСрСносС сСссии GM ΠΏΡ€Π΅Π΄Π»Π°Π³Π°Π΅Ρ‚ 2-3 Π½ΠΎΠ²Ρ‹Ρ… Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ ΠΈ Π΄Π΅Π΄Π»Π°ΠΉΠ½, ΠΈΠ³Ρ€ΠΎΠΊΠΈ Π³ΠΎΠ»ΠΎΡΡƒΡŽΡ‚ ΠΊΠ½ΠΎΠΏΠΊΠ°ΠΌΠΈ, Π° Π±ΠΎΡ‚ ΠΏΠΎΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ Ρ‚Π΅ΠΊΡƒΡ‰ΠΈΠ΅ Ρ€Π΅Π·ΡƒΠ»ΡŒΡ‚Π°Ρ‚Ρ‹ ΠΈ примСняСт побСдивший Π²Π°Ρ€ΠΈΠ°Π½Ρ‚. -- **πŸ”” ΠŸΠ΅Ρ€ΡΠΎΠ½Π°Π»ΡŒΠ½Ρ‹Π΅ увСдомлСния**: Π˜Π³Ρ€ΠΎΠΊΠΈ ΠΏΠΎΠ»ΡƒΡ‡Π°ΡŽΡ‚ DM ΠΎ RSVP Π·Π° 24 часа, Π½Π°ΠΏΠΎΠΌΠΈΠ½Π°Π½ΠΈΠ΅ Π·Π° 1 час, ссылку ΠΏΠ΅Ρ€Π΅Π΄ ΠΈΠ³Ρ€ΠΎΠΉ, ΠΎΡ‚ΠΌΠ΅Π½Ρ‹ ΠΈ пСрСносы; Π³Ρ€ΡƒΠΏΠΏΠΎΠ²Ρ‹Π΅ увСдомлСния ΠΏΡ€ΠΈ этом ΠΎΡΡ‚Π°ΡŽΡ‚ΡΡ. -- **πŸ—“ Экспорт Π² ΠšΠ°Π»Π΅Π½Π΄Π°Ρ€ΡŒ**: ГСнСрация Ρ„Π°ΠΉΠ»Π° `.ics` для добавлСния всСх ΠΈΠ³Ρ€ Π² Google, Apple ΠΈΠ»ΠΈ ЯндСкс ΠšΠ°Π»Π΅Π½Π΄Π°Ρ€ΡŒ ΠΎΠ΄Π½ΠΎΠΉ ΠΊΠΎΠΌΠ°Π½Π΄ΠΎΠΉ. -- **πŸš€ Native AOT**: Π‘ΠΊΠΎΠΌΠΏΠΈΠ»ΠΈΡ€ΠΎΠ²Π°Π½ Π² Π½Π°Ρ‚ΠΈΠ²Π½Ρ‹ΠΉ Π±ΠΈΠ½Π°Ρ€Π½Ρ‹ΠΉ Ρ„Π°ΠΉΠ». ΠœΠ³Π½ΠΎΠ²Π΅Π½Π½Ρ‹ΠΉ запуск ΠΈ минимальноС ΠΏΠΎΡ‚Ρ€Π΅Π±Π»Π΅Π½ΠΈΠ΅ памяти. ИдСально для **Raspberry Pi**. - -### 🌐 Web Dashboard (Blazor Server) -- **πŸ” Авторизация Ρ‡Π΅Ρ€Π΅Π· Telegram**: БСзопасный Π²Ρ…ΠΎΠ΄ с использованиСм Telegram Login Widget (HMAC-SHA256 валидация). -- **πŸ“± Telegram Mini App Dashboard**: Мобильная вСрсия dashboard открываСтся прямо ΠΈΠ· Telegram, провСряСт WebApp `initData` Π½Π° сСрвСрС ΠΈ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ Ρ‚Π΅ ΠΆΠ΅ ΠΏΡ€Π°Π²Π° owner/co-GM, Ρ‡Ρ‚ΠΎ ΠΈ ΠΎΠ±Ρ‹Ρ‡Π½Ρ‹ΠΉ Web Dashboard. Если Mini App ΠΏΠΎΠΏΠ°Π΄Π°Π΅Ρ‚ Π² fallback-Π²Ρ…ΠΎΠ΄, Telegram Login Widget Π°Π²Ρ‚ΠΎΡ€ΠΈΠ·ΡƒΠ΅Ρ‚ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»Ρ callback-запросом Π²Π½ΡƒΡ‚Ρ€ΠΈ Ρ‚Π΅ΠΊΡƒΡ‰Π΅Π³ΠΎ WebView, Π° интСрфСйс ΡƒΡ‡ΠΈΡ‚Ρ‹Π²Π°Π΅Ρ‚ safe-area Ρ‚Π΅Π»Π΅Ρ„ΠΎΠ½Π° ΠΈ Π²Π΅Ρ€Ρ…Π½ΡŽΡŽ панСль Telegram. -- **πŸ“ Π£Π΄ΠΎΠ±Π½ΠΎΠ΅ Ρ€Π΅Π΄Π°ΠΊΡ‚ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅**: Π’Π΅Π±-интСрфСйс для Π΄Π΅Ρ‚Π°Π»ΡŒΠ½ΠΎΠ³ΠΎ рСдактирования сСссий, измСнСния Π΄Π°Ρ‚, Π½Π°Π·Π²Π°Π½ΠΈΠΉ ΠΈ статусов. -- **🀝 Co-GM ΠΈ Π΄Π΅Π»Π΅Π³ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅**: Owner Π³Ρ€ΡƒΠΏΠΏΡ‹ Π½Π°Π·Π½Π°Ρ‡Π°Π΅Ρ‚ ΠΏΠΎΠΌΠΎΡ‰Π½ΠΈΠΊΠΎΠ² ΠΏΠΎ Telegram ID, Π° co-GM ΠΏΠΎΠ»ΡƒΡ‡Π°Π΅Ρ‚ доступ ΠΊ ΡƒΠΏΡ€Π°Π²Π»Π΅Π½ΠΈΡŽ расписаниСм Π² Telegram ΠΈ Web Dashboard. -- **πŸ“‹ Π¨Π°Π±Π»ΠΎΠ½Ρ‹ ΠΊΠ°ΠΌΠΏΠ°Π½ΠΈΠΉ**: Owner ΠΈ co-GM ΡƒΠΏΡ€Π°Π²Π»ΡΡŽΡ‚ Ρ‚ΠΈΠΏΠΎΠ²Ρ‹ΠΌΠΈ ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Π°ΠΌΠΈ ΠΊΠ°ΠΌΠΏΠ°Π½ΠΈΠΉ Π² ΠΎΡ‚Π΄Π΅Π»ΡŒΠ½ΠΎΠΉ Π²ΠΊΠ»Π°Π΄ΠΊΠ΅ `Π¨Π°Π±Π»ΠΎΠ½Ρ‹`, Π° Π½Π° страницС Π³Ρ€ΡƒΠΏΠΏΡ‹ Π·Π°ΠΏΡƒΡΠΊΠ°ΡŽΡ‚ Π½ΠΎΠ²Ρ‹ΠΉ ΠΏΠΎΠ²Ρ‚ΠΎΡ€ΡΡŽΡ‰ΠΈΠΉΡΡ batch ΠΈΠ· Π²Ρ‹Π±Ρ€Π°Π½Π½ΠΎΠ³ΠΎ шаблона. -- **🧩 Bulk-ΠΎΠΏΠ΅Ρ€Π°Ρ†ΠΈΠΈ для Batch Sessions**: Π“Πœ ΠΌΠΎΠΆΠ΅Ρ‚ ΠΎΠ±Π½ΠΎΠ²ΠΈΡ‚ΡŒ ΠΎΠ±Ρ‰ΠΈΠΉ title/link, пСрСнСсти всю ΠΏΠ°Ρ‡ΠΊΡƒ Π½Π° фиксированный шаг ΠΈ ΠΊΠ»ΠΎΠ½ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ batch Π½Π° ΡΠ»Π΅Π΄ΡƒΡŽΡ‰ΡƒΡŽ нСдСлю ΠΈΠ»ΠΈ мСсяц. -- **πŸ”• Π Π΅ΠΆΠΈΠΌ ΡƒΠ²Π΅Π΄ΠΎΠΌΠ»Π΅Π½ΠΈΠΉ batch**: Для ΠΊΠ°ΠΆΠ΄ΠΎΠΉ ΠΏΠ°Ρ‡ΠΊΠΈ ΠΌΠΎΠΆΠ½ΠΎ Π²Ρ‹Π±Ρ€Π°Ρ‚ΡŒ `Π’ Π³Ρ€ΡƒΠΏΠΏΠ΅ ΠΈ Π² Π»ΠΈΡ‡ΠΊΡƒ` ΠΈΠ»ΠΈ `Волько Π² Π³Ρ€ΡƒΠΏΠΏΠ΅`. -- **⬆️ Π£ΠΏΡ€Π°Π²Π»Π΅Π½ΠΈΠ΅ ΠΎΡ‡Π΅Ρ€Π΅Π΄ΡŒΡŽ**: Π’Π΅Π±-интСрфСйс ΠΏΠΎΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ Π·Π°ΠΏΠΎΠ»Π½Π΅Π½Π½ΠΎΡΡ‚ΡŒ, лист оТидания ΠΈ позволяСт Π“ΠœΡƒ ΠΏΠΎΠ΄Π½ΡΡ‚ΡŒ ΠΏΠ΅Ρ€Π²ΠΎΠ³ΠΎ ΠΈΠ³Ρ€ΠΎΠΊΠ° ΠΈΠ· ΠΎΡ‡Π΅Ρ€Π΅Π΄ΠΈ. -- **πŸ”„ АвтоматичСская синхронизация**: Π›ΡŽΠ±Ρ‹Π΅ измСнСния Π² Π²Π΅Π±-интСрфСйсС ΠΌΠ³Π½ΠΎΠ²Π΅Π½Π½ΠΎ ΠΎΠ±Π½ΠΎΠ²Π»ΡΡŽΡ‚ сообщСния с расписаниСм Π² Telegram-Ρ‡Π°Ρ‚Π°Ρ… ΠΈΠ³Ρ€ΠΎΠΊΠΎΠ². -- **πŸ•’ Π£ΠΏΡ€Π°Π²Π»Π΅Π½ΠΈΠ΅ Π²Ρ€Π΅ΠΌΠ΅Π½Π΅ΠΌ**: UI Π°Π΄Π°ΠΏΡ‚ΠΈΡ€ΠΎΠ²Π°Π½ ΠΏΠΎΠ΄ московскоС врСмя (UTC+3), Π² Ρ‚ΠΎ врСмя ΠΊΠ°ΠΊ Π±Π°Π·Π° Π΄Π°Π½Π½Ρ‹Ρ… Ρ€Π°Π±ΠΎΡ‚Π°Π΅Ρ‚ Π² UTC. - ---- - -## πŸ›  ВСхнологичСский стСк - -- **Π―Π·Ρ‹ΠΊ**: C# 14 (.NET 10) -- **АрхитСктура**: Vertical Slice Architecture, общая Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΠ° (`GmRelay.Shared`) для Π΄ΠΎΠΌΠ΅Π½Π½ΠΎΠΉ Π»ΠΎΠ³ΠΈΠΊΠΈ. -- **Π‘ΠΎΡ‚**: Telegram.Bot, Native AOT. -- **Π’Π΅Π±-интСрфСйс**: Blazor Server. -- **ΠžΡ€ΠΊΠ΅ΡΡ‚Ρ€Π°Ρ†ΠΈΡ**: .NET Aspire (`GmRelay.AppHost`). -- **Π‘Π°Π·Π° Π΄Π°Π½Π½Ρ‹Ρ…**: PostgreSQL -- **ORM**: Dapper (с использованиСм Dapper.AOT для source generators). -- **ΠœΠΈΠ³Ρ€Π°Ρ†ΠΈΠΈ**: DbUp. -- **Π Π°Π·Π²Π΅Ρ€Ρ‚Ρ‹Π²Π°Π½ΠΈΠ΅**: Docker Compose + Multi-arch (AMD64/ARM64). - ---- - -## πŸš€ Быстрый старт (Docker Compose) - -ΠŸΡ€ΠΎΠ΅ΠΊΡ‚ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ Docker Compose для ΠΎΠ΄Π½ΠΎΠ²Ρ€Π΅ΠΌΠ΅Π½Π½ΠΎΠ³ΠΎ запуска Π±Π°Π·Ρ‹ Π΄Π°Π½Π½Ρ‹Ρ…, Π±ΠΎΡ‚Π° ΠΈ Π²Π΅Π±-интСрфСйса. - -### 1. ΠŸΠΎΠ΄Π³ΠΎΡ‚ΠΎΠ²ΠΊΠ° -Π£Π±Π΅Π΄ΠΈΡ‚Π΅ΡΡŒ, Ρ‡Ρ‚ΠΎ Ρƒ вас установлСны **Docker** ΠΈ **Docker Compose**. - -### 2. Настройка окруТСния -Π‘ΠΊΠΎΠΏΠΈΡ€ΡƒΠΉΡ‚Π΅ Ρ„Π°ΠΉΠ»-шаблон ΠΈ Π·Π°ΠΏΠΎΠ»Π½ΠΈΡ‚Π΅ Π΅Π³ΠΎ значСниями: - -```bash -cp .env.example .env -``` - -ΠžΡ‚Ρ€Π΅Π΄Π°ΠΊΡ‚ΠΈΡ€ΡƒΠΉΡ‚Π΅ `.env`: - -```env -# Π’ΠΎΠΊΠ΅Π½ вашСго Π±ΠΎΡ‚Π° ΠΎΡ‚ @BotFather (ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ ΠΈ для Π±ΠΎΡ‚Π°, ΠΈ ΠΊΠ°ΠΊ сСкрСтный ΠΊΠ»ΡŽΡ‡ для Π²Π΅Π±-Π°Π²Ρ‚ΠΎΡ€ΠΈΠ·Π°Ρ†ΠΈΠΈ) -TELEGRAM_BOT_TOKEN=ваш_Ρ‚ΠΎΠΊΠ΅Π½_здСсь - -# Имя вашСго Π±ΠΎΡ‚Π° Π² Telegram (Π±Π΅Π· @), Π½Π°ΠΏΡ€ΠΈΠΌΠ΅Ρ€: GmRelayBot. -# Найти Π΅Π³ΠΎ ΠΌΠΎΠΆΠ½ΠΎ Π² ΠΈΠ½Ρ„ΠΎΡ€ΠΌΠ°Ρ†ΠΈΠΈ ΠΎ Π±ΠΎΡ‚Π΅ Ρƒ @BotFather. -# Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ для Ρ€Π°Π±ΠΎΡ‚Ρ‹ Π²ΠΈΠ΄ΠΆΠ΅Ρ‚Π° Π°Π²Ρ‚ΠΎΡ€ΠΈΠ·Π°Ρ†ΠΈΠΈ (Telegram Login Widget). -TELEGRAM_BOT_USERNAME=вашС_имя_Π±ΠΎΡ‚Π°_здСсь - -# HTTPS URL Mini App dashboard, Π½Π°ΠΏΡ€ΠΈΠΌΠ΅Ρ€: https://your-domain.example/miniapp. -# Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ ΠΊΠ½ΠΎΠΏΠΊΠΎΠΉ мСню Telegram ΠΈ ΠΊΠ½ΠΎΠΏΠΊΠΎΠΉ /start. -TELEGRAM_MINI_APP_URL=https://your-domain.example/miniapp - -# ΠŸΠ°Ρ€ΠΎΠ»ΡŒ для Π±Π°Π·Ρ‹ Π΄Π°Π½Π½Ρ‹Ρ… PostgreSQL -POSTGRES_PASSWORD=ваш_Π½Π°Π΄Π΅ΠΆΠ½Ρ‹ΠΉ_ΠΏΠ°Ρ€ΠΎΠ»ΡŒ - -# Π›ΠΎΠΊΠ°Π»ΡŒΠ½Ρ‹ΠΉ ΠΏΠΎΡ€Ρ‚ Π²Π΅Π±-интСрфСйса GM-Relay -GMRELAY_WEB_PORT=8080 -``` - -*(ΠžΠΏΡ†ΠΈΠΎΠ½Π°Π»ΡŒΠ½ΠΎ)* НастройтС Π΄ΠΎΠΌΠ΅Π½ Telegram Π±ΠΎΡ‚Π° Π² @BotFather ΠΊΠΎΠΌΠ°Π½Π΄ΠΎΠΉ `/setdomain` для Ρ€Π°Π±ΠΎΡ‚Ρ‹ Π²ΠΈΠ΄ΠΆΠ΅Ρ‚Π° Π°Π²Ρ‚ΠΎΡ€ΠΈΠ·Π°Ρ†ΠΈΠΈ Π½Π° вашСм сайтС. - -Для Telegram Mini App настройтС Π² @BotFather Π΄ΠΎΠΌΠ΅Π½ Web Dashboard ΠΈ menu button Π½Π° URL ΠΈΠ· `TELEGRAM_MINI_APP_URL`. Π‘ΠΎΡ‚ Ρ‚Π°ΠΊΠΆΠ΅ ΠΏΠΎΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ ΠΊΠ½ΠΎΠΏΠΊΡƒ `ΠžΡ‚ΠΊΡ€Ρ‹Ρ‚ΡŒ dashboard` Π² ΠΎΡ‚Π²Π΅Ρ‚Π΅ Π½Π° `/start`, Ссли пСрСмСнная Π·Π°Π΄Π°Π½Π°. Начиная с v1.9.3 Π΄ΠΎΠΏΠΎΠ»Π½ΠΈΡ‚Π΅Π»ΡŒΠ½Ρ‹Ρ… дСйствий Π² BotFather для фикса Π²Ρ…ΠΎΠ΄Π° Π½Π΅ трСбуСтся: URL остаётся Ρ‚Π΅ΠΌ ΠΆΠ΅ HTTPS-адрСсом `/miniapp`, Π° fallback-Π²Ρ…ΠΎΠ΄ выполняСтся Π²Π½ΡƒΡ‚Ρ€ΠΈ Π°ΠΊΡ‚ΠΈΠ²Π½ΠΎΠ³ΠΎ Telegram WebView. - -### 3. Запуск -Π’Ρ‹ΠΏΠΎΠ»Π½ΠΈΡ‚Π΅ ΠΊΠΎΠΌΠ°Π½Π΄Ρƒ: -```bash -docker compose up -d -``` -Π˜Π½Ρ„Ρ€Π°ΡΡ‚Ρ€ΡƒΠΊΡ‚ΡƒΡ€Π° автоматичСски: -- Боздаст Π»ΠΎΠΊΠ°Π»ΡŒΠ½ΡƒΡŽ Docker-ΡΠ΅Ρ‚ΡŒ ΠΈ volume PostgreSQL, Ссли ΠΈΡ… Π΅Ρ‰Ρ‘ Π½Π΅Ρ‚. -- ΠŸΠΎΠ΄Π½ΠΈΠΌΠ΅Ρ‚ PostgreSQL, доступный для ΠΊΠΎΠ½Ρ‚Π΅ΠΉΠ½Π΅Ρ€ΠΎΠ² ΠΊΠ°ΠΊ `db:5432`. -- Запустит Π±ΠΎΡ‚Π° (ΠΏΡ€ΠΈΠΌΠ΅Π½ΠΈΠ² ΠΌΠΈΠ³Ρ€Π°Ρ†ΠΈΠΈ Π‘Π”). -- Запустит Π²Π΅Π±-интСрфСйс Π½Π° `http://localhost:8080` ΠΈΠ»ΠΈ Π΄Ρ€ΡƒΠ³ΠΎΠΌ ΠΏΠΎΡ€Ρ‚Ρƒ ΠΈΠ· `GMRELAY_WEB_PORT`. - ---- - -## βš™οΈ Настройка Π±ΠΎΡ‚Π° Π² Telegram - -Π§Ρ‚ΠΎΠ±Ρ‹ Π±ΠΎΡ‚ Ρ€Π°Π±ΠΎΡ‚Π°Π» ΠΊΠΎΡ€Ρ€Π΅ΠΊΡ‚Π½ΠΎ: -1. **Π”ΠΎΠ±Π°Π²ΡŒΡ‚Π΅ Π±ΠΎΡ‚Π° Π² Π³Ρ€ΡƒΠΏΠΏΡƒ** (ΠΈΠ»ΠΈ Π‘ΡƒΠΏΠ΅Ρ€Π³Ρ€ΡƒΠΏΠΏΡƒ/Π€ΠΎΡ€ΡƒΠΌ). -2. **ΠΠ°Π·Π½Π°Ρ‡ΡŒΡ‚Π΅ Π±ΠΎΡ‚Π° Администратором**. -3. **НСобходимыС ΠΏΡ€Π°Π²Π°**: - * `Π’Ρ‹Π±ΠΎΡ€ Ρ‚Π΅ΠΌ` (Managed Topics) β€” **ΠΎΠ±ΡΠ·Π°Ρ‚Π΅Π»ΡŒΠ½ΠΎ** для Π€ΠΎΡ€ΡƒΠΌΠΎΠ². - * `ΠžΡ‚ΠΏΡ€Π°Π²ΠΊΠ° сообщСний`. - * `Π—Π°ΠΊΡ€Π΅ΠΏΠ»Π΅Π½ΠΈΠ΅ сообщСний` β€” рСкомСндуСтся. - -> [!TIP] -> Owner Π³Ρ€ΡƒΠΏΠΏΡ‹ опрСдСляСтся ΠΏΠΎ ΠΏΠ΅Ρ€Π²ΠΎΠΌΡƒ Ρ‡Π΅Π»ΠΎΠ²Π΅ΠΊΡƒ, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ создал сСссию Π² этой Π³Ρ€ΡƒΠΏΠΏΠ΅. Owner ΠΌΠΎΠΆΠ΅Ρ‚ Π½Π°Π·Π½Π°Ρ‡Π°Ρ‚ΡŒ co-GM Π² Web Dashboard; owner ΠΈ co-GM ΠΌΠΎΠ³ΡƒΡ‚ ΡƒΠΏΡ€Π°Π²Π»ΡΡ‚ΡŒ сСссиями Ρ‡Π΅Ρ€Π΅Π· ΠΊΠ½ΠΎΠΏΠΊΠΈ Π±ΠΎΡ‚Π° ΠΈ Π²Π΅Π±-интСрфСйс. - ---- - -## πŸ“ Π˜Π½ΡΡ‚Ρ€ΡƒΠΊΡ†ΠΈΡ для ΠœΠ°ΡΡ‚Π΅Ρ€Π° - -### Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ расписания ΠΈΠ³Ρ€ -Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠΉΡ‚Π΅ ΠΊΠΎΠΌΠ°Π½Π΄Ρƒ `/newsession` с описаниСм Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ Ρ„ΠΎΡ€ΠΌΠ°Ρ‚Π΅: - -```text -/newsession -НазваниС: Π›Π΅Π³Π΅Π½Π΄Ρ‹ Π‘Π΅Ρ€Π΅Π³Π° ΠœΠ΅Ρ‡Π΅ΠΉ (D&D 5e) -ВрСмя: 15.05.2024 19:30 -ВрСмя: 22.05.2024 19:00 -ΠœΠ΅ΡΡ‚: 4 -Бсылка: https://discord.gg/invite-link -ΠšΠ°Ρ€Ρ‚ΠΈΠ½ΠΊΠ°: https://example.com/adventure-cover.jpg -``` - -Π‘Ρ‚Ρ€ΠΎΠΊΠ° `ΠœΠ΅ΡΡ‚:` Π½Π΅ΠΎΠ±ΡΠ·Π°Ρ‚Π΅Π»ΡŒΠ½Π°. Если ΠΎΠ½Π° ΡƒΠΊΠ°Π·Π°Π½Π°, ΠΈΠ³Ρ€ΠΎΠΊΠΈ свСрх Π»ΠΈΠΌΠΈΡ‚Π° ΠΏΠΎΠΏΠ°Π΄ΡƒΡ‚ Π² лист оТидания, Π° Π“Πœ смоТСт ΠΏΠΎΠ²Ρ‹ΡΠΈΡ‚ΡŒ ΠΏΠ΅Ρ€Π²ΠΎΠ³ΠΎ ΠΎΠΆΠΈΠ΄Π°ΡŽΡ‰Π΅Π³ΠΎ Ρ‡Π΅Ρ€Π΅Π· ΠΊΠ½ΠΎΠΏΠΊΡƒ Π² Telegram ΠΈΠ»ΠΈ Web Dashboard. - -Π‘Ρ‚Ρ€ΠΎΠΊΠ° `ΠšΠ°Ρ€Ρ‚ΠΈΠ½ΠΊΠ°:` Ρ‚ΠΎΠΆΠ΅ Π½Π΅ΠΎΠ±ΡΠ·Π°Ρ‚Π΅Π»ΡŒΠ½Π°. ВмСсто ссылки ΠΌΠΎΠΆΠ½ΠΎ ΠΏΡ€ΠΈΠΊΡ€Π΅ΠΏΠΈΡ‚ΡŒ Ρ„ΠΎΡ‚ΠΎ ΠΊ ΡΠΎΠΎΠ±Ρ‰Π΅Π½ΠΈΡŽ `/newsession` ΠΈ ΠΏΠΎΠΌΠ΅ΡΡ‚ΠΈΡ‚ΡŒ ΠΊΠΎΠΌΠ°Π½Π΄Ρƒ Π² подпись ΠΊ Ρ„ΠΎΡ‚ΠΎ; Π±ΠΎΡ‚ Π²ΠΎΠ·ΡŒΠΌΡ‘Ρ‚ ΠΏΡ€ΠΈΠΊΡ€Π΅ΠΏΠ»Ρ‘Π½Π½ΠΎΠ΅ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ ΠΈ ΠΎΡ‚ΠΏΡ€Π°Π²ΠΈΡ‚ Π΅Π³ΠΎ ΠΏΠ΅Ρ€Π΅Π΄ расписаниСм. - -Для рСгулярной ΠΊΠ°ΠΌΠΏΠ°Π½ΠΈΠΈ ΠΌΠΎΠΆΠ½ΠΎ Π½Π΅ ΠΏΠ΅Ρ€Π΅Ρ‡ΠΈΡΠ»ΡΡ‚ΡŒ всС Π΄Π°Ρ‚Ρ‹ Π²Ρ€ΡƒΡ‡Π½ΡƒΡŽ. Π£ΠΊΠ°ΠΆΠΈΡ‚Π΅ ΠΎΠ΄Π½Ρƒ строку `ВрСмя:`, количСство ΠΈΠ³Ρ€ ΠΈ ΠΈΠ½Ρ‚Π΅Ρ€Π²Π°Π» Π² днях: - -```text -/newsession -НазваниС: Kingmaker -ВрСмя: 30.04.2026 19:30 -Π˜Π³Ρ€: 6 -Π˜Π½Ρ‚Π΅Ρ€Π²Π°Π»: 7 -ΠœΠ΅ΡΡ‚: 5 -Бсылка: https://discord.gg/invite-link -``` - -Π‘ΠΎΡ‚ создаст 6 ΠΈΠ³Ρ€ с Π½Π΅Π΄Π΅Π»ΡŒΠ½Ρ‹ΠΌ шагом. ВмСсто `Π˜Π³Ρ€:` Ρ‚Π°ΠΊΠΆΠ΅ принимаСтся `БСссий:` ΠΈΠ»ΠΈ `ΠŸΠΎΠ²Ρ‚ΠΎΡ€ΠΎΠ²:`, вмСсто `Π˜Π½Ρ‚Π΅Ρ€Π²Π°Π»:` β€” `Π¨Π°Π³:`. - -Π˜Π³Ρ€ΠΎΠΊ ΠΌΠΎΠΆΠ΅Ρ‚ ΡΠ°ΠΌΠΎΡΡ‚ΠΎΡΡ‚Π΅Π»ΡŒΠ½ΠΎ ΡΠ½ΡΡ‚ΡŒ запись ΠΊΠ½ΠΎΠΏΠΊΠΎΠΉ `πŸšͺ Π’Ρ‹ΠΉΡ‚ΠΈ` Π² сообщСнии расписания. Если ΠΎΠ½ Π±Ρ‹Π» Π² основном составС ΠΈ Π² листС оТидания Π΅ΡΡ‚ΡŒ ΠΈΠ³Ρ€ΠΎΠΊΠΈ, Π±ΠΎΡ‚ автоматичСски ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΈΡ‚ ΠΏΠ΅Ρ€Π²ΠΎΠ³ΠΎ ΠΎΠΆΠΈΠ΄Π°ΡŽΡ‰Π΅Π³ΠΎ Π² основной состав ΠΈ обновляСт сообщСниС ΠΏΠ°Ρ‡ΠΊΠΈ. - -### Π”Π΅Π»Π΅Π³ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ управлСния -На страницС Π³Ρ€ΡƒΠΏΠΏΡ‹ Web Dashboard ΠΏΠΎΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ owner ΠΈ список co-GM. Owner ΠΌΠΎΠΆΠ΅Ρ‚ Π΄ΠΎΠ±Π°Π²ΠΈΡ‚ΡŒ ΠΏΠΎΠΌΠΎΡ‰Π½ΠΈΠΊΠ° ΠΏΠΎ Telegram ID, ΠΈΠΌΠ΅Π½ΠΈ ΠΈ username, Π° Ρ‚Π°ΠΊΠΆΠ΅ ΡΠ½ΡΡ‚ΡŒ Ρ€ΠΎΠ»ΡŒ co-GM. НазначСнный co-GM Π²ΠΈΠ΄ΠΈΡ‚ Π³Ρ€ΡƒΠΏΠΏΡƒ Π² ΠΏΠ°Π½Π΅Π»ΠΈ управлСния ΠΈ ΠΌΠΎΠΆΠ΅Ρ‚ Ρ€Π΅Π΄Π°ΠΊΡ‚ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ сСссии, ΡƒΠΏΡ€Π°Π²Π»ΡΡ‚ΡŒ batch-опСрациями, ΠΎΡ‡Π΅Ρ€Π΅Π΄ΡŒΡŽ, пСрСносами ΠΈ ΡƒΠ΄Π°Π»Π΅Π½ΠΈΠ΅ΠΌ ΠΈΠ³Ρ€, Π½ΠΎ Π½Π΅ ΠΌΠΎΠΆΠ΅Ρ‚ Π½Π°Π·Π½Π°Ρ‡Π°Ρ‚ΡŒ Π΄Ρ€ΡƒΠ³ΠΈΡ… co-GM. - -### ΠŸΠ΅Ρ€Π΅Π½ΠΎΡ сСссии голосованиСм -Owner ΠΈΠ»ΠΈ co-GM Π²Ρ‹Π·Ρ‹Π²Π°Π΅Ρ‚ `/listsessions`, Π½Π°ΠΆΠΈΠΌΠ°Π΅Ρ‚ ΠΊΠ½ΠΎΠΏΠΊΡƒ `⏰` Ρƒ Π½ΡƒΠΆΠ½ΠΎΠΉ сСссии ΠΈ отправляСт Π² Ρ‡Π°Ρ‚ 2-3 Π²Π°Ρ€ΠΈΠ°Π½Ρ‚Π° Π½ΠΎΠ²ΠΎΠ³ΠΎ Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ вмСстС с Π΄Π΅Π΄Π»Π°ΠΉΠ½ΠΎΠΌ: - -```text -25.04.2026 19:30 -26.04.2026 18:00 -Π”Π΅Π΄Π»Π°ΠΉΠ½: 25.04.2026 12:00 -``` - -Π”Π΅Π΄Π»Π°ΠΉΠ½ Π΄ΠΎΠ»ΠΆΠ΅Π½ Π±Ρ‹Ρ‚ΡŒ Π² Π±ΡƒΠ΄ΡƒΡ‰Π΅ΠΌ ΠΈ Ρ€Π°Π½ΡŒΡˆΠ΅ ΠΏΠ΅Ρ€Π²ΠΎΠ³ΠΎ ΠΏΡ€Π΅Π΄Π»ΠΎΠΆΠ΅Π½Π½ΠΎΠ³ΠΎ Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ. Участники Π²Ρ‹Π±ΠΈΡ€Π°ΡŽΡ‚ ΠΎΠ΄ΠΈΠ½ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚ ΠΊΠ½ΠΎΠΏΠΊΠΎΠΉ Π² Telegram, ΠΌΠΎΠ³ΡƒΡ‚ ΠΈΠ·ΠΌΠ΅Π½ΠΈΡ‚ΡŒ голос Π΄ΠΎ Π΄Π΅Π΄Π»Π°ΠΉΠ½Π° ΠΈ видят Ρ‚Π΅ΠΊΡƒΡ‰ΠΈΠ΅ Ρ€Π΅Π·ΡƒΠ»ΡŒΡ‚Π°Ρ‚Ρ‹ Π² сообщСнии голосования. По Π΄Π΅Π΄Π»Π°ΠΉΠ½Ρƒ Π±ΠΎΡ‚ Π²Ρ‹Π±ΠΈΡ€Π°Π΅Ρ‚ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚ с наибольшим числом голосов, пСрСносит сСссию, сбрасываСт RSVP ΠΈ обновляСт batch-сообщСниС. Если голосов Π½Π΅Ρ‚ ΠΈΠ»ΠΈ Π΅ΡΡ‚ΡŒ Π½ΠΈΡ‡ΡŒΡ, пСрСнос отклоняСтся, Π° врСмя сСссии остаётся ΠΏΡ€Π΅ΠΆΠ½ΠΈΠΌ. - -### Π¨Π°Π±Π»ΠΎΠ½Ρ‹ ΠΈ bulk-ΠΎΠΏΠ΅Ρ€Π°Ρ†ΠΈΠΈ Π² Web Dashboard -Π’ΠΊΠ»Π°Π΄ΠΊΠ° `Π¨Π°Π±Π»ΠΎΠ½Ρ‹` Π² Π»Π΅Π²ΠΎΠΌ мСню вынСсСна ΠΎΡ‚Π΄Π΅Π»ΡŒΠ½ΠΎ ΠΎΡ‚ страницы Π³Ρ€ΡƒΠΏΠΏΡ‹. Owner ΠΈ co-GM Π²Ρ‹Π±ΠΈΡ€Π°ΡŽΡ‚ Π³Ρ€ΡƒΠΏΠΏΡƒ, ΡΠΎΡ…Ρ€Π°Π½ΡΡŽΡ‚ шаблон ΠΊΠ°ΠΌΠΏΠ°Π½ΠΈΠΈ с Π½Π°Π·Π²Π°Π½ΠΈΠ΅ΠΌ, ссылкой, количСством ΠΈΠ³Ρ€, ΠΈΠ½Ρ‚Π΅Ρ€Π²Π°Π»ΠΎΠΌ, Π»ΠΈΠΌΠΈΡ‚ΠΎΠΌ мСст ΠΈ Ρ€Π΅ΠΆΠΈΠΌΠΎΠΌ ΡƒΠ²Π΅Π΄ΠΎΠΌΠ»Π΅Π½ΠΈΠΉ, Π° Ρ‚Π°ΠΊΠΆΠ΅ ΡƒΠ΄Π°Π»ΡΡŽΡ‚ ΡƒΡΡ‚Π°Ρ€Π΅Π²ΡˆΠΈΠ΅ ΡˆΠ°Π±Π»ΠΎΠ½Ρ‹. - -На страницС Π³Ρ€ΡƒΠΏΠΏΡ‹ Web Dashboard ΠΏΠΎΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ ΠΏΡ€ΠΈΠΌΠ΅Π½Π΅Π½ΠΈΠ΅ сохранённых шаблонов ΠΈ ΠΎΡ‚Π΄Π΅Π»ΡŒΠ½Ρ‹ΠΉ Π±Π»ΠΎΠΊ для ΠΊΠ°ΠΆΠ΄ΠΎΠΉ ΠΏΠ°Ρ‡ΠΊΠΈ ΠΈΠ³Ρ€. Owner ΠΈ co-GM ΠΌΠΎΠ³ΡƒΡ‚: -- ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ Π½ΠΎΠ²Ρ‹ΠΉ batch ΠΈΠ· шаблона, Π²Ρ‹Π±Ρ€Π°Π² Ρ‚ΠΎΠ»ΡŒΠΊΠΎ ΠΏΠ΅Ρ€Π²ΡƒΡŽ Π΄Π°Ρ‚Ρƒ расписания; -- ΠΎΠ±Π½ΠΎΠ²ΠΈΡ‚ΡŒ ΠΎΠ±Ρ‰ΠΈΠΉ `title` ΠΈ `link` сразу Ρƒ всСх сСссий batch; -- Π²Ρ‹Π±Ρ€Π°Ρ‚ΡŒ Ρ€Π΅ΠΆΠΈΠΌ ΡƒΠ²Π΅Π΄ΠΎΠΌΠ»Π΅Π½ΠΈΠΉ: Π΄ΡƒΠ±Π»ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Π²Π°ΠΆΠ½Ρ‹Π΅ сообщСния ΠΈΠ³Ρ€ΠΎΠΊΠ°ΠΌ Π² Π»ΠΈΡ‡ΠΊΡƒ ΠΈΠ»ΠΈ ΠΎΡΡ‚Π°Π²ΠΈΡ‚ΡŒ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Π³Ρ€ΡƒΠΏΠΏΠΎΠ²Ρ‹Π΅ увСдомлСния; -- пСрСнСсти ΠΏΠ°Ρ‡ΠΊΡƒ, Π·Π°Π΄Π°Π² Π½ΠΎΠ²ΡƒΡŽ ΠΏΠ΅Ρ€Π²ΡƒΡŽ Π΄Π°Ρ‚Ρƒ ΠΈ фиксированный шаг ΠΌΠ΅ΠΆΠ΄Ρƒ ΠΈΠ³Ρ€Π°ΠΌΠΈ Π² днях; -- ΠΊΠ»ΠΎΠ½ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ batch Π½Π° ΡΠ»Π΅Π΄ΡƒΡŽΡ‰ΡƒΡŽ нСдСлю ΠΈΠ»ΠΈ ΡΠ»Π΅Π΄ΡƒΡŽΡ‰ΠΈΠΉ ΠΊΠ°Π»Π΅Π½Π΄Π°Ρ€Π½Ρ‹ΠΉ мСсяц. - -ПослС создания ΠΈΠ· шаблона ΠΈΠ»ΠΈ клонирования появляСтся новая ΠΏΠ°Ρ‡ΠΊΠ° с Π½ΠΎΠ²Ρ‹ΠΌ Telegram-сообщСниСм ΠΈ пустым составом ΠΈΠ³Ρ€ΠΎΠΊΠΎΠ². ПослС рСдактирования ΠΈΠ»ΠΈ пСрСноса исходноС Telegram-сообщСниС расписания пСрСрисовываСтся. - -Если Π²ΠΊΠ»ΡŽΡ‡Ρ‘Π½ Ρ€Π΅ΠΆΠΈΠΌ `Π’ Π³Ρ€ΡƒΠΏΠΏΠ΅ ΠΈ Π² Π»ΠΈΡ‡ΠΊΡƒ`, Π±ΠΎΡ‚ Π΄ΠΎΠΏΠΎΠ»Π½ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎ отправляСт ΠΈΠ³Ρ€ΠΎΠΊΠ°ΠΌ ΠΏΠ΅Ρ€ΡΠΎΠ½Π°Π»ΡŒΠ½Ρ‹Π΅ сообщСния ΠΎ RSVP Π·Π° 24 часа, Π½Π°ΠΏΠΎΠΌΠΈΠ½Π°Π½ΠΈΠ΅ Π·Π° 1 час, ссылку ΠΏΠ΅Ρ€Π΅Π΄ стартом, ΠΎΡ‚ΠΌΠ΅Π½Ρƒ ΠΈ пСрСнос. Если Telegram Π½Π΅ позволяСт Π½Π°ΠΏΠΈΡΠ°Ρ‚ΡŒ ΠΈΠ³Ρ€ΠΎΠΊΡƒ Π² Π›Π‘, Π±ΠΎΡ‚ Π»ΠΎΠ³ΠΈΡ€ΡƒΠ΅Ρ‚ ΠΎΡˆΠΈΠ±ΠΊΡƒ ΠΈ ΠΏΡ€ΠΎΠ΄ΠΎΠ»ΠΆΠ°Π΅Ρ‚ ΠΎΡ‚ΠΏΡ€Π°Π²ΠΊΡƒ ΠΎΡΡ‚Π°Π»ΡŒΠ½Ρ‹ΠΌ участникам. - -### Telegram Mini App Dashboard -Owner ΠΈ co-GM ΠΌΠΎΠ³ΡƒΡ‚ ΠΎΡ‚ΠΊΡ€Ρ‹Ρ‚ΡŒ ΠΌΠΎΠ±ΠΈΠ»ΡŒΠ½Ρ‹ΠΉ dashboard прямо ΠΈΠ· Telegram: Ρ‡Π΅Ρ€Π΅Π· ΠΊΠ½ΠΎΠΏΠΊΡƒ мСню Π±ΠΎΡ‚Π° ΠΈΠ»ΠΈ ΠΊΠ½ΠΎΠΏΠΊΡƒ `ΠžΡ‚ΠΊΡ€Ρ‹Ρ‚ΡŒ dashboard` послС `/start`. Π”ΠΎΠΏΠΎΠ»Π½ΠΈΡ‚Π΅Π»ΡŒΠ½Ρ‹ΠΉ ΠΏΠ°Ρ€ΠΎΠ»ΡŒ Π²Π²ΠΎΠ΄ΠΈΡ‚ΡŒ Π½Π΅ Π½ΡƒΠΆΠ½ΠΎ: GM-Relay сам ΠΏΡ€ΠΎΠ²Π΅Ρ€ΠΈΡ‚ Π²Ρ…ΠΎΠ΄ Ρ‡Π΅Ρ€Π΅Π· Telegram. - -Π’Π½ΡƒΡ‚Ρ€ΠΈ открываСтся Ρ‚Π° ΠΆΠ΅ панСль управлСния, Ρ‚ΠΎΠ»ΡŒΠΊΠΎ удобная для Ρ‚Π΅Π»Π΅Ρ„ΠΎΠ½Π°. МоТно ΡΠΌΠΎΡ‚Ρ€Π΅Ρ‚ΡŒ свои Π³Ρ€ΡƒΠΏΠΏΡ‹, Ρ€Π΅Π΄Π°ΠΊΡ‚ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ ΠΈΠ³Ρ€Ρ‹, ΡƒΠΏΡ€Π°Π²Π»ΡΡ‚ΡŒ листом оТидания, Π·Π°ΠΏΡƒΡΠΊΠ°Ρ‚ΡŒ ΡˆΠ°Π±Π»ΠΎΠ½Ρ‹ ΠΈ Π²Ρ‹ΠΏΠΎΠ»Π½ΡΡ‚ΡŒ массовыС дСйствия с ΠΏΠ°Ρ‡ΠΊΠ°ΠΌΠΈ ΠΈΠ³Ρ€. Π§ΡƒΠΆΠΈΠ΅ Π³Ρ€ΡƒΠΏΠΏΡ‹ Π½Π΅ появятся: dashboard ΠΏΠΎΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Ρ‚Π΅ Π³Ρ€ΡƒΠΏΠΏΡ‹, Π³Π΄Π΅ Π²Ρ‹ owner ΠΈΠ»ΠΈ co-GM. - -Если автоматичСский Π²Ρ…ΠΎΠ΄ Π½Π΅ сработал, Mini App ΠΏΠΎΠΊΠ°ΠΆΠ΅Ρ‚ понятноС сообщСниС ΠΈ ΠΊΠ½ΠΎΠΏΠΊΡƒ Π²Ρ…ΠΎΠ΄Π° Ρ‡Π΅Ρ€Π΅Π· Telegram. НаТмитС Π΅Ρ‘, ΠΏΠΎΠ΄Ρ‚Π²Π΅Ρ€Π΄ΠΈΡ‚Π΅ Π²Ρ…ΠΎΠ΄, ΠΈ dashboard откроСтся Π² Ρ‚ΠΎΠΌ ΠΆΠ΅ ΠΎΠΊΠ½Π΅ Telegram. - -### Π”Ρ€ΡƒΠ³ΠΈΠ΅ ΠΊΠΎΠΌΠ°Π½Π΄Ρ‹ -- `/listsessions` β€” ΠŸΠΎΠΊΠ°Π·Π°Ρ‚ΡŒ список всСх Π°ΠΊΡ‚ΡƒΠ°Π»ΡŒΠ½Ρ‹Ρ… ΠΈΠ³Ρ€ Π² этой Π³Ρ€ΡƒΠΏΠΏΠ΅. Для owner/co-GM ΠΊΠΎΠΌΠ°Π½Π΄Π° Ρ‚Π°ΠΊΠΆΠ΅ ΠΏΠΎΠΊΠ°Π·Ρ‹Π²Π°Π΅Ρ‚ ΠΊΠ½ΠΎΠΏΠΊΠΈ ΠΎΡ‚ΠΌΠ΅Π½Ρ‹, пСрСноса, ΠΏΠΎΠ²Ρ‹ΡˆΠ΅Π½ΠΈΡ ΠΈΠ· листа оТидания ΠΈ удалСния. -- `⏰` Π² ΠΏΠ°Π½Π΅Π»ΠΈ `/listsessions` β€” Π—Π°ΠΏΡƒΡΡ‚ΠΈΡ‚ΡŒ голосованиС ΠΏΠΎ 2-3 Π²Π°Ρ€ΠΈΠ°Π½Ρ‚Π°ΠΌ Π½ΠΎΠ²ΠΎΠ³ΠΎ Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ. -- `/deletesession` β€” Π£Π΄Π°Π»ΠΈΡ‚ΡŒ сСссию. -- `/exportcalendar` β€” ΠŸΠΎΠ»ΡƒΡ‡ΠΈΡ‚ΡŒ `.ics` Ρ„Π°ΠΉΠ» с ΠΈΠ³Ρ€Π°ΠΌΠΈ. -- `/help` β€” Π‘ΠΏΡ€Π°Π²ΠΊΠ° ΠΏΠΎ Ρ„ΠΎΡ€ΠΌΠ°Ρ‚Ρƒ. - ---- - -## πŸ— Π Π°Π·Ρ€Π°Π±ΠΎΡ‚ΠΊΠ° ΠΈ запуск локально (.NET Aspire) - -Для локальной Ρ€Π°Π·Ρ€Π°Π±ΠΎΡ‚ΠΊΠΈ ΠΏΡ€ΠΎΡ‰Π΅ всСго ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ .NET Aspire: - -1. УстановитС [.NET 10 SDK](https://dotnet.microsoft.com/download/dotnet/10.0) ΠΈ workload Aspire. -2. ΠžΡ‚ΠΊΡ€ΠΎΠΉΡ‚Π΅ Ρ€Π΅ΡˆΠ΅Π½ΠΈΠ΅ `GM-Relay.slnx`. -3. УстановитС ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅ окруТСния (ΠΈΠ»ΠΈ user secrets) для `GmRelay.AppHost`. -4. ЗапуститС ΠΏΡ€ΠΎΠ΅ΠΊΡ‚ `GmRelay.AppHost`. Aspire Dashboard запустится автоматичСски, прСдоставляя ΡƒΠ΄ΠΎΠ±Π½Ρ‹ΠΉ ΠΌΠΎΠ½ΠΈΡ‚ΠΎΡ€ΠΈΠ½Π³ Π‘Π”, Π±ΠΎΡ‚Π° ΠΈ Π²Π΅Π±-интСрфСйса. - -> [!NOTE] -> ΠŸΡ€ΠΈ использовании **Dapper** Π² Ρ€Π΅ΠΆΠΈΠΌΠ΅ Native AOT, всС SQL-запросы ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡŽΡ‚ строго Ρ‚ΠΈΠΏΠΈΠ·ΠΈΡ€ΠΎΠ²Π°Π½Π½Ρ‹Π΅ DTO. ДинамичСскиС Ρ‚ΠΈΠΏΡ‹ (`dynamic`) Π½Π΅ ΠΏΠΎΠ΄Π΄Π΅Ρ€ΠΆΠΈΠ²Π°ΡŽΡ‚ΡΡ. - ---- - -## πŸ§ͺ ВСстированиС - -Основной Π½Π°Π±ΠΎΡ€ ΠΏΡ€ΠΎΠ²Π΅Ρ€ΠΎΠΊ запускаСтся ΠΊΠΎΠΌΠ°Π½Π΄ΠΎΠΉ: - -```bash -dotnet test tests/GmRelay.Bot.Tests/GmRelay.Bot.Tests.csproj --collect:"XPlat Code Coverage" -``` - -Начиная с `v1.9.9`, тСстовый Π½Π°Π±ΠΎΡ€ Π²ΠΊΠ»ΡŽΡ‡Π°Π΅Ρ‚ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΎΠ½Π°Π»ΡŒΠ½Ρ‹ΠΉ smoke-сцСнарий ΠΎΠ±Π΅Ρ‰Π°Π½ΠΈΠΉ Π»Π΅Π½Π΄ΠΈΠ½Π³Π° для Telegram: batch-сСссии Π½Π° нСсколько Π΄Π°Ρ‚, inline-ΠΊΠ½ΠΎΠΏΠΊΠΈ записи/Π²Ρ‹Ρ…ΠΎΠ΄Π°, Π»ΠΈΠΌΠΈΡ‚Ρ‹ мСст, waitlist, Π°Π²Ρ‚ΠΎΠΏΠΎΠ²Ρ‹ΡˆΠ΅Π½ΠΈΠ΅ ΠΈΠ³Ρ€ΠΎΠΊΠ°, голосованиС Π·Π° пСрСнос, direct-notification mode ΠΈ пСрСрисовку Telegram batch-поста послС dashboard-ΠΈΠ·ΠΌΠ΅Π½Π΅Π½ΠΈΠΉ. Smoke Ρ€Π°Π±ΠΎΡ‚Π°Π΅Ρ‚ Ρ‡Π΅Ρ€Π΅Π· fake Telegram messenger ΠΈ Π½Π΅ Ρ‚Ρ€Π΅Π±ΡƒΠ΅Ρ‚ внСшнСго Telegram API. - ---- - -## πŸ“œ ЛицСнзия -ΠŸΡ€ΠΎΠ΅ΠΊΡ‚ распространяСтся ΠΏΠΎΠ΄ Π»ΠΈΡ†Π΅Π½Π·ΠΈΠ΅ΠΉ MIT. ИспользованиС Π² нСкоммСрчСских цСлях привСтствуСтся. +IyDwn46yIEdNLVJlbGF5OiBUVFJQRyBTZXNzaW9uIFNjaGVkdWxpbmcgQm90ICYgV2ViIERhc2hib2FyZAoKKipHTS1SZWxheSoqIOKAlCDRjdGC0L4g0LrQvtC80L/Qu9C10LrRgdC90L7QtSDRgNC10YjQtdC90LjQtSDQtNC70Y8g0JzQsNGB0YLQtdGA0L7QsiDQn9C+0LTQt9C10LzQtdC70LjQuSAo0JPQnNC+0LIpLCDRgdC+0YHRgtC+0Y/RidC10LUg0LjQtyDQstGL0YHQvtC60L7Qv9GA0L7QuNC30LLQvtC00LjRgtC10LvRjNC90L7Qs9C+IFRlbGVncmFtLdCx0L7RgtCwINC4INGD0LTQvtCx0L3QvtCz0L4g0LLQtdCxLdC40L3RgtC10YDRhNC10LnRgdCwLiDQn9GA0LXQtNC90LDQt9C90LDRh9C10L3QviDQtNC70Y8g0LDQstGC0L7QvNCw0YLQuNC30LDRhtC40Lgg0LfQsNC/0LjRgdC4INC40LPRgNC+0LrQvtCyINC90LAg0YHQtdGB0YHQuNC4LCDRg9C/0YDQsNCy0LvRtdC90LjRjyDRgNCw0YHQv9C40YHQsNC90LjQtdC8INC4INC/0YDQvtCy0LXQtNC10L3QuNGPINC40LPRgC4KCtCf0YDQvtC10LrRgiDRgNCw0LfRgNCw0LHQvtGC0LDQvSDRgSDRg9C/0L7RgNC+0Lwg0L3QsCDQv9GA0L7QuNC30LLQvtC00LjRgtC10LvRjNC90L7RgdGC0YwsINCw0YDRhdC40YLQtdC60YLRg9GA0YMgVmVydGljYWwgU2xpY2UsIE5hdGl2ZSBBT1QgKNC00LvRjyDQsdC+0YLQsCkg0Lgg0YPQtNC+0LHRgdGC0LLQviDRgNCw0LfQstC10YDRgtGL0LLQsNC90LjRjyDRgSDQuNGB0L/QvtC70YzQt9C+0LLQsNC90LjQtdC8IC5ORVQgQXNwaXJlLgoKKirQotC10LrRg9GJ0LDRjyDQstC10YDRgdC40Y86KiogYHYxLjEwLjFgLgoKLS0tCgojIyDwn5qAIEtleSBGZWF0dXJlcwoKIyMjIPCfkokoIFRlbGVncmFtIEJvdAotICoq8J+ThSDQodC+0LfQtNCw0L3QuNC1INGA0LDRgdC/0LjRgdCw0L3QuNC5IChCYXRjaCBTZXNzaW9ucykqKjog0KHQvtC30LTQsNCy0LDQudGC0LUg0YHQgNCw0LfRgyDQvdC10YHQutC+0LvRjNC60L4g0LjQs9GAINC+0LTQvdC40LzQtdC90LjRjyDQuNC30LzQtdC90LXQvdC40Y8gKNC90LAg0L3QtdC00LXQu9GM0L3Ri9C8INC80LXQsdGP0YYg0LIg0L/QtdGA0LXQtCkuCi0gKirwn5a8INCe0LHQu9C+0LbQutC4INGA0LDRgdC/0LjRgdCw0L3QuNC5Kio6INCYIGJhdGNoLdC/0L7RgdGC0YMg0LzQvtC20L3QviDQv9GA0LjQutGA0LXQv9C40YLRjCDRhNC+0YLQviDQuiBgL25ld3Nlc3Npb25gINC40LvQuCDRg9C60LDQt9Cw0YLRjCDRgdGC0YDQvtC60YMgYNCa0LDRgNGC0LjQvdC60LA6IGh0dHBzOi8vLi4uYDsg0LHQvtGCINC+0YLQv9GA0LDQstC40YIg0L7QsdC70L7QttC60YMg0L/QtdGA0LXQtCDRgdC+0L7QsdGJ0LXQvdC40LXQvCDQt9Cw0L/QuNGB0LguCi0gKirimqEg0JHRi9GB0YLRgNGL0LUg0L/QvtCy0YLQvtGA0Ysg0YDQsNGB0L/QuNGB0LDQvdC40Y8qKjog0JTQu9GPINGA0LXQs9GD0LvRj9GA0L3QvtC5INC60LDQvNC/0LDQvdC40Lgg0LzQvtC20L3QviDRg9C60LDQt9Cw0YLRjCDQvtC00L3RgyDQtNCw0YLRgywg0LrQvtC70LjRh9C10YHRgtCy0L4g0LjQs9GAINC4INC40L3RgtC10YDQstCw0LssINCwINCx0L7RgiDRgdCw0Lwg0YDQsNC30LLQtdGA0L3RkdGCINC/0L7QstGC0L7RgNGP0Y7RidC40LnRgdGPIGJhdGNoLgotICoq4pyLINCY0L3RgtC10YDQsNC60YLQuNCy0L3QsNGPINC30LDQv9C40YHRjCDQuCDQstGL0YXQvtC0Kio6INCY0LPRgNC+0LrQuCDQt9Cw0L/QuNGB0YvQstCw0Y7RgtGB0Y8g0L3QsCDQutC+0L3QutGA0LXRgtC90YvQtSDQtNCw0YLRiyDQuCDRgdCw0LzQvtGB0YLQvtGP0YLQtdC70YzQvdC+INGB0L3QuNC80LDRjtGCINC30LDQv9C40YHRjCDQvdCw0LbQsNGC0LjQtdC8INC+0LTQvdC+0Lkg0LrQvdC+0L/QutC4LgotICoq8J+RpSDQm9C40LzQuNGCINC80LXRgdGCINC4INC70LjRgdGCINC+0LbQuNC00LDQvdC40Y8qKjog0JPQnCDQt9Cw0LTQsNGR0YIg0LzQsNC60YHQuNC80LDQu9GM0L3Ri9C5INGB0L7RgdGC0LDQsiwg0LHQvtGCINC90LUg0L/QtdGA0LXQv9C+0LvQvdGP0LXRgiDRgdC10YHRgdC40Y4sINCw0LLRgtC+0LzQsNGC0LjRh9C10YHQutC4INCy0LXQtNGR0YIg0L7Rh9C10YDQtdC00Ywg0L7QttC40LTQsNC90LjRjyDQuCDQvtGB0LLQvtCx0L7QttC00ZHQvdC90L7QtSDQvNC10YHRgtC+INC+0YLQtNCw0ZHRgiDQv9C10YDQstC+0LzRgyDQvtC20LjQtNCw0Y7RidC10LzRgy4KLSAqKvCfk4Eg0J/QvtC00LTQtdGA0LbQutCwINCk0L7RgNGD0LzQvtCyIChUZWxlZ3JhbSBUb3BpY3MpKio6INCR0L7RgiDQsNCy0YLQvtC80LDRgtC40YfQtdGB0LrQuCDRgdC+0LfQtNCw0LXRgiDRgtC10LzRgyDQstC+INCy0LvQvtC20LXQvdC90YvRhSDRh9Cw0YLQsNGFIFRlbGVncmFtINC/0L7QtCDQutCw0LbQtNGD0Y4g0L3QvtCy0YPRjiDQv9Cw0YfQutGDINC40LPRgC4KLSAqKuKdjCDQo9C/0YDQsNCy0LvQtdC90LjQtSDRgdC10YHRgdC40Y/QvNC4Kio6IE93bmVyINC4INC90LDQt9C90LDRh9C10L3QvdGL0LUgY28tR00g0LzQvtCz0YPRgiDRgdC+0LfQtNCw0LLQsNGC0YwsINC+0YLQvNC10L3Rj9GC0YwsINGD0LTQsNC70Y/RgtGMINC4INC/0LXRgNC10L3QvtGB0LjRgtGMINC40LPRgNGLINC40LcgVGVsZWdyYW0g0YfQtdGA0LXQtyBgL2xpc3RzZXNzaW9uc2A7INC/0YPQsdC70LjRh9C90YvQuSDQv9C+0YHRgiDQt9Cw0L/QuNGB0Lgg0L/QvtC60LDQt9GL0LLQsNC10YIg0YLQvtC70YzQutC+INC60L3QvtC/0LrQuCDQuNCz0YDQvtC60L7Qsi4KLSAqKvCflIQg0JPQvtC70L7RgdC+0LLQsNC90LjQtSDQt9CwINC/0LXRgNC10L3QvtGBKio6INCR0YvRgdGC0YDRi9C5INC/0L7QtNC20LXQvdC90L7Qs9C+INC80LXRgdGC0L4g0YEg0YfQtdGA0LXQtyDRgdCy0L7QsdC+0LTQvdC+0LUg0L3QtdC00LXQu9GMINC4INC60L3QvtC/0LrQsNC80Lgg0L3QvtCy0YvRhSDQstGA0LXQvNC10L3QuCDQuCDQtNC10LTQu9Cw0LnQvdC+0Lw6CiAgYGBgdGV4dAogIDI1LjA0LjIwMjYgMTk6MzAKICAyNi4wNC4yMDI2IDE4OjAwCiAg0JTQtdC00LvQsNC50L06IDI1LjA0LjIwMjYgMTI6MDAKICBgYGAKICANCi0gKirwn5SUINCQ0LLQtdC00L7QvNC70LXQvdC40Y8qKjog0JjQs9GA0L7QuiDQv9C+0LvRg9GH0LDRjtGCINCTLCDQt9CwIDI0INGH0LDRgdCwLCDQvdCw0L/QvtC80LjQvdCw0L3QuNC1INC30LAgMSDRh9Cw0YEsINGB0YHRi9C70LrRgyDQv9C10YDQtdC0INC40LPRgNC+0LksINC+0YLQvNC10L3RiyDQuCDQv9C10YDQtdC90L7RgdGLOyDQs9GA0YPQv9C/0L7QstGL0LUg0YPQstC10LTQvtC80LvQtdC90LjRjyDQv9GA0Lgg0Y3RgtC+0Lwg0L7RgdGC0LDRjtGC0YHRjy4KLSAqKifwn5WjINCg0LXQttC40Lwg0YPQstC10LTQvtC80LvQtdC90LjQuSBiYXRjaCoqOiDQlNC70Y8g0LrQsNC20LTQvtC5INC/0LDRh9C60Lgg0LzQvtC20L3QviDQstGL0LHRgNCw0YLRjCBg0JIg0LPRgNGD0L/Qv9C1INC4INCyINC70LjRh9C60YNgINC40LvQuCBg0KLQvtC70YzQutC+INCyINCz0YDRg9C/0L/QtWAuCi0gKirirIbvuo/igJAg0KPQv9GA0LDQstC70LXQvdC40LUg0L7Rh9C10YDQtdC00YzRjioqOiDQktC10LEt0LjQvdGC0LXRgNGE0LXQudGBINC/0L7QutCw0LfRi9Cy0LDQtdGCINC30LDQv9C+0LvQvdC10L3QvdC+0YHRgtGMLCDQu9C40YHRgiDQvtC20LjQtNCw0L3QuNGPINC4INC/0L7Qt9Cy0L7Qu9GP0LXRgiDQk9Cc0YMg0L/QvtC00L3Rj9GC0Ywg0L/QtdGA0LLQvtCz0L4g0LjQs9GA0L7QurQsINC40Lcg0L7Rh9C10YDQtdC00LguCi0gKirwn5SEINCQ0LLRgtC+0LzQsNGC0LjRh9C10YHQutCw0Y8g0YHQuNC90YXRgNC+0L3QuNC30LDRhtC40Y8qKjog0JvRjtCx0YvQtSDQuNC30LzQtdC90LXQvdC40Y8g0LIg0LLQtdCxLdC40L3RgtC10YDRhNC10LnRgdC1INC80LPQvdC+0LLQtdC90L3QviDQvtCx0L3QvtCy0LvRj9GO0YIg0YHQvtC+0LHRidC10L3QuNGPINGBINGA0LDRgdC/0LjRgdCw0L3QuNC10Lwg0LIgVGVsZWdyYW0t0YfQsNGC0LDRhSDQuNCz0YDQvtC60L7Qsi4KCiMjIyDwn5qAIHdlYiBERFNoYm9hcmQgKEJsYXpvciBTZXJ2ZXIpCi0gKirwn5CUINCR0YPQstGC0L7RgNC40LfQsNGG0LjRjyDRh9C10YDQtdCcgVGVsZWdyYW0qKjog0JHR0LXQt9C+0L/QsNGB0L3Ri9C5INCy0YXQvtC00LTRgSDRgSDQuNGB0L/QvtC70YzQt9C+0LLQsNC90LjQtdC8IFRlbGVncmFtIExvZ2luIFdpZGdldCAoSE1BQy1TSEEyNTYg0LLQsNC70LjQtNCw0YbQuNC4KS4KLSAqKvCfk7EgVGVsZWdyYW0gTWluaSBBcHAgRGFzaGJvYXJkKio6INCR0L7QsdC40LvRjNC90LDRjyDQstC10YDRgdC40Y8gZGFzaGJvYXJkINC+0YLQutGA0YvQstCw0LXRgtGB0Y8g0L/RgNGP0LzQviDQuNC3IFRlbGVncmFtLCDQv9GA0L7QstC10YDQvtC00LjRgtC10YLRgdGPINCy0YHQtdC4INGC0L7QutC10L3QvtC8INCx0L7RgtCwLiDQndCw0LbQsNC90LjRgtC1IFRlbGVncmFtIExvZ2luIFdpZGdldCDQsNCy0YLQvtGA0LjQt9GD0LXRgtGB0Y8g0L/QvtC70YzQt9C+0LLQsNGC0LXQu9GMINCyINGC0LXQutGD0YnQtdCz0L4gV2ViVmlldywg0LAgZGFzaGJvYXJkINC+0YLQutGA0L7QtdGC0YHRjyDQsdC10Lcg0YDRg9GH0L3QvtCz0L4g0LfQsNC60YDRi9GC0LjRjyDQuCDQv9C+0LLRgtC+0YDQvdC+0LPQviDQvdCw0L/QvtC80LjQvdCw0L3QuNC10LwuCi0gKirwn5OdINCo0LDQsdC70L7QvdGLINC60LDQvNC/0LDQvdC40LkqKjogT3duZXIg0LggY28tR00g0YPQv9GA0LDQstC70Y/RjtGCINGC0LjQv9C+0LLRi9C80Lgg0L/QsNGA0LDQvNC10YLRgNCw0LzQuCDQutCw0LzQv9Cw0L3QuNC5INCyINC+0YLQtNC10LvRjNC90L7QuSDQstC60LvQsNC00LrQtSDQoNGw0LHQtdC70L7QvdGLYCwg0LAg0L3QsCDRgdGC0YDQsNC90LjRhtC1INCz0YDRg9C/0L/RiyDQt9Cw0L/Rg9GB0LrQsNGO0YIg0L3QvtCy0YvQuSDQv9C+0LLRgtC+0YDRj9GO0YnQuNC50YHRjyBiYXRjaCDQuNC3INCy0YvQsdGA0LDQvdC90L7Qs9C+INGI0LDQsdC70L7QvdCwLgotICoq8J+TnSDQmNC90YLQtdGA0LLQsNC70L7QvCBidWxrLdC+0L/QtdGA0LDRhtC40LggYmF0Y2ggc2Vzc2lvbnMqKjog0JPQnCDQvNC+0LbQtdGCINC+0LHQvdC+0LLQuNGC0Ywg0L7QsdGJ0LjQuSB0aXRsZS9saW5rLCDQv9C10YDQtdC90LXQsdGC0Lgg0LLRgdGOINC/0LDRh9C60YMg0L3QsCDRhNC40LrRgdC40YDQvtCy0LDQvdC90YvQuSDRiNCw0LMg0Lgg0LrQu9C+0L3QuNGA0L7QstCw0YLRjCBiYXRjaCDQvdCwINGB0LvQtdC00YPRjtGJ0YPRjiDQvdC10LTQtdC70Y4g0LjQu9C4INC80LXRgdGP0YYuCi0gKirwn5WjINCY0L3RgtC10YDQstCw0Lcg0YPQstC10LTQvtC80LvQtdC90LjQuSBiYXRjaCoqOiDQlNC70Y8g0LrQsNC20LTQvtC5INC/0LDRh9C60Lgg0LzQvtC20L3QviDQstGL0LHRgNCw0YLRjCBg0JIg0LPRgNGD0L/Qv9C1INC4INCyINC70LjRh9C60YNgINC40LvQuCBg0KLQvtC70YzQutC+INCyINCz0YDRg9C/0L/QtSDQt9Cw0L/Rg9GB0LrQsNGC0Ywg0YjQsNCx0LvQvtC90YsgV2ViIERhc2hib2FyZC4KLSAqKvCflIwgc3RhdGlzdGljcyBvZiBhdHRlbmRhbmNlIGluIGdyb3Vwcw== \ No newline at end of file