@panguard-ai/core 0.1.0
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.
- package/dist/adapters/adapter-registry.d.ts +150 -0
- package/dist/adapters/adapter-registry.d.ts.map +1 -0
- package/dist/adapters/adapter-registry.js +271 -0
- package/dist/adapters/adapter-registry.js.map +1 -0
- package/dist/adapters/base-adapter.d.ts +101 -0
- package/dist/adapters/base-adapter.d.ts.map +1 -0
- package/dist/adapters/base-adapter.js +160 -0
- package/dist/adapters/base-adapter.js.map +1 -0
- package/dist/adapters/defender-adapter.d.ts +90 -0
- package/dist/adapters/defender-adapter.d.ts.map +1 -0
- package/dist/adapters/defender-adapter.js +227 -0
- package/dist/adapters/defender-adapter.js.map +1 -0
- package/dist/adapters/index.d.ts +22 -0
- package/dist/adapters/index.d.ts.map +1 -0
- package/dist/adapters/index.js +23 -0
- package/dist/adapters/index.js.map +1 -0
- package/dist/adapters/syslog-adapter.d.ts +207 -0
- package/dist/adapters/syslog-adapter.d.ts.map +1 -0
- package/dist/adapters/syslog-adapter.js +432 -0
- package/dist/adapters/syslog-adapter.js.map +1 -0
- package/dist/adapters/types.d.ts +135 -0
- package/dist/adapters/types.d.ts.map +1 -0
- package/dist/adapters/types.js +13 -0
- package/dist/adapters/types.js.map +1 -0
- package/dist/adapters/wazuh-adapter.d.ts +120 -0
- package/dist/adapters/wazuh-adapter.d.ts.map +1 -0
- package/dist/adapters/wazuh-adapter.js +266 -0
- package/dist/adapters/wazuh-adapter.js.map +1 -0
- package/dist/ai/claude-provider.d.ts +66 -0
- package/dist/ai/claude-provider.d.ts.map +1 -0
- package/dist/ai/claude-provider.js +166 -0
- package/dist/ai/claude-provider.js.map +1 -0
- package/dist/ai/funnel-router.d.ts +75 -0
- package/dist/ai/funnel-router.d.ts.map +1 -0
- package/dist/ai/funnel-router.js +173 -0
- package/dist/ai/funnel-router.js.map +1 -0
- package/dist/ai/index.d.ts +77 -0
- package/dist/ai/index.d.ts.map +1 -0
- package/dist/ai/index.js +95 -0
- package/dist/ai/index.js.map +1 -0
- package/dist/ai/ollama-provider.d.ts +73 -0
- package/dist/ai/ollama-provider.d.ts.map +1 -0
- package/dist/ai/ollama-provider.js +200 -0
- package/dist/ai/ollama-provider.js.map +1 -0
- package/dist/ai/openai-provider.d.ts +70 -0
- package/dist/ai/openai-provider.d.ts.map +1 -0
- package/dist/ai/openai-provider.js +175 -0
- package/dist/ai/openai-provider.js.map +1 -0
- package/dist/ai/prompts/event-classifier.d.ts +25 -0
- package/dist/ai/prompts/event-classifier.d.ts.map +1 -0
- package/dist/ai/prompts/event-classifier.js +94 -0
- package/dist/ai/prompts/event-classifier.js.map +1 -0
- package/dist/ai/prompts/index.d.ts +13 -0
- package/dist/ai/prompts/index.d.ts.map +1 -0
- package/dist/ai/prompts/index.js +13 -0
- package/dist/ai/prompts/index.js.map +1 -0
- package/dist/ai/prompts/report-generator.d.ts +25 -0
- package/dist/ai/prompts/report-generator.d.ts.map +1 -0
- package/dist/ai/prompts/report-generator.js +131 -0
- package/dist/ai/prompts/report-generator.js.map +1 -0
- package/dist/ai/prompts/threat-analyzer.d.ts +26 -0
- package/dist/ai/prompts/threat-analyzer.d.ts.map +1 -0
- package/dist/ai/prompts/threat-analyzer.js +75 -0
- package/dist/ai/prompts/threat-analyzer.js.map +1 -0
- package/dist/ai/provider-base.d.ts +100 -0
- package/dist/ai/provider-base.d.ts.map +1 -0
- package/dist/ai/provider-base.js +166 -0
- package/dist/ai/provider-base.js.map +1 -0
- package/dist/ai/response-parser.d.ts +36 -0
- package/dist/ai/response-parser.d.ts.map +1 -0
- package/dist/ai/response-parser.js +195 -0
- package/dist/ai/response-parser.js.map +1 -0
- package/dist/ai/token-tracker.d.ts +72 -0
- package/dist/ai/token-tracker.d.ts.map +1 -0
- package/dist/ai/token-tracker.js +145 -0
- package/dist/ai/token-tracker.js.map +1 -0
- package/dist/ai/types.d.ts +138 -0
- package/dist/ai/types.d.ts.map +1 -0
- package/dist/ai/types.js +12 -0
- package/dist/ai/types.js.map +1 -0
- package/dist/cli/index.d.ts +146 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +515 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/cli/prompts.d.ts +58 -0
- package/dist/cli/prompts.d.ts.map +1 -0
- package/dist/cli/prompts.js +327 -0
- package/dist/cli/prompts.js.map +1 -0
- package/dist/cli/wizard.d.ts +58 -0
- package/dist/cli/wizard.d.ts.map +1 -0
- package/dist/cli/wizard.js +200 -0
- package/dist/cli/wizard.js.map +1 -0
- package/dist/discovery/firewall-checker.d.ts +28 -0
- package/dist/discovery/firewall-checker.d.ts.map +1 -0
- package/dist/discovery/firewall-checker.js +379 -0
- package/dist/discovery/firewall-checker.js.map +1 -0
- package/dist/discovery/index.d.ts +23 -0
- package/dist/discovery/index.d.ts.map +1 -0
- package/dist/discovery/index.js +29 -0
- package/dist/discovery/index.js.map +1 -0
- package/dist/discovery/network-scanner.d.ts +60 -0
- package/dist/discovery/network-scanner.d.ts.map +1 -0
- package/dist/discovery/network-scanner.js +640 -0
- package/dist/discovery/network-scanner.js.map +1 -0
- package/dist/discovery/os-detector.d.ts +24 -0
- package/dist/discovery/os-detector.d.ts.map +1 -0
- package/dist/discovery/os-detector.js +253 -0
- package/dist/discovery/os-detector.js.map +1 -0
- package/dist/discovery/osquery-provider.d.ts +127 -0
- package/dist/discovery/osquery-provider.d.ts.map +1 -0
- package/dist/discovery/osquery-provider.js +214 -0
- package/dist/discovery/osquery-provider.js.map +1 -0
- package/dist/discovery/risk-scorer.d.ts +66 -0
- package/dist/discovery/risk-scorer.d.ts.map +1 -0
- package/dist/discovery/risk-scorer.js +294 -0
- package/dist/discovery/risk-scorer.js.map +1 -0
- package/dist/discovery/security-tools.d.ts +31 -0
- package/dist/discovery/security-tools.d.ts.map +1 -0
- package/dist/discovery/security-tools.js +346 -0
- package/dist/discovery/security-tools.js.map +1 -0
- package/dist/discovery/service-detector.d.ts +28 -0
- package/dist/discovery/service-detector.d.ts.map +1 -0
- package/dist/discovery/service-detector.js +300 -0
- package/dist/discovery/service-detector.js.map +1 -0
- package/dist/discovery/types.d.ts +502 -0
- package/dist/discovery/types.d.ts.map +1 -0
- package/dist/discovery/types.js +12 -0
- package/dist/discovery/types.js.map +1 -0
- package/dist/discovery/user-auditor.d.ts +28 -0
- package/dist/discovery/user-auditor.d.ts.map +1 -0
- package/dist/discovery/user-auditor.js +385 -0
- package/dist/discovery/user-auditor.js.map +1 -0
- package/dist/i18n/config.d.ts +45 -0
- package/dist/i18n/config.d.ts.map +1 -0
- package/dist/i18n/config.js +135 -0
- package/dist/i18n/config.js.map +1 -0
- package/dist/i18n/index.d.ts +8 -0
- package/dist/i18n/index.d.ts.map +1 -0
- package/dist/i18n/index.js +8 -0
- package/dist/i18n/index.js.map +1 -0
- package/dist/index.d.ts +31 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +31 -0
- package/dist/index.js.map +1 -0
- package/dist/monitor/event-normalizer.d.ts +102 -0
- package/dist/monitor/event-normalizer.d.ts.map +1 -0
- package/dist/monitor/event-normalizer.js +195 -0
- package/dist/monitor/event-normalizer.js.map +1 -0
- package/dist/monitor/file-monitor.d.ts +90 -0
- package/dist/monitor/file-monitor.d.ts.map +1 -0
- package/dist/monitor/file-monitor.js +222 -0
- package/dist/monitor/file-monitor.js.map +1 -0
- package/dist/monitor/index.d.ts +147 -0
- package/dist/monitor/index.d.ts.map +1 -0
- package/dist/monitor/index.js +293 -0
- package/dist/monitor/index.js.map +1 -0
- package/dist/monitor/log-monitor.d.ts +102 -0
- package/dist/monitor/log-monitor.d.ts.map +1 -0
- package/dist/monitor/log-monitor.js +245 -0
- package/dist/monitor/log-monitor.js.map +1 -0
- package/dist/monitor/network-monitor.d.ts +103 -0
- package/dist/monitor/network-monitor.d.ts.map +1 -0
- package/dist/monitor/network-monitor.js +336 -0
- package/dist/monitor/network-monitor.js.map +1 -0
- package/dist/monitor/process-monitor.d.ts +108 -0
- package/dist/monitor/process-monitor.d.ts.map +1 -0
- package/dist/monitor/process-monitor.js +245 -0
- package/dist/monitor/process-monitor.js.map +1 -0
- package/dist/monitor/threat-intel-feeds.d.ts +141 -0
- package/dist/monitor/threat-intel-feeds.d.ts.map +1 -0
- package/dist/monitor/threat-intel-feeds.js +430 -0
- package/dist/monitor/threat-intel-feeds.js.map +1 -0
- package/dist/monitor/threat-intel.d.ts +83 -0
- package/dist/monitor/threat-intel.d.ts.map +1 -0
- package/dist/monitor/threat-intel.js +215 -0
- package/dist/monitor/threat-intel.js.map +1 -0
- package/dist/monitor/types.d.ts +65 -0
- package/dist/monitor/types.d.ts.map +1 -0
- package/dist/monitor/types.js +20 -0
- package/dist/monitor/types.js.map +1 -0
- package/dist/rules/index.d.ts +115 -0
- package/dist/rules/index.d.ts.map +1 -0
- package/dist/rules/index.js +244 -0
- package/dist/rules/index.js.map +1 -0
- package/dist/rules/rule-loader.d.ts +54 -0
- package/dist/rules/rule-loader.d.ts.map +1 -0
- package/dist/rules/rule-loader.js +167 -0
- package/dist/rules/rule-loader.js.map +1 -0
- package/dist/rules/sigma-matcher.d.ts +40 -0
- package/dist/rules/sigma-matcher.d.ts.map +1 -0
- package/dist/rules/sigma-matcher.js +447 -0
- package/dist/rules/sigma-matcher.js.map +1 -0
- package/dist/rules/sigma-parser.d.ts +36 -0
- package/dist/rules/sigma-parser.d.ts.map +1 -0
- package/dist/rules/sigma-parser.js +180 -0
- package/dist/rules/sigma-parser.js.map +1 -0
- package/dist/rules/types.d.ts +112 -0
- package/dist/rules/types.d.ts.map +1 -0
- package/dist/rules/types.js +11 -0
- package/dist/rules/types.js.map +1 -0
- package/dist/rules/yara-scanner.d.ts +103 -0
- package/dist/rules/yara-scanner.d.ts.map +1 -0
- package/dist/rules/yara-scanner.js +421 -0
- package/dist/rules/yara-scanner.js.map +1 -0
- package/dist/scoring/achievements.d.ts +76 -0
- package/dist/scoring/achievements.d.ts.map +1 -0
- package/dist/scoring/achievements.js +211 -0
- package/dist/scoring/achievements.js.map +1 -0
- package/dist/scoring/index.d.ts +3 -0
- package/dist/scoring/index.d.ts.map +1 -0
- package/dist/scoring/index.js +3 -0
- package/dist/scoring/index.js.map +1 -0
- package/dist/scoring/security-score.d.ts +60 -0
- package/dist/scoring/security-score.d.ts.map +1 -0
- package/dist/scoring/security-score.js +211 -0
- package/dist/scoring/security-score.js.map +1 -0
- package/dist/types.d.ts +71 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +8 -0
- package/dist/types.js.map +1 -0
- package/dist/utils/index.d.ts +10 -0
- package/dist/utils/index.d.ts.map +1 -0
- package/dist/utils/index.js +9 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/utils/logger.d.ts +38 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/logger.js +71 -0
- package/dist/utils/logger.js.map +1 -0
- package/dist/utils/validation.d.ts +35 -0
- package/dist/utils/validation.d.ts.map +1 -0
- package/dist/utils/validation.js +56 -0
- package/dist/utils/validation.js.map +1 -0
- package/package.json +60 -0
|
@@ -0,0 +1,215 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Threat intelligence matching for known malicious IP addresses
|
|
3
|
+
* 已知惡意 IP 位址的威脅情報比對
|
|
4
|
+
*
|
|
5
|
+
* Provides a built-in threat intelligence database for MVP and supports
|
|
6
|
+
* CIDR range matching for efficient IP lookups.
|
|
7
|
+
* 為 MVP 提供內建威脅情報資料庫,並支援 CIDR 範圍比對以進行高效 IP 查詢。
|
|
8
|
+
*
|
|
9
|
+
* @module @panguard-ai/core/monitor/threat-intel
|
|
10
|
+
*/
|
|
11
|
+
/** Optional live feed manager (set by GuardEngine at startup) */
|
|
12
|
+
let feedManager = null;
|
|
13
|
+
/**
|
|
14
|
+
* Register a live feed manager for real-time threat intel lookups.
|
|
15
|
+
* When set, `checkThreatIntel()` queries the feed manager first,
|
|
16
|
+
* then falls back to the hardcoded list.
|
|
17
|
+
*/
|
|
18
|
+
export function setFeedManager(manager) {
|
|
19
|
+
feedManager = manager;
|
|
20
|
+
}
|
|
21
|
+
/** Get the currently registered feed manager (for tests/status). */
|
|
22
|
+
export function getFeedManager() {
|
|
23
|
+
return feedManager;
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Built-in known malicious IP ranges for MVP
|
|
27
|
+
* MVP 用的內建已知惡意 IP 範圍
|
|
28
|
+
*
|
|
29
|
+
* These are well-known scanner, C2, and botnet IP ranges sourced from
|
|
30
|
+
* public threat intelligence feeds. Uses CIDR notation for range matching.
|
|
31
|
+
* 這些是來自公開威脅情報來源的知名掃描器、C2 和殭屍網路 IP 範圍,
|
|
32
|
+
* 使用 CIDR 表示法進行範圍比對。
|
|
33
|
+
*/
|
|
34
|
+
const KNOWN_MALICIOUS_IPS = [
|
|
35
|
+
// Tor exit node ranges (commonly used for scanning)
|
|
36
|
+
// Tor 出口節點範圍(常用於掃描)
|
|
37
|
+
{ ip: '185.220.101.0/24', type: 'scanner', source: 'tor-exit-nodes' },
|
|
38
|
+
{ ip: '185.220.102.0/24', type: 'scanner', source: 'tor-exit-nodes' },
|
|
39
|
+
// Known scanner infrastructure / 已知掃描器基礎設施
|
|
40
|
+
{ ip: '89.248.167.0/24', type: 'scanner', source: 'recyber' },
|
|
41
|
+
{ ip: '198.235.24.0/24', type: 'scanner', source: 'shadowserver' },
|
|
42
|
+
{ ip: '71.6.135.0/24', type: 'scanner', source: 'censys' },
|
|
43
|
+
// Known C2 infrastructure (fictional but realistic for safety)
|
|
44
|
+
// 已知 C2 基礎設施(出於安全考量使用虛構但寫實的 IP)
|
|
45
|
+
{ ip: '203.0.113.0/24', type: 'c2', source: 'abuse-ch', lastSeen: '2025-01-15' },
|
|
46
|
+
{ ip: '198.51.100.0/24', type: 'c2', source: 'abuse-ch', lastSeen: '2025-02-01' },
|
|
47
|
+
// Known botnet infrastructure / 已知殭屍網路基礎設施
|
|
48
|
+
{ ip: '192.0.2.0/24', type: 'botnet', source: 'spamhaus', lastSeen: '2025-01-20' },
|
|
49
|
+
{ ip: '100.64.0.0/16', type: 'botnet', source: 'emerging-threats', lastSeen: '2025-01-10' },
|
|
50
|
+
// Known malware distribution / 已知惡意軟體散布
|
|
51
|
+
{ ip: '233.252.0.0/24', type: 'malware', source: 'malwaredomainlist', lastSeen: '2025-03-01' },
|
|
52
|
+
];
|
|
53
|
+
/**
|
|
54
|
+
* Mutable threat intelligence entries list
|
|
55
|
+
* 可變的威脅情報條目列表
|
|
56
|
+
*/
|
|
57
|
+
const threatIntelEntries = [...KNOWN_MALICIOUS_IPS];
|
|
58
|
+
/**
|
|
59
|
+
* Parse a CIDR notation string into network address (as 32-bit integer) and mask
|
|
60
|
+
* 將 CIDR 表示法字串解析為網路位址(32 位元整數)和遮罩
|
|
61
|
+
*
|
|
62
|
+
* @param cidr - CIDR notation string (e.g., "192.168.1.0/24") / CIDR 表示法字串
|
|
63
|
+
* @returns Object with network and mask values / 包含網路和遮罩值的物件
|
|
64
|
+
*/
|
|
65
|
+
function parseCIDR(cidr) {
|
|
66
|
+
const parts = cidr.split('/');
|
|
67
|
+
const ipStr = parts[0];
|
|
68
|
+
const prefixLen = parseInt(parts[1] ?? '32', 10);
|
|
69
|
+
if (!ipStr || isNaN(prefixLen) || prefixLen < 0 || prefixLen > 32) {
|
|
70
|
+
return null;
|
|
71
|
+
}
|
|
72
|
+
const ipNum = ipToNumber(ipStr);
|
|
73
|
+
if (ipNum === null)
|
|
74
|
+
return null;
|
|
75
|
+
// Create mask: e.g., /24 -> 0xFFFFFF00
|
|
76
|
+
// 建立遮罩:例如 /24 -> 0xFFFFFF00
|
|
77
|
+
const mask = prefixLen === 0 ? 0 : (~0 << (32 - prefixLen)) >>> 0;
|
|
78
|
+
const network = (ipNum & mask) >>> 0;
|
|
79
|
+
return { network, mask };
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* Convert an IPv4 address string to a 32-bit unsigned integer
|
|
83
|
+
* 將 IPv4 位址字串轉換為 32 位元無號整數
|
|
84
|
+
*
|
|
85
|
+
* @param ip - IPv4 address string / IPv4 位址字串
|
|
86
|
+
* @returns 32-bit unsigned integer or null if invalid / 32 位元無號整數或無效時為 null
|
|
87
|
+
*/
|
|
88
|
+
function ipToNumber(ip) {
|
|
89
|
+
const parts = ip.split('.');
|
|
90
|
+
if (parts.length !== 4)
|
|
91
|
+
return null;
|
|
92
|
+
let result = 0;
|
|
93
|
+
for (const part of parts) {
|
|
94
|
+
const num = parseInt(part, 10);
|
|
95
|
+
if (isNaN(num) || num < 0 || num > 255)
|
|
96
|
+
return null;
|
|
97
|
+
result = ((result << 8) | num) >>> 0;
|
|
98
|
+
}
|
|
99
|
+
return result;
|
|
100
|
+
}
|
|
101
|
+
/**
|
|
102
|
+
* Check if an IP address matches a CIDR range or exact IP
|
|
103
|
+
* 檢查 IP 位址是否符合 CIDR 範圍或精確 IP
|
|
104
|
+
*
|
|
105
|
+
* @param ip - IP address to check / 要檢查的 IP 位址
|
|
106
|
+
* @param pattern - CIDR pattern or exact IP / CIDR 模式或精確 IP
|
|
107
|
+
* @returns True if the IP matches the pattern / 如果 IP 符合模式則為 true
|
|
108
|
+
*/
|
|
109
|
+
function ipMatchesPattern(ip, pattern) {
|
|
110
|
+
const cidr = parseCIDR(pattern);
|
|
111
|
+
if (!cidr)
|
|
112
|
+
return false;
|
|
113
|
+
const ipNum = ipToNumber(ip);
|
|
114
|
+
if (ipNum === null)
|
|
115
|
+
return false;
|
|
116
|
+
return (ipNum & cidr.mask) >>> 0 === cidr.network;
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* Check if an IP address matches any known threat intelligence entry
|
|
120
|
+
* 檢查 IP 位址是否符合任何已知的威脅情報條目
|
|
121
|
+
*
|
|
122
|
+
* @param ip - IPv4 address to check / 要檢查的 IPv4 位址
|
|
123
|
+
* @returns Matching ThreatIntelEntry or null / 符合的 ThreatIntelEntry 或 null
|
|
124
|
+
*
|
|
125
|
+
* @example
|
|
126
|
+
* ```typescript
|
|
127
|
+
* const threat = checkThreatIntel('185.220.101.42');
|
|
128
|
+
* if (threat) {
|
|
129
|
+
* console.log(`Matched: ${threat.type} from ${threat.source}`);
|
|
130
|
+
* }
|
|
131
|
+
* ```
|
|
132
|
+
*/
|
|
133
|
+
export function checkThreatIntel(ip) {
|
|
134
|
+
// Check live feed manager first (if registered)
|
|
135
|
+
if (feedManager) {
|
|
136
|
+
const ioc = feedManager.checkIP(ip);
|
|
137
|
+
if (ioc) {
|
|
138
|
+
const entry = feedManager.toThreatIntelEntry(ioc);
|
|
139
|
+
if (entry)
|
|
140
|
+
return entry;
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
// Fall back to hardcoded list
|
|
144
|
+
for (const entry of threatIntelEntries) {
|
|
145
|
+
if (ipMatchesPattern(ip, entry.ip)) {
|
|
146
|
+
return entry;
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
return null;
|
|
150
|
+
}
|
|
151
|
+
/**
|
|
152
|
+
* Check if an IP address is in a private (RFC 1918) range
|
|
153
|
+
* 檢查 IP 位址是否在私有(RFC 1918)範圍內
|
|
154
|
+
*
|
|
155
|
+
* Checks against:
|
|
156
|
+
* 檢查以下範圍:
|
|
157
|
+
* - 10.0.0.0/8
|
|
158
|
+
* - 172.16.0.0/12
|
|
159
|
+
* - 192.168.0.0/16
|
|
160
|
+
* - 127.0.0.0/8 (loopback / 迴路)
|
|
161
|
+
* - 169.254.0.0/16 (link-local / 鏈路本地)
|
|
162
|
+
*
|
|
163
|
+
* @param ip - IPv4 address to check / 要檢查的 IPv4 位址
|
|
164
|
+
* @returns True if the IP is private / 如果 IP 是私有的則為 true
|
|
165
|
+
*
|
|
166
|
+
* @example
|
|
167
|
+
* ```typescript
|
|
168
|
+
* isPrivateIP('192.168.1.1'); // true
|
|
169
|
+
* isPrivateIP('8.8.8.8'); // false
|
|
170
|
+
* ```
|
|
171
|
+
*/
|
|
172
|
+
export function isPrivateIP(ip) {
|
|
173
|
+
const privateRanges = [
|
|
174
|
+
'10.0.0.0/8',
|
|
175
|
+
'172.16.0.0/12',
|
|
176
|
+
'192.168.0.0/16',
|
|
177
|
+
'127.0.0.0/8',
|
|
178
|
+
'169.254.0.0/16',
|
|
179
|
+
];
|
|
180
|
+
for (const range of privateRanges) {
|
|
181
|
+
if (ipMatchesPattern(ip, range)) {
|
|
182
|
+
return true;
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
return false;
|
|
186
|
+
}
|
|
187
|
+
/**
|
|
188
|
+
* Add a new threat intelligence entry to the database
|
|
189
|
+
* 將新的威脅情報條目新增到資料庫
|
|
190
|
+
*
|
|
191
|
+
* @param entry - Threat intelligence entry to add / 要新增的威脅情報條目
|
|
192
|
+
*
|
|
193
|
+
* @example
|
|
194
|
+
* ```typescript
|
|
195
|
+
* addThreatIntelEntry({
|
|
196
|
+
* ip: '10.99.99.0/24',
|
|
197
|
+
* type: 'c2',
|
|
198
|
+
* source: 'custom-feed',
|
|
199
|
+
* lastSeen: '2025-03-15',
|
|
200
|
+
* });
|
|
201
|
+
* ```
|
|
202
|
+
*/
|
|
203
|
+
export function addThreatIntelEntry(entry) {
|
|
204
|
+
threatIntelEntries.push(entry);
|
|
205
|
+
}
|
|
206
|
+
/**
|
|
207
|
+
* Get all current threat intelligence entries
|
|
208
|
+
* 取得所有目前的威脅情報條目
|
|
209
|
+
*
|
|
210
|
+
* @returns Array of all threat intel entries (copy) / 所有威脅情報條目的陣列(複本)
|
|
211
|
+
*/
|
|
212
|
+
export function getThreatIntelEntries() {
|
|
213
|
+
return [...threatIntelEntries];
|
|
214
|
+
}
|
|
215
|
+
//# sourceMappingURL=threat-intel.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"threat-intel.js","sourceRoot":"","sources":["../../src/monitor/threat-intel.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAKH,iEAAiE;AACjE,IAAI,WAAW,GAAkC,IAAI,CAAC;AAEtD;;;;GAIG;AACH,MAAM,UAAU,cAAc,CAAC,OAAsC;IACnE,WAAW,GAAG,OAAO,CAAC;AACxB,CAAC;AAED,oEAAoE;AACpE,MAAM,UAAU,cAAc;IAC5B,OAAO,WAAW,CAAC;AACrB,CAAC;AAED;;;;;;;;GAQG;AACH,MAAM,mBAAmB,GAAuB;IAC9C,oDAAoD;IACpD,oBAAoB;IACpB,EAAE,EAAE,EAAE,kBAAkB,EAAE,IAAI,EAAE,SAAS,EAAE,MAAM,EAAE,gBAAgB,EAAE;IACrE,EAAE,EAAE,EAAE,kBAAkB,EAAE,IAAI,EAAE,SAAS,EAAE,MAAM,EAAE,gBAAgB,EAAE;IAErE,2CAA2C;IAC3C,EAAE,EAAE,EAAE,iBAAiB,EAAE,IAAI,EAAE,SAAS,EAAE,MAAM,EAAE,SAAS,EAAE;IAC7D,EAAE,EAAE,EAAE,iBAAiB,EAAE,IAAI,EAAE,SAAS,EAAE,MAAM,EAAE,cAAc,EAAE;IAClE,EAAE,EAAE,EAAE,eAAe,EAAE,IAAI,EAAE,SAAS,EAAE,MAAM,EAAE,QAAQ,EAAE;IAE1D,+DAA+D;IAC/D,gCAAgC;IAChC,EAAE,EAAE,EAAE,gBAAgB,EAAE,IAAI,EAAE,IAAI,EAAE,MAAM,EAAE,UAAU,EAAE,QAAQ,EAAE,YAAY,EAAE;IAChF,EAAE,EAAE,EAAE,iBAAiB,EAAE,IAAI,EAAE,IAAI,EAAE,MAAM,EAAE,UAAU,EAAE,QAAQ,EAAE,YAAY,EAAE;IAEjF,2CAA2C;IAC3C,EAAE,EAAE,EAAE,cAAc,EAAE,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE,UAAU,EAAE,QAAQ,EAAE,YAAY,EAAE;IAClF,EAAE,EAAE,EAAE,eAAe,EAAE,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE,kBAAkB,EAAE,QAAQ,EAAE,YAAY,EAAE;IAE3F,wCAAwC;IACxC,EAAE,EAAE,EAAE,gBAAgB,EAAE,IAAI,EAAE,SAAS,EAAE,MAAM,EAAE,mBAAmB,EAAE,QAAQ,EAAE,YAAY,EAAE;CAC/F,CAAC;AAEF;;;GAGG;AACH,MAAM,kBAAkB,GAAuB,CAAC,GAAG,mBAAmB,CAAC,CAAC;AAExE;;;;;;GAMG;AACH,SAAS,SAAS,CAAC,IAAY;IAC7B,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IAC9B,MAAM,KAAK,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;IACvB,MAAM,SAAS,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,IAAI,EAAE,EAAE,CAAC,CAAC;IAEjD,IAAI,CAAC,KAAK,IAAI,KAAK,CAAC,SAAS,CAAC,IAAI,SAAS,GAAG,CAAC,IAAI,SAAS,GAAG,EAAE,EAAE,CAAC;QAClE,OAAO,IAAI,CAAC;IACd,CAAC;IAED,MAAM,KAAK,GAAG,UAAU,CAAC,KAAK,CAAC,CAAC;IAChC,IAAI,KAAK,KAAK,IAAI;QAAE,OAAO,IAAI,CAAC;IAEhC,uCAAuC;IACvC,4BAA4B;IAC5B,MAAM,IAAI,GAAG,SAAS,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,GAAG,SAAS,CAAC,CAAC,KAAK,CAAC,CAAC;IAClE,MAAM,OAAO,GAAG,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC;IAErC,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;AAC3B,CAAC;AAED;;;;;;GAMG;AACH,SAAS,UAAU,CAAC,EAAU;IAC5B,MAAM,KAAK,GAAG,EAAE,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IAC5B,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IAEpC,IAAI,MAAM,GAAG,CAAC,CAAC;IACf,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,MAAM,GAAG,GAAG,QAAQ,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QAC/B,IAAI,KAAK,CAAC,GAAG,CAAC,IAAI,GAAG,GAAG,CAAC,IAAI,GAAG,GAAG,GAAG;YAAE,OAAO,IAAI,CAAC;QACpD,MAAM,GAAG,CAAC,CAAC,MAAM,IAAI,CAAC,CAAC,GAAG,GAAG,CAAC,KAAK,CAAC,CAAC;IACvC,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAED;;;;;;;GAOG;AACH,SAAS,gBAAgB,CAAC,EAAU,EAAE,OAAe;IACnD,MAAM,IAAI,GAAG,SAAS,CAAC,OAAO,CAAC,CAAC;IAChC,IAAI,CAAC,IAAI;QAAE,OAAO,KAAK,CAAC;IAExB,MAAM,KAAK,GAAG,UAAU,CAAC,EAAE,CAAC,CAAC;IAC7B,IAAI,KAAK,KAAK,IAAI;QAAE,OAAO,KAAK,CAAC;IAEjC,OAAO,CAAC,KAAK,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,IAAI,CAAC,OAAO,CAAC;AACpD,CAAC;AAED;;;;;;;;;;;;;;GAcG;AACH,MAAM,UAAU,gBAAgB,CAAC,EAAU;IACzC,gDAAgD;IAChD,IAAI,WAAW,EAAE,CAAC;QAChB,MAAM,GAAG,GAAG,WAAW,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC;QACpC,IAAI,GAAG,EAAE,CAAC;YACR,MAAM,KAAK,GAAG,WAAW,CAAC,kBAAkB,CAAC,GAAG,CAAC,CAAC;YAClD,IAAI,KAAK;gBAAE,OAAO,KAAK,CAAC;QAC1B,CAAC;IACH,CAAC;IAED,8BAA8B;IAC9B,KAAK,MAAM,KAAK,IAAI,kBAAkB,EAAE,CAAC;QACvC,IAAI,gBAAgB,CAAC,EAAE,EAAE,KAAK,CAAC,EAAE,CAAC,EAAE,CAAC;YACnC,OAAO,KAAK,CAAC;QACf,CAAC;IACH,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC;AAED;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,MAAM,UAAU,WAAW,CAAC,EAAU;IACpC,MAAM,aAAa,GAAG;QACpB,YAAY;QACZ,eAAe;QACf,gBAAgB;QAChB,aAAa;QACb,gBAAgB;KACjB,CAAC;IAEF,KAAK,MAAM,KAAK,IAAI,aAAa,EAAE,CAAC;QAClC,IAAI,gBAAgB,CAAC,EAAE,EAAE,KAAK,CAAC,EAAE,CAAC;YAChC,OAAO,IAAI,CAAC;QACd,CAAC;IACH,CAAC;IAED,OAAO,KAAK,CAAC;AACf,CAAC;AAED;;;;;;;;;;;;;;;GAeG;AACH,MAAM,UAAU,mBAAmB,CAAC,KAAuB;IACzD,kBAAkB,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;AACjC,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,qBAAqB;IACnC,OAAO,CAAC,GAAG,kBAAkB,CAAC,CAAC;AACjC,CAAC"}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* System monitoring engine type definitions
|
|
3
|
+
* 系統監控引擎型別定義
|
|
4
|
+
*
|
|
5
|
+
* @module @panguard-ai/core/monitor/types
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Configuration for the monitoring engine
|
|
9
|
+
* 監控引擎配置
|
|
10
|
+
*/
|
|
11
|
+
export interface MonitorConfig {
|
|
12
|
+
/** Enable log monitoring / 啟用日誌監控 */
|
|
13
|
+
logMonitor: boolean;
|
|
14
|
+
/** Enable network monitoring / 啟用網路監控 */
|
|
15
|
+
networkMonitor: boolean;
|
|
16
|
+
/** Enable process monitoring / 啟用程序監控 */
|
|
17
|
+
processMonitor: boolean;
|
|
18
|
+
/** Enable file integrity monitoring / 啟用檔案完整性監控 */
|
|
19
|
+
fileMonitor: boolean;
|
|
20
|
+
/** Network polling interval in ms / 網路輪詢間隔(毫秒) */
|
|
21
|
+
networkPollInterval: number;
|
|
22
|
+
/** Process polling interval in ms / 程序輪詢間隔(毫秒) */
|
|
23
|
+
processPollInterval: number;
|
|
24
|
+
/** File paths to watch for integrity changes / 要監控完整性變更的檔案路徑 */
|
|
25
|
+
watchPaths?: string[];
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Default monitoring configuration
|
|
29
|
+
* 預設監控配置
|
|
30
|
+
*/
|
|
31
|
+
export declare const DEFAULT_MONITOR_CONFIG: MonitorConfig;
|
|
32
|
+
/**
|
|
33
|
+
* Monitor operational status
|
|
34
|
+
* 監控運作狀態
|
|
35
|
+
*/
|
|
36
|
+
export type MonitorStatus = 'running' | 'stopped' | 'error';
|
|
37
|
+
/**
|
|
38
|
+
* Threat intelligence entry for known malicious IP addresses
|
|
39
|
+
* 已知惡意 IP 位址的威脅情報條目
|
|
40
|
+
*/
|
|
41
|
+
export interface ThreatIntelEntry {
|
|
42
|
+
/** IP address or CIDR range / IP 位址或 CIDR 範圍 */
|
|
43
|
+
ip: string;
|
|
44
|
+
/** Threat type / 威脅類型 */
|
|
45
|
+
type: 'c2' | 'scanner' | 'botnet' | 'malware';
|
|
46
|
+
/** Intelligence source / 情報來源 */
|
|
47
|
+
source: string;
|
|
48
|
+
/** Last seen timestamp (ISO string) / 最後發現時間(ISO 字串) */
|
|
49
|
+
lastSeen?: string;
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* File hash record for integrity monitoring
|
|
53
|
+
* 用於完整性監控的檔案雜湊記錄
|
|
54
|
+
*/
|
|
55
|
+
export interface FileHashRecord {
|
|
56
|
+
/** File path / 檔案路徑 */
|
|
57
|
+
path: string;
|
|
58
|
+
/** SHA-256 hash / SHA-256 雜湊 */
|
|
59
|
+
hash: string;
|
|
60
|
+
/** Last checked timestamp (ISO string) / 最後檢查時間(ISO 字串) */
|
|
61
|
+
lastChecked: string;
|
|
62
|
+
/** File size in bytes / 檔案大小(位元組) */
|
|
63
|
+
size: number;
|
|
64
|
+
}
|
|
65
|
+
//# sourceMappingURL=types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/monitor/types.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH;;;GAGG;AACH,MAAM,WAAW,aAAa;IAC5B,qCAAqC;IACrC,UAAU,EAAE,OAAO,CAAC;IACpB,yCAAyC;IACzC,cAAc,EAAE,OAAO,CAAC;IACxB,yCAAyC;IACzC,cAAc,EAAE,OAAO,CAAC;IACxB,mDAAmD;IACnD,WAAW,EAAE,OAAO,CAAC;IACrB,kDAAkD;IAClD,mBAAmB,EAAE,MAAM,CAAC;IAC5B,kDAAkD;IAClD,mBAAmB,EAAE,MAAM,CAAC;IAC5B,gEAAgE;IAChE,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;CACvB;AAED;;;GAGG;AACH,eAAO,MAAM,sBAAsB,EAAE,aAQpC,CAAC;AAEF;;;GAGG;AACH,MAAM,MAAM,aAAa,GAAG,SAAS,GAAG,SAAS,GAAG,OAAO,CAAC;AAE5D;;;GAGG;AACH,MAAM,WAAW,gBAAgB;IAC/B,gDAAgD;IAChD,EAAE,EAAE,MAAM,CAAC;IACX,yBAAyB;IACzB,IAAI,EAAE,IAAI,GAAG,SAAS,GAAG,QAAQ,GAAG,SAAS,CAAC;IAC9C,iCAAiC;IACjC,MAAM,EAAE,MAAM,CAAC;IACf,wDAAwD;IACxD,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED;;;GAGG;AACH,MAAM,WAAW,cAAc;IAC7B,uBAAuB;IACvB,IAAI,EAAE,MAAM,CAAC;IACb,gCAAgC;IAChC,IAAI,EAAE,MAAM,CAAC;IACb,2DAA2D;IAC3D,WAAW,EAAE,MAAM,CAAC;IACpB,qCAAqC;IACrC,IAAI,EAAE,MAAM,CAAC;CACd"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* System monitoring engine type definitions
|
|
3
|
+
* 系統監控引擎型別定義
|
|
4
|
+
*
|
|
5
|
+
* @module @panguard-ai/core/monitor/types
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Default monitoring configuration
|
|
9
|
+
* 預設監控配置
|
|
10
|
+
*/
|
|
11
|
+
export const DEFAULT_MONITOR_CONFIG = {
|
|
12
|
+
logMonitor: true,
|
|
13
|
+
networkMonitor: true,
|
|
14
|
+
processMonitor: true,
|
|
15
|
+
fileMonitor: false,
|
|
16
|
+
networkPollInterval: 30000,
|
|
17
|
+
processPollInterval: 15000,
|
|
18
|
+
watchPaths: [],
|
|
19
|
+
};
|
|
20
|
+
//# sourceMappingURL=types.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/monitor/types.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAuBH;;;GAGG;AACH,MAAM,CAAC,MAAM,sBAAsB,GAAkB;IACnD,UAAU,EAAE,IAAI;IAChB,cAAc,EAAE,IAAI;IACpB,cAAc,EAAE,IAAI;IACpB,WAAW,EAAE,KAAK;IAClB,mBAAmB,EAAE,KAAK;IAC1B,mBAAmB,EAAE,KAAK;IAC1B,UAAU,EAAE,EAAE;CACf,CAAC"}
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Sigma/YARA Rules Engine
|
|
3
|
+
* Sigma/YARA 規則引擎
|
|
4
|
+
*
|
|
5
|
+
* Provides the RuleEngine class for loading, managing, and matching
|
|
6
|
+
* Sigma rules against security events. Supports filesystem loading,
|
|
7
|
+
* hot-reloading, and custom rule injection.
|
|
8
|
+
* 提供 RuleEngine 類別,用於載入、管理和比對 Sigma 規則與安全事件。
|
|
9
|
+
* 支援檔案系統載入、熱載入和自訂規則注入。
|
|
10
|
+
*
|
|
11
|
+
* @module @panguard-ai/core/rules
|
|
12
|
+
*/
|
|
13
|
+
import type { SecurityEvent } from '../types.js';
|
|
14
|
+
import type { SigmaRule, RuleMatch, RuleEngineConfig } from './types.js';
|
|
15
|
+
/** Rules module version / 規則模組版本 */
|
|
16
|
+
export declare const RULES_VERSION = "0.1.0";
|
|
17
|
+
/**
|
|
18
|
+
* Sigma rule engine for loading, managing, and matching security rules
|
|
19
|
+
* Sigma 規則引擎,用於載入、管理和比對安全規則
|
|
20
|
+
*
|
|
21
|
+
* The RuleEngine is the primary entry point for working with Sigma rules.
|
|
22
|
+
* It manages a collection of rules, supports hot-reloading from disk,
|
|
23
|
+
* and provides matching against SecurityEvent instances.
|
|
24
|
+
* RuleEngine 是使用 Sigma 規則的主要入口點。
|
|
25
|
+
* 它管理規則集合、支援從磁碟熱載入,並提供與 SecurityEvent 實例的比對。
|
|
26
|
+
*
|
|
27
|
+
* @example
|
|
28
|
+
* ```typescript
|
|
29
|
+
* const engine = new RuleEngine({ rulesDir: './config/sigma-rules', hotReload: true });
|
|
30
|
+
* await engine.loadRules();
|
|
31
|
+
* const matches = engine.match(event);
|
|
32
|
+
* engine.destroy();
|
|
33
|
+
* ```
|
|
34
|
+
*/
|
|
35
|
+
export declare class RuleEngine {
|
|
36
|
+
/** Internal rules collection / 內部規則集合 */
|
|
37
|
+
private rules;
|
|
38
|
+
/** Cleanup function for the filesystem watcher / 檔案系統監視器的清理函式 */
|
|
39
|
+
private cleanupWatcher?;
|
|
40
|
+
/** Engine configuration / 引擎配置 */
|
|
41
|
+
private config;
|
|
42
|
+
/**
|
|
43
|
+
* Create a new RuleEngine instance
|
|
44
|
+
* 建立新的 RuleEngine 實例
|
|
45
|
+
*
|
|
46
|
+
* @param config - Optional configuration / 可選配置
|
|
47
|
+
*/
|
|
48
|
+
constructor(config?: RuleEngineConfig);
|
|
49
|
+
/**
|
|
50
|
+
* Load rules from the configured directory
|
|
51
|
+
* 從配置的目錄載入規則
|
|
52
|
+
*
|
|
53
|
+
* If a rulesDir is configured, loads all Sigma rules from that directory.
|
|
54
|
+
* If hotReload is enabled, starts watching the directory for changes.
|
|
55
|
+
* 如果配置了 rulesDir,從該目錄載入所有 Sigma 規則。
|
|
56
|
+
* 如果啟用了 hotReload,開始監視目錄的變更。
|
|
57
|
+
*
|
|
58
|
+
* @returns Promise that resolves when rules are loaded / 規則載入完成後 resolve 的 Promise
|
|
59
|
+
*/
|
|
60
|
+
loadRules(): Promise<void>;
|
|
61
|
+
/**
|
|
62
|
+
* Add a single rule to the engine
|
|
63
|
+
* 新增單一規則到引擎
|
|
64
|
+
*
|
|
65
|
+
* @param rule - Sigma rule to add / 要新增的 Sigma 規則
|
|
66
|
+
*/
|
|
67
|
+
addRule(rule: SigmaRule): void;
|
|
68
|
+
/**
|
|
69
|
+
* Remove a rule by its id
|
|
70
|
+
* 依 id 移除規則
|
|
71
|
+
*
|
|
72
|
+
* @param id - The rule id to remove / 要移除的規則 id
|
|
73
|
+
* @returns True if a rule was removed, false if not found / 移除成功回傳 true,找不到回傳 false
|
|
74
|
+
*/
|
|
75
|
+
removeRule(id: string): boolean;
|
|
76
|
+
/**
|
|
77
|
+
* Match a security event against all loaded rules
|
|
78
|
+
* 比對安全事件與所有已載入的規則
|
|
79
|
+
*
|
|
80
|
+
* @param event - The security event to match / 要比對的安全事件
|
|
81
|
+
* @returns Array of RuleMatch for all matching rules / 所有比對規則的 RuleMatch 陣列
|
|
82
|
+
*/
|
|
83
|
+
match(event: SecurityEvent): RuleMatch[];
|
|
84
|
+
/**
|
|
85
|
+
* Get a copy of all currently loaded rules
|
|
86
|
+
* 取得所有已載入規則的副本
|
|
87
|
+
*
|
|
88
|
+
* @returns Array of Sigma rules (shallow copy) / Sigma 規則陣列(淺複製)
|
|
89
|
+
*/
|
|
90
|
+
getRules(): SigmaRule[];
|
|
91
|
+
/**
|
|
92
|
+
* Reload all rules from the configured directory
|
|
93
|
+
* 從配置的目錄重新載入所有規則
|
|
94
|
+
*
|
|
95
|
+
* Clears all existing rules (including custom rules) and reloads from scratch.
|
|
96
|
+
* 清除所有現有規則(包含自訂規則)並從頭重新載入。
|
|
97
|
+
*
|
|
98
|
+
* @returns Promise that resolves when rules are reloaded / 規則重新載入完成後 resolve 的 Promise
|
|
99
|
+
*/
|
|
100
|
+
reload(): Promise<void>;
|
|
101
|
+
/**
|
|
102
|
+
* Destroy the engine and clean up resources
|
|
103
|
+
* 銷毀引擎並清理資源
|
|
104
|
+
*
|
|
105
|
+
* Stops the filesystem watcher if active and clears the rule set.
|
|
106
|
+
* 停止檔案系統監視器(如果活動中)並清除規則集。
|
|
107
|
+
*/
|
|
108
|
+
destroy(): void;
|
|
109
|
+
}
|
|
110
|
+
export type { SigmaLogSource, SigmaDetection, SigmaRule, RuleMatch, RuleEngineConfig, } from './types.js';
|
|
111
|
+
export { parseSigmaYaml, parseSigmaFile } from './sigma-parser.js';
|
|
112
|
+
export { matchEvent, matchEventAgainstRules } from './sigma-matcher.js';
|
|
113
|
+
export { loadRulesFromDirectory, loadRulesRecursive, watchRulesDirectory } from './rule-loader.js';
|
|
114
|
+
export { YaraScanner, type YaraMatch, type YaraScanResult } from './yara-scanner.js';
|
|
115
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/rules/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAGH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AACjD,OAAO,KAAK,EAAE,SAAS,EAAE,SAAS,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAMzE,oCAAoC;AACpC,eAAO,MAAM,aAAa,UAAU,CAAC;AAErC;;;;;;;;;;;;;;;;;GAiBG;AACH,qBAAa,UAAU;IACrB,yCAAyC;IACzC,OAAO,CAAC,KAAK,CAAmB;IAEhC,iEAAiE;IACjE,OAAO,CAAC,cAAc,CAAC,CAAa;IAEpC,kCAAkC;IAClC,OAAO,CAAC,MAAM,CAAmB;IAEjC;;;;;OAKG;gBACS,MAAM,CAAC,EAAE,gBAAgB;IAYrC;;;;;;;;;;OAUG;IACG,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC;IA+EhC;;;;;OAKG;IACH,OAAO,CAAC,IAAI,EAAE,SAAS,GAAG,IAAI;IAe9B;;;;;;OAMG;IACH,UAAU,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO;IAc/B;;;;;;OAMG;IACH,KAAK,CAAC,KAAK,EAAE,aAAa,GAAG,SAAS,EAAE;IAIxC;;;;;OAKG;IACH,QAAQ,IAAI,SAAS,EAAE;IAIvB;;;;;;;;OAQG;IACG,MAAM,IAAI,OAAO,CAAC,IAAI,CAAC;IAgC7B;;;;;;OAMG;IACH,OAAO,IAAI,IAAI;CAQhB;AAGD,YAAY,EACV,cAAc,EACd,cAAc,EACd,SAAS,EACT,SAAS,EACT,gBAAgB,GACjB,MAAM,YAAY,CAAC;AAGpB,OAAO,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AAGnE,OAAO,EAAE,UAAU,EAAE,sBAAsB,EAAE,MAAM,oBAAoB,CAAC;AAGxE,OAAO,EAAE,sBAAsB,EAAE,kBAAkB,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAGnG,OAAO,EAAE,WAAW,EAAE,KAAK,SAAS,EAAE,KAAK,cAAc,EAAE,MAAM,mBAAmB,CAAC"}
|
|
@@ -0,0 +1,244 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Sigma/YARA Rules Engine
|
|
3
|
+
* Sigma/YARA 規則引擎
|
|
4
|
+
*
|
|
5
|
+
* Provides the RuleEngine class for loading, managing, and matching
|
|
6
|
+
* Sigma rules against security events. Supports filesystem loading,
|
|
7
|
+
* hot-reloading, and custom rule injection.
|
|
8
|
+
* 提供 RuleEngine 類別,用於載入、管理和比對 Sigma 規則與安全事件。
|
|
9
|
+
* 支援檔案系統載入、熱載入和自訂規則注入。
|
|
10
|
+
*
|
|
11
|
+
* @module @panguard-ai/core/rules
|
|
12
|
+
*/
|
|
13
|
+
import { createLogger } from '../utils/logger.js';
|
|
14
|
+
import { matchEventAgainstRules } from './sigma-matcher.js';
|
|
15
|
+
import { loadRulesRecursive, watchRulesDirectory } from './rule-loader.js';
|
|
16
|
+
const logger = createLogger('rule-engine');
|
|
17
|
+
/** Rules module version / 規則模組版本 */
|
|
18
|
+
export const RULES_VERSION = '0.1.0';
|
|
19
|
+
/**
|
|
20
|
+
* Sigma rule engine for loading, managing, and matching security rules
|
|
21
|
+
* Sigma 規則引擎,用於載入、管理和比對安全規則
|
|
22
|
+
*
|
|
23
|
+
* The RuleEngine is the primary entry point for working with Sigma rules.
|
|
24
|
+
* It manages a collection of rules, supports hot-reloading from disk,
|
|
25
|
+
* and provides matching against SecurityEvent instances.
|
|
26
|
+
* RuleEngine 是使用 Sigma 規則的主要入口點。
|
|
27
|
+
* 它管理規則集合、支援從磁碟熱載入,並提供與 SecurityEvent 實例的比對。
|
|
28
|
+
*
|
|
29
|
+
* @example
|
|
30
|
+
* ```typescript
|
|
31
|
+
* const engine = new RuleEngine({ rulesDir: './config/sigma-rules', hotReload: true });
|
|
32
|
+
* await engine.loadRules();
|
|
33
|
+
* const matches = engine.match(event);
|
|
34
|
+
* engine.destroy();
|
|
35
|
+
* ```
|
|
36
|
+
*/
|
|
37
|
+
export class RuleEngine {
|
|
38
|
+
/** Internal rules collection / 內部規則集合 */
|
|
39
|
+
rules = [];
|
|
40
|
+
/** Cleanup function for the filesystem watcher / 檔案系統監視器的清理函式 */
|
|
41
|
+
cleanupWatcher;
|
|
42
|
+
/** Engine configuration / 引擎配置 */
|
|
43
|
+
config;
|
|
44
|
+
/**
|
|
45
|
+
* Create a new RuleEngine instance
|
|
46
|
+
* 建立新的 RuleEngine 實例
|
|
47
|
+
*
|
|
48
|
+
* @param config - Optional configuration / 可選配置
|
|
49
|
+
*/
|
|
50
|
+
constructor(config) {
|
|
51
|
+
this.config = config ?? {};
|
|
52
|
+
// Add any pre-loaded custom rules / 新增預載入的自訂規則
|
|
53
|
+
if (this.config.customRules !== undefined && this.config.customRules.length > 0) {
|
|
54
|
+
this.rules.push(...this.config.customRules);
|
|
55
|
+
logger.info(`Initialized with ${this.config.customRules.length} custom rules / 已初始化 ${this.config.customRules.length} 條自訂規則`);
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Load rules from the configured directory
|
|
60
|
+
* 從配置的目錄載入規則
|
|
61
|
+
*
|
|
62
|
+
* If a rulesDir is configured, loads all Sigma rules from that directory.
|
|
63
|
+
* If hotReload is enabled, starts watching the directory for changes.
|
|
64
|
+
* 如果配置了 rulesDir,從該目錄載入所有 Sigma 規則。
|
|
65
|
+
* 如果啟用了 hotReload,開始監視目錄的變更。
|
|
66
|
+
*
|
|
67
|
+
* @returns Promise that resolves when rules are loaded / 規則載入完成後 resolve 的 Promise
|
|
68
|
+
*/
|
|
69
|
+
async loadRules() {
|
|
70
|
+
const existingIds = new Set(this.rules.map((r) => r.id));
|
|
71
|
+
// Load custom rules from rulesDir / 從 rulesDir 載入自訂規則
|
|
72
|
+
if (this.config.rulesDir !== undefined) {
|
|
73
|
+
const customDirRules = loadRulesRecursive(this.config.rulesDir, 'custom');
|
|
74
|
+
for (const rule of customDirRules) {
|
|
75
|
+
if (!existingIds.has(rule.id)) {
|
|
76
|
+
this.rules.push(rule);
|
|
77
|
+
existingIds.add(rule.id);
|
|
78
|
+
}
|
|
79
|
+
else {
|
|
80
|
+
logger.warn(`Skipping duplicate rule id "${rule.id}" from custom directory / 跳過自訂目錄中重複的規則 id "${rule.id}"`);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
// Load community rules from communityRulesDir / 從 communityRulesDir 載入社群規則
|
|
85
|
+
if (this.config.communityRulesDir !== undefined) {
|
|
86
|
+
const communityRules = loadRulesRecursive(this.config.communityRulesDir, 'community');
|
|
87
|
+
for (const rule of communityRules) {
|
|
88
|
+
if (!existingIds.has(rule.id)) {
|
|
89
|
+
this.rules.push(rule);
|
|
90
|
+
existingIds.add(rule.id);
|
|
91
|
+
}
|
|
92
|
+
else {
|
|
93
|
+
logger.warn(`Skipping duplicate rule id "${rule.id}" from community directory / 跳過社群目錄中重複的規則 id "${rule.id}"`);
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
if (this.config.rulesDir === undefined && this.config.communityRulesDir === undefined) {
|
|
98
|
+
logger.warn('No rulesDir or communityRulesDir configured, skipping directory load / 未配置規則目錄,跳過載入');
|
|
99
|
+
}
|
|
100
|
+
logger.info(`Total rules loaded: ${this.rules.length} / 已載入規則總數: ${this.rules.length}`);
|
|
101
|
+
// Set up hot-reload watcher if configured / 如果配置了熱載入,設定監視器
|
|
102
|
+
if (this.config.hotReload && this.config.rulesDir !== undefined) {
|
|
103
|
+
if (this.cleanupWatcher !== undefined) {
|
|
104
|
+
this.cleanupWatcher();
|
|
105
|
+
}
|
|
106
|
+
this.cleanupWatcher = watchRulesDirectory(this.config.rulesDir, (updatedRules) => {
|
|
107
|
+
const customRules = this.config.customRules ?? [];
|
|
108
|
+
const customIds = new Set(customRules.map((r) => r.id));
|
|
109
|
+
this.rules = [...customRules];
|
|
110
|
+
const loadedIds = new Set(customIds);
|
|
111
|
+
for (const rule of updatedRules) {
|
|
112
|
+
if (!loadedIds.has(rule.id)) {
|
|
113
|
+
this.rules.push(rule);
|
|
114
|
+
loadedIds.add(rule.id);
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
// Re-load community rules after hot-reload / 熱載入後重新載入社群規則
|
|
118
|
+
if (this.config.communityRulesDir !== undefined) {
|
|
119
|
+
const communityRules = loadRulesRecursive(this.config.communityRulesDir, 'community');
|
|
120
|
+
for (const rule of communityRules) {
|
|
121
|
+
if (!loadedIds.has(rule.id)) {
|
|
122
|
+
this.rules.push(rule);
|
|
123
|
+
loadedIds.add(rule.id);
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
logger.info(`Hot-reloaded rules, total: ${this.rules.length} / 熱載入規則完成,總數: ${this.rules.length}`);
|
|
128
|
+
});
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
/**
|
|
132
|
+
* Add a single rule to the engine
|
|
133
|
+
* 新增單一規則到引擎
|
|
134
|
+
*
|
|
135
|
+
* @param rule - Sigma rule to add / 要新增的 Sigma 規則
|
|
136
|
+
*/
|
|
137
|
+
addRule(rule) {
|
|
138
|
+
const existingIndex = this.rules.findIndex((r) => r.id === rule.id);
|
|
139
|
+
if (existingIndex !== -1) {
|
|
140
|
+
this.rules[existingIndex] = rule;
|
|
141
|
+
logger.info(`Updated existing rule: "${rule.title}" (${rule.id}) / 更新現有規則: "${rule.title}" (${rule.id})`);
|
|
142
|
+
}
|
|
143
|
+
else {
|
|
144
|
+
this.rules.push(rule);
|
|
145
|
+
logger.info(`Added new rule: "${rule.title}" (${rule.id}) / 新增規則: "${rule.title}" (${rule.id})`);
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
/**
|
|
149
|
+
* Remove a rule by its id
|
|
150
|
+
* 依 id 移除規則
|
|
151
|
+
*
|
|
152
|
+
* @param id - The rule id to remove / 要移除的規則 id
|
|
153
|
+
* @returns True if a rule was removed, false if not found / 移除成功回傳 true,找不到回傳 false
|
|
154
|
+
*/
|
|
155
|
+
removeRule(id) {
|
|
156
|
+
const initialLength = this.rules.length;
|
|
157
|
+
this.rules = this.rules.filter((r) => r.id !== id);
|
|
158
|
+
const removed = this.rules.length < initialLength;
|
|
159
|
+
if (removed) {
|
|
160
|
+
logger.info(`Removed rule: ${id} / 已移除規則: ${id}`);
|
|
161
|
+
}
|
|
162
|
+
else {
|
|
163
|
+
logger.warn(`Rule not found for removal: ${id} / 找不到要移除的規則: ${id}`);
|
|
164
|
+
}
|
|
165
|
+
return removed;
|
|
166
|
+
}
|
|
167
|
+
/**
|
|
168
|
+
* Match a security event against all loaded rules
|
|
169
|
+
* 比對安全事件與所有已載入的規則
|
|
170
|
+
*
|
|
171
|
+
* @param event - The security event to match / 要比對的安全事件
|
|
172
|
+
* @returns Array of RuleMatch for all matching rules / 所有比對規則的 RuleMatch 陣列
|
|
173
|
+
*/
|
|
174
|
+
match(event) {
|
|
175
|
+
return matchEventAgainstRules(event, this.rules);
|
|
176
|
+
}
|
|
177
|
+
/**
|
|
178
|
+
* Get a copy of all currently loaded rules
|
|
179
|
+
* 取得所有已載入規則的副本
|
|
180
|
+
*
|
|
181
|
+
* @returns Array of Sigma rules (shallow copy) / Sigma 規則陣列(淺複製)
|
|
182
|
+
*/
|
|
183
|
+
getRules() {
|
|
184
|
+
return [...this.rules];
|
|
185
|
+
}
|
|
186
|
+
/**
|
|
187
|
+
* Reload all rules from the configured directory
|
|
188
|
+
* 從配置的目錄重新載入所有規則
|
|
189
|
+
*
|
|
190
|
+
* Clears all existing rules (including custom rules) and reloads from scratch.
|
|
191
|
+
* 清除所有現有規則(包含自訂規則)並從頭重新載入。
|
|
192
|
+
*
|
|
193
|
+
* @returns Promise that resolves when rules are reloaded / 規則重新載入完成後 resolve 的 Promise
|
|
194
|
+
*/
|
|
195
|
+
async reload() {
|
|
196
|
+
logger.info('Reloading all rules / 重新載入所有規則');
|
|
197
|
+
// Reset to custom rules only / 重設為僅有自訂規則
|
|
198
|
+
this.rules = this.config.customRules ? [...this.config.customRules] : [];
|
|
199
|
+
const existingIds = new Set(this.rules.map((r) => r.id));
|
|
200
|
+
if (this.config.rulesDir !== undefined) {
|
|
201
|
+
const customDirRules = loadRulesRecursive(this.config.rulesDir, 'custom');
|
|
202
|
+
for (const rule of customDirRules) {
|
|
203
|
+
if (!existingIds.has(rule.id)) {
|
|
204
|
+
this.rules.push(rule);
|
|
205
|
+
existingIds.add(rule.id);
|
|
206
|
+
}
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
if (this.config.communityRulesDir !== undefined) {
|
|
210
|
+
const communityRules = loadRulesRecursive(this.config.communityRulesDir, 'community');
|
|
211
|
+
for (const rule of communityRules) {
|
|
212
|
+
if (!existingIds.has(rule.id)) {
|
|
213
|
+
this.rules.push(rule);
|
|
214
|
+
existingIds.add(rule.id);
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
logger.info(`Reload complete, total rules: ${this.rules.length} / 重新載入完成,規則總數: ${this.rules.length}`);
|
|
219
|
+
}
|
|
220
|
+
/**
|
|
221
|
+
* Destroy the engine and clean up resources
|
|
222
|
+
* 銷毀引擎並清理資源
|
|
223
|
+
*
|
|
224
|
+
* Stops the filesystem watcher if active and clears the rule set.
|
|
225
|
+
* 停止檔案系統監視器(如果活動中)並清除規則集。
|
|
226
|
+
*/
|
|
227
|
+
destroy() {
|
|
228
|
+
if (this.cleanupWatcher !== undefined) {
|
|
229
|
+
this.cleanupWatcher();
|
|
230
|
+
this.cleanupWatcher = undefined;
|
|
231
|
+
}
|
|
232
|
+
this.rules = [];
|
|
233
|
+
logger.info('RuleEngine destroyed / RuleEngine 已銷毀');
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
// Re-export parser functions / 重新匯出解析器函式
|
|
237
|
+
export { parseSigmaYaml, parseSigmaFile } from './sigma-parser.js';
|
|
238
|
+
// Re-export matcher functions / 重新匯出比對器函式
|
|
239
|
+
export { matchEvent, matchEventAgainstRules } from './sigma-matcher.js';
|
|
240
|
+
// Re-export loader functions / 重新匯出載入器函式
|
|
241
|
+
export { loadRulesFromDirectory, loadRulesRecursive, watchRulesDirectory } from './rule-loader.js';
|
|
242
|
+
// Re-export YARA scanner / 重新匯出 YARA 掃描器
|
|
243
|
+
export { YaraScanner } from './yara-scanner.js';
|
|
244
|
+
//# sourceMappingURL=index.js.map
|