@twin.org/entity-storage-connector-dynamodb 0.0.2-next.8 → 0.0.3-next.1

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/README.md CHANGED
@@ -13,7 +13,7 @@ npm install @twin.org/entity-storage-connector-dynamodb
13
13
  The tests developed are functional tests and need an instance of DynamoDB up and running. To run DynamoDB locally:
14
14
 
15
15
  ```sh
16
- docker run -p 8500:8000 --name twin-entity-storage-dynamodb --hostname dynamodb -d amazon/dynamodb-local
16
+ docker run -p 10000:8000 --name twin-entity-storage-dynamodb --hostname dynamodb -d amazon/dynamodb-local
17
17
  ```
18
18
 
19
19
  Afterwards you can run the tests as follows:
@@ -1,39 +1,44 @@
1
- import { waitUntilTableExists, DynamoDB, QueryCommand } from '@aws-sdk/client-dynamodb';
2
- import { GetCommand, PutCommand, DeleteCommand, DynamoDBDocumentClient } from '@aws-sdk/lib-dynamodb';
3
- import { unmarshall } from '@aws-sdk/util-dynamodb';
4
- import { Guards, Is, ComponentFactory, BaseError, GeneralError, Coerce, ObjectHelper, Converter } from '@twin.org/core';
5
- import { EntitySchemaFactory, EntitySchemaHelper, ComparisonOperator, LogicalOperator, SortDirection } from '@twin.org/entity';
6
-
7
1
  // Copyright 2024 IOTA Stiftung.
8
2
  // SPDX-License-Identifier: Apache-2.0.
3
+ import { DynamoDB, QueryCommand, waitUntilTableExists } from "@aws-sdk/client-dynamodb";
4
+ import { DeleteCommand, DynamoDBDocumentClient, GetCommand, PutCommand } from "@aws-sdk/lib-dynamodb";
5
+ import { unmarshall } from "@aws-sdk/util-dynamodb";
6
+ import { ContextIdHelper, ContextIdStore } from "@twin.org/context";
7
+ import { BaseError, Coerce, ComponentFactory, Converter, GeneralError, Guards, Is, ObjectHelper } from "@twin.org/core";
8
+ import { ComparisonOperator, EntitySchemaFactory, EntitySchemaHelper, LogicalOperator, SortDirection } from "@twin.org/entity";
9
9
  /**
10
10
  * Class for performing entity storage operations using Dynamo DB.
11
11
  */
12
- class DynamoDbEntityStorageConnector {
12
+ export class DynamoDbEntityStorageConnector {
13
+ /**
14
+ * Runtime name for the class.
15
+ */
16
+ static CLASS_NAME = "DynamoDbEntityStorageConnector";
13
17
  /**
14
18
  * Limit the number of entities when finding.
15
19
  * @internal
16
20
  */
17
- static _PAGE_SIZE = 40;
21
+ static _DEFAULT_LIMIT = 40;
18
22
  /**
19
23
  * Partition id field name.
20
24
  * @internal
21
25
  */
22
- static _PARTITION_ID_NAME = "partitionId";
26
+ static _PARTITION_KEY = "partitionId";
23
27
  /**
24
28
  * Partition id field value.
25
29
  * @internal
26
30
  */
27
- static _PARTITION_ID_VALUE = "1";
28
- /**
29
- * Runtime name for the class.
30
- */
31
- CLASS_NAME = "DynamoDbEntityStorageConnector";
31
+ static _PARTITION_KEY_VALUE = "root";
32
32
  /**
33
33
  * The schema for the entity.
34
34
  * @internal
35
35
  */
36
36
  _entitySchema;
37
+ /**
38
+ * The keys to use from the context ids to create partitions.
39
+ * @internal
40
+ */
41
+ _partitionContextIds;
37
42
  /**
38
43
  * The primary key.
39
44
  * @internal
@@ -49,20 +54,38 @@ class DynamoDbEntityStorageConnector {
49
54
  * @param options The options for the connector.
50
55
  */
51
56
  constructor(options) {
52
- Guards.object(this.CLASS_NAME, "options", options);
53
- Guards.stringValue(this.CLASS_NAME, "options.entitySchema", options.entitySchema);
54
- Guards.object(this.CLASS_NAME, "options.config", options.config);
55
- Guards.stringValue(this.CLASS_NAME, "options.config.accessKeyId", options.config.accessKeyId);
56
- Guards.stringValue(this.CLASS_NAME, "options.config.secretAccessKey", options.config.secretAccessKey);
57
- Guards.stringValue(this.CLASS_NAME, "options.config.region", options.config.region);
58
- Guards.stringValue(this.CLASS_NAME, "options.config.tableName", options.config.tableName);
57
+ Guards.object(DynamoDbEntityStorageConnector.CLASS_NAME, "options", options);
58
+ Guards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, "options.entitySchema", options.entitySchema);
59
+ Guards.object(DynamoDbEntityStorageConnector.CLASS_NAME, "options.config", options.config);
60
+ options.config.authMode ??= "credentials";
61
+ if (options.config.authMode === "credentials") {
62
+ Guards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, "options.config.accessKeyId", options.config.accessKeyId);
63
+ Guards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, "options.config.secretAccessKey", options.config.secretAccessKey);
64
+ }
65
+ Guards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, "options.config.region", options.config.region);
66
+ Guards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, "options.config.tableName", options.config.tableName);
59
67
  this._entitySchema = EntitySchemaFactory.get(options.entitySchema);
68
+ this._partitionContextIds = options.partitionContextIds;
60
69
  this._primaryKey = EntitySchemaHelper.getPrimaryKey(this._entitySchema);
61
70
  this._config = options.config;
62
71
  this._config.endpoint = Is.stringValue(this._config.endpoint)
63
72
  ? this._config.endpoint
64
73
  : undefined;
65
74
  }
75
+ /**
76
+ * Returns the class name of the component.
77
+ * @returns The class name of the component.
78
+ */
79
+ className() {
80
+ return DynamoDbEntityStorageConnector.CLASS_NAME;
81
+ }
82
+ /**
83
+ * Get the schema for the entities.
84
+ * @returns The schema for the entities.
85
+ */
86
+ getSchema() {
87
+ return this._entitySchema;
88
+ }
66
89
  /**
67
90
  * Bootstrap the component by creating and initializing any resources it needs.
68
91
  * @param nodeLoggingComponentType The node logging component type.
@@ -73,7 +96,7 @@ class DynamoDbEntityStorageConnector {
73
96
  if (!(await this.tableExists(this._config.tableName))) {
74
97
  await nodeLogging?.log({
75
98
  level: "info",
76
- source: this.CLASS_NAME,
99
+ source: DynamoDbEntityStorageConnector.CLASS_NAME,
77
100
  ts: Date.now(),
78
101
  message: "tableCreating",
79
102
  data: {
@@ -94,11 +117,11 @@ class DynamoDbEntityStorageConnector {
94
117
  // We always add a partition key to the table as a non optional hash key
95
118
  // is always required when querying using sort parameters
96
119
  tableParams.AttributeDefinitions?.push({
97
- AttributeName: DynamoDbEntityStorageConnector._PARTITION_ID_NAME,
120
+ AttributeName: DynamoDbEntityStorageConnector._PARTITION_KEY,
98
121
  AttributeType: "S"
99
122
  });
100
123
  tableParams.KeySchema?.push({
101
- AttributeName: DynamoDbEntityStorageConnector._PARTITION_ID_NAME,
124
+ AttributeName: DynamoDbEntityStorageConnector._PARTITION_KEY,
102
125
  KeyType: "HASH"
103
126
  });
104
127
  const gsi = [];
@@ -125,7 +148,7 @@ class DynamoDbEntityStorageConnector {
125
148
  IndexName: `${prop.property}Index`,
126
149
  KeySchema: [
127
150
  {
128
- AttributeName: DynamoDbEntityStorageConnector._PARTITION_ID_NAME,
151
+ AttributeName: DynamoDbEntityStorageConnector._PARTITION_KEY,
129
152
  KeyType: "HASH"
130
153
  },
131
154
  {
@@ -157,7 +180,7 @@ class DynamoDbEntityStorageConnector {
157
180
  });
158
181
  await nodeLogging?.log({
159
182
  level: "info",
160
- source: this.CLASS_NAME,
183
+ source: DynamoDbEntityStorageConnector.CLASS_NAME,
161
184
  ts: Date.now(),
162
185
  message: "tableCreated",
163
186
  data: {
@@ -169,7 +192,7 @@ class DynamoDbEntityStorageConnector {
169
192
  if (BaseError.isErrorCode(err, "ResourceInUseException")) {
170
193
  await nodeLogging?.log({
171
194
  level: "info",
172
- source: this.CLASS_NAME,
195
+ source: DynamoDbEntityStorageConnector.CLASS_NAME,
173
196
  ts: Date.now(),
174
197
  message: "tableExists",
175
198
  data: {
@@ -180,7 +203,7 @@ class DynamoDbEntityStorageConnector {
180
203
  else {
181
204
  await nodeLogging?.log({
182
205
  level: "error",
183
- source: this.CLASS_NAME,
206
+ source: DynamoDbEntityStorageConnector.CLASS_NAME,
184
207
  ts: Date.now(),
185
208
  message: "tableCreateFailed",
186
209
  error: BaseError.fromError(err),
@@ -195,7 +218,7 @@ class DynamoDbEntityStorageConnector {
195
218
  else {
196
219
  await nodeLogging?.log({
197
220
  level: "info",
198
- source: this.CLASS_NAME,
221
+ source: DynamoDbEntityStorageConnector.CLASS_NAME,
199
222
  ts: Date.now(),
200
223
  message: "tableExists",
201
224
  data: {
@@ -205,13 +228,6 @@ class DynamoDbEntityStorageConnector {
205
228
  }
206
229
  return true;
207
230
  }
208
- /**
209
- * Get the schema for the entities.
210
- * @returns The schema for the entities.
211
- */
212
- getSchema() {
213
- return this._entitySchema;
214
- }
215
231
  /**
216
232
  * Get an entity.
217
233
  * @param id The id of the entity to get, or the index value if secondaryIndex is set.
@@ -220,19 +236,21 @@ class DynamoDbEntityStorageConnector {
220
236
  * @returns The object if it can be found or undefined.
221
237
  */
222
238
  async get(id, secondaryIndex, conditions) {
223
- Guards.stringValue(this.CLASS_NAME, "id", id);
239
+ Guards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, "id", id);
240
+ const contextIds = await ContextIdStore.getContextIds();
241
+ const partitionKey = ContextIdHelper.combinedContextKey(contextIds, this._partitionContextIds);
224
242
  try {
225
243
  const docClient = this.createDocClient();
226
244
  if (Is.empty(secondaryIndex) && Is.empty(conditions)) {
227
245
  const getCommand = new GetCommand({
228
246
  TableName: this._config.tableName,
229
247
  Key: {
230
- [DynamoDbEntityStorageConnector._PARTITION_ID_NAME]: DynamoDbEntityStorageConnector._PARTITION_ID_VALUE,
248
+ [DynamoDbEntityStorageConnector._PARTITION_KEY]: partitionKey ?? DynamoDbEntityStorageConnector._PARTITION_KEY_VALUE,
231
249
  [this._primaryKey.property]: id
232
250
  }
233
251
  });
234
252
  const response = await docClient.send(getCommand);
235
- delete response.Item?.[DynamoDbEntityStorageConnector._PARTITION_ID_NAME];
253
+ delete response.Item?.[DynamoDbEntityStorageConnector._PARTITION_KEY];
236
254
  return response.Item;
237
255
  }
238
256
  const finalConditions = {
@@ -254,16 +272,16 @@ class DynamoDbEntityStorageConnector {
254
272
  });
255
273
  }
256
274
  }
257
- const queryResult = await this.internalQuery(finalConditions, undefined, undefined, undefined, 1, secondaryIndex);
275
+ const queryResult = await this.internalQuery(finalConditions, undefined, undefined, undefined, 1, secondaryIndex, partitionKey);
258
276
  return queryResult.entities[0];
259
277
  }
260
278
  catch (err) {
261
279
  if (BaseError.isErrorCode(err, "ResourceNotFoundException")) {
262
- throw new GeneralError(this.CLASS_NAME, "tableDoesNotExist", {
263
- table: this._config.tableName
280
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "tableDoesNotExist", {
281
+ tableName: this._config.tableName
264
282
  }, err);
265
283
  }
266
- throw new GeneralError(this.CLASS_NAME, "getFailed", {
284
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "getFailed", {
267
285
  id
268
286
  }, err);
269
287
  }
@@ -275,7 +293,9 @@ class DynamoDbEntityStorageConnector {
275
293
  * @returns The id of the entity.
276
294
  */
277
295
  async set(entity, conditions) {
278
- Guards.object(this.CLASS_NAME, "entity", entity);
296
+ Guards.object(DynamoDbEntityStorageConnector.CLASS_NAME, "entity", entity);
297
+ const contextIds = await ContextIdStore.getContextIds();
298
+ const partitionKey = ContextIdHelper.combinedContextKey(contextIds, this._partitionContextIds);
279
299
  EntitySchemaHelper.validateEntity(entity, this.getSchema());
280
300
  const id = entity[this._primaryKey.property];
281
301
  try {
@@ -284,7 +304,7 @@ class DynamoDbEntityStorageConnector {
284
304
  const putCommand = new PutCommand({
285
305
  TableName: this._config.tableName,
286
306
  Item: {
287
- [DynamoDbEntityStorageConnector._PARTITION_ID_NAME]: DynamoDbEntityStorageConnector._PARTITION_ID_VALUE,
307
+ [DynamoDbEntityStorageConnector._PARTITION_KEY]: partitionKey ?? DynamoDbEntityStorageConnector._PARTITION_KEY_VALUE,
288
308
  ...entity
289
309
  },
290
310
  // Only set the condition expression if we have conditions to match
@@ -302,11 +322,11 @@ class DynamoDbEntityStorageConnector {
302
322
  return;
303
323
  }
304
324
  if (BaseError.isErrorCode(err, "ResourceNotFoundException")) {
305
- throw new GeneralError(this.CLASS_NAME, "tableDoesNotExist", {
325
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "tableDoesNotExist", {
306
326
  tableName: this._config.tableName
307
327
  }, err);
308
328
  }
309
- throw new GeneralError(this.CLASS_NAME, "setFailed", {
329
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "setFailed", {
310
330
  id
311
331
  }, err);
312
332
  }
@@ -318,14 +338,16 @@ class DynamoDbEntityStorageConnector {
318
338
  * @returns Nothing.
319
339
  */
320
340
  async remove(id, conditions) {
321
- Guards.stringValue(this.CLASS_NAME, "id", id);
341
+ Guards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, "id", id);
342
+ const contextIds = await ContextIdStore.getContextIds();
343
+ const partitionKey = ContextIdHelper.combinedContextKey(contextIds, this._partitionContextIds);
322
344
  try {
323
345
  const docClient = this.createDocClient();
324
346
  const { conditionExpression, attributeNames, attributeValues } = this.buildConditionExpression(conditions);
325
347
  const deleteCommand = new DeleteCommand({
326
348
  TableName: this._config.tableName,
327
349
  Key: {
328
- [DynamoDbEntityStorageConnector._PARTITION_ID_NAME]: DynamoDbEntityStorageConnector._PARTITION_ID_VALUE,
350
+ [DynamoDbEntityStorageConnector._PARTITION_KEY]: partitionKey ?? DynamoDbEntityStorageConnector._PARTITION_KEY_VALUE,
329
351
  [this._primaryKey.property]: id
330
352
  },
331
353
  ConditionExpression: conditionExpression,
@@ -339,11 +361,11 @@ class DynamoDbEntityStorageConnector {
339
361
  return;
340
362
  }
341
363
  if (BaseError.isErrorCode(err, "ResourceNotFoundException")) {
342
- throw new GeneralError(this.CLASS_NAME, "tableDoesNotExist", {
343
- table: this._config.tableName
364
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "tableDoesNotExist", {
365
+ tableName: this._config.tableName
344
366
  }, err);
345
367
  }
346
- throw new GeneralError(this.CLASS_NAME, "removeFailed", {
368
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "removeFailed", {
347
369
  id
348
370
  }, err);
349
371
  }
@@ -353,13 +375,15 @@ class DynamoDbEntityStorageConnector {
353
375
  * @param conditions The conditions to match for the entities.
354
376
  * @param sortProperties The optional sort order.
355
377
  * @param properties The optional properties to return, defaults to all.
356
- * @param cursor The cursor to request the next page of entities.
357
- * @param pageSize The suggested number of entities to return in each chunk, in some scenarios can return a different amount.
378
+ * @param cursor The cursor to request the next chunk of entities.
379
+ * @param limit The suggested number of entities to return in each chunk, in some scenarios can return a different amount.
358
380
  * @returns All the entities for the storage matching the conditions,
359
381
  * and a cursor which can be used to request more entities.
360
382
  */
361
- async query(conditions, sortProperties, properties, cursor, pageSize) {
362
- return this.internalQuery(conditions, sortProperties, properties, cursor, pageSize);
383
+ async query(conditions, sortProperties, properties, cursor, limit) {
384
+ const contextIds = await ContextIdStore.getContextIds();
385
+ const partitionKey = ContextIdHelper.combinedContextKey(contextIds, this._partitionContextIds);
386
+ return this.internalQuery(conditions, sortProperties, properties, cursor, limit, undefined, partitionKey);
363
387
  }
364
388
  /**
365
389
  * Delete the table.
@@ -489,7 +513,7 @@ class DynamoDbEntityStorageConnector {
489
513
  else if (comparator.comparison === ComparisonOperator.In) {
490
514
  return `${propName} IN ${attributeName}`;
491
515
  }
492
- throw new GeneralError(this.CLASS_NAME, "comparisonNotSupported", {
516
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "comparisonNotSupported", {
493
517
  comparison: comparator.comparison
494
518
  });
495
519
  }
@@ -526,7 +550,9 @@ class DynamoDbEntityStorageConnector {
526
550
  else if (operator === LogicalOperator.Or) {
527
551
  return "OR";
528
552
  }
529
- throw new GeneralError(this.CLASS_NAME, "conditionalNotSupported", { operator });
553
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "conditionalNotSupported", {
554
+ operator
555
+ });
530
556
  }
531
557
  /**
532
558
  * Format a value to insert into DB.
@@ -582,11 +608,19 @@ class DynamoDbEntityStorageConnector {
582
608
  * @internal
583
609
  */
584
610
  createConnectionConfig() {
611
+ if (Is.stringValue(this._config.secretAccessKey) &&
612
+ Is.stringValue(this._config.accessKeyId) &&
613
+ this._config.authMode === "credentials") {
614
+ return {
615
+ credentials: {
616
+ accessKeyId: this._config.accessKeyId,
617
+ secretAccessKey: this._config.secretAccessKey
618
+ },
619
+ endpoint: this._config.endpoint,
620
+ region: this._config.region
621
+ };
622
+ }
585
623
  return {
586
- credentials: {
587
- accessKeyId: this._config.accessKeyId,
588
- secretAccessKey: this._config.secretAccessKey
589
- },
590
624
  endpoint: this._config.endpoint,
591
625
  region: this._config.region
592
626
  };
@@ -612,16 +646,17 @@ class DynamoDbEntityStorageConnector {
612
646
  * @param conditions The conditions to match for the entities.
613
647
  * @param sortProperties The optional sort order.
614
648
  * @param properties The optional properties to return, defaults to all.
615
- * @param cursor The cursor to request the next page of entities.
616
- * @param pageSize The suggested number of entities to return in each chunk, in some scenarios can return a different amount.
649
+ * @param cursor The cursor to request the next chunk of entities.
650
+ * @param limit The suggested number of entities to return in each chunk, in some scenarios can return a different amount.
617
651
  * @param secondaryIndex The secondary index to use for the query.
652
+ * @param partitionKey The partition key to use for the query.
618
653
  * @returns All the entities for the storage matching the conditions,
619
654
  * and a cursor which can be used to request more entities.
620
655
  * @internal
621
656
  */
622
- async internalQuery(conditions, sortProperties, properties, cursor, pageSize, secondaryIndex) {
657
+ async internalQuery(conditions, sortProperties, properties, cursor, limit, secondaryIndex, partitionKey) {
623
658
  try {
624
- const returnSize = pageSize ?? DynamoDbEntityStorageConnector._PAGE_SIZE;
659
+ const returnSize = limit ?? DynamoDbEntityStorageConnector._DEFAULT_LIMIT;
625
660
  let indexName = Is.stringValue(secondaryIndex)
626
661
  ? `${secondaryIndex}Index`
627
662
  : undefined;
@@ -630,7 +665,7 @@ class DynamoDbEntityStorageConnector {
630
665
  let scanAscending = true;
631
666
  if (Is.arrayValue(sortProperties)) {
632
667
  if (sortProperties.length > 1) {
633
- throw new GeneralError(this.CLASS_NAME, "sortSingle");
668
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "sortSingle");
634
669
  }
635
670
  for (const sortProperty of sortProperties) {
636
671
  const propertySchema = this._entitySchema.properties?.find(e => e.property === sortProperty.property);
@@ -638,7 +673,7 @@ class DynamoDbEntityStorageConnector {
638
673
  (!propertySchema.isPrimary &&
639
674
  !propertySchema.isSecondary &&
640
675
  Is.empty(propertySchema.sortDirection))) {
641
- throw new GeneralError(this.CLASS_NAME, "sortNotIndexed", {
676
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "sortNotIndexed", {
642
677
  property: sortProperty.property
643
678
  });
644
679
  }
@@ -650,8 +685,8 @@ class DynamoDbEntityStorageConnector {
650
685
  }
651
686
  const attributeNames = { "#partitionId": "partitionId" };
652
687
  const attributeValues = {
653
- [`:${DynamoDbEntityStorageConnector._PARTITION_ID_NAME}`]: {
654
- S: DynamoDbEntityStorageConnector._PARTITION_ID_VALUE
688
+ [`:${DynamoDbEntityStorageConnector._PARTITION_KEY}`]: {
689
+ S: partitionKey ?? DynamoDbEntityStorageConnector._PARTITION_KEY_VALUE
655
690
  }
656
691
  };
657
692
  const expressions = this.buildQueryParameters("", conditions, attributeNames, attributeValues, secondaryIndex);
@@ -681,7 +716,7 @@ class DynamoDbEntityStorageConnector {
681
716
  if (Is.arrayValue(results.Items)) {
682
717
  entities = results.Items.map(item => {
683
718
  const unmarshalled = unmarshall(item);
684
- delete unmarshalled[DynamoDbEntityStorageConnector._PARTITION_ID_NAME];
719
+ delete unmarshalled[DynamoDbEntityStorageConnector._PARTITION_KEY];
685
720
  return unmarshalled;
686
721
  });
687
722
  }
@@ -694,11 +729,11 @@ class DynamoDbEntityStorageConnector {
694
729
  }
695
730
  catch (err) {
696
731
  if (BaseError.isErrorCode(err, "ResourceNotFoundException")) {
697
- throw new GeneralError(this.CLASS_NAME, "tableDoesNotExist", {
698
- table: this._config.tableName
732
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "tableDoesNotExist", {
733
+ tableName: this._config.tableName
699
734
  }, err);
700
735
  }
701
- throw new GeneralError(this.CLASS_NAME, "queryFailed", undefined, err);
736
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "queryFailed", undefined, err);
702
737
  }
703
738
  }
704
739
  /**
@@ -717,7 +752,7 @@ class DynamoDbEntityStorageConnector {
717
752
  for (const c of conditions) {
718
753
  const schemaProp = this._entitySchema.properties?.find(p => p.property === c.property);
719
754
  if (Is.undefined(schemaProp)) {
720
- throw new GeneralError(this.CLASS_NAME, "propertyNotFound", {
755
+ throw new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, "propertyNotFound", {
721
756
  property: c.property
722
757
  });
723
758
  }
@@ -734,5 +769,4 @@ class DynamoDbEntityStorageConnector {
734
769
  return { conditionExpression, attributeNames, attributeValues };
735
770
  }
736
771
  }
737
-
738
- export { DynamoDbEntityStorageConnector };
772
+ //# sourceMappingURL=dynamoDbEntityStorageConnector.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dynamoDbEntityStorageConnector.js","sourceRoot":"","sources":["../../src/dynamoDbEntityStorageConnector.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright 2024 IOTA Stiftung.\n// SPDX-License-Identifier: Apache-2.0.\nimport {\n\ttype AttributeValue,\n\ttype CreateTableCommandInput,\n\tDynamoDB,\n\ttype GlobalSecondaryIndex,\n\tQueryCommand,\n\twaitUntilTableExists\n} from \"@aws-sdk/client-dynamodb\";\nimport {\n\tDeleteCommand,\n\tDynamoDBDocumentClient,\n\tGetCommand,\n\tPutCommand\n} from \"@aws-sdk/lib-dynamodb\";\nimport { type NativeAttributeValue, unmarshall } from \"@aws-sdk/util-dynamodb\";\nimport { ContextIdHelper, ContextIdStore } from \"@twin.org/context\";\nimport {\n\tBaseError,\n\tCoerce,\n\tComponentFactory,\n\tConverter,\n\tGeneralError,\n\tGuards,\n\tIs,\n\tObjectHelper\n} from \"@twin.org/core\";\nimport {\n\tComparisonOperator,\n\ttype EntityCondition,\n\tEntitySchemaFactory,\n\tEntitySchemaHelper,\n\ttype EntitySchemaPropertyType,\n\ttype IComparator,\n\ttype IEntitySchema,\n\ttype IEntitySchemaProperty,\n\tLogicalOperator,\n\tSortDirection\n} from \"@twin.org/entity\";\nimport type { IEntityStorageConnector } from \"@twin.org/entity-storage-models\";\nimport type { ILoggingComponent } from \"@twin.org/logging-models\";\nimport { nameof } from \"@twin.org/nameof\";\nimport type { IDynamoDbEntityStorageConnectorConfig } from \"./models/IDynamoDbEntityStorageConnectorConfig.js\";\nimport type { IDynamoDbEntityStorageConnectorConstructorOptions } from \"./models/IDynamoDbEntityStorageConnectorConstructorOptions.js\";\n\n/**\n * Class for performing entity storage operations using Dynamo DB.\n */\nexport class DynamoDbEntityStorageConnector<T = unknown> implements IEntityStorageConnector<T> {\n\t/**\n\t * Runtime name for the class.\n\t */\n\tpublic static readonly CLASS_NAME: string = nameof<DynamoDbEntityStorageConnector>();\n\n\t/**\n\t * Limit the number of entities when finding.\n\t * @internal\n\t */\n\tprivate static readonly _DEFAULT_LIMIT: number = 40;\n\n\t/**\n\t * Partition id field name.\n\t * @internal\n\t */\n\tprivate static readonly _PARTITION_KEY: string = \"partitionId\";\n\n\t/**\n\t * Partition id field value.\n\t * @internal\n\t */\n\tprivate static readonly _PARTITION_KEY_VALUE: string = \"root\";\n\n\t/**\n\t * The schema for the entity.\n\t * @internal\n\t */\n\tprivate readonly _entitySchema: IEntitySchema<T>;\n\n\t/**\n\t * The keys to use from the context ids to create partitions.\n\t * @internal\n\t */\n\tprivate readonly _partitionContextIds?: string[];\n\n\t/**\n\t * The primary key.\n\t * @internal\n\t */\n\tprivate readonly _primaryKey: IEntitySchemaProperty<T>;\n\n\t/**\n\t * The configuration for the connector.\n\t * @internal\n\t */\n\tprivate readonly _config: IDynamoDbEntityStorageConnectorConfig;\n\n\t/**\n\t * Create a new instance of DynamoDbEntityStorageConnector.\n\t * @param options The options for the connector.\n\t */\n\tconstructor(options: IDynamoDbEntityStorageConnectorConstructorOptions) {\n\t\tGuards.object(DynamoDbEntityStorageConnector.CLASS_NAME, nameof(options), options);\n\t\tGuards.stringValue(\n\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\tnameof(options.entitySchema),\n\t\t\toptions.entitySchema\n\t\t);\n\t\tGuards.object<IDynamoDbEntityStorageConnectorConfig>(\n\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\tnameof(options.config),\n\t\t\toptions.config\n\t\t);\n\n\t\toptions.config.authMode ??= \"credentials\";\n\n\t\tif (options.config.authMode === \"credentials\") {\n\t\t\tGuards.stringValue(\n\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\tnameof(options.config.accessKeyId),\n\t\t\t\toptions.config.accessKeyId\n\t\t\t);\n\t\t\tGuards.stringValue(\n\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\tnameof(options.config.secretAccessKey),\n\t\t\t\toptions.config.secretAccessKey\n\t\t\t);\n\t\t}\n\t\tGuards.stringValue(\n\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\tnameof(options.config.region),\n\t\t\toptions.config.region\n\t\t);\n\t\tGuards.stringValue(\n\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\tnameof(options.config.tableName),\n\t\t\toptions.config.tableName\n\t\t);\n\n\t\tthis._entitySchema = EntitySchemaFactory.get(options.entitySchema);\n\t\tthis._partitionContextIds = options.partitionContextIds;\n\n\t\tthis._primaryKey = EntitySchemaHelper.getPrimaryKey<T>(this._entitySchema);\n\n\t\tthis._config = options.config;\n\t\tthis._config.endpoint = Is.stringValue(this._config.endpoint)\n\t\t\t? this._config.endpoint\n\t\t\t: undefined;\n\t}\n\n\t/**\n\t * Returns the class name of the component.\n\t * @returns The class name of the component.\n\t */\n\tpublic className(): string {\n\t\treturn DynamoDbEntityStorageConnector.CLASS_NAME;\n\t}\n\n\t/**\n\t * Get the schema for the entities.\n\t * @returns The schema for the entities.\n\t */\n\tpublic getSchema(): IEntitySchema {\n\t\treturn this._entitySchema as IEntitySchema;\n\t}\n\n\t/**\n\t * Bootstrap the component by creating and initializing any resources it needs.\n\t * @param nodeLoggingComponentType The node logging component type.\n\t * @returns True if the bootstrapping process was successful.\n\t */\n\tpublic async bootstrap(nodeLoggingComponentType?: string): Promise<boolean> {\n\t\tconst nodeLogging = ComponentFactory.getIfExists<ILoggingComponent>(nodeLoggingComponentType);\n\n\t\tif (!(await this.tableExists(this._config.tableName))) {\n\t\t\tawait nodeLogging?.log({\n\t\t\t\tlevel: \"info\",\n\t\t\t\tsource: DynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\tts: Date.now(),\n\t\t\t\tmessage: \"tableCreating\",\n\t\t\t\tdata: {\n\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t}\n\t\t\t});\n\n\t\t\ttry {\n\t\t\t\tconst dbConnection = this.createConnection();\n\n\t\t\t\tconst tableParams: CreateTableCommandInput = {\n\t\t\t\t\tAttributeDefinitions: [],\n\t\t\t\t\tKeySchema: [],\n\t\t\t\t\tProvisionedThroughput: {\n\t\t\t\t\t\tReadCapacityUnits: 1,\n\t\t\t\t\t\tWriteCapacityUnits: 1\n\t\t\t\t\t},\n\t\t\t\t\tTableName: this._config.tableName\n\t\t\t\t};\n\n\t\t\t\t// We always add a partition key to the table as a non optional hash key\n\t\t\t\t// is always required when querying using sort parameters\n\t\t\t\ttableParams.AttributeDefinitions?.push({\n\t\t\t\t\tAttributeName: DynamoDbEntityStorageConnector._PARTITION_KEY,\n\t\t\t\t\tAttributeType: \"S\"\n\t\t\t\t});\n\t\t\t\ttableParams.KeySchema?.push({\n\t\t\t\t\tAttributeName: DynamoDbEntityStorageConnector._PARTITION_KEY,\n\t\t\t\t\tKeyType: \"HASH\"\n\t\t\t\t});\n\n\t\t\t\tconst gsi: GlobalSecondaryIndex[] = [];\n\n\t\t\t\tif (Is.arrayValue(this._entitySchema.properties)) {\n\t\t\t\t\tfor (const prop of this._entitySchema.properties) {\n\t\t\t\t\t\tif (prop.isPrimary) {\n\t\t\t\t\t\t\ttableParams.AttributeDefinitions?.push({\n\t\t\t\t\t\t\t\tAttributeName: prop.property as string,\n\t\t\t\t\t\t\t\tAttributeType: prop.type === \"integer\" || prop.type === \"number\" ? \"N\" : \"S\"\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\ttableParams.KeySchema?.push({\n\t\t\t\t\t\t\t\tAttributeName: prop.property as string,\n\t\t\t\t\t\t\t\tKeyType: \"RANGE\"\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t} else if (Is.stringValue(prop.sortDirection) || prop.isSecondary) {\n\t\t\t\t\t\t\t// You can only query and sort items if you have a secondary index\n\t\t\t\t\t\t\t// defined for the property\n\t\t\t\t\t\t\ttableParams.AttributeDefinitions?.push({\n\t\t\t\t\t\t\t\tAttributeName: prop.property as string,\n\t\t\t\t\t\t\t\tAttributeType: prop.type === \"integer\" || prop.type === \"number\" ? \"N\" : \"S\"\n\t\t\t\t\t\t\t});\n\n\t\t\t\t\t\t\tgsi.push({\n\t\t\t\t\t\t\t\tIndexName: `${prop.property as string}Index`,\n\t\t\t\t\t\t\t\tKeySchema: [\n\t\t\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t\t\tAttributeName: DynamoDbEntityStorageConnector._PARTITION_KEY,\n\t\t\t\t\t\t\t\t\t\tKeyType: \"HASH\"\n\t\t\t\t\t\t\t\t\t},\n\t\t\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t\t\tAttributeName: prop.property as string,\n\t\t\t\t\t\t\t\t\t\tKeyType: \"RANGE\"\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t],\n\t\t\t\t\t\t\t\tProjection: {\n\t\t\t\t\t\t\t\t\tProjectionType: \"ALL\"\n\t\t\t\t\t\t\t\t},\n\t\t\t\t\t\t\t\tProvisionedThroughput: {\n\t\t\t\t\t\t\t\t\tReadCapacityUnits: 1,\n\t\t\t\t\t\t\t\t\tWriteCapacityUnits: 1\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (gsi.length > 0) {\n\t\t\t\t\ttableParams.GlobalSecondaryIndexes = gsi;\n\t\t\t\t}\n\n\t\t\t\tawait dbConnection.createTable(tableParams);\n\n\t\t\t\t// Wait for table to exist\n\t\t\t\tawait waitUntilTableExists(\n\t\t\t\t\t{\n\t\t\t\t\t\tclient: dbConnection,\n\t\t\t\t\t\tmaxWaitTime: 60000\n\t\t\t\t\t},\n\t\t\t\t\t{\n\t\t\t\t\t\tTableName: this._config.tableName\n\t\t\t\t\t}\n\t\t\t\t);\n\n\t\t\t\tawait nodeLogging?.log({\n\t\t\t\t\tlevel: \"info\",\n\t\t\t\t\tsource: DynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\tts: Date.now(),\n\t\t\t\t\tmessage: \"tableCreated\",\n\t\t\t\t\tdata: {\n\t\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t} catch (err) {\n\t\t\t\tif (BaseError.isErrorCode(err, \"ResourceInUseException\")) {\n\t\t\t\t\tawait nodeLogging?.log({\n\t\t\t\t\t\tlevel: \"info\",\n\t\t\t\t\t\tsource: DynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\t\tts: Date.now(),\n\t\t\t\t\t\tmessage: \"tableExists\",\n\t\t\t\t\t\tdata: {\n\t\t\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t} else {\n\t\t\t\t\tawait nodeLogging?.log({\n\t\t\t\t\t\tlevel: \"error\",\n\t\t\t\t\t\tsource: DynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\t\tts: Date.now(),\n\t\t\t\t\t\tmessage: \"tableCreateFailed\",\n\t\t\t\t\t\terror: BaseError.fromError(err),\n\t\t\t\t\t\tdata: {\n\t\t\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t\treturn false;\n\t\t\t}\n\t\t} else {\n\t\t\tawait nodeLogging?.log({\n\t\t\t\tlevel: \"info\",\n\t\t\t\tsource: DynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\tts: Date.now(),\n\t\t\t\tmessage: \"tableExists\",\n\t\t\t\tdata: {\n\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get an entity.\n\t * @param id The id of the entity to get, or the index value if secondaryIndex is set.\n\t * @param secondaryIndex Get the item using a secondary index.\n\t * @param conditions The optional conditions to match for the entities.\n\t * @returns The object if it can be found or undefined.\n\t */\n\tpublic async get(\n\t\tid: string,\n\t\tsecondaryIndex?: keyof T,\n\t\tconditions?: { property: keyof T; value: unknown }[]\n\t): Promise<T | undefined> {\n\t\tGuards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, nameof(id), id);\n\n\t\tconst contextIds = await ContextIdStore.getContextIds();\n\t\tconst partitionKey = ContextIdHelper.combinedContextKey(contextIds, this._partitionContextIds);\n\n\t\ttry {\n\t\t\tconst docClient = this.createDocClient();\n\n\t\t\tif (Is.empty(secondaryIndex) && Is.empty(conditions)) {\n\t\t\t\tconst getCommand = new GetCommand({\n\t\t\t\t\tTableName: this._config.tableName,\n\t\t\t\t\tKey: {\n\t\t\t\t\t\t[DynamoDbEntityStorageConnector._PARTITION_KEY]:\n\t\t\t\t\t\t\tpartitionKey ?? DynamoDbEntityStorageConnector._PARTITION_KEY_VALUE,\n\t\t\t\t\t\t[this._primaryKey.property]: id\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\tconst response = await docClient.send(getCommand);\n\n\t\t\t\tdelete response.Item?.[DynamoDbEntityStorageConnector._PARTITION_KEY];\n\t\t\t\treturn response.Item as T;\n\t\t\t}\n\n\t\t\tconst finalConditions: EntityCondition<T> = {\n\t\t\t\tconditions: []\n\t\t\t};\n\n\t\t\tif (Is.stringValue(secondaryIndex)) {\n\t\t\t\tfinalConditions.conditions.push({\n\t\t\t\t\tproperty: secondaryIndex,\n\t\t\t\t\tcomparison: ComparisonOperator.Equals,\n\t\t\t\t\tvalue: id\n\t\t\t\t});\n\t\t\t}\n\t\t\tif (Is.arrayValue(conditions)) {\n\t\t\t\tfor (const c of conditions) {\n\t\t\t\t\tfinalConditions.conditions.push({\n\t\t\t\t\t\tproperty: c.property as string,\n\t\t\t\t\t\tcomparison: ComparisonOperator.Equals,\n\t\t\t\t\t\tvalue: c.value\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tconst queryResult = await this.internalQuery(\n\t\t\t\tfinalConditions,\n\t\t\t\tundefined,\n\t\t\t\tundefined,\n\t\t\t\tundefined,\n\t\t\t\t1,\n\t\t\t\tsecondaryIndex as string,\n\t\t\t\tpartitionKey\n\t\t\t);\n\n\t\t\treturn queryResult.entities[0] as T;\n\t\t} catch (err) {\n\t\t\tif (BaseError.isErrorCode(err, \"ResourceNotFoundException\")) {\n\t\t\t\tthrow new GeneralError(\n\t\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\t\"tableDoesNotExist\",\n\t\t\t\t\t{\n\t\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t\t},\n\t\t\t\t\terr\n\t\t\t\t);\n\t\t\t}\n\t\t\tthrow new GeneralError(\n\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\"getFailed\",\n\t\t\t\t{\n\t\t\t\t\tid\n\t\t\t\t},\n\t\t\t\terr\n\t\t\t);\n\t\t}\n\t}\n\n\t/**\n\t * Set an entity.\n\t * @param entity The entity to set.\n\t * @param conditions The optional conditions to match for the entities.\n\t * @returns The id of the entity.\n\t */\n\tpublic async set(entity: T, conditions?: { property: keyof T; value: unknown }[]): Promise<void> {\n\t\tGuards.object<T>(DynamoDbEntityStorageConnector.CLASS_NAME, nameof(entity), entity);\n\n\t\tconst contextIds = await ContextIdStore.getContextIds();\n\t\tconst partitionKey = ContextIdHelper.combinedContextKey(contextIds, this._partitionContextIds);\n\n\t\tEntitySchemaHelper.validateEntity(entity, this.getSchema());\n\n\t\tconst id = entity[this._primaryKey.property];\n\n\t\ttry {\n\t\t\tconst docClient = this.createDocClient();\n\n\t\t\tconst { conditionExpression, attributeNames, attributeValues } =\n\t\t\t\tthis.buildConditionExpression(conditions);\n\n\t\t\tconst putCommand = new PutCommand({\n\t\t\t\tTableName: this._config.tableName,\n\t\t\t\tItem: {\n\t\t\t\t\t[DynamoDbEntityStorageConnector._PARTITION_KEY]:\n\t\t\t\t\t\tpartitionKey ?? DynamoDbEntityStorageConnector._PARTITION_KEY_VALUE,\n\t\t\t\t\t...entity\n\t\t\t\t} as { [id: string]: unknown },\n\t\t\t\t// Only set the condition expression if we have conditions to match\n\t\t\t\t// and the primary key exists, otherwise we are creating a new object\n\t\t\t\tConditionExpression: Is.stringValue(conditionExpression)\n\t\t\t\t\t? `(attribute_exists(${this._primaryKey.property as string}) AND ${conditionExpression}) OR attribute_not_exists(${this._primaryKey.property as string})`\n\t\t\t\t\t: undefined,\n\t\t\t\tExpressionAttributeNames: attributeNames,\n\t\t\t\tExpressionAttributeValues: attributeValues\n\t\t\t});\n\n\t\t\tawait docClient.send(putCommand);\n\t\t} catch (err) {\n\t\t\tif (BaseError.isErrorName(err, \"ConditionalCheckFailedException\")) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tif (BaseError.isErrorCode(err, \"ResourceNotFoundException\")) {\n\t\t\t\tthrow new GeneralError(\n\t\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\t\"tableDoesNotExist\",\n\t\t\t\t\t{\n\t\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t\t},\n\t\t\t\t\terr\n\t\t\t\t);\n\t\t\t}\n\n\t\t\tthrow new GeneralError(\n\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\"setFailed\",\n\t\t\t\t{\n\t\t\t\t\tid\n\t\t\t\t},\n\t\t\t\terr\n\t\t\t);\n\t\t}\n\t}\n\n\t/**\n\t * Remove the entity.\n\t * @param id The id of the entity to remove.\n\t * @param conditions The optional conditions to match for the entities.\n\t * @returns Nothing.\n\t */\n\tpublic async remove(\n\t\tid: string,\n\t\tconditions?: { property: keyof T; value: unknown }[]\n\t): Promise<void> {\n\t\tGuards.stringValue(DynamoDbEntityStorageConnector.CLASS_NAME, nameof(id), id);\n\n\t\tconst contextIds = await ContextIdStore.getContextIds();\n\t\tconst partitionKey = ContextIdHelper.combinedContextKey(contextIds, this._partitionContextIds);\n\n\t\ttry {\n\t\t\tconst docClient = this.createDocClient();\n\n\t\t\tconst { conditionExpression, attributeNames, attributeValues } =\n\t\t\t\tthis.buildConditionExpression(conditions);\n\n\t\t\tconst deleteCommand = new DeleteCommand({\n\t\t\t\tTableName: this._config.tableName,\n\t\t\t\tKey: {\n\t\t\t\t\t[DynamoDbEntityStorageConnector._PARTITION_KEY]:\n\t\t\t\t\t\tpartitionKey ?? DynamoDbEntityStorageConnector._PARTITION_KEY_VALUE,\n\t\t\t\t\t[this._primaryKey.property as string]: id\n\t\t\t\t},\n\t\t\t\tConditionExpression: conditionExpression,\n\t\t\t\tExpressionAttributeNames: attributeNames,\n\t\t\t\tExpressionAttributeValues: attributeValues\n\t\t\t});\n\n\t\t\tawait docClient.send(deleteCommand);\n\t\t} catch (err) {\n\t\t\tif (BaseError.isErrorName(err, \"ConditionalCheckFailedException\")) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tif (BaseError.isErrorCode(err, \"ResourceNotFoundException\")) {\n\t\t\t\tthrow new GeneralError(\n\t\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\t\"tableDoesNotExist\",\n\t\t\t\t\t{\n\t\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t\t},\n\t\t\t\t\terr\n\t\t\t\t);\n\t\t\t}\n\n\t\t\tthrow new GeneralError(\n\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\"removeFailed\",\n\t\t\t\t{\n\t\t\t\t\tid\n\t\t\t\t},\n\t\t\t\terr\n\t\t\t);\n\t\t}\n\t}\n\n\t/**\n\t * Find all the entities which match the conditions.\n\t * @param conditions The conditions to match for the entities.\n\t * @param sortProperties The optional sort order.\n\t * @param properties The optional properties to return, defaults to all.\n\t * @param cursor The cursor to request the next chunk of entities.\n\t * @param limit The suggested number of entities to return in each chunk, in some scenarios can return a different amount.\n\t * @returns All the entities for the storage matching the conditions,\n\t * and a cursor which can be used to request more entities.\n\t */\n\tpublic async query(\n\t\tconditions?: EntityCondition<T>,\n\t\tsortProperties?: {\n\t\t\tproperty: keyof T;\n\t\t\tsortDirection: SortDirection;\n\t\t}[],\n\t\tproperties?: (keyof T)[],\n\t\tcursor?: string,\n\t\tlimit?: number\n\t): Promise<{\n\t\t/**\n\t\t * The entities, which can be partial if a limited keys list was provided.\n\t\t */\n\t\tentities: Partial<T>[];\n\t\t/**\n\t\t * An optional cursor, when defined can be used to call find to get more entities.\n\t\t */\n\t\tcursor?: string;\n\t}> {\n\t\tconst contextIds = await ContextIdStore.getContextIds();\n\t\tconst partitionKey = ContextIdHelper.combinedContextKey(contextIds, this._partitionContextIds);\n\n\t\treturn this.internalQuery(\n\t\t\tconditions,\n\t\t\tsortProperties,\n\t\t\tproperties,\n\t\t\tcursor,\n\t\t\tlimit,\n\t\t\tundefined,\n\t\t\tpartitionKey\n\t\t);\n\t}\n\n\t/**\n\t * Delete the table.\n\t * @returns Nothing.\n\t */\n\tpublic async tableDelete(): Promise<void> {\n\t\ttry {\n\t\t\tconst dbConnection = this.createConnection();\n\n\t\t\tawait dbConnection.deleteTable({ TableName: this._config.tableName });\n\t\t} catch {}\n\t}\n\n\t/**\n\t * Create the parameters for a query.\n\t * @param objectPath The path for the nested object.\n\t * @param condition The conditions to create the query from.\n\t * @param attributeNames The attribute names to use in the query.\n\t * @param attributeValues The attribute values to use in the query.\n\t * @returns The condition clause.\n\t * @internal\n\t */\n\tprivate buildQueryParameters(\n\t\tobjectPath: string,\n\t\tcondition: EntityCondition<T> | undefined,\n\t\tattributeNames: { [id: string]: string },\n\t\tattributeValues: { [id: string]: AttributeValue },\n\t\tsecondaryIndex?: string\n\t): {\n\t\tkeyCondition: string;\n\t\tfilterCondition: string;\n\t} {\n\t\t// If no conditions are defined then return empty string\n\t\tif (Is.undefined(condition)) {\n\t\t\treturn {\n\t\t\t\tkeyCondition: \"\",\n\t\t\t\tfilterCondition: \"\"\n\t\t\t};\n\t\t}\n\n\t\tif (\"conditions\" in condition) {\n\t\t\tif (condition.conditions.length === 0) {\n\t\t\t\treturn {\n\t\t\t\t\tkeyCondition: \"\",\n\t\t\t\t\tfilterCondition: \"\"\n\t\t\t\t};\n\t\t\t}\n\t\t\t// It's a group of comparisons, so check the individual items and combine with the logical operator\n\t\t\tconst joinConditions: {\n\t\t\t\tkeyCondition: string;\n\t\t\t\tfilterCondition: string;\n\t\t\t}[] = condition.conditions.map(c =>\n\t\t\t\tthis.buildQueryParameters(objectPath, c, attributeNames, attributeValues, secondaryIndex)\n\t\t\t);\n\n\t\t\tconst logicalOperator = this.mapConditionalOperator(condition.logicalOperator);\n\t\t\tconst keyCondition = joinConditions\n\t\t\t\t.filter(j => j.keyCondition.length > 0)\n\t\t\t\t.map(j => j.keyCondition)\n\t\t\t\t.join(` ${logicalOperator} `);\n\t\t\tconst filterCondition = joinConditions\n\t\t\t\t.filter(j => j.filterCondition.length > 0)\n\t\t\t\t.map(j => j.filterCondition)\n\t\t\t\t.join(` ${logicalOperator} `);\n\n\t\t\treturn {\n\t\t\t\tkeyCondition: Is.stringValue(keyCondition) ? ` (${keyCondition}) ` : \"\",\n\t\t\t\tfilterCondition: Is.stringValue(filterCondition) ? ` (${filterCondition}) ` : \"\"\n\t\t\t};\n\t\t}\n\n\t\tconst schemaProp = this._entitySchema.properties?.find(p => p.property === condition.property);\n\n\t\t// It's a single value so just create the property comparison for the condition\n\t\tconst comparison = this.mapComparisonOperator(\n\t\t\tobjectPath,\n\t\t\tcondition,\n\t\t\tschemaProp?.type,\n\t\t\tattributeNames,\n\t\t\tattributeValues\n\t\t);\n\n\t\tconst isKey =\n\t\t\tschemaProp?.isPrimary ?? (schemaProp?.isSecondary && schemaProp?.property === secondaryIndex);\n\t\treturn {\n\t\t\tkeyCondition: isKey ? comparison : \"\",\n\t\t\tfilterCondition: !isKey ? comparison : \"\"\n\t\t};\n\t}\n\n\t/**\n\t * Map the framework comparison operators to those in DynamoDB.\n\t * @param objectPath The prefix to use for the condition.\n\t * @param comparator The operator to map.\n\t * @param type The type of the property.\n\t * @param attributeNames The attribute names to use in the query.\n\t * @param attributeValues The attribute values to use in the query.\n\t * @returns The comparison expression.\n\t * @throws GeneralError if the comparison operator is not supported.\n\t * @internal\n\t */\n\tprivate mapComparisonOperator(\n\t\tobjectPath: string,\n\t\tcomparator: IComparator,\n\t\ttype: EntitySchemaPropertyType | undefined,\n\t\tattributeNames: { [id: string]: string },\n\t\tattributeValues: { [id: string]: AttributeValue }\n\t): string {\n\t\tlet prop = objectPath;\n\t\tif (prop.length > 0) {\n\t\t\tprop += \".\";\n\t\t}\n\t\tprop += comparator.property;\n\n\t\tlet attributeName = this.populateAttributeNames(prop, attributeNames);\n\n\t\tif (Is.empty(comparator.value)) {\n\t\t\tif (comparator.comparison === ComparisonOperator.Equals) {\n\t\t\t\treturn `attribute_not_exists(${attributeName})`;\n\t\t\t} else if (comparator.comparison === ComparisonOperator.NotEquals) {\n\t\t\t\treturn `attribute_exists(${attributeName})`;\n\t\t\t}\n\t\t}\n\n\t\tlet propName = `:${attributeName.replace(/\\./g, \"\").replace(/#/g, \"\")}`;\n\n\t\tif (Is.array(comparator.value)) {\n\t\t\tconst dbValues = comparator.value.map(v => this.propertyToDbValue(v, type));\n\t\t\tconst arrAttributeNames = [];\n\t\t\tfor (let i = 0; i < dbValues.length; i++) {\n\t\t\t\tconst arrAttributeName = `${propName}${i}`;\n\t\t\t\tattributeValues[arrAttributeName] = dbValues[i];\n\t\t\t\tarrAttributeNames.push(arrAttributeName);\n\t\t\t}\n\t\t\tpropName = attributeName;\n\t\t\tattributeName = `(${arrAttributeNames.join(\", \")})`;\n\t\t} else {\n\t\t\tattributeValues[propName] = this.propertyToDbValue(comparator.value, type);\n\t\t}\n\n\t\tif (comparator.comparison === ComparisonOperator.Equals) {\n\t\t\treturn `${attributeName} = ${propName}`;\n\t\t} else if (comparator.comparison === ComparisonOperator.NotEquals) {\n\t\t\treturn `${attributeName} <> ${propName}`;\n\t\t} else if (comparator.comparison === ComparisonOperator.GreaterThan) {\n\t\t\treturn `${attributeName} > ${propName}`;\n\t\t} else if (comparator.comparison === ComparisonOperator.LessThan) {\n\t\t\treturn `${attributeName} < ${propName}`;\n\t\t} else if (comparator.comparison === ComparisonOperator.GreaterThanOrEqual) {\n\t\t\treturn `${attributeName} >= ${propName}`;\n\t\t} else if (comparator.comparison === ComparisonOperator.LessThanOrEqual) {\n\t\t\treturn `${attributeName} <= ${propName}`;\n\t\t} else if (comparator.comparison === ComparisonOperator.Includes) {\n\t\t\treturn `contains(${attributeName}, ${propName})`;\n\t\t} else if (comparator.comparison === ComparisonOperator.NotIncludes) {\n\t\t\treturn `notContains(${attributeName}, ${propName})`;\n\t\t} else if (comparator.comparison === ComparisonOperator.In) {\n\t\t\treturn `${propName} IN ${attributeName}`;\n\t\t}\n\n\t\tthrow new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, \"comparisonNotSupported\", {\n\t\t\tcomparison: comparator.comparison\n\t\t});\n\t}\n\n\t/**\n\t * Create a unique name for the attribute.\n\t * @param name The name to create a unique name for.\n\t * @param attributeNames The attribute names to use in the query.\n\t * @returns The unique name.\n\t * @internal\n\t */\n\tprivate populateAttributeNames(name: string, attributeNames: { [id: string]: string }): string {\n\t\tconst parts = name.split(\".\");\n\t\tconst attributeNameParts: string[] = [];\n\n\t\tfor (const part of parts) {\n\t\t\tconst hashPart = `#${part}`;\n\t\t\tif (Is.empty(attributeNames[hashPart])) {\n\t\t\t\tattributeNames[hashPart] = part;\n\t\t\t}\n\t\t\tattributeNameParts.push(hashPart);\n\t\t}\n\n\t\treturn attributeNameParts.join(\".\");\n\t}\n\n\t/**\n\t * Map the framework conditional operators to those in DynamoDB.\n\t * @param operator The operator to map.\n\t * @returns The conditional operator.\n\t * @throws GeneralError if the conditional operator is not supported.\n\t * @internal\n\t */\n\tprivate mapConditionalOperator(operator?: LogicalOperator): string {\n\t\tif ((operator ?? LogicalOperator.And) === LogicalOperator.And) {\n\t\t\treturn \"AND\";\n\t\t} else if (operator === LogicalOperator.Or) {\n\t\t\treturn \"OR\";\n\t\t}\n\n\t\tthrow new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, \"conditionalNotSupported\", {\n\t\t\toperator\n\t\t});\n\t}\n\n\t/**\n\t * Format a value to insert into DB.\n\t * @param value The value to format.\n\t * @param type The type for the property.\n\t * @returns The value after conversion.\n\t * @internal\n\t */\n\tprivate propertyToDbValue(value: unknown, type?: EntitySchemaPropertyType): AttributeValue {\n\t\tif (Is.object(value)) {\n\t\t\tconst map: { [id: string]: AttributeValue } = {};\n\t\t\tfor (const key in value) {\n\t\t\t\tmap[key] = this.propertyToDbValue(value[key]);\n\t\t\t}\n\t\t\treturn {\n\t\t\t\tM: map\n\t\t\t};\n\t\t}\n\n\t\tif (type === \"integer\" || type === \"number\") {\n\t\t\treturn { N: Coerce.string(value) ?? \"\" };\n\t\t} else if (type === \"boolean\") {\n\t\t\treturn { BOOL: Coerce.boolean(value) ?? false };\n\t\t}\n\n\t\treturn { S: Coerce.string(value) ?? \"\" };\n\t}\n\n\t/**\n\t * Create a doc client connection.\n\t * @returns The dynamo db document client.\n\t * @internal\n\t */\n\tprivate createDocClient(): DynamoDBDocumentClient {\n\t\treturn DynamoDBDocumentClient.from(\n\t\t\tnew DynamoDB({\n\t\t\t\tapiVersion: \"2012-10-08\",\n\t\t\t\t...this.createConnectionConfig()\n\t\t\t}),\n\t\t\t{\n\t\t\t\tmarshallOptions: {\n\t\t\t\t\tremoveUndefinedValues: true\n\t\t\t\t}\n\t\t\t}\n\t\t);\n\t}\n\n\t/**\n\t * Create a new DB connection.\n\t * @returns The Dynamo DB connection.\n\t * @internal\n\t */\n\tprivate createConnection(): DynamoDB {\n\t\treturn new DynamoDB(this.createConnectionConfig());\n\t}\n\n\t/**\n\t * Create a new DB connection configuration.\n\t * @returns The Dynamo DB connection configuration.\n\t * @internal\n\t */\n\tprivate createConnectionConfig(): {\n\t\tcredentials?: {\n\t\t\taccessKeyId: string;\n\t\t\tsecretAccessKey: string;\n\t\t};\n\t\tendpoint?: string;\n\t\tregion: string;\n\t} {\n\t\tif (\n\t\t\tIs.stringValue(this._config.secretAccessKey) &&\n\t\t\tIs.stringValue(this._config.accessKeyId) &&\n\t\t\tthis._config.authMode === \"credentials\"\n\t\t) {\n\t\t\treturn {\n\t\t\t\tcredentials: {\n\t\t\t\t\taccessKeyId: this._config.accessKeyId,\n\t\t\t\t\tsecretAccessKey: this._config.secretAccessKey\n\t\t\t\t},\n\t\t\t\tendpoint: this._config.endpoint,\n\t\t\t\tregion: this._config.region\n\t\t\t};\n\t\t}\n\n\t\treturn {\n\t\t\tendpoint: this._config.endpoint,\n\t\t\tregion: this._config.region\n\t\t};\n\t}\n\n\t/**\n\t * Check if the table exists.\n\t * @param tableName The table to check.\n\t * @returns True if the table exists.\n\t * @internal\n\t */\n\tprivate async tableExists(tableName: string): Promise<boolean> {\n\t\ttry {\n\t\t\tconst dbConnection = this.createConnection();\n\n\t\t\tawait dbConnection.describeTable({ TableName: tableName });\n\n\t\t\treturn true;\n\t\t} catch {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\t/**\n\t * Find all the entities which match the conditions.\n\t * @param conditions The conditions to match for the entities.\n\t * @param sortProperties The optional sort order.\n\t * @param properties The optional properties to return, defaults to all.\n\t * @param cursor The cursor to request the next chunk of entities.\n\t * @param limit The suggested number of entities to return in each chunk, in some scenarios can return a different amount.\n\t * @param secondaryIndex The secondary index to use for the query.\n\t * @param partitionKey The partition key to use for the query.\n\t * @returns All the entities for the storage matching the conditions,\n\t * and a cursor which can be used to request more entities.\n\t * @internal\n\t */\n\tprivate async internalQuery(\n\t\tconditions?: EntityCondition<T>,\n\t\tsortProperties?: {\n\t\t\tproperty: keyof T;\n\t\t\tsortDirection: SortDirection;\n\t\t}[],\n\t\tproperties?: (keyof T)[],\n\t\tcursor?: string,\n\t\tlimit?: number,\n\t\tsecondaryIndex?: string,\n\t\tpartitionKey?: string\n\t): Promise<{\n\t\t/**\n\t\t * The entities, which can be partial if a limited keys list was provided.\n\t\t */\n\t\tentities: Partial<T>[];\n\t\t/**\n\t\t * An optional cursor, when defined can be used to call find to get more entities.\n\t\t */\n\t\tcursor?: string;\n\t}> {\n\t\ttry {\n\t\t\tconst returnSize = limit ?? DynamoDbEntityStorageConnector._DEFAULT_LIMIT;\n\n\t\t\tlet indexName: string | undefined = Is.stringValue(secondaryIndex)\n\t\t\t\t? `${secondaryIndex}Index`\n\t\t\t\t: undefined;\n\n\t\t\t// If we have a sortable property defined in the descriptor then we must use\n\t\t\t// the secondary index for the query\n\t\t\tlet scanAscending = true;\n\t\t\tif (Is.arrayValue(sortProperties)) {\n\t\t\t\tif (sortProperties.length > 1) {\n\t\t\t\t\tthrow new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, \"sortSingle\");\n\t\t\t\t}\n\n\t\t\t\tfor (const sortProperty of sortProperties) {\n\t\t\t\t\tconst propertySchema = this._entitySchema.properties?.find(\n\t\t\t\t\t\te => e.property === sortProperty.property\n\t\t\t\t\t);\n\t\t\t\t\tif (\n\t\t\t\t\t\tIs.undefined(propertySchema) ||\n\t\t\t\t\t\t(!propertySchema.isPrimary &&\n\t\t\t\t\t\t\t!propertySchema.isSecondary &&\n\t\t\t\t\t\t\tIs.empty(propertySchema.sortDirection))\n\t\t\t\t\t) {\n\t\t\t\t\t\tthrow new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, \"sortNotIndexed\", {\n\t\t\t\t\t\t\tproperty: sortProperty.property\n\t\t\t\t\t\t});\n\t\t\t\t\t}\n\n\t\t\t\t\tindexName = propertySchema.isPrimary\n\t\t\t\t\t\t? undefined\n\t\t\t\t\t\t: `${sortProperty.property as string}Index`;\n\t\t\t\t\tscanAscending = sortProperty.sortDirection === SortDirection.Ascending;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tconst attributeNames: { [id: string]: string } = { \"#partitionId\": \"partitionId\" };\n\t\t\tconst attributeValues: { [id: string]: AttributeValue } = {\n\t\t\t\t[`:${DynamoDbEntityStorageConnector._PARTITION_KEY}`]: {\n\t\t\t\t\tS: partitionKey ?? DynamoDbEntityStorageConnector._PARTITION_KEY_VALUE\n\t\t\t\t}\n\t\t\t};\n\n\t\t\tconst expressions = this.buildQueryParameters(\n\t\t\t\t\"\",\n\t\t\t\tconditions,\n\t\t\t\tattributeNames,\n\t\t\t\tattributeValues,\n\t\t\t\tsecondaryIndex\n\t\t\t);\n\n\t\t\tlet keyExpression = \"#partitionId = :partitionId\";\n\t\t\tif (expressions.keyCondition.length > 0) {\n\t\t\t\tkeyExpression += ` AND ${expressions.keyCondition}`;\n\t\t\t}\n\n\t\t\tconst query = new QueryCommand({\n\t\t\t\tTableName: this._config.tableName,\n\t\t\t\tIndexName: indexName,\n\t\t\t\tKeyConditionExpression: keyExpression,\n\t\t\t\tFilterExpression: Is.stringValue(expressions.filterCondition)\n\t\t\t\t\t? expressions.filterCondition\n\t\t\t\t\t: undefined,\n\t\t\t\tExpressionAttributeNames: attributeNames,\n\t\t\t\tExpressionAttributeValues: attributeValues,\n\t\t\t\tProjectionExpression: properties?.map(p => p as string).join(\", \"),\n\t\t\t\tLimit: returnSize,\n\t\t\t\tScanIndexForward: scanAscending,\n\t\t\t\tExclusiveStartKey: Is.empty(cursor)\n\t\t\t\t\t? undefined\n\t\t\t\t\t: ObjectHelper.fromBytes(Converter.base64ToBytes(cursor))\n\t\t\t});\n\n\t\t\tconst connection = this.createDocClient();\n\n\t\t\tconst results = await connection.send(query);\n\n\t\t\tlet entities: T[] = [];\n\n\t\t\tif (Is.arrayValue(results.Items)) {\n\t\t\t\tentities = results.Items.map(item => {\n\t\t\t\t\tconst unmarshalled = unmarshall(item);\n\t\t\t\t\tdelete unmarshalled[DynamoDbEntityStorageConnector._PARTITION_KEY];\n\t\t\t\t\treturn unmarshalled as T;\n\t\t\t\t});\n\t\t\t}\n\n\t\t\treturn {\n\t\t\t\tentities,\n\t\t\t\tcursor: Is.empty(results.LastEvaluatedKey)\n\t\t\t\t\t? undefined\n\t\t\t\t\t: Converter.bytesToBase64(ObjectHelper.toBytes(results.LastEvaluatedKey))\n\t\t\t};\n\t\t} catch (err) {\n\t\t\tif (BaseError.isErrorCode(err, \"ResourceNotFoundException\")) {\n\t\t\t\tthrow new GeneralError(\n\t\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\t\"tableDoesNotExist\",\n\t\t\t\t\t{\n\t\t\t\t\t\ttableName: this._config.tableName\n\t\t\t\t\t},\n\t\t\t\t\terr\n\t\t\t\t);\n\t\t\t}\n\t\t\tthrow new GeneralError(\n\t\t\t\tDynamoDbEntityStorageConnector.CLASS_NAME,\n\t\t\t\t\"queryFailed\",\n\t\t\t\tundefined,\n\t\t\t\terr\n\t\t\t);\n\t\t}\n\t}\n\n\t/**\n\t * Build the condition expression for the query.\n\t * @param conditions The conditions to build the expression from.\n\t * @returns The condition expression.\n\t * @throws GeneralError if the property is not found in the schema.\n\t * @internal\n\t */\n\tprivate buildConditionExpression(conditions?: { property: keyof T; value: unknown }[]): {\n\t\tconditionExpression: string | undefined;\n\t\tattributeNames: { [id: string]: string } | undefined;\n\t\tattributeValues: { [key: string]: NativeAttributeValue } | undefined;\n\t} {\n\t\tlet conditionExpression: string | undefined;\n\t\tlet attributeNames: { [id: string]: string } | undefined;\n\t\tlet attributeValues: { [key: string]: NativeAttributeValue } | undefined;\n\n\t\tif (Is.arrayValue(conditions)) {\n\t\t\tconst expressions: string[] = [];\n\n\t\t\tfor (const c of conditions) {\n\t\t\t\tconst schemaProp = this._entitySchema.properties?.find(p => p.property === c.property);\n\n\t\t\t\tif (Is.undefined(schemaProp)) {\n\t\t\t\t\tthrow new GeneralError(DynamoDbEntityStorageConnector.CLASS_NAME, \"propertyNotFound\", {\n\t\t\t\t\t\tproperty: c.property\n\t\t\t\t\t});\n\t\t\t\t}\n\n\t\t\t\tconst attributeName = `#${c.property as string}`;\n\t\t\t\tconst attributeValueName = `:${c.property as string}`;\n\t\t\t\tattributeNames ??= {};\n\t\t\t\tattributeValues ??= {};\n\t\t\t\tattributeNames[attributeName] = c.property as string;\n\t\t\t\tattributeValues[attributeValueName] = c.value;\n\t\t\t\texpressions.push(`${attributeName} = ${attributeValueName}`);\n\t\t\t}\n\n\t\t\tconditionExpression = expressions.join(\" AND \");\n\t\t}\n\t\treturn { conditionExpression, attributeNames, attributeValues };\n\t}\n}\n"]}
@@ -0,0 +1,6 @@
1
+ // Copyright 2024 IOTA Stiftung.
2
+ // SPDX-License-Identifier: Apache-2.0.
3
+ export * from "./dynamoDbEntityStorageConnector.js";
4
+ export * from "./models/IDynamoDbEntityStorageConnectorConfig.js";
5
+ export * from "./models/IDynamoDbEntityStorageConnectorConstructorOptions.js";
6
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,gCAAgC;AAChC,uCAAuC;AACvC,cAAc,qCAAqC,CAAC;AACpD,cAAc,mDAAmD,CAAC;AAClE,cAAc,+DAA+D,CAAC","sourcesContent":["// Copyright 2024 IOTA Stiftung.\n// SPDX-License-Identifier: Apache-2.0.\nexport * from \"./dynamoDbEntityStorageConnector.js\";\nexport * from \"./models/IDynamoDbEntityStorageConnectorConfig.js\";\nexport * from \"./models/IDynamoDbEntityStorageConnectorConstructorOptions.js\";\n"]}
@@ -0,0 +1,4 @@
1
+ // Copyright 2024 IOTA Stiftung.
2
+ // SPDX-License-Identifier: Apache-2.0.
3
+ export {};
4
+ //# sourceMappingURL=IDynamoDbEntityStorageConnectorConfig.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"IDynamoDbEntityStorageConnectorConfig.js","sourceRoot":"","sources":["../../../src/models/IDynamoDbEntityStorageConnectorConfig.ts"],"names":[],"mappings":"AAAA,gCAAgC;AAChC,uCAAuC","sourcesContent":["// Copyright 2024 IOTA Stiftung.\n// SPDX-License-Identifier: Apache-2.0.\n\n/**\n * Configuration for the Dynamo DB Entity Storage Connector.\n */\nexport interface IDynamoDbEntityStorageConnectorConfig {\n\t/**\n\t * The region for the AWS connection.\n\t */\n\tregion: string;\n\n\t/**\n\t * The authentication mode.\n\t * - \"credentials\": Use access key ID and secret access key.\n\t * - \"pod\": Use IAM role attached to the pod (e.g., in EKS).\n\t * @default credentials\n\t */\n\tauthMode?: \"credentials\" | \"pod\";\n\n\t/**\n\t * The AWS access key ID.\n\t */\n\taccessKeyId?: string;\n\n\t/**\n\t * The AWS secret access key.\n\t */\n\tsecretAccessKey?: string;\n\n\t/**\n\t * The name of the table for the storage.\n\t */\n\ttableName: string;\n\n\t/**\n\t * AWS endpoint, not usually required but could be used for local DynamoDB instance e.g. http://localhost:10000.\n\t */\n\tendpoint?: string;\n}\n"]}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=IDynamoDbEntityStorageConnectorConstructorOptions.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"IDynamoDbEntityStorageConnectorConstructorOptions.js","sourceRoot":"","sources":["../../../src/models/IDynamoDbEntityStorageConnectorConstructorOptions.ts"],"names":[],"mappings":"","sourcesContent":["// Copyright 2024 IOTA Stiftung.\n// SPDX-License-Identifier: Apache-2.0.\nimport type { IDynamoDbEntityStorageConnectorConfig } from \"./IDynamoDbEntityStorageConnectorConfig.js\";\n\n/**\n * Options for the Dynamo DB Entity Storage Connector constructor.\n */\nexport interface IDynamoDbEntityStorageConnectorConstructorOptions {\n\t/**\n\t * The schema for the entity\n\t */\n\tentitySchema: string;\n\n\t/**\n\t * The keys to use from the context ids to create partitions.\n\t */\n\tpartitionContextIds?: string[];\n\n\t/**\n\t * The type of logging component to use, defaults to no logging.\n\t */\n\tloggingComponentType?: string;\n\n\t/**\n\t * The configuration for the connector.\n\t */\n\tconfig: IDynamoDbEntityStorageConnectorConfig;\n}\n"]}