const path = require('path') const express = require('express') const multer = require('multer') const { z } = require('zod') const { nanoid } = require('nanoid') const { findGameById, createGame, updateGameThumbnail, createGameItem, deleteGameItem, deleteGame, } = require('../db') const { requireAdmin } = require('../middleware/auth') const router = express.Router() function buildUploadFilename(file) { const ext = path.extname(file.originalname || '').toLowerCase() const safeExt = ext && /^[.a-z0-9]+$/.test(ext) ? ext : '' return `${Date.now()}-${nanoid()}${safeExt}` } const upload = multer({ storage: multer.diskStorage({ destination: (req, file, cb) => cb(null, path.join(__dirname, '..', '..', 'uploads', 'games')), filename: (req, file, cb) => cb(null, buildUploadFilename(file)), }), limits: { fileSize: 6 * 1024 * 1024 }, }) router.post('/games', requireAdmin, async (req, res) => { const schema = z.object({ id: z.string().min(1), name: z.string().min(1).max(60) }) const parsed = schema.safeParse(req.body) if (!parsed.success) return res.status(400).json({ error: 'bad_request' }) const exists = await findGameById(parsed.data.id) if (exists) return res.status(409).json({ error: 'game_id_taken' }) const game = await createGame({ id: parsed.data.id, name: parsed.data.name }) res.json({ game }) }) router.post('/games/:gameId/thumbnail', requireAdmin, upload.single('thumbnail'), async (req, res) => { if (!req.file) return res.status(400).json({ error: 'file_required' }) const game = await findGameById(req.params.gameId) if (!game) return res.status(404).json({ error: 'not_found' }) const updated = await updateGameThumbnail(req.params.gameId, `/uploads/games/${req.file.filename}`) res.json({ game: updated }) }) router.post('/games/:gameId/images', requireAdmin, upload.single('image'), async (req, res) => { if (!req.file) return res.status(400).json({ error: 'file_required' }) const schema = z.object({ label: z.string().min(1).max(60) }) const parsed = schema.safeParse(req.body) if (!parsed.success) return res.status(400).json({ error: 'bad_request' }) const game = await findGameById(req.params.gameId) if (!game) return res.status(404).json({ error: 'not_found' }) const item = await createGameItem({ id: nanoid(), gameId: game.id, src: `/uploads/games/${req.file.filename}`, label: parsed.data.label, }) res.json({ item }) }) router.delete('/games/:gameId/items/:itemId', requireAdmin, async (req, res) => { const game = await findGameById(req.params.gameId) if (!game) return res.status(404).json({ error: 'not_found' }) await deleteGameItem(req.params.itemId) res.json({ ok: true }) }) router.delete('/games/:gameId', requireAdmin, async (req, res) => { const game = await findGameById(req.params.gameId) if (!game) return res.status(404).json({ error: 'not_found' }) await deleteGame(req.params.gameId) res.json({ ok: true }) }) module.exports = router