342 lines
9.1 KiB
JavaScript
342 lines
9.1 KiB
JavaScript
const express = require('express');
|
|
const jwt = require('jsonwebtoken');
|
|
const { getGameSystem } = require('../systems/GameSystem');
|
|
const logger = require('../utils/logger');
|
|
|
|
const router = express.Router();
|
|
|
|
// Middleware to authenticate JWT token
|
|
const authenticateToken = (req, res, next) => {
|
|
const token = req.header('Authorization')?.replace('Bearer ', '');
|
|
|
|
if (!token) {
|
|
return res.status(401).json({ error: 'Access token required' });
|
|
}
|
|
|
|
try {
|
|
const decoded = jwt.verify(token, process.env.JWT_SECRET || 'fallback_secret');
|
|
req.userId = decoded.userId;
|
|
next();
|
|
} catch (error) {
|
|
res.status(401).json({ error: 'Invalid token' });
|
|
}
|
|
};
|
|
|
|
// Get server list
|
|
router.get('/', authenticateToken, async (req, res) => {
|
|
try {
|
|
const gameSystem = getGameSystem();
|
|
const serverList = gameSystem.getServerList();
|
|
|
|
res.json({
|
|
servers: serverList,
|
|
totalServers: serverList.length
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('Error getting server list:', error);
|
|
res.status(500).json({ error: 'Internal server error' });
|
|
}
|
|
});
|
|
|
|
// Create new server
|
|
router.post('/create', authenticateToken, async (req, res) => {
|
|
try {
|
|
const { name, type = 'public', maxPlayers = 10, region = 'us-east', settings = {} } = req.body;
|
|
|
|
if (!name) {
|
|
return res.status(400).json({ error: 'Server name required' });
|
|
}
|
|
|
|
if (name.length < 3 || name.length > 50) {
|
|
return res.status(400).json({ error: 'Server name must be between 3 and 50 characters' });
|
|
}
|
|
|
|
const gameSystem = getGameSystem();
|
|
|
|
const serverData = {
|
|
name,
|
|
type,
|
|
maxPlayers,
|
|
region,
|
|
settings,
|
|
ownerId: req.userId,
|
|
ownerName: req.username || 'Unknown'
|
|
};
|
|
|
|
const server = await gameSystem.createServer(serverData);
|
|
|
|
// Auto-join the creator to the server
|
|
await gameSystem.joinServer(server.id, req.userId);
|
|
|
|
logger.info(`Server created: ${server.id} by user ${req.userId}`);
|
|
|
|
res.status(201).json({
|
|
message: 'Server created successfully',
|
|
server: {
|
|
id: server.id,
|
|
name: server.name,
|
|
type: server.type,
|
|
maxPlayers: server.maxPlayers,
|
|
currentPlayers: server.players.length,
|
|
region: server.region,
|
|
status: server.status,
|
|
ownerId: server.ownerId,
|
|
createdAt: server.createdAt
|
|
}
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('Error creating server:', error);
|
|
res.status(500).json({ error: error.message });
|
|
}
|
|
});
|
|
|
|
// Join server
|
|
router.post('/:serverId/join', authenticateToken, async (req, res) => {
|
|
try {
|
|
const { serverId } = req.params;
|
|
const { password } = req.body; // For private servers
|
|
|
|
if (!serverId) {
|
|
return res.status(400).json({ error: 'Server ID required' });
|
|
}
|
|
|
|
const gameSystem = getGameSystem();
|
|
const server = await gameSystem.joinServer(serverId, req.userId);
|
|
|
|
// Update player's current server
|
|
const Player = require('../models/Player');
|
|
await Player.findOneAndUpdate(
|
|
{ userId: req.userId },
|
|
{ currentServer: serverId }
|
|
);
|
|
|
|
logger.info(`User ${req.userId} joined server ${serverId}`);
|
|
|
|
res.json({
|
|
message: 'Joined server successfully',
|
|
server: {
|
|
id: server.id,
|
|
name: server.name,
|
|
type: server.type,
|
|
maxPlayers: server.maxPlayers,
|
|
currentPlayers: server.players.length,
|
|
region: server.region
|
|
}
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('Error joining server:', error);
|
|
res.status(500).json({ error: error.message });
|
|
}
|
|
});
|
|
|
|
// Leave server
|
|
router.post('/:serverId/leave', authenticateToken, async (req, res) => {
|
|
try {
|
|
const { serverId } = req.params;
|
|
|
|
if (!serverId) {
|
|
return res.status(400).json({ error: 'Server ID required' });
|
|
}
|
|
|
|
const gameSystem = getGameSystem();
|
|
const server = await gameSystem.leaveServer(serverId, req.userId);
|
|
|
|
// Update player's current server
|
|
const Player = require('../models/Player');
|
|
await Player.findOneAndUpdate(
|
|
{ userId: req.userId },
|
|
{ currentServer: null }
|
|
);
|
|
|
|
logger.info(`User ${req.userId} left server ${serverId}`);
|
|
|
|
res.json({
|
|
message: 'Left server successfully',
|
|
server: server || null
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('Error leaving server:', error);
|
|
res.status(500).json({ error: error.message });
|
|
}
|
|
});
|
|
|
|
// Get server details
|
|
router.get('/:serverId', authenticateToken, async (req, res) => {
|
|
try {
|
|
const { serverId } = req.params;
|
|
|
|
if (!serverId) {
|
|
return res.status(400).json({ error: 'Server ID required' });
|
|
}
|
|
|
|
const gameSystem = getGameSystem();
|
|
const server = gameSystem.servers.get(serverId);
|
|
|
|
if (!server) {
|
|
return res.status(404).json({ error: 'Server not found' });
|
|
}
|
|
|
|
// Get player details for all players in the server
|
|
const Player = require('../models/Player');
|
|
const players = await Player.find({
|
|
userId: { $in: server.players }
|
|
}).select('userId username info stats');
|
|
|
|
res.json({
|
|
server: {
|
|
id: server.id,
|
|
name: server.name,
|
|
type: server.type,
|
|
maxPlayers: server.maxPlayers,
|
|
currentPlayers: server.players.length,
|
|
region: server.region,
|
|
status: server.status,
|
|
ownerId: server.ownerId,
|
|
createdAt: server.createdAt,
|
|
settings: server.settings
|
|
},
|
|
players: players.map(player => ({
|
|
userId: player.userId,
|
|
username: player.username,
|
|
level: player.stats.level,
|
|
title: player.info.title,
|
|
rank: player.info.rank
|
|
}))
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('Error getting server details:', error);
|
|
res.status(500).json({ error: 'Internal server error' });
|
|
}
|
|
});
|
|
|
|
// Get user's current server
|
|
router.get('/current', authenticateToken, async (req, res) => {
|
|
try {
|
|
const Player = require('../models/Player');
|
|
const player = await Player.findOne({ userId: req.userId });
|
|
|
|
if (!player || !player.currentServer) {
|
|
return res.json({ currentServer: null });
|
|
}
|
|
|
|
const gameSystem = getGameSystem();
|
|
const server = gameSystem.servers.get(player.currentServer);
|
|
|
|
if (!server) {
|
|
// Clear the invalid server reference
|
|
player.currentServer = null;
|
|
await player.save();
|
|
return res.json({ currentServer: null });
|
|
}
|
|
|
|
res.json({
|
|
currentServer: {
|
|
id: server.id,
|
|
name: server.name,
|
|
type: server.type,
|
|
maxPlayers: server.maxPlayers,
|
|
currentPlayers: server.players.length,
|
|
region: server.region,
|
|
status: server.status
|
|
}
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('Error getting current server:', error);
|
|
res.status(500).json({ error: 'Internal server error' });
|
|
}
|
|
});
|
|
|
|
// Update server settings (owner only)
|
|
router.put('/:serverId/settings', authenticateToken, async (req, res) => {
|
|
try {
|
|
const { serverId } = req.params;
|
|
const { settings } = req.body;
|
|
|
|
if (!serverId) {
|
|
return res.status(400).json({ error: 'Server ID required' });
|
|
}
|
|
|
|
const gameSystem = getGameSystem();
|
|
const server = gameSystem.servers.get(serverId);
|
|
|
|
if (!server) {
|
|
return res.status(404).json({ error: 'Server not found' });
|
|
}
|
|
|
|
// Check if user is the server owner
|
|
if (server.ownerId !== req.userId) {
|
|
return res.status(403).json({ error: 'Only server owner can update settings' });
|
|
}
|
|
|
|
// Update server settings
|
|
server.settings = { ...server.settings, ...settings };
|
|
|
|
logger.info(`Server settings updated: ${serverId} by user ${req.userId}`);
|
|
|
|
res.json({
|
|
message: 'Server settings updated successfully',
|
|
settings: server.settings
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('Error updating server settings:', error);
|
|
res.status(500).json({ error: 'Internal server error' });
|
|
}
|
|
});
|
|
|
|
// Delete server (owner only)
|
|
router.delete('/:serverId', authenticateToken, async (req, res) => {
|
|
try {
|
|
const { serverId } = req.params;
|
|
|
|
if (!serverId) {
|
|
return res.status(400).json({ error: 'Server ID required' });
|
|
}
|
|
|
|
const gameSystem = getGameSystem();
|
|
const server = gameSystem.servers.get(serverId);
|
|
|
|
if (!server) {
|
|
return res.status(404).json({ error: 'Server not found' });
|
|
}
|
|
|
|
// Check if user is the server owner
|
|
if (server.ownerId !== req.userId) {
|
|
return res.status(403).json({ error: 'Only server owner can delete server' });
|
|
}
|
|
|
|
// Remove all players from the server
|
|
for (const playerId of server.players) {
|
|
await gameSystem.leaveServer(serverId, playerId);
|
|
|
|
// Update player's current server
|
|
const Player = require('../models/Player');
|
|
await Player.findOneAndUpdate(
|
|
{ userId: playerId },
|
|
{ currentServer: null }
|
|
);
|
|
}
|
|
|
|
// Delete the server
|
|
gameSystem.servers.delete(serverId);
|
|
|
|
logger.info(`Server deleted: ${serverId} by user ${req.userId}`);
|
|
|
|
res.json({
|
|
message: 'Server deleted successfully'
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('Error deleting server:', error);
|
|
res.status(500).json({ error: 'Internal server error' });
|
|
}
|
|
});
|
|
|
|
module.exports = router;
|