feat: add per-org SMS wallet with adm panel and header credit
Bill all platform SMS (including OTP), allow negative balance with manual/auto cutoffs, and support own-panel bypass without wallet debit.
This commit is contained in:
@@ -1,14 +1,13 @@
|
||||
import { Module } from '@nestjs/common';
|
||||
import { AuthModule } from '../auth/auth.module';
|
||||
import { NotificationsModule } from '../notifications/notifications.module';
|
||||
import { SmsService } from '../common/sms.service';
|
||||
import { MessageAutomationsController } from './message-automations.controller';
|
||||
import { MessageAutomationsService } from './message-automations.service';
|
||||
|
||||
@Module({
|
||||
imports: [AuthModule, NotificationsModule],
|
||||
controllers: [MessageAutomationsController],
|
||||
providers: [MessageAutomationsService, SmsService],
|
||||
providers: [MessageAutomationsService],
|
||||
exports: [MessageAutomationsService],
|
||||
})
|
||||
export class MessageAutomationsModule {}
|
||||
|
||||
@@ -13,7 +13,7 @@ import type {
|
||||
import { Prisma } from '@prisma/client';
|
||||
import { PrismaService } from '../prisma/prisma.service';
|
||||
import { NotificationsService } from '../notifications/notifications.service';
|
||||
import { SmsService } from '../common/sms.service';
|
||||
import { SmsGatewayService } from '../sms-billing/sms-gateway.service';
|
||||
import { dateToJalali, jalaliMonthName } from '../common/jalali';
|
||||
import { OutboundSmsLogService } from '../outbound-sms/outbound-sms-log.service';
|
||||
import {
|
||||
@@ -47,7 +47,7 @@ export class MessageAutomationsService {
|
||||
constructor(
|
||||
private readonly prisma: PrismaService,
|
||||
private readonly notifications: NotificationsService,
|
||||
private readonly sms: SmsService,
|
||||
private readonly sms: SmsGatewayService,
|
||||
private readonly outboundSms: OutboundSmsLogService,
|
||||
) {}
|
||||
|
||||
@@ -397,7 +397,10 @@ export class MessageAutomationsService {
|
||||
},
|
||||
select: { mobile: true },
|
||||
});
|
||||
await this.sendSms(user?.mobile, smsText);
|
||||
await this.sendSms(user?.mobile, smsText, {
|
||||
organizationId: job.organizationId,
|
||||
ruleId: job.ruleId || job.rule.id || '',
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -413,7 +416,7 @@ export class MessageAutomationsService {
|
||||
private async sendSms(
|
||||
mobile: string | null | undefined,
|
||||
text: string,
|
||||
log?: {
|
||||
log: {
|
||||
organizationId: string;
|
||||
personId?: string | null;
|
||||
ruleId: string;
|
||||
@@ -423,12 +426,13 @@ export class MessageAutomationsService {
|
||||
this.logger.warn('Message automation SMS skipped: no mobile');
|
||||
return;
|
||||
}
|
||||
if (!this.sms.isConfigured()) {
|
||||
this.logger.warn('Message automation SMS skipped: SMS not configured');
|
||||
return;
|
||||
}
|
||||
const result = await this.sms.sendSmsDetailed(mobile, text);
|
||||
if (log?.personId) {
|
||||
const result = await this.sms.send({
|
||||
organizationId: log.organizationId,
|
||||
phone: mobile,
|
||||
text,
|
||||
source: 'automation',
|
||||
});
|
||||
if (log.personId) {
|
||||
await this.outboundSms.record({
|
||||
organizationId: log.organizationId,
|
||||
personId: log.personId,
|
||||
|
||||
Reference in New Issue
Block a user