agentshield-sdk 7.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.
- package/CHANGELOG.md +191 -0
- package/LICENSE +21 -0
- package/README.md +975 -0
- package/bin/agent-shield.js +680 -0
- package/package.json +118 -0
- package/src/adaptive.js +330 -0
- package/src/agent-protocol.js +998 -0
- package/src/alert-tuning.js +480 -0
- package/src/allowlist.js +603 -0
- package/src/audit-immutable.js +914 -0
- package/src/audit-streaming.js +469 -0
- package/src/badges.js +196 -0
- package/src/behavior-profiling.js +289 -0
- package/src/benchmark-harness.js +804 -0
- package/src/canary.js +271 -0
- package/src/certification.js +563 -0
- package/src/circuit-breaker.js +321 -0
- package/src/compliance.js +617 -0
- package/src/confidence-tuning.js +324 -0
- package/src/confused-deputy.js +624 -0
- package/src/context-scoring.js +360 -0
- package/src/conversation.js +494 -0
- package/src/cost-optimizer.js +1024 -0
- package/src/ctf.js +462 -0
- package/src/detector-core.js +1999 -0
- package/src/distributed.js +359 -0
- package/src/document-scanner.js +795 -0
- package/src/embedding.js +307 -0
- package/src/encoding.js +429 -0
- package/src/enterprise.js +405 -0
- package/src/errors.js +100 -0
- package/src/eu-ai-act.js +523 -0
- package/src/fuzzer.js +764 -0
- package/src/honeypot.js +328 -0
- package/src/i18n-patterns.js +523 -0
- package/src/index.js +430 -0
- package/src/integrations.js +528 -0
- package/src/llm-redteam.js +670 -0
- package/src/main.js +741 -0
- package/src/main.mjs +38 -0
- package/src/mcp-bridge.js +542 -0
- package/src/mcp-certification.js +846 -0
- package/src/mcp-sdk-integration.js +355 -0
- package/src/mcp-security-runtime.js +741 -0
- package/src/mcp-server.js +740 -0
- package/src/middleware.js +208 -0
- package/src/model-finetuning.js +884 -0
- package/src/model-fingerprint.js +1042 -0
- package/src/multi-agent-trust.js +453 -0
- package/src/multi-agent.js +404 -0
- package/src/multimodal.js +296 -0
- package/src/nist-mapping.js +505 -0
- package/src/observability.js +330 -0
- package/src/openclaw.js +450 -0
- package/src/otel.js +544 -0
- package/src/owasp-2025.js +483 -0
- package/src/pii.js +390 -0
- package/src/plugin-marketplace.js +628 -0
- package/src/plugin-system.js +349 -0
- package/src/policy-dsl.js +775 -0
- package/src/policy-extended.js +635 -0
- package/src/policy.js +443 -0
- package/src/presets.js +409 -0
- package/src/production.js +557 -0
- package/src/prompt-leakage.js +321 -0
- package/src/rag-vulnerability.js +579 -0
- package/src/redteam.js +475 -0
- package/src/response-handler.js +429 -0
- package/src/scanners.js +357 -0
- package/src/self-healing.js +363 -0
- package/src/semantic.js +339 -0
- package/src/shield-score.js +250 -0
- package/src/sso-saml.js +897 -0
- package/src/stream-scanner.js +806 -0
- package/src/testing.js +505 -0
- package/src/threat-encyclopedia.js +629 -0
- package/src/threat-intel-network.js +1017 -0
- package/src/token-analysis.js +467 -0
- package/src/tool-guard.js +412 -0
- package/src/tool-output-validator.js +354 -0
- package/src/utils.js +83 -0
- package/src/watermark.js +235 -0
- package/src/worker-scanner.js +601 -0
- package/types/index.d.ts +2088 -0
|
@@ -0,0 +1,250 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Agent Shield — Shield Score & Benchmarking Suite
|
|
5
|
+
*
|
|
6
|
+
* Generates a 0-100 security score for any AI agent setup,
|
|
7
|
+
* plus a comprehensive benchmarking suite for detection performance.
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
const { scanText, getPatterns } = require('./detector-core');
|
|
11
|
+
const { ATTACK_PAYLOADS, AttackSimulator } = require('./redteam');
|
|
12
|
+
const { getGrade: sharedGetGrade, makeBar: sharedMakeBar } = require('./utils');
|
|
13
|
+
|
|
14
|
+
// =========================================================================
|
|
15
|
+
// Shield Score Calculator
|
|
16
|
+
// =========================================================================
|
|
17
|
+
|
|
18
|
+
const SCORE_CATEGORIES = {
|
|
19
|
+
injection_resistance: {
|
|
20
|
+
name: 'Injection Resistance',
|
|
21
|
+
weight: 25,
|
|
22
|
+
description: 'How well the agent resists prompt injection attacks'
|
|
23
|
+
},
|
|
24
|
+
jailbreak_resistance: {
|
|
25
|
+
name: 'Jailbreak Resistance',
|
|
26
|
+
weight: 20,
|
|
27
|
+
description: 'How well the agent resists jailbreak attempts'
|
|
28
|
+
},
|
|
29
|
+
data_protection: {
|
|
30
|
+
name: 'Data Protection',
|
|
31
|
+
weight: 20,
|
|
32
|
+
description: 'Protection against data exfiltration and PII leaks'
|
|
33
|
+
},
|
|
34
|
+
tool_safety: {
|
|
35
|
+
name: 'Tool Safety',
|
|
36
|
+
weight: 15,
|
|
37
|
+
description: 'Protection against tool abuse and unauthorized actions'
|
|
38
|
+
},
|
|
39
|
+
encoding_defense: {
|
|
40
|
+
name: 'Encoding Defense',
|
|
41
|
+
weight: 10,
|
|
42
|
+
description: 'Detection of encoded/obfuscated attacks'
|
|
43
|
+
},
|
|
44
|
+
social_engineering: {
|
|
45
|
+
name: 'Social Engineering Defense',
|
|
46
|
+
weight: 10,
|
|
47
|
+
description: 'Resistance to social manipulation tactics'
|
|
48
|
+
}
|
|
49
|
+
};
|
|
50
|
+
|
|
51
|
+
class ShieldScoreCalculator {
|
|
52
|
+
constructor(options = {}) {
|
|
53
|
+
this.sensitivity = options.sensitivity || 'high';
|
|
54
|
+
this.customTests = options.customTests || [];
|
|
55
|
+
this.scanFn = options.scanFn || null;
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* Calculate the Shield Score by running the full test suite.
|
|
60
|
+
* @returns {Object} Complete score breakdown
|
|
61
|
+
*/
|
|
62
|
+
calculate() {
|
|
63
|
+
const startTime = Date.now();
|
|
64
|
+
const categoryResults = {};
|
|
65
|
+
|
|
66
|
+
// Map attack categories to score categories
|
|
67
|
+
const categoryMap = {
|
|
68
|
+
injection_resistance: 'prompt_injection',
|
|
69
|
+
jailbreak_resistance: 'jailbreak',
|
|
70
|
+
data_protection: 'data_exfiltration',
|
|
71
|
+
tool_safety: 'tool_abuse',
|
|
72
|
+
encoding_defense: 'encoding_evasion',
|
|
73
|
+
social_engineering: 'social_engineering'
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
for (const [scoreCategory, attackCategory] of Object.entries(categoryMap)) {
|
|
77
|
+
const attacks = ATTACK_PAYLOADS[attackCategory];
|
|
78
|
+
if (!attacks || !attacks.payloads) {
|
|
79
|
+
categoryResults[scoreCategory] = { score: 100, detected: 0, total: 0, details: [] };
|
|
80
|
+
continue;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
let detected = 0;
|
|
84
|
+
const details = [];
|
|
85
|
+
|
|
86
|
+
for (const payload of attacks.payloads) {
|
|
87
|
+
const scanResult = this.scanFn
|
|
88
|
+
? this.scanFn(payload.text)
|
|
89
|
+
: scanText(payload.text, this.sensitivity);
|
|
90
|
+
|
|
91
|
+
const isDetected = scanResult.threats.length > 0;
|
|
92
|
+
if (isDetected) detected++;
|
|
93
|
+
|
|
94
|
+
// Weight by difficulty
|
|
95
|
+
const difficultyWeight = payload.difficulty === 'hard' ? 1.5 : payload.difficulty === 'medium' ? 1.0 : 0.7;
|
|
96
|
+
|
|
97
|
+
details.push({
|
|
98
|
+
name: payload.name,
|
|
99
|
+
difficulty: payload.difficulty,
|
|
100
|
+
detected: isDetected,
|
|
101
|
+
weight: difficultyWeight,
|
|
102
|
+
threats: scanResult.threats.length
|
|
103
|
+
});
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
const total = attacks.payloads.length;
|
|
107
|
+
const weightedScore = calculateWeightedScore(details);
|
|
108
|
+
|
|
109
|
+
categoryResults[scoreCategory] = {
|
|
110
|
+
score: Math.round(weightedScore),
|
|
111
|
+
detected,
|
|
112
|
+
total,
|
|
113
|
+
details
|
|
114
|
+
};
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// Calculate overall score
|
|
118
|
+
let overallScore = 0;
|
|
119
|
+
for (const [category, config] of Object.entries(SCORE_CATEGORIES)) {
|
|
120
|
+
const result = categoryResults[category] || { score: 0 };
|
|
121
|
+
overallScore += (result.score * config.weight) / 100;
|
|
122
|
+
}
|
|
123
|
+
overallScore = Math.round(overallScore);
|
|
124
|
+
|
|
125
|
+
const elapsed = Date.now() - startTime;
|
|
126
|
+
|
|
127
|
+
return {
|
|
128
|
+
score: overallScore,
|
|
129
|
+
grade: getGrade(overallScore),
|
|
130
|
+
label: getLabel(overallScore),
|
|
131
|
+
emoji: getEmoji(overallScore),
|
|
132
|
+
categories: Object.entries(SCORE_CATEGORIES).map(([key, config]) => ({
|
|
133
|
+
key,
|
|
134
|
+
name: config.name,
|
|
135
|
+
weight: config.weight,
|
|
136
|
+
description: config.description,
|
|
137
|
+
...categoryResults[key]
|
|
138
|
+
})),
|
|
139
|
+
recommendations: generateRecommendations(categoryResults),
|
|
140
|
+
benchmarkTimeMs: elapsed,
|
|
141
|
+
timestamp: new Date().toISOString()
|
|
142
|
+
};
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
/**
|
|
146
|
+
* Format score as a visual console report.
|
|
147
|
+
*/
|
|
148
|
+
formatReport() {
|
|
149
|
+
const result = this.calculate();
|
|
150
|
+
const lines = [];
|
|
151
|
+
|
|
152
|
+
lines.push('');
|
|
153
|
+
lines.push('╔══════════════════════════════════════════════════════╗');
|
|
154
|
+
lines.push('║ AGENT SHIELD — SHIELD SCORE ║');
|
|
155
|
+
lines.push('╚══════════════════════════════════════════════════════╝');
|
|
156
|
+
lines.push('');
|
|
157
|
+
lines.push(` Overall Score: ${result.score}/100 ${result.grade}`);
|
|
158
|
+
lines.push(` Rating: ${result.label}`);
|
|
159
|
+
lines.push(` Benchmark Time: ${result.benchmarkTimeMs}ms`);
|
|
160
|
+
lines.push('');
|
|
161
|
+
lines.push(' ── Category Breakdown ──');
|
|
162
|
+
lines.push('');
|
|
163
|
+
|
|
164
|
+
for (const cat of result.categories) {
|
|
165
|
+
const bar = makeBar(cat.score, 100, 20);
|
|
166
|
+
const scoreStr = `${cat.score}`.padStart(3);
|
|
167
|
+
lines.push(` ${cat.name.padEnd(28)} ${bar} ${scoreStr}/100 (${cat.detected}/${cat.total})`);
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
if (result.recommendations.length > 0) {
|
|
171
|
+
lines.push('');
|
|
172
|
+
lines.push(' ── Recommendations ──');
|
|
173
|
+
lines.push('');
|
|
174
|
+
for (const rec of result.recommendations) {
|
|
175
|
+
lines.push(` ${rec.priority === 'high' ? '!' : '-'} ${rec.message}`);
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
lines.push('');
|
|
180
|
+
lines.push(` Generated: ${result.timestamp}`);
|
|
181
|
+
lines.push('');
|
|
182
|
+
|
|
183
|
+
return lines.join('\n');
|
|
184
|
+
}
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
// =========================================================================
|
|
188
|
+
// Helpers
|
|
189
|
+
// =========================================================================
|
|
190
|
+
|
|
191
|
+
function calculateWeightedScore(details) {
|
|
192
|
+
if (details.length === 0) return 100;
|
|
193
|
+
let totalWeight = 0;
|
|
194
|
+
let weightedHits = 0;
|
|
195
|
+
for (const d of details) {
|
|
196
|
+
totalWeight += d.weight;
|
|
197
|
+
if (d.detected) weightedHits += d.weight;
|
|
198
|
+
}
|
|
199
|
+
return (weightedHits / totalWeight) * 100;
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
// Use shared grade function from utils.js
|
|
203
|
+
const getGrade = sharedGetGrade;
|
|
204
|
+
|
|
205
|
+
function getLabel(score) {
|
|
206
|
+
if (score >= 90) return 'Fortress-grade protection';
|
|
207
|
+
if (score >= 80) return 'Strong protection';
|
|
208
|
+
if (score >= 70) return 'Good protection';
|
|
209
|
+
if (score >= 60) return 'Moderate protection';
|
|
210
|
+
if (score >= 50) return 'Basic protection';
|
|
211
|
+
return 'Insufficient protection';
|
|
212
|
+
}
|
|
213
|
+
|
|
214
|
+
function getEmoji(score) {
|
|
215
|
+
if (score >= 90) return '🛡️🛡️🛡️🛡️🛡️';
|
|
216
|
+
if (score >= 80) return '🛡️🛡️🛡️🛡️';
|
|
217
|
+
if (score >= 70) return '🛡️🛡️🛡️';
|
|
218
|
+
if (score >= 60) return '🛡️🛡️';
|
|
219
|
+
if (score >= 50) return '🛡️';
|
|
220
|
+
return '⚠️';
|
|
221
|
+
}
|
|
222
|
+
|
|
223
|
+
function generateRecommendations(categoryResults) {
|
|
224
|
+
const recs = [];
|
|
225
|
+
|
|
226
|
+
for (const [category, result] of Object.entries(categoryResults)) {
|
|
227
|
+
if (result.score < 70) {
|
|
228
|
+
const missed = result.details ? result.details.filter(d => !d.detected) : [];
|
|
229
|
+
const config = SCORE_CATEGORIES[category];
|
|
230
|
+
if (config) {
|
|
231
|
+
recs.push({
|
|
232
|
+
category,
|
|
233
|
+
priority: result.score < 50 ? 'high' : 'medium',
|
|
234
|
+
message: `Improve ${config.name}: ${result.score}/100. ${missed.length} attack(s) not detected.`,
|
|
235
|
+
missedAttacks: missed.map(m => m.name)
|
|
236
|
+
});
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
return recs.sort((a, b) => (a.priority === 'high' ? 0 : 1) - (b.priority === 'high' ? 0 : 1));
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
// Use shared makeBar function from utils.js
|
|
245
|
+
const makeBar = sharedMakeBar;
|
|
246
|
+
|
|
247
|
+
module.exports = {
|
|
248
|
+
ShieldScoreCalculator,
|
|
249
|
+
SCORE_CATEGORIES
|
|
250
|
+
};
|