@unrdf/knowledge-engine 5.0.1 → 26.4.2

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 (71) hide show
  1. package/package.json +23 -17
  2. package/src/ai-enhanced-search.mjs +371 -0
  3. package/src/anomaly-detector.mjs +226 -0
  4. package/src/artifact-generator.mjs +252 -0
  5. package/src/browser.mjs +1 -1
  6. package/src/chatman/disruption-arithmetic.mjs +140 -0
  7. package/src/chatman/market-dynamics.mjs +140 -0
  8. package/src/chatman/organizational-dynamics.mjs +140 -0
  9. package/src/chatman/strategic-dynamics.mjs +140 -0
  10. package/src/chatman-config-loader.mjs +282 -0
  11. package/src/chatman-engine.mjs +435 -0
  12. package/src/chatman-operator.mjs +343 -0
  13. package/src/dark-field-detector.mjs +332 -0
  14. package/src/formation-theorems.mjs +345 -0
  15. package/src/index.mjs +20 -2
  16. package/src/knowledge-hook-manager.mjs +1 -1
  17. package/src/lockchain-writer-browser.mjs +2 -2
  18. package/src/observability.mjs +40 -4
  19. package/src/query-optimizer.mjs +1 -1
  20. package/src/resolution-layer.mjs +1 -1
  21. package/src/transaction.mjs +11 -9
  22. package/README.md +0 -84
  23. package/src/browser-shims.mjs +0 -343
  24. package/src/canonicalize.mjs +0 -414
  25. package/src/condition-cache.mjs +0 -109
  26. package/src/condition-evaluator.mjs +0 -722
  27. package/src/dark-matter-core.mjs +0 -742
  28. package/src/define-hook.mjs +0 -213
  29. package/src/effect-sandbox-browser.mjs +0 -283
  30. package/src/effect-sandbox-worker.mjs +0 -170
  31. package/src/effect-sandbox.mjs +0 -517
  32. package/src/engines/index.mjs +0 -11
  33. package/src/engines/rdf-engine.mjs +0 -299
  34. package/src/file-resolver.mjs +0 -387
  35. package/src/hook-executor-batching.mjs +0 -277
  36. package/src/hook-executor.mjs +0 -870
  37. package/src/hook-management.mjs +0 -150
  38. package/src/ken-parliment.mjs +0 -119
  39. package/src/ken.mjs +0 -149
  40. package/src/knowledge-engine/builtin-rules.mjs +0 -190
  41. package/src/knowledge-engine/inference-engine.mjs +0 -418
  42. package/src/knowledge-engine/knowledge-engine.mjs +0 -317
  43. package/src/knowledge-engine/pattern-dsl.mjs +0 -142
  44. package/src/knowledge-engine/pattern-matcher.mjs +0 -215
  45. package/src/knowledge-engine/rules.mjs +0 -184
  46. package/src/knowledge-engine.mjs +0 -319
  47. package/src/knowledge-hook-engine.mjs +0 -360
  48. package/src/knowledge-substrate-core.mjs +0 -927
  49. package/src/lite.mjs +0 -222
  50. package/src/lockchain-writer.mjs +0 -602
  51. package/src/monitoring/andon-signals.mjs +0 -775
  52. package/src/parse.mjs +0 -290
  53. package/src/performance-optimizer.mjs +0 -678
  54. package/src/policy-pack.mjs +0 -572
  55. package/src/query-cache.mjs +0 -116
  56. package/src/query.mjs +0 -306
  57. package/src/reason.mjs +0 -350
  58. package/src/schemas.mjs +0 -1063
  59. package/src/security/error-sanitizer.mjs +0 -257
  60. package/src/security/path-validator.mjs +0 -194
  61. package/src/security/sandbox-restrictions.mjs +0 -331
  62. package/src/security-validator.mjs +0 -389
  63. package/src/store-cache.mjs +0 -137
  64. package/src/telemetry.mjs +0 -167
  65. package/src/utils/adaptive-monitor.mjs +0 -746
  66. package/src/utils/circuit-breaker.mjs +0 -513
  67. package/src/utils/edge-case-handler.mjs +0 -503
  68. package/src/utils/memory-manager.mjs +0 -498
  69. package/src/utils/ring-buffer.mjs +0 -282
  70. package/src/validate.mjs +0 -319
  71. package/src/validators/index.mjs +0 -338
@@ -1,602 +0,0 @@
1
- /**
2
- * @file Lockchain Writer for persistent, verifiable audit trail
3
- * @module lockchain-writer
4
- *
5
- * @description
6
- * Implements a persistent, verifiable audit trail by anchoring signed receipts
7
- * to Git. Provides cryptographic integrity and tamper-proof provenance.
8
- */
9
-
10
- import { execSync } from 'child_process';
11
- import { writeFileSync, readFileSync, existsSync, mkdirSync } from 'fs';
12
- import { join, dirname } from 'path';
13
- import { fileURLToPath } from 'url';
14
-
15
- const __dirname = dirname(fileURLToPath(import.meta.url));
16
- import { sha3_256 } from '@noble/hashes/sha3.js';
17
- import { _blake3 } from '@noble/hashes/blake3.js';
18
- import { utf8ToBytes, bytesToHex } from '@noble/hashes/utils.js';
19
- import { randomUUID } from 'crypto';
20
- import { z } from 'zod';
21
-
22
- /**
23
- * Schema for lockchain entry
24
- */
25
- const LockchainEntrySchema = z.object({
26
- id: z.string().uuid(),
27
- timestamp: z.number(),
28
- receipt: z.any(), // Transaction receipt
29
- signature: z.object({
30
- algorithm: z.string(),
31
- value: z.string(),
32
- publicKey: z.string().optional(),
33
- }),
34
- previousHash: z.string().optional().nullable(),
35
- merkleRoot: z.string().optional(),
36
- gitCommit: z.string().optional(),
37
- gitRef: z.string().optional(),
38
- });
39
-
40
- /**
41
- * Schema for lockchain configuration
42
- */
43
- const LockchainConfigSchema = z.object({
44
- gitRepo: z.string().default(process.cwd()),
45
- refName: z.string().default('refs/notes/lockchain'),
46
- signingKey: z.string().optional(),
47
- algorithm: z.enum(['ed25519', 'ecdsa', 'rsa']).default('ed25519'),
48
- batchSize: z.number().int().positive().default(10),
49
- enableMerkle: z.boolean().default(true),
50
- enableGitAnchoring: z.boolean().default(true),
51
- storagePath: z.string().optional(),
52
- });
53
-
54
- /**
55
- * Lockchain Writer for persistent, verifiable audit trail
56
- */
57
- export class LockchainWriter {
58
- /**
59
- * Create a new lockchain writer
60
- * @param {Object} [config] - Lockchain configuration
61
- */
62
- constructor(config = {}) {
63
- const validatedConfig = LockchainConfigSchema.parse(config);
64
- this.config = validatedConfig;
65
-
66
- // Initialize storage
67
- this.storagePath = validatedConfig.storagePath || join(validatedConfig.gitRepo, '.lockchain');
68
- this.initialized = false;
69
-
70
- // Cache for pending entries
71
- this.pendingEntries = [];
72
- this.entryCache = new Map();
73
- }
74
-
75
- /**
76
- * Initialize lockchain writer (async initialization pattern)
77
- * @returns {Promise<void>}
78
- */
79
- async init() {
80
- if (this.initialized) {
81
- return; // Already initialized
82
- }
83
-
84
- // Initialize storage
85
- this._ensureStorageExists();
86
-
87
- // Initialize Git repository if needed
88
- this._initializeGitRepo();
89
-
90
- this.initialized = true;
91
- }
92
-
93
- /**
94
- * Write a receipt to the lockchain
95
- * @param {Object} receipt - Transaction receipt
96
- * @param {Object} [options] - Write options
97
- * @returns {Promise<Object>} Lockchain entry
98
- */
99
- async writeReceipt(receipt, options = {}) {
100
- // Auto-initialize if not already initialized
101
- if (!this.initialized) {
102
- await this.init();
103
- }
104
-
105
- const entryId = randomUUID();
106
- const timestamp = Date.now();
107
-
108
- // Serialize receipt first
109
- const serializedReceipt = this._serializeReceipt(receipt);
110
-
111
- // Create lockchain entry (without merkleRoot first)
112
- const entry = {
113
- id: entryId,
114
- timestamp,
115
- receipt: serializedReceipt,
116
- signature: await this._signEntry(serializedReceipt, entryId, timestamp),
117
- previousHash: this._getPreviousHash() || '',
118
- };
119
-
120
- // Calculate and add Merkle root if enabled
121
- if (this.config.enableMerkle) {
122
- entry.merkleRoot = this._calculateEntryMerkleRoot(entry);
123
- } else if (options.merkleRoot) {
124
- entry.merkleRoot = options.merkleRoot;
125
- }
126
-
127
- // Validate entry
128
- const validatedEntry = LockchainEntrySchema.parse(entry);
129
-
130
- // Store entry
131
- await this._storeEntry(validatedEntry);
132
-
133
- // Add to pending batch
134
- this.pendingEntries.push(validatedEntry);
135
-
136
- // Auto-commit if batch is full
137
- if (this.pendingEntries.length >= this.config.batchSize) {
138
- await this.commitBatch();
139
- }
140
-
141
- return validatedEntry;
142
- }
143
-
144
- /**
145
- * Commit pending entries to Git
146
- * @param {Object} [options] - Commit options
147
- * @returns {Promise<Object>} Commit result
148
- */
149
- async commitBatch(_options = {}) {
150
- if (this.pendingEntries.length === 0) {
151
- return { committed: false, message: 'No pending entries' };
152
- }
153
-
154
- const batchId = randomUUID();
155
- const timestamp = Date.now();
156
-
157
- try {
158
- // Create batch file
159
- const batchData = {
160
- id: batchId,
161
- timestamp,
162
- entries: this.pendingEntries,
163
- merkleRoot: this.config.enableMerkle
164
- ? this._calculateMerkleRoot(this.pendingEntries)
165
- : null,
166
- entryCount: this.pendingEntries.length,
167
- };
168
-
169
- const batchFile = join(this.storagePath, `batch-${batchId}.json`);
170
- writeFileSync(batchFile, JSON.stringify(batchData, null, 2));
171
-
172
- // Git operations
173
- if (this.config.enableGitAnchoring) {
174
- await this._gitAdd(batchFile);
175
- const commitHash = await this._gitCommit(`Lockchain batch ${batchId}`, {
176
- entries: this.pendingEntries.length,
177
- timestamp,
178
- });
179
-
180
- // Update entries with Git commit info
181
- for (const entry of this.pendingEntries) {
182
- entry.gitCommit = commitHash;
183
- entry.gitRef = this.config.refName;
184
- await this._updateEntry(entry);
185
- }
186
- }
187
-
188
- // Clear pending entries
189
- const committedCount = this.pendingEntries.length;
190
- this.pendingEntries = [];
191
-
192
- return {
193
- committed: true,
194
- batchId,
195
- commitHash: this.config.enableGitAnchoring ? await this._getLatestCommit() : null,
196
- entryCount: committedCount,
197
- timestamp,
198
- };
199
- } catch (error) {
200
- throw new Error(`Failed to commit lockchain batch: ${error.message}`);
201
- }
202
- }
203
-
204
- /**
205
- * Verify a receipt (alias for verifyEntry for README compatibility)
206
- * @param {Object|string} receipt - Receipt object or entry ID
207
- * @returns {Promise<boolean>} Verification result (true if valid)
208
- */
209
- async verifyReceipt(receipt) {
210
- const entryId = typeof receipt === 'string' ? receipt : receipt.id;
211
- const result = await this.verifyEntry(entryId);
212
- return result.valid;
213
- }
214
-
215
- /**
216
- * Verify a lockchain entry
217
- * @param {string} entryId - Entry ID to verify
218
- * @returns {Promise<Object>} Verification result
219
- */
220
- async verifyEntry(entryId) {
221
- const entry = await this._loadEntry(entryId);
222
- if (!entry) {
223
- return { valid: false, error: 'Entry not found' };
224
- }
225
-
226
- try {
227
- // Verify signature
228
- const signatureValid = await this._verifySignature(entry);
229
- if (!signatureValid) {
230
- return { valid: false, error: 'Invalid signature' };
231
- }
232
-
233
- // Verify Git commit if present
234
- if (entry.gitCommit && this.config.enableGitAnchoring) {
235
- const gitValid = await this._verifyGitCommit(entry.gitCommit);
236
- if (!gitValid) {
237
- return { valid: false, error: 'Invalid Git commit' };
238
- }
239
- }
240
-
241
- // Verify merkle root if present
242
- if (entry.merkleRoot && this.config.enableMerkle) {
243
- const merkleValid = await this._verifyMerkleRoot(entry);
244
- if (!merkleValid) {
245
- return { valid: false, error: 'Invalid merkle root' };
246
- }
247
- }
248
-
249
- return { valid: true, entry };
250
- } catch (error) {
251
- return { valid: false, error: error.message };
252
- }
253
- }
254
-
255
- /**
256
- * Get lockchain statistics
257
- * @returns {Object} Statistics
258
- */
259
- getStats() {
260
- return {
261
- config: this.config,
262
- pendingEntries: this.pendingEntries.length,
263
- storagePath: this.storagePath,
264
- gitEnabled: this.config.enableGitAnchoring,
265
- merkleEnabled: this.config.enableMerkle,
266
- };
267
- }
268
-
269
- /**
270
- * Ensure storage directory exists
271
- * @private
272
- */
273
- _ensureStorageExists() {
274
- if (!existsSync(this.storagePath)) {
275
- mkdirSync(this.storagePath, { recursive: true });
276
- }
277
- }
278
-
279
- /**
280
- * Initialize Git repository
281
- * @private
282
- */
283
- _initializeGitRepo() {
284
- if (!this.config.enableGitAnchoring) return;
285
-
286
- try {
287
- // Check if Git repo exists
288
- execSync('git rev-parse --git-dir', {
289
- cwd: this.config.gitRepo,
290
- stdio: 'pipe',
291
- });
292
- } catch (error) {
293
- throw new Error(`Git repository not found at ${this.config.gitRepo}`);
294
- }
295
- }
296
-
297
- /**
298
- * Serialize receipt for storage
299
- * @param {Object} receipt - Transaction receipt
300
- * @returns {Object} Serialized receipt
301
- * @private
302
- */
303
- _serializeReceipt(receipt) {
304
- return {
305
- ...receipt,
306
- _serialized: true,
307
- _timestamp: Date.now(),
308
- };
309
- }
310
-
311
- /**
312
- * Sign an entry
313
- * @param {Object} receipt - Transaction receipt
314
- * @param {string} entryId - Entry ID
315
- * @param {number} timestamp - Timestamp
316
- * @returns {Promise<Object>} Signature
317
- * @private
318
- */
319
- async _signEntry(receipt, entryId, timestamp) {
320
- // For now, use a simple hash-based signature
321
- // In production, this would use proper cryptographic signatures
322
- const data = JSON.stringify({ receipt, entryId, timestamp });
323
- const hash = bytesToHex(sha3_256(utf8ToBytes(data)));
324
-
325
- return {
326
- algorithm: 'sha3-256',
327
- value: hash,
328
- publicKey: this.config.signingKey || 'default',
329
- };
330
- }
331
-
332
- /**
333
- * Get previous hash for chaining
334
- * @returns {string} Previous hash
335
- * @private
336
- */
337
- _getPreviousHash() {
338
- if (this.pendingEntries.length === 0) {
339
- return null;
340
- }
341
-
342
- const lastEntry = this.pendingEntries[this.pendingEntries.length - 1];
343
- return lastEntry.signature.value;
344
- }
345
-
346
- /**
347
- * Store an entry
348
- * @param {Object} entry - Lockchain entry
349
- * @private
350
- */
351
- async _storeEntry(entry) {
352
- const entryFile = join(this.storagePath, `entry-${entry.id}.json`);
353
- writeFileSync(entryFile, JSON.stringify(entry, null, 2));
354
-
355
- // Cache entry
356
- this.entryCache.set(entry.id, entry);
357
- }
358
-
359
- /**
360
- * Update an entry
361
- * @param {Object} entry - Updated entry
362
- * @private
363
- */
364
- async _updateEntry(entry) {
365
- const entryFile = join(this.storagePath, `entry-${entry.id}.json`);
366
- writeFileSync(entryFile, JSON.stringify(entry, null, 2));
367
-
368
- // Update cache
369
- this.entryCache.set(entry.id, entry);
370
- }
371
-
372
- /**
373
- * Load an entry
374
- * @param {string} entryId - Entry ID
375
- * @returns {Promise<Object>} Entry or null
376
- * @private
377
- */
378
- async _loadEntry(entryId) {
379
- // Check cache first
380
- if (this.entryCache.has(entryId)) {
381
- return this.entryCache.get(entryId);
382
- }
383
-
384
- const entryFile = join(this.storagePath, `entry-${entryId}.json`);
385
- if (!existsSync(entryFile)) {
386
- return null;
387
- }
388
-
389
- const entry = JSON.parse(readFileSync(entryFile, 'utf8'));
390
- this.entryCache.set(entryId, entry);
391
- return entry;
392
- }
393
-
394
- /**
395
- * Calculate merkle root for a single entry
396
- * @param {Object} entry - Single entry
397
- * @returns {string} Merkle root hash
398
- * @private
399
- *
400
- * @description
401
- * Calculates a Merkle root for a single entry by hashing its canonical data.
402
- * Uses deterministic JSON serialization to ensure consistent hashing.
403
- */
404
- _calculateEntryMerkleRoot(entry) {
405
- // Build canonical data representation
406
- // Use same structure as verification for consistency
407
- const entryData = {
408
- id: entry.id,
409
- timestamp: entry.timestamp,
410
- receipt: entry.receipt,
411
- signature: entry.signature,
412
- previousHash: entry.previousHash || null,
413
- };
414
-
415
- // Calculate hash using SHA3-256
416
- const entryJson = JSON.stringify(entryData);
417
- return bytesToHex(sha3_256(utf8ToBytes(entryJson)));
418
- }
419
-
420
- /**
421
- * Calculate merkle root for multiple entries (batch)
422
- * @param {Array} entries - Entries
423
- * @returns {string} Merkle root
424
- * @private
425
- */
426
- _calculateMerkleRoot(entries) {
427
- if (entries.length === 0) return null;
428
-
429
- const hashes = entries.map(entry => bytesToHex(sha3_256(utf8ToBytes(JSON.stringify(entry)))));
430
-
431
- // Simple merkle tree calculation
432
- let currentLevel = hashes;
433
- while (currentLevel.length > 1) {
434
- const nextLevel = [];
435
- for (let i = 0; i < currentLevel.length; i += 2) {
436
- const left = currentLevel[i];
437
- const right = currentLevel[i + 1] || left;
438
- const combined = left + right;
439
- nextLevel.push(bytesToHex(sha3_256(utf8ToBytes(combined))));
440
- }
441
- currentLevel = nextLevel;
442
- }
443
-
444
- return currentLevel[0];
445
- }
446
-
447
- /**
448
- * Git add operation
449
- * @param {string} filePath - File to add
450
- * @private
451
- */
452
- async _gitAdd(filePath) {
453
- execSync(`git add "${filePath}"`, {
454
- cwd: this.config.gitRepo,
455
- stdio: 'pipe',
456
- });
457
- }
458
-
459
- /**
460
- * Git commit operation
461
- * @param {string} message - Commit message
462
- * @param {Object} metadata - Commit metadata
463
- * @returns {Promise<string>} Commit hash
464
- * @private
465
- */
466
- async _gitCommit(message, metadata = {}) {
467
- const commitMessage = `${message}\n\nMetadata: ${JSON.stringify(metadata)}`;
468
-
469
- const output = execSync(`git commit -m "${commitMessage}"`, {
470
- cwd: this.config.gitRepo,
471
- stdio: 'pipe',
472
- encoding: 'utf8',
473
- });
474
-
475
- // Extract commit hash from output
476
- const commitHash = output.trim().split('\n').pop();
477
- return commitHash;
478
- }
479
-
480
- /**
481
- * Get latest commit hash
482
- * @returns {Promise<string>} Latest commit hash
483
- * @private
484
- */
485
- async _getLatestCommit() {
486
- const output = execSync('git rev-parse HEAD', {
487
- cwd: this.config.gitRepo,
488
- stdio: 'pipe',
489
- encoding: 'utf8',
490
- });
491
-
492
- return output.trim();
493
- }
494
-
495
- /**
496
- * Verify signature
497
- * @param {Object} entry - Entry to verify
498
- * @returns {Promise<boolean>} Signature valid
499
- * @private
500
- */
501
- async _verifySignature(entry) {
502
- // For now, just verify the hash matches
503
- const data = JSON.stringify({
504
- receipt: entry.receipt,
505
- entryId: entry.id,
506
- timestamp: entry.timestamp,
507
- });
508
- const expectedHash = bytesToHex(sha3_256(utf8ToBytes(data)));
509
-
510
- return entry.signature.value === expectedHash;
511
- }
512
-
513
- /**
514
- * Verify Git commit
515
- * @param {string} commitHash - Commit hash
516
- * @returns {Promise<boolean>} Commit valid
517
- * @private
518
- */
519
- async _verifyGitCommit(commitHash) {
520
- try {
521
- execSync(`git cat-file -t ${commitHash}`, {
522
- cwd: this.config.gitRepo,
523
- stdio: 'pipe',
524
- });
525
- return true;
526
- } catch (error) {
527
- return false;
528
- }
529
- }
530
-
531
- /**
532
- * Verify merkle root cryptographically
533
- * @param {Object} entry - Entry to verify
534
- * @returns {Promise<boolean>} Merkle root valid
535
- * @private
536
- *
537
- * @description
538
- * Validates the Merkle root by:
539
- * 1. Extracting the entry data components (receipt, signature, timestamp, etc.)
540
- * 2. Calculating the Merkle root from these components using SHA3-256
541
- * 3. Comparing the calculated root with the stored entry.merkleRoot
542
- *
543
- * This ensures cryptographic integrity - any tampering with the entry data
544
- * will cause the verification to fail.
545
- */
546
- async _verifyMerkleRoot(entry) {
547
- if (!entry.merkleRoot) {
548
- return true; // No merkle root to verify
549
- }
550
-
551
- try {
552
- // Build canonical data representation for verification
553
- // Include all critical entry components in deterministic order
554
- const entryData = {
555
- id: entry.id,
556
- timestamp: entry.timestamp,
557
- receipt: entry.receipt,
558
- signature: entry.signature,
559
- previousHash: entry.previousHash || null,
560
- };
561
-
562
- // Calculate hash of entry data (leaf node in Merkle tree)
563
- const entryJson = JSON.stringify(entryData);
564
- const entryHash = bytesToHex(sha3_256(utf8ToBytes(entryJson)));
565
-
566
- // For a single entry, the Merkle root should be the hash of the entry itself
567
- // (a Merkle tree with one leaf node has that leaf as the root)
568
- // If the entry was part of a batch, we verify against the batch's Merkle root
569
- const calculatedRoot = entryHash;
570
-
571
- // Compare calculated root with stored root
572
- const isValid = calculatedRoot === entry.merkleRoot;
573
-
574
- if (!isValid) {
575
- console.error('[LockchainWriter] Merkle root verification failed', {
576
- entryId: entry.id,
577
- stored: entry.merkleRoot,
578
- calculated: calculatedRoot,
579
- });
580
- }
581
-
582
- return isValid;
583
- } catch (error) {
584
- console.error('[LockchainWriter] Error verifying Merkle root:', error);
585
- return false;
586
- }
587
- }
588
- }
589
-
590
- /**
591
- * Create a lockchain writer instance
592
- * @param {Object} [config] - Configuration
593
- * @returns {LockchainWriter} Lockchain writer instance
594
- */
595
- export function createLockchainWriter(config = {}) {
596
- return new LockchainWriter(config);
597
- }
598
-
599
- /**
600
- * Default lockchain writer instance
601
- */
602
- export const defaultLockchainWriter = createLockchainWriter();