fix(worker): handle edge cases when jobs are not delayed

This commit is contained in:
Carl-Gerhard Lindesvärd
2024-09-25 09:11:54 +02:00
parent 66a49c53cf
commit ea141e99a2
7 changed files with 116 additions and 43 deletions

View File

@@ -99,7 +99,7 @@ async function start() {
logger.info('job completed', {
worker: worker.name,
data: job.data,
duration:
elapsed:
job.processedOn && job.finishedOn
? job.finishedOn - job.processedOn
: undefined,

View File

@@ -44,7 +44,7 @@ async function getCompleteSessionWithSessionStart({
logger: ILogger;
}): Promise<ReturnType<typeof getEvents>> {
const intervals = [6, 12, 24, 72];
let intervalIndex = 0;
for (const hoursInterval of intervals) {
const events = await getCompleteSession({
projectId,
@@ -56,7 +56,10 @@ async function getCompleteSessionWithSessionStart({
return events;
}
logger.warn(`Checking last ${hoursInterval} hours for session_start`);
const nextHoursInterval = intervals[++intervalIndex];
if (nextHoursInterval) {
logger.warn(`Checking last ${nextHoursInterval} hours for session_start`);
}
}
return [];

View File

@@ -9,7 +9,11 @@ import { getTime, isSameDomain, parsePath } from '@openpanel/common';
import type { IServiceCreateEventPayload } from '@openpanel/db';
import { createEvent } from '@openpanel/db';
import { getLastScreenViewFromProfileId } from '@openpanel/db/src/services/event.service';
import { findJobByPrefix, sessionsQueue } from '@openpanel/queue';
import {
findJobByPrefix,
sessionsQueue,
sessionsQueueEvents,
} from '@openpanel/queue';
import type {
EventsQueuePayloadCreateSessionEnd,
EventsQueuePayloadIncomingEvent,
@@ -215,18 +219,48 @@ async function getSessionEnd({
currentDeviceId: string;
previousDeviceId: string;
}) {
async function handleJobStates(
job: Job,
): Promise<{ deviceId: string; job: Job } | null> {
const state = await job.getState();
if (state === 'delayed') {
return { deviceId: currentDeviceId, job };
}
if (state === 'completed' || state === 'failed') {
await job.remove();
}
if (state === 'active' || state === 'waiting') {
await job.waitUntilFinished(sessionsQueueEvents, 1000 * 10);
return getSessionEnd({
projectId,
currentDeviceId,
previousDeviceId,
});
}
return null;
}
const job = await sessionsQueue.getJob(
getSessionEndJobId(projectId, currentDeviceId),
);
if (job && (await job.isDelayed())) {
return { deviceId: currentDeviceId, job };
if (job) {
const res = await handleJobStates(job);
if (res) {
return res;
}
}
const previousJob = await sessionsQueue.getJob(
getSessionEndJobId(projectId, previousDeviceId),
);
if (previousJob && (await previousJob.isDelayed())) {
return { deviceId: previousDeviceId, job: previousJob };
if (previousJob) {
const res = await handleJobStates(previousJob);
if (res) {
return res;
}
}
// Fallback during migration period