scriptguard 1.0.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.
Files changed (50) hide show
  1. package/README.md +430 -0
  2. package/dist/ai/analyzers/false-positive-filter.d.ts +15 -0
  3. package/dist/ai/analyzers/false-positive-filter.d.ts.map +1 -0
  4. package/dist/ai/analyzers/false-positive-filter.js +162 -0
  5. package/dist/ai/analyzers/false-positive-filter.js.map +1 -0
  6. package/dist/ai/analyzers/insight-generator.d.ts +7 -0
  7. package/dist/ai/analyzers/insight-generator.d.ts.map +1 -0
  8. package/dist/ai/analyzers/insight-generator.js +384 -0
  9. package/dist/ai/analyzers/insight-generator.js.map +1 -0
  10. package/dist/ai/analyzers/threat-detector.d.ts +7 -0
  11. package/dist/ai/analyzers/threat-detector.d.ts.map +1 -0
  12. package/dist/ai/analyzers/threat-detector.js +249 -0
  13. package/dist/ai/analyzers/threat-detector.js.map +1 -0
  14. package/dist/ai/gemini-client.d.ts +47 -0
  15. package/dist/ai/gemini-client.d.ts.map +1 -0
  16. package/dist/ai/gemini-client.js +222 -0
  17. package/dist/ai/gemini-client.js.map +1 -0
  18. package/dist/ai/index.d.ts +8 -0
  19. package/dist/ai/index.d.ts.map +1 -0
  20. package/dist/ai/index.js +19 -0
  21. package/dist/ai/index.js.map +1 -0
  22. package/dist/ai/prompts.d.ts +11 -0
  23. package/dist/ai/prompts.d.ts.map +1 -0
  24. package/dist/ai/prompts.js +212 -0
  25. package/dist/ai/prompts.js.map +1 -0
  26. package/dist/cli.d.ts +4 -0
  27. package/dist/cli.d.ts.map +1 -0
  28. package/dist/cli.js +283 -0
  29. package/dist/cli.js.map +1 -0
  30. package/dist/index.d.ts +6 -0
  31. package/dist/index.d.ts.map +1 -0
  32. package/dist/index.js +16 -0
  33. package/dist/index.js.map +1 -0
  34. package/dist/scanners/index.d.ts +10 -0
  35. package/dist/scanners/index.d.ts.map +1 -0
  36. package/dist/scanners/index.js +202 -0
  37. package/dist/scanners/index.js.map +1 -0
  38. package/dist/scanners/lifecycle.d.ts +10 -0
  39. package/dist/scanners/lifecycle.d.ts.map +1 -0
  40. package/dist/scanners/lifecycle.js +202 -0
  41. package/dist/scanners/lifecycle.js.map +1 -0
  42. package/dist/scanners/patterns.d.ts +4 -0
  43. package/dist/scanners/patterns.d.ts.map +1 -0
  44. package/dist/scanners/patterns.js +188 -0
  45. package/dist/scanners/patterns.js.map +1 -0
  46. package/dist/types/index.d.ts +123 -0
  47. package/dist/types/index.d.ts.map +1 -0
  48. package/dist/types/index.js +4 -0
  49. package/dist/types/index.js.map +1 -0
  50. package/package.json +46 -0
@@ -0,0 +1,384 @@
1
+ "use strict";
2
+ /** ScriptGuard — Insight generator for actionable security guidance */
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.generateInsights = generateInsights;
5
+ /**
6
+ * Generate actionable security insights for findings
7
+ */
8
+ function generateInsights(analysis, includeMitigation = true) {
9
+ const insights = [];
10
+ // Group findings by severity
11
+ const findingsBySeverity = groupBySeverity(analysis.findings);
12
+ // Generate insights for each severity level
13
+ for (const [severity, findings] of Object.entries(findingsBySeverity)) {
14
+ if (findings.length === 0)
15
+ continue;
16
+ const severityInsights = generateInsightsForSeverity(findings, severity, analysis, includeMitigation);
17
+ insights.push(...severityInsights);
18
+ }
19
+ return insights;
20
+ }
21
+ /**
22
+ * Generate insights for a specific severity level
23
+ */
24
+ function generateInsightsForSeverity(findings, severity, analysis, includeMitigation) {
25
+ const insights = [];
26
+ switch (severity) {
27
+ case 'critical':
28
+ insights.push(generateCriticalInsight(findings, analysis, includeMitigation));
29
+ break;
30
+ case 'high':
31
+ insights.push(...generateHighInsights(findings, analysis, includeMitigation));
32
+ break;
33
+ case 'medium':
34
+ insights.push(...generateMediumInsights(findings, analysis, includeMitigation));
35
+ break;
36
+ case 'low':
37
+ insights.push(generateLowInsight(findings, analysis));
38
+ break;
39
+ }
40
+ return insights;
41
+ }
42
+ /**
43
+ * Generate insights for critical findings
44
+ */
45
+ function generateCriticalInsight(findings, analysis, includeMitigation) {
46
+ const threatTypes = findings.map(f => f.pattern);
47
+ const uniqueThreats = [...new Set(threatTypes)];
48
+ const descriptions = [];
49
+ const techniques = [];
50
+ for (const threat of uniqueThreats) {
51
+ switch (threat) {
52
+ case 'curl-pipe':
53
+ case 'wget-pipe':
54
+ descriptions.push('Remote code execution via download pipe');
55
+ techniques.push('Remote payload execution');
56
+ break;
57
+ case 'ssh-access':
58
+ descriptions.push('SSH private key access detected');
59
+ techniques.push('Credential theft');
60
+ break;
61
+ case 'aws-creds':
62
+ descriptions.push('AWS credentials being accessed');
63
+ techniques.push('Cloud credential theft');
64
+ break;
65
+ case 'passwd-shadow':
66
+ descriptions.push('System credential file access');
67
+ techniques.push('Privilege escalation / credential harvesting');
68
+ break;
69
+ case 'keychain-access':
70
+ descriptions.push('macOS Keychain access detected');
71
+ techniques.push('Credential theft');
72
+ break;
73
+ case 'base64-exec':
74
+ descriptions.push('Base64-encoded payload execution');
75
+ techniques.push('Obfuscated code execution');
76
+ break;
77
+ case 'crypto-miner':
78
+ descriptions.push('Cryptocurrency mining software detected');
79
+ techniques.push('Resource hijacking');
80
+ break;
81
+ case 'reverse-shell':
82
+ descriptions.push('Reverse shell backdoor detected');
83
+ techniques.push('Remote access trojan (RAT)');
84
+ break;
85
+ default:
86
+ descriptions.push(`Critical threat: ${threat}`);
87
+ techniques.push('Unknown critical threat');
88
+ }
89
+ }
90
+ return {
91
+ type: 'threat',
92
+ severity: 'critical',
93
+ description: `Package ${analysis.name}@${analysis.version} contains ${findings.length} critical security issue${findings.length > 1 ? 's' : ''}: ${descriptions.join(', ')}. This package should NOT be installed.`,
94
+ attackTechnique: techniques.join(', '),
95
+ remediation: includeMitigation ? generateCriticalMitigation(findings, analysis) : undefined,
96
+ confidence: 0.95,
97
+ };
98
+ }
99
+ /**
100
+ * Generate insights for high findings
101
+ */
102
+ function generateHighInsights(findings, analysis, includeMitigation) {
103
+ const insights = [];
104
+ // Group by pattern to avoid duplicate insights
105
+ const findingsByPattern = new Map();
106
+ for (const finding of findings) {
107
+ const existing = findingsByPattern.get(finding.pattern) || [];
108
+ existing.push(finding);
109
+ findingsByPattern.set(finding.pattern, existing);
110
+ }
111
+ for (const [pattern, patternFindings] of findingsByPattern) {
112
+ const insight = generateHighInsightForPattern(pattern, patternFindings, analysis, includeMitigation);
113
+ insights.push(insight);
114
+ }
115
+ return insights;
116
+ }
117
+ function generateHighInsightForPattern(pattern, findings, analysis, includeMitigation) {
118
+ const scriptsAffected = [...new Set(findings.map(f => f.scriptName))];
119
+ switch (pattern) {
120
+ case 'curl-silent':
121
+ case 'curl-post':
122
+ return {
123
+ type: 'threat',
124
+ severity: 'high',
125
+ description: `Silent or outbound HTTP requests in ${scriptsAffected.join(', ')} scripts. This may indicate data exfiltration or command & control communication.`,
126
+ attackTechnique: 'Data exfiltration / C2 communication',
127
+ remediation: includeMitigation
128
+ ? 'Review the destination URLs. If unknown, block network access for this package and consider removing it.'
129
+ : undefined,
130
+ confidence: 0.8,
131
+ };
132
+ case 'eval-usage':
133
+ return {
134
+ type: 'threat',
135
+ severity: 'high',
136
+ description: `Dynamic code execution (eval/Function) detected in ${scriptsAffected.join(', ')} scripts. This allows arbitrary code execution and is extremely dangerous.`,
137
+ attackTechnique: 'Arbitrary code execution',
138
+ remediation: includeMitigation
139
+ ? 'Avoid this package. Dynamic code execution in lifecycle scripts is unacceptable for production dependencies.'
140
+ : undefined,
141
+ confidence: 0.9,
142
+ };
143
+ case 'shell-exec':
144
+ return {
145
+ type: 'threat',
146
+ severity: 'high',
147
+ description: `Direct shell execution detected in ${scriptsAffected.join(', ')} scripts. This can execute arbitrary system commands.`,
148
+ attackTechnique: 'Arbitrary command execution',
149
+ remediation: includeMitigation
150
+ ? 'Review what commands are being executed. If unclear or suspicious, remove this package.'
151
+ : undefined,
152
+ confidence: 0.85,
153
+ };
154
+ case 'node-eval':
155
+ return {
156
+ type: 'threat',
157
+ severity: 'high',
158
+ description: `Node.js evaluating code from command line in ${scriptsAffected.join(', ')} scripts. This executes arbitrary JavaScript code.`,
159
+ attackTechnique: 'Arbitrary code execution',
160
+ remediation: includeMitigation
161
+ ? 'Determine what code is being evaluated. If not absolutely necessary, remove this package.'
162
+ : undefined,
163
+ confidence: 0.85,
164
+ };
165
+ case 'env-file':
166
+ return {
167
+ type: 'threat',
168
+ severity: 'high',
169
+ description: `Reading .env files in ${scriptsAffected.join(', ')} scripts. May expose API keys, database credentials, or other secrets.`,
170
+ attackTechnique: 'Secret exfiltration',
171
+ remediation: includeMitigation
172
+ ? 'Check if this package legitimately needs .env access. If not, remove it. Consider using environment variables directly instead.'
173
+ : undefined,
174
+ confidence: 0.75,
175
+ };
176
+ case 'env-exfil':
177
+ return {
178
+ type: 'threat',
179
+ severity: 'high',
180
+ description: `Accessing environment variables in ${scriptsAffected.join(', ')} scripts. Could exfiltrate sensitive data like API keys or tokens.`,
181
+ attackTechnique: 'Credential theft',
182
+ remediation: includeMitigation
183
+ ? 'Review which environment variables are accessed. If suspicious, remove the package and rotate any exposed credentials.'
184
+ : undefined,
185
+ confidence: 0.7,
186
+ };
187
+ case 'clipboard-access':
188
+ return {
189
+ type: 'threat',
190
+ severity: 'high',
191
+ description: `Accessing system clipboard in ${scriptsAffected.join(', ')} scripts. Can steal sensitive data recently copied by the user.`,
192
+ attackTechnique: 'Data theft',
193
+ remediation: includeMitigation
194
+ ? 'Avoid packages that access the clipboard. This is highly suspicious behavior for an npm package.'
195
+ : undefined,
196
+ confidence: 0.85,
197
+ };
198
+ case 'hex-encode':
199
+ return {
200
+ type: 'threat',
201
+ severity: 'high',
202
+ description: `Hex-encoded strings detected in ${scriptsAffected.join(', ')} scripts. This is likely obfuscation to hide malicious code.`,
203
+ attackTechnique: 'Obfuscation',
204
+ remediation: includeMitigation
205
+ ? 'Decode the hex strings to reveal the actual code. If the purpose is unclear, treat this package as compromised.'
206
+ : undefined,
207
+ confidence: 0.8,
208
+ };
209
+ default:
210
+ return {
211
+ type: 'threat',
212
+ severity: 'high',
213
+ description: `High-risk pattern "${pattern}" detected in ${scriptsAffected.join(', ')} scripts.`,
214
+ attackTechnique: 'Unknown high-severity threat',
215
+ remediation: includeMitigation
216
+ ? 'Review the script content manually. If the purpose is unclear, remove this package.'
217
+ : undefined,
218
+ confidence: 0.7,
219
+ };
220
+ }
221
+ }
222
+ /**
223
+ * Generate insights for medium findings
224
+ */
225
+ function generateMediumInsights(findings, analysis, includeMitigation) {
226
+ const insights = [];
227
+ // Group by pattern
228
+ const findingsByPattern = new Map();
229
+ for (const finding of findings) {
230
+ const existing = findingsByPattern.get(finding.pattern) || [];
231
+ existing.push(finding);
232
+ findingsByPattern.set(finding.pattern, existing);
233
+ }
234
+ for (const [pattern, patternFindings] of findingsByPattern) {
235
+ const insight = generateMediumInsightForPattern(pattern, patternFindings, analysis, includeMitigation);
236
+ insights.push(insight);
237
+ }
238
+ return insights;
239
+ }
240
+ function generateMediumInsightForPattern(pattern, findings, analysis, includeMitigation) {
241
+ const scriptsAffected = [...new Set(findings.map(f => f.scriptName))];
242
+ switch (pattern) {
243
+ case 'http-request':
244
+ return {
245
+ type: 'threat',
246
+ severity: 'medium',
247
+ description: `Outbound HTTP requests in ${scriptsAffected.join(', ')} scripts. Verify destination URLs are legitimate.`,
248
+ attackTechnique: 'Network activity',
249
+ remediation: includeMitigation
250
+ ? 'Check the destination URLs. If unknown or suspicious, remove the package.'
251
+ : undefined,
252
+ confidence: 0.6,
253
+ };
254
+ case 'dns-lookup':
255
+ return {
256
+ type: 'threat',
257
+ severity: 'medium',
258
+ description: `DNS lookups in ${scriptsAffected.join(', ')} scripts. May be used for DNS tunneling data exfiltration.`,
259
+ attackTechnique: 'DNS tunneling',
260
+ remediation: includeMitigation
261
+ ? 'Verify why DNS lookups are needed. If unclear, review the package source code.'
262
+ : undefined,
263
+ confidence: 0.65,
264
+ };
265
+ case 'child-process':
266
+ return {
267
+ type: 'threat',
268
+ severity: 'medium',
269
+ description: `Spawning child processes in ${scriptsAffected.join(', ')} scripts. This is common for build tools but can execute arbitrary commands.`,
270
+ attackTechnique: 'Command execution',
271
+ remediation: includeMitigation
272
+ ? 'If this is a build tool package, it may be legitimate. Otherwise, review what commands are executed.'
273
+ : undefined,
274
+ confidence: 0.5,
275
+ };
276
+ case 'require-resolve':
277
+ return {
278
+ type: 'threat',
279
+ severity: 'medium',
280
+ description: `Dynamic require() calls in ${scriptsAffected.join(', ')} scripts. This can load arbitrary code at runtime.`,
281
+ attackTechnique: 'Dynamic code loading',
282
+ remediation: includeMitigation
283
+ ? 'Determine what modules are being loaded dynamically. If unclear, treat as suspicious.'
284
+ : undefined,
285
+ confidence: 0.6,
286
+ };
287
+ case 'tmp-write':
288
+ return {
289
+ type: 'threat',
290
+ severity: 'medium',
291
+ description: `Writing to temp directory in ${scriptsAffected.join(', ')} scripts. May be used for staging malicious files.`,
292
+ attackTechnique: 'File system activity',
293
+ remediation: includeMitigation
294
+ ? 'Check what files are being written and why. If unclear, review the package source.'
295
+ : undefined,
296
+ confidence: 0.5,
297
+ };
298
+ case 'chmod-exec':
299
+ return {
300
+ type: 'threat',
301
+ severity: 'medium',
302
+ description: `Making files executable in ${scriptsAffected.join(', ')} scripts. Verify what files are affected.`,
303
+ attackTechnique: 'Permission modification',
304
+ remediation: includeMitigation
305
+ ? 'Review what files are being made executable. If not necessary for the package, this is suspicious.'
306
+ : undefined,
307
+ confidence: 0.55,
308
+ };
309
+ case 'unicode-escape':
310
+ return {
311
+ type: 'threat',
312
+ severity: 'medium',
313
+ description: `Unicode-escaped strings in ${scriptsAffected.join(', ')} scripts. May be obfuscating malicious code.`,
314
+ attackTechnique: 'Obfuscation',
315
+ remediation: includeMitigation
316
+ ? 'Unescape the strings to check what they contain. If suspicious, remove the package.'
317
+ : undefined,
318
+ confidence: 0.6,
319
+ };
320
+ default:
321
+ return {
322
+ type: 'threat',
323
+ severity: 'medium',
324
+ description: `Medium-risk pattern "${pattern}" detected in ${scriptsAffected.join(', ')} scripts.`,
325
+ attackTechnique: 'Unknown medium-severity threat',
326
+ remediation: includeMitigation
327
+ ? 'Review the script content to understand if this is legitimate for the package functionality.'
328
+ : undefined,
329
+ confidence: 0.5,
330
+ };
331
+ }
332
+ }
333
+ /**
334
+ * Generate insights for low findings
335
+ */
336
+ function generateLowInsight(findings, analysis) {
337
+ const scriptsAffected = [...new Set(findings.map(f => f.scriptName))];
338
+ return {
339
+ type: 'threat',
340
+ severity: 'low',
341
+ description: `Package ${analysis.name}@${analysis.version} has ${findings.length} low-risk finding${findings.length > 1 ? 's' : ''} in ${scriptsAffected.join(', ')} scripts. These are often lifecycle scripts with no detected malicious patterns - review as needed.`,
342
+ confidence: 0.4,
343
+ };
344
+ }
345
+ /**
346
+ * Generate mitigation guidance for critical findings
347
+ */
348
+ function generateCriticalMitigation(findings, analysis) {
349
+ const steps = [];
350
+ steps.push('IMMEDIATE ACTIONS:');
351
+ steps.push(`1. Uninstall this package: npm uninstall ${analysis.name}`);
352
+ steps.push('2. Review all packages installed around the same time');
353
+ steps.push('3. Check for unauthorized access or data exfiltration');
354
+ steps.push('4. Scan your system for compromise');
355
+ steps.push('5. Rotate any credentials that may have been exposed');
356
+ steps.push('\nINVESTIGATION:');
357
+ steps.push('- Check package installation date and source');
358
+ steps.push('- Review the full script content in node_modules');
359
+ steps.push('- Check network logs for suspicious connections');
360
+ steps.push('- Audit system logs for unusual activity');
361
+ steps.push('\nPREVENTION:');
362
+ steps.push('- Always audit packages before installation');
363
+ steps.push('- Use `npm audit` and `scriptguard scan` regularly');
364
+ steps.push('- Pin dependency versions to prevent surprise updates');
365
+ steps.push('- Consider using a private npm registry');
366
+ steps.push('- Enable 2FA on your npm account');
367
+ return steps.join('\n');
368
+ }
369
+ /**
370
+ * Group findings by severity
371
+ */
372
+ function groupBySeverity(findings) {
373
+ const grouped = {
374
+ low: [],
375
+ medium: [],
376
+ high: [],
377
+ critical: [],
378
+ };
379
+ for (const finding of findings) {
380
+ grouped[finding.riskLevel].push(finding);
381
+ }
382
+ return grouped;
383
+ }
384
+ //# sourceMappingURL=insight-generator.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"insight-generator.js","sourceRoot":"","sources":["../../../src/ai/analyzers/insight-generator.ts"],"names":[],"mappings":";AAAA,uEAAuE;;AAOvE,4CAwBC;AA3BD;;GAEG;AACH,SAAgB,gBAAgB,CAC9B,QAAyB,EACzB,oBAA6B,IAAI;IAEjC,MAAM,QAAQ,GAAgB,EAAE,CAAC;IAEjC,6BAA6B;IAC7B,MAAM,kBAAkB,GAAG,eAAe,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;IAE9D,4CAA4C;IAC5C,KAAK,MAAM,CAAC,QAAQ,EAAE,QAAQ,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,kBAAkB,CAAC,EAAE,CAAC;QACtE,IAAI,QAAQ,CAAC,MAAM,KAAK,CAAC;YAAE,SAAS;QAEpC,MAAM,gBAAgB,GAAG,2BAA2B,CAClD,QAAQ,EACR,QAAqB,EACrB,QAAQ,EACR,iBAAiB,CAClB,CAAC;QAEF,QAAQ,CAAC,IAAI,CAAC,GAAG,gBAAgB,CAAC,CAAC;IACrC,CAAC;IAED,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED;;GAEG;AACH,SAAS,2BAA2B,CAClC,QAAmB,EACnB,QAAmB,EACnB,QAAyB,EACzB,iBAA0B;IAE1B,MAAM,QAAQ,GAAgB,EAAE,CAAC;IAEjC,QAAQ,QAAQ,EAAE,CAAC;QACjB,KAAK,UAAU;YACb,QAAQ,CAAC,IAAI,CAAC,uBAAuB,CAAC,QAAQ,EAAE,QAAQ,EAAE,iBAAiB,CAAC,CAAC,CAAC;YAC9E,MAAM;QAER,KAAK,MAAM;YACT,QAAQ,CAAC,IAAI,CAAC,GAAG,oBAAoB,CAAC,QAAQ,EAAE,QAAQ,EAAE,iBAAiB,CAAC,CAAC,CAAC;YAC9E,MAAM;QAER,KAAK,QAAQ;YACX,QAAQ,CAAC,IAAI,CAAC,GAAG,sBAAsB,CAAC,QAAQ,EAAE,QAAQ,EAAE,iBAAiB,CAAC,CAAC,CAAC;YAChF,MAAM;QAER,KAAK,KAAK;YACR,QAAQ,CAAC,IAAI,CAAC,kBAAkB,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC,CAAC;YACtD,MAAM;IACV,CAAC;IAED,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED;;GAEG;AACH,SAAS,uBAAuB,CAC9B,QAAmB,EACnB,QAAyB,EACzB,iBAA0B;IAE1B,MAAM,WAAW,GAAG,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC;IACjD,MAAM,aAAa,GAAG,CAAC,GAAG,IAAI,GAAG,CAAC,WAAW,CAAC,CAAC,CAAC;IAEhD,MAAM,YAAY,GAAa,EAAE,CAAC;IAClC,MAAM,UAAU,GAAa,EAAE,CAAC;IAEhC,KAAK,MAAM,MAAM,IAAI,aAAa,EAAE,CAAC;QACnC,QAAQ,MAAM,EAAE,CAAC;YACf,KAAK,WAAW,CAAC;YACjB,KAAK,WAAW;gBACd,YAAY,CAAC,IAAI,CAAC,yCAAyC,CAAC,CAAC;gBAC7D,UAAU,CAAC,IAAI,CAAC,0BAA0B,CAAC,CAAC;gBAC5C,MAAM;YAER,KAAK,YAAY;gBACf,YAAY,CAAC,IAAI,CAAC,iCAAiC,CAAC,CAAC;gBACrD,UAAU,CAAC,IAAI,CAAC,kBAAkB,CAAC,CAAC;gBACpC,MAAM;YAER,KAAK,WAAW;gBACd,YAAY,CAAC,IAAI,CAAC,gCAAgC,CAAC,CAAC;gBACpD,UAAU,CAAC,IAAI,CAAC,wBAAwB,CAAC,CAAC;gBAC1C,MAAM;YAER,KAAK,eAAe;gBAClB,YAAY,CAAC,IAAI,CAAC,+BAA+B,CAAC,CAAC;gBACnD,UAAU,CAAC,IAAI,CAAC,8CAA8C,CAAC,CAAC;gBAChE,MAAM;YAER,KAAK,iBAAiB;gBACpB,YAAY,CAAC,IAAI,CAAC,gCAAgC,CAAC,CAAC;gBACpD,UAAU,CAAC,IAAI,CAAC,kBAAkB,CAAC,CAAC;gBACpC,MAAM;YAER,KAAK,aAAa;gBAChB,YAAY,CAAC,IAAI,CAAC,kCAAkC,CAAC,CAAC;gBACtD,UAAU,CAAC,IAAI,CAAC,2BAA2B,CAAC,CAAC;gBAC7C,MAAM;YAER,KAAK,cAAc;gBACjB,YAAY,CAAC,IAAI,CAAC,yCAAyC,CAAC,CAAC;gBAC7D,UAAU,CAAC,IAAI,CAAC,oBAAoB,CAAC,CAAC;gBACtC,MAAM;YAER,KAAK,eAAe;gBAClB,YAAY,CAAC,IAAI,CAAC,iCAAiC,CAAC,CAAC;gBACrD,UAAU,CAAC,IAAI,CAAC,4BAA4B,CAAC,CAAC;gBAC9C,MAAM;YAER;gBACE,YAAY,CAAC,IAAI,CAAC,oBAAoB,MAAM,EAAE,CAAC,CAAC;gBAChD,UAAU,CAAC,IAAI,CAAC,yBAAyB,CAAC,CAAC;QAC/C,CAAC;IACH,CAAC;IAED,OAAO;QACL,IAAI,EAAE,QAAQ;QACd,QAAQ,EAAE,UAAU;QACpB,WAAW,EAAE,WAAW,QAAQ,CAAC,IAAI,IAAI,QAAQ,CAAC,OAAO,aAAa,QAAQ,CAAC,MAAM,2BAA2B,QAAQ,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,KAAK,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC,yCAAyC;QACnN,eAAe,EAAE,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC;QACtC,WAAW,EAAE,iBAAiB,CAAC,CAAC,CAAC,0BAA0B,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC,CAAC,CAAC,SAAS;QAC3F,UAAU,EAAE,IAAI;KACjB,CAAC;AACJ,CAAC;AAED;;GAEG;AACH,SAAS,oBAAoB,CAC3B,QAAmB,EACnB,QAAyB,EACzB,iBAA0B;IAE1B,MAAM,QAAQ,GAAgB,EAAE,CAAC;IAEjC,+CAA+C;IAC/C,MAAM,iBAAiB,GAAG,IAAI,GAAG,EAAqB,CAAC;IACvD,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE,CAAC;QAC/B,MAAM,QAAQ,GAAG,iBAAiB,CAAC,GAAG,CAAC,OAAO,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC;QAC9D,QAAQ,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACvB,iBAAiB,CAAC,GAAG,CAAC,OAAO,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;IACnD,CAAC;IAED,KAAK,MAAM,CAAC,OAAO,EAAE,eAAe,CAAC,IAAI,iBAAiB,EAAE,CAAC;QAC3D,MAAM,OAAO,GAAG,6BAA6B,CAAC,OAAO,EAAE,eAAe,EAAE,QAAQ,EAAE,iBAAiB,CAAC,CAAC;QACrG,QAAQ,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;IACzB,CAAC;IAED,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,SAAS,6BAA6B,CACpC,OAAe,EACf,QAAmB,EACnB,QAAyB,EACzB,iBAA0B;IAE1B,MAAM,eAAe,GAAG,CAAC,GAAG,IAAI,GAAG,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC;IAEtE,QAAQ,OAAO,EAAE,CAAC;QAChB,KAAK,aAAa,CAAC;QACnB,KAAK,WAAW;YACd,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,uCAAuC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,mFAAmF;gBACjK,eAAe,EAAE,sCAAsC;gBACvD,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,0GAA0G;oBAC5G,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ,KAAK,YAAY;YACf,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,sDAAsD,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,4EAA4E;gBACzK,eAAe,EAAE,0BAA0B;gBAC3C,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,8GAA8G;oBAChH,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ,KAAK,YAAY;YACf,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,sCAAsC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,uDAAuD;gBACpI,eAAe,EAAE,6BAA6B;gBAC9C,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,yFAAyF;oBAC3F,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,IAAI;aACjB,CAAC;QAEJ,KAAK,WAAW;YACd,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,gDAAgD,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,oDAAoD;gBAC3I,eAAe,EAAE,0BAA0B;gBAC3C,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,2FAA2F;oBAC7F,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,IAAI;aACjB,CAAC;QAEJ,KAAK,UAAU;YACb,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,yBAAyB,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,wEAAwE;gBACxI,eAAe,EAAE,qBAAqB;gBACtC,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,iIAAiI;oBACnI,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,IAAI;aACjB,CAAC;QAEJ,KAAK,WAAW;YACd,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,sCAAsC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,oEAAoE;gBACjJ,eAAe,EAAE,kBAAkB;gBACnC,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,wHAAwH;oBAC1H,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ,KAAK,kBAAkB;YACrB,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,iCAAiC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,iEAAiE;gBACzI,eAAe,EAAE,YAAY;gBAC7B,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,kGAAkG;oBACpG,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,IAAI;aACjB,CAAC;QAEJ,KAAK,YAAY;YACf,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,mCAAmC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,8DAA8D;gBACxI,eAAe,EAAE,aAAa;gBAC9B,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,iHAAiH;oBACnH,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ;YACE,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,MAAM;gBAChB,WAAW,EAAE,sBAAsB,OAAO,iBAAiB,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,WAAW;gBAChG,eAAe,EAAE,8BAA8B;gBAC/C,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,qFAAqF;oBACvF,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;IACN,CAAC;AACH,CAAC;AAED;;GAEG;AACH,SAAS,sBAAsB,CAC7B,QAAmB,EACnB,QAAyB,EACzB,iBAA0B;IAE1B,MAAM,QAAQ,GAAgB,EAAE,CAAC;IAEjC,mBAAmB;IACnB,MAAM,iBAAiB,GAAG,IAAI,GAAG,EAAqB,CAAC;IACvD,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE,CAAC;QAC/B,MAAM,QAAQ,GAAG,iBAAiB,CAAC,GAAG,CAAC,OAAO,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC;QAC9D,QAAQ,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACvB,iBAAiB,CAAC,GAAG,CAAC,OAAO,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;IACnD,CAAC;IAED,KAAK,MAAM,CAAC,OAAO,EAAE,eAAe,CAAC,IAAI,iBAAiB,EAAE,CAAC;QAC3D,MAAM,OAAO,GAAG,+BAA+B,CAAC,OAAO,EAAE,eAAe,EAAE,QAAQ,EAAE,iBAAiB,CAAC,CAAC;QACvG,QAAQ,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;IACzB,CAAC;IAED,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,SAAS,+BAA+B,CACtC,OAAe,EACf,QAAmB,EACnB,QAAyB,EACzB,iBAA0B;IAE1B,MAAM,eAAe,GAAG,CAAC,GAAG,IAAI,GAAG,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC;IAEtE,QAAQ,OAAO,EAAE,CAAC;QAChB,KAAK,cAAc;YACjB,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,QAAQ;gBAClB,WAAW,EAAE,6BAA6B,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,mDAAmD;gBACvH,eAAe,EAAE,kBAAkB;gBACnC,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,2EAA2E;oBAC7E,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ,KAAK,YAAY;YACf,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,QAAQ;gBAClB,WAAW,EAAE,kBAAkB,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,4DAA4D;gBACrH,eAAe,EAAE,eAAe;gBAChC,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,gFAAgF;oBAClF,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,IAAI;aACjB,CAAC;QAEJ,KAAK,eAAe;YAClB,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,QAAQ;gBAClB,WAAW,EAAE,+BAA+B,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,8EAA8E;gBACpJ,eAAe,EAAE,mBAAmB;gBACpC,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,sGAAsG;oBACxG,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ,KAAK,iBAAiB;YACpB,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,QAAQ;gBAClB,WAAW,EAAE,8BAA8B,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,oDAAoD;gBACzH,eAAe,EAAE,sBAAsB;gBACvC,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,uFAAuF;oBACzF,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ,KAAK,WAAW;YACd,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,QAAQ;gBAClB,WAAW,EAAE,gCAAgC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,oDAAoD;gBAC3H,eAAe,EAAE,sBAAsB;gBACvC,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,oFAAoF;oBACtF,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ,KAAK,YAAY;YACf,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,QAAQ;gBAClB,WAAW,EAAE,8BAA8B,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,2CAA2C;gBAChH,eAAe,EAAE,yBAAyB;gBAC1C,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,oGAAoG;oBACtG,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,IAAI;aACjB,CAAC;QAEJ,KAAK,gBAAgB;YACnB,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,QAAQ;gBAClB,WAAW,EAAE,8BAA8B,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,8CAA8C;gBACnH,eAAe,EAAE,aAAa;gBAC9B,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,qFAAqF;oBACvF,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;QAEJ;YACE,OAAO;gBACL,IAAI,EAAE,QAAQ;gBACd,QAAQ,EAAE,QAAQ;gBAClB,WAAW,EAAE,wBAAwB,OAAO,iBAAiB,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,WAAW;gBAClG,eAAe,EAAE,gCAAgC;gBACjD,WAAW,EAAE,iBAAiB;oBAC5B,CAAC,CAAC,8FAA8F;oBAChG,CAAC,CAAC,SAAS;gBACb,UAAU,EAAE,GAAG;aAChB,CAAC;IACN,CAAC;AACH,CAAC;AAED;;GAEG;AACH,SAAS,kBAAkB,CACzB,QAAmB,EACnB,QAAyB;IAEzB,MAAM,eAAe,GAAG,CAAC,GAAG,IAAI,GAAG,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC;IAEtE,OAAO;QACL,IAAI,EAAE,QAAQ;QACd,QAAQ,EAAE,KAAK;QACf,WAAW,EAAE,WAAW,QAAQ,CAAC,IAAI,IAAI,QAAQ,CAAC,OAAO,QAAQ,QAAQ,CAAC,MAAM,oBAAoB,QAAQ,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,OAAO,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,qGAAqG;QACxQ,UAAU,EAAE,GAAG;KAChB,CAAC;AACJ,CAAC;AAED;;GAEG;AACH,SAAS,0BAA0B,CAAC,QAAmB,EAAE,QAAyB;IAChF,MAAM,KAAK,GAAa,EAAE,CAAC;IAE3B,KAAK,CAAC,IAAI,CAAC,oBAAoB,CAAC,CAAC;IACjC,KAAK,CAAC,IAAI,CAAC,4CAA4C,QAAQ,CAAC,IAAI,EAAE,CAAC,CAAC;IACxE,KAAK,CAAC,IAAI,CAAC,uDAAuD,CAAC,CAAC;IACpE,KAAK,CAAC,IAAI,CAAC,uDAAuD,CAAC,CAAC;IACpE,KAAK,CAAC,IAAI,CAAC,oCAAoC,CAAC,CAAC;IACjD,KAAK,CAAC,IAAI,CAAC,sDAAsD,CAAC,CAAC;IAEnE,KAAK,CAAC,IAAI,CAAC,kBAAkB,CAAC,CAAC;IAC/B,KAAK,CAAC,IAAI,CAAC,8CAA8C,CAAC,CAAC;IAC3D,KAAK,CAAC,IAAI,CAAC,kDAAkD,CAAC,CAAC;IAC/D,KAAK,CAAC,IAAI,CAAC,iDAAiD,CAAC,CAAC;IAC9D,KAAK,CAAC,IAAI,CAAC,0CAA0C,CAAC,CAAC;IAEvD,KAAK,CAAC,IAAI,CAAC,eAAe,CAAC,CAAC;IAC5B,KAAK,CAAC,IAAI,CAAC,6CAA6C,CAAC,CAAC;IAC1D,KAAK,CAAC,IAAI,CAAC,oDAAoD,CAAC,CAAC;IACjE,KAAK,CAAC,IAAI,CAAC,uDAAuD,CAAC,CAAC;IACpE,KAAK,CAAC,IAAI,CAAC,yCAAyC,CAAC,CAAC;IACtD,KAAK,CAAC,IAAI,CAAC,kCAAkC,CAAC,CAAC;IAE/C,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAC1B,CAAC;AAED;;GAEG;AACH,SAAS,eAAe,CAAC,QAAmB;IAC1C,MAAM,OAAO,GAAiC;QAC5C,GAAG,EAAE,EAAE;QACP,MAAM,EAAE,EAAE;QACV,IAAI,EAAE,EAAE;QACR,QAAQ,EAAE,EAAE;KACb,CAAC;IAEF,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE,CAAC;QAC/B,OAAO,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;IAC3C,CAAC;IAED,OAAO,OAAO,CAAC;AACjB,CAAC"}
@@ -0,0 +1,7 @@
1
+ /** ScriptGuard — Advanced threat detector analyzer */
2
+ import type { PackageAnalysis, AIInsight } from '../../types/index.js';
3
+ /**
4
+ * Detect advanced threats that may have been missed by regex patterns
5
+ */
6
+ export declare function detectAdvancedThreats(analysis: PackageAnalysis, aiInsights: AIInsight[]): AIInsight[];
7
+ //# sourceMappingURL=threat-detector.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"threat-detector.d.ts","sourceRoot":"","sources":["../../../src/ai/analyzers/threat-detector.ts"],"names":[],"mappings":"AAAA,sDAAsD;AAEtD,OAAO,KAAK,EAAE,eAAe,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AAEvE;;GAEG;AACH,wBAAgB,qBAAqB,CACnC,QAAQ,EAAE,eAAe,EACzB,UAAU,EAAE,SAAS,EAAE,GACtB,SAAS,EAAE,CAqBb"}
@@ -0,0 +1,249 @@
1
+ "use strict";
2
+ /** ScriptGuard — Advanced threat detector analyzer */
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.detectAdvancedThreats = detectAdvancedThreats;
5
+ /**
6
+ * Detect advanced threats that may have been missed by regex patterns
7
+ */
8
+ function detectAdvancedThreats(analysis, aiInsights) {
9
+ const threats = [];
10
+ // Add AI-identified threats
11
+ for (const insight of aiInsights) {
12
+ if (insight.type === 'threat') {
13
+ threats.push(insight);
14
+ }
15
+ }
16
+ // Run additional detection heuristics
17
+ const obfuscationThreats = detectObfuscation(analysis);
18
+ threats.push(...obfuscationThreats);
19
+ const correlationThreats = detectMultiStageAttacks(analysis);
20
+ threats.push(...correlationThreats);
21
+ const novelThreats = detectNovelPatterns(analysis);
22
+ threats.push(...novelThreats);
23
+ return threats;
24
+ }
25
+ /**
26
+ * Detect obfuscation techniques
27
+ */
28
+ function detectObfuscation(analysis) {
29
+ const threats = [];
30
+ const { scripts, name } = analysis;
31
+ for (const [scriptName, content] of Object.entries(scripts)) {
32
+ // Check for various obfuscation techniques
33
+ // 1. Excessive encoding (base64, hex, unicode)
34
+ const encodingCount = [
35
+ (content.match(/\\x[0-9a-fA-F]{2}/g) || []).length,
36
+ (content.match(/\\u[0-9a-fA-F]{4}/g) || []).length,
37
+ (content.match(/atob\s*\(/g) || []).length,
38
+ (content.match(/btoa\s*\(/g) || []).length,
39
+ (content.match(/Buffer\.from\s*\(/g) || []).length,
40
+ (content.match(/toString\s*\(\s*['"](base64|hex|binary)['"]\s*\)/g) || []).length,
41
+ ].reduce((sum, count) => sum + count, 0);
42
+ if (encodingCount > 3) {
43
+ threats.push({
44
+ type: 'threat',
45
+ severity: 'high',
46
+ description: `Script "${scriptName}" uses extensive encoding (${encodingCount} instances). This is a strong indicator of obfuscated malicious code attempting to hide its true purpose.`,
47
+ attackTechnique: 'Obfuscation via encoding',
48
+ remediation: 'Review the decoded content to understand what the script actually does. Avoid packages with heavily obfuscated lifecycle scripts.',
49
+ confidence: Math.min(0.95, 0.5 + encodingCount * 0.1),
50
+ });
51
+ }
52
+ // 2. String concatenation to hide keywords
53
+ const concatenationPatterns = [
54
+ /['"][\w\s]{1,5}['"]\s*\+\s*['"][\w\s]{1,5}['"]\s*\+\s*['"][\w\s]{1,5}['"]/g,
55
+ /['"][\w\s]{1,5}['"]\s*\+\s*\w+\s*\+\s*['"][\w\s]{1,5}['"]/g,
56
+ ];
57
+ let concatenationCount = 0;
58
+ for (const pattern of concatenationPatterns) {
59
+ const matches = content.match(pattern);
60
+ if (matches)
61
+ concatenationCount += matches.length;
62
+ }
63
+ if (concatenationCount > 2) {
64
+ threats.push({
65
+ type: 'threat',
66
+ severity: 'medium',
67
+ description: `Script "${scriptName}" uses extensive string concatenation (${concatenationCount} instances). This may be used to hide malicious keywords from detection.`,
68
+ attackTechnique: 'Keyword obfuscation',
69
+ remediation: 'Deobfuscate the string concatenations to reveal the actual code. Be suspicious of packages trying to hide what their scripts do.',
70
+ confidence: Math.min(0.85, 0.4 + concatenationCount * 0.15),
71
+ });
72
+ }
73
+ // 3. Eval-like patterns (beyond basic regex)
74
+ const advancedEvalPatterns = [
75
+ /Function\s*\(\s*['"]+[\w\s]*['"]+\s*\)/g, // Function("code")()
76
+ /new\s+Function\s*\(/g,
77
+ /setInterval\s*\(\s*['"]/g, // setInterval("code")
78
+ /setTimeout\s*\(\s*['"]/g, // setTimeout("code")
79
+ /require\s*\(\s*[^'"]*\+/g, // dynamic require
80
+ ];
81
+ for (const pattern of advancedEvalPatterns) {
82
+ if (pattern.test(content)) {
83
+ threats.push({
84
+ type: 'threat',
85
+ severity: 'high',
86
+ description: `Script "${scriptName}" uses dynamic code execution patterns. This allows arbitrary code execution and is commonly used in malware.`,
87
+ attackTechnique: 'Dynamic code execution',
88
+ remediation: 'Avoid packages with dynamic code execution in lifecycle scripts. This is extremely dangerous even if the code looks innocent.',
89
+ confidence: 0.8,
90
+ });
91
+ break; // Only add once per script
92
+ }
93
+ }
94
+ // 4. Polyglot code (code that can execute in multiple contexts)
95
+ const polyglotIndicators = [
96
+ /\/\/\s*@<script>/i, // JavaScript inside HTML
97
+ /\/\*\s*@if\s*\(/, // Conditional compilation
98
+ /<\?[pP][hH][pP]/, // PHP tags
99
+ /<%/g, // ASP tags
100
+ ];
101
+ for (const indicator of polyglotIndicators) {
102
+ if (indicator.test(content)) {
103
+ threats.push({
104
+ type: 'threat',
105
+ severity: 'critical',
106
+ description: `Script "${scriptName}" contains polyglot code patterns. This can execute in multiple contexts and is a hallmark of sophisticated malware.`,
107
+ attackTechnique: 'Polyglot code injection',
108
+ remediation: 'Immediately remove this package. Polyglot code in lifecycle scripts is almost always malicious.',
109
+ confidence: 0.9,
110
+ });
111
+ break;
112
+ }
113
+ }
114
+ }
115
+ return threats;
116
+ }
117
+ /**
118
+ * Detect multi-stage attacks across multiple scripts
119
+ */
120
+ function detectMultiStageAttacks(analysis) {
121
+ const threats = [];
122
+ const { scripts, name } = analysis;
123
+ const scriptNames = Object.keys(scripts);
124
+ if (scriptNames.length < 2) {
125
+ return threats;
126
+ }
127
+ // Check for attack chains across scripts
128
+ // 1. preinstall → postinstall chain (setup then execute)
129
+ if (scripts.preinstall && scripts.postinstall) {
130
+ const preinstallDownloads = /\b(curl|wget|fetch|request|http\.get|axios)\b/i.test(scripts.preinstall);
131
+ const postinstallExecutes = /\b(eval|exec|spawn|bash|sh|node\s+-e)\b/i.test(scripts.postinstall);
132
+ if (preinstallDownloads && postinstallExecutes) {
133
+ threats.push({
134
+ type: 'threat',
135
+ severity: 'critical',
136
+ description: `Multi-stage attack detected: preinstall downloads content, postinstall executes it. This is a classic supply chain attack pattern.`,
137
+ attackTechnique: 'Multi-stage payload delivery',
138
+ remediation: 'Immediately remove this package and review all packages installed around the same time. Scan your system for compromise.',
139
+ confidence: 0.95,
140
+ });
141
+ }
142
+ }
143
+ // 2. Multiple scripts accessing sensitive data
144
+ let sensitiveAccessCount = 0;
145
+ const sensitivePatterns = [
146
+ /~\/\.ssh/, /\.aws/, /process\.env/, /\.env/, /credential/, /secret/, /key/i
147
+ ];
148
+ for (const [scriptName, content] of Object.entries(scripts)) {
149
+ for (const pattern of sensitivePatterns) {
150
+ if (pattern.test(content)) {
151
+ sensitiveAccessCount++;
152
+ break;
153
+ }
154
+ }
155
+ }
156
+ if (sensitiveAccessCount >= 2) {
157
+ threats.push({
158
+ type: 'threat',
159
+ severity: 'high',
160
+ description: `${sensitiveAccessCount} lifecycle scripts access sensitive data. This coordinated access pattern suggests data exfiltration preparation.`,
161
+ attackTechnique: 'Credential harvesting',
162
+ remediation: 'Review all scripts to understand what data they\'re accessing. Consider this package compromised unless you can verify legitimacy.',
163
+ confidence: 0.75,
164
+ });
165
+ }
166
+ // 3. Scripts that create other scripts (persistence mechanism)
167
+ let scriptCreationCount = 0;
168
+ for (const [scriptName, content] of Object.entries(scripts)) {
169
+ const createsScripts = /\b(writeFile|writeFileSync|appendFile|createWriteStream|\.js|\.sh|\.bash)\b/i.test(content);
170
+ if (createsScripts) {
171
+ scriptCreationCount++;
172
+ }
173
+ }
174
+ if (scriptCreationCount >= 2) {
175
+ threats.push({
176
+ type: 'threat',
177
+ severity: 'high',
178
+ description: `${scriptCreationCount} lifecycle scripts create files. This may be a persistence mechanism to maintain access after installation.`,
179
+ attackTechnique: 'Persistence via file creation',
180
+ remediation: 'Search for any unusual files created by this package. Check for newly created scripts in node_modules, /tmp, or home directory.',
181
+ confidence: 0.7,
182
+ });
183
+ }
184
+ return threats;
185
+ }
186
+ /**
187
+ * Detect novel attack patterns not covered by regex rules
188
+ */
189
+ function detectNovelPatterns(analysis) {
190
+ const threats = [];
191
+ const { scripts, name, findings } = analysis;
192
+ // 1. Packages with no regex findings but suspicious behavior
193
+ if (findings.length === 0 && Object.keys(scripts).length > 0) {
194
+ const hasComplexScript = Object.values(scripts).some(content => content.length > 300 || content.includes('&&') || content.includes('||'));
195
+ if (hasComplexScript) {
196
+ threats.push({
197
+ type: 'threat',
198
+ severity: 'low',
199
+ description: `Package has complex lifecycle scripts but didn't match known malicious patterns. This doesn't mean it's safe - novel attacks may not match existing rules.`,
200
+ attackTechnique: 'Unknown / novel attack',
201
+ remediation: 'Manually review all lifecycle scripts. Consider whether the functionality is necessary and if you trust the package maintainer.',
202
+ confidence: 0.4,
203
+ });
204
+ }
205
+ }
206
+ // 2. Suspicious package naming patterns
207
+ const suspiciousNaming = [
208
+ /update/i, /patch/i, /fix/i, /critical/i, /security/i,
209
+ /urgent/i, /important/i, /official/i, /verified/i
210
+ ];
211
+ for (const pattern of suspiciousNaming) {
212
+ if (pattern.test(name) && !isWellKnownPackage(name)) {
213
+ threats.push({
214
+ type: 'threat',
215
+ severity: 'medium',
216
+ description: `Package name "${name}" includes urgency/authority keywords. Attackers often use such names to trick users into installing malicious packages.`,
217
+ attackTechnique: 'Typosquatting / impersonation',
218
+ remediation: 'Verify this is the official package. Check spelling, publisher, and download count. Look for the official package instead.',
219
+ confidence: 0.6,
220
+ });
221
+ break;
222
+ }
223
+ }
224
+ // 3. Recently created packages with invasive scripts
225
+ // (We can't check creation date without npm registry API, but we can flag for review)
226
+ if (Object.keys(scripts).length > 2) {
227
+ threats.push({
228
+ type: 'threat',
229
+ severity: 'low',
230
+ description: `Package has ${Object.keys(scripts).length} lifecycle scripts. Most legitimate packages only need 1-2. Multiple scripts may indicate unnecessary complexity or malicious intent.`,
231
+ attackTechnique: 'Excessive script footprint',
232
+ remediation: 'Review each script to understand its purpose. Be suspicious of packages with more lifecycle scripts than necessary.',
233
+ confidence: 0.5,
234
+ });
235
+ }
236
+ return threats;
237
+ }
238
+ /**
239
+ * Check if package is well-known/legitimate
240
+ */
241
+ function isWellKnownPackage(packageName) {
242
+ const knownPackages = [
243
+ 'eslint', 'prettier', 'typescript', 'babel', 'webpack',
244
+ 'vite', 'rollup', 'esbuild', 'jest', 'vitest',
245
+ 'lodash', 'axios', 'react', 'vue', 'angular'
246
+ ];
247
+ return knownPackages.some(known => packageName.startsWith(known));
248
+ }
249
+ //# sourceMappingURL=threat-detector.js.map