hackmyagent 0.16.5 → 0.17.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/.integrity-manifest.json +1 -1
- package/dist/arp/crypto/hybrid-signing.d.ts +107 -0
- package/dist/arp/crypto/hybrid-signing.d.ts.map +1 -0
- package/dist/arp/crypto/hybrid-signing.js +321 -0
- package/dist/arp/crypto/hybrid-signing.js.map +1 -0
- package/dist/arp/crypto/index.d.ts +13 -0
- package/dist/arp/crypto/index.d.ts.map +1 -0
- package/dist/arp/crypto/index.js +33 -0
- package/dist/arp/crypto/index.js.map +1 -0
- package/dist/arp/crypto/manifest-loader.d.ts +117 -0
- package/dist/arp/crypto/manifest-loader.d.ts.map +1 -0
- package/dist/arp/crypto/manifest-loader.js +361 -0
- package/dist/arp/crypto/manifest-loader.js.map +1 -0
- package/dist/arp/crypto/types.d.ts +69 -0
- package/dist/arp/crypto/types.d.ts.map +1 -0
- package/dist/arp/crypto/types.js +11 -0
- package/dist/arp/crypto/types.js.map +1 -0
- package/dist/arp/index.d.ts +28 -1
- package/dist/arp/index.d.ts.map +1 -1
- package/dist/arp/index.js +97 -4
- package/dist/arp/index.js.map +1 -1
- package/dist/arp/intelligence/behavioral-risk-server.d.ts +82 -0
- package/dist/arp/intelligence/behavioral-risk-server.d.ts.map +1 -0
- package/dist/arp/intelligence/behavioral-risk-server.js +258 -0
- package/dist/arp/intelligence/behavioral-risk-server.js.map +1 -0
- package/dist/arp/intelligence/behavioral-risk.d.ts +217 -0
- package/dist/arp/intelligence/behavioral-risk.d.ts.map +1 -0
- package/dist/arp/intelligence/behavioral-risk.js +429 -0
- package/dist/arp/intelligence/behavioral-risk.js.map +1 -0
- package/dist/arp/intelligence/coordinator.d.ts +93 -2
- package/dist/arp/intelligence/coordinator.d.ts.map +1 -1
- package/dist/arp/intelligence/coordinator.js +281 -1
- package/dist/arp/intelligence/coordinator.js.map +1 -1
- package/dist/arp/intelligence/guard-anomaly.d.ts +349 -0
- package/dist/arp/intelligence/guard-anomaly.d.ts.map +1 -0
- package/dist/arp/intelligence/guard-anomaly.js +399 -0
- package/dist/arp/intelligence/guard-anomaly.js.map +1 -0
- package/dist/arp/intelligence/nanomind-l1.d.ts +37 -0
- package/dist/arp/intelligence/nanomind-l1.d.ts.map +1 -1
- package/dist/arp/intelligence/nanomind-l1.js +78 -0
- package/dist/arp/intelligence/nanomind-l1.js.map +1 -1
- package/dist/arp/intelligence/runtime-twin.d.ts +157 -0
- package/dist/arp/intelligence/runtime-twin.d.ts.map +1 -0
- package/dist/arp/intelligence/runtime-twin.js +479 -0
- package/dist/arp/intelligence/runtime-twin.js.map +1 -0
- package/dist/arp/intelligence/verify-classification.d.ts +124 -0
- package/dist/arp/intelligence/verify-classification.d.ts.map +1 -0
- package/dist/arp/intelligence/verify-classification.js +329 -0
- package/dist/arp/intelligence/verify-classification.js.map +1 -0
- package/dist/arp/proxy/server.d.ts +38 -8
- package/dist/arp/proxy/server.d.ts.map +1 -1
- package/dist/arp/proxy/server.js +89 -0
- package/dist/arp/proxy/server.js.map +1 -1
- package/dist/arp/types.d.ts +229 -1
- package/dist/arp/types.d.ts.map +1 -1
- package/dist/cli.js +691 -154
- package/dist/cli.js.map +1 -1
- package/dist/hardening/scanner.d.ts.map +1 -1
- package/dist/hardening/scanner.js +11 -1
- package/dist/hardening/scanner.js.map +1 -1
- package/dist/nanomind-core/compiler/semantic-compiler.d.ts.map +1 -1
- package/dist/nanomind-core/compiler/semantic-compiler.js +170 -10
- package/dist/nanomind-core/compiler/semantic-compiler.js.map +1 -1
- package/dist/nanomind-core/compiler/source-code-preprocessor.d.ts +64 -0
- package/dist/nanomind-core/compiler/source-code-preprocessor.d.ts.map +1 -0
- package/dist/nanomind-core/compiler/source-code-preprocessor.js +656 -0
- package/dist/nanomind-core/compiler/source-code-preprocessor.js.map +1 -0
- package/dist/nanomind-core/ingestion/artifact-parser.d.ts.map +1 -1
- package/dist/nanomind-core/ingestion/artifact-parser.js +15 -6
- package/dist/nanomind-core/ingestion/artifact-parser.js.map +1 -1
- package/package.json +3 -1
|
@@ -0,0 +1,361 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Capability manifest YAML loader with hybrid Ed25519+ML-DSA-65 signature
|
|
4
|
+
* verification.
|
|
5
|
+
*
|
|
6
|
+
* The loader implements parse-to-deny (CR-001): any failure at any step --
|
|
7
|
+
* I/O, oversized file, YAML parse error, schema mismatch, missing signature,
|
|
8
|
+
* wrong algorithm, malformed public key, signature rejection, or expiry --
|
|
9
|
+
* raises a `CapabilityManifestError`. Callers must treat the thrown error as
|
|
10
|
+
* an authoritative signal to refuse loading the manifest. There is no
|
|
11
|
+
* partial-success path.
|
|
12
|
+
*
|
|
13
|
+
* Wire format (YAML on disk):
|
|
14
|
+
*
|
|
15
|
+
* version: "1.0.0"
|
|
16
|
+
* agentId: "example-agent"
|
|
17
|
+
* tier: "execute"
|
|
18
|
+
* comply:
|
|
19
|
+
* permitted_classes: ["class-a", "class-b"]
|
|
20
|
+
* prohibited_classes: ["class-c"]
|
|
21
|
+
* on_violation: "deny"
|
|
22
|
+
* issuedAt: "2026-04-13T00:00:00.000Z"
|
|
23
|
+
* expiresAt: "2027-04-13T00:00:00.000Z"
|
|
24
|
+
* ed25519PublicKey: "<base64>"
|
|
25
|
+
* mldsa65PublicKey: "<base64>"
|
|
26
|
+
* signature:
|
|
27
|
+
* alg: "Ed25519+ML-DSA-65"
|
|
28
|
+
* ed25519Sig: "<base64>"
|
|
29
|
+
* mldsaSig: "<base64>"
|
|
30
|
+
* ts: 1712880000000
|
|
31
|
+
*
|
|
32
|
+
* The signed payload is the manifest object with the `signature` field
|
|
33
|
+
* stripped, serialized to canonical JSON (sorted keys, no whitespace). Signer
|
|
34
|
+
* and verifier must produce byte-identical canonical output or round-tripping
|
|
35
|
+
* will not work. The closed schema (scalars + string arrays + one nested
|
|
36
|
+
* object) is simple enough that full RFC 8785 JCS is unnecessary; the
|
|
37
|
+
* `stableStringify` helper below is deterministic for the shapes we accept.
|
|
38
|
+
*
|
|
39
|
+
* Integration points (deferred to follow-up sessions, not wired yet):
|
|
40
|
+
* - `src/arp/proxy/server.ts`: load manifest on agent registration, fail
|
|
41
|
+
* closed if verification raises.
|
|
42
|
+
* - `src/arp/intelligence/coordinator.ts`: consult the `comply` envelope
|
|
43
|
+
* when an event's classification lands outside permitted classes.
|
|
44
|
+
*/
|
|
45
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
46
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
47
|
+
};
|
|
48
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
49
|
+
exports.CapabilityManifestError = exports.MAX_MANIFEST_SIZE_BYTES = exports.MANIFEST_SIGNATURE_ALGORITHM = exports.MANIFEST_VERSION = void 0;
|
|
50
|
+
exports.canonicalizeManifestPayload = canonicalizeManifestPayload;
|
|
51
|
+
exports.loadCapabilityManifest = loadCapabilityManifest;
|
|
52
|
+
exports.parseCapabilityManifest = parseCapabilityManifest;
|
|
53
|
+
const fs_1 = require("fs");
|
|
54
|
+
const js_yaml_1 = __importDefault(require("js-yaml"));
|
|
55
|
+
const hybrid_signing_1 = require("./hybrid-signing");
|
|
56
|
+
/** Only wire format version currently accepted. */
|
|
57
|
+
exports.MANIFEST_VERSION = '1.0.0';
|
|
58
|
+
/**
|
|
59
|
+
* Only hybrid algorithm permitted for capability manifests. ML-DSA-65 is the
|
|
60
|
+
* NIST category 3 parameter set, matching the AIM SDK default for manifests.
|
|
61
|
+
* ML-DSA-44 is reserved for high-throughput identity signals; ML-DSA-87 for
|
|
62
|
+
* root keys. Manifests that claim a different algorithm are refused.
|
|
63
|
+
*/
|
|
64
|
+
exports.MANIFEST_SIGNATURE_ALGORITHM = 'Ed25519+ML-DSA-65';
|
|
65
|
+
/**
|
|
66
|
+
* Hard cap on the manifest file size. Anything larger is rejected before
|
|
67
|
+
* YAML parsing to bound worst-case memory and CPU for a malicious file. 64
|
|
68
|
+
* KiB is ample: a realistic manifest with a few hundred permitted classes
|
|
69
|
+
* and base64 public keys sits well under 8 KiB.
|
|
70
|
+
*/
|
|
71
|
+
exports.MAX_MANIFEST_SIZE_BYTES = 64 * 1024;
|
|
72
|
+
/** Allowed capability tiers (kept in sync with `CapabilityTier` in ../types). */
|
|
73
|
+
const ALLOWED_TIERS = new Set([
|
|
74
|
+
'minimal',
|
|
75
|
+
'read',
|
|
76
|
+
'execute',
|
|
77
|
+
'mutate',
|
|
78
|
+
'privileged',
|
|
79
|
+
]);
|
|
80
|
+
/** Allowed on_violation actions (kept in sync with `ComplyOnViolation`). */
|
|
81
|
+
const ALLOWED_ON_VIOLATION = new Set(['log', 'alert', 'pause', 'kill', 'deny']);
|
|
82
|
+
/**
|
|
83
|
+
* Error raised on any loader failure. Callers MUST treat a thrown
|
|
84
|
+
* `CapabilityManifestError` as an authoritative parse-to-deny signal. Do not
|
|
85
|
+
* fall through to a "load without verification" path under any circumstance.
|
|
86
|
+
*/
|
|
87
|
+
class CapabilityManifestError extends Error {
|
|
88
|
+
constructor(code, message, details) {
|
|
89
|
+
super(`[arp/crypto/manifest] ${code}: ${message}`);
|
|
90
|
+
this.code = code;
|
|
91
|
+
this.details = details;
|
|
92
|
+
this.name = 'CapabilityManifestError';
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
exports.CapabilityManifestError = CapabilityManifestError;
|
|
96
|
+
/**
|
|
97
|
+
* Produce canonical signed-payload bytes for a parsed manifest object.
|
|
98
|
+
*
|
|
99
|
+
* Canonicalization:
|
|
100
|
+
* 1. Remove the `signature` field if present.
|
|
101
|
+
* 2. Serialize as JSON with recursively sorted object keys and no
|
|
102
|
+
* whitespace between tokens.
|
|
103
|
+
* 3. Encode the result as UTF-8.
|
|
104
|
+
*
|
|
105
|
+
* Exported because fixture generators and out-of-repo signers need to
|
|
106
|
+
* produce the exact same bytes as the verifier. Duplicating this logic in a
|
|
107
|
+
* signer is a recipe for drift.
|
|
108
|
+
*/
|
|
109
|
+
function canonicalizeManifestPayload(payload) {
|
|
110
|
+
const stripped = { ...payload };
|
|
111
|
+
delete stripped.signature;
|
|
112
|
+
return new TextEncoder().encode(stableStringify(stripped));
|
|
113
|
+
}
|
|
114
|
+
/**
|
|
115
|
+
* Deterministic JSON serializer: sorted object keys, no whitespace. Accepts
|
|
116
|
+
* the closed set of JSON-compatible values that manifest payloads contain
|
|
117
|
+
* (string, number, boolean, null, array, plain object). Any other value
|
|
118
|
+
* type is serialized via `JSON.stringify`, which will produce `undefined`
|
|
119
|
+
* for functions or symbols -- the schema guards prevent those from reaching
|
|
120
|
+
* this helper in practice.
|
|
121
|
+
*/
|
|
122
|
+
function stableStringify(value) {
|
|
123
|
+
if (value === null || typeof value !== 'object')
|
|
124
|
+
return JSON.stringify(value);
|
|
125
|
+
if (Array.isArray(value)) {
|
|
126
|
+
return `[${value.map((v) => stableStringify(v)).join(',')}]`;
|
|
127
|
+
}
|
|
128
|
+
const obj = value;
|
|
129
|
+
const keys = Object.keys(obj).sort();
|
|
130
|
+
const pairs = keys.map((k) => `${JSON.stringify(k)}:${stableStringify(obj[k])}`);
|
|
131
|
+
return `{${pairs.join(',')}}`;
|
|
132
|
+
}
|
|
133
|
+
/**
|
|
134
|
+
* Load and verify a capability manifest from a YAML file on disk.
|
|
135
|
+
*
|
|
136
|
+
* On success, returns the verified `CapabilityManifest` shape (without the
|
|
137
|
+
* signature block, which is not part of the runtime type). On any failure
|
|
138
|
+
* throws a `CapabilityManifestError` -- the caller fails closed.
|
|
139
|
+
*
|
|
140
|
+
* The file is read once, size-checked, then parsed and verified. I/O errors
|
|
141
|
+
* are reported with `code: 'IO_ERROR'` and the underlying error exposed via
|
|
142
|
+
* `details.cause` so callers can log the root cause without re-throwing.
|
|
143
|
+
*/
|
|
144
|
+
async function loadCapabilityManifest(filePath) {
|
|
145
|
+
let raw;
|
|
146
|
+
try {
|
|
147
|
+
const stat = await fs_1.promises.stat(filePath);
|
|
148
|
+
if (stat.size > exports.MAX_MANIFEST_SIZE_BYTES) {
|
|
149
|
+
throw new CapabilityManifestError('SIZE_EXCEEDED', `manifest file exceeds ${exports.MAX_MANIFEST_SIZE_BYTES} bytes`, { reason: `size=${stat.size}` });
|
|
150
|
+
}
|
|
151
|
+
raw = await fs_1.promises.readFile(filePath, 'utf8');
|
|
152
|
+
}
|
|
153
|
+
catch (err) {
|
|
154
|
+
if (err instanceof CapabilityManifestError)
|
|
155
|
+
throw err;
|
|
156
|
+
throw new CapabilityManifestError('IO_ERROR', `unable to read manifest at ${filePath}`, { reason: err.message, cause: err });
|
|
157
|
+
}
|
|
158
|
+
return parseCapabilityManifest(raw);
|
|
159
|
+
}
|
|
160
|
+
/**
|
|
161
|
+
* Parse and verify a capability manifest from YAML text.
|
|
162
|
+
*
|
|
163
|
+
* Separated from `loadCapabilityManifest` so callers that already have the
|
|
164
|
+
* text in memory (pulled from a database, stdin, IPC channel) can verify
|
|
165
|
+
* without a filesystem round trip.
|
|
166
|
+
*/
|
|
167
|
+
async function parseCapabilityManifest(yamlText) {
|
|
168
|
+
if (typeof yamlText !== 'string') {
|
|
169
|
+
throw new CapabilityManifestError('PARSE_ERROR', 'manifest text must be a string');
|
|
170
|
+
}
|
|
171
|
+
if (Buffer.byteLength(yamlText, 'utf8') > exports.MAX_MANIFEST_SIZE_BYTES) {
|
|
172
|
+
throw new CapabilityManifestError('SIZE_EXCEEDED', `manifest text exceeds ${exports.MAX_MANIFEST_SIZE_BYTES} bytes`);
|
|
173
|
+
}
|
|
174
|
+
let parsed;
|
|
175
|
+
try {
|
|
176
|
+
parsed = js_yaml_1.default.load(yamlText, {
|
|
177
|
+
// FAILSAFE_SCHEMA would reject base64 strings that look like YAML
|
|
178
|
+
// booleans. CORE_SCHEMA accepts the scalars we use (string, number,
|
|
179
|
+
// bool, null) without executing YAML type coercions like !!js/function.
|
|
180
|
+
schema: js_yaml_1.default.CORE_SCHEMA,
|
|
181
|
+
filename: 'capability-manifest.yaml',
|
|
182
|
+
});
|
|
183
|
+
}
|
|
184
|
+
catch (err) {
|
|
185
|
+
throw new CapabilityManifestError('PARSE_ERROR', 'YAML parse failed', { reason: err.message, cause: err });
|
|
186
|
+
}
|
|
187
|
+
if (parsed === null || typeof parsed !== 'object' || Array.isArray(parsed)) {
|
|
188
|
+
throw new CapabilityManifestError('SCHEMA_ERROR', 'manifest root must be a YAML mapping');
|
|
189
|
+
}
|
|
190
|
+
const obj = parsed;
|
|
191
|
+
// Version gate first. Rejecting unsupported versions before touching any
|
|
192
|
+
// other field lets us evolve the wire format without leaking half-parsed
|
|
193
|
+
// data from a newer schema into a validator that does not understand it.
|
|
194
|
+
const version = obj.version;
|
|
195
|
+
if (version !== exports.MANIFEST_VERSION) {
|
|
196
|
+
throw new CapabilityManifestError('VERSION_UNSUPPORTED', `unsupported manifest version`, { reason: `got=${JSON.stringify(version)} expected=${exports.MANIFEST_VERSION}` });
|
|
197
|
+
}
|
|
198
|
+
// Signature block presence check comes before schema validation so that a
|
|
199
|
+
// manifest missing a signature fails with the more specific error code.
|
|
200
|
+
// An attacker who strips the signature block should see the same rejection
|
|
201
|
+
// regardless of whether the remaining schema is well-formed.
|
|
202
|
+
const sigRaw = obj.signature;
|
|
203
|
+
if (sigRaw === undefined || sigRaw === null) {
|
|
204
|
+
throw new CapabilityManifestError('SIGNATURE_MISSING', 'manifest has no signature block');
|
|
205
|
+
}
|
|
206
|
+
if (typeof sigRaw !== 'object' || Array.isArray(sigRaw)) {
|
|
207
|
+
throw new CapabilityManifestError('SIGNATURE_MISSING', 'signature block must be a mapping');
|
|
208
|
+
}
|
|
209
|
+
// Schema validation of the payload itself. Narrow order: every required
|
|
210
|
+
// field must be present and of the correct shape before we run any crypto.
|
|
211
|
+
const schemaError = validateManifestSchema(obj);
|
|
212
|
+
if (schemaError) {
|
|
213
|
+
throw new CapabilityManifestError('SCHEMA_ERROR', schemaError);
|
|
214
|
+
}
|
|
215
|
+
// Structural signature checks. Algorithm gate is strict: anything other
|
|
216
|
+
// than the required manifest algorithm is refused outright rather than
|
|
217
|
+
// downgraded.
|
|
218
|
+
const sig = sigRaw;
|
|
219
|
+
const alg = sig.alg;
|
|
220
|
+
if (alg !== exports.MANIFEST_SIGNATURE_ALGORITHM) {
|
|
221
|
+
throw new CapabilityManifestError('ALGORITHM_UNSUPPORTED', `signature algorithm must be ${exports.MANIFEST_SIGNATURE_ALGORITHM}`, { reason: `got=${JSON.stringify(alg)}` });
|
|
222
|
+
}
|
|
223
|
+
if (typeof sig.ed25519Sig !== 'string' ||
|
|
224
|
+
typeof sig.mldsaSig !== 'string' ||
|
|
225
|
+
typeof sig.ts !== 'number') {
|
|
226
|
+
throw new CapabilityManifestError('SCHEMA_ERROR', 'signature block fields malformed', {
|
|
227
|
+
reason: `ed25519Sig=${typeof sig.ed25519Sig} mldsaSig=${typeof sig.mldsaSig} ts=${typeof sig.ts}`,
|
|
228
|
+
});
|
|
229
|
+
}
|
|
230
|
+
// Decode keys and signature into raw bytes. Any failure here (bad base64,
|
|
231
|
+
// wrong size after decode) becomes a KEY_FORMAT_ERROR so callers can
|
|
232
|
+
// distinguish "signature cryptographically wrong" from "signature bytes
|
|
233
|
+
// structurally invalid".
|
|
234
|
+
let publicKeyBytes;
|
|
235
|
+
let signatureBytes;
|
|
236
|
+
try {
|
|
237
|
+
const encodedPk = {
|
|
238
|
+
algorithm: exports.MANIFEST_SIGNATURE_ALGORITHM,
|
|
239
|
+
ed25519PublicKey: obj.ed25519PublicKey,
|
|
240
|
+
mldsaPublicKey: obj.mldsa65PublicKey,
|
|
241
|
+
mldsaVariant: 'ML-DSA-65',
|
|
242
|
+
};
|
|
243
|
+
publicKeyBytes = (0, hybrid_signing_1.decodeHybridPublicKey)(encodedPk);
|
|
244
|
+
const encodedSig = {
|
|
245
|
+
alg: exports.MANIFEST_SIGNATURE_ALGORITHM,
|
|
246
|
+
ed25519Sig: sig.ed25519Sig,
|
|
247
|
+
mldsaSig: sig.mldsaSig,
|
|
248
|
+
ts: sig.ts,
|
|
249
|
+
};
|
|
250
|
+
signatureBytes = (0, hybrid_signing_1.decodeHybridSignature)(encodedSig);
|
|
251
|
+
}
|
|
252
|
+
catch (err) {
|
|
253
|
+
throw new CapabilityManifestError('KEY_FORMAT_ERROR', 'failed to decode hybrid key or signature bytes', { reason: err.message, cause: err });
|
|
254
|
+
}
|
|
255
|
+
// Node's `Buffer.from(_, 'base64')` is permissive: invalid characters are
|
|
256
|
+
// silently dropped and the result is whatever byte length falls out. Catch
|
|
257
|
+
// size mismatches here so the caller sees KEY_FORMAT_ERROR rather than a
|
|
258
|
+
// downstream SIGNATURE_INVALID that hides a structurally malformed key.
|
|
259
|
+
if (!(0, hybrid_signing_1.validateKeySize)('Ed25519', 'publicKey', publicKeyBytes.ed25519PublicKey)) {
|
|
260
|
+
throw new CapabilityManifestError('KEY_FORMAT_ERROR', 'ed25519 public key has wrong length after base64 decode', { reason: `length=${publicKeyBytes.ed25519PublicKey.length}` });
|
|
261
|
+
}
|
|
262
|
+
if (!(0, hybrid_signing_1.validateKeySize)('ML-DSA-65', 'publicKey', publicKeyBytes.mldsaPublicKey)) {
|
|
263
|
+
throw new CapabilityManifestError('KEY_FORMAT_ERROR', 'ml-dsa-65 public key has wrong length after base64 decode', { reason: `length=${publicKeyBytes.mldsaPublicKey.length}` });
|
|
264
|
+
}
|
|
265
|
+
if (!(0, hybrid_signing_1.validateKeySize)('Ed25519', 'signature', signatureBytes.ed25519Sig)) {
|
|
266
|
+
throw new CapabilityManifestError('KEY_FORMAT_ERROR', 'ed25519 signature has wrong length after base64 decode', { reason: `length=${signatureBytes.ed25519Sig.length}` });
|
|
267
|
+
}
|
|
268
|
+
if (!(0, hybrid_signing_1.validateKeySize)('ML-DSA-65', 'signature', signatureBytes.mldsaSig)) {
|
|
269
|
+
throw new CapabilityManifestError('KEY_FORMAT_ERROR', 'ml-dsa-65 signature has wrong length after base64 decode', { reason: `length=${signatureBytes.mldsaSig.length}` });
|
|
270
|
+
}
|
|
271
|
+
// Canonicalize the signed payload (the original parsed object minus the
|
|
272
|
+
// signature block) and run the non-short-circuit hybrid verifier. Both
|
|
273
|
+
// halves are evaluated on every call; a structured `{valid: false, reason}`
|
|
274
|
+
// result comes back on any mismatch and becomes SIGNATURE_INVALID here.
|
|
275
|
+
const canonical = canonicalizeManifestPayload(obj);
|
|
276
|
+
const result = await (0, hybrid_signing_1.hybridVerify)(canonical, signatureBytes, publicKeyBytes);
|
|
277
|
+
if (!result.valid) {
|
|
278
|
+
throw new CapabilityManifestError('SIGNATURE_INVALID', 'hybrid signature rejected', { reason: result.reason ?? 'no reason provided by verifier' });
|
|
279
|
+
}
|
|
280
|
+
// Expiry check runs LAST, after signature verification, so an attacker who
|
|
281
|
+
// manipulates expiresAt cannot force a cheap rejection path that reveals
|
|
282
|
+
// anything about the signature state. Even a valid signature over an
|
|
283
|
+
// expired manifest is denied.
|
|
284
|
+
if (typeof obj.expiresAt === 'string') {
|
|
285
|
+
const expiresAtMs = Date.parse(obj.expiresAt);
|
|
286
|
+
if (!Number.isFinite(expiresAtMs)) {
|
|
287
|
+
throw new CapabilityManifestError('SCHEMA_ERROR', 'expiresAt is not a valid ISO timestamp', { reason: `got=${obj.expiresAt}` });
|
|
288
|
+
}
|
|
289
|
+
if (expiresAtMs <= Date.now()) {
|
|
290
|
+
throw new CapabilityManifestError('EXPIRED', 'manifest expiresAt has passed', { reason: `expiresAt=${obj.expiresAt}` });
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
// The runtime shape: everything except the signature block.
|
|
294
|
+
const manifest = {
|
|
295
|
+
version: exports.MANIFEST_VERSION,
|
|
296
|
+
agentId: obj.agentId,
|
|
297
|
+
tier: obj.tier,
|
|
298
|
+
comply: {
|
|
299
|
+
permitted_classes: obj.comply
|
|
300
|
+
.permitted_classes.slice(),
|
|
301
|
+
prohibited_classes: obj.comply
|
|
302
|
+
.prohibited_classes.slice(),
|
|
303
|
+
on_violation: obj.comply
|
|
304
|
+
.on_violation,
|
|
305
|
+
},
|
|
306
|
+
issuedAt: obj.issuedAt,
|
|
307
|
+
...(typeof obj.expiresAt === 'string'
|
|
308
|
+
? { expiresAt: obj.expiresAt }
|
|
309
|
+
: {}),
|
|
310
|
+
ed25519PublicKey: obj.ed25519PublicKey,
|
|
311
|
+
mldsa65PublicKey: obj.mldsa65PublicKey,
|
|
312
|
+
};
|
|
313
|
+
return manifest;
|
|
314
|
+
}
|
|
315
|
+
/**
|
|
316
|
+
* Schema validation for the non-signature fields. Returns a human-readable
|
|
317
|
+
* error string if validation fails, or `null` on success. Kept as a
|
|
318
|
+
* string-returning helper (rather than throwing) so the caller can wrap the
|
|
319
|
+
* result in a single typed error with the correct code.
|
|
320
|
+
*/
|
|
321
|
+
function validateManifestSchema(obj) {
|
|
322
|
+
if (typeof obj.agentId !== 'string' || obj.agentId.length === 0) {
|
|
323
|
+
return 'agentId must be a non-empty string';
|
|
324
|
+
}
|
|
325
|
+
if (typeof obj.tier !== 'string' || !ALLOWED_TIERS.has(obj.tier)) {
|
|
326
|
+
return `tier must be one of ${Array.from(ALLOWED_TIERS).join(', ')}`;
|
|
327
|
+
}
|
|
328
|
+
if (typeof obj.issuedAt !== 'string' || !Number.isFinite(Date.parse(obj.issuedAt))) {
|
|
329
|
+
return 'issuedAt must be an ISO timestamp string';
|
|
330
|
+
}
|
|
331
|
+
if (obj.expiresAt !== undefined &&
|
|
332
|
+
obj.expiresAt !== null &&
|
|
333
|
+
typeof obj.expiresAt !== 'string') {
|
|
334
|
+
return 'expiresAt must be an ISO timestamp string or omitted';
|
|
335
|
+
}
|
|
336
|
+
if (typeof obj.ed25519PublicKey !== 'string' || obj.ed25519PublicKey.length === 0) {
|
|
337
|
+
return 'ed25519PublicKey must be a non-empty base64 string';
|
|
338
|
+
}
|
|
339
|
+
if (typeof obj.mldsa65PublicKey !== 'string' || obj.mldsa65PublicKey.length === 0) {
|
|
340
|
+
return 'mldsa65PublicKey must be a non-empty base64 string';
|
|
341
|
+
}
|
|
342
|
+
const comply = obj.comply;
|
|
343
|
+
if (comply === null || typeof comply !== 'object' || Array.isArray(comply)) {
|
|
344
|
+
return 'comply must be a mapping';
|
|
345
|
+
}
|
|
346
|
+
const c = comply;
|
|
347
|
+
if (!Array.isArray(c.permitted_classes) ||
|
|
348
|
+
!c.permitted_classes.every((v) => typeof v === 'string')) {
|
|
349
|
+
return 'comply.permitted_classes must be an array of strings';
|
|
350
|
+
}
|
|
351
|
+
if (!Array.isArray(c.prohibited_classes) ||
|
|
352
|
+
!c.prohibited_classes.every((v) => typeof v === 'string')) {
|
|
353
|
+
return 'comply.prohibited_classes must be an array of strings';
|
|
354
|
+
}
|
|
355
|
+
if (typeof c.on_violation !== 'string' ||
|
|
356
|
+
!ALLOWED_ON_VIOLATION.has(c.on_violation)) {
|
|
357
|
+
return `comply.on_violation must be one of ${Array.from(ALLOWED_ON_VIOLATION).join(', ')}`;
|
|
358
|
+
}
|
|
359
|
+
return null;
|
|
360
|
+
}
|
|
361
|
+
//# sourceMappingURL=manifest-loader.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"manifest-loader.js","sourceRoot":"","sources":["../../../src/arp/crypto/manifest-loader.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ARP crypto types (scaffolding, AIComply P1).
|
|
3
|
+
*
|
|
4
|
+
* Shared shapes for hybrid Ed25519 + ML-DSA signing. The first commit lands only
|
|
5
|
+
* these types and stub functions. The follow-up commit wires real signing against
|
|
6
|
+
* `@noble/ed25519` and `@noble/post-quantum`, mirroring
|
|
7
|
+
* `agent-identity-management/sdk/typescript/src/crypto/pqc.ts`.
|
|
8
|
+
*/
|
|
9
|
+
/** Supported ML-DSA parameter sets (FIPS 204). */
|
|
10
|
+
export type MLDsaVariant = 'ML-DSA-44' | 'ML-DSA-65' | 'ML-DSA-87';
|
|
11
|
+
/** Hybrid algorithm identifier, matching the AIM SDK and Go backend wire format. */
|
|
12
|
+
export type HybridAlgorithm = 'Ed25519+ML-DSA-44' | 'Ed25519+ML-DSA-65' | 'Ed25519+ML-DSA-87';
|
|
13
|
+
/**
|
|
14
|
+
* Hybrid key pair: Ed25519 (classical) plus ML-DSA (post-quantum).
|
|
15
|
+
* Both halves co-sign every payload; verification requires both to pass.
|
|
16
|
+
*/
|
|
17
|
+
export interface HybridKeyPair {
|
|
18
|
+
algorithm: HybridAlgorithm;
|
|
19
|
+
ed25519: {
|
|
20
|
+
publicKey: Uint8Array;
|
|
21
|
+
privateKey: Uint8Array;
|
|
22
|
+
};
|
|
23
|
+
mldsa: {
|
|
24
|
+
variant: MLDsaVariant;
|
|
25
|
+
publicKey: Uint8Array;
|
|
26
|
+
privateKey: Uint8Array;
|
|
27
|
+
};
|
|
28
|
+
createdAt: Date;
|
|
29
|
+
}
|
|
30
|
+
/** Hybrid public key in raw (non-encoded) form, used for verification. */
|
|
31
|
+
export interface HybridPublicKey {
|
|
32
|
+
algorithm: HybridAlgorithm;
|
|
33
|
+
ed25519PublicKey: Uint8Array;
|
|
34
|
+
mldsaPublicKey: Uint8Array;
|
|
35
|
+
mldsaVariant: MLDsaVariant;
|
|
36
|
+
}
|
|
37
|
+
/** Hybrid signature: both halves must validate for the signature to be accepted. */
|
|
38
|
+
export interface HybridSignature {
|
|
39
|
+
algorithm: HybridAlgorithm;
|
|
40
|
+
ed25519Sig: Uint8Array;
|
|
41
|
+
mldsaSig: Uint8Array;
|
|
42
|
+
/** Unix ms timestamp when the signature was produced */
|
|
43
|
+
timestamp: number;
|
|
44
|
+
}
|
|
45
|
+
/** Base64-encoded form of a hybrid signature (for YAML/JSON transport). */
|
|
46
|
+
export interface EncodedHybridSignature {
|
|
47
|
+
alg: HybridAlgorithm;
|
|
48
|
+
ed25519Sig: string;
|
|
49
|
+
mldsaSig: string;
|
|
50
|
+
ts: number;
|
|
51
|
+
}
|
|
52
|
+
/** Base64-encoded form of a hybrid public key (for YAML/JSON transport). */
|
|
53
|
+
export interface EncodedHybridPublicKey {
|
|
54
|
+
algorithm: HybridAlgorithm;
|
|
55
|
+
ed25519PublicKey: string;
|
|
56
|
+
mldsaPublicKey: string;
|
|
57
|
+
mldsaVariant: MLDsaVariant;
|
|
58
|
+
}
|
|
59
|
+
/** Result of a hybrid signature verification. */
|
|
60
|
+
export interface HybridVerifyResult {
|
|
61
|
+
/** True only if BOTH ed25519 and mldsa halves verify successfully. */
|
|
62
|
+
valid: boolean;
|
|
63
|
+
/** Per-half breakdown, for diagnostics and structured logging. */
|
|
64
|
+
ed25519Valid: boolean;
|
|
65
|
+
mldsaValid: boolean;
|
|
66
|
+
/** Human-readable reason when `valid` is false. */
|
|
67
|
+
reason?: string;
|
|
68
|
+
}
|
|
69
|
+
//# sourceMappingURL=types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/arp/crypto/types.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,kDAAkD;AAClD,MAAM,MAAM,YAAY,GAAG,WAAW,GAAG,WAAW,GAAG,WAAW,CAAC;AAEnE,oFAAoF;AACpF,MAAM,MAAM,eAAe,GACvB,mBAAmB,GACnB,mBAAmB,GACnB,mBAAmB,CAAC;AAExB;;;GAGG;AACH,MAAM,WAAW,aAAa;IAC5B,SAAS,EAAE,eAAe,CAAC;IAC3B,OAAO,EAAE;QACP,SAAS,EAAE,UAAU,CAAC;QACtB,UAAU,EAAE,UAAU,CAAC;KACxB,CAAC;IACF,KAAK,EAAE;QACL,OAAO,EAAE,YAAY,CAAC;QACtB,SAAS,EAAE,UAAU,CAAC;QACtB,UAAU,EAAE,UAAU,CAAC;KACxB,CAAC;IACF,SAAS,EAAE,IAAI,CAAC;CACjB;AAED,0EAA0E;AAC1E,MAAM,WAAW,eAAe;IAC9B,SAAS,EAAE,eAAe,CAAC;IAC3B,gBAAgB,EAAE,UAAU,CAAC;IAC7B,cAAc,EAAE,UAAU,CAAC;IAC3B,YAAY,EAAE,YAAY,CAAC;CAC5B;AAED,oFAAoF;AACpF,MAAM,WAAW,eAAe;IAC9B,SAAS,EAAE,eAAe,CAAC;IAC3B,UAAU,EAAE,UAAU,CAAC;IACvB,QAAQ,EAAE,UAAU,CAAC;IACrB,wDAAwD;IACxD,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,2EAA2E;AAC3E,MAAM,WAAW,sBAAsB;IACrC,GAAG,EAAE,eAAe,CAAC;IACrB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;IACjB,EAAE,EAAE,MAAM,CAAC;CACZ;AAED,4EAA4E;AAC5E,MAAM,WAAW,sBAAsB;IACrC,SAAS,EAAE,eAAe,CAAC;IAC3B,gBAAgB,EAAE,MAAM,CAAC;IACzB,cAAc,EAAE,MAAM,CAAC;IACvB,YAAY,EAAE,YAAY,CAAC;CAC5B;AAED,iDAAiD;AACjD,MAAM,WAAW,kBAAkB;IACjC,sEAAsE;IACtE,KAAK,EAAE,OAAO,CAAC;IACf,kEAAkE;IAClE,YAAY,EAAE,OAAO,CAAC;IACtB,UAAU,EAAE,OAAO,CAAC;IACpB,mDAAmD;IACnD,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* ARP crypto types (scaffolding, AIComply P1).
|
|
4
|
+
*
|
|
5
|
+
* Shared shapes for hybrid Ed25519 + ML-DSA signing. The first commit lands only
|
|
6
|
+
* these types and stub functions. The follow-up commit wires real signing against
|
|
7
|
+
* `@noble/ed25519` and `@noble/post-quantum`, mirroring
|
|
8
|
+
* `agent-identity-management/sdk/typescript/src/crypto/pqc.ts`.
|
|
9
|
+
*/
|
|
10
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
11
|
+
//# sourceMappingURL=types.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.js","sourceRoot":"","sources":["../../../src/arp/crypto/types.ts"],"names":[],"mappings":";AAAA;;;;;;;GAOG"}
|
package/dist/arp/index.d.ts
CHANGED
|
@@ -5,7 +5,7 @@ export { CorrelationEngine } from './engine/correlation';
|
|
|
5
5
|
export { IntelligenceCoordinator } from './intelligence/coordinator';
|
|
6
6
|
export { BudgetController } from './intelligence/budget';
|
|
7
7
|
export { AnomalyDetector } from './intelligence/anomaly';
|
|
8
|
-
export {
|
|
8
|
+
export { RuntimeTwin } from './intelligence/runtime-twin';
|
|
9
9
|
export { AnthropicAdapter, OpenAIAdapter, OllamaAdapter, createAdapter, autoDetectAdapter } from './intelligence/adapters';
|
|
10
10
|
export { ProcessMonitor } from './monitors/process';
|
|
11
11
|
export { NetworkMonitor } from './monitors/network';
|
|
@@ -28,6 +28,7 @@ export { GTINForwarder, generateSensorToken, buildGTINPayload, submitGTINEvent,
|
|
|
28
28
|
import type { ARPConfig, ARPEvent } from './types';
|
|
29
29
|
import { EventEngine } from './engine/event-engine';
|
|
30
30
|
import { IntelligenceCoordinator } from './intelligence/coordinator';
|
|
31
|
+
import { RuntimeTwin } from './intelligence/runtime-twin';
|
|
31
32
|
import { EnforcementEngine, type AlertCallback } from './enforcement/kill-switch';
|
|
32
33
|
/**
|
|
33
34
|
* Agent Runtime Protection — the main entry point.
|
|
@@ -52,6 +53,23 @@ export declare class AgentRuntimeProtection {
|
|
|
52
53
|
private readonly monitors;
|
|
53
54
|
private gtinForwarder;
|
|
54
55
|
private running;
|
|
56
|
+
/**
|
|
57
|
+
* In-process runtime twin (behavioral anomaly scorer). Held for the
|
|
58
|
+
* lifetime of the ARP instance, attached to the event engine in
|
|
59
|
+
* start() so every event trains the twin's baseline. Null when the
|
|
60
|
+
* runtime twin is disabled in config.
|
|
61
|
+
*/
|
|
62
|
+
private readonly runtimeTwin;
|
|
63
|
+
/**
|
|
64
|
+
* Transport-agnostic view of the runtime twin passed to the
|
|
65
|
+
* coordinator. Null when the twin is disabled.
|
|
66
|
+
*/
|
|
67
|
+
private readonly behavioralRiskSource;
|
|
68
|
+
/**
|
|
69
|
+
* Classification drift detector. Non-null only when the caller
|
|
70
|
+
* provided a baseline in `config.intelligence.guardAnomaly.baseline`.
|
|
71
|
+
*/
|
|
72
|
+
private readonly guardAnomaly;
|
|
55
73
|
constructor(configOrPath?: ARPConfig | string);
|
|
56
74
|
/** Start all monitors */
|
|
57
75
|
start(): Promise<void>;
|
|
@@ -83,5 +101,14 @@ export declare class AgentRuntimeProtection {
|
|
|
83
101
|
getEngine(): EventEngine;
|
|
84
102
|
/** Get the enforcement engine (for test harnesses) */
|
|
85
103
|
getEnforcement(): EnforcementEngine;
|
|
104
|
+
/**
|
|
105
|
+
* Get the intelligence coordinator. Exposed so tests can assert the
|
|
106
|
+
* coordinator was constructed with the expected behavioral risk and
|
|
107
|
+
* guard anomaly sources, and so advanced integrations can swap
|
|
108
|
+
* sources at runtime via `setBehavioralRiskSource` / `setGuardAnomaly`.
|
|
109
|
+
*/
|
|
110
|
+
getIntelligence(): IntelligenceCoordinator;
|
|
111
|
+
/** The runtime twin instance, or null when disabled. */
|
|
112
|
+
getRuntimeTwin(): RuntimeTwin | null;
|
|
86
113
|
}
|
|
87
114
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/arp/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/arp/index.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,OAAO,UAAU,CAAC;AAG/B,YAAY,EACV,SAAS,EACT,QAAQ,EACR,WAAW,EACX,aAAa,EACb,aAAa,EACb,UAAU,EACV,cAAc,EACd,aAAa,EACb,WAAW,EACX,kBAAkB,EAClB,WAAW,EACX,SAAS,EACT,cAAc,EACd,aAAa,EACb,iBAAiB,EACjB,aAAa,EACb,WAAW,EACX,aAAa,EACb,iBAAiB,EACjB,iBAAiB,EACjB,OAAO,EACP,UAAU,GACX,MAAM,SAAS,CAAC;AAGjB,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AACpD,OAAO,EAAE,iBAAiB,EAAE,MAAM,sBAAsB,CAAC;AACzD,OAAO,EAAE,uBAAuB,EAAE,MAAM,4BAA4B,CAAC;AACrE,OAAO,EAAE,gBAAgB,EAAE,MAAM,uBAAuB,CAAC;AACzD,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AACzD,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/arp/index.ts"],"names":[],"mappings":"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"}
|