@glassmkr/crucible 0.1.0 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (45) hide show
  1. package/.github/ISSUE_TEMPLATE/bug_report.md +24 -0
  2. package/.github/ISSUE_TEMPLATE/no_data.md +26 -0
  3. package/README.md +48 -52
  4. package/dist/alerts/rules.js +120 -0
  5. package/dist/alerts/rules.js.map +1 -1
  6. package/dist/collect/cpu.js +57 -16
  7. package/dist/collect/cpu.js.map +1 -1
  8. package/dist/collect/disks.js +48 -2
  9. package/dist/collect/disks.js.map +1 -1
  10. package/dist/collect/ipmi.js +160 -2
  11. package/dist/collect/ipmi.js.map +1 -1
  12. package/dist/collect/security.d.ts +39 -0
  13. package/dist/collect/security.js +176 -0
  14. package/dist/collect/security.js.map +1 -0
  15. package/dist/config.d.ts +23 -0
  16. package/dist/config.js +5 -0
  17. package/dist/config.js.map +1 -1
  18. package/dist/index.js +48 -3
  19. package/dist/index.js.map +1 -1
  20. package/dist/lib/types.d.ts +64 -0
  21. package/dist/lib/version-check.d.ts +7 -0
  22. package/dist/lib/version-check.js +39 -0
  23. package/dist/lib/version-check.js.map +1 -0
  24. package/dist/metrics-server.d.ts +3 -0
  25. package/dist/metrics-server.js +113 -0
  26. package/dist/metrics-server.js.map +1 -0
  27. package/dist/notify/telegram.js +27 -9
  28. package/dist/notify/telegram.js.map +1 -1
  29. package/dist/push/forge.d.ts +1 -0
  30. package/dist/push/forge.js +80 -4
  31. package/dist/push/forge.js.map +1 -1
  32. package/package.json +1 -1
  33. package/scripts/sign-release.sh +29 -0
  34. package/src/alerts/rules.ts +99 -0
  35. package/src/collect/cpu.ts +64 -16
  36. package/src/collect/disks.ts +57 -2
  37. package/src/collect/ipmi.ts +147 -3
  38. package/src/collect/security.ts +238 -0
  39. package/src/config.ts +5 -0
  40. package/src/index.ts +49 -3
  41. package/src/lib/types.ts +44 -0
  42. package/src/lib/version-check.ts +38 -0
  43. package/src/metrics-server.ts +123 -0
  44. package/src/notify/telegram.ts +29 -9
  45. package/src/push/forge.ts +89 -5
@@ -2,7 +2,7 @@ import { run } from "../lib/exec.js";
2
2
  export async function collectIpmi() {
3
3
  const sensorRaw = await run("ipmitool", ["sensor"]);
4
4
  if (!sensorRaw) {
5
- return { available: false, sensors: [], ecc_errors: { correctable: 0, uncorrectable: 0 }, sel_entries_count: 0 };
5
+ return { available: false, sensors: [], ecc_errors: { correctable: 0, uncorrectable: 0 }, sel_entries_count: 0, sel_events_recent: [], fans: [] };
6
6
  }
7
7
  // Parse sensor readings
8
8
  const sensors = [];
@@ -16,7 +16,6 @@ export async function collectIpmi() {
16
16
  const status = parts[3];
17
17
  const numValue = parseFloat(rawValue);
18
18
  const value = isNaN(numValue) ? rawValue : numValue;
19
- // Parse upper critical threshold
20
19
  let upperCritical;
21
20
  if (parts[8]) {
22
21
  const uc = parseFloat(parts[8]);
@@ -45,11 +44,170 @@ export async function collectIpmi() {
45
44
  if (match)
46
45
  selCount = parseInt(match[1], 10);
47
46
  }
47
+ // SEL recent events
48
+ const selEvents = await collectSelEvents();
49
+ // Fan status
50
+ const fans = await collectFanStatus();
48
51
  return {
49
52
  available: true,
50
53
  sensors,
51
54
  ecc_errors: { correctable, uncorrectable },
52
55
  sel_entries_count: selCount,
56
+ sel_events_recent: selEvents,
57
+ fans,
53
58
  };
54
59
  }
60
+ async function collectSelEvents() {
61
+ const output = await run("ipmitool", ["sel", "elist"]);
62
+ if (!output)
63
+ return [];
64
+ const events = [];
65
+ const lines = output.trim().split("\n");
66
+ const fiveMinAgo = new Date(Date.now() - 5 * 60 * 1000);
67
+ for (const line of lines) {
68
+ const parts = line.split("|").map((s) => s.trim());
69
+ if (parts.length < 5)
70
+ continue;
71
+ const [idStr, date, time, sensor, event, direction] = parts;
72
+ const timestamp = parseSelTimestamp(date, time);
73
+ const tsDate = new Date(timestamp);
74
+ // Only include events from the last 5 minutes on subsequent runs
75
+ // On first run this will include everything (fiveMinAgo is always recent)
76
+ // We keep last 20 events max regardless
77
+ const sensorType = classifySensor(sensor);
78
+ const severity = deriveSelSeverity(event, sensorType);
79
+ events.push({
80
+ id: parseInt(idStr) || 0,
81
+ timestamp,
82
+ sensor,
83
+ sensor_type: sensorType,
84
+ event,
85
+ direction: direction || "Asserted",
86
+ severity,
87
+ });
88
+ }
89
+ // Return last 20 events, most recent first
90
+ return events.slice(-20).reverse();
91
+ }
92
+ function parseSelTimestamp(date, time) {
93
+ if (!date || !time)
94
+ return new Date().toISOString();
95
+ // Format: "04/05/2026" and "14:23:05"
96
+ const parts = date.split("/");
97
+ if (parts.length !== 3)
98
+ return new Date().toISOString();
99
+ const [month, day, year] = parts;
100
+ return `${year}-${month.padStart(2, "0")}-${day.padStart(2, "0")}T${time}Z`;
101
+ }
102
+ function classifySensor(sensor) {
103
+ const lower = sensor.toLowerCase();
104
+ if (lower.includes("memory") || lower.includes("dimm"))
105
+ return "memory";
106
+ if (lower.includes("power supply") || lower.includes("psu"))
107
+ return "power";
108
+ if (lower.includes("fan"))
109
+ return "fan";
110
+ if (lower.includes("watchdog"))
111
+ return "watchdog";
112
+ if (lower.includes("processor") || lower.includes("cpu"))
113
+ return "processor";
114
+ if (lower.includes("temperature") || lower.includes("temp"))
115
+ return "temperature";
116
+ if (lower.includes("voltage"))
117
+ return "voltage";
118
+ if (lower.includes("drive") || lower.includes("disk"))
119
+ return "storage";
120
+ if (lower.includes("chassis") || lower.includes("intrusion"))
121
+ return "chassis";
122
+ return "other";
123
+ }
124
+ function deriveSelSeverity(event, sensorType) {
125
+ const lower = event.toLowerCase();
126
+ // Critical events
127
+ if (lower.includes("uncorrectable"))
128
+ return "critical";
129
+ if (lower.includes("failure detected"))
130
+ return "critical";
131
+ if (lower.includes("ac lost"))
132
+ return "critical";
133
+ if (lower.includes("hard reset"))
134
+ return "critical";
135
+ if (lower.includes("power off"))
136
+ return "critical";
137
+ if (lower.includes("critical"))
138
+ return "critical";
139
+ if (lower.includes("non-recoverable"))
140
+ return "critical";
141
+ if (lower.includes("thermal trip"))
142
+ return "critical";
143
+ if (lower.includes("processor disabled"))
144
+ return "critical";
145
+ if (lower.includes("machine check"))
146
+ return "critical";
147
+ // Warning events
148
+ if (lower.includes("correctable ecc"))
149
+ return "warning";
150
+ if (lower.includes("logging limit"))
151
+ return "warning";
152
+ if (lower.includes("lower critical going low"))
153
+ return "warning";
154
+ if (lower.includes("upper critical going high"))
155
+ return "warning";
156
+ if (lower.includes("redundancy lost"))
157
+ return "warning";
158
+ if (lower.includes("predictive failure"))
159
+ return "warning";
160
+ if (lower.includes("degraded"))
161
+ return "warning";
162
+ // Info events
163
+ if (lower.includes("presence detected"))
164
+ return "info";
165
+ if (lower.includes("power cycle"))
166
+ return "info";
167
+ if (lower.includes("oem"))
168
+ return "info";
169
+ if (["memory", "power", "fan", "processor"].includes(sensorType))
170
+ return "warning";
171
+ return "info";
172
+ }
173
+ async function collectFanStatus() {
174
+ const output = await run("ipmitool", ["sdr", "type", "Fan"]);
175
+ if (!output)
176
+ return [];
177
+ const fans = [];
178
+ const lines = output.trim().split("\n");
179
+ for (const line of lines) {
180
+ const parts = line.split("|").map((s) => s.trim());
181
+ if (parts.length < 3)
182
+ continue;
183
+ const name = parts[0];
184
+ const fullLine = parts.join(" ");
185
+ let rpm = 0;
186
+ let status = "ok";
187
+ // Search all fields for RPM value (format varies by BMC)
188
+ const rpmMatch = fullLine.match(/(\d+)\s*RPM/i);
189
+ if (rpmMatch) {
190
+ rpm = parseInt(rpmMatch[1]);
191
+ }
192
+ // Check status codes across all fields
193
+ const hasNoReading = fullLine.toLowerCase().includes("no reading");
194
+ const statusCodes = parts.slice(1).map((p) => p.toLowerCase());
195
+ const hasCritical = statusCodes.some((s) => s === "cr" || s === "nr");
196
+ const hasWarning = statusCodes.some((s) => s === "nc");
197
+ const hasAbsent = statusCodes.some((s) => s === "ns") || hasNoReading;
198
+ const hasOk = statusCodes.some((s) => s === "ok");
199
+ if (hasCritical)
200
+ status = "critical";
201
+ else if (hasWarning)
202
+ status = "warning";
203
+ else if (hasAbsent)
204
+ status = "absent";
205
+ else if (hasOk)
206
+ status = "ok";
207
+ else if (rpm === 0 && !hasNoReading)
208
+ status = "critical";
209
+ fans.push({ name, rpm, status });
210
+ }
211
+ return fans;
212
+ }
55
213
  //# sourceMappingURL=ipmi.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"ipmi.js","sourceRoot":"","sources":["../../src/collect/ipmi.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,gBAAgB,CAAC;AAGrC,MAAM,CAAC,KAAK,UAAU,WAAW;IAC/B,MAAM,SAAS,GAAG,MAAM,GAAG,CAAC,UAAU,EAAE,CAAC,QAAQ,CAAC,CAAC,CAAC;IACpD,IAAI,CAAC,SAAS,EAAE,CAAC;QACf,OAAO,EAAE,SAAS,EAAE,KAAK,EAAE,OAAO,EAAE,EAAE,EAAE,UAAU,EAAE,EAAE,WAAW,EAAE,CAAC,EAAE,aAAa,EAAE,CAAC,EAAE,EAAE,iBAAiB,EAAE,CAAC,EAAE,CAAC;IACnH,CAAC;IAED,wBAAwB;IACxB,MAAM,OAAO,GAAwB,EAAE,CAAC;IACxC,KAAK,MAAM,IAAI,IAAI,SAAS,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC;QACzC,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC;QACnD,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC;YAAE,SAAS;QAC/B,MAAM,IAAI,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;QACtB,MAAM,QAAQ,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;QAC1B,MAAM,IAAI,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;QACtB,MAAM,MAAM,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;QAExB,MAAM,QAAQ,GAAG,UAAU,CAAC,QAAQ,CAAC,CAAC;QACtC,MAAM,KAAK,GAAoB,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,QAAQ,CAAC;QAErE,iCAAiC;QACjC,IAAI,aAAiC,CAAC;QACtC,IAAI,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC;YACb,MAAM,EAAE,GAAG,UAAU,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC;YAChC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC;gBAAE,aAAa,GAAG,EAAE,CAAC;QACrC,CAAC;QAED,OAAO,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,IAAI,EAAE,MAAM,EAAE,cAAc,EAAE,aAAa,EAAE,CAAC,CAAC;IAC7E,CAAC;IAED,sCAAsC;IACtC,IAAI,WAAW,GAAG,CAAC,CAAC;IACpB,IAAI,aAAa,GAAG,CAAC,CAAC;IACtB,KAAK,MAAM,MAAM,IAAI,OAAO,EAAE,CAAC;QAC7B,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,WAAW,EAAE,CAAC;QACvC,IAAI,IAAI,CAAC,QAAQ,CAAC,aAAa,CAAC,IAAI,OAAO,MAAM,CAAC,KAAK,KAAK,QAAQ,EAAE,CAAC;YACrE,WAAW,IAAI,MAAM,CAAC,KAAK,CAAC;QAC9B,CAAC;QACD,IAAI,IAAI,CAAC,QAAQ,CAAC,eAAe,CAAC,IAAI,OAAO,MAAM,CAAC,KAAK,KAAK,QAAQ,EAAE,CAAC;YACvE,aAAa,IAAI,MAAM,CAAC,KAAK,CAAC;QAChC,CAAC;IACH,CAAC;IAED,kBAAkB;IAClB,IAAI,QAAQ,GAAG,CAAC,CAAC;IACjB,MAAM,OAAO,GAAG,MAAM,GAAG,CAAC,UAAU,EAAE,CAAC,KAAK,EAAE,MAAM,CAAC,CAAC,CAAC;IACvD,IAAI,OAAO,EAAE,CAAC;QACZ,MAAM,KAAK,GAAG,OAAO,CAAC,KAAK,CAAC,sBAAsB,CAAC,CAAC;QACpD,IAAI,KAAK;YAAE,QAAQ,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IAC/C,CAAC;IAED,OAAO;QACL,SAAS,EAAE,IAAI;QACf,OAAO;QACP,UAAU,EAAE,EAAE,WAAW,EAAE,aAAa,EAAE;QAC1C,iBAAiB,EAAE,QAAQ;KAC5B,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"ipmi.js","sourceRoot":"","sources":["../../src/collect/ipmi.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,39 @@
1
+ export interface SshSecurityStatus {
2
+ permitRootLogin: string;
3
+ passwordAuthentication: string;
4
+ rootPasswordExposed: boolean;
5
+ }
6
+ export interface FirewallStatus {
7
+ active: boolean;
8
+ source: string;
9
+ details: string;
10
+ }
11
+ export interface SecurityUpdateStatus {
12
+ distro: string;
13
+ pendingCount: number;
14
+ available: boolean;
15
+ }
16
+ export interface VulnerabilityStatus {
17
+ name: string;
18
+ status: string;
19
+ mitigated: boolean;
20
+ }
21
+ export interface KernelRebootStatus {
22
+ running: string;
23
+ installed: string;
24
+ needsReboot: boolean;
25
+ }
26
+ export interface AutoUpdateStatus {
27
+ configured: boolean;
28
+ mechanism: string;
29
+ details: string;
30
+ }
31
+ export interface SecurityData {
32
+ ssh: SshSecurityStatus | null;
33
+ firewall: FirewallStatus;
34
+ pending_updates: SecurityUpdateStatus | null;
35
+ kernel_vulns: VulnerabilityStatus[];
36
+ kernel_reboot: KernelRebootStatus | null;
37
+ auto_updates: AutoUpdateStatus;
38
+ }
39
+ export declare function collectSecurity(): Promise<SecurityData>;
@@ -0,0 +1,176 @@
1
+ import { run } from "../lib/exec.js";
2
+ import { readFileSync, existsSync, readdirSync } from "fs";
3
+ export async function collectSecurity() {
4
+ const [ssh, firewall, pendingUpdates, kernelVulns, kernelReboot, autoUpdates] = await Promise.all([
5
+ checkSshConfig(),
6
+ checkFirewall(),
7
+ checkSecurityUpdates(),
8
+ checkKernelVulnerabilities(),
9
+ checkKernelReboot(),
10
+ checkAutoUpdates(),
11
+ ]);
12
+ return { ssh, firewall, pending_updates: pendingUpdates, kernel_vulns: kernelVulns, kernel_reboot: kernelReboot, auto_updates: autoUpdates };
13
+ }
14
+ // === SSH ===
15
+ async function checkSshConfig() {
16
+ // Prefer sshd -T (resolves includes and match blocks)
17
+ const output = await run("sshd", ["-T"], 5000);
18
+ if (output) {
19
+ const getVal = (key) => {
20
+ const line = output.split("\n").find((l) => l.startsWith(key + " "));
21
+ return line ? line.split(" ")[1].trim() : "";
22
+ };
23
+ const permitRootLogin = getVal("permitrootlogin");
24
+ const passwordAuth = getVal("passwordauthentication");
25
+ const rootPasswordExposed = permitRootLogin === "yes" && passwordAuth !== "no";
26
+ return { permitRootLogin, passwordAuthentication: passwordAuth, rootPasswordExposed };
27
+ }
28
+ // Fallback: parse sshd_config directly
29
+ try {
30
+ const config = readFileSync("/etc/ssh/sshd_config", "utf-8");
31
+ const lines = config.split("\n").map((l) => l.trim()).filter((l) => l && !l.startsWith("#"));
32
+ const find = (key) => {
33
+ const line = lines.find((l) => l.toLowerCase().startsWith(key.toLowerCase()));
34
+ return line ? line.split(/\s+/)[1] : null;
35
+ };
36
+ const permitRootLogin = find("PermitRootLogin") || "prohibit-password";
37
+ const passwordAuth = find("PasswordAuthentication") || "yes";
38
+ const rootPasswordExposed = permitRootLogin.toLowerCase() === "yes" && passwordAuth.toLowerCase() !== "no";
39
+ return { permitRootLogin, passwordAuthentication: passwordAuth, rootPasswordExposed };
40
+ }
41
+ catch {
42
+ return null;
43
+ }
44
+ }
45
+ // === Firewall ===
46
+ async function checkFirewall() {
47
+ // UFW
48
+ const ufw = await run("ufw", ["status"], 5000);
49
+ if (ufw && ufw.includes("Status: active")) {
50
+ return { active: true, source: "ufw", details: "UFW is active" };
51
+ }
52
+ // firewalld
53
+ const fwd = await run("firewall-cmd", ["--state"], 5000);
54
+ if (fwd && fwd.trim() === "running") {
55
+ return { active: true, source: "firewalld", details: "firewalld is running" };
56
+ }
57
+ // nftables
58
+ const nft = await run("nft", ["list", "ruleset"], 5000);
59
+ if (nft) {
60
+ const ruleLines = nft.split("\n").filter((l) => l.trim().match(/^\s*(meta|ip |ip6 |tcp |udp |ct |drop|reject|accept)/));
61
+ if (ruleLines.length > 0) {
62
+ return { active: true, source: "nftables", details: `${ruleLines.length} nftables rules` };
63
+ }
64
+ }
65
+ // iptables
66
+ const ipt = await run("iptables", ["-L", "-n"], 5000);
67
+ if (ipt) {
68
+ const lines = ipt.split("\n").filter((l) => l.trim() && !l.startsWith("Chain ") && !l.startsWith("target "));
69
+ if (lines.length > 0)
70
+ return { active: true, source: "iptables", details: `${lines.length} iptables rules` };
71
+ if (ipt.includes("policy DROP") || ipt.includes("policy REJECT")) {
72
+ return { active: true, source: "iptables", details: "Default policy is DROP/REJECT" };
73
+ }
74
+ }
75
+ return { active: false, source: "none", details: "No firewall detected" };
76
+ }
77
+ // === Pending Security Updates ===
78
+ async function checkSecurityUpdates() {
79
+ let osRelease = "";
80
+ try {
81
+ osRelease = readFileSync("/etc/os-release", "utf-8").toLowerCase();
82
+ }
83
+ catch {
84
+ return null;
85
+ }
86
+ if (osRelease.includes("debian") || osRelease.includes("ubuntu") || osRelease.includes("mint")) {
87
+ const output = await run("bash", ["-c", 'apt list --upgradable 2>/dev/null | grep -i "security" | wc -l'], 30000);
88
+ if (output) {
89
+ const count = parseInt(output.trim()) || 0;
90
+ return { distro: osRelease.includes("ubuntu") ? "ubuntu" : "debian", pendingCount: count, available: true };
91
+ }
92
+ return { distro: "debian", pendingCount: 0, available: false };
93
+ }
94
+ if (osRelease.includes("rhel") || osRelease.includes("rocky") || osRelease.includes("alma") || osRelease.includes("fedora") || osRelease.includes("centos")) {
95
+ const cmd = existsSync("/usr/bin/dnf") ? "dnf" : "yum";
96
+ const output = await run("bash", ["-c", `${cmd} updateinfo list security --available 2>/dev/null | grep -c "/"`], 60000);
97
+ if (output) {
98
+ const count = parseInt(output.trim()) || 0;
99
+ const distro = osRelease.includes("rocky") ? "rocky" : osRelease.includes("alma") ? "alma" : osRelease.includes("fedora") ? "fedora" : "rhel";
100
+ return { distro, pendingCount: count, available: true };
101
+ }
102
+ return { distro: "rhel", pendingCount: 0, available: false };
103
+ }
104
+ return null;
105
+ }
106
+ // === Kernel Vulnerabilities ===
107
+ function checkKernelVulnerabilities() {
108
+ const vulnDir = "/sys/devices/system/cpu/vulnerabilities";
109
+ if (!existsSync(vulnDir))
110
+ return [];
111
+ try {
112
+ const files = readdirSync(vulnDir);
113
+ return files.map((file) => {
114
+ try {
115
+ const status = readFileSync(`${vulnDir}/${file}`, "utf-8").trim();
116
+ const mitigated = status.startsWith("Not affected") || status.startsWith("Mitigation:");
117
+ return { name: file, status, mitigated };
118
+ }
119
+ catch {
120
+ return { name: file, status: "unknown", mitigated: true };
121
+ }
122
+ });
123
+ }
124
+ catch {
125
+ return [];
126
+ }
127
+ }
128
+ // === Kernel Reboot ===
129
+ async function checkKernelReboot() {
130
+ const running = (await run("uname", ["-r"]))?.trim();
131
+ if (!running)
132
+ return null;
133
+ // Method 1: reboot-required flag (Debian/Ubuntu)
134
+ if (existsSync("/var/run/reboot-required")) {
135
+ const installed = (await run("bash", ["-c", 'dpkg -l "linux-image-*" 2>/dev/null | grep "^ii" | awk \'{print $2}\' | sort -V | tail -1 | sed "s/linux-image-//"']))?.trim() || "unknown";
136
+ return { running, installed, needsReboot: true };
137
+ }
138
+ // Method 2: Compare packages (Debian/Ubuntu)
139
+ const debPkg = (await run("bash", ["-c", 'dpkg -l "linux-image-*" 2>/dev/null | grep "^ii" | awk \'{print $2}\' | grep -v "linux-image-generic" | sed "s/linux-image-//" | sort -V | tail -1']))?.trim();
140
+ if (debPkg) {
141
+ return { running, installed: debPkg, needsReboot: debPkg !== running };
142
+ }
143
+ // Method 3: RPM-based
144
+ const rpmPkg = (await run("bash", ["-c", 'rpm -q kernel --queryformat "%{VERSION}-%{RELEASE}.%{ARCH}\\n" 2>/dev/null | sort -V | tail -1']))?.trim();
145
+ if (rpmPkg) {
146
+ return { running, installed: rpmPkg, needsReboot: rpmPkg !== running };
147
+ }
148
+ return null;
149
+ }
150
+ // === Auto Updates ===
151
+ async function checkAutoUpdates() {
152
+ // Debian/Ubuntu: unattended-upgrades
153
+ const uuInstalled = await run("bash", ["-c", 'dpkg -l unattended-upgrades 2>/dev/null | grep "^ii"'], 5000);
154
+ if (uuInstalled) {
155
+ const autoConf = "/etc/apt/apt.conf.d/20auto-upgrades";
156
+ if (existsSync(autoConf)) {
157
+ const content = readFileSync(autoConf, "utf-8");
158
+ if (content.includes('Update-Package-Lists "1"') && content.includes('Unattended-Upgrade "1"')) {
159
+ return { configured: true, mechanism: "unattended-upgrades", details: "Installed and enabled" };
160
+ }
161
+ return { configured: false, mechanism: "unattended-upgrades", details: "Installed but not enabled in 20auto-upgrades" };
162
+ }
163
+ return { configured: false, mechanism: "unattended-upgrades", details: "Installed but missing 20auto-upgrades config" };
164
+ }
165
+ // RHEL/Rocky/Alma: dnf-automatic
166
+ const dnfAuto = await run("bash", ["-c", "rpm -q dnf-automatic 2>/dev/null"], 5000);
167
+ if (dnfAuto && !dnfAuto.includes("not installed")) {
168
+ const timerActive = await run("bash", ["-c", "systemctl is-enabled dnf-automatic-install.timer 2>/dev/null || systemctl is-enabled dnf-automatic.timer 2>/dev/null"], 5000);
169
+ if (timerActive && timerActive.includes("enabled")) {
170
+ return { configured: true, mechanism: "dnf-automatic", details: "Installed and timer enabled" };
171
+ }
172
+ return { configured: false, mechanism: "dnf-automatic", details: "Installed but timer not enabled" };
173
+ }
174
+ return { configured: false, mechanism: "none", details: "No automatic security update mechanism detected" };
175
+ }
176
+ //# sourceMappingURL=security.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"security.js","sourceRoot":"","sources":["../../src/collect/security.ts"],"names":[],"mappings":"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"}
package/dist/config.d.ts CHANGED
@@ -18,14 +18,17 @@ declare const ConfigSchema: z.ZodObject<{
18
18
  enabled: z.ZodDefault<z.ZodBoolean>;
19
19
  url: z.ZodDefault<z.ZodString>;
20
20
  api_key: z.ZodDefault<z.ZodString>;
21
+ tls_pin: z.ZodDefault<z.ZodString>;
21
22
  }, "strip", z.ZodTypeAny, {
22
23
  enabled: boolean;
23
24
  url: string;
24
25
  api_key: string;
26
+ tls_pin: string;
25
27
  }, {
26
28
  enabled?: boolean | undefined;
27
29
  url?: string | undefined;
28
30
  api_key?: string | undefined;
31
+ tls_pin?: string | undefined;
29
32
  }>>;
30
33
  thresholds: z.ZodDefault<z.ZodObject<{
31
34
  ram_percent: z.ZodDefault<z.ZodNumber>;
@@ -124,6 +127,16 @@ declare const ConfigSchema: z.ZodObject<{
124
127
  webhook_url?: string | undefined;
125
128
  } | undefined;
126
129
  }>>;
130
+ prometheus: z.ZodDefault<z.ZodObject<{
131
+ enabled: z.ZodDefault<z.ZodBoolean>;
132
+ port: z.ZodDefault<z.ZodNumber>;
133
+ }, "strip", z.ZodTypeAny, {
134
+ enabled: boolean;
135
+ port: number;
136
+ }, {
137
+ enabled?: boolean | undefined;
138
+ port?: number | undefined;
139
+ }>>;
127
140
  }, "strip", z.ZodTypeAny, {
128
141
  server_name: string;
129
142
  collection: {
@@ -135,6 +148,7 @@ declare const ConfigSchema: z.ZodObject<{
135
148
  enabled: boolean;
136
149
  url: string;
137
150
  api_key: string;
151
+ tls_pin: string;
138
152
  };
139
153
  thresholds: {
140
154
  ram_percent: number;
@@ -163,6 +177,10 @@ declare const ConfigSchema: z.ZodObject<{
163
177
  webhook_url: string;
164
178
  };
165
179
  };
180
+ prometheus: {
181
+ enabled: boolean;
182
+ port: number;
183
+ };
166
184
  }, {
167
185
  server_name?: string | undefined;
168
186
  collection?: {
@@ -174,6 +192,7 @@ declare const ConfigSchema: z.ZodObject<{
174
192
  enabled?: boolean | undefined;
175
193
  url?: string | undefined;
176
194
  api_key?: string | undefined;
195
+ tls_pin?: string | undefined;
177
196
  } | undefined;
178
197
  thresholds?: {
179
198
  ram_percent?: number | undefined;
@@ -202,6 +221,10 @@ declare const ConfigSchema: z.ZodObject<{
202
221
  webhook_url?: string | undefined;
203
222
  } | undefined;
204
223
  } | undefined;
224
+ prometheus?: {
225
+ enabled?: boolean | undefined;
226
+ port?: number | undefined;
227
+ } | undefined;
205
228
  }>;
206
229
  export type Config = z.infer<typeof ConfigSchema>;
207
230
  export declare function loadConfig(path: string): Config;
package/dist/config.js CHANGED
@@ -12,6 +12,7 @@ const ConfigSchema = z.object({
12
12
  enabled: z.boolean().default(false),
13
13
  url: z.string().default("https://forge.glassmkr.com"),
14
14
  api_key: z.string().default(""),
15
+ tls_pin: z.string().default(""),
15
16
  }).default({}),
16
17
  thresholds: z.object({
17
18
  ram_percent: z.number().default(90),
@@ -40,6 +41,10 @@ const ConfigSchema = z.object({
40
41
  webhook_url: z.string().default(""),
41
42
  }).default({}),
42
43
  }).default({}),
44
+ prometheus: z.object({
45
+ enabled: z.boolean().default(false),
46
+ port: z.number().default(9101),
47
+ }).default({}),
43
48
  });
44
49
  export function loadConfig(path) {
45
50
  try {
@@ -1 +1 @@
1
- {"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"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"}
package/dist/index.js CHANGED
@@ -1,5 +1,20 @@
1
1
  #!/usr/bin/env node
2
+ import { readFileSync } from "node:fs";
3
+ import { fileURLToPath } from "node:url";
4
+ import { dirname, join } from "node:path";
2
5
  import { loadConfig } from "./config.js";
6
+ const __dirname = dirname(fileURLToPath(import.meta.url));
7
+ const PKG_VERSION = (() => {
8
+ try {
9
+ const pkg = JSON.parse(readFileSync(join(__dirname, "..", "package.json"), "utf8"));
10
+ return pkg.version || "0.0.0";
11
+ }
12
+ catch {
13
+ return "0.0.0";
14
+ }
15
+ })();
16
+ import { checkForUpdates } from "./lib/version-check.js";
17
+ import { startMetricsServer, updateMetrics } from "./metrics-server.js";
3
18
  import { collectSystem } from "./collect/system.js";
4
19
  import { collectCpu } from "./collect/cpu.js";
5
20
  import { collectMemory } from "./collect/memory.js";
@@ -14,13 +29,27 @@ import { updateAlertState } from "./alerts/state.js";
14
29
  import { sendTelegram } from "./notify/telegram.js";
15
30
  import { sendSlack } from "./notify/slack.js";
16
31
  import { sendEmail } from "./notify/email.js";
17
- import { pushToForge } from "./push/forge.js";
32
+ import { pushToForge, initForgeAgent } from "./push/forge.js";
33
+ import { collectSecurity } from "./collect/security.js";
18
34
  const configPath = process.argv[2] || "/etc/glassmkr/collector.yaml";
19
35
  const config = loadConfig(configPath);
20
36
  console.log(`[collector] Starting. Server: ${config.server_name}. Interval: ${config.collection.interval_seconds}s`);
21
37
  console.log(`[collector] IPMI: ${config.collection.ipmi ? "enabled" : "disabled"}, SMART: ${config.collection.smart ? "enabled" : "disabled"}`);
22
38
  console.log(`[collector] Forge: ${config.forge.enabled ? config.forge.url : "disabled"}`);
23
- const emptyIpmi = { available: false, sensors: [], ecc_errors: { correctable: 0, uncorrectable: 0 }, sel_entries_count: 0 };
39
+ console.log(`[collector] Prometheus: ${config.prometheus.enabled ? `:${config.prometheus.port}/metrics` : "disabled"}`);
40
+ // Start Prometheus metrics server if enabled
41
+ if (config.prometheus.enabled) {
42
+ startMetricsServer(config.prometheus.port);
43
+ }
44
+ // Initialize TLS pinning for Forge if configured
45
+ if (config.forge.tls_pin) {
46
+ initForgeAgent(config.forge.tls_pin);
47
+ console.log("[collector] TLS pinning enabled for Forge");
48
+ }
49
+ const emptyIpmi = { available: false, sensors: [], ecc_errors: { correctable: 0, uncorrectable: 0 }, sel_entries_count: 0, sel_events_recent: [], fans: [] };
50
+ // Security checks run once per hour (every 12th cycle at 5-min intervals)
51
+ let securityCycleCount = 0;
52
+ let cachedSecurity;
24
53
  async function collect() {
25
54
  const startTime = Date.now();
26
55
  console.log(`[collector] Collecting...`);
@@ -35,11 +64,25 @@ async function collect() {
35
64
  config.collection.ipmi ? collectIpmi() : Promise.resolve(emptyIpmi),
36
65
  collectOsAlerts(),
37
66
  ]);
67
+ // Security checks: run once per hour, reuse cached data between runs
68
+ securityCycleCount++;
69
+ if (securityCycleCount >= 12 || !cachedSecurity) {
70
+ securityCycleCount = 0;
71
+ try {
72
+ cachedSecurity = await collectSecurity();
73
+ }
74
+ catch (err) {
75
+ console.error("[security] Collection error:", err);
76
+ }
77
+ }
38
78
  const snapshot = {
39
- collector_version: "0.1.0",
79
+ collector_version: PKG_VERSION,
40
80
  timestamp: new Date().toISOString(),
41
81
  system, cpu, memory, disks, smart, network, raid, ipmi, os_alerts: osAlerts,
82
+ security: cachedSecurity,
42
83
  };
84
+ // Update Prometheus metrics
85
+ updateMetrics(snapshot);
43
86
  // Evaluate alerts
44
87
  const alertResults = evaluateAlerts(snapshot, config.thresholds);
45
88
  const { newAlerts, resolvedAlerts } = updateAlertState(alertResults);
@@ -61,6 +104,8 @@ async function collect() {
61
104
  if (config.forge.enabled && config.forge.api_key) {
62
105
  pushToForge(config.forge.url, config.forge.api_key, snapshot);
63
106
  }
107
+ // Check for updates (every 6 hours, non-blocking)
108
+ checkForUpdates(config.forge.enabled ? config.forge.url : undefined);
64
109
  // Print summary on first run
65
110
  if (firstRun) {
66
111
  firstRun = false;