Review a pull request: ticket attachments
Not solvedCustomers can now attach files to support tickets. Upload handling is one of the riskiest features to get wrong — review it.
- Level
- Practitioner
- Estimated time
- ~25 min
- Points
- 0/85 pts
- Questions
- 0/0 answered
- OWASP
- A01:2025
- OWASP
- A05:2025
- OWASP
- A06:2025
- CWE
- CWE-434
- CWE
- CWE-22
- CWE
- CWE-639
src/routes/attachments.ts0/4 found
| import path from 'node:path' | ||
| import fs from 'node:fs/promises' | ||
| import multer from 'multer' | ||
| + | const UPLOAD_DIR = path.join(__dirname, '../../public/uploads') | |
| + | const upload = multer({ limits: { fileSize: 5 * 1024 * 1024 } }) | |
| + | ||
| + | // Customers attach screenshots and invoices to their support tickets | |
| + | router.post('/api/tickets/:id/attachments', requireAuth, upload.single('file'), async (req, res) => { | |
| + | const file = req.file | |
| + | if (!/\.(png|jpe?g|pdf)/i.test(file.originalname)) { | |
| + | return res.status(400).json({ error: 'Only images and PDFs are allowed' }) | |
| + | } | |
| + | const ticket = await db.tickets.findById(req.params.id) | |
| + | if (!ticket) return res.status(404).json({ error: 'Not found' }) | |
| + | const dest = path.join(UPLOAD_DIR, file.originalname) | |
| + | await fs.writeFile(dest, file.buffer) | |
| + | const url = `/uploads/${encodeURIComponent(file.originalname)}` | |
| + | await db.attachments.insert({ ticketId: ticket.id, url, uploadedBy: req.user.id }) | |
| + | res.status(201).json({ url }) | |
| + | }) | |
| + | ||
| + | router.get('/uploads/:name', requireAuth, (req, res) => { | |
| + | res.type(String(req.query.type || path.extname(req.params.name))) | |
| + | res.sendFile(path.join(UPLOAD_DIR, path.basename(req.params.name))) | |
| + | }) |
Click a line number to flag a defect. The review code appears when every defect is flagged with no false positives.