This commit is contained in:
2025-12-02 23:04:09 +03:30
parent f193266235
commit 8298e2fb3e
@@ -39,21 +39,22 @@ export class PaymentsService {
throw new NotFoundException('Payment method not found');
}
if (paymentMethod.method !== PaymentMethodEnum.Online && !paymentMethod.merchantId) {
throw new BadRequestException('Merchant ID is not provided');
if (paymentMethod.method === PaymentMethodEnum.Online && !paymentMethod.merchantId) {
throw new BadRequestException('Merchant ID is required for online payments');
}
// Create payment record and save authority
const restaurantDomain = paymentMethod.restaurant.domain;
const gateway = paymentMethod.gateway as PaymentGatewayEnum | null;
const { authority } = await this.createPayment(restaurantDomain, {
amount,
orderId,
paymentMethod: paymentMethod.method,
merchantId: paymentMethod.merchantId ?? null,
gateway: paymentMethod.gateway as PaymentGatewayEnum | null,
gateway,
});
const paymentUrl = this.zarinpalPaymentUrl(paymentMethod.gateway, authority);
const paymentUrl = this.zarinpalPaymentUrl(gateway, authority);
return { paymentUrl };
}
@@ -83,34 +84,56 @@ export class PaymentsService {
domain: string,
gateway: PaymentGatewayEnum | null | undefined,
): Promise<{ authority: string | null }> {
if (paymentMethod === PaymentMethodEnum.Online && merchantId) {
const callbackUrl = `${domain}/payments/callback`;
if (gateway === PaymentGatewayEnum.ZarinPal) {
try {
const gatewayResponse = await this.requestToZarinPalGateway({
amount,
merchantId,
description: `Payment for order #${orderId}`,
callbackUrl,
metadata: {
orderId,
},
});
// Check gateway response code (typically 100 means success for Iranian gateways)
if (gatewayResponse.code !== 100 && gatewayResponse.code !== 0) {
throw new BadRequestException(`Payment gateway error: ${gatewayResponse.message || 'Unknown error'}`);
}
// For non-online payment methods, no gateway request is needed
if (paymentMethod !== PaymentMethodEnum.Online) {
return { authority: null };
}
if (!gatewayResponse.authority) {
throw new BadRequestException('Payment gateway did not return an authority token');
}
} catch (error) {
const errorMessage = error instanceof Error ? error.message : 'Unknown error';
throw new BadRequestException(`Failed to connect to payment gateway: ${errorMessage}`);
// Online payments require merchantId and gateway
if (!merchantId) {
throw new BadRequestException('Merchant ID is required for online payments');
}
if (!gateway) {
throw new BadRequestException('Payment gateway is required for online payments');
}
const callbackUrl = `${domain}/payments/callback`;
// Handle ZarinPal gateway
if (gateway === PaymentGatewayEnum.ZarinPal) {
try {
const gatewayResponse = await this.requestToZarinPalGateway({
amount,
merchantId,
description: `Payment for order #${orderId}`,
callbackUrl,
metadata: {
orderId,
},
});
// Check gateway response code (typically 100 means success for Iranian gateways)
if (gatewayResponse.code !== 100 && gatewayResponse.code !== 0) {
throw new BadRequestException(`Payment gateway error: ${gatewayResponse.message || 'Unknown error'}`);
}
if (!gatewayResponse.authority) {
throw new BadRequestException('Payment gateway did not return an authority token');
}
return { authority: gatewayResponse.authority };
} catch (error) {
if (error instanceof BadRequestException) {
throw error;
}
const errorMessage = error instanceof Error ? error.message : 'Unknown error';
throw new BadRequestException(`Failed to connect to payment gateway: ${errorMessage}`);
}
}
return { authority: null };
// If gateway is not supported, throw an error
throw new BadRequestException(`Unsupported payment gateway: ${String(gateway)}`);
}
private async requestToZarinPalGateway(requestPayment: IPaymentRequest): Promise<IPaymentResponse> {