feat: Radio Plugin – 3D Globe mit weltweiten Radiosendern
- Radio Garden API Client (30K+ Orte, Sender-Suche, Stream-URL Auflösung) - Discord Voice Streaming via ffmpeg (PCM Pipeline) - Interactive 3D Globe (globe.gl) mit allen Radiosender-Standorten - Sender-Panel mit Play/Stop/Favoriten - Live-Suche nach Sendern und Städten - Now-Playing Bar mit Equalizer-Animation - Guild/Voice-Channel Auswahl - SSE Broadcasting für Live-Updates - Favoriten-System mit Persistenz - Responsive Design (Mobile/Tablet/Desktop) Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
ae1c41f0ae
commit
847c963d86
7 changed files with 1487 additions and 9 deletions
|
|
@ -4,6 +4,7 @@ import client from './core/discord.js';
|
|||
import { addSSEClient, removeSSEClient, sseBroadcast, getSSEClientCount } from './core/sse.js';
|
||||
import { loadState, getFullState } from './core/persistence.js';
|
||||
import { getPlugins, registerPlugin, PluginContext } from './core/plugin.js';
|
||||
import radioPlugin from './plugins/radio/index.js';
|
||||
|
||||
// ── Config ──
|
||||
const PORT = Number(process.env.PORT ?? 8080);
|
||||
|
|
@ -68,10 +69,7 @@ app.get('/api/plugins', (_req, res) => {
|
|||
})));
|
||||
});
|
||||
|
||||
// ── SPA Fallback ──
|
||||
app.get('*', (_req, res) => {
|
||||
res.sendFile(path.join(import.meta.dirname ?? __dirname, '..', '..', 'web', 'dist', 'index.html'));
|
||||
});
|
||||
// NOTE: SPA fallback is added in boot() AFTER plugin routes
|
||||
|
||||
// ── Discord Ready ──
|
||||
client.once('ready', async () => {
|
||||
|
|
@ -87,8 +85,8 @@ client.once('ready', async () => {
|
|||
|
||||
// ── Init Plugins ──
|
||||
async function boot(): Promise<void> {
|
||||
// --- Load plugins dynamically here ---
|
||||
// Example: import('./plugins/soundboard/index.js').then(m => registerPlugin(m.default));
|
||||
// ── Register plugins ──
|
||||
registerPlugin(radioPlugin);
|
||||
|
||||
// Init all plugins
|
||||
for (const p of getPlugins()) {
|
||||
|
|
@ -101,6 +99,11 @@ async function boot(): Promise<void> {
|
|||
}
|
||||
}
|
||||
|
||||
// SPA Fallback (MUST be after plugin routes)
|
||||
app.get('*', (_req, res) => {
|
||||
res.sendFile(path.join(import.meta.dirname ?? __dirname, '..', '..', 'web', 'dist', 'index.html'));
|
||||
});
|
||||
|
||||
// Start Express
|
||||
app.listen(PORT, () => console.log(`[HTTP] Listening on :${PORT}`));
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue