import { PrismaService } from '../src/prisma/prisma.service'; import { ReportsService } from '../src/reports/reports.service'; const ids = { tenant: 'it-report-tenant', application: 'it-report-app', channel: 'it-report-channel', batch: 'it-report-batch', successMessage: 'it-report-message-success', failedMessage: 'it-report-message-failed', }; async function main() { const prisma = new PrismaService(); const reports = new ReportsService(prisma); const queuedAt = new Date('2026-07-18T02:00:00.000Z'); try { await prisma.tenant.create({ data: { id: ids.tenant, name: '报表集成验证企业', code: 'IT-REPORT-TENANT' } }); await prisma.smsApplication.create({ data: { id: ids.application, tenantId: ids.tenant, name: '报表集成验证应用', cmppAccount: 'it-report-account', cmppEnterpriseCode: 'ITREPORT', secretHash: 'not-a-real-secret', } }); await prisma.smsChannel.create({ data: { id: ids.channel, code: 'IT-REPORT-CHANNEL', name: '报表集成验证通道', gatewayHost: '127.0.0.1', gatewayPort: 17890, account: 'it-report-upstream', passwordCipher: 'not-a-real-password', srcId: '10690000', unitPrice: 200n, } }); await prisma.smsBatchTask.create({ data: { id: ids.batch, tenantId: ids.tenant, applicationId: ids.application, taskNo: 'IT-REPORT-BATCH', sourceType: 'api', content: '报表集成验证', phoneTotal: 2, status: 'finished', createdAt: queuedAt, } }); const baseMessage = { tenantId: ids.tenant, batchTaskId: ids.batch, applicationId: ids.application, content: '报表集成验证', billingUnits: 1, unitPrice: 352n, amountCents: 352n, channelId: ids.channel, submittedAt: queuedAt, queuedAt, }; await prisma.smsMessageRecord.createMany({ data: [ { ...baseMessage, id: ids.successMessage, messageId: 'IT-REPORT-MSG-SUCCESS', phoneNumber: '13800000001', submitId: 'IT-REPORT-SUB-SUCCESS', gatewayMessageId: 'IT-REPORT-GW-SUCCESS', status: 'delivered', submitStatus: 'accepted', receiptStatus: 'delivered', receiptRawStatus: 'DELIVRD', deliveredAt: new Date(queuedAt.getTime() + 5_000) }, { ...baseMessage, id: ids.failedMessage, messageId: 'IT-REPORT-MSG-FAILED', phoneNumber: '13800000002', submitId: 'IT-REPORT-SUB-FAILED', gatewayMessageId: 'IT-REPORT-GW-FAILED', status: 'failed', submitStatus: 'accepted', receiptStatus: 'undelivered', receiptRawStatus: 'UNDELIV', deliveredAt: new Date(queuedAt.getTime() + 8_000) }, ] }); await prisma.smsSubmitRecord.createMany({ data: [ { id: 'it-report-submit-success', tenantId: ids.tenant, batchTaskId: ids.batch, messageRecordId: ids.successMessage, channelId: ids.channel, submitId: 'IT-REPORT-SUB-SUCCESS', gatewayMessageId: 'IT-REPORT-GW-SUCCESS', submitStatus: 'accepted', costUnitPrice: 200n, costAmountCents: 200n, submittedAt: queuedAt }, { id: 'it-report-submit-failed', tenantId: ids.tenant, batchTaskId: ids.batch, messageRecordId: ids.failedMessage, channelId: ids.channel, submitId: 'IT-REPORT-SUB-FAILED', gatewayMessageId: 'IT-REPORT-GW-FAILED', submitStatus: 'accepted', costUnitPrice: 200n, costAmountCents: 200n, submittedAt: queuedAt }, ] }); await prisma.smsReceiptRecord.createMany({ data: [ { id: 'it-report-receipt-success', receiptKey: 'it-report-receipt-key-success', tenantId: ids.tenant, batchTaskId: ids.batch, messageRecordId: ids.successMessage, channelId: ids.channel, messageId: 'IT-REPORT-MSG-SUCCESS', gatewayMessageId: 'IT-REPORT-GW-SUCCESS', receiptStatus: 'delivered', rawStatus: 'DELIVRD', deliveredAt: new Date(queuedAt.getTime() + 5_000) }, { id: 'it-report-receipt-failed', receiptKey: 'it-report-receipt-key-failed', tenantId: ids.tenant, batchTaskId: ids.batch, messageRecordId: ids.failedMessage, channelId: ids.channel, messageId: 'IT-REPORT-MSG-FAILED', gatewayMessageId: 'IT-REPORT-GW-FAILED', receiptStatus: 'undelivered', rawStatus: 'UNDELIV', deliveredAt: new Date(queuedAt.getTime() + 8_000) }, ] }); await prisma.smsBillingRecord.createMany({ data: [ { id: 'it-report-billing-success', tenantId: ids.tenant, applicationId: ids.application, taskId: ids.batch, messageId: 'IT-REPORT-MSG-SUCCESS', phoneNumber: '13800000001', contentLength: 8, billingUnits: 1, unitPrice: 352n, amountCents: 352n, billingStatus: 'charged', createdAt: queuedAt }, { id: 'it-report-billing-refunded', tenantId: ids.tenant, applicationId: ids.application, taskId: ids.batch, messageId: 'IT-REPORT-MSG-FAILED', phoneNumber: '13800000002', contentLength: 8, billingUnits: 1, unitPrice: 352n, amountCents: 352n, billingStatus: 'refunded', createdAt: queuedAt }, ] }); await reports.refreshRollingWindow(new Date('2026-07-20T05:00:00.000Z')); const [reconciliation, applicationProfit, channelProfit, applicationQuality, channelQuality] = await Promise.all([ prisma.dailyReconciliationReport.findUnique({ where: { reportDate_tenantId_applicationId: { reportDate: new Date('2026-07-18'), tenantId: ids.tenant, applicationId: ids.application } } }), prisma.dailyProfitReport.findUnique({ where: { reportDate_dimensionType_dimensionId: { reportDate: new Date('2026-07-18'), dimensionType: 'application', dimensionId: ids.application } } }), prisma.dailyProfitReport.findUnique({ where: { reportDate_dimensionType_dimensionId: { reportDate: new Date('2026-07-18'), dimensionType: 'channel', dimensionId: ids.channel } } }), prisma.dailyQualityReport.findUnique({ where: { reportDate_dimensionType_dimensionId: { reportDate: new Date('2026-07-18'), dimensionType: 'application', dimensionId: ids.application } } }), prisma.dailyQualityReport.findUnique({ where: { reportDate_dimensionType_dimensionId: { reportDate: new Date('2026-07-18'), dimensionType: 'channel', dimensionId: ids.channel } } }), ]); const evidence = JSON.parse(JSON.stringify({ reconciliation, applicationProfit, channelProfit, applicationQuality, channelQuality }, (_key, value) => typeof value === 'bigint' ? value.toString() : value)); const valid = reconciliation?.sentUnits === 2 && reconciliation.successUnits === 1 && reconciliation.failedUnits === 1 && applicationProfit?.revenueCents === 352n && applicationProfit.refundCents === 352n && applicationProfit.costCents === 400n && applicationProfit.profitCents === -48n && channelProfit?.successUnits === 1 && channelProfit.failedUnits === 1 && applicationQuality?.avgArrivalMs === 5_000 && channelQuality?.avgArrivalMs === 5_000; if (!valid) throw new Error(`report recalculation assertion failed: ${JSON.stringify(evidence)}`); console.log(JSON.stringify({ ok: true, evidence })); } finally { await prisma.dailyQualityReport.deleteMany({ where: { OR: [{ tenantId: ids.tenant }, { channelId: ids.channel }] } }); await prisma.dailyProfitReport.deleteMany({ where: { OR: [{ tenantId: ids.tenant }, { channelId: ids.channel }] } }); await prisma.dailyReconciliationReport.deleteMany({ where: { tenantId: ids.tenant } }); await prisma.smsBillingRecord.deleteMany({ where: { tenantId: ids.tenant } }); await prisma.smsReceiptRecord.deleteMany({ where: { tenantId: ids.tenant } }); await prisma.smsSubmitRecord.deleteMany({ where: { tenantId: ids.tenant } }); await prisma.smsMessageRecord.deleteMany({ where: { tenantId: ids.tenant } }); await prisma.smsBatchTask.deleteMany({ where: { tenantId: ids.tenant } }); await prisma.smsChannel.deleteMany({ where: { id: ids.channel } }); await prisma.smsApplication.deleteMany({ where: { id: ids.application } }); await prisma.tenant.deleteMany({ where: { id: ids.tenant } }); await prisma.$disconnect(); } } void main().catch((error) => { console.error(error); process.exitCode = 1; });