import { Injectable, Logger } from '@nestjs/common'; import { Cron } from '@nestjs/schedule'; import { PrismaService } from '../prisma/prisma.service'; import { PlatformAdminAlertService } from './platform-admin-alert.service'; @Injectable() export class BillingExpiryService { private readonly logger = new Logger(BillingExpiryService.name); constructor( private readonly prisma: PrismaService, private readonly alerts: PlatformAdminAlertService, ) {} @Cron('15 * * * *', { timeZone: 'Asia/Tehran' }) async handleHourly(): Promise { await this.notifyEnded(); } async notifyEnded(): Promise { const rows = await this.prisma.billingAccount.findMany({ where: { expiryNotifiedAt: null, planCode: { not: 'lifetime' }, status: { not: 'suspended' }, expiresAt: { lte: new Date() }, }, select: { id: true }, take: 100, }); for (const row of rows) { try { await this.alerts.notifySubscriptionEnded(row.id); } catch (error) { this.logger.warn( `expiry notify failed ${row.id}: ${error instanceof Error ? error.message : 'unknown'}`, ); } } if (rows.length) this.logger.log(`subscription expiry checked: ${rows.length}`); return rows.length; } }