'use strict'; const path = require('path'); const express = require('express'); const expressSession = require('express-session'); const debug = require('debug')('Server'); const Util = require('./Util'); const ServerError = require('./ServerError'); const WireGuard = require('../services/WireGuard'); const { PORT, PASSWORD, } = require('../config'); module.exports = class Server { constructor() { // Express this.app = express() .use('/', express.static(path.join(__dirname, '..', 'www'))) .use(express.json()) .use(expressSession({ secret: String(Math.random()), resave: true, saveUninitialized: true, })) // Authentication .get('/api/session', Util.promisify(async req => { return { authenticated: !!(req.session && req.session.authenticated), }; })) .post('/api/session', Util.promisify(async req => { const { password, } = req.body; if (typeof password !== 'string') { throw new ServerError('Missing: Password', 401); } if (password !== PASSWORD) { throw new ServerError('Incorrect Password', 401); } req.session.authenticated = true; req.session.save(); debug(`New Session: ${req.session.id})`); })) // WireGuard .use(Util.requireSession) .delete('/api/session', Util.promisify(async req => { const sessionId = req.session.id; req.session.destroy(); debug(`Deleted Session: ${sessionId}`); })) .get('/api/wireguard/client', Util.promisify(async req => { return WireGuard.getClients(); })) .get('/api/wireguard/client/:clientId/qrcode.svg', Util.promisify(async (req, res) => { const { clientId } = req.params; const svg = await WireGuard.getClientQRCodeSVG({ clientId }); res.header('Content-Type', 'image/svg+xml'); res.send(svg); })) .get('/api/wireguard/client/:clientId/configuration', Util.promisify(async (req, res) => { const { clientId } = req.params; const client = await WireGuard.getClient({ clientId }); const config = await WireGuard.getClientConfiguration({ clientId }); res.header('Content-Disposition', `attachment; filename="${client.name}.conf"`); res.header('Content-Type', 'text/plain'); res.send(config); })) .post('/api/wireguard/client', Util.promisify(async req => { const { name } = req.body; return WireGuard.createClient({ name }); })) .delete('/api/wireguard/client/:clientId', Util.promisify(async req => { const { clientId } = req.params; return WireGuard.deleteClient({ clientId }); })) .post('/api/wireguard/client/:clientId/enable', Util.promisify(async req => { const { clientId } = req.params; return WireGuard.enableClient({ clientId }); })) .post('/api/wireguard/client/:clientId/disable', Util.promisify(async req => { const { clientId } = req.params; return WireGuard.disableClient({ clientId }); })) .listen(PORT, () => { debug(`Listening on http://0.0.0.0:${PORT}`); }); } };