UNPKG

factorio-rcon-prometheus-exporter

Version:

A Prometheus exporter that connects to a Factorio server via RCON and exports metrics.

137 lines (133 loc) 4.04 kB
#!/usr/bin/env node "use strict"; var __create = Object.create; var __defProp = Object.defineProperty; var __getOwnPropDesc = Object.getOwnPropertyDescriptor; var __getOwnPropNames = Object.getOwnPropertyNames; var __getProtoOf = Object.getPrototypeOf; var __hasOwnProp = Object.prototype.hasOwnProperty; 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( // If the importer is in node compatibility mode or this is not an ESM // file that has been converted to a CommonJS file using a Babel- // compatible transform (i.e. "__esModule" has not been set), then set // "default" to the CommonJS "module.exports" for node compatibility. isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target, mod )); // bin/http.ts var import_express = __toESM(require("express")); // src/rcon.ts var import_promises = require("node:fs/promises"); var import_node_path = require("node:path"); var import_rcon_client = require("rcon-client"); var FactorioRcon = class extends import_rcon_client.Rcon { connected = false; metricsScript; constructor(host, port, password) { super({ host, port, password }); this.on("connect", this.onConnect); this.on("end", this.onDisconnect); this.on("error", this.onError); } getHostname() { return this.config.host + ":" + this.config.port; } async runScript(script) { if (!this.connected) await this.connect(); const response = await this.send("/sc " + script); return response; } async getMetrics() { if (!this.connected) await this.connect(); if (!this.metricsScript) { const scriptPath = (0, import_node_path.join)(__dirname, "metrics.lua"); const originalScript = await (0, import_promises.readFile)(scriptPath, "utf-8"); this.metricsScript = originalScript.replaceAll(/process\.env\.(\w+)/g, (substr, environmentVariable) => { return JSON.stringify(process.env[environmentVariable] ?? substr); }); } return await this.runScript(this.metricsScript); } onConnect = () => { this.connected = true; }; onDisconnect = () => { this.connected = false; }; onError = (error) => { console.log(error); }; }; // bin/http.ts var { /** * Host to bind the HTTP server to */ HOST = "0.0.0.0", /** * Port for the HTTP server */ PORT = "9772", /** * IP or Hostname for the RCON server */ RCON_HOST = "localhost", /** * RCON port */ RCON_PORT = "27015", /** * RCON password */ RCON_PASSWORD = "" } = process.env; var app = (0, import_express.default)(); var rcon = new FactorioRcon(RCON_HOST, parseInt(RCON_PORT, 10), RCON_PASSWORD); app.get("/", (_req, res) => { res.send(`<html lang="en"> <head> <title>Factorio RCON Prometheus Exporter</title> </head> <body> <h1>Factorio RCON Prometheus Exporter</h1> <p><a href="/metrics">Metrics</a></p> </body> </html> `); }); app.get("/metrics", (_req, res) => { rcon.getMetrics().then((metrics) => { res.set("Content-Disposition", "inline"); res.set("Content-Type", "text/plain; version=0.0.4"); res.end(metrics); }).catch((err) => { console.error(err); if (err instanceof Error) { res.status(500).end(`# ${err.message}`); } else { res.status(500).end(`# ${String(err)}`); } }); }); app.listen(parseInt(PORT, 10), HOST, () => { console.log(`Server running at http://${HOST}:${PORT}/`); }); process.on("SIGINT", () => { process.exit(); }); process.on("SIGTERM", () => { process.exit(); }); //# sourceMappingURL=http.js.map