Xử lý lỗi
Các loại error và cách xử lý trong Node.js SDK
SDK sử dụng hệ thống error phân cấp. Tất cả error đều kế thừa từ SSIError, kế thừa từ Error chuẩn.
Danh sách Error
| Error Class | Kế thừa | Mô tả |
|---|---|---|
SSIError | Error | Error cơ sở — có message, code, statusCode, responseBody (đã che secret), headers |
APIError | SSIError | API trả về lỗi. code là mã lỗi của server, HTTP status nằm ở statusCode. HTTP 200 kèm code khác 200/204 cũng ném APIError |
DuplicateRequestError | APIError | HTTP 409: clientRequestId hoặc batchRequestId đã dùng (xem Batch Orders) |
AuthenticationError | SSIError | Xác thực thất bại (sai credentials, token hết hạn). Không kế thừa APIError |
SmartOTPPendingError | AuthenticationError | Smart OTP chưa được duyệt (HTTP 202, code 401114) |
SmartOTPRejectedError | AuthenticationError | Smart OTP bị từ chối |
ReauthenticationRequired | AuthenticationError | Không refresh được phiên và không có OTP: cần xác thực lại bằng OTP |
RateLimitError | SSIError | Vượt quá giới hạn request — có thêm retryAfterMs (mili giây), limit, remaining, reset |
WebSocketError | SSIError | Lỗi kết nối hoặc giao tiếp WebSocket |
TradingWSError | WebSocketError | Server của Trading WebSocket trả frame lỗi — có thêm status, errorCode, serverMessage |
ValidationError | SSIError | Lỗi validate input |
ConfigurationError | SSIError | Lỗi cấu hình (kể cả option không tồn tại) |
Import
import {
SSIError,
APIError,
DuplicateRequestError,
AuthenticationError,
SmartOTPPendingError,
SmartOTPRejectedError,
ReauthenticationRequired,
RateLimitError,
WebSocketError,
TradingWSError,
ValidationError,
ConfigurationError,
} from '@ssi.developer/ssi-sdk';Sử dụng cơ bản
try {
const token = await auth.authenticate('wrong_otp');
} catch (error) {
console.error(`Error: ${error.message}`);
}Xử lý lỗi chi tiết
AuthenticationError không phải là APIError, nên thứ tự các nhánh instanceof không còn quan trọng giữa hai lớp này. Các lớp con (DuplicateRequestError, TradingWSError, SmartOTP*) cần được kiểm tra trước lớp cha nếu muốn xử lý riêng.
try {
const result = await trading.trading.placeLimitOrder(
'YOUR_ACCOUNT_NO', 'SSI', OrderSide.BUY, 100, 68000,
);
} catch (error) {
if (error instanceof ReauthenticationRequired) {
console.log('Cần xác thực lại bằng OTP');
} else if (error instanceof AuthenticationError) {
console.log('Xác thực thất bại');
} else if (error instanceof RateLimitError) {
console.log(`Rate limited, retry sau ${error.retryAfterMs}ms`);
} else if (error instanceof DuplicateRequestError) {
console.log(`Trùng id (HTTP 409): ${error.message}`);
} else if (error instanceof APIError) {
console.log(`API error ${error.statusCode} (code ${error.code}): ${error.message}`);
} else if (error instanceof ValidationError) {
console.log(`Validation: ${error.message}`);
} else if (error instanceof TradingWSError) {
console.log(`Trading WS: status=${error.status} code=${error.errorCode} msg=${error.serverMessage}`);
} else if (error instanceof WebSocketError) {
console.log(`WebSocket: ${error.message}`);
} else if (error instanceof ConfigurationError) {
console.log(`Config: ${error.message}`);
} else if (error instanceof SSIError) {
console.log(`SDK error: ${error.message}`);
} else {
console.log(`Unknown error: ${error}`);
}
}Thuộc tính Error
SSIError / APIError
| Thuộc tính | Kiểu | Mô tả |
|---|---|---|
message | string | Thông báo lỗi |
code | string | number? | Mã lỗi (với APIError là mã của server) |
statusCode | number? | HTTP status code |
responseBody | unknown? | Body response gốc (nếu có), đã che secret |
headers | Record<string, string> | Header response |
RateLimitError
| Thuộc tính | Kiểu | Mô tả |
|---|---|---|
message | string | Thông báo lỗi |
retryAfterMs | number? | Thời gian chờ trước khi retry (mili giây). Trước đây tên là retryAfter (giây) |
limit, remaining, reset | number? | Thông tin rate limit server gửi kèm (nếu có) |
code mặc định là 'RATE_LIMITED' và statusCode là 429. Với GET, REST client tự chờ khi gặp 429 (tối đa 3 lần retry, không bao giờ chờ quá 30 giây).
TradingWSError
| Thuộc tính | Kiểu | Mô tả |
|---|---|---|
status | number | Status code trong frame lỗi (ví dụ 429) |
errorCode | string | Mã lỗi server |
serverMessage | string | Thông báo của server |
Lỗi theo tính năng
Batch Orders
Xem cách dùng ở API Services, mục 5.6.
| Lỗi | Khi nào | Cách xử lý |
|---|---|---|
ValidationError | Lô rỗng, vượt maxBatchOrders, hoặc một lệnh sai (thiếu field, clientRequestId quá dài, lệnh hủy không có đúng một id...) | Sửa input. Chưa có request nào được gửi |
DuplicateRequestError | HTTP 409: clientRequestId hoặc batchRequestId đã dùng trong ngày | Kiểm tra sổ lệnh, đừng gửi lại bằng id khác |
AuthenticationError | Xác thực thất bại (sai credentials, token hết hạn) | Xác thực lại bằng OTP |
RateLimitError | Vượt giới hạn request | Chờ rồi retry có kiểm soát |
APIError | Lỗi server khác (có statusCode, code), ví dụ 400111 khi batchRequestTime ngoài cửa sổ replay | Đọc code và message, không retry mù quáng |
Lô không bao giờ bị retry tự động.
Trading WebSocket
| Lỗi | Khi nào |
|---|---|
TradingWSError | Server trả frame lỗi, hoặc từ chối kết nối sau khi đã nhận socket (HTTP 101). Có status, errorCode, serverMessage. Kế thừa WebSocketError |
WebSocketError | Chưa kết nối, gửi thất bại, hết thời gian chờ phản hồi (không retry), socket đóng trước khi có phản hồi, hoặc thiếu private key cho lệnh đổi trạng thái |
ValidationError | Input sai bị bắt tại máy (ví dụ subscribe nhiều tài khoản, batch rỗng hoặc quá giới hạn). Vì method là async, lỗi này làm Promise bị reject |
Status 429 từ server cho ra TradingWSError với status 429. Mã chữ ký bị từ chối 401006, 401008, 401013 được SDK thử lại một lần ở chế độ signatureEncoding: 'auto'.
Hướng dẫn xử lý
- Dùng
instanceofđể xử lý từng loại error. - Bắt
AuthenticationErrorkhi cần làm mới token hoặc lấy OTP mới.ReauthenticationRequirednghĩa là bắt buộc phải xác thực lại bằng OTP. - Bắt
RateLimitErrorvà tuân thủretryAfterMsđể backoff. - Bắt
APIErrorđể xử lý lỗi nghiệp vụ từ server. Mã401101-401104và401106-401108(refresh token không dùng được) buộc phải xác thực lại. - Bắt
WebSocketErrorkhi xử lý kết nối streaming.connect()lần đầu thất bại némWebSocketErrorhoặcAuthenticationError. - Bắt
ValidationErrorđể kiểm tra input trước khi gọi API. - Bắt
ConfigurationErrorkhi cấu hình thiếu hoặc không hợp lệ. - Dùng
SSIErrorlàm fallback cho tất cả lỗi SDK.