UNPKG

@kibot/cli

Version:

🧙 Kibot's command line tool written in node

390 lines (369 loc) • 14.3 kB
#!/usr/bin/env node var __create = Object.create; var __defProp = Object.defineProperty; var __getOwnPropDesc = Object.getOwnPropertyDescriptor; var __getOwnPropNames = Object.getOwnPropertyNames; var __getOwnPropSymbols = Object.getOwnPropertySymbols; var __getProtoOf = Object.getPrototypeOf; var __hasOwnProp = Object.prototype.hasOwnProperty; var __propIsEnum = Object.prototype.propertyIsEnumerable; var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value; var __spreadValues = (a, b) => { for (var prop in b || (b = {})) if (__hasOwnProp.call(b, prop)) __defNormalProp(a, prop, b[prop]); if (__getOwnPropSymbols) for (var prop of __getOwnPropSymbols(b)) { if (__propIsEnum.call(b, prop)) __defNormalProp(a, prop, b[prop]); } return a; }; var __copyProps = (to, from, except, desc) => { if (from && typeof from === "object" || typeof from === "function") { for (let key of __getOwnPropNames(from)) if (!__hasOwnProp.call(to, key) && key !== except) __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable }); } return to; }; var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target, mod)); // src/kibot.ts var import_commander4 = require("commander"); // src/cmd/config/index.ts var import_commander = require("commander"); // src/cmd/config/query.ts var import_chalk3 = __toESM(require("chalk")); // src/utils/config.ts var import_chalk2 = __toESM(require("chalk")); var import_fs = require("fs"); var import_promises = require("fs/promises"); var import_os = require("os"); var import_path = require("path"); // src/utils/logger.ts var import_chalk = __toESM(require("chalk")); var log = (...message) => { console.log(...message); }; var success = (...message) => { console.log(import_chalk.default.green(...message)); }; var info = (...message) => { console.info(import_chalk.default.blue(...message)); }; var warn = (...message) => { console.warn(import_chalk.default.yellow(...message)); }; var error = (...message) => { console.error(import_chalk.default.red(...message)); return process.exit(1); }; var json = (object) => { console.log(JSON.stringify(object, null, 2)); }; var table = (object) => { console.table(object); }; var Logger = { log, success, info, warn, error, json, table }; // src/utils/config.ts var defaultConfig = { apps: { quiron: { client: 0, database: { server: "", database: "", user: "", password: "", options: { trustedConnection: true, trustServerCertificate: true } }, webhooks: { uploadAppointments: "https://some-url.com" } } } }; var configFilename = ".kibot-config.json"; function getGlobalConfigPath() { try { const home = (0, import_os.homedir)(); if (!home) { throw new Error("No home directory found."); } const configPath = (0, import_path.join)(home, configFilename); return configPath; } catch (error2) { return Logger.error(error2); } } function readGlobalConfig() { try { const configPath = getGlobalConfigPath(); if (!(0, import_fs.existsSync)(configPath)) { Logger.warn("Config file wasn't found"); process.exit(0); } return JSON.parse((0, import_fs.readFileSync)(configPath, "utf8")); } catch (error2) { return Logger.error(error2); } } async function removeGlobalConfig() { try { const configPath = getGlobalConfigPath(); if (!(0, import_fs.existsSync)(configPath)) { Logger.warn("Config file wasn't found"); process.exit(0); } await (0, import_promises.unlink)(configPath); } catch (error2) { Logger.error(error2); } } async function createGlobalConfig(optionalConfig = {}) { try { const configPath = getGlobalConfigPath(); await (0, import_promises.writeFile)(configPath, JSON.stringify(__spreadValues(__spreadValues({}, defaultConfig), optionalConfig), null, 2)); return import_chalk2.default.blue.underline(configPath); } catch (error2) { return Logger.error(error2); } } // src/cmd/config/query.ts var revealConfigFile = async () => { Logger.info(import_chalk3.default.underline(getGlobalConfigPath())); }; var previewConfigFile = async () => { const currentConfig = readGlobalConfig(); if (currentConfig) { Logger.json(currentConfig); } }; var removeConfigFile = async () => { await removeGlobalConfig(); }; var createConfigFile = async (app, options) => { var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y; const currentApps = ["quiron"]; if (!currentApps.includes(app.toLowerCase())) { Logger.error("App", import_chalk3.default.bold.underline(app), "is not yet available"); } const newConfig = { apps: {} }; if (app === "quiron") { newConfig.apps.quiron = { client: !isNaN(+options.client) ? +options.client : (_b = (_a = defaultConfig.apps) == null ? void 0 : _a.quiron) == null ? void 0 : _b.client, database: { database: options.database || ((_e = (_d = (_c = defaultConfig.apps) == null ? void 0 : _c.quiron) == null ? void 0 : _d.database) == null ? void 0 : _e.database), server: options.server || ((_h = (_g = (_f = defaultConfig.apps) == null ? void 0 : _f.quiron) == null ? void 0 : _g.database) == null ? void 0 : _h.server), user: options.user || ((_k = (_j = (_i = defaultConfig.apps) == null ? void 0 : _i.quiron) == null ? void 0 : _j.database) == null ? void 0 : _k.user), password: options.user || ((_n = (_m = (_l = defaultConfig.apps) == null ? void 0 : _l.quiron) == null ? void 0 : _m.database) == null ? void 0 : _n.password), options: { trustedConnection: (_r = (_q = (_p = (_o = defaultConfig.apps) == null ? void 0 : _o.quiron) == null ? void 0 : _p.database) == null ? void 0 : _q.options) == null ? void 0 : _r.trustedConnection, trustServerCertificate: (_v = (_u = (_t = (_s = defaultConfig.apps) == null ? void 0 : _s.quiron) == null ? void 0 : _t.database) == null ? void 0 : _u.options) == null ? void 0 : _v.trustServerCertificate } }, webhooks: { uploadAppointments: options.uploadwebhook || ((_y = (_x = (_w = defaultConfig.apps) == null ? void 0 : _w.quiron) == null ? void 0 : _x.webhooks) == null ? void 0 : _y.uploadAppointments) } }; } Logger.log(await createGlobalConfig(newConfig)); }; // src/cmd/config/index.ts var config = () => { const cmd = new import_commander.Command("config"); cmd.addCommand(new import_commander.Command("reveal").action(revealConfigFile)); cmd.addCommand(new import_commander.Command("preview").action(previewConfigFile)); cmd.addCommand(new import_commander.Command("remove").action(removeConfigFile)); cmd.addCommand(new import_commander.Command("create").arguments("<app>").option("-c --client <client>", "Client ID").option("-db --database <database>", "Database name").option("-s --server <server>", "Server instance name").option("-usr --user <user>", "Username").option("-pwd --password <password>", "Password").option("-uw --uploadwebhook <uploadwebhook>", "Webhook to upload appointments").action(createConfigFile)); return cmd; }; // src/cmd/db/index.ts var import_commander2 = require("commander"); // src/cmd/db/query.ts var import_chalk5 = __toESM(require("chalk")); // src/database/connection.ts var import_chalk4 = __toESM(require("chalk")); var import_msnodesqlv8 = __toESM(require("mssql/msnodesqlv8")); var getConnection = async () => { var _a, _b, _c, _d, _e; const dbConfig = (_c = (_b = (_a = readGlobalConfig()) == null ? void 0 : _a.apps) == null ? void 0 : _b.quiron) == null ? void 0 : _c.database; if (!dbConfig) { throw new Error(import_chalk4.default.red.bold("Database config was not found")); } const mssqlConfig = { driver: "msnodesqlv8", database: dbConfig.database, server: dbConfig.server || "", user: dbConfig.user, password: dbConfig.password, options: { trustedConnection: (_d = dbConfig.options) == null ? void 0 : _d.trustedConnection, trustServerCertificate: (_e = dbConfig.options) == null ? void 0 : _e.trustServerCertificate } }; try { const pool = import_msnodesqlv8.default.connect(mssqlConfig); return pool; } catch (error2) { return Logger.error(error2); } }; // src/cmd/db/query.ts var testDatabaseConnection = async () => { try { const pool = await getConnection(); const connectionStatus = pool.connected ? import_chalk5.default.green.bold("Connected") : import_chalk5.default.red.bold("Disconnected"); const connectionHealth = pool.healthy ? import_chalk5.default.green.bold("Healthy") : import_chalk5.default.red.bold("Unhealthy"); Logger.log("Status ->", connectionStatus, " - ", "Connection ->", connectionHealth); } catch (error2) { Logger.error(error2); } }; // src/cmd/db/index.ts var db = () => { const cmd = new import_commander2.Command("db"); cmd.addCommand(new import_commander2.Command("test").action(testDatabaseConnection)); return cmd; }; // src/cmd/quiron/appointments/index.ts var import_commander3 = require("commander"); // src/cmd/quiron/appointments/query.ts var import_chalk6 = __toESM(require("chalk")); // src/utils/http-service.ts var import_cross_fetch = __toESM(require("cross-fetch")); var get = async (url) => { (0, import_cross_fetch.default)(url); }; var post = async (url, body) => (0, import_cross_fetch.default)(url, { method: "post", body: JSON.stringify(body), headers: { Accept: "application/json", "Content-Type": "application/json" } }); var put = async (url, body) => (0, import_cross_fetch.default)(url, { method: "put", body: JSON.stringify(body), headers: { Accept: "application/json", "Content-Type": "application/json" } }); var patch = async (url, body) => (0, import_cross_fetch.default)(url, { method: "patch", body: JSON.stringify(body), headers: { Accept: "application/json", "Content-Type": "application/json" } }); var del = async (url, body) => (0, import_cross_fetch.default)(url, { method: "delete" }); var HttpService = { get, post, put, patch, del }; // src/utils/http-utilities.ts var HTTPResponseError = class extends Error { response; constructor(r) { super(`HTTP Error response: ${r.status} ${r.statusText}`); this.response = r; } }; var checkHttpStatus = (response) => { if (response.ok) { return response; } else { throw new HTTPResponseError(response); } }; // src/cmd/quiron/appointments/query.ts var listAppointments = async (options) => { try { const pool = await getConnection(); const query = await pool.request().query(`exec ObtenerChatBotCitas`); const appointments2 = query.recordset; if (appointments2.length === 0) { Logger.log("No appointments were found"); process.exit(0); } if (options.format === "table") { Logger.table(appointments2); } else { Logger.json(appointments2); } } catch (error2) { Logger.error(error2); } process.exit(0); }; var prepareAppointments = async () => { try { const pool = await getConnection(); const query = await pool.request().query(`exec SpGrabarCitasChatBot`); Logger.log(`Rows affected: ${query.rowsAffected}`); } catch (error2) { Logger.error(error2); } process.exit(0); }; var uploadAppointments = async () => { var _a, _b, _c; const quironConfig = (_b = (_a = readGlobalConfig()) == null ? void 0 : _a.apps) == null ? void 0 : _b.quiron; const { client, webhooks } = quironConfig || {}; if (!client) { Logger.error("Client config was not found"); } if (!webhooks) { Logger.error("Webhook config was not found"); } try { const pool = await getConnection(); const query = await pool.query(`exec ObtenerChatBotCitas`); const appointments2 = query.recordset; if (appointments2.length === 0) { Logger.warn("No appointments were found. Make sure to prepare them first."); process.exit(0); } const payload = { Citas: appointments2, IdCliente: client }; const response = await HttpService.post(webhooks.uploadAppointments, payload); checkHttpStatus(response); const { isSuccess, result } = await response.json(); if (isSuccess) { for (const appointment of (_c = result == null ? void 0 : result.responseSend) == null ? void 0 : _c.result) { const stmt = ` UPDATE ChatBotCitas SET Enviado = $1, FechaHoraEnvio = '$2' WHERE NumeroCita = $3 AND IdPaciente = $4`.replace("$1", Boolean(appointment.enviado) ? "1" : "0").replace("$2", new Date(appointment.fechaHoraEnvio).toISOString()).replace("$3", appointment.numeroCita).replace("$4", appointment.idPaciente); const updateQuery = await pool.query(stmt); Logger.log("Appointment:", appointment.numeroCita, "Pacient:", `${appointment.nombresPaciente} (${appointment.celular})`, "->", updateQuery.rowsAffected[0] > 0 ? import_chalk6.default.green.bold("SUCCEEDED") : import_chalk6.default.red.bold("FAILED")); } } } catch (error2) { if (error2 instanceof HTTPResponseError) { Logger.error(await error2.response.text()); } else { Logger.error(error2); } } process.exit(0); }; // src/cmd/quiron/appointments/index.ts var appointments = () => { const cmd = new import_commander3.Command("appointments"); cmd.addCommand(new import_commander3.Command("list").option("-f --format <format>", "display data in JSON or Table format", "json").action(listAppointments)); cmd.addCommand(new import_commander3.Command("prepare").action(prepareAppointments)); cmd.addCommand(new import_commander3.Command("upload").action(uploadAppointments)); return cmd; }; // src/kibot.ts var program = new import_commander4.Command(); program.addCommand(config()); program.addCommand(db()); program.addCommand(appointments()); program.parse(process.argv);