@originals/sdk 1.5.0 → 1.6.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/adapters/FeeOracleMock.js +2 -2
- package/dist/bitcoin/OrdinalsClient.d.ts +1 -1
- package/dist/bitcoin/OrdinalsClient.js +10 -8
- package/dist/bitcoin/PSBTBuilder.js +1 -1
- package/dist/bitcoin/utxo-selection.js +2 -2
- package/dist/cel/ExternalReferenceManager.d.ts +57 -0
- package/dist/cel/ExternalReferenceManager.js +73 -0
- package/dist/cel/OriginalsCel.d.ts +245 -0
- package/dist/cel/OriginalsCel.js +349 -0
- package/dist/cel/algorithms/createEventLog.d.ts +32 -0
- package/dist/cel/algorithms/createEventLog.js +56 -0
- package/dist/cel/algorithms/deactivateEventLog.d.ts +35 -0
- package/dist/cel/algorithms/deactivateEventLog.js +91 -0
- package/dist/cel/algorithms/index.d.ts +10 -0
- package/dist/cel/algorithms/index.js +10 -0
- package/dist/cel/algorithms/updateEventLog.d.ts +34 -0
- package/dist/cel/algorithms/updateEventLog.js +82 -0
- package/dist/cel/algorithms/verifyEventLog.d.ts +45 -0
- package/dist/cel/algorithms/verifyEventLog.js +255 -0
- package/dist/cel/algorithms/witnessEvent.d.ts +29 -0
- package/dist/cel/algorithms/witnessEvent.js +75 -0
- package/dist/cel/cli/create.d.ts +36 -0
- package/dist/cel/cli/create.js +282 -0
- package/dist/cel/cli/index.d.ts +11 -0
- package/dist/cel/cli/index.js +351 -0
- package/dist/cel/cli/inspect.d.ts +30 -0
- package/dist/cel/cli/inspect.js +475 -0
- package/dist/cel/cli/migrate.d.ts +41 -0
- package/dist/cel/cli/migrate.js +405 -0
- package/dist/cel/cli/verify.d.ts +31 -0
- package/dist/cel/cli/verify.js +205 -0
- package/dist/cel/hash.d.ts +46 -0
- package/dist/cel/hash.js +66 -0
- package/dist/cel/index.d.ts +15 -0
- package/dist/cel/index.js +15 -0
- package/dist/cel/layers/BtcoCelManager.d.ts +121 -0
- package/dist/cel/layers/BtcoCelManager.js +329 -0
- package/dist/cel/layers/PeerCelManager.d.ts +151 -0
- package/dist/cel/layers/PeerCelManager.js +299 -0
- package/dist/cel/layers/WebVHCelManager.d.ts +122 -0
- package/dist/cel/layers/WebVHCelManager.js +291 -0
- package/dist/cel/layers/index.d.ts +13 -0
- package/dist/cel/layers/index.js +16 -0
- package/dist/cel/serialization/cbor.d.ts +42 -0
- package/dist/cel/serialization/cbor.js +163 -0
- package/dist/cel/serialization/index.d.ts +9 -0
- package/dist/cel/serialization/index.js +9 -0
- package/dist/cel/serialization/json.d.ts +41 -0
- package/dist/cel/serialization/json.js +180 -0
- package/dist/cel/types.d.ts +149 -0
- package/dist/cel/types.js +7 -0
- package/dist/cel/witnesses/BitcoinWitness.d.ts +83 -0
- package/dist/cel/witnesses/BitcoinWitness.js +116 -0
- package/dist/cel/witnesses/HttpWitness.d.ts +79 -0
- package/dist/cel/witnesses/HttpWitness.js +163 -0
- package/dist/cel/witnesses/WitnessService.d.ts +49 -0
- package/dist/cel/witnesses/WitnessService.js +10 -0
- package/dist/cel/witnesses/index.d.ts +10 -0
- package/dist/cel/witnesses/index.js +7 -0
- package/dist/core/OriginalsSDK.js +5 -1
- package/dist/crypto/Signer.js +14 -6
- package/dist/crypto/noble-init.js +20 -1
- package/dist/did/BtcoDidResolver.d.ts +2 -2
- package/dist/did/BtcoDidResolver.js +12 -8
- package/dist/did/DIDManager.js +6 -4
- package/dist/did/KeyManager.d.ts +1 -1
- package/dist/did/KeyManager.js +7 -4
- package/dist/did/WebVHManager.js +1 -1
- package/dist/did/createBtcoDidDocument.js +2 -1
- package/dist/events/types.d.ts +4 -1
- package/dist/examples/create-module-original.js +1 -1
- package/dist/examples/full-lifecycle-flow.js +2 -2
- package/dist/index.d.ts +13 -0
- package/dist/index.js +12 -0
- package/dist/kinds/KindRegistry.js +59 -29
- package/dist/lifecycle/BatchOperations.d.ts +5 -3
- package/dist/lifecycle/BatchOperations.js +11 -5
- package/dist/lifecycle/LifecycleManager.d.ts +1 -1
- package/dist/lifecycle/LifecycleManager.js +42 -33
- package/dist/lifecycle/OriginalsAsset.js +2 -2
- package/dist/migration/MigrationManager.js +67 -3
- package/dist/storage/LocalStorageAdapter.js +4 -1
- package/dist/storage/MemoryStorageAdapter.js +7 -7
- package/dist/types/network.js +6 -3
- package/dist/utils/Logger.d.ts +6 -6
- package/dist/utils/Logger.js +5 -3
- package/dist/utils/MetricsCollector.js +1 -1
- package/dist/utils/bitcoin-address.js +4 -2
- package/dist/utils/cbor.js +16 -3
- package/dist/utils/encoding.d.ts +4 -4
- package/dist/utils/encoding.js +7 -6
- package/dist/utils/hash.js +6 -1
- package/dist/utils/serialization.d.ts +2 -2
- package/dist/utils/serialization.js +7 -5
- package/dist/utils/telemetry.js +6 -2
- package/dist/utils/validation.js +8 -4
- package/dist/vc/CredentialManager.d.ts +8 -8
- package/dist/vc/CredentialManager.js +46 -33
- package/dist/vc/Issuer.d.ts +2 -2
- package/dist/vc/Issuer.js +5 -1
- package/dist/vc/Verifier.d.ts +2 -2
- package/dist/vc/Verifier.js +12 -6
- package/dist/vc/documentLoader.d.ts +5 -3
- package/dist/vc/documentLoader.js +5 -4
- package/package.json +4 -1
|
@@ -0,0 +1,349 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* OriginalsCel - Unified SDK Entry Point for CEL Operations
|
|
3
|
+
*
|
|
4
|
+
* Provides a single, simplified interface for all Cryptographic Event Log
|
|
5
|
+
* operations across all layers (peer, webvh, btco).
|
|
6
|
+
*
|
|
7
|
+
* This class delegates to the appropriate layer manager based on
|
|
8
|
+
* the configured layer and the current state of the event log.
|
|
9
|
+
*
|
|
10
|
+
* @example
|
|
11
|
+
* ```typescript
|
|
12
|
+
* // Create a peer-layer asset
|
|
13
|
+
* const cel = new OriginalsCel({
|
|
14
|
+
* layer: 'peer',
|
|
15
|
+
* signer: async (data) => createEdDsaProof(data, privateKey),
|
|
16
|
+
* });
|
|
17
|
+
*
|
|
18
|
+
* const log = await cel.create('My Asset', [
|
|
19
|
+
* { digestMultibase: 'uXYZ...', mediaType: 'image/png' }
|
|
20
|
+
* ]);
|
|
21
|
+
*
|
|
22
|
+
* // Update the asset
|
|
23
|
+
* const updated = await cel.update(log, { description: 'Updated' });
|
|
24
|
+
*
|
|
25
|
+
* // Verify the log
|
|
26
|
+
* const result = await cel.verify(updated);
|
|
27
|
+
*
|
|
28
|
+
* // Migrate to webvh layer
|
|
29
|
+
* const migrated = await cel.migrate(updated, 'webvh');
|
|
30
|
+
* ```
|
|
31
|
+
*/
|
|
32
|
+
import { PeerCelManager } from './layers/PeerCelManager';
|
|
33
|
+
import { WebVHCelManager } from './layers/WebVHCelManager';
|
|
34
|
+
import { BtcoCelManager } from './layers/BtcoCelManager';
|
|
35
|
+
import { verifyEventLog } from './algorithms/verifyEventLog';
|
|
36
|
+
/**
|
|
37
|
+
* OriginalsCel - Unified SDK for Cryptographic Event Log operations
|
|
38
|
+
*
|
|
39
|
+
* Provides a consistent API for creating, updating, verifying, and migrating
|
|
40
|
+
* assets across all supported layers (peer, webvh, btco).
|
|
41
|
+
*/
|
|
42
|
+
export class OriginalsCel {
|
|
43
|
+
/**
|
|
44
|
+
* Creates a new OriginalsCel instance
|
|
45
|
+
*
|
|
46
|
+
* @param options - Configuration options
|
|
47
|
+
* @param options.layer - The target layer for operations (peer, webvh, btco)
|
|
48
|
+
* @param options.signer - Function that signs data and returns a DataIntegrityProof
|
|
49
|
+
* @param options.config - Optional layer-specific configuration
|
|
50
|
+
*
|
|
51
|
+
* @throws Error if signer is not a function
|
|
52
|
+
* @throws Error if layer is invalid
|
|
53
|
+
*/
|
|
54
|
+
constructor(options) {
|
|
55
|
+
if (typeof options.signer !== 'function') {
|
|
56
|
+
throw new Error('OriginalsCel requires a signer function');
|
|
57
|
+
}
|
|
58
|
+
const validLayers = ['peer', 'webvh', 'btco'];
|
|
59
|
+
if (!validLayers.includes(options.layer)) {
|
|
60
|
+
throw new Error(`Invalid layer: ${options.layer}. Must be one of: ${validLayers.join(', ')}`);
|
|
61
|
+
}
|
|
62
|
+
this.layer = options.layer;
|
|
63
|
+
this.signer = options.signer;
|
|
64
|
+
this.config = options.config || {};
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Gets or creates the PeerCelManager instance
|
|
68
|
+
*/
|
|
69
|
+
get peerManager() {
|
|
70
|
+
if (!this._peerManager) {
|
|
71
|
+
this._peerManager = new PeerCelManager(this.signer, this.config.peer);
|
|
72
|
+
}
|
|
73
|
+
return this._peerManager;
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* Gets or creates the WebVHCelManager instance
|
|
77
|
+
*
|
|
78
|
+
* @throws Error if domain is not configured for webvh operations
|
|
79
|
+
*/
|
|
80
|
+
getWebVHManager(domain) {
|
|
81
|
+
const webvhDomain = domain || this.config.webvh?.domain;
|
|
82
|
+
if (!webvhDomain) {
|
|
83
|
+
throw new Error('WebVH operations require a domain. Provide it in config.webvh.domain');
|
|
84
|
+
}
|
|
85
|
+
// Always create a new instance with the current domain to support different domains
|
|
86
|
+
return new WebVHCelManager(this.signer, webvhDomain, this.config.webvh?.witnesses || [], this.config.webvh);
|
|
87
|
+
}
|
|
88
|
+
/**
|
|
89
|
+
* Gets or creates the BtcoCelManager instance
|
|
90
|
+
*
|
|
91
|
+
* @throws Error if BitcoinManager is not configured for btco operations
|
|
92
|
+
*/
|
|
93
|
+
get btcoManager() {
|
|
94
|
+
if (!this._btcoManager) {
|
|
95
|
+
const bitcoinManager = this.config.btco?.bitcoinManager;
|
|
96
|
+
if (!bitcoinManager) {
|
|
97
|
+
throw new Error('BTCO operations require a BitcoinManager. Provide it in config.btco.bitcoinManager');
|
|
98
|
+
}
|
|
99
|
+
this._btcoManager = new BtcoCelManager(this.signer, bitcoinManager, this.config.btco);
|
|
100
|
+
}
|
|
101
|
+
return this._btcoManager;
|
|
102
|
+
}
|
|
103
|
+
/**
|
|
104
|
+
* Creates a new asset with a CEL event log
|
|
105
|
+
*
|
|
106
|
+
* This method creates an asset at the configured layer. Note that
|
|
107
|
+
* new assets can only be created at the peer layer - for other layers,
|
|
108
|
+
* create at peer first and then migrate.
|
|
109
|
+
*
|
|
110
|
+
* @param name - Human-readable name for the asset
|
|
111
|
+
* @param resources - External resources associated with the asset
|
|
112
|
+
* @returns Promise resolving to an EventLog with the create event
|
|
113
|
+
*
|
|
114
|
+
* @throws Error if signer produces invalid proof
|
|
115
|
+
* @throws Error if trying to create at non-peer layer
|
|
116
|
+
*
|
|
117
|
+
* @example
|
|
118
|
+
* ```typescript
|
|
119
|
+
* const log = await cel.create('My Asset', [
|
|
120
|
+
* createExternalReference(imageData, 'image/png')
|
|
121
|
+
* ]);
|
|
122
|
+
* ```
|
|
123
|
+
*/
|
|
124
|
+
async create(name, resources) {
|
|
125
|
+
// Assets can only be created at the peer layer
|
|
126
|
+
// Other layers require migration from peer
|
|
127
|
+
if (this.layer !== 'peer') {
|
|
128
|
+
throw new Error(`Cannot create assets at ${this.layer} layer directly. ` +
|
|
129
|
+
`Create at peer layer first, then use migrate() to move to ${this.layer}.`);
|
|
130
|
+
}
|
|
131
|
+
return this.peerManager.create(name, resources);
|
|
132
|
+
}
|
|
133
|
+
/**
|
|
134
|
+
* Updates an existing event log by appending an update event
|
|
135
|
+
*
|
|
136
|
+
* The new event is cryptographically linked to the previous event
|
|
137
|
+
* via a hash chain (previousEvent field).
|
|
138
|
+
*
|
|
139
|
+
* @param log - The existing event log to update
|
|
140
|
+
* @param data - The update data (new metadata, resources, etc.)
|
|
141
|
+
* @returns Promise resolving to a new EventLog with the update event appended
|
|
142
|
+
*
|
|
143
|
+
* @throws Error if the log is empty or deactivated
|
|
144
|
+
* @throws Error if signer produces invalid proof
|
|
145
|
+
*
|
|
146
|
+
* @example
|
|
147
|
+
* ```typescript
|
|
148
|
+
* const updated = await cel.update(log, {
|
|
149
|
+
* description: 'Updated description',
|
|
150
|
+
* tags: ['art', 'digital']
|
|
151
|
+
* });
|
|
152
|
+
* ```
|
|
153
|
+
*/
|
|
154
|
+
async update(log, data) {
|
|
155
|
+
// Determine the current layer of the log
|
|
156
|
+
const currentLayer = this.getCurrentLayer(log);
|
|
157
|
+
// Use the appropriate manager based on current layer
|
|
158
|
+
switch (currentLayer) {
|
|
159
|
+
case 'peer':
|
|
160
|
+
return this.peerManager.update(log, data);
|
|
161
|
+
case 'webvh': {
|
|
162
|
+
// For webvh, we need to use the webvh manager
|
|
163
|
+
// Get domain from the log if possible
|
|
164
|
+
const webvhDomain = this.extractDomainFromLog(log);
|
|
165
|
+
return this.getWebVHManager(webvhDomain).migrate(log).then(
|
|
166
|
+
// webvh manager doesn't have update, use peer manager's algorithm
|
|
167
|
+
() => this.peerManager.update(log, data));
|
|
168
|
+
}
|
|
169
|
+
case 'btco':
|
|
170
|
+
// For btco, updates use the same underlying algorithm
|
|
171
|
+
return this.peerManager.update(log, data);
|
|
172
|
+
default: {
|
|
173
|
+
// TypeScript exhaustiveness check
|
|
174
|
+
const _exhaustive = currentLayer;
|
|
175
|
+
throw new Error(`Unknown layer: ${String(_exhaustive)}`);
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
/**
|
|
180
|
+
* Verifies all proofs and hash chain integrity in an event log
|
|
181
|
+
*
|
|
182
|
+
* This method verifies:
|
|
183
|
+
* - Each event has at least one proof
|
|
184
|
+
* - Each proof is structurally valid
|
|
185
|
+
* - The hash chain is intact (each event links to previous)
|
|
186
|
+
*
|
|
187
|
+
* @param log - The event log to verify
|
|
188
|
+
* @param options - Optional verification options
|
|
189
|
+
* @returns Promise resolving to VerificationResult with detailed status
|
|
190
|
+
*
|
|
191
|
+
* @example
|
|
192
|
+
* ```typescript
|
|
193
|
+
* const result = await cel.verify(log);
|
|
194
|
+
* if (result.verified) {
|
|
195
|
+
* console.log('Log is valid!');
|
|
196
|
+
* } else {
|
|
197
|
+
* console.error('Verification failed:', result.errors);
|
|
198
|
+
* }
|
|
199
|
+
* ```
|
|
200
|
+
*/
|
|
201
|
+
async verify(log, options) {
|
|
202
|
+
return verifyEventLog(log, options);
|
|
203
|
+
}
|
|
204
|
+
/**
|
|
205
|
+
* Migrates an event log to a target layer
|
|
206
|
+
*
|
|
207
|
+
* Migration adds an update event with migration data and (optionally)
|
|
208
|
+
* witness proofs. The valid migration paths are:
|
|
209
|
+
* - peer → webvh
|
|
210
|
+
* - webvh → btco
|
|
211
|
+
* - peer → btco (requires intermediate webvh migration)
|
|
212
|
+
*
|
|
213
|
+
* @param log - The event log to migrate
|
|
214
|
+
* @param targetLayer - The layer to migrate to
|
|
215
|
+
* @param options - Optional migration options (e.g., domain for webvh)
|
|
216
|
+
* @returns Promise resolving to the migrated EventLog
|
|
217
|
+
*
|
|
218
|
+
* @throws Error if migration path is invalid
|
|
219
|
+
* @throws Error if required config is missing for target layer
|
|
220
|
+
*
|
|
221
|
+
* @example
|
|
222
|
+
* ```typescript
|
|
223
|
+
* // Migrate peer to webvh
|
|
224
|
+
* const webvhLog = await cel.migrate(peerLog, 'webvh', {
|
|
225
|
+
* domain: 'example.com'
|
|
226
|
+
* });
|
|
227
|
+
*
|
|
228
|
+
* // Migrate webvh to btco
|
|
229
|
+
* const btcoLog = await cel.migrate(webvhLog, 'btco');
|
|
230
|
+
* ```
|
|
231
|
+
*/
|
|
232
|
+
async migrate(log, targetLayer, options) {
|
|
233
|
+
const currentLayer = this.getCurrentLayer(log);
|
|
234
|
+
// Validate migration path
|
|
235
|
+
if (currentLayer === targetLayer) {
|
|
236
|
+
throw new Error(`Log is already at ${targetLayer} layer`);
|
|
237
|
+
}
|
|
238
|
+
if (currentLayer === 'btco') {
|
|
239
|
+
throw new Error('Cannot migrate from btco layer - it is the final layer');
|
|
240
|
+
}
|
|
241
|
+
// Perform migration based on current and target layers
|
|
242
|
+
switch (targetLayer) {
|
|
243
|
+
case 'peer':
|
|
244
|
+
throw new Error('Cannot migrate to peer layer - it is the initial layer');
|
|
245
|
+
case 'webvh': {
|
|
246
|
+
if (currentLayer !== 'peer') {
|
|
247
|
+
throw new Error(`Invalid migration: ${currentLayer} → webvh. Can only migrate peer → webvh.`);
|
|
248
|
+
}
|
|
249
|
+
const domain = options?.domain || this.config.webvh?.domain;
|
|
250
|
+
return this.getWebVHManager(domain).migrate(log);
|
|
251
|
+
}
|
|
252
|
+
case 'btco': {
|
|
253
|
+
if (currentLayer === 'peer') {
|
|
254
|
+
// Need to do two-step migration: peer → webvh → btco
|
|
255
|
+
throw new Error('Cannot migrate directly from peer to btco. ' +
|
|
256
|
+
'Migrate to webvh first, then to btco.');
|
|
257
|
+
}
|
|
258
|
+
if (currentLayer !== 'webvh') {
|
|
259
|
+
throw new Error(`Invalid migration: ${String(currentLayer)} → btco. Can only migrate webvh → btco.`);
|
|
260
|
+
}
|
|
261
|
+
return this.btcoManager.migrate(log);
|
|
262
|
+
}
|
|
263
|
+
default: {
|
|
264
|
+
// TypeScript exhaustiveness check
|
|
265
|
+
const _exhaustive = targetLayer;
|
|
266
|
+
throw new Error(`Unknown target layer: ${String(_exhaustive)}`);
|
|
267
|
+
}
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
/**
|
|
271
|
+
* Derives the current asset state by replaying all events in the log
|
|
272
|
+
*
|
|
273
|
+
* @param log - The event log to derive state from
|
|
274
|
+
* @returns The current AssetState
|
|
275
|
+
*
|
|
276
|
+
* @example
|
|
277
|
+
* ```typescript
|
|
278
|
+
* const state = cel.getCurrentState(log);
|
|
279
|
+
* console.log(state.name); // Asset name
|
|
280
|
+
* console.log(state.layer); // Current layer
|
|
281
|
+
* console.log(state.deactivated); // Whether deactivated
|
|
282
|
+
* ```
|
|
283
|
+
*/
|
|
284
|
+
getCurrentState(log) {
|
|
285
|
+
// Determine current layer and use appropriate manager
|
|
286
|
+
const currentLayer = this.getCurrentLayer(log);
|
|
287
|
+
switch (currentLayer) {
|
|
288
|
+
case 'peer':
|
|
289
|
+
return this.peerManager.getCurrentState(log);
|
|
290
|
+
case 'webvh': {
|
|
291
|
+
// WebVH manager also handles state derivation correctly
|
|
292
|
+
const domain = this.extractDomainFromLog(log) || 'unknown.com';
|
|
293
|
+
return this.getWebVHManager(domain).getCurrentState(log);
|
|
294
|
+
}
|
|
295
|
+
case 'btco':
|
|
296
|
+
return this.btcoManager.getCurrentState(log);
|
|
297
|
+
default:
|
|
298
|
+
// Fallback to peer manager which handles all event types
|
|
299
|
+
return this.peerManager.getCurrentState(log);
|
|
300
|
+
}
|
|
301
|
+
}
|
|
302
|
+
/**
|
|
303
|
+
* Determines the current layer of an event log by examining its events
|
|
304
|
+
*
|
|
305
|
+
* @param log - The event log to examine
|
|
306
|
+
* @returns The current layer of the log
|
|
307
|
+
*/
|
|
308
|
+
getCurrentLayer(log) {
|
|
309
|
+
if (!log || !log.events || log.events.length === 0) {
|
|
310
|
+
return 'peer'; // Default for empty logs
|
|
311
|
+
}
|
|
312
|
+
let currentLayer = 'peer';
|
|
313
|
+
for (const event of log.events) {
|
|
314
|
+
const eventData = event.data;
|
|
315
|
+
if (event.type === 'create') {
|
|
316
|
+
currentLayer = eventData.layer || 'peer';
|
|
317
|
+
}
|
|
318
|
+
else if (event.type === 'update' && eventData.targetDid && eventData.layer) {
|
|
319
|
+
// This is a migration event
|
|
320
|
+
currentLayer = eventData.layer;
|
|
321
|
+
}
|
|
322
|
+
}
|
|
323
|
+
return currentLayer;
|
|
324
|
+
}
|
|
325
|
+
/**
|
|
326
|
+
* Extracts the domain from a webvh log's migration event
|
|
327
|
+
*
|
|
328
|
+
* @param log - The event log to examine
|
|
329
|
+
* @returns The domain if found, undefined otherwise
|
|
330
|
+
*/
|
|
331
|
+
extractDomainFromLog(log) {
|
|
332
|
+
if (!log || !log.events) {
|
|
333
|
+
return undefined;
|
|
334
|
+
}
|
|
335
|
+
for (const event of log.events) {
|
|
336
|
+
const eventData = event.data;
|
|
337
|
+
if (eventData.domain) {
|
|
338
|
+
return eventData.domain;
|
|
339
|
+
}
|
|
340
|
+
}
|
|
341
|
+
return undefined;
|
|
342
|
+
}
|
|
343
|
+
/**
|
|
344
|
+
* Gets the configured layer for this instance
|
|
345
|
+
*/
|
|
346
|
+
get currentLayer() {
|
|
347
|
+
return this.layer;
|
|
348
|
+
}
|
|
349
|
+
}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* createEventLog Algorithm
|
|
3
|
+
*
|
|
4
|
+
* Creates a new Cryptographic Event Log with an initial "create" event.
|
|
5
|
+
* The create event is the first event in a log and has no previousEvent reference.
|
|
6
|
+
*
|
|
7
|
+
* @see https://w3c-ccg.github.io/cel-spec/
|
|
8
|
+
*/
|
|
9
|
+
import type { EventLog, CreateOptions } from '../types';
|
|
10
|
+
/**
|
|
11
|
+
* Creates a new event log with a single "create" event.
|
|
12
|
+
*
|
|
13
|
+
* This is the first step in creating a CEL-based provenance chain.
|
|
14
|
+
* The create event establishes the initial state of an asset.
|
|
15
|
+
*
|
|
16
|
+
* @param data - The initial data for the asset (e.g., name, resources, metadata)
|
|
17
|
+
* @param options - Signing options including signer function and verification method
|
|
18
|
+
* @returns A new EventLog containing a single create event
|
|
19
|
+
*
|
|
20
|
+
* @example
|
|
21
|
+
* ```typescript
|
|
22
|
+
* const log = await createEventLog(
|
|
23
|
+
* { name: 'My Asset', resources: [...] },
|
|
24
|
+
* {
|
|
25
|
+
* signer: async (data) => createEdDsaProof(data, privateKey),
|
|
26
|
+
* verificationMethod: 'did:key:z6Mk...',
|
|
27
|
+
* proofPurpose: 'assertionMethod'
|
|
28
|
+
* }
|
|
29
|
+
* );
|
|
30
|
+
* ```
|
|
31
|
+
*/
|
|
32
|
+
export declare function createEventLog(data: unknown, options: CreateOptions): Promise<EventLog>;
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* createEventLog Algorithm
|
|
3
|
+
*
|
|
4
|
+
* Creates a new Cryptographic Event Log with an initial "create" event.
|
|
5
|
+
* The create event is the first event in a log and has no previousEvent reference.
|
|
6
|
+
*
|
|
7
|
+
* @see https://w3c-ccg.github.io/cel-spec/
|
|
8
|
+
*/
|
|
9
|
+
/**
|
|
10
|
+
* Creates a new event log with a single "create" event.
|
|
11
|
+
*
|
|
12
|
+
* This is the first step in creating a CEL-based provenance chain.
|
|
13
|
+
* The create event establishes the initial state of an asset.
|
|
14
|
+
*
|
|
15
|
+
* @param data - The initial data for the asset (e.g., name, resources, metadata)
|
|
16
|
+
* @param options - Signing options including signer function and verification method
|
|
17
|
+
* @returns A new EventLog containing a single create event
|
|
18
|
+
*
|
|
19
|
+
* @example
|
|
20
|
+
* ```typescript
|
|
21
|
+
* const log = await createEventLog(
|
|
22
|
+
* { name: 'My Asset', resources: [...] },
|
|
23
|
+
* {
|
|
24
|
+
* signer: async (data) => createEdDsaProof(data, privateKey),
|
|
25
|
+
* verificationMethod: 'did:key:z6Mk...',
|
|
26
|
+
* proofPurpose: 'assertionMethod'
|
|
27
|
+
* }
|
|
28
|
+
* );
|
|
29
|
+
* ```
|
|
30
|
+
*/
|
|
31
|
+
export async function createEventLog(data, options) {
|
|
32
|
+
const { signer, verificationMethod, proofPurpose = 'assertionMethod' } = options;
|
|
33
|
+
// Create the event structure without proof first
|
|
34
|
+
const eventBase = {
|
|
35
|
+
type: 'create',
|
|
36
|
+
data,
|
|
37
|
+
// Note: First event has no previousEvent
|
|
38
|
+
};
|
|
39
|
+
// Generate proof using the provided signer
|
|
40
|
+
const proof = await signer(eventBase);
|
|
41
|
+
// Validate the proof has required fields
|
|
42
|
+
if (!proof.type || !proof.cryptosuite || !proof.proofValue) {
|
|
43
|
+
throw new Error('Invalid proof: missing required fields (type, cryptosuite, proofValue)');
|
|
44
|
+
}
|
|
45
|
+
// Construct the complete log entry
|
|
46
|
+
const entry = {
|
|
47
|
+
type: 'create',
|
|
48
|
+
data,
|
|
49
|
+
proof: [proof],
|
|
50
|
+
};
|
|
51
|
+
// Return the new event log
|
|
52
|
+
const eventLog = {
|
|
53
|
+
events: [entry],
|
|
54
|
+
};
|
|
55
|
+
return eventLog;
|
|
56
|
+
}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* deactivateEventLog Algorithm
|
|
3
|
+
*
|
|
4
|
+
* Seals an event log with a "deactivate" event. Once deactivated,
|
|
5
|
+
* no further events should be added to the log.
|
|
6
|
+
*
|
|
7
|
+
* @see https://w3c-ccg.github.io/cel-spec/
|
|
8
|
+
*/
|
|
9
|
+
import type { EventLog, DeactivateOptions } from '../types';
|
|
10
|
+
/**
|
|
11
|
+
* Deactivates an event log by appending a final "deactivate" event.
|
|
12
|
+
*
|
|
13
|
+
* The deactivate event seals the log, indicating that no further
|
|
14
|
+
* events should be added. This is used to mark an asset as retired,
|
|
15
|
+
* revoked, or otherwise no longer active.
|
|
16
|
+
*
|
|
17
|
+
* @param log - The existing event log to deactivate
|
|
18
|
+
* @param reason - The reason for deactivation (e.g., "retired", "revoked", "superseded")
|
|
19
|
+
* @param options - Signing options including signer function and verification method
|
|
20
|
+
* @returns A new EventLog with the deactivate event appended (input is not mutated)
|
|
21
|
+
*
|
|
22
|
+
* @example
|
|
23
|
+
* ```typescript
|
|
24
|
+
* const deactivatedLog = await deactivateEventLog(
|
|
25
|
+
* existingLog,
|
|
26
|
+
* 'Asset has been superseded by a new version',
|
|
27
|
+
* {
|
|
28
|
+
* signer: async (data) => createEdDsaProof(data, privateKey),
|
|
29
|
+
* verificationMethod: 'did:key:z6Mk...',
|
|
30
|
+
* proofPurpose: 'assertionMethod'
|
|
31
|
+
* }
|
|
32
|
+
* );
|
|
33
|
+
* ```
|
|
34
|
+
*/
|
|
35
|
+
export declare function deactivateEventLog(log: EventLog, reason: string, options: DeactivateOptions): Promise<EventLog>;
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* deactivateEventLog Algorithm
|
|
3
|
+
*
|
|
4
|
+
* Seals an event log with a "deactivate" event. Once deactivated,
|
|
5
|
+
* no further events should be added to the log.
|
|
6
|
+
*
|
|
7
|
+
* @see https://w3c-ccg.github.io/cel-spec/
|
|
8
|
+
*/
|
|
9
|
+
import { computeDigestMultibase } from '../hash';
|
|
10
|
+
/**
|
|
11
|
+
* Serializes a LogEntry to a deterministic byte representation for hashing.
|
|
12
|
+
* Uses JSON with sorted keys for reproducibility.
|
|
13
|
+
*
|
|
14
|
+
* @param entry - The log entry to serialize
|
|
15
|
+
* @returns UTF-8 encoded bytes
|
|
16
|
+
*/
|
|
17
|
+
function serializeEntry(entry) {
|
|
18
|
+
// Use JSON with sorted keys for deterministic serialization
|
|
19
|
+
const json = JSON.stringify(entry, Object.keys(entry).sort());
|
|
20
|
+
return new TextEncoder().encode(json);
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Deactivates an event log by appending a final "deactivate" event.
|
|
24
|
+
*
|
|
25
|
+
* The deactivate event seals the log, indicating that no further
|
|
26
|
+
* events should be added. This is used to mark an asset as retired,
|
|
27
|
+
* revoked, or otherwise no longer active.
|
|
28
|
+
*
|
|
29
|
+
* @param log - The existing event log to deactivate
|
|
30
|
+
* @param reason - The reason for deactivation (e.g., "retired", "revoked", "superseded")
|
|
31
|
+
* @param options - Signing options including signer function and verification method
|
|
32
|
+
* @returns A new EventLog with the deactivate event appended (input is not mutated)
|
|
33
|
+
*
|
|
34
|
+
* @example
|
|
35
|
+
* ```typescript
|
|
36
|
+
* const deactivatedLog = await deactivateEventLog(
|
|
37
|
+
* existingLog,
|
|
38
|
+
* 'Asset has been superseded by a new version',
|
|
39
|
+
* {
|
|
40
|
+
* signer: async (data) => createEdDsaProof(data, privateKey),
|
|
41
|
+
* verificationMethod: 'did:key:z6Mk...',
|
|
42
|
+
* proofPurpose: 'assertionMethod'
|
|
43
|
+
* }
|
|
44
|
+
* );
|
|
45
|
+
* ```
|
|
46
|
+
*/
|
|
47
|
+
export async function deactivateEventLog(log, reason, options) {
|
|
48
|
+
const { signer, verificationMethod, proofPurpose = 'assertionMethod' } = options;
|
|
49
|
+
// Validate input log
|
|
50
|
+
if (!log.events || log.events.length === 0) {
|
|
51
|
+
throw new Error('Cannot deactivate an empty event log');
|
|
52
|
+
}
|
|
53
|
+
// Check if log is already deactivated
|
|
54
|
+
const lastEvent = log.events[log.events.length - 1];
|
|
55
|
+
if (lastEvent.type === 'deactivate') {
|
|
56
|
+
throw new Error('Event log is already deactivated');
|
|
57
|
+
}
|
|
58
|
+
// Compute the digestMultibase of the last event
|
|
59
|
+
const previousEvent = computeDigestMultibase(serializeEntry(lastEvent));
|
|
60
|
+
// Deactivation data includes the reason
|
|
61
|
+
const deactivationData = {
|
|
62
|
+
reason,
|
|
63
|
+
deactivatedAt: new Date().toISOString(),
|
|
64
|
+
};
|
|
65
|
+
// Create the event structure without proof first
|
|
66
|
+
const eventBase = {
|
|
67
|
+
type: 'deactivate',
|
|
68
|
+
data: deactivationData,
|
|
69
|
+
previousEvent,
|
|
70
|
+
};
|
|
71
|
+
// Generate proof using the provided signer
|
|
72
|
+
const proof = await signer(eventBase);
|
|
73
|
+
// Validate the proof has required fields
|
|
74
|
+
if (!proof.type || !proof.cryptosuite || !proof.proofValue) {
|
|
75
|
+
throw new Error('Invalid proof: missing required fields (type, cryptosuite, proofValue)');
|
|
76
|
+
}
|
|
77
|
+
// Construct the complete log entry
|
|
78
|
+
const entry = {
|
|
79
|
+
type: 'deactivate',
|
|
80
|
+
data: deactivationData,
|
|
81
|
+
previousEvent,
|
|
82
|
+
proof: [proof],
|
|
83
|
+
};
|
|
84
|
+
// Return a new event log (immutable - does not mutate input)
|
|
85
|
+
const eventLog = {
|
|
86
|
+
events: [...log.events, entry],
|
|
87
|
+
// Preserve previousLog reference if it exists
|
|
88
|
+
...(log.previousLog ? { previousLog: log.previousLog } : {}),
|
|
89
|
+
};
|
|
90
|
+
return eventLog;
|
|
91
|
+
}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* CEL Algorithms
|
|
3
|
+
*
|
|
4
|
+
* Core algorithms for working with Cryptographic Event Logs.
|
|
5
|
+
*/
|
|
6
|
+
export { createEventLog } from './createEventLog';
|
|
7
|
+
export { updateEventLog } from './updateEventLog';
|
|
8
|
+
export { deactivateEventLog } from './deactivateEventLog';
|
|
9
|
+
export { verifyEventLog } from './verifyEventLog';
|
|
10
|
+
export { witnessEvent } from './witnessEvent';
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* CEL Algorithms
|
|
3
|
+
*
|
|
4
|
+
* Core algorithms for working with Cryptographic Event Logs.
|
|
5
|
+
*/
|
|
6
|
+
export { createEventLog } from './createEventLog';
|
|
7
|
+
export { updateEventLog } from './updateEventLog';
|
|
8
|
+
export { deactivateEventLog } from './deactivateEventLog';
|
|
9
|
+
export { verifyEventLog } from './verifyEventLog';
|
|
10
|
+
export { witnessEvent } from './witnessEvent';
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* updateEventLog Algorithm
|
|
3
|
+
*
|
|
4
|
+
* Appends an update event to an existing Cryptographic Event Log.
|
|
5
|
+
* Each update event references the previous event via a hash chain.
|
|
6
|
+
*
|
|
7
|
+
* @see https://w3c-ccg.github.io/cel-spec/
|
|
8
|
+
*/
|
|
9
|
+
import type { EventLog, UpdateOptions } from '../types';
|
|
10
|
+
/**
|
|
11
|
+
* Updates an event log by appending a new "update" event.
|
|
12
|
+
*
|
|
13
|
+
* The new event is cryptographically linked to the previous event
|
|
14
|
+
* via a hash of the last event (previousEvent field).
|
|
15
|
+
*
|
|
16
|
+
* @param log - The existing event log to update
|
|
17
|
+
* @param data - The update data (e.g., modified metadata, new resources)
|
|
18
|
+
* @param options - Signing options including signer function and verification method
|
|
19
|
+
* @returns A new EventLog with the update event appended (input is not mutated)
|
|
20
|
+
*
|
|
21
|
+
* @example
|
|
22
|
+
* ```typescript
|
|
23
|
+
* const updatedLog = await updateEventLog(
|
|
24
|
+
* existingLog,
|
|
25
|
+
* { name: 'Updated Asset Name', version: 2 },
|
|
26
|
+
* {
|
|
27
|
+
* signer: async (data) => createEdDsaProof(data, privateKey),
|
|
28
|
+
* verificationMethod: 'did:key:z6Mk...',
|
|
29
|
+
* proofPurpose: 'assertionMethod'
|
|
30
|
+
* }
|
|
31
|
+
* );
|
|
32
|
+
* ```
|
|
33
|
+
*/
|
|
34
|
+
export declare function updateEventLog(log: EventLog, data: unknown, options: UpdateOptions): Promise<EventLog>;
|