dragonflight/services/mam-api/src/routes/capture.js

64 lines
1.7 KiB
JavaScript
Raw Normal View History

// TODO(authz): per-project scoping not yet enforced. Capture sessions carry a
// project_id; adopt assertProjectAccess (auth/authz.js) — see bins.js pattern.
import express from 'express';
const router = express.Router();
const CAPTURE_URL = process.env.CAPTURE_URL || 'http://capture:3001';
async function proxyRequest(method, path, body = null) {
const options = {
method,
headers: { 'Content-Type': 'application/json' },
signal: AbortSignal.timeout(8000),
};
if (body) options.body = JSON.stringify(body);
const response = await fetch(`${CAPTURE_URL}${path}`, options);
const text = await response.text();
let data;
try {
data = JSON.parse(text);
} catch {
// Capture service returned non-JSON (HTML error page, plain text, etc.)
data = { message: text.slice(0, 300) || '(empty response)' };
}
return { status: response.status, data };
}
// POST /start
router.post('/start', async (req, res, next) => {
try {
const { status, data } = await proxyRequest('POST', '/start', req.body);
res.status(status).json(data);
} catch (err) { next(err); }
});
// POST /stop
router.post('/stop', async (req, res, next) => {
try {
const { status, data } = await proxyRequest('POST', '/stop', req.body);
res.status(status).json(data);
} catch (err) { next(err); }
});
// GET /status
router.get('/status', async (req, res, next) => {
try {
const { status, data } = await proxyRequest('GET', '/status');
res.status(status).json(data);
} catch (err) { next(err); }
});
// GET /devices
router.get('/devices', async (req, res, next) => {
try {
const { status, data } = await proxyRequest('GET', '/devices');
res.status(status).json(data);
} catch (err) { next(err); }
});
export default router;