### Create VNPAY Options Example Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md An example of a service implementing `VnpayModuleOptionsFactory` to provide VNPAY configuration from environment variables. ```typescript import { Injectable } from '@nestjs/common'; import { ConfigService } from '@nestjs/config'; import { VnpayModuleOptionsFactory, VnpayModuleOptions } from 'nestjs-vnpay'; @Injectable() export class VnpayConfigService implements VnpayModuleOptionsFactory { constructor(private configService: ConfigService) {} createVnpayOptions(): VnpayModuleOptions { return { tmnCode: this.configService.get('VNPAY_TMN_CODE'), secureSecret: this.configService.get('VNPAY_SECURE_SECRET'), }; } } ``` -------------------------------- ### Install nestjs-vnpay and vnpay Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/00-START-HERE.md Install the necessary packages for integrating VNPay with NestJS. ```bash npm install nestjs-vnpay vnpay ``` -------------------------------- ### Complete NestJS VNPAY Controller Example Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md This snippet shows a full controller implementation for handling VNPAY payments. It includes endpoints for creating payment URLs, processing return callbacks, handling IPN notifications, querying transaction status, and initiating refunds. Ensure you have the `nestjs-vnpay` package installed and configured. ```typescript import { Controller, Post, Get, Query, Body, } from '@nestjs/common'; import { VnpayService } from 'nestjs-vnpay'; @Controller('payment') export class PaymentController { constructor(private vnpayService: VnpayService) {} // Endpoint để tạo URL thanh toán @Post('create') createPayment(@Body() body: { amount: number; orderId: string }) { const paymentUrl = this.vnpayService.buildPaymentUrl({ amount: body.amount, orderId: body.orderId, orderInfo: 'Thanh toán hóa đơn', returnUrl: 'https://example.com/payment/return', ipnUrl: 'https://example.com/payment/ipn', locale: 'vi', }); return { success: true, paymentUrl }; } // Return URL callback từ VNPay @Get('return') async handleReturn(@Query() query: any) { const verified = await this.vnpayService.verifyReturnUrl(query); if (verified.isValid && verified.isSuccess) { return { success: true, message: 'Thanh toán thành công', orderId: verified.data.orderId, }; } return { success: false, message: 'Thanh toán thất bại' }; } // IPN callback từ VNPay (webhook) @Post('ipn') async handleIpn(@Body() body: any) { const verified = await this.vnpayService.verifyIpnCall(body); if (!verified.isValid) { return { RspCode: '97', Message: 'Invalid' }; } // Kiểm tra đơn hàng const order = await this.getOrder(verified.data.orderId); if (!order || order.amount !== verified.data.amount) { return { RspCode: '04', Message: 'Amount mismatch' }; } // Cập nhật trạng thái đơn hàng if (verified.data.isSuccess) { await this.updateOrderStatus(order.id, 'PAID'); } return { RspCode: '00', Message: 'Success' }; } // Query transaction status @Post('query') async queryTransaction(@Body() body: { orderId: string; transactionDate: number }) { const result = await this.vnpayService.queryDr({ orderId: body.orderId, transactionDate: body.transactionDate, }); return { success: true, data: result }; } // Refund transaction @Post('refund') async refundTransaction(@Body() body: { orderId: string; amount: number; transactionDate: number }) { try { const result = await this.vnpayService.refund({ orderId: body.orderId, amount: body.amount, transactionDate: body.transactionDate, }); return { success: true, data: result }; } catch (error) { return { success: false, message: error.message }; } } private async getOrder(orderId: string) { // Lấy đơn hàng từ DB return null; } private async updateOrderStatus(orderId: string, status: string) { // Cập nhật trạng thái đơn hàng } } ``` -------------------------------- ### Example Usage of generateQr Method Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Demonstrates how to call the `generateQr` method with payment details and an optional logger function. Ensure all required fields like `amount`, `orderId`, `orderInfo`, `returnUrl`, and `ipnUrl` are provided. ```typescript const result = await vnpayService.generateQr( { amount: 100000, orderId: '12345', orderInfo: 'Thanh toán QR', returnUrl: 'https://example.com/return', ipnUrl: 'https://example.com/ipn', }, { loggerFn: (data) => console.log(data), } ); ``` -------------------------------- ### Build Payment URL with Logger Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Example of using `buildPaymentUrl` with additional options, including a custom logger function to log data during URL construction. ```typescript vnpayService.buildPaymentUrl( { amount: 100000, orderId: '12345', orderInfo: 'Thanh toán hóa đơn', returnUrl: 'https://example.com/return', ipnUrl: 'https://example.com/ipn', }, { loggerFn: (data) => console.log(data), } ); ``` -------------------------------- ### Asynchronous Configuration (RegisterAsync) Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/00-START-HERE.md Use this method when configuration needs to be loaded asynchronously, for example, from environment variables or a database using ConfigService. ```typescript VnpayModule.registerAsync({ useFactory, inject: [ConfigService] }) ``` -------------------------------- ### Use VnpayService to Create Payment URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/00-START-HERE.md Inject the VnpayService into your payment service to build payment URLs. This example demonstrates creating a payment URL for a given amount and order ID, including essential details like order info, return URL, and IPN URL. ```typescript import { Injectable } from '@nestjs/common'; import { VnpayService } from 'nestjs-vnpay'; @Injectable() export class PaymentService { constructor(private vnpayService: VnpayService) {} createPayment(amount: number, orderId: string) { return this.vnpayService.buildPaymentUrl({ amount, orderId, orderInfo: 'Thanh toán đơn hàng', returnUrl: 'https://example.com/return', ipnUrl: 'https://example.com/ipn', }); } } ``` -------------------------------- ### Setup Alerts for Verification Failures Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/best-practices.md Implement alerts for critical events like payment verification failures. This snippet shows how to send an error alert using an alerting service. ```typescript // Ví dụ: Alert khi có lỗi xác thực if (!verified.isValid) { await this.alertingService.sendAlert({ level: 'ERROR', message: 'Payment verification failed', details: { query, timestamp: new Date() }, }); } ``` -------------------------------- ### VnpayModuleAsyncOptions Interface Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Defines the configuration options for asynchronous setup of the VnpayModule. It supports various strategies for providing configuration, including factory functions and existing providers. ```typescript export interface VnpayModuleAsyncOptions extends Pick { useExisting?: Type; useClass?: Type; useFactory?: (...args: any[]) => Promise | VnpayModuleOptions; inject?: any[]; extraProviders?: Provider[]; } ``` -------------------------------- ### Get Bank List Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Retrieves a list of supported banks from the VNPAY service. ```APIDOC ## Get Bank List ### Description Retrieves a list of supported banks from the VNPAY service. ### Method ``` POST ``` ### Endpoint ``` /v1/payment/get_bank_list ``` ### Parameters #### Query Parameters - **vnp_version** (string) - Required - Version of the API - **vnp_command** (string) - Required - Command to execute, e.g., `get_bank_list` - **vnp_tmncode** (string) - Required - Merchant code - **vnp_locale** (string) - Optional - Language of the response (e.g., `vn`, `en`) - **vnp_hash** (string) - Required - Hashed request string ### Response #### Success Response (200) - **data** (array) - List of bank objects, each containing `bankCode` and `bankName`. ### Response Example ```json { "data": [ { "bankCode": "NCB", "bankName": "Ngân hàng TMCP Quốc Dân" } ] } ``` ``` -------------------------------- ### Query Transaction Result using VNPAY Service Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/api-reference/vnpay-service.md This example demonstrates how to use the `queryDr` method from the `VnpayService` to query the payment status of a transaction. It's useful for verifying transaction outcomes or handling special cases. ```typescript import { Controller, Post, Body } from '@nestjs/common'; import { VnpayService } from 'nestjs-vnpay'; interface QueryPaymentDto { orderId: string; transactionDate: number; // YYYYMMDD format } @Controller('payment') export class PaymentController { constructor(private vnpayService: VnpayService) {} @Post('query-transaction') async queryTransaction(@Body() dto: QueryPaymentDto) { const result = await this.vnpayService.queryDr({ orderId: dto.orderId, transactionDate: dto.transactionDate, }); return { success: result.isVerified, data: result, }; } } ``` -------------------------------- ### Get Bank List Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Call this method to retrieve a list of supported banks from VNPAY. ```typescript const banks = await this.vnpayService.getBankList(); console.log(banks); ``` -------------------------------- ### Cache VNPAY Bank List in NestJS Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/troubleshooting.md Improves performance by caching the bank list for 24 hours to avoid frequent API calls. This example demonstrates how to implement a cache within a NestJS service. ```typescript // ✅ Đúng - Cache 24 giờ @Injectable() export class PaymentService { private bankListCache: Bank[] | null = null; private cacheExpiry = 0; async getBankList(): Promise { if (this.bankListCache && Date.now() < this.cacheExpiry) { return this.bankListCache; } this.bankListCache = await this.vnpayService.getBankList(); this.cacheExpiry = Date.now() + 24 * 60 * 60 * 1000; // 24 giờ return this.bankListCache; } } ``` -------------------------------- ### Create Order on Server Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/payment-flows.md This snippet demonstrates how to create a new order record in the database with a pending status before initiating a payment. ```typescript @Post('create-order') async createOrder(@Body() body: { amount: number; description: string }) { // Lưu đơn hàng vào database const order = await this.orderService.create({ amount: body.amount, description: body.description, status: 'PENDING', // Chưa thanh toán orderId: `ORDER-${Date.now()}`, }); return { success: true, orderId: order.orderId, amount: order.amount, }; } ``` -------------------------------- ### Configure VNPAY Module for Sandbox Testing Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/best-practices.md Demonstrates how to register the VnpayModule with specific configuration for testing in a sandbox environment. Set `testMode` to true to enable sandbox URLs and logging. ```typescript // Use sandbox URL khi test const testConfig = { tmnCode: 'SANDBOX_TMN_CODE', secureSecret: 'SANDBOX_SECRET', testMode: true, // Sử dụng sandbox enableLog: true, }; const module = await Test.createTestingModule({ imports: [VnpayModule.register(testConfig)], // ... }).compile(); ``` -------------------------------- ### Mock VnpayService for PaymentService Testing Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/best-practices.md Sets up a mock VnpayService to isolate and test the PaymentService logic. This is useful for verifying payment URL building and return URL verification without external dependencies. ```typescript import { Test, TestingModule } from '@nestjs/testing'; import { PaymentService } from './payment.service'; // Assuming PaymentService is in the same directory import { VnpayService } from './vnpay.service'; // Assuming VnpayService is in the same directory describe('PaymentService', () => { let service: PaymentService; let vnpayService: VnpayService; beforeEach(async () => { const module: TestingModule = await Test.createTestingModule({ providers: [ PaymentService, { provide: VnpayService, useValue: { buildPaymentUrl: jest.fn().mockReturnValue('https://payment.url'), verifyReturnUrl: jest.fn().mockResolvedValue({ isValid: true, isSuccess: true, data: { orderId: '123', amount: 100000 }, }), }, }, ], }).compile(); service = module.get(PaymentService); vnpayService = module.get(VnpayService); }); it('should build payment URL', async () => { const result = service.buildPaymentUrl({ amount: 100000, orderId: '123', }); expect(result).toBe('https://payment.url'); expect(vnpayService.buildPaymentUrl).toHaveBeenCalled(); }); it('should verify return URL', async () => { const result = await service.verifyPaymentReturn({ vnp_Amount: '100000' }); expect(result.isValid).toBe(true); expect(vnpayService.verifyReturnUrl).toHaveBeenCalled(); }); }); ``` -------------------------------- ### Configure VNPAY Environment Variables Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/00-START-HERE.md Set up your VNPAY merchant code and secure secret in your .env file. Never hardcode these secrets. ```env VNPAY_TMN_CODE=your_code_here VNPAY_SECURE_SECRET=your_secret_here ``` -------------------------------- ### Generate QR Code Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Generates a QR code for payment initiation. ```APIDOC ## Generate QR Code ### Description Generates a QR code that can be scanned by a mobile payment application to initiate a transaction. ### Method ``` POST ``` ### Endpoint ``` /v1/payment/generate_qr ``` ### Parameters #### Request Body - **amount** (number) - Required - The transaction amount in VND. - **orderId** (string) - Required - Unique identifier for the order. - **orderInfo** (string) - Required - Description of the order. - **returnUrl** (string) - Required - The URL to redirect the user to after payment completion. - **ipnUrl** (string) - Required - The URL for VNPAY to send Instant Payment Notification (IPN) callbacks. ### Request Example ```json { "amount": 100000, "orderId": "ORDER123", "orderInfo": "Thanh toán QR", "returnUrl": "https://example.com/payment/return", "ipnUrl": "https://example.com/payment/ipn" } ``` ### Response #### Success Response (200) - **data** (string) - The QR code data, typically a string that can be rendered as a QR code image. ``` -------------------------------- ### VnpayService Methods Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/MANIFEST.md Reference for the VNPayService class, including its instance getter and seven core methods for interacting with the VNPAY API. ```APIDOC ## VnpayService API Reference ### Class Overview Provides an interface to interact with VNPAY services. ### Getter `instance` Access the singleton instance of the VnpayService. ### Methods #### `getBankList()` - **Description**: Retrieves a list of supported banks. - **Parameters**: None - **Return Type**: `Promise` (Details of the bank list structure are not provided in the source) #### `buildPaymentUrl(options: BuildPaymentUrlOptions)` - **Description**: Constructs a payment URL for VNPAY. - **Parameters**: - **options** (BuildPaymentUrlOptions) - Required - Options for building the payment URL. - **Return Type**: `Promise` #### `generateQr(options: GenerateQrOptions)` - **Description**: Generates a QR code for payment. - **Parameters**: - **options** (GenerateQrOptions) - Required - Options for generating the QR code. - **Return Type**: `Promise` (Details of the QR code structure are not provided in the source) #### `verifyReturnUrl(options: VerifyReturnUrlOptions)` - **Description**: Verifies the return URL after a payment attempt. - **Parameters**: - **options** (VerifyReturnUrlOptions) - Required - Options for verifying the return URL. - **Return Type**: `Promise` (Details of the verification result structure are not provided in the source) #### `verifyIpnCall(options: VerifyIpnCallOptions)` - **Description**: Verifies an IPN (Instant Payment Notification) call. - **Parameters**: - **options** (VerifyIpnCallOptions) - Required - Options for verifying the IPN call. - **Return Type**: `Promise` (Details of the verification result structure are not provided in the source) #### `queryDr(options: QueryDrOptions)` - **Description**: Queries the status of a transaction (Debit/Credit). - **Parameters**: - **options** (QueryDrOptions) - Required - Options for querying the transaction status. - **Return Type**: `Promise` (Details of the query result structure are not provided in the source) #### `refund(options: RefundOptions)` - **Description**: Processes a refund for a transaction. - **Parameters**: - **options** (RefundOptions) - Required - Options for processing the refund. - **Return Type**: `Promise` (Details of the refund result structure are not provided in the source) ### Examples Examples for each method are available in the source documentation. ``` -------------------------------- ### Implement VnpayModuleOptionsFactory Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Implement this interface to create dynamic VNPAY configurations. Use with `registerAsync()`'s `useClass` or `useExisting`. ```typescript export interface VnpayModuleOptionsFactory { createVnpayOptions(): Promise | VnpayModuleOptions; } ``` -------------------------------- ### Build Payment URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Constructs the VNPAY payment URL with specified order details. Ensure `returnUrl` and `ipnUrl` are correctly configured. ```typescript const paymentUrl = this.vnpayService.buildPaymentUrl({ amount: 100000, // VNĐ orderId: 'ORDER123', orderInfo: 'Thanh toán đơn hàng', returnUrl: 'https://example.com/payment/return', ipnUrl: 'https://example.com/payment/ipn', locale: 'vi', bankCode: undefined, // Tùy chọn }); ``` -------------------------------- ### Build Payment URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Constructs a payment URL for initiating a transaction with VNPAY. ```APIDOC ## Build Payment URL ### Description Constructs a payment URL for initiating a transaction with VNPAY. This URL can be used to redirect users to the VNPAY payment gateway. ### Method ``` POST ``` ### Endpoint ``` /v1/payment/create_payment ``` ### Parameters #### Request Body - **amount** (number) - Required - The transaction amount in VND. - **orderId** (string) - Required - Unique identifier for the order. - **orderInfo** (string) - Required - Description of the order. - **returnUrl** (string) - Required - The URL to redirect the user to after payment completion. - **ipnUrl** (string) - Required - The URL for VNPAY to send Instant Payment Notification (IPN) callbacks. - **locale** (string) - Optional - Language of the payment page (e.g., `vn`, `en`). Defaults to `vn`. - **bankCode** (string) - Optional - Specific bank code to pre-select for payment. ### Request Example ```json { "amount": 100000, "orderId": "ORDER123", "orderInfo": "Thanh toán đơn hàng", "returnUrl": "https://example.com/payment/return", "ipnUrl": "https://example.com/payment/ipn", "locale": "vi", "bankCode": null } ``` ### Response #### Success Response (200) - **paymentUrl** (string) - The generated URL for the VNPAY payment gateway. ``` -------------------------------- ### GenerateQrOptions Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Type for the options of the `generateQr()` method. It allows passing options when creating a payment QR code. ```APIDOC ## GenerateQrOptions Type for the options of the `generateQr()` method. ### Description This type allows passing options when creating a payment QR code. ### Usage ```typescript const result = await vnpayService.generateQr( { amount: 100000, orderId: '12345', orderInfo: 'Thanh toán QR', returnUrl: 'https://example.com/return', ipnUrl: 'https://example.com/ipn', }, { loggerFn: (data) => console.log(data), } ); ``` ``` -------------------------------- ### Generate QR Code Options Type Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Defines the options for the `generateQr()` method. Use this to pass custom configurations when creating a payment QR code. ```typescript export type GenerateQrOptions = VnpayGenerateQrResponseOptions; ``` -------------------------------- ### Initialize VnpayModule in AppModule Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/00-START-HERE.md Register the VnpayModule in your application's root module with your VNPay credentials and configuration. Ensure you replace 'YOUR_CODE' and 'YOUR_SECRET' with your actual values. ```typescript import { Module } from '@nestjs/common'; import { VnpayModule } from 'nestjs-vnpay'; @Module({ imports: [ VnpayModule.register({ tmnCode: 'YOUR_CODE', secureSecret: 'YOUR_SECRET', testMode: true, }) ], }) export class AppModule {} ``` -------------------------------- ### Static Configuration (Register) Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/00-START-HERE.md Use this method when the configuration (tmnCode, secureSecret) is known at build time. ```typescript VnpayModule.register({ tmnCode, secureSecret }) ``` -------------------------------- ### NestJS VNPAY Compilation Cycle Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/project-structure.md Illustrates the build process where TypeScript source files in 'src/' are compiled into JavaScript and .d.ts files in 'lib/', followed by publishing to npm. ```tree src/ (TypeScript) │ ├─ tsc (TypeScript Compiler) │ ▼ lib/ (JavaScript + .d.ts) │ ├─ lib/index.js ├─ lib/index.d.ts ├─ lib/vnpay.module.js ├─ lib/vnpay.module.d.ts ├─ lib/vnpay.service.js ├─ lib/vnpay.service.d.ts └─ ... (các files khác) │ ├─ npm publish │ ▼ npm (Published Package) │ ├─ Consumer projects │ └─ import { VnpayModule } from 'nestjs-vnpay' ``` -------------------------------- ### Import VNPay Class Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Import the main VNPay class from the 'vnpay' package. This class serves as the primary wrapper for interacting with the VNPay API. ```typescript import { VNPay } from 'vnpay'; ``` -------------------------------- ### BuildPaymentUrl Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Data for building a payment URL. Used as a parameter for `buildPaymentUrl()` and `generateQr()`. ```APIDOC ## BuildPaymentUrl Data for building a payment URL. ### Interface ```typescript interface BuildPaymentUrl { amount: number; orderId: string; orderInfo: string; returnUrl: string; ipnUrl: string; locale?: 'en' | 'vi'; bankCode?: string; // ... other fields } ``` ### Usage Parameter for `buildPaymentUrl()` and `generateQr()` ``` -------------------------------- ### GenerateQrResponse Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Response when generating a QR code. Returned from `generateQr()`. ```APIDOC ## GenerateQrResponse Response when generating a QR code. ### Interface ```typescript interface GenerateQrResponse { code: string; message: string; data: string; } ``` ### Usage Returned from `generateQr()` ``` -------------------------------- ### Configure VNPAY Module Statically Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/README.md Registers the VNPAY module with static configuration values. Ensure that 'YOUR_TMN_CODE' and 'YOUR_SECURE_SECRET' are replaced with your actual VNPAY credentials. ```typescript VnpayModule.register({ tmnCode: 'YOUR_TMN_CODE', secureSecret: 'YOUR_SECURE_SECRET', vnpayHost: 'https://sandbox.vnpayment.vn', testMode: true, hashAlgorithm: 'SHA512', enableLog: true, }) ``` -------------------------------- ### VnpayModule Registration Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/MANIFEST.md Details on how to register the VnpayModule using either `register` or `registerAsync` methods. ```APIDOC ## VnpayModule Registration ### `register(options: VnpayModuleOptions)` - **Description**: Registers the VnpayModule with provided configuration options. - **Parameters**: - **options** (VnpayModuleOptions) - Required - Detailed configuration for the VNPAY module. ### `registerAsync(options: VnpayModuleAsyncOptions)` - **Description**: Registers the VnpayModule asynchronously, allowing for dynamic configuration. - **Parameters**: - **options** (VnpayModuleAsyncOptions) - Required - Asynchronous configuration options, potentially including a `useFactory` or `useClass`. ### Examples - **useFactory**: Example demonstrating how to use the `useFactory` provider for asynchronous registration. - **useClass**: Example demonstrating how to use the `useClass` provider for asynchronous registration. ``` -------------------------------- ### Verify Return URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Verifies the parameters received from a return URL callback after a payment attempt. ```APIDOC ## Verify Return URL ### Description Verifies the parameters received from a return URL callback after a payment attempt. This helps confirm the payment status and details. ### Method ``` GET ``` ### Endpoint ``` /payment/return ``` ### Parameters #### Query Parameters - **queryParams** (object) - Required - An object containing all query parameters received from the return URL. - **vnp_amount** (string) - The transaction amount. - **vnp_bankcode** (string) - The bank code used for the transaction. - **vnp_orderinfo** (string) - Order information. - **vnp_transactionstatus** (string) - The status of the transaction. - **vnp_responsecode** (string) - The response code from VNPAY. - **vnp_transactionno** (string) - The VNPAY transaction number. - **vnp_tmncode** (string) - Merchant code. - **vnp_paydate** (string) - Payment date. - **vnp_createDate** (string) - Creation date. - **vnp_checksum** (string) - Checksum for verification. ### Response #### Success Response (200) - **isValid** (boolean) - Indicates if the verification was successful. - **isSuccess** (boolean) - Indicates if the payment was successful. - **data** (object) - Contains transaction details if `isValid` and `isSuccess` are true. ``` -------------------------------- ### Build Payment URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/README.md Generates a payment URL for redirecting users to the VNPAY payment gateway. Requires amount, order details, return and IPN URLs, and locale. ```APIDOC ## Build Payment URL ### Description Generates a payment URL for redirecting users to the VNPAY payment gateway. ### Method `vnpayService.buildPaymentUrl(options)` ### Parameters #### Options Object - **amount** (number) - Required - The payment amount in VND. - **orderId** (string) - Required - Unique identifier for the order. - **orderInfo** (string) - Required - Description of the order. - **returnUrl** (string) - Required - The URL to redirect to after payment completion. - **ipnUrl** (string) - Required - The URL for VNPAY to send Instant Payment Notification (IPN) callbacks. - **locale** (string) - Optional - The language for the payment page (e.g., 'vi', 'en'). ### Request Example ```typescript const paymentUrl = vnpayService.buildPaymentUrl({ amount: 100000, orderId: 'ORDER123', orderInfo: 'Thanh toán hóa đơn', returnUrl: 'https://example.com/payment/return', ipnUrl: 'https://example.com/payment/ipn', locale: 'vi', }); ``` ``` -------------------------------- ### ReturnQueryFromVNPay Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Data returned from VNPay (query parameters or body). Used as a parameter for `verifyReturnUrl()` and `verifyIpnCall()`. ```APIDOC ## ReturnQueryFromVNPay Data returned from VNPay (query parameters or body). ### Interface ```typescript interface ReturnQueryFromVNPay { // Contains all query parameters returned from VNPay // [key: string]: any } ``` ### Usage Parameter for `verifyReturnUrl()` and `verifyIpnCall()` ``` -------------------------------- ### BuildPaymentUrlOptions Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Type for the options of the `buildPaymentUrl()` method. This type allows passing additional options when building the payment URL, such as a logger callback. ```APIDOC ## Type: BuildPaymentUrlOptions ### Description Type for the options of the `buildPaymentUrl()` method. This type allows passing additional options when building the payment URL, such as a logger callback. ### Usage Example ```typescript vnpayService.buildPaymentUrl( { amount: 100000, orderId: '12345', orderInfo: 'Thanh toán hóa đơn', returnUrl: 'https://example.com/return', ipnUrl: 'https://example.com/ipn', }, { loggerFn: (data) => console.log(data), } ); ``` ``` -------------------------------- ### BuildPaymentUrl Interface Definition Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Defines the data structure required to construct a payment URL. This interface is used as a parameter for the `buildPaymentUrl()` and `generateQr()` methods. Optional fields like `locale`, `bankCode`, and others can be included. ```typescript interface BuildPaymentUrl { amount: number; orderId: string; orderInfo: string; returnUrl: string; ipnUrl: string; locale?: 'en' | 'vi'; bankCode?: string; // ... các trường khác } ``` -------------------------------- ### Configure VNPAY Module Asynchronously Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/README.md Registers the VNPAY module asynchronously, allowing configuration values to be injected from other modules, such as a ConfigModule. This is useful for managing sensitive credentials securely. ```typescript VnpayModule.registerAsync({ imports: [ConfigModule], useFactory: async (configService: ConfigService) => ({ tmnCode: configService.get('VNPAY_TMN_CODE'), secureSecret: configService.get('VNPAY_SECURE_SECRET'), }), inject: [ConfigService], }) ``` -------------------------------- ### VnpayModuleOptionsFactory Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Interface for implementing dynamic VNPay configuration creation. Classes implementing this interface are used with `useClass` or `useExisting` in `registerAsync()`. ```APIDOC ## Interface: VnpayModuleOptionsFactory ### Description Interface to implement dynamic VNPay configuration creation. Classes implementing this interface are used with `useClass` or `useExisting` in `registerAsync()`. ### Methods #### `createVnpayOptions()` - **Returns**: `Promise | VnpayModuleOptions` - **Description**: Creates and returns the VNPay configuration. ### Example Usage ```typescript import { Injectable } from '@nestjs/common'; import { ConfigService } from '@nestjs/config'; import { VnpayModuleOptionsFactory, VnpayModuleOptions } from 'nestjs-vnpay'; @Injectable() export class VnpayConfigService implements VnpayModuleOptionsFactory { constructor(private configService: ConfigService) {} createVnpayOptions(): VnpayModuleOptions { return { tmnCode: this.configService.get('VNPAY_TMN_CODE'), secureSecret: this.configService.get('VNPAY_SECURE_SECRET'), }; } } ``` ``` -------------------------------- ### Batch Query Transactions Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/best-practices.md Efficiently query multiple transactions in parallel using Promise.all. This is useful when you need to check the status of several transactions simultaneously. ```typescript // Nếu cần query nhiều giao dịch async queryMultipleTransactions(transactionIds: string[]) { const results = await Promise.all( transactionIds.map(id => this.vnpayService.queryDr({ orderId: id, transactionDate: this.getTodayDate(), }).catch(error => ({ orderId: id, error: error.message, })) ) ); return results; } ``` -------------------------------- ### Build VNPAY Payment URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/README.md Generates a payment URL for redirecting users to the VNPAY payment gateway. Ensure all required parameters are provided. ```typescript const paymentUrl = vnpayService.buildPaymentUrl({ amount: 100000, // VNĐ orderId: 'ORDER123', orderInfo: 'Thanh toán hóa đơn', returnUrl: 'https://example.com/payment/return', ipnUrl: 'https://example.com/payment/ipn', locale: 'vi', }); // Chuyển hướng người dùng đến paymentUrl ``` -------------------------------- ### Verify VNPAY Return URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/README.md Handles the callback from VNPAY after a user completes or cancels a payment. It verifies the integrity of the return data and checks for successful payment. ```typescript @Get('payment/return') async handleReturn(@Query() query: any) { const verified = await vnpayService.verifyReturnUrl(query); if (verified.isValid && verified.isSuccess) { // Cập nhật trạng thái đơn hàng thành "Đã thanh toán" } } ``` -------------------------------- ### Handle IPN Callback Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/README.md Processes Instant Payment Notification (IPN) callbacks sent by VNPAY to your server. This is crucial for asynchronously confirming payments. ```APIDOC ## Handle IPN Callback ### Description Processes Instant Payment Notification (IPN) callbacks sent by VNPAY to your server. ### Method `vnpayService.verifyIpnCall(requestBody)` ### Parameters #### Request Body - **requestBody** (object) - Required - The payload received from the VNPAY IPN callback. ### Response - **RspCode** (string) - Response code from VNPAY (e.g., '00' for success, '97' for invalid). - **Message** (string) - Message indicating the status of the verification. ### Request Example ```typescript @Post('payment/ipn') async handleIpn(@Body() body: any) { const verified = await vnpayService.verifyIpnCall(body); if (!verified.isValid) { return { RspCode: '97', Message: 'Invalid' }; } // Update order status return { RspCode: '00', Message: 'Success' }; } ``` ``` -------------------------------- ### Handle VNPay IPN Callback (Webhook) Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/payment-flows.md This endpoint processes Instant Payment Notification (IPN) callbacks from VNPay, which are used for server-to-server confirmation of payment status. It verifies the data, updates the order, and handles payment success or failure. ```typescript @Post('ipn') async handleIpn(@Body() body: any) { try { // Xác thực dữ liệu từ VNPay const verified = await this.vnpayService.verifyIpnCall(body); if (!verified.isValid) { return { RspCode: '97', Message: 'Invalid data' }; } // Tìm đơn hàng const order = await this.orderService.findByOrderId(verified.data.orderId); if (!order) { return { RspCode: '01', Message: 'Order not found' }; } // Kiểm tra số tiền if (order.amount !== verified.data.amount) { return { RspCode: '04', Message: 'Amount mismatch' }; } // Kiểm tra nếu đã cập nhật trước đó if (order.status === 'COMPLETED') { return { RspCode: '00', Message: 'Already processed' }; } // Cập nhật trạng thái nếu thanh toán thành công if (verified.data.isSuccess) { await this.orderService.update(order.id, { status: 'COMPLETED', transactionNo: verified.data.transactionNo, paymentDate: new Date(), }); // Thực hiện các tác vụ sau thanh toán await this.handlePaymentSuccess(order); } else { // Thanh toán bị từ chối await this.orderService.update(order.id, { status: 'FAILED', failureReason: verified.data.message, }); } // Phản hồi thành công return { RspCode: '00', Message: 'Success' }; } catch (error) { console.error('IPN processing error:', error); return { RspCode: '99', Message: 'Internal error' }; } } private async handlePaymentSuccess(order: any) { // Gửi email xác nhận // Cập nhật inventory // Trigger webhook cho 3rd party service // v.v. } ``` -------------------------------- ### GenerateQrResponse Interface Definition Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Represents the response received after successfully generating a QR code. This interface is returned by the `generateQr()` method. ```typescript interface GenerateQrResponse { code: string; message: string; data: string; } ``` -------------------------------- ### Verify IPN Callback with VNPay Service Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/api-reference/vnpay-service.md This snippet demonstrates how to use the `verifyIpnCall` method to validate an IPN callback from VNPay. It includes steps for checking the validity of the data, verifying the order details and amount, and updating the order status. This is typically used in a payment controller to handle post-payment notifications. ```typescript import { Controller, Post, Body } from '@nestjs/common'; import { VnpayService } from 'nestjs-vnpay'; @Controller('payment') export class PaymentController { constructor(private vnpayService: VnpayService) {} @Post('ipn') async handleIpnCallback(@Body() body: any) { // Xác thực dữ liệu từ VNPay const verifyResult = await this.vnpayService.verifyIpnCall(body); if (!verifyResult.isValid) { // Dữ liệu không hợp lệ return { RspCode: '97', Message: 'Xác thực không thành công', }; } // Kiểm tra đơn hàng và số tiền const order = await this.getOrder(verifyResult.data.orderId); if (!order || order.amount !== verifyResult.data.amount) { return { RspCode: '04', Message: 'Số tiền không khớp', }; } // Cập nhật trạng thái đơn hàng trong cơ sở dữ liệu if (verifyResult.data.isSuccess) { await this.markOrderAsCompleted(order.id); } // Phản hồi thành công return { RspCode: '00', Message: 'Xác thực thành công', }; } private async getOrder(orderId: string) { // Lấy đơn hàng từ cơ sở dữ liệu return null; } private async markOrderAsCompleted(orderId: string) { // Cập nhật trạng thái đơn hàng } } ``` -------------------------------- ### Generate Payment QR Code Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Generates a QR code for payment. The QR code string is available in `qrResponse.data`. ```typescript const qrResponse = await this.vnpayService.generateQr({ amount: 100000, orderId: 'ORDER123', orderInfo: 'Thanh toán QR', returnUrl: 'https://example.com/payment/return', ipnUrl: 'https://example.com/payment/ipn', }); console.log(qrResponse.data); // Chuỗi QR ``` -------------------------------- ### VnpayModuleOptions Interface Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Defines the configuration options for the VnpayModule. It extends VNPayConfig and is used for direct module configuration. ```typescript export interface VnpayModuleOptions extends VNPayConfig {} ``` -------------------------------- ### Verify Return URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Validates the return URL parameters after a user completes or cancels a payment. Checks for validity and success status. ```typescript const result = await this.vnpayService.verifyReturnUrl(queryParams); if (result.isValid && result.isSuccess) { console.log('Thanh toán thành công'); console.log(result.data); } ``` -------------------------------- ### Handle VNPAY Return URL Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md This endpoint is the return URL callback from VNPAY after a payment attempt. It verifies the transaction and returns the status. ```APIDOC ## GET /payment/return ### Description Handles the return URL callback from VNPAY after a payment. ### Method GET ### Endpoint /payment/return ### Parameters #### Query Parameters - **query** (any) - Required - Contains VNPAY response parameters. ### Response #### Success Response (200) - **success** (boolean) - Indicates if the payment was successful. - **message** (string) - A message indicating the payment status. - **orderId** (string) - The order ID associated with the transaction. #### Response Example { "success": true, "message": "Thanh toán thành công", "orderId": "ORDER123" } ``` -------------------------------- ### VerifyReturnUrl Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Result of verifying the return URL. Returned from `verifyReturnUrl()`. ```APIDOC ## VerifyReturnUrl Result of verifying the return URL. ### Interface ```typescript interface VerifyReturnUrl { isValid: boolean; isSuccess: boolean; data: { orderId: string; amount: number; // ... other fields }; } ``` ### Usage Returned from `verifyReturnUrl()` ``` -------------------------------- ### Handle VNPay Return URL Callback Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/payment-flows.md This function processes the callback from VNPay after a user completes or cancels a payment. It verifies the transaction, updates the order status, and renders a success or error page. ```typescript @Get('return') async handleReturn(@Query() query: any) { try { // Xác thực dữ liệu từ VNPay const verified = await this.vnpayService.verifyReturnUrl(query); if (!verified.isValid) { return this.renderErrorPage('Xác thực thất bại'); } if (!verified.isSuccess) { return this.renderErrorPage('Thanh toán không thành công'); } // Cập nhật trạng thái đơn hàng const order = await this.orderService.findByOrderId(verified.data.orderId); if (!order) { return this.renderErrorPage('Không tìm thấy đơn hàng'); } // Kiểm tra số tiền if (order.amount !== verified.data.amount) { return this.renderErrorPage('Số tiền không khớp'); } // Cập nhật trạng thái await this.orderService.update(order.id, { status: 'COMPLETED', transactionNo: verified.data.transactionNo, bankTransactionNo: verified.data.bankTransactionNo, paymentDate: new Date(), }); return this.renderSuccessPage('Thanh toán thành công', verified.data); } catch (error) { return this.renderErrorPage('Lỗi xử lý thanh toán'); } } ``` -------------------------------- ### Process Refund Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Initiates a refund for a specific transaction. Requires order ID, amount, and transaction date. ```typescript const result = await this.vnpayService.refund({ orderId: 'ORDER123', amount: 100000, transactionDate: 20240101, }); ``` -------------------------------- ### ReturnQueryFromVNPay Interface Definition Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/types.md Represents the data returned from VNPay, typically as query parameters or in the request body. This interface is used for verifying return URLs and IPN calls. ```typescript interface ReturnQueryFromVNPay { // Chứa tất cả các query parameters trả về từ VNPay // [key: string]: any } ``` -------------------------------- ### Verify IPN Callback Source: https://github.com/lehuygiang28/nestjs-vnpay/blob/main/_autodocs/quick-reference.md Authenticates the Instant Payment Notification (IPN) callback from VNPAY. Updates order status if the payment is successful. ```typescript const result = await this.vnpayService.verifyIpnCall(ipnData); if (result.isValid) { if (result.data.isSuccess) { // Cập nhật đơn hàng thành "Đã thanh toán" } return { RspCode: '00', Message: 'Success' }; } else { return { RspCode: '97', Message: 'Invalid' }; } ```