mirror of
https://gitcode.com/gh_mirrors/hy/Hydro.git
synced 2026-10-20 01:38:19 +08:00
core: auto-manage daily task
This commit is contained in:
1 parent
c7c70a6abb
commit
bf88b828ec
4 files changed
+33
-34
No files matched your search
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "hydrooj",
|
"name": "hydrooj",
|
||||||
"version": "2.32.16",
|
"version": "2.32.17",
|
||||||
"bin": "bin/hydrooj.js",
|
"bin": "bin/hydrooj.js",
|
||||||
"main": "src/loader",
|
"main": "src/loader",
|
||||||
"module": "src/loader",
|
"module": "src/loader",
|
||||||
|
|||||||
@@ -310,17 +310,13 @@ export class ContestProblemHandler extends Handler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class ContestProblemFileDownloadHandler extends ContestProblemHandler {
|
export class ContestProblemFileDownloadHandler extends ContestProblemHandler {
|
||||||
@query('type', Types.Range(['additional_file', 'testdata']), true)
|
|
||||||
@param('filename', Types.Name)
|
@param('filename', Types.Name)
|
||||||
@param('noDisposition', Types.Boolean)
|
@param('noDisposition', Types.Boolean)
|
||||||
async get(domainId: string, type = 'additional_file', filename: string, noDisposition = false) {
|
async get(domainId: string, filename: string, noDisposition = false) {
|
||||||
if (type === 'testdata' && !this.user.own(this.pdoc)) {
|
|
||||||
if (!this.user.hasPriv(PRIV.PRIV_READ_PROBLEM_DATA)) this.checkPerm(PERM.PERM_READ_PROBLEM_DATA);
|
|
||||||
}
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
if (typeof this.pdoc.docId === 'string') this.pdoc.docId = this.pdoc.docId.split(':')[1];
|
if (typeof this.pdoc.docId === 'string') this.pdoc.docId = this.pdoc.docId.split(':')[1];
|
||||||
this.response.redirect = await storage.signDownloadLink(
|
this.response.redirect = await storage.signDownloadLink(
|
||||||
`problem/${this.pdoc.domainId}/${this.pdoc.docId}/${type}/${filename}`,
|
`problem/${this.pdoc.domainId}/${this.pdoc.docId}/additional_file/${filename}`,
|
||||||
noDisposition ? undefined : filename, false, 'user',
|
noDisposition ? undefined : filename, false, 'user',
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -175,18 +175,14 @@ class HomeworkDetailProblemHandler extends Handler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export class HomeworkProblemFileDownloadHandler extends HomeworkDetailProblemHandler {
|
export class HomeworkProblemFileDownloadHandler extends HomeworkDetailProblemHandler {
|
||||||
@query('type', Types.Range(['additional_file', 'testdata']), true)
|
|
||||||
@param('filename', Types.Name)
|
@param('filename', Types.Name)
|
||||||
@param('noDisposition', Types.Boolean)
|
@param('noDisposition', Types.Boolean)
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
async get(domainId: string, type = 'additional_file', filename: string, noDisposition = false) {
|
async get(domainId: string, filename: string, noDisposition = false) {
|
||||||
if (type === 'testdata' && !this.user.own(this.pdoc)) {
|
|
||||||
if (!this.user.hasPriv(PRIV.PRIV_READ_PROBLEM_DATA)) this.checkPerm(PERM.PERM_READ_PROBLEM_DATA);
|
|
||||||
}
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
if (typeof this.pdoc.docId === 'string') this.pdoc.docId = this.pdoc.docId.split(':')[1];
|
if (typeof this.pdoc.docId === 'string') this.pdoc.docId = this.pdoc.docId.split(':')[1];
|
||||||
this.response.redirect = await storage.signDownloadLink(
|
this.response.redirect = await storage.signDownloadLink(
|
||||||
`problem/${this.pdoc.domainId}/${this.pdoc.docId}/${type}/${filename}`,
|
`problem/${this.pdoc.domainId}/${this.pdoc.docId}/additional_file/${filename}`,
|
||||||
noDisposition ? undefined : filename, false, 'user',
|
noDisposition ? undefined : filename, false, 'user',
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -60,25 +60,19 @@ class Consumer {
|
|||||||
|
|
||||||
class WorkerService implements BaseService {
|
class WorkerService implements BaseService {
|
||||||
private handlers: Record<string, Function> = {};
|
private handlers: Record<string, Function> = {};
|
||||||
public consumer: Consumer;
|
public consumer = new Consumer(
|
||||||
public started = false;
|
{ type: 'schedule', subType: { $in: Object.keys(this.handlers) } },
|
||||||
|
async (doc) => {
|
||||||
public start() {
|
try {
|
||||||
this.consumer = new Consumer(
|
logger.debug('Worker task: %o', doc);
|
||||||
{ type: 'schedule', subType: { $in: Object.keys(this.handlers) } },
|
await this.handlers[doc.subType](doc);
|
||||||
async (doc) => {
|
} catch (e) {
|
||||||
try {
|
logger.error('Worker task fail: ', e);
|
||||||
logger.debug('Worker task: %o', doc);
|
logger.error('%o', doc);
|
||||||
await this.handlers[doc.subType](doc);
|
}
|
||||||
} catch (e) {
|
},
|
||||||
logger.error('Worker task fail: ', e);
|
false,
|
||||||
logger.error('%o', doc);
|
);
|
||||||
}
|
|
||||||
},
|
|
||||||
false,
|
|
||||||
);
|
|
||||||
this.started = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
public addHandler(type: string, handler: Function) {
|
public addHandler(type: string, handler: Function) {
|
||||||
this.handlers[type] = handler;
|
this.handlers[type] = handler;
|
||||||
@@ -87,7 +81,6 @@ class WorkerService implements BaseService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const Worker = new WorkerService();
|
const Worker = new WorkerService();
|
||||||
Worker.start();
|
|
||||||
|
|
||||||
class TaskModel {
|
class TaskModel {
|
||||||
static async add(task: Partial<Task> & { type: string }) {
|
static async add(task: Partial<Task> & { type: string }) {
|
||||||
@@ -122,7 +115,7 @@ class TaskModel {
|
|||||||
|
|
||||||
static async getDelay(query?: FilterQuery<Task>): Promise<[number, Date]> {
|
static async getDelay(query?: FilterQuery<Task>): Promise<[number, Date]> {
|
||||||
const now = new Date();
|
const now = new Date();
|
||||||
const res = await coll.findOne(query, { sort: { executeAfter: 1 } });
|
const [res] = await coll.find(query).sort({ executeAfter: 1 }).limit(1).toArray();
|
||||||
if (res) return [Math.max(0, now.getTime() - res.executeAfter.getTime()), res.executeAfter];
|
if (res) return [Math.max(0, now.getTime() - res.executeAfter.getTime()), res.executeAfter];
|
||||||
return [0, now];
|
return [0, now];
|
||||||
}
|
}
|
||||||
@@ -136,7 +129,21 @@ class TaskModel {
|
|||||||
static Worker = Worker;
|
static Worker = Worker;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Worker.addHandler('task.daily', async () => {
|
||||||
|
await global.Hydro.script.rp?.run({}, new Logger('task/rp').debug);
|
||||||
|
await global.Hydro.script.problemStat?.run({}, new Logger('task/problem').debug);
|
||||||
|
});
|
||||||
bus.on('domain/delete', (domainId) => coll.deleteMany({ domainId }));
|
bus.on('domain/delete', (domainId) => coll.deleteMany({ domainId }));
|
||||||
|
bus.once('app/started', async () => {
|
||||||
|
if (!await TaskModel.count({ type: 'schedule', subType: 'task.daily' })) {
|
||||||
|
await TaskModel.add({
|
||||||
|
type: 'schedule',
|
||||||
|
subType: 'task.daily',
|
||||||
|
executeAfter: moment().hour(3).minute(0).second(0).millisecond(0).toDate(),
|
||||||
|
interval: [1, 'day'],
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
export default TaskModel;
|
export default TaskModel;
|
||||||
global.Hydro.model.task = TaskModel;
|
global.Hydro.model.task = TaskModel;
|
||||||
Reference in new issue
Block a user