Files
webcb/server/index.js
2026-05-13 21:41:56 +02:00

122 lines
3.7 KiB
JavaScript

import express from 'express';
import { createServer } from 'http';
import { Server } from 'socket.io';
import { fileURLToPath } from 'url';
import { dirname, join } from 'path';
const __dirname = dirname(fileURLToPath(import.meta.url));
const app = express();
const httpServer = createServer(app);
const io = new Server(httpServer, {
cors: { origin: '*' }
});
app.use(express.static(join(__dirname, '../client')));
const CHANNEL_NAMES = {
1: 'Europa 1', 2: 'Europa 2', 3: 'Europa 3', 4: 'Funker TG',
8: 'Notruf', 9: 'Notruf', 19: 'Bande (LKW/Auto)', 27: 'WW Band'
};
const channels = Array.from({ length: 40 }, (_, i) => ({
id: i + 1,
users: []
}));
const usedNames = new Set();
function makeUniqueName(name) {
let finalName = name;
let counter = 1;
while (usedNames.has(finalName.toLowerCase())) {
finalName = `${name}${counter}`;
counter++;
}
usedNames.add(finalName.toLowerCase());
return finalName;
}
io.on('connection', (socket) => {
let currentChannel = null;
let username = '';
socket.on('check_name', (name, callback) => {
if (!name || name.trim().length < 2) {
callback({ available: false, message: 'Mindestens 2 Zeichen' });
return;
}
if (usedNames.has(name.toLowerCase())) {
callback({ available: false, suggested: makeUniqueName(name) });
} else {
callback({ available: true });
}
});
socket.on('join', ({ name, channel }) => {
username = makeUniqueName(name);
currentChannel = channel;
if (currentChannel) {
channels[currentChannel - 1].users.push({ id: socket.id, name: username, isTransmitting: false });
}
socket.emit('init', { channels, CHANNEL_NAMES, myName: username });
socket.broadcast.emit('user_update', { name: username, channel: currentChannel, joined: true });
});
socket.on('join_channel', ({ channel }) => {
socket.join(`channel-${channel}`);
if (currentChannel && currentChannel !== channel) {
socket.leave(`channel-${currentChannel}`);
channels[currentChannel - 1].users = channels[currentChannel - 1].users.filter(u => u.id !== socket.id);
}
currentChannel = channel;
if (!channels[channel - 1].users.find(u => u.id === socket.id)) {
channels[channel - 1].users.push({ id: socket.id, name: username, isTransmitting: false });
}
io.emit('channel_update', { channels });
});
socket.on('leave_channel', () => {
if (currentChannel) {
socket.leave(`channel-${currentChannel}`);
channels[currentChannel - 1].users = channels[currentChannel - 1].users.filter(u => u.id !== socket.id);
currentChannel = null;
io.emit('channel_update', { channels });
}
});
socket.on('transmitting', (isTransmitting) => {
if (currentChannel) {
const user = channels[currentChannel - 1].users.find(u => u.id === socket.id);
if (user) user.isTransmitting = isTransmitting;
io.emit('channel_update', { channels });
}
});
socket.on('audio', (audioData) => {
if (currentChannel) {
socket.broadcast.to(`channel-${currentChannel}`).emit('audio', audioData);
}
});
socket.on('slang', ({ channel, text, user }) => {
io.to(`channel-${channel}`).emit('slang', { text, user });
});
socket.on('disconnect', () => {
if (username) {
usedNames.delete(username.toLowerCase());
}
if (currentChannel) {
channels[currentChannel - 1].users = channels[currentChannel - 1].users.filter(u => u.id !== socket.id);
io.emit('channel_update', { channels });
io.emit('user_update', { name: username, channel: currentChannel, joined: false });
}
});
});
const PORT = process.env.PORT || 3001;
httpServer.listen(PORT, () => {
console.log(`WebCB Server läuft auf http://localhost:${PORT}`);
});