mirror of
https://github.com/whyour/qinglong.git
synced 2026-07-01 04:40:38 +08:00
增加任务重复运行提醒
This commit is contained in:
+43
-1
@@ -3,14 +3,29 @@ import os from 'os';
|
||||
import { AuthDataType, SystemModel } from '../data/system';
|
||||
import Logger from '../loaders/logger';
|
||||
import { Dependence } from '../data/dependence';
|
||||
import { ICron } from '../protos/cron';
|
||||
import NotificationService from '../services/notify';
|
||||
import { Inject } from 'typedi';
|
||||
|
||||
export type Override<
|
||||
T,
|
||||
K extends Partial<{ [P in keyof T]: any }> | string,
|
||||
> = K extends string
|
||||
? Omit<T, K> & { [P in keyof T]: T[P] | unknown }
|
||||
: Omit<T, keyof K> & K;
|
||||
type TCron = Override<Partial<ICron>, { id: string }>;
|
||||
interface IDependencyFn<T> {
|
||||
(): Promise<T>;
|
||||
dependency?: Dependence;
|
||||
}
|
||||
interface ICronFn<T> {
|
||||
(): Promise<T>;
|
||||
cron?: TCron;
|
||||
}
|
||||
class TaskLimit {
|
||||
private dependenyLimit = new PQueue({ concurrency: 1 });
|
||||
private queuedDependencyIds = new Set<number>([]);
|
||||
private queuedCrons = new Map<string, TCron[]>();
|
||||
private updateLogLimit = new PQueue({ concurrency: 1 });
|
||||
private cronLimit = new PQueue({
|
||||
concurrency: Math.max(os.cpus().length, 4),
|
||||
@@ -18,6 +33,8 @@ class TaskLimit {
|
||||
private manualCronoLimit = new PQueue({
|
||||
concurrency: Math.max(os.cpus().length, 4),
|
||||
});
|
||||
@Inject((type) => NotificationService)
|
||||
private notificationService!: NotificationService;
|
||||
|
||||
get cronLimitActiveCount() {
|
||||
return this.cronLimit.pending;
|
||||
@@ -71,6 +88,16 @@ class TaskLimit {
|
||||
}
|
||||
}
|
||||
|
||||
public removeQueuedCron(id: string) {
|
||||
if (this.queuedCrons.has(id)) {
|
||||
const runs = this.queuedCrons.get(id);
|
||||
if (runs && runs.length > 0) {
|
||||
runs.pop();
|
||||
this.queuedCrons.set(id, runs);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public async setCustomLimit(limit?: number) {
|
||||
if (limit) {
|
||||
this.cronLimit.concurrency = limit;
|
||||
@@ -88,9 +115,24 @@ class TaskLimit {
|
||||
}
|
||||
|
||||
public async runWithCronLimit<T>(
|
||||
fn: () => Promise<T>,
|
||||
cron: TCron,
|
||||
fn: ICronFn<T>,
|
||||
options?: Partial<QueueAddOptions>,
|
||||
): Promise<T | void> {
|
||||
let runs = this.queuedCrons.get(cron.id);
|
||||
if (!runs?.length) {
|
||||
runs = [];
|
||||
}
|
||||
runs.push(cron);
|
||||
if (runs.length >= 5) {
|
||||
this.notificationService.notify(
|
||||
'任务重复运行',
|
||||
`任务 ${cron.name} ${cron.command} 处于运行中的已达 5 个,请检查系统日志`,
|
||||
);
|
||||
return;
|
||||
}
|
||||
this.queuedCrons.set(cron.id, runs);
|
||||
fn.cron = cron;
|
||||
return this.cronLimit.add(fn, options);
|
||||
}
|
||||
|
||||
|
||||
+11
-4
@@ -1,11 +1,18 @@
|
||||
import { spawn } from 'cross-spawn';
|
||||
import taskLimit from './pLimit';
|
||||
import Logger from '../loaders/logger';
|
||||
import { ICron } from '../protos/cron';
|
||||
|
||||
export function runCron(cmd: string, options?: { schedule: string; extraSchedules: Array<{ schedule: string }>; name: string }): Promise<number | void> {
|
||||
return taskLimit.runWithCronLimit(() => {
|
||||
export function runCron(cmd: string, cron: ICron): Promise<number | void> {
|
||||
return taskLimit.runWithCronLimit(cron, () => {
|
||||
return new Promise(async (resolve: any) => {
|
||||
Logger.info(`[schedule][开始执行任务] 参数 ${JSON.stringify({ ...options, command: cmd })}`);
|
||||
taskLimit.removeQueuedCron(cron.id);
|
||||
Logger.info(
|
||||
`[schedule][开始执行任务] 参数 ${JSON.stringify({
|
||||
...cron,
|
||||
command: cmd,
|
||||
})}`,
|
||||
);
|
||||
const cp = spawn(cmd, { shell: '/bin/bash' });
|
||||
|
||||
cp.stderr.on('data', (data) => {
|
||||
@@ -24,7 +31,7 @@ export function runCron(cmd: string, options?: { schedule: string; extraSchedule
|
||||
});
|
||||
|
||||
cp.on('exit', async (code) => {
|
||||
resolve({ ...options, command: cmd, pid: cp.pid, code });
|
||||
resolve({ ...cron, command: cmd, pid: cp.pid, code });
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user