High-Level Architecture
Relevant source files
The following files were used as context for generating this wiki page:
This document outlines the high-level architecture of the zalopay application, a Node.js-based backend service designed to integrate with the ZaloPay payment gateway. The system's primary functions are to create payment orders and to securely handle callback notifications from ZaloPay after a transaction's status changes.
The architecture is centered around an Express.js web server that exposes API endpoints for these two core functions. It follows a simple service-oriented pattern, separating the web layer from the business logic for order creation and payment processing. Security is a key aspect, with HMAC-SHA256 being used to sign requests to ZaloPay and verify incoming callbacks, ensuring data integrity and authenticity.
Core Components
The application is composed of several key components that work together to facilitate the payment integration.
This diagram shows the main components of the application. The Express Server receives requests, which are routed to the appropriate service (Order or Payment). These services use the HMAC Utility and Configuration to communicate securely with the external ZaloPay API.
Sources: index.js, services/order.js, services/payment.js
1. Express Server (index.js)
The entry point of the application is an Express.js server. It is responsible for:
- Initializing the web server.
- Applying necessary middleware, including
corsfor cross-origin requests andbody-parserto handle JSON request bodies. - Defining the main API routes and delegating requests to the appropriate service layer.
- Listening for incoming connections on a configured port (defaulting to 3000).
Sources: index.js:3-15
2. Configuration (common/config.js)
All application-level and ZaloPay-specific configurations are centralized in a single file. This allows for easy management of credentials and environment settings without hardcoding them in the business logic.
| Key | Description |
|---|---|
app_id | The application ID provided by ZaloPay. |
key1 | The first secret key provided by ZaloPay, used for signing outgoing order creation requests. |
key2 | The second secret key provided by ZaloPay, used for verifying the signature of incoming callbacks. |
endpoint | The URL for the ZaloPay API endpoint to create orders. |
Sources: common/config.js:1-6
3. Cryptographic Utility (common/hmac.js)
This module provides a crucial security function: HMAC (Hash-based Message Authentication Code) generation. It exports a single function, HmacSHA256, which creates a SHA256 HMAC signature from a given data string and a secret key. This is fundamental to ZaloPay integration for authenticating requests and callbacks.
// common/hmac.js:1-5
const crypto = require('crypto');
module.exports.HmacSHA256 = (data, key) => {
return crypto.createHmac('sha256', key).update(data).digest('hex');
}
Sources: common/hmac.js:1-5
4. Service Layer (services/)
The business logic is encapsulated within service modules.
OrderService(services/order.js): This service handles the creation of new payment orders. It constructs the order payload, generates the requiredmacsignature usingkey1, and sends the request to the ZaloPay API.PaymentService(services/payment.js): This service is responsible for processing callbacks from ZaloPay. Its primary task is to verify the integrity and authenticity of the callback data by recalculating the HMAC signature withkey2and comparing it to the signature provided by ZaloPay.
Sources: services/order.js, services/payment.js
API Endpoints and Flows
The application exposes two primary API endpoints that define its interaction with clients and the ZaloPay gateway.
| Method | Endpoint | Description |
|---|---|---|
POST | /api/create-order | Creates a new payment order with ZaloPay. |
POST | /api/callback | An endpoint for ZaloPay to send transaction status updates. |
Sources: index.js:9-12
Order Creation Flow
The order creation process is initiated by a client sending a request to the /api/create-order endpoint. The server then orchestrates the creation of a transaction with ZaloPay.
This sequence diagram illustrates the steps involved in creating a ZaloPay order, from the initial client request to receiving the payment URL from ZaloPay.
The data sent to ZaloPay includes a mac field, which is a signature generated from a concatenated string of order parameters.
Signature Data String Format:
app_id + "|" + app_trans_id + "|" + app_user + "|" + amount + "|" + app_time + "|" + embed_data + "|" + item
Sources: services/order.js:18-20
Payment Callback Flow
After the user completes or cancels the payment on ZaloPay's side, ZaloPay sends a POST request to the /api/callback endpoint configured in the ZaloPay developer portal.
This diagram shows the callback validation process. The server uses key2 to verify that the incoming notification is genuinely from ZaloPay and has not been tampered with.
Sources: services/payment.js:6-16, common/config.js:4
Summary
The zalopay project provides a lean and effective server-side implementation for integrating with the ZaloPay payment gateway. Its architecture is straightforward, relying on an Express server to handle HTTP requests and a service layer to contain the core business logic. The separation of concerns—with distinct modules for configuration, cryptographic functions, and business logic—makes the system maintainable. The critical use of HMAC signatures for both outgoing requests and incoming callbacks ensures a secure communication channel with the ZaloPay API.