UNPKG

ndk-rpc-cluster

Version:

Enterprise-grade RPC cluster system with load balancing, fault tolerance, service discovery and automatic failover support

123 lines (104 loc) 4.45 kB
import chalk from "chalk"; import ApiResponse from "../../utils/ApiResponse.js"; const logInfo = (label, obj = null) => { const time = new Date().toISOString(); if (obj) { console.log( chalk.blue(`[INFO ${time}]`) + " " + chalk.bold(label) + " → " + chalk.cyan(JSON.stringify(obj, null, 2)) ); } else { console.log(chalk.blue(`[INFO ${time}]`) + " " + chalk.bold(label)); } }; const logSuccess = (label, obj = null) => { const time = new Date().toISOString(); if (obj) { console.log( chalk.green(`[SUCCESS ${time}]`) + " " + chalk.bold(label) + " → " + chalk.green(JSON.stringify(obj, null, 2)) ); } else { console.log(chalk.green(`[SUCCESS ${time}]`) + " " + chalk.bold(label)); } }; const logError = (label, obj = null) => { const time = new Date().toISOString(); if (obj) { console.error( chalk.red(`[ERROR ${time}]`) + " " + chalk.bold(label) + " → " + chalk.red(JSON.stringify(obj, null, 2)) ); } else { console.error(chalk.red(`[ERROR ${time}]`) + " " + chalk.bold(label)); } }; const MiddlemanController = async (req, res) => { const { method: serverMethod, params: serverParams, key } = req.body; if (!serverMethod || !serverParams || !key) { logError("Missing required fields in request body", { serverMethod, serverParams, key }); return res.status(400).json(new ApiResponse(400, "All Method/params/key is required")); } const { registryHost, registryPort, showLog } = req.registryData; if (showLog) { logInfo("Sending request to Registry", { key, serverMethod, serverParams }); } let jsonresponse; try { const registryResponse = await fetch(`http://${registryHost}:${registryPort}/api/v1/get-registry-data`, { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ key, method: serverMethod, params: serverParams }), }); logSuccess("Received response from Registry", { status: registryResponse.status }); // console.log("Registry Response: ", registryResponse) jsonresponse = await registryResponse.json(); } catch (err) { logError("Failed to fetch registry data", { error: err.message }); return res.status(500).json(new ApiResponse(500, "Registry request failed")); } const { host, port, method, params } = jsonresponse.data || {}; if (!host || !port) { logError("Registry returned invalid server info", jsonresponse); return res.status(500).json(new ApiResponse(500, "Invalid server info from registry")); } if (showLog) { logInfo("Sending request to Server", { host, port, method, params }); } let jsonresponsee; try { // here host and port of load balancer is used const serverResponse = await fetch(`http://${host}:${port}/api/v1/ndk-load-balancer/forward-requests`, { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ method, params }), }); if (showLog) { logSuccess("Received response from Server", { status: serverResponse.status, host, port, method }); } jsonresponsee = await serverResponse.json(); } catch (err) { if (showLog) { logError("Failed to fetch server response", { error: err.message }); } return res.status(500).json(new ApiResponse(500, "Server request failed")); } if (jsonresponsee.statusCode !== 200) { if (showLog) { logError("Server returned an error", jsonresponsee); } return res.status(jsonresponsee.statusCode).json( new ApiResponse(jsonresponsee.statusCode, { message: jsonresponsee.message, statusCode: jsonresponsee.statusCode }) ); } if (showLog) { logSuccess("Method executed successfully", { message: jsonresponsee.message }); } return res.status(200).json( new ApiResponse(200, "Method executed successfully", { message: jsonresponsee.message, data: jsonresponsee.data }) ); }; export { MiddlemanController };