82 lines
1.8 KiB
TypeScript
82 lines
1.8 KiB
TypeScript
/* eslint-disable @typescript-eslint/no-explicit-any */
|
|
|
|
import { v4 as uuidv4 } from "uuid";
|
|
import CryptoJS from "crypto-js";
|
|
import { ENV } from "../constants/env";
|
|
|
|
/* =========================
|
|
HELPERS (COPY POSTMAN)
|
|
========================= */
|
|
|
|
export function parseQueryParamsManual(url: string) {
|
|
const result: Record<string, any> = {};
|
|
const queryStartIndex = url.indexOf("?");
|
|
|
|
if (queryStartIndex === -1 || queryStartIndex === url.length - 1) {
|
|
return result;
|
|
}
|
|
|
|
const queryString = url.substring(queryStartIndex + 1);
|
|
const pairs = queryString.split("&");
|
|
|
|
for (const pair of pairs) {
|
|
const parts = pair.split("=");
|
|
|
|
if (parts.length === 2) {
|
|
const key = decodeURIComponent(parts[0].replace(/\+/g, " "));
|
|
const value = decodeURIComponent(parts[1].replace(/\+/g, " "));
|
|
result[key] = value;
|
|
}
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
export function sortKeysDeep(obj: any): any {
|
|
if (Array.isArray(obj)) {
|
|
return obj.map(sortKeysDeep);
|
|
}
|
|
|
|
if (obj !== null && typeof obj === "object") {
|
|
return Object.keys(obj)
|
|
.sort()
|
|
.reduce((acc: any, key) => {
|
|
acc[key] = sortKeysDeep(obj[key]);
|
|
return acc;
|
|
}, {});
|
|
}
|
|
|
|
return obj;
|
|
}
|
|
|
|
/* =========================
|
|
SIGNATURE
|
|
========================= */
|
|
|
|
export interface SignatureResult {
|
|
timestamp: number;
|
|
nonce: string;
|
|
signature: string;
|
|
}
|
|
|
|
export function generateSignature(rawBody: any): SignatureResult {
|
|
const timestamp = Math.floor(Date.now() / 1000);
|
|
const nonce = uuidv4();
|
|
|
|
const body = sortKeysDeep(rawBody ?? {});
|
|
|
|
const payload = JSON.stringify({
|
|
timestamp,
|
|
nonce,
|
|
body: JSON.stringify(body), // ⚠️ STRINGIFY GANDA (WAJIB)
|
|
});
|
|
|
|
const hash = CryptoJS.HmacSHA256(payload, ENV.secretKey);
|
|
|
|
return {
|
|
timestamp,
|
|
nonce,
|
|
signature: CryptoJS.enc.Hex.stringify(hash),
|
|
};
|
|
}
|