Files
zyrarbot/README.md
T

127 lines
6.0 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# ŻyrarBOT
Bot muzyczny Discord z panelem webowym: kolejka odtwarzania, historia, serwerowa
baza plików i sterowanie na żywo przez WebSocket.
## Uruchomienie
```bash
pip install -r requirements.txt
python main.py # albo: python -m zyrarbot
```
Wymagane zmienne środowiskowe (plik `.env`):
| Zmienna | Opis |
| --------------- | ----------------------------------------------------------- |
| `DISCORD_TOKEN` | Token bota Discord. |
| `GUILD_ID` | Opcjonalnie - synchronizuje komendy tylko z jednym serwerem. |
Panel działa pod `http://localhost:8000` podczas uruchomienia lokalnego. W Dockerze
jest dostępny pod `http://localhost` po wykonaniu `docker compose up --build`.
Panel obsługuje wiele serwerów Discorda. Wybór serwera w nagłówku przełącza jego
osobną kolejkę, historię, bazę plików i ustawienia odtwarzania. Istniejące dane ze
starego, wspólnego formatu są przypisywane do pierwszego użytego serwera.
Historia jest zapisywana w osobnych plikach `config/history/<guild_id>.json`, a
uploady w katalogach `uploads/<guild_id>/`.
Ostatnia kolejka jest zapisywana w `config/queues/<guild_id>.json` przy zatrzymaniu
lub rozłączeniu i może zostać przywrócona z widoku kolejki.
## Komendy Discorda
Wszystkie komendy działają w kontekście bieżącego serwera. Discord pokazuje wybór
utworów przez autocomplete, a kanały przez natywne selektory — nie trzeba wpisywać
indeksów ręcznie.
| Komenda | Działanie |
| --- | --- |
| `/player` | Publiczny panel odtwarzacza z przyciskami sterowania |
| `/play query` | Dodaje utwór, link lub zapytanie wyszukiwania |
| `/playfile filename` | Odtwarza plik z biblioteki serwera |
| `/upload file` | Przesyła i waliduje plik audio/wideo do biblioteki |
| `/deletefile filename` | Usuwa wybrany plik z biblioteki |
| `/replay track_id` | Ponownie odtwarza utwór z historii |
| `/queue` | Pokazuje kolejkę w embedzie |
| `/history` | Pokazuje historię odtwarzania |
| `/restorequeue` | Przywraca ostatnią zapisaną kolejkę |
| `/jump track_id` | Rozpoczyna wybrany utwór z kolejki |
| `/remove track_id` | Usuwa wybrany utwór z kolejki |
| `/move track_id before_id` | Przenosi utwór przed wybrany utwór docelowy |
| `/trackplays track_id count` | Ustawia liczbę odtworzeń utworu |
| `/pause`, `/resume` | Wstrzymuje lub wznawia odtwarzanie |
| `/skip` | Pomija bieżący utwór |
| `/stop` | Zatrzymuje odtwarzanie i czyści kolejkę |
| `/volume volume` | Ustawia głośność w zakresie 1–100 |
| `/nowplaying` | Pokazuje bieżący utwór |
| `/loop` | Przełącza tryb zapętlania |
| `/loopplaylist` | Włącza lub wyłącza zapętlanie kolejki |
| `/defaultplays count` | Ustawia domyślną liczbę odtworzeń dla nowych utworów |
| `/connect channel` | Łączy bota z wybranym kanałem głosowym |
| `/notificationchannel channel` | Ustawia kanał powiadomień |
| `/leave` | Rozłącza bota z kanału głosowego |
## Testy
```bash
python -m unittest discover -s tests -t .
```
## Struktura pakietu
Każda klasa mieszka w osobnym pliku, a pliki są pogrupowane w przestrzenie nazw
odpowiadające warstwom aplikacji:
```
zyrarbot/
├── settings.py Settings - konfiguracja ze zmiennych środowiskowych
├── application.py Application - korzeń kompozycji, spina bota i API
├── storage/ Warstwa trwałości (pliki JSON, katalog uploadów)
│ ├── json_file_store.py JsonFileStore
│ ├── guild_config_repository.py GuildConfigRepository
│ ├── history_repository.py HistoryRepository
│ ├── uploads_repository.py UploadsRepository
│ └── upload_file_info.py UploadFileInfo
├── audio/ Pozyskiwanie dźwięku
│ ├── ytdl_options.py YtdlOptions
│ ├── ytdl_source.py YTDLSource
│ ├── media_probe.py MediaProbe
│ └── track_factory.py TrackFactory
├── music/ Domena odtwarzania
│ ├── loop_mode.py LoopMode
│ ├── history_entry.py HistoryEntry
│ ├── guild_music_state.py GuildMusicState
│ ├── track_embed_factory.py TrackEmbedFactory
│ ├── notification_channel_resolver.py NotificationChannelResolver
│ └── music_player.py MusicPlayer
└── ui/ Warstwa interfejsów użytkownika
├── api/ API panelu (FastAPI)
│ ├── factory.py mount_api - konfiguracja i routery API
│ ├── connection_manager.py ConnectionManager
│ ├── status_service.py StatusService
│ ├── status_broadcaster.py StatusBroadcaster
│ ├── dependencies.py wstrzykiwanie zależności z app.state
│ ├── requests/ modele żądań - jeden na plik
│ └── routers/ trasy pogrupowane tematycznie
└── bot/ Warstwa Discorda
├── client.py MusicBot
├── guild_resolver.py GuildResolver
└── cogs/ komendy i listenery Discorda
├── common.py wspólne zależności i helpery
├── playback_cog.py PlaybackCog
├── queue_cog.py QueueCog
├── control_cog.py ControlCog
├── voice_cog.py VoiceCog
└── settings_cog.py SettingsCog
```
### Zasady
- **`MusicPlayer` jest jedynym właścicielem stanu odtwarzania.** Zarówno komendy
Discorda, jak i endpointy panelu operują wyłącznie przez niego - nie ma już
dwóch niezależnych ścieżek modyfikujących kolejkę.
- **Kolejka jest nieusuwalna, pozycję śledzi indeks** (`GuildMusicState.index`),
dzięki czemu działa przeskakiwanie i przewijanie w tył.
- **Zależności wędrują przez konstruktory**, a w API przez `app.state`
i funkcje z `api/dependencies.py`. Nie ma globalnych singletonów.