@blamejs/core 0.7.106 → 0.8.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 (51) hide show
  1. package/CHANGELOG.md +19 -1
  2. package/NOTICE +17 -1
  3. package/README.md +4 -3
  4. package/index.js +16 -0
  5. package/lib/asyncapi-bindings.js +160 -0
  6. package/lib/asyncapi-traits.js +143 -0
  7. package/lib/asyncapi.js +531 -0
  8. package/lib/audit.js +6 -0
  9. package/lib/auth/acr-vocabulary.js +265 -0
  10. package/lib/auth/auth-time-tracker.js +111 -0
  11. package/lib/auth/elevation-grant.js +306 -0
  12. package/lib/auth/sd-jwt-vc-disclosure.js +95 -0
  13. package/lib/auth/sd-jwt-vc-holder.js +203 -0
  14. package/lib/auth/sd-jwt-vc-issuer.js +197 -0
  15. package/lib/auth/sd-jwt-vc.js +526 -0
  16. package/lib/auth/step-up-policy.js +335 -0
  17. package/lib/auth/step-up.js +445 -0
  18. package/lib/compliance-ai-act-logging.js +186 -0
  19. package/lib/compliance-ai-act-prohibited.js +205 -0
  20. package/lib/compliance-ai-act-risk.js +189 -0
  21. package/lib/compliance-ai-act-transparency.js +200 -0
  22. package/lib/compliance-ai-act.js +558 -0
  23. package/lib/compliance.js +2 -0
  24. package/lib/crypto.js +32 -0
  25. package/lib/flag-cache.js +136 -0
  26. package/lib/flag-evaluation-context.js +135 -0
  27. package/lib/flag-providers.js +279 -0
  28. package/lib/flag-targeting.js +210 -0
  29. package/lib/flag.js +284 -0
  30. package/lib/inbox.js +367 -0
  31. package/lib/mail-arc-sign.js +372 -0
  32. package/lib/mail-auth.js +2 -0
  33. package/lib/middleware/ai-act-disclosure.js +166 -0
  34. package/lib/middleware/asyncapi-serve.js +136 -0
  35. package/lib/middleware/flag-context.js +76 -0
  36. package/lib/middleware/index.js +15 -0
  37. package/lib/middleware/openapi-serve.js +143 -0
  38. package/lib/middleware/require-step-up.js +186 -0
  39. package/lib/openapi-paths-builder.js +248 -0
  40. package/lib/openapi-schema-walk.js +192 -0
  41. package/lib/openapi-security.js +169 -0
  42. package/lib/openapi-yaml.js +154 -0
  43. package/lib/openapi.js +443 -0
  44. package/lib/pqc-software.js +195 -0
  45. package/lib/vault/index.js +3 -0
  46. package/lib/vault-aad.js +259 -0
  47. package/lib/vendor/MANIFEST.json +29 -0
  48. package/lib/vendor/noble-post-quantum.cjs +18 -0
  49. package/lib/ws-client.js +829 -0
  50. package/package.json +1 -1
  51. package/sbom.cyclonedx.json +6 -6
@@ -0,0 +1,558 @@
1
+ "use strict";
2
+ /**
3
+ * b.compliance.aiAct — EU AI Act (Regulation (EU) 2024/1689) compliance
4
+ * primitive.
5
+ *
6
+ * Public surface (b.compliance.aiAct.*):
7
+ *
8
+ * .classify(systemDescription)
9
+ * → { tier, prohibitedHits[], annexIIIHits[], obligations[] }
10
+ *
11
+ * .prohibited.{listPractices,listIds,getPractice,classify}
12
+ * .risk.{listAnnexIII,getAnnexIII,classifyAnnexIII,isHighRisk,obligationsFor}
13
+ * .transparency.{banner,htmlBanner,watermark,jsonLdDisclosure,metaTags}
14
+ * .logging.{buildEvent,emit,logEvent,retentionFloorMs,loggerFor}
15
+ * .gpai.{classify, listObligations} (Article 51-55)
16
+ * .deadlines (Article 113)
17
+ * .articleObligations(article)
18
+ *
19
+ * Per the no-MVP rule: every spec'd surface above is implemented; the
20
+ * five Annex III §1-8 use-cases plus the eight Article 5 prohibited
21
+ * practices plus the four Article 50 transparency obligations all ship
22
+ * here. GPAI obligations (Article 51-55) ship as a sibling helper.
23
+ *
24
+ * Operators integrate via the framework's compliance-posture flow:
25
+ *
26
+ * var assessment = b.compliance.aiAct.classify({
27
+ * purpose: "credit-scoring",
28
+ * deployContext: "consumer-finance",
29
+ * deployerType: "private-company",
30
+ * });
31
+ * // assessment.tier === "high-risk"
32
+ * // assessment.annexIIIHits === ["essential-services"]
33
+ * // assessment.obligations === [...Art-9..15 obligations]
34
+ *
35
+ * The framework does NOT perform legal interpretation — operators
36
+ * remain responsible for engaging counsel before deployment.
37
+ */
38
+
39
+ var validateOpts = require("./validate-opts");
40
+ var lazyRequire = require("./lazy-require");
41
+ var { ComplianceError } = require("./framework-error");
42
+
43
+ var prohibited = require("./compliance-ai-act-prohibited");
44
+ var risk = require("./compliance-ai-act-risk");
45
+ var transparency = require("./compliance-ai-act-transparency");
46
+ var logging = require("./compliance-ai-act-logging");
47
+ var audit = lazyRequire(function () { return require("./audit"); });
48
+
49
+ // ---- Article 113 deadline calendar ----
50
+ //
51
+ // Per Art. 113, different parts of the regulation phase in:
52
+ //
53
+ // 2024-08-01 — Regulation enters into force
54
+ // 2026-02-02 — Chapters I (general) + II (prohibited practices)
55
+ // become applicable
56
+ // 2026-08-02 — Chapter V (general-purpose AI) + Chapter X-XI obligations
57
+ // applicable; transparency obligations applicable
58
+ // 2027-08-02 — Chapter III (high-risk AI systems) become applicable
59
+ // for products covered by Art. 6(1) Annex I third-party
60
+ // conformity assessment
61
+ // 2027-08-02 — Member states designate competent authorities
62
+
63
+ var DEADLINES = Object.freeze({
64
+ enteredForce: "2024-08-01",
65
+ prohibitedPractices: "2026-02-02",
66
+ generalPurposeAI: "2026-08-02",
67
+ transparencyObligations: "2026-08-02",
68
+ highRiskAnnexIII: "2027-08-02",
69
+ highRiskAnnexIProducts: "2027-08-02",
70
+ });
71
+
72
+ // ---- Article 51-55 — General-Purpose AI Models ----
73
+
74
+ var GPAI_OBLIGATIONS = Object.freeze([
75
+ Object.freeze({
76
+ article: "Art. 53(1)(a)",
77
+ title: "Technical documentation",
78
+ description: "Provider keeps up-to-date technical documentation including training and testing process, evaluation results, info per Annex XI.",
79
+ }),
80
+ Object.freeze({
81
+ article: "Art. 53(1)(b)",
82
+ title: "Information for downstream providers",
83
+ description: "Provider draws up information / documentation to enable downstream providers to comply with their obligations and to understand the model's capabilities / limitations.",
84
+ }),
85
+ Object.freeze({
86
+ article: "Art. 53(1)(c)",
87
+ title: "Copyright policy",
88
+ description: "Provider puts in place a policy to comply with EU copyright law, in particular to identify and respect machine-readable rights reservations under Art. 4(3) Directive 2019/790.",
89
+ }),
90
+ Object.freeze({
91
+ article: "Art. 53(1)(d)",
92
+ title: "Training-content public summary",
93
+ description: "Provider draws up and makes publicly available a sufficiently detailed summary of the content used for training the GPAI model, per a template provided by the AI Office.",
94
+ }),
95
+ Object.freeze({
96
+ article: "Art. 55",
97
+ title: "Systemic-risk obligations (FLOP threshold)",
98
+ description: "GPAI models with systemic risk (cumulative training compute > 10^25 FLOP per Art. 51(2)) MUST: perform model evaluation including adversarial testing, assess and mitigate possible Union-level systemic risks, track and report serious incidents to the AI Office, ensure adequate cybersecurity.",
99
+ }),
100
+ ]);
101
+
102
+ function gpaiClassify(opts) {
103
+ if (!opts || typeof opts !== "object") return { isGpai: false, isSystemicRisk: false };
104
+ var isGpai = opts.kind === "gpai" ||
105
+ (typeof opts.modalities === "object" && opts.generalPurpose === true);
106
+ var isSystemicRisk = false;
107
+ // Art. 51(2) — presumption of systemic risk if cumulative training
108
+ // compute > 10^25 FLOP.
109
+ if (typeof opts.trainingFlops === "number" && opts.trainingFlops >= 1e25) {
110
+ isSystemicRisk = true;
111
+ }
112
+ if (opts.designatedSystemicRisk === true) {
113
+ isSystemicRisk = true;
114
+ }
115
+ return {
116
+ isGpai: isGpai,
117
+ isSystemicRisk: isSystemicRisk,
118
+ obligations: isGpai ? listGpaiObligations(isSystemicRisk) : [],
119
+ };
120
+ }
121
+
122
+ function listGpaiObligations(includeSystemic) {
123
+ var out = [];
124
+ for (var i = 0; i < GPAI_OBLIGATIONS.length; i += 1) {
125
+ var entry = GPAI_OBLIGATIONS[i];
126
+ if (entry.article === "Art. 55") {
127
+ if (includeSystemic) out.push(entry);
128
+ } else {
129
+ out.push(entry);
130
+ }
131
+ }
132
+ return out;
133
+ }
134
+
135
+ // ---- Article catalog (cross-reference helper) ----
136
+ var ARTICLE_OBLIGATIONS = Object.freeze({
137
+ "Art. 9": Object.freeze({
138
+ title: "Risk-management system",
139
+ summary: "Iterative process throughout the AI system lifecycle: identification + analysis of foreseeable risks, mitigation measures, residual-risk acceptance, post-market evaluation.",
140
+ }),
141
+ "Art. 10": Object.freeze({
142
+ title: "Data and data governance",
143
+ summary: "Training, validation, and testing datasets relevant, sufficiently representative, free of errors / complete; data-governance practices including bias examination + mitigation.",
144
+ }),
145
+ "Art. 11": Object.freeze({
146
+ title: "Technical documentation",
147
+ summary: "Drawn up before placement on market; includes Annex IV elements (general description, design specifications, monitoring + functioning, risk-management procedure, etc.).",
148
+ }),
149
+ "Art. 12": Object.freeze({
150
+ title: "Record-keeping (logging)",
151
+ summary: "Automatic recording of events over the system's lifetime; for biometric ID systems, minimum logged fields per Art. 12(3).",
152
+ }),
153
+ "Art. 13": Object.freeze({
154
+ title: "Transparency and information to deployers",
155
+ summary: "Designed so deployers can interpret + use output appropriately; instructions for use including capabilities + limitations + known foreseeable misuse.",
156
+ }),
157
+ "Art. 14": Object.freeze({
158
+ title: "Human oversight",
159
+ summary: "Effective human oversight by natural persons during use, including ability to intervene, decide not to use the system, or override the output.",
160
+ }),
161
+ "Art. 15": Object.freeze({
162
+ title: "Accuracy, robustness and cybersecurity",
163
+ summary: "Appropriate accuracy / robustness / cybersecurity throughout the lifecycle; declaration of accuracy levels and metrics in instructions for use.",
164
+ }),
165
+ "Art. 27": Object.freeze({
166
+ title: "Fundamental rights impact assessment",
167
+ summary: "Required for deployers using high-risk AI in essential-services / law-enforcement / migration contexts; documents who is using, purpose, individuals affected, risks of harm, governance measures.",
168
+ }),
169
+ "Art. 50": Object.freeze({
170
+ title: "Transparency obligations",
171
+ summary: "Disclosure to natural persons that they are interacting with AI, that content is AI-generated, that emotion recognition / biometric categorisation is in use, that media is a deep fake.",
172
+ }),
173
+ "Art. 53": Object.freeze({
174
+ title: "GPAI provider obligations",
175
+ summary: "Technical documentation, downstream-info, copyright policy, training-content public summary.",
176
+ }),
177
+ "Art. 55": Object.freeze({
178
+ title: "GPAI systemic-risk obligations",
179
+ summary: "Adversarial evaluation, systemic-risk assessment + mitigation, serious-incident reporting, cybersecurity.",
180
+ }),
181
+ });
182
+
183
+ function articleObligations(article) {
184
+ if (typeof article !== "string") return null;
185
+ if (Object.prototype.hasOwnProperty.call(ARTICLE_OBLIGATIONS, article)) {
186
+ return ARTICLE_OBLIGATIONS[article];
187
+ }
188
+ return null;
189
+ }
190
+
191
+ function listArticles() {
192
+ return Object.keys(ARTICLE_OBLIGATIONS).slice();
193
+ }
194
+
195
+ // ---- top-level classifier ----
196
+
197
+ function classify(systemDescription) {
198
+ if (!systemDescription || typeof systemDescription !== "object") {
199
+ throw new ComplianceError("compliance-ai-act/bad-input",
200
+ "compliance.aiAct.classify: systemDescription must be an object — got " +
201
+ typeof systemDescription);
202
+ }
203
+
204
+ var prohibitedHits = prohibited.classify(systemDescription);
205
+ if (prohibitedHits.length > 0) {
206
+ return {
207
+ tier: "prohibited",
208
+ prohibitedHits: prohibitedHits,
209
+ annexIIIHits: [],
210
+ obligations: [],
211
+ action: "do-not-deploy",
212
+ legalReference: prohibitedHits.map(function (id) {
213
+ var p = prohibited.getPractice(id);
214
+ return p ? p.article : null;
215
+ }).filter(Boolean),
216
+ };
217
+ }
218
+
219
+ var annexIIIHits = [];
220
+ if (typeof systemDescription.purpose === "string") {
221
+ annexIIIHits = risk.classifyAnnexIII(systemDescription.purpose);
222
+ }
223
+ if (systemDescription.annexIIIRow && Array.isArray(systemDescription.annexIIIRow)) {
224
+ for (var i = 0; i < systemDescription.annexIIIRow.length; i += 1) {
225
+ if (annexIIIHits.indexOf(systemDescription.annexIIIRow[i]) === -1) {
226
+ annexIIIHits.push(systemDescription.annexIIIRow[i]);
227
+ }
228
+ }
229
+ }
230
+
231
+ var isHighRisk = annexIIIHits.length > 0 ||
232
+ (systemDescription.safetyComponentForRegulatedProduct === true &&
233
+ systemDescription.requiresThirdPartyConformity === true);
234
+
235
+ if (isHighRisk) {
236
+ var obligations = [];
237
+ var seen = Object.create(null);
238
+ for (var j = 0; j < annexIIIHits.length; j += 1) {
239
+ var rowObs = risk.obligationsFor(annexIIIHits[j]);
240
+ for (var k = 0; k < rowObs.length; k += 1) {
241
+ if (!seen[rowObs[k]]) { seen[rowObs[k]] = true; obligations.push(rowObs[k]); }
242
+ }
243
+ }
244
+ return {
245
+ tier: "high-risk",
246
+ prohibitedHits: [],
247
+ annexIIIHits: annexIIIHits,
248
+ obligations: obligations,
249
+ action: "deploy-with-art-9-15-controls",
250
+ legalReference: ["Art. 6(2)", "Annex III"],
251
+ };
252
+ }
253
+
254
+ // GPAI?
255
+ var gpai = gpaiClassify(systemDescription);
256
+ if (gpai.isGpai) {
257
+ return {
258
+ tier: "general-purpose",
259
+ prohibitedHits: [],
260
+ annexIIIHits: [],
261
+ obligations: gpai.obligations.map(function (o) { return o.article; }),
262
+ isSystemicRisk: gpai.isSystemicRisk,
263
+ action: gpai.isSystemicRisk ? "deploy-with-art-53-55-controls" :
264
+ "deploy-with-art-53-controls",
265
+ legalReference: gpai.isSystemicRisk ? ["Art. 51", "Art. 53", "Art. 55"]
266
+ : ["Art. 53"],
267
+ };
268
+ }
269
+
270
+ // Limited-risk transparency-only systems
271
+ if (systemDescription.directlyInteractsWithUsers === true ||
272
+ systemDescription.generatesSyntheticContent === true ||
273
+ systemDescription.usesEmotionRecognition === true ||
274
+ systemDescription.usesBiometricCategorisation === true ||
275
+ systemDescription.generatesDeepFake === true) {
276
+ return {
277
+ tier: "limited-risk",
278
+ prohibitedHits: [],
279
+ annexIIIHits: [],
280
+ obligations: ["Art. 50"],
281
+ action: "deploy-with-art-50-disclosures",
282
+ legalReference: ["Art. 50"],
283
+ };
284
+ }
285
+
286
+ return {
287
+ tier: "minimal-risk",
288
+ prohibitedHits: [],
289
+ annexIIIHits: [],
290
+ obligations: [],
291
+ action: "deploy-no-specific-obligations",
292
+ legalReference: [],
293
+ };
294
+ }
295
+
296
+ // Operator-side hook: emit an audit event whenever a classification is
297
+ // run on the production path. Useful for compliance reviewers tracing
298
+ // which system was classified at which decision point.
299
+ function emitClassificationAudit(systemDescription, result) {
300
+ try {
301
+ audit().safeEmit({
302
+ action: "compliance.aiact.classified",
303
+ outcome: result.tier === "prohibited" ? "denied" : "success",
304
+ actor: { systemId: systemDescription.systemId || null,
305
+ deployer: systemDescription.deployerName || null },
306
+ metadata: {
307
+ tier: result.tier,
308
+ prohibitedHits: result.prohibitedHits,
309
+ annexIIIHits: result.annexIIIHits,
310
+ obligationCount: result.obligations.length,
311
+ },
312
+ });
313
+ } catch (_e) { /* drop-silent */ }
314
+ }
315
+
316
+ // Operator helper that builds the Annex IV technical-documentation
317
+ // scaffold. Returns a sectioned document the operator fills in over
318
+ // the deployment lifecycle. Validated against minimum-required keys at
319
+ // generation time so an operator can't accidentally omit a section.
320
+ function annexIVScaffold(opts) {
321
+ opts = opts || {};
322
+ validateOpts(opts, [
323
+ "systemId", "deployerName", "providerName", "intendedPurpose",
324
+ "annexIIIRow", "deploymentScope", "version",
325
+ ], "compliance.aiAct.annexIVScaffold");
326
+ validateOpts.requireNonEmptyString(opts.systemId,
327
+ "annexIVScaffold: systemId", ComplianceError, "compliance-ai-act/bad-input");
328
+
329
+ return {
330
+ "@context": "https://blamejs.com/schemas/ai-act-annex-iv/v1",
331
+ aiActArticle: "Annex IV",
332
+ sections: {
333
+ "1-general-description": {
334
+ title: "General description of the AI system",
335
+ required: ["systemId", "intendedPurpose", "annexIIIRow", "version", "providerName", "deployerName"],
336
+ provided: {
337
+ systemId: opts.systemId,
338
+ intendedPurpose: opts.intendedPurpose || null,
339
+ annexIIIRow: opts.annexIIIRow || null,
340
+ version: opts.version || null,
341
+ providerName: opts.providerName || null,
342
+ deployerName: opts.deployerName || null,
343
+ deploymentScope: opts.deploymentScope || null,
344
+ },
345
+ },
346
+ "2-detailed-description": {
347
+ title: "Detailed description of the elements and process for development",
348
+ required: ["modelArchitecture", "trainingDataDescription", "preProcessing"],
349
+ provided: null,
350
+ },
351
+ "3-monitoring-functioning": {
352
+ title: "Detailed information about monitoring + functioning + control",
353
+ required: ["accuracyMetrics", "robustnessMetrics", "monitoringMechanism"],
354
+ provided: null,
355
+ },
356
+ "4-risk-management": {
357
+ title: "Description of the risk-management system per Art. 9",
358
+ required: ["riskRegister", "mitigationMeasures", "residualRiskAcceptance"],
359
+ provided: null,
360
+ },
361
+ "5-changes": {
362
+ title: "Description of any changes made to the system through its lifecycle",
363
+ required: ["changeLog"],
364
+ provided: null,
365
+ },
366
+ "6-list-of-harmonised-standards": {
367
+ title: "List of harmonised standards applied",
368
+ required: ["standardsList"],
369
+ provided: null,
370
+ },
371
+ "7-eu-declaration-of-conformity": {
372
+ title: "EU declaration of conformity per Art. 47 + Annex V",
373
+ required: ["declarationDocument"],
374
+ provided: null,
375
+ },
376
+ "8-post-market-monitoring": {
377
+ title: "Description of the post-market monitoring system per Art. 72",
378
+ required: ["monitoringPlan"],
379
+ provided: null,
380
+ },
381
+ },
382
+ };
383
+ }
384
+
385
+ // Operator-actionable checklist derived from a classify() result. Each
386
+ // entry carries a status ("required" | "conditional" | "deferred") +
387
+ // the article reference + a short next-step description.
388
+ function deployerChecklist(assessment) {
389
+ if (!assessment || typeof assessment !== "object") {
390
+ throw new ComplianceError("compliance-ai-act/bad-checklist-input",
391
+ "deployerChecklist: assessment must be a classify() result object");
392
+ }
393
+ var items = [];
394
+ if (assessment.tier === "prohibited") {
395
+ items.push({
396
+ status: "required",
397
+ action: "do-not-deploy",
398
+ article: "Art. 5",
399
+ description: "System falls under Art. 5 prohibited practices — do not deploy in EU market.",
400
+ });
401
+ return items;
402
+ }
403
+ if (assessment.tier === "high-risk") {
404
+ items.push({
405
+ status: "required",
406
+ action: "engage-conformity-assessment",
407
+ article: "Art. 16-26",
408
+ description: "Engage notified body for third-party conformity assessment per Annex VII (or self-assess for systems where self-assessment is permitted under Art. 43).",
409
+ });
410
+ items.push({
411
+ status: "required",
412
+ action: "draw-up-technical-documentation",
413
+ article: "Art. 11 + Annex IV",
414
+ description: "Prepare Annex IV technical documentation. Use b.compliance.aiAct.annexIVScaffold().",
415
+ });
416
+ items.push({
417
+ status: "required",
418
+ action: "establish-risk-management-system",
419
+ article: "Art. 9",
420
+ description: "Iterative risk-management system over the system lifecycle.",
421
+ });
422
+ items.push({
423
+ status: "required",
424
+ action: "data-governance",
425
+ article: "Art. 10",
426
+ description: "Training / validation / testing dataset governance including bias examination.",
427
+ });
428
+ items.push({
429
+ status: "required",
430
+ action: "automatic-logging",
431
+ article: "Art. 12",
432
+ description: "Implement automatic logging via b.compliance.aiAct.logging.loggerFor().",
433
+ });
434
+ items.push({
435
+ status: "required",
436
+ action: "human-oversight",
437
+ article: "Art. 14",
438
+ description: "Effective human oversight by natural persons during use; ability to intervene / override.",
439
+ });
440
+ items.push({
441
+ status: "required",
442
+ action: "accuracy-robustness-cyber",
443
+ article: "Art. 15",
444
+ description: "Declare accuracy / robustness / cybersecurity levels in instructions for use.",
445
+ });
446
+ if (assessment.obligations.indexOf("fundamental-rights-impact-assessment-art-27") !== -1) {
447
+ items.push({
448
+ status: "required",
449
+ action: "fundamental-rights-impact-assessment",
450
+ article: "Art. 27",
451
+ description: "Conduct FRIA before first deployment; documents purpose, individuals affected, foreseeable harms, mitigation.",
452
+ });
453
+ }
454
+ items.push({
455
+ status: "required",
456
+ action: "register-eu-database",
457
+ article: "Art. 71",
458
+ description: "Register the high-risk AI system in the EU database before placing on market or putting into service.",
459
+ });
460
+ items.push({
461
+ status: "required",
462
+ action: "post-market-monitoring",
463
+ article: "Art. 72",
464
+ description: "Establish a post-market monitoring system commensurate with the AI risks.",
465
+ });
466
+ return items;
467
+ }
468
+ if (assessment.tier === "limited-risk") {
469
+ items.push({
470
+ status: "required",
471
+ action: "transparency-disclosure",
472
+ article: "Art. 50",
473
+ description: "Mount b.middleware.aiActDisclosure({ kind: ... }) on routes that interact with users / generate synthetic content / use emotion or biometric categorisation.",
474
+ });
475
+ return items;
476
+ }
477
+ if (assessment.tier === "general-purpose") {
478
+ items.push({
479
+ status: "required",
480
+ action: "gpai-technical-documentation",
481
+ article: "Art. 53(1)(a) + Annex XI",
482
+ description: "Maintain up-to-date technical documentation incl. training process, evaluation results, capabilities / limitations.",
483
+ });
484
+ items.push({
485
+ status: "required",
486
+ action: "downstream-info",
487
+ article: "Art. 53(1)(b)",
488
+ description: "Provide info to downstream providers to enable their compliance.",
489
+ });
490
+ items.push({
491
+ status: "required",
492
+ action: "copyright-policy",
493
+ article: "Art. 53(1)(c)",
494
+ description: "Adopt a policy compliant with EU copyright law including respecting Art. 4(3) Directive 2019/790 rights reservations.",
495
+ });
496
+ items.push({
497
+ status: "required",
498
+ action: "training-content-summary",
499
+ article: "Art. 53(1)(d)",
500
+ description: "Publish a sufficiently detailed summary of training content per the AI Office template.",
501
+ });
502
+ if (assessment.isSystemicRisk === true) {
503
+ items.push({
504
+ status: "required",
505
+ action: "adversarial-evaluation",
506
+ article: "Art. 55",
507
+ description: "Perform model evaluation including adversarial testing to identify systemic risk.",
508
+ });
509
+ items.push({
510
+ status: "required",
511
+ action: "systemic-risk-mitigation",
512
+ article: "Art. 55",
513
+ description: "Assess and mitigate possible Union-level systemic risks.",
514
+ });
515
+ items.push({
516
+ status: "required",
517
+ action: "incident-reporting",
518
+ article: "Art. 55",
519
+ description: "Track and report serious incidents + corrective measures to the AI Office.",
520
+ });
521
+ items.push({
522
+ status: "required",
523
+ action: "cybersecurity",
524
+ article: "Art. 55",
525
+ description: "Ensure adequate cybersecurity protection of the model and physical infrastructure.",
526
+ });
527
+ }
528
+ return items;
529
+ }
530
+ // minimal-risk
531
+ items.push({
532
+ status: "deferred",
533
+ action: "voluntary-codes",
534
+ article: "Art. 95",
535
+ description: "Consider adoption of voluntary codes of conduct for minimal-risk AI per Art. 95.",
536
+ });
537
+ return items;
538
+ }
539
+
540
+ module.exports = {
541
+ classify: classify,
542
+ deployerChecklist: deployerChecklist,
543
+ prohibited: prohibited,
544
+ risk: risk,
545
+ transparency: transparency,
546
+ logging: logging,
547
+ gpai: {
548
+ classify: gpaiClassify,
549
+ listObligations: listGpaiObligations,
550
+ OBLIGATIONS: GPAI_OBLIGATIONS,
551
+ },
552
+ articleObligations: articleObligations,
553
+ listArticles: listArticles,
554
+ ARTICLE_OBLIGATIONS: ARTICLE_OBLIGATIONS,
555
+ DEADLINES: DEADLINES,
556
+ emitClassificationAudit: emitClassificationAudit,
557
+ annexIVScaffold: annexIVScaffold,
558
+ };
package/lib/compliance.js CHANGED
@@ -30,6 +30,7 @@
30
30
 
31
31
  var lazyRequire = require("./lazy-require");
32
32
  var sanctions = require("./compliance-sanctions");
33
+ var aiAct = require("./compliance-ai-act");
33
34
  var { ComplianceError } = require("./framework-error");
34
35
 
35
36
  var audit = lazyRequire(function () { return require("./audit"); });
@@ -307,6 +308,7 @@ module.exports = {
307
308
  posturesByJurisdiction: posturesByJurisdiction,
308
309
  list: list,
309
310
  sanctions: sanctions,
311
+ aiAct: aiAct,
310
312
  KNOWN_POSTURES: KNOWN_POSTURES,
311
313
  REGIME_MAP: REGIME_MAP,
312
314
  ComplianceError: ComplianceError,
package/lib/crypto.js CHANGED
@@ -361,6 +361,37 @@ function encryptMlkem768X25519(plaintext, recipient) {
361
361
  ]).toString("base64");
362
362
  }
363
363
 
364
+ // Symmetric named-pair to encryptMlkem768X25519. Operators wiring the
365
+ // IETF / Cloudflare / Chrome TLS-1.3 hybrid (codepoint 0x11EC) want
366
+ // the encrypt + decrypt halves under symmetric, discoverable names.
367
+ //
368
+ // The generic b.crypto.decrypt already dispatches by KEM ID and
369
+ // handles ML_KEM_768_X25519 envelopes correctly; this helper REJECTS
370
+ // any other KEM ID at the head, so an operator who calls
371
+ // decryptMlkem768X25519 with a ciphertext sealed under a different
372
+ // algorithm gets a clear error rather than the generic "unsupported
373
+ // KEM ID" path.
374
+ //
375
+ // recipient: { privateKey, x25519PrivateKey } — operator's keys
376
+ // ciphertext: base64 envelope from encryptMlkem768X25519
377
+ function decryptMlkem768X25519(ciphertext, recipient) {
378
+ if (!recipient || typeof recipient !== "object" ||
379
+ !recipient.privateKey || !recipient.x25519PrivateKey) {
380
+ throw new Error("decryptMlkem768X25519 requires { privateKey, x25519PrivateKey } " +
381
+ "(privateKey is the ML-KEM-768 PEM, x25519PrivateKey is the X25519 PEM)");
382
+ }
383
+ var packed = Buffer.from(ciphertext, "base64");
384
+ if (packed[0] !== C.ENVELOPE_MAGIC) {
385
+ throw new Error("decryptMlkem768X25519: invalid envelope (bad magic byte)");
386
+ }
387
+ if (packed[1] !== C.KEM_IDS.ML_KEM_768_X25519) {
388
+ throw new Error("decryptMlkem768X25519: envelope KEM ID is " + packed[1] +
389
+ ", expected " + C.KEM_IDS.ML_KEM_768_X25519 +
390
+ " (ML_KEM_768_X25519). Use b.crypto.decrypt for KEM-id dispatch.");
391
+ }
392
+ return decryptEnvelope(packed, recipient);
393
+ }
394
+
364
395
  // ---- Cert-peer envelope primitives ----
365
396
  //
366
397
  // The framework's default `encrypt` / `decrypt` source the recipient
@@ -515,6 +546,7 @@ module.exports = {
515
546
  encrypt: encrypt,
516
547
  decrypt: decrypt,
517
548
  encryptMlkem768X25519: encryptMlkem768X25519,
549
+ decryptMlkem768X25519: decryptMlkem768X25519,
518
550
  encryptEnvelopeAsCertPeer: encryptEnvelopeAsCertPeer,
519
551
  decryptEnvelopeAsCertPeer: decryptEnvelopeAsCertPeer,
520
552
  SUPPORTED_KEM_ALGORITHMS: SUPPORTED_KEM_ALGORITHMS,