You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
235 lines
6.4 KiB
235 lines
6.4 KiB
// task.js
|
|
// Copyright (C) 2024 DTP Technologies, LLC
|
|
// All Rights Reserved
|
|
|
|
'use strict';
|
|
|
|
import express from 'express';
|
|
|
|
import { SiteController, SiteError } from '../../lib/site-lib.js';
|
|
|
|
export default class TaskController extends SiteController {
|
|
|
|
static get name ( ) { return 'TaskController'; }
|
|
static get slug ( ) { return 'task'; }
|
|
|
|
constructor (dtp) {
|
|
super(dtp, TaskController);
|
|
}
|
|
|
|
async start ( ) {
|
|
const { dtp } = this;
|
|
|
|
const { limiter: limiterService } = dtp.services;
|
|
const limiterConfig = limiterService.config.task;
|
|
|
|
const multer = this.createMulter(TaskController.slug, {
|
|
limits: {
|
|
fileSize: 1024 * 1000 * 5,
|
|
},
|
|
});
|
|
|
|
const router = express.Router();
|
|
dtp.app.use('/task', router);
|
|
|
|
router.use(async (req, res, next) => {
|
|
res.locals.currentView = TaskController.name;
|
|
return next();
|
|
});
|
|
|
|
async function checkTaskOwnership (req, res, next) {
|
|
if (!res.locals.task.user._id.equals(req.user._id)) {
|
|
throw new SiteError(401, 'This is not your task');
|
|
}
|
|
return next();
|
|
}
|
|
|
|
async function checkSessionOwnership (req, res, next) {
|
|
if (!res.locals.session.user._id.equals(req.user._id)) {
|
|
throw new SiteError(401, 'This is not your session');
|
|
}
|
|
return next();
|
|
}
|
|
|
|
router.param('taskId', this.populateTaskId.bind(this));
|
|
router.param('sessionId', this.populateSessionId.bind(this));
|
|
|
|
router.post(
|
|
'/:taskId/session/start',
|
|
limiterService.create(limiterConfig.postStartTaskSession),
|
|
this.postStartTaskSession.bind(this),
|
|
);
|
|
|
|
router.post(
|
|
'/:taskId/session/:sessionId/screenshot',
|
|
checkSessionOwnership,
|
|
limiterService.create(limiterConfig.postTaskSessionScreenshot),
|
|
multer.single('image'),
|
|
this.postTaskSessionScreenshot.bind(this),
|
|
);
|
|
|
|
router.post(
|
|
'/:taskId/session/:sessionId/close',
|
|
limiterService.create(limiterConfig.postCloseTaskSession),
|
|
checkSessionOwnership,
|
|
this.postCloseTaskSession.bind(this),
|
|
);
|
|
|
|
router.post(
|
|
'/:taskId/start',
|
|
limiterService.create(limiterConfig.postStartTask),
|
|
checkTaskOwnership,
|
|
this.postStartTask.bind(this),
|
|
);
|
|
router.post(
|
|
'/:taskId/close',
|
|
limiterService.create(limiterConfig.postCloseTask),
|
|
checkTaskOwnership,
|
|
this.postCloseTask.bind(this),
|
|
);
|
|
|
|
router.post(
|
|
'/',
|
|
limiterService.create(limiterConfig.postCreateTask),
|
|
this.postCreateTask.bind(this),
|
|
);
|
|
|
|
router.get(
|
|
'/:taskId/session/:sessionId',
|
|
limiterService.create(limiterConfig.getTaskSessionView),
|
|
checkSessionOwnership,
|
|
this.getTaskSessionView.bind(this),
|
|
);
|
|
|
|
router.get(
|
|
'/:taskId',
|
|
limiterService.create(limiterConfig.getTaskView),
|
|
checkTaskOwnership,
|
|
this.getTaskView.bind(this),
|
|
);
|
|
}
|
|
|
|
async populateTaskId (req, res, next, taskId) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
res.locals.task = await taskService.getTaskById(taskId);
|
|
if (!res.locals.task) {
|
|
throw new SiteError(404, 'Task not found');
|
|
}
|
|
return next();
|
|
} catch (error) {
|
|
return next(error);
|
|
}
|
|
}
|
|
|
|
async populateSessionId (req, res, next, sessionId) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
res.locals.session = await taskService.getTaskSessionById(sessionId);
|
|
if (!res.locals.session) {
|
|
throw new SiteError(404, 'Task session not found');
|
|
}
|
|
return next();
|
|
} catch (error) {
|
|
return next(error);
|
|
}
|
|
}
|
|
|
|
async postStartTaskSession (req, res) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
res.locals.session = await taskService.createTaskSession(res.locals.task);
|
|
res.status(200).json({
|
|
success: true,
|
|
session: res.locals.session,
|
|
});
|
|
} catch (error) {
|
|
this.log.error('failed to create task session', { error });
|
|
res.status(error.statusCode || 500).json({
|
|
success: false,
|
|
message: error.message,
|
|
});
|
|
}
|
|
}
|
|
|
|
async postTaskSessionScreenshot (req, res) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
await taskService.addTaskSessionScreenshot(res.locals.session, req.file);
|
|
res.status(200).json({ success: true });
|
|
} catch (error) {
|
|
this.log.error('failed to add task session screenshot', { error });
|
|
res.status(error.statusCode || 500).json({
|
|
success: false,
|
|
message: error.message,
|
|
});
|
|
}
|
|
}
|
|
|
|
async postCloseTaskSession (req, res) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
await taskService.closeTaskSession(res.locals.session);
|
|
res.status(200).json({ success: true });
|
|
} catch (error) {
|
|
this.log.error('failed to close task session', { error });
|
|
res.status(error.statusCode || 500).json({
|
|
success: false,
|
|
message: error.message,
|
|
});
|
|
}
|
|
}
|
|
|
|
async postStartTask (req, res, next) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
await taskService.startTask(res.locals.task);
|
|
res.redirect(`/task/${res.locals.task._id}`);
|
|
} catch (error) {
|
|
this.log.error('failed to close task session', { error });
|
|
return next(error);
|
|
}
|
|
}
|
|
|
|
async postCloseTask (req, res, next) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
await taskService.closeTask(res.locals.task);
|
|
res.redirect('/');
|
|
} catch (error) {
|
|
this.log.error('failed to close task', { error });
|
|
return next(error);
|
|
}
|
|
}
|
|
|
|
async postCreateTask (req, res, next) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
res.locals.task = await taskService.createTask(req.user, req.body);
|
|
res.redirect(`/task/${res.locals.task._id}`);
|
|
} catch (error) {
|
|
this.log.error('failed to create new task', { error });
|
|
return next(error);
|
|
}
|
|
}
|
|
|
|
async getTaskSessionView (req, res) {
|
|
res.render('task/session/view');
|
|
}
|
|
|
|
async getTaskView (req, res, next) {
|
|
const { task: taskService } = this.dtp.services;
|
|
try {
|
|
res.locals.pagination = this.getPaginationParameters(req, 50);
|
|
res.locals.sessions = await taskService.getSessionsForTask(
|
|
res.locals.task,
|
|
res.locals.pagination,
|
|
);
|
|
|
|
res.render('task/view');
|
|
} catch (error) {
|
|
this.log.error('failed to present the Task view', { error });
|
|
return next(error);
|
|
}
|
|
}
|
|
}
|