chore: update the processor of the notification
This commit is contained in:
@@ -13,7 +13,7 @@ export function databaseConfigs(): TypeOrmModuleAsyncOptions {
|
|||||||
username: configService.getOrThrow<string>("DB_USER"),
|
username: configService.getOrThrow<string>("DB_USER"),
|
||||||
password: configService.getOrThrow<string>("DB_PASS"),
|
password: configService.getOrThrow<string>("DB_PASS"),
|
||||||
autoLoadEntities: true,
|
autoLoadEntities: true,
|
||||||
synchronize: configService.getOrThrow<string>("NODE_ENV") == "production" ? false : true,
|
synchronize: configService.getOrThrow<string>("NODE_ENV") == "production" ? false : false,
|
||||||
logging: configService.getOrThrow<string>("NODE_ENV") == "production" ? false : true,
|
logging: configService.getOrThrow<string>("NODE_ENV") == "production" ? false : true,
|
||||||
migrationsTableName: "typeorm_migrations",
|
migrationsTableName: "typeorm_migrations",
|
||||||
migrationsRun: false,
|
migrationsRun: false,
|
||||||
|
|||||||
@@ -41,7 +41,12 @@ type NotificationJobData = {
|
|||||||
| INewTicketNotificationData;
|
| INewTicketNotificationData;
|
||||||
};
|
};
|
||||||
|
|
||||||
@Processor(NOTIFICATION.QUEUE_NAME, { concurrency: 5 })
|
@Processor(NOTIFICATION.QUEUE_NAME, {
|
||||||
|
concurrency: 5,
|
||||||
|
lockDuration: 30000, // 30 seconds lock duration
|
||||||
|
stalledInterval: 30000, // Check for stalled jobs every 30 seconds
|
||||||
|
maxStalledCount: 2, // Allow 2 stalls before failing
|
||||||
|
})
|
||||||
export class NotificationProcessor extends WorkerProcessor {
|
export class NotificationProcessor extends WorkerProcessor {
|
||||||
protected readonly logger = new Logger(NotificationProcessor.name);
|
protected readonly logger = new Logger(NotificationProcessor.name);
|
||||||
|
|
||||||
@@ -62,103 +67,129 @@ export class NotificationProcessor extends WorkerProcessor {
|
|||||||
await queryRunner.connect();
|
await queryRunner.connect();
|
||||||
await queryRunner.startTransaction();
|
await queryRunner.startTransaction();
|
||||||
|
|
||||||
|
const heartbeat = setInterval(() => {
|
||||||
|
job.updateProgress(50);
|
||||||
|
}, 10000); // Update progress every 10 seconds
|
||||||
|
|
||||||
const { type, recipientId, data } = job.data;
|
const { type, recipientId, data } = job.data;
|
||||||
|
|
||||||
switch (type) {
|
try {
|
||||||
// Admin Notifications
|
switch (type) {
|
||||||
case NotifType.NEW_BLOG_COMMENT:
|
// Admin Notifications
|
||||||
await this.notificationsService.createNewBlogCommentNotification(recipientId, data as IBlogCommentNotificationData, queryRunner);
|
case NotifType.NEW_BLOG_COMMENT:
|
||||||
break;
|
await this.notificationsService.createNewBlogCommentNotification(
|
||||||
case NotifType.NEW_SERVICE_REVIEW:
|
recipientId,
|
||||||
await this.notificationsService.createNewServiceReviewNotification(
|
data as IBlogCommentNotificationData,
|
||||||
recipientId,
|
queryRunner,
|
||||||
data as IServiceReviewNotificationData,
|
);
|
||||||
queryRunner,
|
break;
|
||||||
);
|
case NotifType.NEW_SERVICE_REVIEW:
|
||||||
break;
|
await this.notificationsService.createNewServiceReviewNotification(
|
||||||
case NotifType.NEW_CUSTOMER:
|
recipientId,
|
||||||
await this.notificationsService.createNewCustomerNotification(recipientId, data as INewCustomerNotificationData, queryRunner);
|
data as IServiceReviewNotificationData,
|
||||||
break;
|
queryRunner,
|
||||||
case NotifType.NEW_SUBSCRIPTION:
|
);
|
||||||
await this.notificationsService.createNewSubscriptionNotification(
|
break;
|
||||||
recipientId,
|
case NotifType.NEW_CUSTOMER:
|
||||||
data as INewSubscriptionNotificationData,
|
await this.notificationsService.createNewCustomerNotification(recipientId, data as INewCustomerNotificationData, queryRunner);
|
||||||
queryRunner,
|
break;
|
||||||
);
|
case NotifType.NEW_SUBSCRIPTION:
|
||||||
break;
|
await this.notificationsService.createNewSubscriptionNotification(
|
||||||
case NotifType.NEW_CRITICISM:
|
recipientId,
|
||||||
await this.notificationsService.createNewCriticismNotification(recipientId, data as INewCriticismNotificationData, queryRunner);
|
data as INewSubscriptionNotificationData,
|
||||||
break;
|
queryRunner,
|
||||||
case NotifType.NEW_TICKET:
|
);
|
||||||
await this.notificationsService.createNewTicketGlobalNotification(recipientId, data as INewTicketNotificationData, queryRunner);
|
break;
|
||||||
break;
|
case NotifType.NEW_CRITICISM:
|
||||||
|
await this.notificationsService.createNewCriticismNotification(recipientId, data as INewCriticismNotificationData, queryRunner);
|
||||||
|
break;
|
||||||
|
case NotifType.NEW_TICKET:
|
||||||
|
await this.notificationsService.createNewTicketGlobalNotification(recipientId, data as INewTicketNotificationData, queryRunner);
|
||||||
|
break;
|
||||||
|
|
||||||
// User Notifications
|
// User Notifications
|
||||||
case NotifType.USER_LOGIN:
|
case NotifType.USER_LOGIN:
|
||||||
await this.notificationsService.createLoginNotification(recipientId, data);
|
await this.notificationsService.createLoginNotification(recipientId, data);
|
||||||
break;
|
break;
|
||||||
case NotifType.ANNOUNCEMENT:
|
case NotifType.ANNOUNCEMENT:
|
||||||
await this.notificationsService.createAnnouncementNotification(recipientId, data as IAnnouncementNotificationData, queryRunner);
|
await this.notificationsService.createAnnouncementNotification(recipientId, data as IAnnouncementNotificationData, queryRunner);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
// Wallet Notifications
|
// Wallet Notifications
|
||||||
case NotifType.WALLET_CHARGE:
|
case NotifType.WALLET_CHARGE:
|
||||||
await this.notificationsService.createWalletChargeNotification(recipientId, data as IWalletNotificationData, queryRunner);
|
await this.notificationsService.createWalletChargeNotification(recipientId, data as IWalletNotificationData, queryRunner);
|
||||||
break;
|
break;
|
||||||
case NotifType.WALLET_DEDUCTION:
|
case NotifType.WALLET_DEDUCTION:
|
||||||
await this.notificationsService.createWalletDeductionNotification(recipientId, data as IWalletNotificationData, queryRunner);
|
await this.notificationsService.createWalletDeductionNotification(recipientId, data as IWalletNotificationData, queryRunner);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
// Ticket Notifications
|
// Ticket Notifications
|
||||||
case NotifType.ANSWER_TICKET:
|
case NotifType.ANSWER_TICKET:
|
||||||
await this.notificationsService.createAnswerTicketNotification(recipientId, data as ITicketNotificationData, queryRunner);
|
await this.notificationsService.createAnswerTicketNotification(recipientId, data as ITicketNotificationData, queryRunner);
|
||||||
break;
|
break;
|
||||||
case NotifType.CREATE_TICKET:
|
case NotifType.CREATE_TICKET:
|
||||||
await this.notificationsService.createTicketNotification(recipientId, data as ITicketNotificationData, queryRunner);
|
await this.notificationsService.createTicketNotification(recipientId, data as ITicketNotificationData, queryRunner);
|
||||||
break;
|
break;
|
||||||
case NotifType.ASSIGN_TICKET:
|
case NotifType.ASSIGN_TICKET:
|
||||||
await this.notificationsService.createAssignTicketNotificationForAdmin(recipientId, data as ITicketNotificationData, queryRunner);
|
await this.notificationsService.createAssignTicketNotificationForAdmin(
|
||||||
break;
|
recipientId,
|
||||||
|
data as ITicketNotificationData,
|
||||||
|
queryRunner,
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
|
||||||
// Invoice Notifications
|
// Invoice Notifications
|
||||||
case NotifType.CREATE_INVOICE:
|
case NotifType.CREATE_INVOICE:
|
||||||
await this.notificationsService.createInvoiceCreationNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
await this.notificationsService.createInvoiceCreationNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
||||||
break;
|
break;
|
||||||
case NotifType.BILL_INVOICE_REMINDER:
|
case NotifType.BILL_INVOICE_REMINDER:
|
||||||
await this.notificationsService.createBillInvoiceReminderNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
await this.notificationsService.createBillInvoiceReminderNotification(
|
||||||
break;
|
recipientId,
|
||||||
case NotifType.BILL_INVOICE:
|
data as IInvoiceNotificationData,
|
||||||
await this.notificationsService.createBillInvoiceNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
queryRunner,
|
||||||
break;
|
);
|
||||||
case NotifType.APPROVE_INVOICE:
|
break;
|
||||||
await this.notificationsService.createApprovedInvoiceNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
case NotifType.BILL_INVOICE:
|
||||||
break;
|
await this.notificationsService.createBillInvoiceNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
||||||
case NotifType.INVOICE_OVERDUE:
|
break;
|
||||||
await this.notificationsService.createInvoiceOverdueNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
case NotifType.APPROVE_INVOICE:
|
||||||
break;
|
await this.notificationsService.createApprovedInvoiceNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
||||||
case NotifType.RECURRING_INVOICE:
|
break;
|
||||||
await this.notificationsService.createRecurringInvoiceNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
case NotifType.INVOICE_OVERDUE:
|
||||||
break;
|
await this.notificationsService.createInvoiceOverdueNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
||||||
|
break;
|
||||||
|
case NotifType.RECURRING_INVOICE:
|
||||||
|
await this.notificationsService.createRecurringInvoiceNotification(recipientId, data as IInvoiceNotificationData, queryRunner);
|
||||||
|
break;
|
||||||
|
|
||||||
// Service Notifications
|
// Service Notifications
|
||||||
case NotifType.BLOCK_SERVICE:
|
case NotifType.BLOCK_SERVICE:
|
||||||
await this.notificationsService.createBlockServiceNotification(recipientId, data as ISubscriptionNotificationData, queryRunner);
|
await this.notificationsService.createBlockServiceNotification(recipientId, data as ISubscriptionNotificationData, queryRunner);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
// Payment Notifications
|
// Payment Notifications
|
||||||
case NotifType.PAYMENT_REMINDER:
|
case NotifType.PAYMENT_REMINDER:
|
||||||
await this.notificationsService.createPaymentReminderNotification(recipientId, data as IPaymentNotificationData, queryRunner);
|
await this.notificationsService.createPaymentReminderNotification(recipientId, data as IPaymentNotificationData, queryRunner);
|
||||||
break;
|
break;
|
||||||
case NotifType.PAYMENT_CANCELLATION:
|
case NotifType.PAYMENT_CANCELLATION:
|
||||||
await this.notificationsService.createPaymentCancellationNotification(recipientId, data as IPaymentNotificationData, queryRunner);
|
await this.notificationsService.createPaymentCancellationNotification(
|
||||||
break;
|
recipientId,
|
||||||
|
data as IPaymentNotificationData,
|
||||||
|
queryRunner,
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
this.logger.warn(`Unknown notification type: ${type}`);
|
this.logger.warn(`Unknown notification type: ${type}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
await queryRunner.commitTransaction();
|
||||||
|
clearInterval(heartbeat);
|
||||||
|
return true;
|
||||||
|
} catch (error) {
|
||||||
|
clearInterval(heartbeat);
|
||||||
|
throw error;
|
||||||
}
|
}
|
||||||
|
|
||||||
await queryRunner.commitTransaction();
|
|
||||||
return true;
|
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
this.logger.error(
|
this.logger.error(
|
||||||
`Failed to process notification: ${error instanceof Error ? error.message : "Unknown error"}`,
|
`Failed to process notification: ${error instanceof Error ? error.message : "Unknown error"}`,
|
||||||
|
|||||||
Reference in New Issue
Block a user