dyno-table 2.2.1 → 2.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (102) hide show
  1. package/README.md +200 -1860
  2. package/dist/builders.cjs +55 -0
  3. package/dist/builders.d.cts +4 -0
  4. package/dist/builders.d.ts +4 -0
  5. package/dist/builders.js +2 -0
  6. package/dist/chunk-2EWNZOUK.js +618 -0
  7. package/dist/chunk-2WIBY7PZ.js +46 -0
  8. package/dist/chunk-7UJJ7JXM.cjs +63 -0
  9. package/dist/chunk-DTFJJASK.js +3200 -0
  10. package/dist/chunk-EODPMYPE.js +558 -0
  11. package/dist/chunk-KA3VPIPS.cjs +560 -0
  12. package/dist/chunk-NTA6GDPP.cjs +622 -0
  13. package/dist/chunk-PB7BBCZO.cjs +32 -0
  14. package/dist/chunk-QVRMYGC4.js +29 -0
  15. package/dist/chunk-XYL43FDX.cjs +3217 -0
  16. package/dist/conditions.cjs +67 -62
  17. package/dist/conditions.js +1 -48
  18. package/dist/entity.cjs +14 -625
  19. package/dist/entity.d.cts +2 -10
  20. package/dist/entity.d.ts +2 -10
  21. package/dist/entity.js +2 -626
  22. package/dist/index-2cbm07Bi.d.ts +2797 -0
  23. package/dist/index-DlN8G9hd.d.cts +2797 -0
  24. package/dist/index.cjs +111 -4460
  25. package/dist/index.d.cts +2 -10
  26. package/dist/index.d.ts +2 -10
  27. package/dist/index.js +5 -4442
  28. package/dist/standard-schema.cjs +0 -2
  29. package/dist/standard-schema.js +0 -2
  30. package/dist/table.cjs +7 -3796
  31. package/dist/table.d.cts +163 -12
  32. package/dist/table.d.ts +163 -12
  33. package/dist/table.js +3 -3799
  34. package/dist/types.cjs +0 -2
  35. package/dist/types.js +0 -2
  36. package/dist/utils.cjs +10 -30
  37. package/dist/utils.js +1 -31
  38. package/package.json +6 -66
  39. package/dist/batch-builder-BiQDIZ7p.d.cts +0 -398
  40. package/dist/batch-builder-CNsLS6sR.d.ts +0 -398
  41. package/dist/builder-types-BTVhQSHI.d.cts +0 -169
  42. package/dist/builder-types-CzuLR4Th.d.ts +0 -169
  43. package/dist/builders/condition-check-builder.cjs +0 -422
  44. package/dist/builders/condition-check-builder.cjs.map +0 -1
  45. package/dist/builders/condition-check-builder.d.cts +0 -153
  46. package/dist/builders/condition-check-builder.d.ts +0 -153
  47. package/dist/builders/condition-check-builder.js +0 -420
  48. package/dist/builders/condition-check-builder.js.map +0 -1
  49. package/dist/builders/delete-builder.cjs +0 -484
  50. package/dist/builders/delete-builder.cjs.map +0 -1
  51. package/dist/builders/delete-builder.d.cts +0 -211
  52. package/dist/builders/delete-builder.d.ts +0 -211
  53. package/dist/builders/delete-builder.js +0 -482
  54. package/dist/builders/delete-builder.js.map +0 -1
  55. package/dist/builders/paginator.cjs +0 -193
  56. package/dist/builders/paginator.cjs.map +0 -1
  57. package/dist/builders/paginator.d.cts +0 -155
  58. package/dist/builders/paginator.d.ts +0 -155
  59. package/dist/builders/paginator.js +0 -191
  60. package/dist/builders/paginator.js.map +0 -1
  61. package/dist/builders/put-builder.cjs +0 -554
  62. package/dist/builders/put-builder.cjs.map +0 -1
  63. package/dist/builders/put-builder.d.cts +0 -319
  64. package/dist/builders/put-builder.d.ts +0 -319
  65. package/dist/builders/put-builder.js +0 -552
  66. package/dist/builders/put-builder.js.map +0 -1
  67. package/dist/builders/query-builder.cjs +0 -757
  68. package/dist/builders/query-builder.cjs.map +0 -1
  69. package/dist/builders/query-builder.d.cts +0 -6
  70. package/dist/builders/query-builder.d.ts +0 -6
  71. package/dist/builders/query-builder.js +0 -755
  72. package/dist/builders/query-builder.js.map +0 -1
  73. package/dist/builders/transaction-builder.cjs +0 -906
  74. package/dist/builders/transaction-builder.cjs.map +0 -1
  75. package/dist/builders/transaction-builder.d.cts +0 -464
  76. package/dist/builders/transaction-builder.d.ts +0 -464
  77. package/dist/builders/transaction-builder.js +0 -904
  78. package/dist/builders/transaction-builder.js.map +0 -1
  79. package/dist/builders/update-builder.cjs +0 -668
  80. package/dist/builders/update-builder.cjs.map +0 -1
  81. package/dist/builders/update-builder.d.cts +0 -374
  82. package/dist/builders/update-builder.d.ts +0 -374
  83. package/dist/builders/update-builder.js +0 -666
  84. package/dist/builders/update-builder.js.map +0 -1
  85. package/dist/conditions.cjs.map +0 -1
  86. package/dist/conditions.js.map +0 -1
  87. package/dist/entity.cjs.map +0 -1
  88. package/dist/entity.js.map +0 -1
  89. package/dist/index.cjs.map +0 -1
  90. package/dist/index.js.map +0 -1
  91. package/dist/query-builder-D3URwK9k.d.cts +0 -477
  92. package/dist/query-builder-cfEkU0_w.d.ts +0 -477
  93. package/dist/standard-schema.cjs.map +0 -1
  94. package/dist/standard-schema.js.map +0 -1
  95. package/dist/table-ClST8nkR.d.cts +0 -276
  96. package/dist/table-vE3cGoDy.d.ts +0 -276
  97. package/dist/table.cjs.map +0 -1
  98. package/dist/table.js.map +0 -1
  99. package/dist/types.cjs.map +0 -1
  100. package/dist/types.js.map +0 -1
  101. package/dist/utils.cjs.map +0 -1
  102. package/dist/utils.js.map +0 -1
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/builders/batch-builder.ts","../src/conditions.ts","../src/expression.ts","../src/utils/debug-expression.ts","../src/builders/delete-builder.ts","../src/builders/put-builder.ts","../src/builders/paginator.ts","../src/builders/filter-builder.ts","../src/builders/result-iterator.ts","../src/builders/query-builder.ts","../src/utils/debug-transaction.ts","../src/builders/transaction-builder.ts","../src/builders/update-builder.ts","../src/builders/entity-aware-builders.ts","../src/entity/ddb-indexing.ts","../src/entity/index-utils.ts","../src/entity/entity.ts","../src/builders/condition-check-builder.ts","../src/builders/get-builder.ts","../src/builders/scan-builder.ts","../src/utils/chunk-array.ts","../src/table.ts","../src/utils/partition-key-template.ts","../src/utils/sort-key-template.ts"],"names":["value","buildIndexes","key","keyConditionExpression"],"mappings":"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","file":"index.cjs","sourcesContent":["import type { PrimaryKeyWithoutExpression } from \"../conditions\";\nimport type { BatchWriteOperation } from \"../operation-types\";\nimport type { DynamoItem } from \"../types\";\nimport type { DeleteCommandParams, PutCommandParams } from \"./builder-types\";\nimport type { GetCommandParams } from \"./get-builder\";\n\n// Constants for DynamoDB batch limits\nconst _DDB_BATCH_WRITE_LIMIT = 25;\nconst _DDB_BATCH_GET_LIMIT = 100;\n\n/**\n * Represents a single operation within a DynamoDB batch.\n * Each operation can be one of:\n * - Put: Insert or replace an item\n * - Delete: Remove an item\n * - Get: Retrieve an item\n */\nexport type BatchItem =\n | { type: \"Put\"; params: PutCommandParams }\n | { type: \"Delete\"; params: DeleteCommandParams }\n | { type: \"Get\"; params: GetCommandParams };\n\n/**\n * Typed batch item that preserves entity type information\n */\nexport type TypedBatchItem<T extends DynamoItem = DynamoItem> =\n | { type: \"Put\"; params: PutCommandParams; entityType?: string; resultType?: T }\n | { type: \"Delete\"; params: DeleteCommandParams; entityType?: string }\n | { type: \"Get\"; params: GetCommandParams; entityType?: string; resultType?: T };\n\n/**\n * Configuration for batch operations\n */\nexport interface BatchConfig {\n partitionKey: string;\n sortKey?: string;\n}\n\n/**\n * Executor function for batch write operations\n */\ntype BatchWriteExecutor = (operations: Array<BatchWriteOperation<DynamoItem>>) => Promise<{\n unprocessedItems: Array<BatchWriteOperation<DynamoItem>>;\n}>;\n\n/**\n * Executor function for batch get operations\n */\ntype BatchGetExecutor = (keys: Array<PrimaryKeyWithoutExpression>) => Promise<{\n items: DynamoItem[];\n unprocessedKeys: PrimaryKeyWithoutExpression[];\n}>;\n\n/**\n * Error class for batch operation failures\n */\nexport class BatchError extends Error {\n public readonly operation: \"write\" | \"read\";\n public override readonly cause?: Error;\n\n constructor(message: string, operation: \"write\" | \"read\", cause?: Error) {\n super(message);\n this.name = \"BatchError\";\n this.operation = operation;\n this.cause = cause;\n }\n}\n\n/**\n * Result structure for batch operations\n */\nexport interface BatchResult {\n /** Whether the batch operation completed successfully */\n success: boolean;\n\n /** Write operation results */\n writes: {\n /** Number of write operations processed successfully */\n processed: number;\n /** Write operations that were not processed and may need retry */\n unprocessed: Array<BatchWriteOperation<DynamoItem>>;\n };\n\n /** Read operation results */\n reads: {\n /** Items retrieved from the batch get operations */\n items: DynamoItem[];\n /** Number of items found and returned */\n found: number;\n /** Keys that were not processed and may need retry */\n unprocessed: PrimaryKeyWithoutExpression[];\n };\n\n /** Total number of operations in the batch */\n totalOperations: number;\n\n /** Any errors that occurred during batch processing */\n errors?: BatchError[];\n}\n\n/**\n * Typed result structure for batch operations with entity type information\n */\nexport interface TypedBatchResult<TEntities extends Record<string, DynamoItem> = Record<string, DynamoItem>> {\n /** Whether the batch operation completed successfully */\n success: boolean;\n\n /** Write operation results */\n writes: {\n /** Number of write operations processed successfully */\n processed: number;\n /** Write operations that were not processed and may need retry */\n unprocessed: Array<BatchWriteOperation<DynamoItem>>;\n };\n\n /** Read operation results with typed items */\n reads: {\n /** Items retrieved from the batch get operations, grouped by entity type */\n itemsByType: {\n [K in keyof TEntities]: TEntities[K][];\n };\n /** All items retrieved (typed as union of all entity types) */\n items: TEntities[keyof TEntities][];\n /** Number of items found and returned */\n found: number;\n /** Keys that were not processed and may need retry */\n unprocessed: PrimaryKeyWithoutExpression[];\n };\n\n /** Total number of operations in the batch */\n totalOperations: number;\n\n /** Any errors that occurred during batch execution */\n errors?: BatchError[];\n}\n\n/**\n * Builder for creating and executing DynamoDB batch operations with full entity support and type inference.\n *\n * Use BatchBuilder when you need to:\n * - Perform multiple operations efficiently (up to 25 writes, 100 reads per batch)\n * - Maintain entity validation, key generation, and type safety\n * - Mix read and write operations in a single batch\n * - Get typed results grouped by entity type\n *\n * @example Basic Usage\n * ```typescript\n * // Define entity types for the batch\n * const batch = table.batchBuilder<{\n * User: UserEntity;\n * Order: OrderEntity;\n * }>();\n *\n * // Add operations using entity repositories\n * userRepo.create(newUser).withBatch(batch, 'User')\n * userRepo.delete({ id: 'old-user' }).withBatch(batch, 'User')\n * orderRepo.get({ id: 'existing-order' }).withBatch(batch, 'Order')\n *\n * // Execute all operations and get typed results\n * const result = await batch.execute()\n * const users: UserEntity[] = result.reads.itemsByType.User\n * const orders: OrderEntity[] = result.reads.itemsByType.Order\n * ```\n *\n * @example Error Handling\n * ```typescript\n * try {\n * const result = await batch.execute()\n *\n * if (result.writes.unprocessed.length > 0) {\n * console.warn('Some writes were not processed:', result.writes.unprocessed)\n * }\n * } catch (error) {\n * if (error instanceof BatchError) {\n * console.error('Batch operation failed:', error.message)\n * }\n * }\n * ```\n */\nexport class BatchBuilder<TEntities extends Record<string, DynamoItem> = Record<string, DynamoItem>> {\n private writeItems: Array<TypedBatchItem<DynamoItem>> = [];\n private getItems: Array<TypedBatchItem<DynamoItem>> = [];\n\n constructor(\n private batchWriteExecutor: BatchWriteExecutor,\n private batchGetExecutor: BatchGetExecutor,\n private config: BatchConfig,\n ) {}\n\n /**\n * Checks if the batch is empty (contains no operations)\n *\n * @returns true if the batch contains no operations\n */\n isEmpty(): boolean {\n return this.writeItems.length === 0 && this.getItems.length === 0;\n }\n\n /**\n * Gets the count of operations in the batch\n *\n * @returns Object containing the count of write and read operations\n */\n getOperationCount(): { writes: number; reads: number } {\n return {\n writes: this.writeItems.length,\n reads: this.getItems.length,\n };\n }\n\n /**\n * Validates that the batch is not empty before execution\n *\n * @throws {BatchError} If the batch is empty\n */\n private validateNotEmpty(): void {\n if (this.isEmpty()) {\n throw new BatchError(\n \"Cannot execute empty batch. Add operations using entity builders with .withBatch()\",\n \"write\",\n );\n }\n }\n\n /**\n * Adds a put operation to the batch with entity type information.\n * This method is used internally by entity builders.\n *\n * @param command - The complete put command configuration\n * @param entityType - The entity type name for type tracking\n * @returns The batch builder for method chaining\n * @internal\n */\n putWithCommand<K extends keyof TEntities>(command: PutCommandParams, entityType?: K): this {\n const batchItem: TypedBatchItem<TEntities[K]> = {\n type: \"Put\",\n params: command,\n entityType: entityType as string,\n };\n this.writeItems.push(batchItem);\n return this;\n }\n\n /**\n * Adds a delete operation to the batch with entity type information.\n * This method is used internally by entity builders.\n *\n * @param command - The complete delete command configuration\n * @param entityType - The entity type name for type tracking\n * @returns The batch builder for method chaining\n * @internal\n */\n deleteWithCommand<K extends keyof TEntities>(command: DeleteCommandParams, entityType?: K): this {\n const batchItem: TypedBatchItem = {\n type: \"Delete\",\n params: command,\n entityType: entityType as string,\n };\n this.writeItems.push(batchItem);\n return this;\n }\n\n /**\n * Adds a get operation to the batch with entity type information.\n * This method is used internally by entity builders.\n *\n * @param command - The complete get command configuration\n * @param entityType - The entity type name for type tracking\n * @returns The batch builder for method chaining\n * @internal\n */\n getWithCommand<K extends keyof TEntities>(command: GetCommandParams, entityType?: K): this {\n const batchItem: TypedBatchItem<TEntities[K]> = {\n type: \"Get\",\n params: command,\n entityType: entityType as string,\n };\n this.getItems.push(batchItem);\n return this;\n }\n\n /**\n * Executes all write operations in the batch.\n *\n * @returns A promise that resolves to any unprocessed operations\n * @private\n */\n private async executeWrites(): Promise<{ unprocessedItems: Array<BatchWriteOperation<DynamoItem>> }> {\n if (this.writeItems.length === 0) {\n return { unprocessedItems: [] };\n }\n\n try {\n // Convert batch items to BatchWriteOperation format\n const operations: Array<BatchWriteOperation<DynamoItem>> = this.writeItems.map((item) => {\n if (item.type === \"Put\") {\n return {\n type: \"put\" as const,\n item: item.params.item,\n };\n }\n\n if (item.type === \"Delete\") {\n // Convert key to PrimaryKeyWithoutExpression format if needed\n let key: PrimaryKeyWithoutExpression;\n if (typeof item.params.key === \"object\" && item.params.key !== null && \"pk\" in item.params.key) {\n key = item.params.key as PrimaryKeyWithoutExpression;\n } else {\n // Convert from table key format to PrimaryKeyWithoutExpression\n const tableKey = item.params.key as Record<string, unknown>;\n key = {\n pk: tableKey[this.config.partitionKey] as string,\n sk: this.config.sortKey ? (tableKey[this.config.sortKey] as string) : undefined,\n };\n }\n\n return {\n type: \"delete\" as const,\n key,\n };\n }\n\n throw new BatchError(`Unsupported batch item type for write operation: ${item.type}`, \"write\");\n });\n\n return await this.batchWriteExecutor(operations);\n } catch (error) {\n throw new BatchError(\n `Failed to execute batch write operations: ${error instanceof Error ? error.message : \"Unknown error\"}`,\n \"write\",\n error instanceof Error ? error : undefined,\n );\n }\n }\n\n /**\n * Executes all get operations in the batch.\n *\n * @returns A promise that resolves to the retrieved items\n * @private\n */\n private async executeGets(): Promise<{ items: DynamoItem[]; unprocessedKeys: PrimaryKeyWithoutExpression[] }> {\n if (this.getItems.length === 0) {\n return { items: [], unprocessedKeys: [] };\n }\n\n try {\n // Convert batch items to keys for batch get\n const keys: Array<PrimaryKeyWithoutExpression> = this.getItems.map((item) => {\n if (item.type === \"Get\") {\n // Convert key to PrimaryKeyWithoutExpression format if needed\n if (typeof item.params.key === \"object\" && item.params.key !== null && \"pk\" in item.params.key) {\n return item.params.key as PrimaryKeyWithoutExpression;\n }\n\n // Convert from table key format to PrimaryKeyWithoutExpression\n const tableKey = item.params.key as Record<string, unknown>;\n return {\n pk: tableKey[this.config.partitionKey] as string,\n sk: this.config.sortKey ? (tableKey[this.config.sortKey] as string) : undefined,\n };\n }\n\n throw new BatchError(`Unsupported batch item type for get operation: ${item.type}`, \"read\");\n });\n\n return await this.batchGetExecutor(keys);\n } catch (error) {\n throw new BatchError(\n `Failed to execute batch get operations: ${error instanceof Error ? error.message : \"Unknown error\"}`,\n \"read\",\n error instanceof Error ? error : undefined,\n );\n }\n }\n\n /**\n * Groups retrieved items by their entity type.\n * @private\n */\n private groupItemsByType(items: DynamoItem[]): { [K in keyof TEntities]: TEntities[K][] } {\n const grouped = {} as { [K in keyof TEntities]: TEntities[K][] };\n\n // Initialize all entity types with empty arrays\n for (const item of this.getItems) {\n if (item.entityType) {\n const entityType = item.entityType as keyof TEntities;\n if (!grouped[entityType]) {\n grouped[entityType] = [];\n }\n }\n }\n\n // Group items by their entityType attribute\n for (const item of items) {\n const entityType = item.entityType as keyof TEntities;\n if (entityType && grouped[entityType]) {\n grouped[entityType].push(item as TEntities[keyof TEntities]);\n }\n }\n\n return grouped;\n }\n\n /**\n * Executes all operations in the batch with typed results.\n * Performs write operations first, then get operations.\n *\n * @returns A promise that resolves to a TypedBatchResult with entity type information\n * @throws {BatchError} If the batch is empty or if operations fail\n */\n async execute(): Promise<TypedBatchResult<TEntities>> {\n this.validateNotEmpty();\n\n const errors: BatchError[] = [];\n let writeResults: { unprocessedItems: Array<BatchWriteOperation<DynamoItem>> } = { unprocessedItems: [] };\n let getResults: { items: DynamoItem[]; unprocessedKeys: PrimaryKeyWithoutExpression[] } = {\n items: [],\n unprocessedKeys: [],\n };\n\n // Execute writes if any\n if (this.writeItems.length > 0) {\n try {\n writeResults = await this.executeWrites();\n } catch (error) {\n if (error instanceof BatchError) {\n errors.push(error);\n } else {\n errors.push(\n new BatchError(\n \"Unexpected error during write operations\",\n \"write\",\n error instanceof Error ? error : undefined,\n ),\n );\n }\n }\n }\n\n // Execute gets if any\n if (this.getItems.length > 0) {\n try {\n getResults = await this.executeGets();\n } catch (error) {\n if (error instanceof BatchError) {\n errors.push(error);\n } else {\n errors.push(\n new BatchError(\n \"Unexpected error during read operations\",\n \"read\",\n error instanceof Error ? error : undefined,\n ),\n );\n }\n }\n }\n\n // If there were critical errors, throw them\n if (\n errors.length > 0 &&\n (writeResults.unprocessedItems.length === this.writeItems.length ||\n getResults.unprocessedKeys.length === this.getItems.length)\n ) {\n throw errors[0]; // Throw the first critical error\n }\n\n const totalOperations = this.writeItems.length + this.getItems.length;\n const success =\n errors.length === 0 && writeResults.unprocessedItems.length === 0 && getResults.unprocessedKeys.length === 0;\n\n return {\n success,\n writes: {\n processed: this.writeItems.length - writeResults.unprocessedItems.length,\n unprocessed: writeResults.unprocessedItems,\n },\n reads: {\n itemsByType: this.groupItemsByType(getResults.items),\n items: getResults.items as TEntities[keyof TEntities][],\n found: getResults.items.length,\n unprocessed: getResults.unprocessedKeys,\n },\n totalOperations,\n errors: errors.length > 0 ? errors : undefined,\n };\n }\n}\n","import type { Path, PathType } from \"./builders/types\";\nimport type { DynamoItem } from \"./types\";\n\n/**\n * Supported comparison operators for DynamoDB conditions.\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html AWS DynamoDB - Comparison Operator Reference}\n *\n * - eq: Equals (=)\n * - ne: Not equals (≠ / <>)\n * - lt: Less than (<)\n * - lte: Less than or equal to (≤)\n * - gt: Greater than (>)\n * - gte: Greater than or equal to (≥)\n * - between: Between two values (inclusive)\n * - in: Checks if attribute value is in a list of values\n * - beginsWith: Checks if string attribute begins with specified substring\n * - contains: Checks if string/set attribute contains specified value\n * - attributeExists: Checks if attribute exists\n * - attributeNotExists: Checks if attribute does not exist\n */\nexport type ComparisonOperator =\n | \"eq\"\n | \"ne\"\n | \"lt\"\n | \"lte\"\n | \"gt\"\n | \"gte\"\n | \"between\"\n | \"in\"\n | \"beginsWith\"\n | \"contains\"\n | \"attributeExists\"\n | \"attributeNotExists\";\n\n/**\n * Logical operators for combining multiple conditions.\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Logical AWS DynamoDB - Logical Operator Reference}\n *\n * - and: Evaluates to true if all conditions are true\n * - or: Evaluates to true if any condition is true\n * - not: Negate the result of a condition\n */\nexport type LogicalOperator = \"and\" | \"or\" | \"not\";\n\n/**\n * Represents a DynamoDB condition expression.\n * Can be either a comparison condition or a logical combination of conditions.\n *\n * @example\n * // Simple comparison condition\n * const condition: Condition = {\n * type: \"eq\",\n * attr: \"status\",\n * value: \"ACTIVE\"\n * };\n *\n * @example\n * // Logical combination of conditions\n * const condition: Condition = {\n * type: \"and\",\n * conditions: [\n * { type: \"eq\", attr: \"status\", value: \"ACTIVE\" },\n * { type: \"gt\", attr: \"age\", value: 5 }\n * ]\n * };\n */\nexport interface Condition {\n /** The type of condition (comparison or logical operator) */\n type: ComparisonOperator | LogicalOperator;\n /** The attribute name for comparison conditions */\n attr?: string;\n /** The value to compare against for comparison conditions */\n value?: unknown;\n /** Array of conditions for logical operators (and/or) */\n conditions?: Condition[];\n /** Single condition for the 'not' operator */\n condition?: Condition;\n}\n\n/**\n * Parameters used to build DynamoDB expression strings.\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.ExpressionAttributeNames.html Expression Attribute Names}\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.ExpressionAttributeValues.html Expression Attribute Values}\n */\nexport interface ExpressionParams {\n /** Map of attribute name placeholders to actual attribute names */\n expressionAttributeNames: Record<string, string>;\n /** Map of value placeholders to actual values */\n expressionAttributeValues: DynamoItem;\n /** Counter for generating unique value placeholders */\n valueCounter: { count: number };\n}\n\n/**\n * Creates a comparison condition builder function for the specified operator.\n * @internal\n */\nexport const createComparisonCondition =\n (type: ComparisonOperator) =>\n (attr: string, value: unknown): Condition => ({\n type,\n attr,\n value,\n });\n\n/**\n * Creates an equals (=) condition\n * @example\n * eq(\"status\", \"ACTIVE\") // status = \"ACTIVE\"\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html}\n */\nexport const eq = createComparisonCondition(\"eq\");\n\n/**\n * Creates a not equals (≠) condition\n * @example\n * ne(\"status\", \"DELETED\") // status <> \"DELETED\"\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html}\n */\nexport const ne = createComparisonCondition(\"ne\");\n\n/**\n * Creates a less than (<) condition\n * @example\n * lt(\"age\", 18) // age < 18\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html}\n */\nexport const lt = createComparisonCondition(\"lt\");\n\n/**\n * Creates a less than or equal to (≤) condition\n * @example\n * lte(\"age\", 18) // age <= 18\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html}\n */\nexport const lte = createComparisonCondition(\"lte\");\n\n/**\n * Creates a greater than (>) condition\n * @example\n * gt(\"price\", 100) // price > 100\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html}\n */\nexport const gt = createComparisonCondition(\"gt\");\n\n/**\n * Creates a greater than or equal to (≥) condition\n * @example\n * gte(\"price\", 100) // price >= 100\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html}\n */\nexport const gte = createComparisonCondition(\"gte\");\n\n/**\n * Creates a between condition that checks if a value is within a range (inclusive)\n * @example\n * between(\"age\", 18, 65) // age BETWEEN 18 AND 65\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - BETWEEN}\n */\nexport const between = (attr: string, lower: unknown, upper: unknown): Condition => ({\n type: \"between\",\n attr,\n value: [lower, upper],\n});\n\n/**\n * Creates an in condition that checks if a value is in a list of values\n * @example\n * inArray(\"status\", [\"ACTIVE\", \"PENDING\", \"PROCESSING\"]) // status IN (\"ACTIVE\", \"PENDING\", \"PROCESSING\")\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - IN}\n */\nexport const inArray = (attr: string, values: unknown[]): Condition => ({\n type: \"in\",\n attr,\n value: values,\n});\n\n/**\n * Creates a begins_with condition that checks if a string attribute starts with a substring\n * @example\n * beginsWith(\"email\", \"@example.com\") // begins_with(email, \"@example.com\")\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Functions AWS DynamoDB - begins_with}\n */\nexport const beginsWith = createComparisonCondition(\"beginsWith\");\n\n/**\n * Creates a contains condition that checks if a string contains a substring or if a set contains an element\n * @example\n * contains(\"tags\", \"important\") // contains(tags, \"important\")\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Functions AWS DynamoDB - contains}\n */\nexport const contains = createComparisonCondition(\"contains\");\n\n/**\n * Creates a condition that checks if an attribute exists\n * @example\n * attributeExists(\"email\") // attribute_exists(email)\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Functions AWS DynamoDB - attribute_exists}\n */\nexport const attributeExists = (attr: string): Condition => ({\n type: \"attributeExists\",\n attr,\n});\n\n/**\n * Creates a condition that checks if an attribute does not exist\n * @example\n * attributeNotExists(\"deletedAt\") // attribute_not_exists(deletedAt)\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Functions AWS DynamoDB - attribute_not_exists}\n */\nexport const attributeNotExists = (attr: string): Condition => ({\n type: \"attributeNotExists\",\n attr,\n});\n\n// --- Logical Operators ---\n\n/**\n * Combines multiple conditions with AND operator\n * @example\n * and(\n * eq(\"status\", \"ACTIVE\"),\n * gt(\"age\", 18)\n * ) // status = \"ACTIVE\" AND age > 18\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Logical AWS DynamoDB - AND}\n */\nexport const and = (...conditions: Condition[]): Condition => ({\n type: \"and\",\n conditions,\n});\n\n/**\n * Combines multiple conditions with OR operator\n * @example\n * or(\n * eq(\"status\", \"PENDING\"),\n * eq(\"status\", \"PROCESSING\")\n * ) // status = \"PENDING\" OR status = \"PROCESSING\"\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Logical AWS DynamoDB - OR}\n */\nexport const or = (...conditions: Condition[]): Condition => ({\n type: \"or\",\n conditions,\n});\n\n/**\n * Negates a condition\n * @example\n * not(eq(\"status\", \"DELETED\")) // NOT status = \"DELETED\"\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Logical AWS DynamoDB - NOT}\n */\nexport const not = (condition: Condition): Condition => ({\n type: \"not\",\n condition,\n});\n\n/**\n * Type-safe operators for building key conditions in DynamoDB queries.\n * Only includes operators that are valid for key conditions.\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Query.html#Query.KeyConditionExpressions AWS DynamoDB - Key Condition Expressions}\n *\n * @example\n * // Using with sort key conditions\n * table.query({\n * pk: \"USER#123\",\n * sk: op => op.beginsWith(\"ORDER#\")\n * })\n */\nexport type KeyConditionOperator = {\n /** Equals comparison for key attributes */\n eq: (value: unknown) => Condition;\n /** Less than comparison for key attributes */\n lt: (value: unknown) => Condition;\n /** Less than or equal comparison for key attributes */\n lte: (value: unknown) => Condition;\n /** Greater than comparison for key attributes */\n gt: (value: unknown) => Condition;\n /** Greater than or equal comparison for key attributes */\n gte: (value: unknown) => Condition;\n /** Between range comparison for key attributes */\n between: (lower: unknown, upper: unknown) => Condition;\n /** Begins with comparison for key attributes */\n beginsWith: (value: unknown) => Condition;\n /** Combines multiple key conditions with AND */\n and: (...conditions: Condition[]) => Condition;\n};\n\n// Helper types that allow string paths and unknown values when strict typing can't be resolved\ntype FlexiblePath<T> = Path<T> extends never ? string : Path<T>;\n// biome-ignore lint: Using any as we don't really know if it's not provided\ntype FlexiblePathType<T, K extends keyof any> = PathType<T, K> extends never ? unknown : PathType<T, K>;\n\n/**\n * Type-safe operators for building conditions in DynamoDB operations.\n * Includes all available condition operators with proper type inference.\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html AWS DynamoDB - Condition Expressions}\n *\n * @example\n * // Using with type-safe conditions\n * interface User {\n * status: string;\n * age: number;\n * email?: string;\n * }\n *\n * table.scan<User>()\n * .where(op => op.and(\n * op.eq(\"status\", \"ACTIVE\"),\n * op.gt(\"age\", 18),\n * op.attributeExists(\"email\")\n * ))\n *\n * @template T The type of the item being operated on\n */\nexport type ConditionOperator<T extends DynamoItem> = {\n /**\n * Creates an equals (=) condition for type-safe attribute comparison.\n * Tests if the specified attribute equals the provided value.\n *\n * @param attr - The attribute path to compare (with full type safety)\n * @param value - The value to compare against (must match attribute type)\n * @returns A condition that evaluates to true when attr equals value\n *\n * @example\n * ```typescript\n * interface User { status: string; age: number; }\n *\n * // String comparison\n * op.eq(\"status\", \"ACTIVE\") // status = \"ACTIVE\"\n *\n * // Numeric comparison\n * op.eq(\"age\", 25) // age = 25\n *\n * // Nested attribute\n * op.eq(\"profile.role\", \"admin\") // profile.role = \"admin\"\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - Comparison Operators}\n */\n eq: <K extends FlexiblePath<T>>(attr: K, value: FlexiblePathType<T, K>) => Condition;\n\n /**\n * Creates a not equals (≠ / <>) condition for type-safe attribute comparison.\n * Tests if the specified attribute does not equal the provided value.\n *\n * @param attr - The attribute path to compare (with full type safety)\n * @param value - The value to compare against (must match attribute type)\n * @returns A condition that evaluates to true when attr does not equal value\n *\n * @example\n * ```typescript\n * interface User { status: string; priority: number; }\n *\n * // String comparison\n * op.ne(\"status\", \"DELETED\") // status <> \"DELETED\"\n *\n * // Numeric comparison\n * op.ne(\"priority\", 0) // priority <> 0\n *\n * // Useful for filtering out specific values\n * op.ne(\"category\", \"ARCHIVED\") // category <> \"ARCHIVED\"\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - Comparison Operators}\n */\n ne: <K extends FlexiblePath<T>>(attr: K, value: FlexiblePathType<T, K>) => Condition;\n\n /**\n * Creates a less than (<) condition for type-safe attribute comparison.\n * Tests if the specified attribute is less than the provided value.\n * Works with numbers, strings (lexicographic), and dates.\n *\n * @param attr - The attribute path to compare (with full type safety)\n * @param value - The value to compare against (must match attribute type)\n * @returns A condition that evaluates to true when attr is less than value\n *\n * @example\n * ```typescript\n * interface Product { price: number; name: string; createdAt: string; }\n *\n * // Numeric comparison\n * op.lt(\"price\", 100) // price < 100\n *\n * // String comparison (lexicographic)\n * op.lt(\"name\", \"M\") // name < \"M\" (names starting with A-L)\n *\n * // Date comparison (ISO strings)\n * op.lt(\"createdAt\", \"2024-01-01\") // createdAt < \"2024-01-01\"\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - Comparison Operators}\n */\n lt: <K extends FlexiblePath<T>>(attr: K, value: FlexiblePathType<T, K>) => Condition;\n\n /**\n * Creates a less than or equal to (≤) condition for type-safe attribute comparison.\n * Tests if the specified attribute is less than or equal to the provided value.\n * Works with numbers, strings (lexicographic), and dates.\n *\n * @param attr - The attribute path to compare (with full type safety)\n * @param value - The value to compare against (must match attribute type)\n * @returns A condition that evaluates to true when attr is less than or equal to value\n *\n * @example\n * ```typescript\n * interface Order { total: number; priority: number; dueDate: string; }\n *\n * // Numeric comparison\n * op.lte(\"total\", 1000) // total <= 1000\n *\n * // Priority levels\n * op.lte(\"priority\", 3) // priority <= 3 (low to medium priority)\n *\n * // Date deadlines\n * op.lte(\"dueDate\", \"2024-12-31\") // dueDate <= \"2024-12-31\"\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - Comparison Operators}\n */\n lte: <K extends FlexiblePath<T>>(attr: K, value: FlexiblePathType<T, K>) => Condition;\n\n /**\n * Creates a greater than (>) condition for type-safe attribute comparison.\n * Tests if the specified attribute is greater than the provided value.\n * Works with numbers, strings (lexicographic), and dates.\n *\n * @param attr - The attribute path to compare (with full type safety)\n * @param value - The value to compare against (must match attribute type)\n * @returns A condition that evaluates to true when attr is greater than value\n *\n * @example\n * ```typescript\n * interface User { age: number; score: number; lastLogin: string; }\n *\n * // Age restrictions\n * op.gt(\"age\", 18) // age > 18 (adults only)\n *\n * // Performance thresholds\n * op.gt(\"score\", 85) // score > 85 (high performers)\n *\n * // Recent activity\n * op.gt(\"lastLogin\", \"2024-01-01\") // lastLogin > \"2024-01-01\"\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - Comparison Operators}\n */\n gt: <K extends FlexiblePath<T>>(attr: K, value: FlexiblePathType<T, K>) => Condition;\n\n /**\n * Creates a greater than or equal to (≥) condition for type-safe attribute comparison.\n * Tests if the specified attribute is greater than or equal to the provided value.\n * Works with numbers, strings (lexicographic), and dates.\n *\n * @param attr - The attribute path to compare (with full type safety)\n * @param value - The value to compare against (must match attribute type)\n * @returns A condition that evaluates to true when attr is greater than or equal to value\n *\n * @example\n * ```typescript\n * interface Product { rating: number; version: string; releaseDate: string; }\n *\n * // Minimum ratings\n * op.gte(\"rating\", 4.0) // rating >= 4.0 (highly rated)\n *\n * // Version requirements\n * op.gte(\"version\", \"2.0.0\") // version >= \"2.0.0\"\n *\n * // Release date filters\n * op.gte(\"releaseDate\", \"2024-01-01\") // releaseDate >= \"2024-01-01\"\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - Comparison Operators}\n */\n gte: <K extends FlexiblePath<T>>(attr: K, value: FlexiblePathType<T, K>) => Condition;\n\n /**\n * Creates a between condition for type-safe range comparison.\n * Tests if the specified attribute value falls within the inclusive range [lower, upper].\n * Works with numbers, strings (lexicographic), and dates.\n *\n * @param attr - The attribute path to compare (with full type safety)\n * @param lower - The lower bound of the range (inclusive, must match attribute type)\n * @param upper - The upper bound of the range (inclusive, must match attribute type)\n * @returns A condition that evaluates to true when lower ≤ attr ≤ upper\n *\n * @example\n * ```typescript\n * interface Event { price: number; date: string; priority: number; }\n *\n * // Price range\n * op.between(\"price\", 50, 200) // price BETWEEN 50 AND 200\n *\n * // Date range\n * op.between(\"date\", \"2024-01-01\", \"2024-12-31\") // date BETWEEN \"2024-01-01\" AND \"2024-12-31\"\n *\n * // Priority levels\n * op.between(\"priority\", 1, 5) // priority BETWEEN 1 AND 5\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - BETWEEN}\n */\n between: <K extends FlexiblePath<T>>(\n attr: K,\n lower: FlexiblePathType<T, K>,\n upper: FlexiblePathType<T, K>,\n ) => Condition;\n\n /**\n * Creates an IN condition for type-safe list membership testing.\n * Tests if the specified attribute value matches any value in the provided list.\n * Supports up to 100 values in the list as per DynamoDB limitations.\n *\n * @param attr - The attribute path to compare (with full type safety)\n * @param values - Array of values to test against (must match attribute type, max 100 items)\n * @returns A condition that evaluates to true when attr matches any value in the list\n *\n * @example\n * ```typescript\n * interface User { status: string; role: string; priority: number; }\n *\n * // Status filtering\n * op.inArray(\"status\", [\"ACTIVE\", \"PENDING\", \"PROCESSING\"]) // status IN (\"ACTIVE\", \"PENDING\", \"PROCESSING\")\n *\n * // Role-based access\n * op.inArray(\"role\", [\"admin\", \"moderator\", \"editor\"]) // role IN (\"admin\", \"moderator\", \"editor\")\n *\n * // Priority levels\n * op.inArray(\"priority\", [1, 2, 3]) // priority IN (1, 2, 3)\n * ```\n *\n * @throws {Error} When values array is empty or contains more than 100 items\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Comparators AWS DynamoDB - IN}\n */\n inArray: <K extends FlexiblePath<T>>(attr: K, values: FlexiblePathType<T, K>[]) => Condition;\n\n /**\n * Creates a begins_with condition for type-safe string prefix testing.\n * Tests if the specified string attribute starts with the provided substring.\n * Only works with string attributes - will fail on other data types.\n *\n * @param attr - The string attribute path to test (with full type safety)\n * @param value - The prefix string to test for (must match attribute type)\n * @returns A condition that evaluates to true when attr starts with value\n *\n * @example\n * ```typescript\n * interface User { email: string; name: string; id: string; }\n *\n * // Email domain filtering\n * op.beginsWith(\"email\", \"admin@\") // begins_with(email, \"admin@\")\n *\n * // Name prefix search\n * op.beginsWith(\"name\", \"John\") // begins_with(name, \"John\")\n *\n * // ID pattern matching\n * op.beginsWith(\"id\", \"USER#\") // begins_with(id, \"USER#\")\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Functions AWS DynamoDB - begins_with}\n */\n beginsWith: <K extends FlexiblePath<T>>(attr: K, value: FlexiblePathType<T, K>) => Condition;\n\n /**\n * Creates a contains condition for type-safe substring or set membership testing.\n * For strings: tests if the attribute contains the specified substring.\n * For sets: tests if the set contains the specified element.\n *\n * @param attr - The attribute path to test (with full type safety)\n * @param value - The substring or element to search for (must match attribute type)\n * @returns A condition that evaluates to true when attr contains value\n *\n * @example\n * ```typescript\n * interface Post { content: string; tags: Set<string>; categories: string[]; }\n *\n * // Substring search in content\n * op.contains(\"content\", \"important\") // contains(content, \"important\")\n *\n * // Tag membership (for DynamoDB String Sets)\n * op.contains(\"tags\", \"featured\") // contains(tags, \"featured\")\n *\n * // Category search (for string arrays stored as lists)\n * op.contains(\"categories\", \"technology\") // contains(categories, \"technology\")\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Functions AWS DynamoDB - contains}\n */\n contains: <K extends FlexiblePath<T>>(attr: K, value: FlexiblePathType<T, K>) => Condition;\n\n /**\n * Creates an attribute_exists condition for type-safe attribute presence testing.\n * Tests if the specified attribute exists in the item, regardless of its value.\n * Useful for filtering items that have optional attributes populated.\n *\n * @param attr - The attribute path to test for existence (with full type safety)\n * @returns A condition that evaluates to true when the attribute exists\n *\n * @example\n * ```typescript\n * interface User { email: string; phone?: string; profile?: { avatar?: string; }; }\n *\n * // Check for optional fields\n * op.attributeExists(\"phone\") // attribute_exists(phone)\n *\n * // Check for nested optional attributes\n * op.attributeExists(\"profile.avatar\") // attribute_exists(profile.avatar)\n *\n * // Useful in combination with other conditions\n * op.and(\n * op.eq(\"status\", \"ACTIVE\"),\n * op.attributeExists(\"email\") // Only active users with email\n * )\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Functions AWS DynamoDB - attribute_exists}\n */\n attributeExists: <K extends FlexiblePath<T>>(attr: K) => Condition;\n\n /**\n * Creates an attribute_not_exists condition for type-safe attribute absence testing.\n * Tests if the specified attribute does not exist in the item.\n * Useful for conditional writes to prevent overwriting existing data.\n *\n * @param attr - The attribute path to test for absence (with full type safety)\n * @returns A condition that evaluates to true when the attribute does not exist\n *\n * @example\n * ```typescript\n * interface User { id: string; email: string; deletedAt?: string; }\n *\n * // Ensure item hasn't been soft-deleted\n * op.attributeNotExists(\"deletedAt\") // attribute_not_exists(deletedAt)\n *\n * // Prevent duplicate creation\n * op.attributeNotExists(\"id\") // attribute_not_exists(id)\n *\n * // Conditional updates\n * op.and(\n * op.eq(\"status\", \"PENDING\"),\n * op.attributeNotExists(\"processedAt\") // Only unprocessed items\n * )\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Functions AWS DynamoDB - attribute_not_exists}\n */\n attributeNotExists: <K extends FlexiblePath<T>>(attr: K) => Condition;\n\n /**\n * Combines multiple conditions with logical AND operator.\n * All provided conditions must evaluate to true for the AND condition to be true.\n * Supports any number of conditions as arguments.\n *\n * @param conditions - Variable number of conditions to combine with AND\n * @returns A condition that evaluates to true when all input conditions are true\n *\n * @example\n * ```typescript\n * interface User { status: string; age: number; role: string; verified: boolean; }\n *\n * // Multiple criteria\n * op.and(\n * op.eq(\"status\", \"ACTIVE\"),\n * op.gt(\"age\", 18),\n * op.eq(\"verified\", true)\n * ) // status = \"ACTIVE\" AND age > 18 AND verified = true\n *\n * // Complex business logic\n * op.and(\n * op.inArray(\"role\", [\"admin\", \"moderator\"]),\n * op.attributeExists(\"permissions\"),\n * op.ne(\"status\", \"SUSPENDED\")\n * )\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Logical AWS DynamoDB - AND}\n */\n and: (...conditions: Condition[]) => Condition;\n\n /**\n * Combines multiple conditions with logical OR operator.\n * At least one of the provided conditions must evaluate to true for the OR condition to be true.\n * Supports any number of conditions as arguments.\n *\n * @param conditions - Variable number of conditions to combine with OR\n * @returns A condition that evaluates to true when any input condition is true\n *\n * @example\n * ```typescript\n * interface Order { status: string; priority: string; urgent: boolean; }\n *\n * // Alternative statuses\n * op.or(\n * op.eq(\"status\", \"PENDING\"),\n * op.eq(\"status\", \"PROCESSING\"),\n * op.eq(\"status\", \"SHIPPED\")\n * ) // status = \"PENDING\" OR status = \"PROCESSING\" OR status = \"SHIPPED\"\n *\n * // High priority items\n * op.or(\n * op.eq(\"priority\", \"HIGH\"),\n * op.eq(\"urgent\", true)\n * )\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Logical AWS DynamoDB - OR}\n */\n or: (...conditions: Condition[]) => Condition;\n\n /**\n * Negates a condition with logical NOT operator.\n * Inverts the boolean result of the provided condition.\n *\n * @param condition - The condition to negate\n * @returns A condition that evaluates to true when the input condition is false\n *\n * @example\n * ```typescript\n * interface User { status: string; role: string; banned: boolean; }\n *\n * // Exclude specific status\n * op.not(op.eq(\"status\", \"DELETED\")) // NOT status = \"DELETED\"\n *\n * // Complex negation\n * op.not(\n * op.and(\n * op.eq(\"role\", \"guest\"),\n * op.eq(\"banned\", true)\n * )\n * ) // NOT (role = \"guest\" AND banned = true)\n *\n * // Exclude multiple values\n * op.not(op.inArray(\"status\", [\"DELETED\", \"ARCHIVED\"]))\n * ```\n *\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Expressions.OperatorsAndFunctions.html#Expressions.OperatorsAndFunctions.Logical AWS DynamoDB - NOT}\n */\n not: (condition: Condition) => Condition;\n};\n\n/**\n * Primary key type for QUERY operations.\n * Allows building complex key conditions for the sort key.\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Query.html AWS DynamoDB - Query Operations}\n *\n * @example\n * // Query items with a specific partition key and sort key prefix\n * table.query({\n * pk: \"USER#123\",\n * sk: op => op.beginsWith(\"ORDER#2023\")\n * })\n *\n * @example\n * // Query items within a specific sort key range\n * table.query({\n * pk: \"USER#123\",\n * sk: op => op.between(\"ORDER#2023-01\", \"ORDER#2023-12\")\n * })\n */\nexport type PrimaryKey = {\n /** Partition key value */\n pk: string;\n /** Optional sort key condition builder */\n sk?: (op: KeyConditionOperator) => Condition;\n};\n\n/**\n * Primary key type for GET and DELETE operations.\n * Used when you need to specify exact key values without conditions.\n * @see {@link https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/WorkingWithItems.html AWS DynamoDB - Working with Items}\n *\n * @example\n * // Get a specific item by its complete primary key\n * table.get({\n * pk: \"USER#123\",\n * sk: \"PROFILE#123\"\n * })\n *\n * @example\n * // Delete a specific item by its complete primary key\n * table.delete({\n * pk: \"USER#123\",\n * sk: \"ORDER#456\"\n * })\n */\nexport type PrimaryKeyWithoutExpression = {\n /** Partition key value */\n pk: string;\n /** Optional sort key value */\n sk?: string;\n};\n","import type { ComparisonOperator, Condition, ExpressionParams, LogicalOperator } from \"./conditions\";\n\nexport const generateAttributeName = (params: ExpressionParams, attr: string): string => {\n // Handle nested paths by splitting on dots\n if (attr.includes(\".\")) {\n const pathSegments = attr.split(\".\");\n const segmentNames: string[] = [];\n\n for (const segment of pathSegments) {\n // Check if this segment already exists in expressionAttributeNames\n let segmentName: string | undefined;\n for (const [existingName, existingAttr] of Object.entries(params.expressionAttributeNames)) {\n if (existingAttr === segment) {\n segmentName = existingName;\n break;\n }\n }\n\n // If not found, create a new attribute name for this segment\n if (!segmentName) {\n segmentName = `#${Object.keys(params.expressionAttributeNames).length}`;\n params.expressionAttributeNames[segmentName] = segment;\n }\n\n segmentNames.push(segmentName);\n }\n\n return segmentNames.join(\".\");\n }\n\n // Handle single-level attributes (original logic)\n // Check if the attribute already exists in the expressionAttributeNames\n for (const [existingName, existingAttr] of Object.entries(params.expressionAttributeNames)) {\n if (existingAttr === attr) {\n return existingName;\n }\n }\n\n // If not found, create a new attribute name\n const attrName = `#${Object.keys(params.expressionAttributeNames).length}`;\n params.expressionAttributeNames[attrName] = attr;\n return attrName;\n};\n\nexport const generateValueName = (params: ExpressionParams, value: unknown): string => {\n const valueName = `:${params.valueCounter.count++}`;\n params.expressionAttributeValues[valueName] = value;\n return valueName;\n};\n\nconst validateCondition = (condition: Condition, requiresAttr = true, requiresValue = true): void => {\n if (requiresAttr && !condition.attr) {\n throw new Error(`Attribute is required for ${condition.type} condition`);\n }\n\n if (requiresValue && condition.value === undefined) {\n throw new Error(`Value is required for ${condition.type} condition`);\n }\n};\n\nconst buildComparisonExpression = (condition: Condition, operator: string, params: ExpressionParams): string => {\n validateCondition(condition);\n\n if (!condition.attr) {\n throw new Error(`Attribute is required for ${condition.type} condition`);\n }\n\n const attrName = generateAttributeName(params, condition.attr);\n const valueName = generateValueName(params, condition.value);\n\n return `${attrName} ${operator} ${valueName}`;\n};\n\nconst buildBetweenExpression = (condition: Condition, params: ExpressionParams): string => {\n validateCondition(condition);\n\n if (!condition.attr) {\n throw new Error(`Attribute is required for ${condition.type} condition`);\n }\n\n if (!Array.isArray(condition.value) || condition.value.length !== 2) {\n throw new Error(\"Between condition requires an array of two values\");\n }\n\n const attrName = generateAttributeName(params, condition.attr);\n const lowerName = generateValueName(params, condition.value[0]);\n const upperName = generateValueName(params, condition.value[1]);\n\n return `${attrName} BETWEEN ${lowerName} AND ${upperName}`;\n};\n\nconst buildInExpression = (condition: Condition, params: ExpressionParams): string => {\n validateCondition(condition);\n\n if (!condition.attr) {\n throw new Error(`Attribute is required for ${condition.type} condition`);\n }\n\n if (!Array.isArray(condition.value) || condition.value.length === 0) {\n throw new Error(\"In condition requires a non-empty array of values\");\n }\n\n if (condition.value.length > 100) {\n throw new Error(\"In condition supports a maximum of 100 values\");\n }\n\n const attrName = generateAttributeName(params, condition.attr);\n const valueNames = condition.value.map((value) => generateValueName(params, value));\n\n return `${attrName} IN (${valueNames.join(\", \")})`;\n};\n\nconst buildFunctionExpression = (functionName: string, condition: Condition, params: ExpressionParams): string => {\n validateCondition(condition);\n\n if (!condition.attr) {\n throw new Error(`Attribute is required for ${condition.type} condition`);\n }\n\n const attrName = generateAttributeName(params, condition.attr);\n const valueName = generateValueName(params, condition.value);\n\n return `${functionName}(${attrName}, ${valueName})`;\n};\n\nconst buildAttributeFunction = (functionName: string, condition: Condition, params: ExpressionParams): string => {\n validateCondition(condition, true, false);\n\n if (!condition.attr) {\n throw new Error(`Attribute is required for ${condition.type} condition`);\n }\n\n const attrName = generateAttributeName(params, condition.attr);\n return `${functionName}(${attrName})`;\n};\n\nconst buildLogicalExpression = (operator: string, conditions: Condition[], params: ExpressionParams): string => {\n if (!conditions || conditions.length === 0) {\n throw new Error(`At least one condition is required for ${operator} expression`);\n }\n\n const expressions = conditions.map((c) => buildExpression(c, params));\n return `(${expressions.join(` ${operator} `)})`;\n};\n\nexport const buildExpression = (condition: Condition, params: ExpressionParams): string => {\n if (!condition) return \"\";\n\n try {\n // Map of condition types to their expression builders\n const expressionBuilders: Record<ComparisonOperator | LogicalOperator, () => string> = {\n eq: () => buildComparisonExpression(condition, \"=\", params),\n ne: () => buildComparisonExpression(condition, \"<>\", params),\n lt: () => buildComparisonExpression(condition, \"<\", params),\n lte: () => buildComparisonExpression(condition, \"<=\", params),\n gt: () => buildComparisonExpression(condition, \">\", params),\n gte: () => buildComparisonExpression(condition, \">=\", params),\n between: () => buildBetweenExpression(condition, params),\n in: () => buildInExpression(condition, params),\n beginsWith: () => buildFunctionExpression(\"begins_with\", condition, params),\n contains: () => buildFunctionExpression(\"contains\", condition, params),\n attributeExists: () => buildAttributeFunction(\"attribute_exists\", condition, params),\n attributeNotExists: () => buildAttributeFunction(\"attribute_not_exists\", condition, params),\n and: () => {\n if (!condition.conditions) {\n throw new Error(\"Conditions array is required for AND operator\");\n }\n return buildLogicalExpression(\"AND\", condition.conditions, params);\n },\n or: () => {\n if (!condition.conditions) {\n throw new Error(\"Conditions array is required for OR operator\");\n }\n return buildLogicalExpression(\"OR\", condition.conditions, params);\n },\n not: () => {\n if (!condition.condition) {\n throw new Error(\"Condition is required for NOT operator\");\n }\n return `NOT (${buildExpression(condition.condition, params)})`;\n },\n };\n\n const builder = expressionBuilders[condition.type];\n if (!builder) {\n throw new Error(`Unknown condition type: ${condition.type}`);\n }\n\n return builder();\n } catch (error: unknown) {\n if (error instanceof Error) {\n console.error(`Error building expression for condition type ${condition.type}:`, error.message);\n } else {\n console.error(`Error building expression for condition type ${condition.type}:`, error);\n }\n throw error;\n }\n};\n\nexport const prepareExpressionParams = (\n condition?: Condition,\n): {\n expression?: string;\n names?: Record<string, string>;\n values?: Record<string, unknown>;\n} => {\n if (!condition) return {};\n\n const params: ExpressionParams = {\n expressionAttributeNames: {},\n expressionAttributeValues: {},\n valueCounter: { count: 0 },\n };\n\n const expression = buildExpression(condition, params);\n\n return {\n expression,\n names: Object.keys(params.expressionAttributeNames).length > 0 ? params.expressionAttributeNames : undefined,\n values: Object.keys(params.expressionAttributeValues).length > 0 ? params.expressionAttributeValues : undefined,\n };\n};\n","/**\n * Interface for DynamoDB command objects that can contain expressions\n */\nexport interface DynamoCommandWithExpressions {\n conditionExpression?: string;\n updateExpression?: string;\n filterExpression?: string;\n keyConditionExpression?: string;\n projectionExpression?: string;\n expressionAttributeNames?: Record<string, string>;\n expressionAttributeValues?: Record<string, unknown>;\n [key: string]: unknown;\n}\n\ntype ReadableDynamoCommand = {\n conditionExpression?: string;\n updateExpression?: string;\n filterExpression?: string;\n keyConditionExpression?: string;\n projectionExpression?: string;\n};\n\n/**\n * Utility function to debug a DynamoDB command by replacing all placeholders\n * in expressions with their actual values.\n *\n * @param command Any DynamoDB command with expressions and attribute maps\n * @returns An object with the same structure but with readable expressions\n */\nexport function debugCommand<T extends DynamoCommandWithExpressions>(\n command: T,\n): {\n raw: T;\n readable: ReadableDynamoCommand;\n} {\n // Create a copy of the command\n const result: ReadableDynamoCommand = {};\n\n function replaceAliases(expressionString: string) {\n if (!expressionString) {\n return expressionString;\n }\n\n let replacedString = expressionString;\n for (const alias in command.expressionAttributeNames) {\n const attributeName = command.expressionAttributeNames[alias];\n const regex = new RegExp(alias, \"g\");\n\n replacedString = replacedString.replace(regex, attributeName as string);\n }\n\n for (const alias in command.expressionAttributeValues) {\n let attributeValue = command.expressionAttributeValues[alias];\n\n // Handle Set objects for better readability\n if (attributeValue instanceof Set) {\n const array = Array.from(attributeValue);\n attributeValue = `Set(${array.length}){${array.map((v) => JSON.stringify(v)).join(\", \")}}`;\n } else {\n // Stringify other values for display\n attributeValue = JSON.stringify(attributeValue);\n }\n\n const regex = new RegExp(alias, \"g\");\n replacedString = replacedString.replace(regex, attributeValue as string);\n }\n\n return replacedString;\n }\n\n if (command.updateExpression) {\n result.updateExpression = replaceAliases(command.updateExpression);\n }\n if (command.conditionExpression) {\n result.conditionExpression = replaceAliases(command.conditionExpression);\n }\n if (command.filterExpression) {\n result.filterExpression = replaceAliases(command.filterExpression);\n }\n if (command.keyConditionExpression) {\n result.keyConditionExpression = replaceAliases(command.keyConditionExpression);\n }\n if (command.projectionExpression) {\n result.projectionExpression = replaceAliases(command.projectionExpression);\n }\n\n return {\n raw: command,\n readable: result,\n };\n}\n","import type { Condition, ConditionOperator, PrimaryKeyWithoutExpression } from \"../conditions\";\nimport {\n and,\n attributeExists,\n attributeNotExists,\n beginsWith,\n between,\n contains,\n eq,\n gt,\n gte,\n inArray,\n lt,\n lte,\n ne,\n not,\n or,\n} from \"../conditions\";\nimport { prepareExpressionParams } from \"../expression\";\nimport type { DynamoItem } from \"../types\";\nimport { debugCommand } from \"../utils/debug-expression\";\nimport type { BatchBuilder } from \"./batch-builder\";\nimport type { DeleteCommandParams } from \"./builder-types\";\nimport type { TransactionBuilder } from \"./transaction-builder\";\n\nexport interface DeleteOptions {\n condition?: Condition;\n returnValues?: \"ALL_OLD\";\n}\n\ntype DeleteExecutor = (params: DeleteCommandParams) => Promise<{ item?: DynamoItem }>;\n\n/**\n * Builder for creating DynamoDB delete operations.\n *\n * @example\n * ```typescript\n * // Simple delete\n * const result = await new DeleteBuilder(executor, 'dinosaurs', { id: 'TREX-001' })\n * .execute();\n *\n * // Conditional delete with old value retrieval\n * const result = await new DeleteBuilder(executor, 'habitats', { id: 'PADDOCK-A' })\n * .condition(op =>\n * op.and([\n * op.eq('status', 'DECOMMISSIONED'),\n * op.eq('occupants', 0),\n * op.lt('securityIncidents', 1)\n * ])\n * )\n * .returnValues('ALL_OLD')\n * .execute();\n * ```\n */\nexport class DeleteBuilder {\n private options: DeleteOptions = {\n returnValues: \"ALL_OLD\",\n };\n private readonly executor: DeleteExecutor;\n private readonly tableName: string;\n private readonly key: PrimaryKeyWithoutExpression;\n\n constructor(executor: DeleteExecutor, tableName: string, key: PrimaryKeyWithoutExpression) {\n this.executor = executor;\n this.tableName = tableName;\n this.key = key;\n }\n\n /**\n * Adds a condition that must be satisfied for the delete operation to succeed.\n *\n * @example\n * ```typescript\n * // Ensure dinosaur can be safely removed\n * builder.condition(op =>\n * op.and([\n * op.eq('status', 'SEDATED'),\n * op.eq('location', 'MEDICAL_BAY'),\n * op.attributeExists('lastCheckup')\n * ])\n * );\n *\n * // Verify habitat is empty\n * builder.condition(op =>\n * op.and([\n * op.eq('occupants', 0),\n * op.eq('maintenanceStatus', 'COMPLETE'),\n * op.not(op.attributeExists('activeAlerts'))\n * ])\n * );\n * ```\n *\n * @param condition - Either a Condition object or a callback function that builds the condition\n * @returns The builder instance for method chaining\n */\n public condition<T extends DynamoItem>(\n condition: Condition | ((op: ConditionOperator<T>) => Condition),\n ): DeleteBuilder {\n if (typeof condition === \"function\") {\n const conditionOperator: ConditionOperator<T> = {\n eq,\n ne,\n lt,\n lte,\n gt,\n gte,\n between,\n inArray,\n beginsWith,\n contains,\n attributeExists,\n attributeNotExists,\n and,\n or,\n not,\n };\n this.options.condition = condition(conditionOperator);\n } else {\n this.options.condition = condition;\n }\n return this;\n }\n\n /**\n * Sets whether to return the item's attribute values before deletion.\n *\n * @example\n * ```ts\n * // Archive dinosaur data before removal\n * const result = await builder\n * .returnValues('ALL_OLD')\n * .execute();\n *\n * if (result.item) {\n * console.log('Removed dinosaur data:', {\n * species: result.item.species,\n * age: result.item.age,\n * lastLocation: result.item.location\n * });\n * }\n * ```\n *\n * @param returnValues - Use 'ALL_OLD' to return all attributes of the deleted item\n * @returns The builder instance for method chaining\n */\n public returnValues(returnValues: \"ALL_OLD\"): DeleteBuilder {\n this.options.returnValues = returnValues;\n return this;\n }\n\n /**\n * Generate the DynamoDB command parameters\n */\n private toDynamoCommand(): DeleteCommandParams {\n const { expression, names, values } = prepareExpressionParams(this.options.condition);\n\n return {\n tableName: this.tableName,\n key: this.key,\n conditionExpression: expression,\n expressionAttributeNames: names,\n expressionAttributeValues: values,\n returnValues: this.options.returnValues,\n };\n }\n\n /**\n * Adds this delete operation to a transaction.\n *\n * @example\n * ```ts\n * const transaction = new TransactionBuilder();\n *\n * // Remove dinosaur from old habitat\n * new DeleteBuilder(executor, 'dinosaurs', { id: 'RAPTOR-001' })\n * .condition(op => op.eq('status', 'SEDATED'))\n * .withTransaction(transaction);\n *\n * // Update old habitat occupancy\n * new UpdateBuilder(executor, 'habitats', { id: 'PADDOCK-A' })\n * .add('occupants', -1)\n * .withTransaction(transaction);\n *\n * // Execute transfer atomically\n * await transaction.execute();\n * ```\n *\n * @param transaction - The transaction builder to add this operation to\n */\n public withTransaction(transaction: TransactionBuilder) {\n const command = this.toDynamoCommand();\n\n transaction.deleteWithCommand(command);\n }\n\n /**\n * Adds this delete operation to a batch with optional entity type information.\n *\n * @example Basic Usage\n * ```ts\n * const batch = table.batchBuilder();\n *\n * // Remove multiple dinosaurs in batch\n * dinosaurRepo.delete({ id: 'old-dino-1' }).withBatch(batch);\n * dinosaurRepo.delete({ id: 'old-dino-2' }).withBatch(batch);\n * dinosaurRepo.delete({ id: 'old-dino-3' }).withBatch(batch);\n *\n * // Execute all deletions efficiently\n * await batch.execute();\n * ```\n *\n * @example Typed Usage\n * ```ts\n * const batch = table.batchBuilder<{\n * User: UserEntity;\n * Order: OrderEntity;\n * }>();\n *\n * // Add operations with type information\n * userRepo.delete({ id: 'user-1' }).withBatch(batch, 'User');\n * orderRepo.delete({ id: 'order-1' }).withBatch(batch, 'Order');\n *\n * // Execute batch operations\n * await batch.execute();\n * ```\n *\n * @param batch - The batch builder to add this operation to\n * @param entityType - Optional entity type key for type tracking\n */\n public withBatch<\n TEntities extends Record<string, DynamoItem> = Record<string, DynamoItem>,\n K extends keyof TEntities = keyof TEntities,\n >(batch: BatchBuilder<TEntities>, entityType?: K) {\n const command = this.toDynamoCommand();\n batch.deleteWithCommand(command, entityType);\n }\n\n /**\n * Executes the delete operation against DynamoDB.\n *\n * @example\n * ```ts\n * // Delete with condition and retrieve old values\n * const result = await new DeleteBuilder(executor, 'myTable', { id: '123' })\n * .condition(op => op.eq('status', 'INACTIVE'))\n * .returnValues('ALL_OLD')\n * .execute();\n *\n * if (result.item) {\n * console.log('Deleted item:', result.item);\n * }\n * ```\n *\n * @returns A promise that resolves to an object containing the deleted item's attributes (if returnValues is 'ALL_OLD')\n */\n public async execute(): Promise<{ item?: DynamoItem }> {\n const params = this.toDynamoCommand();\n return this.executor(params);\n }\n\n /**\n * Gets a human-readable representation of the delete command\n * with all expression placeholders replaced by their actual values.\n *\n * @example\n * ```ts\n * const debugInfo = new DeleteBuilder(executor, 'dinosaurs', { id: 'TREX-001' })\n * .condition(op => op.and([\n * op.eq('status', 'SEDATED'),\n * op.eq('location', 'MEDICAL_BAY'),\n * op.gt('sedationLevel', 8)\n * op.eq('version', 1),\n * op.attributeExists('status')\n * ]))\n * .debug();\n *\n * console.log('Delete command:', debugInfo);\n * ```\n *\n * @returns A readable representation of the delete command with resolved expressions\n */\n debug() {\n const command = this.toDynamoCommand();\n return debugCommand(command);\n }\n}\n","import type { Condition, ConditionOperator } from \"../conditions\";\nimport {\n and,\n attributeExists,\n attributeNotExists,\n beginsWith,\n between,\n contains,\n eq,\n gt,\n gte,\n inArray,\n lt,\n lte,\n ne,\n not,\n or,\n} from \"../conditions\";\nimport { prepareExpressionParams } from \"../expression\";\nimport type { DynamoItem } from \"../types\";\nimport { debugCommand } from \"../utils/debug-expression\";\nimport type { BatchBuilder } from \"./batch-builder\";\nimport type { PutCommandParams } from \"./builder-types\";\nimport type { TransactionBuilder } from \"./transaction-builder\";\nimport type { Path, PathType } from \"./types\";\n\n/**\n * Configuration options for DynamoDB put operations.\n */\nexport interface PutOptions {\n /** Optional condition that must be satisfied for the put operation to succeed */\n condition?: Condition;\n /** Determines how to handle the return value of the put operation\n * @options\n * - NONE: No return value\n * - ALL_OLD: Returns the item's previous state if it existed\n * - CONSISTENT: Performs a GET operation after the put to retrieve the item's new state\n * - INPUT: Returns the input values that were passed to the operation\n */\n returnValues?: \"ALL_OLD\" | \"NONE\" | \"CONSISTENT\" | \"INPUT\";\n}\n\ntype PutExecutor<T extends DynamoItem> = (params: PutCommandParams) => Promise<T>;\n\n/**\n * Builder for creating DynamoDB put operations.\n *\n * @example\n * ```typescript\n * // Add new dinosaur\n * const result = await new PutBuilder(executor, {\n * id: 'RAPTOR-001',\n * species: 'Velociraptor',\n * status: 'ACTIVE',\n * stats: {\n * health: 100,\n * age: 5,\n * threatLevel: 8\n * }\n * }, 'dinosaurs').execute();\n *\n * // Create new habitat with conditions\n * const result = await new PutBuilder(executor, {\n * id: 'PADDOCK-C',\n * type: 'CARNIVORE',\n * securityLevel: 'MAXIMUM',\n * capacity: 3,\n * environmentType: 'TROPICAL'\n * }, 'habitats')\n * .condition(op => op.attributeNotExists('id'))\n * .execute();\n * ```\n *\n * @typeParam T - The type of item being put into the table\n */\nexport class PutBuilder<T extends DynamoItem> {\n private readonly item: T;\n private options: PutOptions;\n private readonly executor: PutExecutor<T>;\n private readonly tableName: string;\n\n constructor(executor: PutExecutor<T>, item: T, tableName: string) {\n this.executor = executor;\n this.item = item;\n this.tableName = tableName;\n this.options = {\n returnValues: \"NONE\",\n };\n }\n\n /**\n * Sets multiple attributes of an item using an DynamoItem.\n *\n * @example\n * ```typescript\n * // Update multiple attributes\n * builder.set({\n * species: 'Tyrannosaurus Rex',\n * height: 20,\n * diet: 'CARNIVORE',\n * 'stats.threatLevel': 10\n * });\n * ```\n */\n set(values: Partial<T>): this;\n\n /**\n * Sets a single attribute to a specific value.\n *\n * @example\n * ```typescript\n * // Set simple attributes\n * builder\n * .set('status', 'SLEEPING')\n * .set('lastFeeding', new Date().toISOString());\n *\n * // Set nested attributes\n * builder\n * .set('location.zone', 'RESTRICTED')\n * .set('stats.health', 100);\n * ```\n */\n set<K extends Path<T>>(path: K, value: PathType<T, K>): this;\n set<K extends Path<T>>(valuesOrPath: K | Partial<T>, value?: PathType<T, K>): this {\n if (typeof valuesOrPath === \"object\") {\n Object.assign(this.item, valuesOrPath);\n } else {\n // @ts-expect-error\n this.item[valuesOrPath] = value;\n }\n return this;\n }\n\n /**\n * Adds a condition that must be satisfied for the put operation to succeed.\n *\n * @example\n * ```ts\n * // Ensure item doesn't exist (insert only)\n * builder.condition(op => op.attributeNotExists('id'))\n *\n * // Complex condition with version check\n * builder.condition(op =>\n * op.and([\n * op.attributeExists('id'),\n * op.eq('version', currentVersion),\n * op.eq('status', 'ACTIVE')\n * ])\n * )\n * ```\n *\n * @param condition - Either a Condition object or a callback function that builds the condition\n * @returns The builder instance for method chaining\n */\n /**\n * Adds a condition that must be satisfied for the put operation to succeed.\n *\n * @example\n * ```typescript\n * // Ensure unique dinosaur ID\n * builder.condition(op =>\n * op.attributeNotExists('id')\n * );\n *\n * // Verify habitat requirements\n * builder.condition(op =>\n * op.and([\n * op.eq('securityStatus', 'READY'),\n * op.attributeExists('lastInspection'),\n * op.gt('securityLevel', 5)\n * ])\n * );\n *\n * // Check breeding facility conditions\n * builder.condition(op =>\n * op.and([\n * op.between('temperature', 25, 30),\n * op.between('humidity', 60, 80),\n * op.eq('quarantineStatus', 'CLEAR')\n * ])\n * );\n * ```\n *\n * @param condition - Either a Condition object or a callback function that builds the condition\n * @returns The builder instance for method chaining\n */\n public condition(condition: Condition | ((op: ConditionOperator<T>) => Condition)): this {\n if (typeof condition === \"function\") {\n const conditionOperator: ConditionOperator<T> = {\n eq,\n ne,\n lt,\n lte,\n gt,\n gte,\n between,\n inArray,\n beginsWith,\n contains,\n attributeExists,\n attributeNotExists,\n and,\n or,\n not,\n };\n this.options.condition = condition(conditionOperator);\n } else {\n this.options.condition = condition;\n }\n return this;\n }\n\n /**\n * Sets whether to return the item's previous values (if it existed).\n *\n * @options\n * - NONE: No return value\n * - ALL_OLD: Returns the item's previous state if it existed, no read capacity units are consumed\n * - CONSISTENT: Performs a GET operation after the put to retrieve the item's new state\n * - INPUT: Returns the input values that were passed to the operation\n *\n * @example\n * ```ts\n * // Get previous dinosaur state\n * const result = await builder\n * .returnValues('ALL_OLD')\n * .execute();\n *\n * if (result) {\n * console.log('Previous profile:', {\n * species: result.species,\n * status: result.status,\n * stats: {\n * health: result.stats.health,\n * threatLevel: result.stats.threatLevel\n * }\n * });\n * }\n *\n * // Return input values for create operations\n * const createResult = await builder\n * .returnValues('INPUT')\n * .execute();\n * ```\n *\n * @param returnValues - Use 'ALL_OLD' to return previous values, 'INPUT' to return input values, 'CONSISTENT' for fresh data, or 'NONE' (default).\n * @returns The builder instance for method chaining\n */\n public returnValues(returnValues: \"ALL_OLD\" | \"NONE\" | \"CONSISTENT\" | \"INPUT\"): this {\n this.options.returnValues = returnValues;\n return this;\n }\n\n /**\n * Generate the DynamoDB command parameters\n */\n private toDynamoCommand(): PutCommandParams {\n const { expression, names, values } = prepareExpressionParams(this.options.condition);\n\n return {\n tableName: this.tableName,\n item: this.item,\n conditionExpression: expression,\n expressionAttributeNames: names,\n expressionAttributeValues: values,\n returnValues: this.options.returnValues,\n };\n }\n\n /**\n * Adds this put operation to a transaction.\n *\n * @example\n * ```ts\n * const transaction = new TransactionBuilder();\n *\n * // Add dinosaur to new habitat\n * new PutBuilder(executor, {\n * id: 'TREX-002',\n * location: 'PADDOCK-B',\n * status: 'ACTIVE',\n * transferDate: new Date().toISOString()\n * }, 'dinosaurs')\n * .withTransaction(transaction);\n *\n * // Update habitat records\n * new UpdateBuilder(executor, 'habitats', { id: 'PADDOCK-B' })\n * .add('occupants', 1)\n * .set('lastTransfer', new Date().toISOString())\n * .withTransaction(transaction);\n *\n * // Execute transfer atomically\n * await transaction.execute();\n * ```\n *\n * @param transaction - The transaction builder to add this operation to\n * @returns The builder instance for method chaining\n */\n public withTransaction(transaction: TransactionBuilder): this {\n const command = this.toDynamoCommand();\n transaction.putWithCommand(command);\n\n return this;\n }\n\n /**\n * Adds this put operation to a batch with optional entity type information.\n *\n * @example Basic Usage\n * ```ts\n * const batch = table.batchBuilder();\n *\n * // Add multiple dinosaurs to batch\n * dinosaurRepo.create(newDino1).withBatch(batch);\n * dinosaurRepo.create(newDino2).withBatch(batch);\n * dinosaurRepo.create(newDino3).withBatch(batch);\n *\n * // Execute all operations efficiently\n * await batch.execute();\n * ```\n *\n * @example Typed Usage\n * ```ts\n * const batch = table.batchBuilder<{\n * User: UserEntity;\n * Order: OrderEntity;\n * }>();\n *\n * // Add operations with type information\n * userRepo.create(newUser).withBatch(batch, 'User');\n * orderRepo.create(newOrder).withBatch(batch, 'Order');\n *\n * // Execute and get typed results\n * const result = await batch.execute();\n * const users: UserEntity[] = result.reads.itemsByType.User;\n * ```\n *\n * @param batch - The batch builder to add this operation to\n * @param entityType - Optional entity type key for type tracking\n */\n public withBatch<\n TEntities extends Record<string, DynamoItem> = Record<string, DynamoItem>,\n K extends keyof TEntities = keyof TEntities,\n >(batch: BatchBuilder<TEntities>, entityType?: K) {\n const command = this.toDynamoCommand();\n batch.putWithCommand(command, entityType);\n }\n\n /**\n * Executes the put operation against DynamoDB.\n *\n * @example\n * ```ts\n * try {\n * // Put with condition and return old values\n * const result = await new PutBuilder(executor, newItem, 'myTable')\n * .condition(op => op.eq('version', 1))\n * .returnValues('ALL_OLD')\n * .execute();\n *\n * console.log('Put successful, old item:', result);\n * } catch (error) {\n * // Handle condition check failure or other errors\n * console.error('Put failed:', error);\n * }\n * ```\n *\n * @returns A promise that resolves to the operation result (type depends on returnValues setting)\n * @throws Will throw an error if the condition check fails or other DynamoDB errors occur\n */\n public async execute(): Promise<T | undefined> {\n const params = this.toDynamoCommand();\n return this.executor(params);\n }\n\n /**\n * Gets a human-readable representation of the put command\n * with all expression placeholders replaced by their actual values.\n *\n * @example\n * ```ts\n * const debugInfo = new PutBuilder(executor, {\n * id: 'RAPTOR-003',\n * species: 'Velociraptor',\n * status: 'QUARANTINE',\n * stats: {\n * health: 100,\n * aggressionLevel: 7,\n * age: 2\n * }\n * }, 'dinosaurs')\n * .condition(op =>\n * op.and([\n * op.attributeNotExists('id'),\n * op.eq('quarantineStatus', 'READY'),\n * op.gt('securityLevel', 8)\n * ])\n * )\n * .debug();\n *\n * console.log('Dinosaur transfer command:', debugInfo);\n * ```\n *\n * @returns A readable representation of the put command with resolved expressions\n */\n public debug() {\n const command = this.toDynamoCommand();\n return debugCommand(command);\n }\n}\n","import type { DynamoItem, TableConfig } from \"../types\";\nimport type { PaginationResult, QueryBuilderInterface } from \"./builder-types\";\n\n/**\n * A utility class for handling DynamoDB pagination.\n * Use this class when you need to:\n * - Browse large collections of dinosaurs\n * - Review extensive security logs\n * - Analyze habitat inspection history\n * - Process feeding schedules\n *\n * The paginator maintains internal state and automatically handles:\n * - Page boundaries\n * - Result set limits\n * - Continuation tokens\n *\n * @example\n * ```typescript\n * // List all velociraptors with pagination\n * const paginator = new QueryBuilder(executor, eq('species', 'Velociraptor'))\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .paginate(10);\n *\n * // Process each page of dinosaurs\n * while (paginator.hasNextPage()) {\n * const page = await paginator.getNextPage();\n * console.log(`Processing page ${page.page} of velociraptors`);\n *\n * for (const raptor of page.items) {\n * console.log(`- ${raptor.id}: Health=${raptor.stats.health}`);\n * }\n * }\n * ```\n *\n * @typeParam T - The type of items being paginated\n * @typeParam TConfig - The table configuration type\n */\nexport class Paginator<T extends DynamoItem, TConfig extends TableConfig = TableConfig> {\n private queryBuilder: QueryBuilderInterface<T, TConfig>;\n private readonly pageSize?: number;\n private currentPage = 0;\n private lastEvaluatedKey?: DynamoItem;\n private hasMorePages = true;\n private totalItemsRetrieved = 0;\n private readonly overallLimit?: number;\n\n constructor(queryBuilder: QueryBuilderInterface<T, TConfig>, pageSize?: number) {\n this.queryBuilder = queryBuilder;\n this.pageSize = pageSize;\n // Store the overall limit from the query builder if it exists\n this.overallLimit = queryBuilder.getLimit();\n }\n\n /**\n * Gets the current page number (1-indexed).\n *\n * @example\n * ```ts\n * const paginator = new QueryBuilder(executor, eq('species', 'Tyrannosaurus'))\n * .paginate(5);\n *\n * await paginator.getNextPage();\n * console.log(`Reviewing T-Rex group ${paginator.getCurrentPage()}`);\n * ```\n *\n * @returns The current page number, starting from 1\n */\n public getCurrentPage(): number {\n return this.currentPage;\n }\n\n /**\n * Checks if there are more pages of dinosaurs or habitats to process.\n *\n * This method takes into account both:\n * - DynamoDB's lastEvaluatedKey mechanism\n * - Any overall limit set on the query\n *\n * @example\n * ```ts\n * // Process all security incidents\n * const paginator = new QueryBuilder(executor, eq('type', 'SECURITY_BREACH'))\n * .sortDescending()\n * .paginate(10);\n *\n * while (paginator.hasNextPage()) {\n * const page = await paginator.getNextPage();\n * for (const incident of page.items) {\n * await processSecurityBreach(incident);\n * }\n * console.log(`Processed incidents page ${page.page}`);\n * }\n * ```\n *\n * @returns true if there are more pages available, false otherwise\n */\n public hasNextPage(): boolean {\n // If we have an overall limit and we've already retrieved that many items, there are no more pages\n if (this.overallLimit !== undefined && this.totalItemsRetrieved >= this.overallLimit) {\n return false;\n }\n return this.hasMorePages;\n }\n\n /**\n * Retrieves the next page of dinosaurs or habitats from DynamoDB.\n *\n * This method handles:\n * - Automatic continuation between groups\n * - Respect for park capacity limits\n * - Group size adjustments for safety\n *\n * @example\n * ```ts\n * const paginator = new QueryBuilder(executor, eq('species', 'Velociraptor'))\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .paginate(5);\n *\n * // Check first raptor group\n * const page1 = await paginator.getNextPage();\n * console.log(`Found ${page1.items.length} active raptors`);\n *\n * // Continue inspection if more groups exist\n * if (page1.hasNextPage) {\n * const page2 = await paginator.getNextPage();\n * console.log(`Inspecting raptor group ${page2.page}`);\n *\n * for (const raptor of page2.items) {\n * await performHealthCheck(raptor);\n * }\n * }\n * ```\n *\n * @returns A promise that resolves to a PaginationResult containing:\n * - items: The dinosaurs/habitats for this page\n * - hasNextPage: Whether more groups exist\n * - page: The current group number\n * - lastEvaluatedKey: DynamoDB's continuation token\n */\n public async getNextPage(): Promise<PaginationResult<T>> {\n if (!this.hasNextPage()) {\n return {\n items: [],\n hasNextPage: false,\n page: this.currentPage,\n };\n }\n\n // Calculate how many items to fetch for this page\n let effectivePageSize = this.pageSize;\n\n // If we have an overall limit, make sure we don't fetch more than what's left\n if (this.overallLimit !== undefined) {\n const remainingItems = this.overallLimit - this.totalItemsRetrieved;\n if (remainingItems <= 0) {\n return {\n items: [],\n hasNextPage: false,\n page: this.currentPage,\n };\n }\n if (effectivePageSize !== undefined) {\n effectivePageSize = Math.min(effectivePageSize, remainingItems);\n } else {\n effectivePageSize = remainingItems;\n }\n }\n\n // Clone the query builder to avoid modifying the original\n const query = this.queryBuilder.clone();\n\n // Only set limit if we have an effective page size (not automatic paging)\n if (effectivePageSize !== undefined) {\n query.limit(effectivePageSize);\n }\n\n // Apply the last evaluated key if we have one\n if (this.lastEvaluatedKey) {\n query.startFrom(this.lastEvaluatedKey);\n }\n\n // Execute the query and get the first page from the generator\n const generator = await query.execute();\n const items: T[] = [];\n\n // Take items up to the effective page size\n let itemCount = 0;\n for await (const item of generator) {\n if (effectivePageSize !== undefined && itemCount >= effectivePageSize) {\n break;\n }\n items.push(item);\n itemCount++;\n }\n\n // Get the last evaluated key from the generator\n const lastEvaluatedKey = generator.getLastEvaluatedKey();\n\n const result = { items, lastEvaluatedKey };\n\n // Update pagination state\n this.currentPage += 1;\n this.lastEvaluatedKey = result.lastEvaluatedKey;\n this.totalItemsRetrieved += result.items.length;\n\n // Determine if there are more pages\n // We have more pages if:\n // 1. DynamoDB returned a lastEvaluatedKey AND\n // 2. We haven't hit our overall limit (if one exists)\n this.hasMorePages =\n !!result.lastEvaluatedKey && (this.overallLimit === undefined || this.totalItemsRetrieved < this.overallLimit);\n\n return {\n items: result.items,\n lastEvaluatedKey: result.lastEvaluatedKey,\n hasNextPage: this.hasNextPage(),\n page: this.currentPage,\n };\n }\n\n /**\n * Gets all remaining dinosaurs or habitats and combines them into a single array.\n *\n * @example\n * ```ts\n * // Get complete carnivore inventory\n * const paginator = new QueryBuilder(executor, eq('diet', 'CARNIVORE'))\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .paginate(10);\n *\n * try {\n * const allCarnivores = await paginator.getAllPages();\n * console.log(`Park contains ${allCarnivores.length} active carnivores`);\n *\n * // Calculate total threat level\n * const totalThreat = allCarnivores.reduce(\n * (sum, dino) => sum + dino.stats.threatLevel,\n * 0\n * );\n * console.log(`Total threat level: ${totalThreat}`);\n * } catch (error) {\n * console.error('Failed to complete carnivore census:', error);\n * }\n * ```\n *\n * @returns A promise that resolves to an array containing all remaining items\n */\n public async getAllPages(): Promise<T[]> {\n const allItems: T[] = [];\n\n while (this.hasNextPage()) {\n const result = await this.getNextPage();\n allItems.push(...result.items);\n }\n\n return allItems;\n }\n}\n","import {\n and,\n attributeExists,\n attributeNotExists,\n beginsWith,\n between,\n type Condition,\n type ConditionOperator,\n contains,\n eq,\n gt,\n gte,\n inArray,\n lt,\n lte,\n ne,\n not,\n or,\n} from \"../conditions\";\nimport type { DynamoItem, GSINames, TableConfig } from \"../types\";\nimport type { FilterBuilderInterface } from \"./builder-types\";\nimport { Paginator } from \"./paginator\";\nimport type { ResultIterator } from \"./result-iterator\";\nimport type { Path } from \"./types\";\n\n/**\n * Configuration options for DynamoDB filter operations.\n * These are common options shared between query and scan operations.\n */\nexport interface FilterOptions {\n /** Filter conditions applied to results */\n filter?: Condition;\n /** Maximum number of items to return */\n limit?: number;\n /** Name of the Global Secondary Index to use */\n indexName?: string;\n /** Whether to use strongly consistent reads */\n consistentRead?: boolean;\n /** List of attributes to return in the result */\n projection?: string[];\n /** Token for starting the operation from a specific point */\n lastEvaluatedKey?: DynamoItem;\n}\n\n/**\n * Abstract base builder for creating DynamoDB filter operations.\n * This class provides common functionality for both Query and Scan operations.\n *\n * The builder supports:\n * - Type-safe GSI selection\n * - Complex filter conditions\n * - Pagination\n * - Consistent reads\n * - Attribute projection\n *\n * @typeParam T - The type of items being filtered\n * @typeParam TConfig - The table configuration type for type-safe GSI selection\n */\nexport abstract class FilterBuilder<T extends DynamoItem, TConfig extends TableConfig = TableConfig>\n implements FilterBuilderInterface<T, TConfig>\n{\n protected options: FilterOptions = {};\n protected selectedFields: Set<string> = new Set();\n\n /**\n * Sets the maximum number of items to return.\n *\n * Note: This limit applies to the items that match the key condition\n * before any filter expressions are applied.\n *\n * @example\n * ```typescript\n * // Get first 10 dinosaurs\n * const result = await builder\n * .limit(10)\n * .execute();\n * ```\n *\n * @param limit - Maximum number of items to return\n * @returns The builder instance for method chaining\n */\n limit(limit: number): this {\n this.options.limit = limit;\n return this;\n }\n\n /**\n * Gets the current limit set on the operation.\n * This is used internally by the paginator to manage result sets.\n *\n * @returns The current limit or undefined if no limit is set\n */\n getLimit(): number | undefined {\n return this.options.limit;\n }\n\n /**\n * Specifies a Global Secondary Index (GSI) to use for the operation.\n *\n * @example\n * ```typescript\n * // Find all dinosaurs of a specific species\n * builder\n * .useIndex('species-status-index')\n * .filter(op => op.eq('status', 'ACTIVE'));\n *\n * // Search high-security habitats\n * builder\n * .useIndex('security-level-index')\n * .filter(op =>\n * op.and([\n * op.gt('securityLevel', 8),\n * op.eq('status', 'OPERATIONAL')\n * ])\n * );\n * ```\n *\n * @param indexName - The name of the GSI to use (type-safe based on table configuration)\n * @returns The builder instance for method chaining\n */\n useIndex<I extends GSINames<TConfig>>(indexName: I): this {\n this.options.indexName = indexName as string;\n return this;\n }\n\n /**\n * Sets whether to use strongly consistent reads for the operation.\n *\n * Note:\n * - Consistent reads are not available on GSIs\n * - Consistent reads consume twice the throughput\n * - Default is eventually consistent reads\n *\n * @example\n * ```typescript\n * // Check immediate dinosaur status\n * const result = await builder\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .consistentRead()\n * .execute();\n *\n * // Monitor security breaches\n * const result = await builder\n * .useIndex('primary-index')\n * .consistentRead(isEmergencyMode)\n * .execute();\n * ```\n *\n * @param consistentRead - Whether to use consistent reads (defaults to true)\n * @returns The builder instance for method chaining\n */\n consistentRead(consistentRead = true): this {\n this.options.consistentRead = consistentRead;\n return this;\n }\n\n /**\n * Adds a filter expression to refine the operation results.\n *\n * @example\n * ```typescript\n * // Find aggressive carnivores\n * builder.filter(op =>\n * op.and([\n * op.eq('diet', 'CARNIVORE'),\n * op.gt('aggressionLevel', 7),\n * op.eq('status', 'ACTIVE')\n * ])\n * );\n *\n * // Search suitable breeding habitats\n * builder.filter(op =>\n * op.and([\n * op.between('temperature', 25, 30),\n * op.lt('currentOccupants', 3),\n * op.eq('quarantineStatus', 'CLEAR')\n * ])\n * );\n * ```\n *\n * @param condition - Either a Condition object or a callback function that builds the condition\n * @returns The builder instance for method chaining\n */\n filter(condition: Condition | ((op: ConditionOperator<T>) => Condition)): this {\n const newCondition = typeof condition === \"function\" ? condition(this.getConditionOperator()) : condition;\n\n if (this.options.filter) {\n // If the existing filter is already an 'and' condition, flatten the new condition into it\n if (this.options.filter.type === \"and\" && this.options.filter.conditions) {\n // If the new condition is also an 'and' condition, flatten its conditions\n if (newCondition.type === \"and\" && newCondition.conditions) {\n this.options.filter = {\n type: \"and\",\n conditions: [...this.options.filter.conditions, ...newCondition.conditions],\n };\n } else {\n this.options.filter = {\n type: \"and\",\n conditions: [...this.options.filter.conditions, newCondition],\n };\n }\n } else {\n // If the new condition is an 'and' condition, flatten it\n if (newCondition.type === \"and\" && newCondition.conditions) {\n this.options.filter = {\n type: \"and\",\n conditions: [this.options.filter, ...newCondition.conditions],\n };\n } else {\n this.options.filter = and(this.options.filter, newCondition);\n }\n }\n } else {\n this.options.filter = newCondition;\n }\n\n return this;\n }\n\n private getConditionOperator(): ConditionOperator<T> {\n return {\n eq,\n ne,\n lt,\n lte,\n gt,\n gte,\n between,\n inArray,\n beginsWith,\n contains,\n attributeExists,\n attributeNotExists,\n and,\n or,\n not,\n };\n }\n\n /**\n * Specifies which attributes to return in the results.\n *\n * @example\n * ```typescript\n * // Get basic dinosaur info\n * builder.select([\n * 'species',\n * 'status',\n * 'stats.health',\n * 'stats.aggressionLevel'\n * ]);\n *\n * // Monitor habitat conditions\n * builder\n * .select('securityStatus')\n * .select([\n * 'currentOccupants',\n * 'temperature',\n * 'lastInspectionDate'\n * ]);\n * ```\n *\n * @param fields - A single field name or an array of field names to return\n * @returns The builder instance for method chaining\n */\n select<K extends Path<T>>(fields: K | K[]): this {\n if (typeof fields === \"string\") {\n this.selectedFields.add(fields);\n } else if (Array.isArray(fields)) {\n for (const field of fields) {\n this.selectedFields.add(field);\n }\n }\n\n this.options.projection = Array.from(this.selectedFields);\n return this;\n }\n\n /**\n * Creates a paginator that handles DynamoDB pagination automatically.\n * The paginator handles:\n * - Tracking the last evaluated key\n * - Managing page boundaries\n * - Respecting overall query limits\n *\n * @example\n * ```typescript\n * // Create a paginator for dinosaur records with specific page size\n * const paginator = builder\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .paginate(10);\n *\n * // Create a paginator with automatic DynamoDB paging (no page size limit)\n * const autoPaginator = builder\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .paginate();\n *\n * // Process pages of dinosaur results\n * while (paginator.hasNextPage()) {\n * const page = await paginator.getNextPage();\n * console.log(`Processing page ${page.page}, count: ${page.items.length}`);\n * // Process dinosaur data\n * }\n * ```\n *\n * @param pageSize - The number of items to return per page. If not provided, DynamoDB will automatically determine page sizes.\n * @returns A Paginator instance that manages the pagination state\n * @see Paginator for more pagination control options\n */\n paginate(pageSize?: number): Paginator<T, TConfig> {\n return new Paginator<T, TConfig>(this, pageSize);\n }\n\n /**\n * Sets the starting point using a previous lastEvaluatedKey.\n *\n * Note: This method is typically used for manual pagination.\n * For automatic pagination, use the paginate() method instead.\n *\n * @example\n * ```typescript\n * // First batch of dinosaurs\n * const result1 = await builder\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .limit(5)\n * .execute();\n *\n * const lastKey = result1.getLastEvaluatedKey();\n * if (lastKey) {\n * // Continue listing dinosaurs\n * const result2 = await builder\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .startFrom(lastKey)\n * .limit(5)\n * .execute();\n *\n * const items = await result2.toArray();\n * console.log('Additional dinosaurs:', items);\n * }\n * ```\n *\n * @param lastEvaluatedKey - The exclusive start key from a previous result\n * @returns The builder instance for method chaining\n */\n startFrom(lastEvaluatedKey: DynamoItem): this {\n this.options.lastEvaluatedKey = lastEvaluatedKey;\n return this;\n }\n\n /**\n * Creates a deep clone of this builder instance.\n *\n * This is particularly useful when:\n * - Implementing pagination (used internally by paginate())\n * - Creating operation templates\n * - Running multiple variations of an operation\n *\n * @example\n * ```typescript\n * // Create base dinosaur query\n * const baseBuilder = builder\n * .useIndex('status-index')\n * .select(['id', 'status', 'location']);\n *\n * // Check active dinosaurs\n * const activeRaptors = baseBuilder.clone()\n * .filter(op => op.eq('status', 'HUNTING'))\n * .execute();\n *\n * // Check contained dinosaurs\n * const containedRaptors = baseBuilder.clone()\n * .filter(op => op.eq('status', 'CONTAINED'))\n * .execute();\n * ```\n *\n * @returns A new builder instance with the same configuration\n */\n abstract clone(): FilterBuilderInterface<T, TConfig>;\n\n /**\n * Executes the operation against DynamoDB and returns a generator that behaves like an array.\n * This method must be implemented by subclasses to handle\n * their specific execution logic.\n */\n abstract execute(): Promise<ResultIterator<T, TConfig>>;\n}\n","import type { DynamoItem, TableConfig } from \"../types\";\nimport type { QueryBuilderInterface } from \"./builder-types\";\n\n/**\n * Function type for executing DynamoDB operations and returning raw results.\n */\ntype DirectExecutor<T extends DynamoItem> = () => Promise<{ items: T[]; lastEvaluatedKey?: DynamoItem }>;\n\n/**\n * Minimal result generator that provides async iteration over DynamoDB results with automatic pagination.\n *\n * @example\n * ```typescript\n * const results = await queryBuilder.execute();\n *\n * for await (const item of results) {\n * console.log(item);\n * }\n * ```\n */\nexport class ResultIterator<T extends DynamoItem, TConfig extends TableConfig = TableConfig> {\n private lastEvaluatedKey?: DynamoItem | null;\n private itemsYielded = 0;\n private readonly overallLimit?: number;\n\n constructor(\n private queryBuilder: QueryBuilderInterface<T, TConfig>,\n private directExecutor: DirectExecutor<T>,\n ) {\n this.overallLimit = queryBuilder.getLimit();\n }\n\n /**\n * Async iterator with automatic pagination\n */\n async *[Symbol.asyncIterator](): AsyncIterableIterator<T> {\n let hasMorePages = true;\n\n while (hasMorePages) {\n const result = await this.directExecutor();\n\n for (const item of result.items) {\n // Check if we've reached the overall limit\n if (this.overallLimit !== undefined && this.itemsYielded >= this.overallLimit) {\n return;\n }\n\n yield item;\n this.itemsYielded++;\n }\n\n // Update lastEvaluatedKey, but preserve the last non-null value\n if (result.lastEvaluatedKey !== null && result.lastEvaluatedKey !== undefined) {\n this.lastEvaluatedKey = result.lastEvaluatedKey;\n // Update the query builder's options for the next iteration\n this.queryBuilder.startFrom(result.lastEvaluatedKey);\n } else if (result.lastEvaluatedKey === null) {\n // Only set to null if we haven't seen a lastEvaluatedKey yet\n if (this.lastEvaluatedKey === undefined) {\n this.lastEvaluatedKey = null;\n }\n }\n\n // Stop if we've reached the overall limit or no more pages\n hasMorePages =\n !!result.lastEvaluatedKey && (this.overallLimit === undefined || this.itemsYielded < this.overallLimit);\n }\n }\n\n /**\n * Convert to array (loads all pages).\n *\n * ```ts\n * const result = await table.query({ pk: \"foo\" }).execute();\n * const allItemsFromDynamo = await result.toArray();\n * ```\n *\n * Note: This will load all pages into memory. For large datasets, consider using async iteration instead.\n *```ts\n * const result = await table.query({ pk: \"foo\" }).execute();\n * for await (const item of result) {\n * // Process each item\n * }\n * ```\n */\n async toArray(): Promise<T[]> {\n const items: T[] = [];\n for await (const item of this) {\n items.push(item);\n }\n return items;\n }\n\n /**\n * Get the last evaluated key\n */\n getLastEvaluatedKey(): DynamoItem | undefined {\n return this.lastEvaluatedKey === null ? undefined : this.lastEvaluatedKey;\n }\n}\n","import type { Condition } from \"../conditions\";\nimport type { DynamoItem, TableConfig } from \"../types\";\nimport type { QueryBuilderInterface } from \"./builder-types\";\nimport { FilterBuilder, type FilterOptions } from \"./filter-builder\";\nimport { ResultIterator } from \"./result-iterator\";\n\n/**\n * Configuration options for DynamoDB query operations.\n * Extends the base FilterOptions with query-specific options.\n */\nexport interface QueryOptions extends FilterOptions {\n /** Condition for the sort key in the table or index */\n sortKeyCondition?: Condition;\n /** Direction of sort key traversal (true for ascending, false for descending) */\n scanIndexForward?: boolean;\n}\n\n/**\n * Function type for executing DynamoDB query operations.\n * @typeParam T - The type of items being queried\n */\ntype QueryExecutor<T extends DynamoItem> = (\n keyCondition: Condition,\n options: QueryOptions,\n) => Promise<{ items: T[]; lastEvaluatedKey?: Record<string, unknown> }>;\n\n/**\n * Builder for creating DynamoDB query operations.\n *\n * The builder supports:\n * - Type-safe GSI selection\n * - Complex filter conditions\n * - Automatic pagination handling\n * - Consistent reads\n * - Forward and reverse sorting\n *\n * @example\n * ```typescript\n * // Simple query\n * const result = await new QueryBuilder(executor, eq('userId', '123'))\n * .execute();\n *\n * // Complex query with GSI and filtering\n * const result = await new QueryBuilder(executor, eq('status', 'ACTIVE'))\n * .useIndex('status-index')\n * .filter(op => op.beginsWith('name', 'John'))\n * .select(['id', 'name', 'email'])\n * .sortDescending()\n * .limit(10)\n * .execute();\n *\n * // Query with pagination\n * const paginator = new QueryBuilder(executor, eq('type', 'order'))\n * .paginate(25);\n *\n * while (paginator.hasNextPage()) {\n * const page = await paginator.getNextPage();\n * // Process page.items\n * }\n * ```\n *\n * @typeParam T - The type of items being queried\n * @typeParam TConfig - The table configuration type for type-safe GSI selection\n */\nexport class QueryBuilder<T extends DynamoItem, TConfig extends TableConfig = TableConfig>\n extends FilterBuilder<T, TConfig>\n implements QueryBuilderInterface<T, TConfig>\n{\n private readonly keyCondition: Condition;\n protected override options: QueryOptions = {};\n protected readonly executor: QueryExecutor<T>;\n\n constructor(executor: QueryExecutor<T>, keyCondition: Condition) {\n super();\n this.executor = executor;\n this.keyCondition = keyCondition;\n }\n\n /**\n * Sets the maximum number of items to return from the query.\n *\n * Note: This is the default behavior if no sort order is specified.\n *\n * @example\n * ```typescript\n * // Get orders in chronological order\n * const result = await new QueryBuilder(executor, eq('userId', '123'))\n * .sortAscending()\n * .execute();\n *\n * // Get events from oldest to newest\n * const result = await new QueryBuilder(executor, eq('entityId', 'order-123'))\n * .useIndex('entity-timestamp-index')\n * .sortAscending()\n * .execute();\n * ```\n *\n * @returns The builder instance for method chaining\n */\n /**\n * Sets the query to return items in ascending order by sort key.\n *\n * @example\n * ```typescript\n * // List dinosaurs by age\n * const result = await new QueryBuilder(executor, eq('species', 'Velociraptor'))\n * .useIndex('age-index')\n * .sortAscending()\n * .execute();\n *\n * // View incidents chronologically\n * const result = await new QueryBuilder(executor, eq('type', 'SECURITY_BREACH'))\n * .useIndex('date-index')\n * .sortAscending()\n * .execute();\n * ```\n *\n * @returns The builder instance for method chaining\n */\n sortAscending(): this {\n this.options.scanIndexForward = true;\n return this;\n }\n\n /**\n * Sets the query to return items in descending order by sort key.\n *\n * @example\n * ```typescript\n * // Get most recent security incidents\n * const result = await new QueryBuilder(executor, eq('type', 'SECURITY_BREACH'))\n * .useIndex('date-index')\n * .sortDescending()\n * .limit(10)\n * .execute();\n *\n * // Check latest dinosaur activities\n * const result = await new QueryBuilder(executor, eq('species', 'Velociraptor'))\n * .useIndex('activity-time-index')\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .sortDescending()\n * .execute();\n * ```\n *\n * @returns The builder instance for method chaining\n */\n sortDescending(): this {\n this.options.scanIndexForward = false;\n return this;\n }\n\n /**\n * Creates a deep clone of this QueryBuilder instance.\n *\n * This is particularly useful when:\n * - Implementing pagination (used internally by paginate())\n * - Creating query templates\n * - Running multiple variations of a query\n *\n * @example\n * ```typescript\n * // Create base dinosaur query\n * const baseQuery = new QueryBuilder(executor, eq('species', 'Velociraptor'))\n * .useIndex('status-index')\n * .select(['id', 'status', 'location']);\n *\n * // Check active dinosaurs\n * const activeRaptors = baseQuery.clone()\n * .filter(op => op.eq('status', 'HUNTING'))\n * .execute();\n *\n * // Check contained dinosaurs\n * const containedRaptors = baseQuery.clone()\n * .filter(op => op.eq('status', 'CONTAINED'))\n * .execute();\n *\n * // Check sedated dinosaurs\n * const sedatedRaptors = baseQuery.clone()\n * .filter(op => op.eq('status', 'SEDATED'))\n * .execute();\n * ```\n *\n * @returns A new QueryBuilder instance with the same configuration\n */\n clone(): QueryBuilder<T, TConfig> {\n const clone = new QueryBuilder<T, TConfig>(this.executor, this.keyCondition);\n clone.options = {\n ...this.options,\n filter: this.deepCloneFilter(this.options.filter),\n };\n clone.selectedFields = new Set(this.selectedFields);\n return clone;\n }\n\n private deepCloneFilter(filter: Condition | undefined): Condition | undefined {\n if (!filter) return filter;\n if (filter.type === \"and\" || filter.type === \"or\") {\n return {\n ...filter,\n conditions: filter.conditions\n ?.map((condition) => this.deepCloneFilter(condition))\n .filter((c): c is Condition => c !== undefined),\n };\n }\n return { ...filter };\n }\n\n /**\n * Executes the query against DynamoDB and returns a generator that behaves like an array.\n *\n * The generator automatically handles pagination and provides array-like methods\n * for processing results efficiently without loading everything into memory at once.\n *\n * @example\n * ```typescript\n * try {\n * // Find active carnivores with automatic pagination\n * const results = await new QueryBuilder(executor, eq('habitatId', 'PADDOCK-A'))\n * .useIndex('species-status-index')\n * .filter(op =>\n * op.and([\n * op.eq('diet', 'CARNIVORE'),\n * op.eq('status', 'ACTIVE'),\n * op.gt('aggressionLevel', 7)\n * ])\n * )\n * .sortDescending()\n * .execute();\n *\n * // Use like an array with automatic pagination\n * for await (const dinosaur of results) {\n * console.log(`Processing ${dinosaur.name}`);\n * }\n *\n * // Or convert to array and use array methods\n * const allItems = await results.toArray();\n * const dangerousOnes = allItems.filter(dino => dino.aggressionLevel > 9);\n * const totalCount = allItems.length;\n * } catch (error) {\n * console.error('Security scan failed:', error);\n * }\n * ```\n *\n * @returns A promise that resolves to a ResultGenerator that behaves like an array\n */\n async execute(): Promise<ResultIterator<T, TConfig>> {\n const directExecutor = () => this.executor(this.keyCondition, this.options);\n return new ResultIterator(this, directExecutor);\n }\n}\n","import type { TransactionItem } from \"../builders/builder-types\";\nimport { debugCommand } from \"./debug-expression\";\n\n/**\n * Utility function to create a human-readable representation of a transaction item\n * by replacing all expression placeholders with their actual values.\n *\n * @param item The transaction item to debug\n * @returns A readable representation of the transaction item\n */\nexport function debugTransactionItem(item: TransactionItem): Record<string, unknown> {\n const result: Record<string, unknown> = {\n type: item.type,\n tableName: item.params.tableName,\n };\n\n // Add key if present\n if (\"key\" in item.params) {\n result.key = item.params.key;\n }\n\n // Add item if present (for Put operations)\n if (item.type === \"Put\") {\n result.item = item.params.item;\n }\n\n // Add readable expressions based on operation type\n switch (item.type) {\n case \"Put\":\n case \"Delete\":\n case \"ConditionCheck\":\n result.readable = debugCommand(item.params).readable;\n break;\n case \"Update\":\n result.readable = debugCommand(item.params).readable;\n break;\n }\n\n return result;\n}\n\n/**\n * Utility function to create a human-readable representation of all transaction items\n * in a transaction by replacing all expression placeholders with their actual values.\n *\n * @param items Array of transaction items to debug\n * @returns An array of readable representations of the transaction items\n */\nexport function debugTransaction(items: TransactionItem[]): Record<string, unknown>[] {\n return items.map((item) => debugTransactionItem(item));\n}\n","import type { TransactWriteCommandInput } from \"@aws-sdk/lib-dynamodb\";\nimport type { Condition, PrimaryKeyWithoutExpression } from \"../conditions\";\nimport { prepareExpressionParams } from \"../expression\";\nimport type { DynamoItem } from \"../types\";\nimport { debugTransaction } from \"../utils/debug-transaction\";\nimport type {\n ConditionCheckCommandParams,\n DeleteCommandParams,\n PutCommandParams,\n TransactionItem,\n UpdateCommandParams,\n} from \"./builder-types\";\n\n/**\n * Configuration options for DynamoDB transactions.\n */\nexport interface TransactionOptions {\n /** Unique identifier for the transaction request (idempotency token) */\n clientRequestToken?: string;\n /** Level of consumed capacity details to return */\n returnConsumedCapacity?: \"INDEXES\" | \"TOTAL\" | \"NONE\";\n /** Whether to return item collection metrics */\n returnItemCollectionMetrics?: \"SIZE\" | \"NONE\";\n}\n\n/**\n * Configuration for table indexes used in duplicate detection.\n * Defines the key structure for checking uniqueness constraints.\n */\ninterface IndexConfig {\n /** The partition key attribute name */\n partitionKey: string;\n /** Optional sort key attribute name */\n sortKey?: string;\n}\n\n/**\n * Function type for executing DynamoDB transaction operations.\n * @param params - The complete transaction command input\n * @returns A promise that resolves when the transaction completes\n */\nexport type TransactionExecutor = (params: TransactWriteCommandInput) => Promise<void>;\n\n/**\n * Builder for creating and executing DynamoDB transactions.\n * Use this builder when you need to:\n * - Perform multiple operations atomically\n * - Ensure data consistency across operations\n * - Implement complex business logic that requires atomic updates\n * - Prevent duplicate items across tables\n *\n * The builder supports:\n * - Put operations (insert/replace items)\n * - Delete operations\n * - Update operations\n * - Condition checks\n * - Duplicate detection\n * - Transaction-wide options\n *\n * @example\n * ```typescript\n * // Create a transaction with multiple operations\n * const transaction = new TransactionBuilder(executor, {\n * partitionKey: 'id',\n * sortKey: 'type'\n * });\n *\n * // Add a new order\n * transaction.put('orders', {\n * orderId: '123',\n * status: 'PENDING'\n * });\n *\n * // Update inventory with condition\n * transaction.update(\n * 'inventory',\n * { productId: 'ABC' },\n * 'set quantity = quantity - :amount',\n * { ':amount': 1 },\n * op => op.gte('quantity', 1)\n * );\n *\n * // Execute the transaction atomically\n * await transaction.execute();\n * ```\n *\n * Note: DynamoDB transactions have some limitations:\n * - Maximum 25 operations per transaction\n * - All operations must be in the same AWS region\n * - Cannot include table scans or queries\n */\nexport class TransactionBuilder {\n private items: TransactionItem[] = [];\n private options: TransactionOptions = {};\n private indexConfig: IndexConfig;\n private readonly executor: TransactionExecutor;\n\n constructor(executor: TransactionExecutor, indexConfig: IndexConfig) {\n this.executor = executor;\n this.indexConfig = indexConfig;\n }\n\n /**\n * Checks if an item with the same primary key already exists in the transaction\n * @private\n */\n private checkForDuplicateItem(tableName: string, newItem: DynamoItem): void {\n const pkName = this.indexConfig.partitionKey;\n const skName = this.indexConfig.sortKey ?? \"\";\n\n // Extract the primary key values from the provided key\n const pkValue = newItem[pkName];\n const skValue = skName ? newItem[skName] : undefined;\n\n if (!pkValue) {\n throw new Error(`Primary key value for '${pkName}' is missing`);\n }\n\n const duplicateItem = this.items.find((item) => {\n // Get the key from the item based on its type\n let itemKey: Record<string, unknown> | undefined;\n let itemTableName: string | undefined;\n\n switch (item.type) {\n case \"Put\":\n itemTableName = item.params.tableName;\n // For Put operations, the key is part of the item\n itemKey = item.params.item;\n break;\n case \"Update\":\n case \"Delete\":\n case \"ConditionCheck\":\n itemTableName = item.params.tableName;\n itemKey = item.params.key;\n break;\n }\n\n // Check if the table name and keys match\n if (itemTableName === tableName && itemKey) {\n const itemPkValue = itemKey[pkName];\n const itemSkValue = skName ? itemKey[skName] : undefined;\n\n // Match if partition keys match and either both sort keys match or both are undefined\n if (itemPkValue === pkValue) {\n if (skValue === undefined && itemSkValue === undefined) {\n return true;\n }\n if (skValue !== undefined && itemSkValue !== undefined && skValue === itemSkValue) {\n return true;\n }\n }\n }\n\n return false;\n });\n\n if (duplicateItem) {\n throw new Error(\n `Duplicate item detected in transaction: Table=${tableName}, ${pkName}=${String(pkValue)}, ${skName}=${skValue !== undefined ? String(skValue) : \"undefined\"}. DynamoDB transactions do not allow multiple operations on the same item.`,\n );\n }\n }\n\n createKeyForPrimaryIndex(key: PrimaryKeyWithoutExpression) {\n // Turn the pk/sk into the key object\n const keyCondition = {\n [this.indexConfig.partitionKey]: key.pk,\n };\n\n if (this.indexConfig.sortKey) {\n if (key.sk === undefined) {\n throw new Error(\"Sort key is required for delete operation\");\n }\n keyCondition[this.indexConfig.sortKey] = key.sk;\n }\n\n return keyCondition;\n }\n\n /**\n * Adds a put operation to the transaction.\n *\n * The method automatically checks for duplicate items within the transaction\n * to prevent multiple operations on the same item.\n *\n * @example\n * ```typescript\n * // Simple put operation\n * transaction.put('orders', {\n * orderId: '123',\n * status: 'PENDING',\n * amount: 100\n * });\n *\n * // Conditional put operation\n * transaction.put(\n * 'inventory',\n * { productId: 'ABC', quantity: 50 },\n * op => op.attributeNotExists('productId')\n * );\n *\n * // Put with complex condition\n * transaction.put(\n * 'users',\n * { userId: '123', status: 'ACTIVE' },\n * op => op.and([\n * op.attributeNotExists('userId'),\n * op.beginsWith('status', 'ACTIVE')\n * ])\n * );\n * ```\n *\n * @param tableName - The name of the DynamoDB table\n * @param item - The item to put into the table\n * @param condition - Optional condition that must be satisfied\n * @returns The transaction builder for method chaining\n * @throws {Error} If a duplicate item is detected in the transaction\n */\n put<T extends DynamoItem>(tableName: string, item: T, condition?: Condition): this {\n // Check for duplicate item\n this.checkForDuplicateItem(tableName, item);\n\n const transactionItem: TransactionItem = {\n type: \"Put\",\n params: {\n tableName,\n item,\n },\n };\n\n if (condition) {\n const { expression, names, values } = prepareExpressionParams(condition);\n transactionItem.params.conditionExpression = expression;\n transactionItem.params.expressionAttributeNames = names;\n transactionItem.params.expressionAttributeValues = values;\n }\n\n this.items.push(transactionItem);\n return this;\n }\n\n /**\n * Adds a pre-configured put operation to the transaction.\n *\n * This method is particularly useful when working with PutBuilder\n * to maintain consistency in put operations across your application.\n *\n * @example\n * ```typescript\n * // Create a put command with PutBuilder\n * const putCommand = new PutBuilder(executor, newItem, 'users')\n * .condition(op => op.attributeNotExists('userId'))\n * .toDynamoCommand();\n *\n * // Add the command to the transaction\n * transaction.putWithCommand(putCommand);\n * ```\n *\n * @param command - The complete put command configuration\n * @returns The transaction builder for method chaining\n * @throws {Error} If a duplicate item is detected in the transaction\n * @see PutBuilder for creating put commands\n */\n putWithCommand(command: PutCommandParams): TransactionBuilder {\n // Check for duplicate item\n this.checkForDuplicateItem(command.tableName, command.item);\n\n const transactionItem: TransactionItem = {\n type: \"Put\",\n params: command,\n };\n\n this.items.push(transactionItem);\n return this;\n }\n\n /**\n * Adds a delete operation to the transaction.\n *\n * The method automatically checks for duplicate items within the transaction\n * to prevent multiple operations on the same item.\n *\n * @example\n * ```typescript\n * // Simple delete operation\n * transaction.delete('orders', {\n * pk: 'ORDER#123',\n * sk: 'METADATA'\n * });\n *\n * // Conditional delete operation\n * transaction.delete(\n * 'users',\n * { pk: 'USER#123' },\n * op => op.eq('status', 'INACTIVE')\n * );\n *\n * // Delete with complex condition\n * transaction.delete(\n * 'products',\n * { pk: 'PROD#ABC' },\n * op => op.and([\n * op.eq('status', 'DRAFT'),\n * op.lt('version', 5)\n * ])\n * );\n * ```\n *\n * @param tableName - The name of the DynamoDB table\n * @param key - The primary key of the item to delete\n * @param condition - Optional condition that must be satisfied\n * @returns The transaction builder for method chaining\n * @throws {Error} If a duplicate item is detected in the transaction\n */\n delete(tableName: string, key: PrimaryKeyWithoutExpression, condition?: Condition): TransactionBuilder {\n const keyCondition = this.createKeyForPrimaryIndex(key);\n\n // Check for duplicate item\n this.checkForDuplicateItem(tableName, keyCondition);\n\n const transactionItem: TransactionItem = {\n type: \"Delete\",\n params: {\n tableName,\n key: keyCondition,\n },\n };\n\n if (condition) {\n const { expression, names, values } = prepareExpressionParams(condition);\n transactionItem.params.conditionExpression = expression;\n transactionItem.params.expressionAttributeNames = names;\n transactionItem.params.expressionAttributeValues = values;\n }\n\n this.items.push(transactionItem);\n return this;\n }\n\n /**\n * Adds a pre-configured delete operation to the transaction.\n *\n * This method is particularly useful when working with DeleteBuilder\n * to maintain consistency in delete operations across your application.\n *\n * @example\n * ```typescript\n * // Create a delete command with DeleteBuilder\n * const deleteCommand = new DeleteBuilder(executor, 'users', { pk: 'USER#123' })\n * .condition(op => op.and([\n * op.attributeExists('pk'),\n * op.eq('status', 'INACTIVE')\n * ]))\n * .toDynamoCommand();\n *\n * // Add the command to the transaction\n * transaction.deleteWithCommand(deleteCommand);\n * ```\n *\n * @param command - The complete delete command configuration\n * @returns The transaction builder for method chaining\n * @throws {Error} If a duplicate item is detected in the transaction\n * @see DeleteBuilder for creating delete commands\n */\n deleteWithCommand(command: DeleteCommandParams): this {\n // The command.key from DeleteBuilder.toDynamoCommand() is in PrimaryKeyWithoutExpression format\n // but DeleteCommandParams expects it to be in the table's actual key format\n // We need to check if it's already converted or needs conversion\n let keyForDuplicateCheck: Record<string, unknown>;\n let keyForTransaction: Record<string, unknown>;\n\n // Check if the key is in PrimaryKeyWithoutExpression format (has pk/sk properties)\n if (typeof command.key === \"object\" && command.key !== null && \"pk\" in command.key) {\n // Convert from PrimaryKeyWithoutExpression to table key format\n keyForTransaction = this.createKeyForPrimaryIndex(command.key as PrimaryKeyWithoutExpression);\n keyForDuplicateCheck = keyForTransaction;\n } else {\n // Key is already in table format\n keyForTransaction = command.key;\n keyForDuplicateCheck = command.key;\n }\n\n // Check for duplicate item\n this.checkForDuplicateItem(command.tableName, keyForDuplicateCheck);\n\n const transactionItem: TransactionItem = {\n type: \"Delete\",\n params: {\n ...command,\n key: keyForTransaction,\n },\n };\n this.items.push(transactionItem);\n return this;\n }\n\n /**\n * Adds an update operation to the transaction.\n *\n * The method supports all DynamoDB update expressions:\n * - SET: Modify or add attributes\n * - REMOVE: Delete attributes\n * - ADD: Update numbers and sets\n * - DELETE: Remove elements from a set\n *\n * @example\n * ```typescript\n * // Simple update\n * transaction.update(\n * 'orders',\n * { pk: 'ORDER#123' },\n * 'SET #status = :status',\n * { '#status': 'status' },\n * { ':status': 'PROCESSING' }\n * );\n *\n * // Complex update with multiple operations\n * transaction.update(\n * 'products',\n * { pk: 'PROD#ABC' },\n * 'SET #qty = #qty - :amount, #status = :status REMOVE #oldAttr',\n * { '#qty': 'quantity', '#status': 'status', '#oldAttr': 'deprecated_field' },\n * { ':amount': 1, ':status': 'LOW_STOCK' }\n * );\n *\n * // Conditional update\n * transaction.update(\n * 'users',\n * { pk: 'USER#123' },\n * 'SET #lastLogin = :now',\n * { '#lastLogin': 'lastLoginDate' },\n * { ':now': new Date().toISOString() },\n * op => op.attributeExists('pk')\n * );\n * ```\n *\n * @param tableName - The name of the DynamoDB table\n * @param key - The primary key of the item to update\n * @param updateExpression - The update expression (SET, REMOVE, ADD, DELETE)\n * @param expressionAttributeNames - Map of attribute name placeholders to actual names\n * @param expressionAttributeValues - Map of value placeholders to actual values\n * @param condition - Optional condition that must be satisfied\n * @returns The transaction builder for method chaining\n * @throws {Error} If a duplicate item is detected in the transaction\n */\n update<T extends DynamoItem>(\n tableName: string,\n key: PrimaryKeyWithoutExpression,\n updateExpression: string,\n expressionAttributeNames?: Record<string, string>,\n expressionAttributeValues?: Record<string, unknown>,\n condition?: Condition,\n ): this {\n const keyCondition = this.createKeyForPrimaryIndex(key);\n\n // Check for duplicate item\n this.checkForDuplicateItem(tableName, keyCondition);\n\n const transactionItem: TransactionItem = {\n type: \"Update\",\n params: {\n tableName,\n key: keyCondition,\n updateExpression,\n expressionAttributeNames,\n expressionAttributeValues,\n },\n };\n\n if (condition) {\n const { expression, names, values } = prepareExpressionParams(condition);\n transactionItem.params.conditionExpression = expression;\n\n // Merge the condition expression attribute names and values with the update ones\n transactionItem.params.expressionAttributeNames = {\n ...transactionItem.params.expressionAttributeNames,\n ...names,\n };\n\n transactionItem.params.expressionAttributeValues = {\n ...transactionItem.params.expressionAttributeValues,\n ...values,\n };\n }\n\n this.items.push(transactionItem);\n return this;\n }\n\n /**\n * Adds a pre-configured update operation to the transaction.\n *\n * This method is particularly useful when working with UpdateBuilder\n * to maintain consistency in update operations across your application.\n *\n * @example\n * ```typescript\n * // Create an update command with UpdateBuilder\n * const updateCommand = new UpdateBuilder(executor, 'inventory', { pk: 'PROD#ABC' })\n * .set('quantity', ':qty')\n * .set('lastUpdated', ':now')\n * .values({\n * ':qty': 100,\n * ':now': new Date().toISOString()\n * })\n * .condition(op => op.gt('quantity', 0))\n * .toDynamoCommand();\n *\n * // Add the command to the transaction\n * transaction.updateWithCommand(updateCommand);\n * ```\n *\n * @param command - The complete update command configuration\n * @returns The transaction builder for method chaining\n * @throws {Error} If a duplicate item is detected in the transaction\n * @see UpdateBuilder for creating update commands\n */\n updateWithCommand(command: UpdateCommandParams): TransactionBuilder {\n // The command.key from UpdateBuilder.toDynamoCommand() is in PrimaryKeyWithoutExpression format\n // but UpdateCommandParams expects it to be in the table's actual key format\n // We need to check if it's already converted or needs conversion\n let keyForDuplicateCheck: Record<string, unknown>;\n let keyForTransaction: Record<string, unknown>;\n\n // Check if the key is in PrimaryKeyWithoutExpression format (has pk/sk properties)\n if (typeof command.key === \"object\" && command.key !== null && \"pk\" in command.key) {\n // Convert from PrimaryKeyWithoutExpression to table key format\n keyForTransaction = this.createKeyForPrimaryIndex(command.key as PrimaryKeyWithoutExpression);\n keyForDuplicateCheck = keyForTransaction;\n } else {\n // Key is already in table format\n keyForTransaction = command.key;\n keyForDuplicateCheck = command.key;\n }\n\n // Check for duplicate item\n this.checkForDuplicateItem(command.tableName, keyForDuplicateCheck);\n\n const transactionItem: TransactionItem = {\n type: \"Update\",\n params: {\n ...command,\n key: keyForTransaction,\n },\n };\n\n this.items.push(transactionItem);\n return this;\n }\n\n /**\n * Adds a condition check operation to the transaction.\n *\n * Condition checks are particularly useful for:\n * - Implementing optimistic locking\n * - Ensuring referential integrity\n * - Validating business rules atomically\n *\n * @example\n * ```typescript\n * // Check if order is in correct state\n * transaction.conditionCheck(\n * 'orders',\n * { pk: 'ORDER#123' },\n * op => op.eq('status', 'PENDING')\n * );\n *\n * // Complex condition check\n * transaction.conditionCheck(\n * 'inventory',\n * { pk: 'PROD#ABC' },\n * op => op.and([\n * op.gt('quantity', 0),\n * op.eq('status', 'ACTIVE'),\n * op.attributeExists('lastRestockDate')\n * ])\n * );\n *\n * // Check with multiple attributes\n * transaction.conditionCheck(\n * 'users',\n * { pk: 'USER#123' },\n * op => op.or([\n * op.eq('status', 'PREMIUM'),\n * op.gte('credits', 100)\n * ])\n * );\n * ```\n *\n * @param tableName - The name of the DynamoDB table\n * @param key - The primary key of the item to check\n * @param condition - The condition that must be satisfied\n * @returns The transaction builder for method chaining\n * @throws {Error} If a duplicate item is detected in the transaction\n * @throws {Error} If condition expression generation fails\n */\n conditionCheck(tableName: string, key: PrimaryKeyWithoutExpression, condition: Condition): TransactionBuilder {\n const keyCondition = this.createKeyForPrimaryIndex(key);\n\n // Check for duplicate item\n this.checkForDuplicateItem(tableName, keyCondition);\n\n const { expression, names, values } = prepareExpressionParams(condition);\n\n if (!expression) {\n throw new Error(\"Failed to generate condition expression\");\n }\n\n const transactionItem: TransactionItem = {\n type: \"ConditionCheck\",\n params: {\n tableName,\n key: keyCondition,\n conditionExpression: expression,\n expressionAttributeNames: names,\n expressionAttributeValues: values,\n },\n };\n\n this.items.push(transactionItem);\n return this;\n }\n\n /**\n * Adds a pre-configured condition check operation to the transaction.\n *\n * This method is particularly useful when working with ConditionCheckBuilder\n * to maintain consistency in condition checks across your application.\n *\n * @example\n * ```typescript\n * // Create a condition check with ConditionCheckBuilder\n * const checkCommand = new ConditionCheckBuilder('inventory', { pk: 'PROD#ABC' })\n * .condition(op => op.and([\n * op.between('quantity', 10, 100),\n * op.beginsWith('category', 'ELECTRONICS'),\n * op.attributeExists('lastAuditDate')\n * ]))\n * .toDynamoCommand();\n *\n * // Add the command to the transaction\n * transaction.conditionCheckWithCommand(checkCommand);\n * ```\n *\n * @param command - The complete condition check command configuration\n * @returns The transaction builder for method chaining\n * @throws {Error} If a duplicate item is detected in the transaction\n * @see ConditionCheckBuilder for creating condition check commands\n */\n conditionCheckWithCommand(command: ConditionCheckCommandParams): TransactionBuilder {\n // The command.key from ConditionCheckBuilder.toDynamoCommand() is in PrimaryKeyWithoutExpression format\n // but ConditionCheckCommandParams expects it to be in the table's actual key format\n // We need to check if it's already converted or needs conversion\n let keyForDuplicateCheck: Record<string, unknown>;\n let keyForTransaction: Record<string, unknown>;\n\n // Check if the key is in PrimaryKeyWithoutExpression format (has pk/sk properties)\n if (typeof command.key === \"object\" && command.key !== null && \"pk\" in command.key) {\n // Convert from PrimaryKeyWithoutExpression to table key format\n keyForTransaction = this.createKeyForPrimaryIndex(command.key as PrimaryKeyWithoutExpression);\n keyForDuplicateCheck = keyForTransaction;\n } else {\n // Key is already in table format\n keyForTransaction = command.key;\n keyForDuplicateCheck = command.key;\n }\n\n // Check for duplicate item\n this.checkForDuplicateItem(command.tableName, keyForDuplicateCheck);\n\n const transactionItem: TransactionItem = {\n type: \"ConditionCheck\",\n params: {\n ...command,\n key: keyForTransaction,\n },\n };\n this.items.push(transactionItem);\n return this;\n }\n\n /**\n * Sets options for the transaction execution.\n *\n * @example\n * ```typescript\n * // Enable idempotency and capacity tracking\n * transaction.withOptions({\n * clientRequestToken: 'unique-request-id-123',\n * returnConsumedCapacity: 'TOTAL'\n * });\n *\n * // Track item collection metrics\n * transaction.withOptions({\n * returnItemCollectionMetrics: 'SIZE'\n * });\n * ```\n *\n * Note: ClientRequestToken can be used to make transactions idempotent,\n * ensuring the same transaction is not executed multiple times.\n *\n * @param options - Configuration options for the transaction\n * @returns The transaction builder for method chaining\n */\n withOptions(options: TransactionOptions): TransactionBuilder {\n this.options = { ...this.options, ...options };\n return this;\n }\n\n /**\n * Gets a human-readable representation of the transaction items.\n *\n * The method resolves all expression placeholders with their actual values,\n * making it easier to understand the transaction's operations.\n *\n * @example\n * ```typescript\n * // Add multiple operations\n * transaction\n * .put('orders', { orderId: '123', status: 'PENDING' })\n * .update('inventory',\n * { productId: 'ABC' },\n * 'SET quantity = quantity - :amount',\n * undefined,\n * { ':amount': 1 }\n * );\n *\n * // Debug the transaction\n * const debugInfo = transaction.debug();\n * console.log('Transaction operations:', debugInfo);\n * ```\n *\n * @returns An array of readable representations of the transaction items\n */\n debug() {\n return debugTransaction(this.items);\n }\n\n /**\n * Executes all operations in the transaction atomically.\n *\n * The transaction will only succeed if all operations succeed.\n * If any operation fails, the entire transaction is rolled back.\n *\n * @example\n * ```typescript\n * try {\n * // Build and execute transaction\n * await transaction\n * .put('orders', newOrder)\n * .update('inventory',\n * { productId: 'ABC' },\n * 'SET quantity = quantity - :qty',\n * undefined,\n * { ':qty': 1 }\n * )\n * .conditionCheck('products',\n * { productId: 'ABC' },\n * op => op.eq('status', 'ACTIVE')\n * )\n * .execute();\n *\n * console.log('Transaction completed successfully');\n * } catch (error) {\n * // Handle transaction failure\n * console.error('Transaction failed:', error);\n * }\n * ```\n *\n * @throws {Error} If no transaction items are specified\n * @throws {Error} If any operation in the transaction fails\n * @returns A promise that resolves when the transaction completes\n */\n async execute(): Promise<void> {\n if (this.items.length === 0) {\n throw new Error(\"No transaction items specified\");\n }\n\n const transactItems = this.items.map((item) => {\n switch (item.type) {\n case \"Put\":\n return {\n Put: {\n TableName: item.params.tableName,\n Item: item.params.item,\n ConditionExpression: item.params.conditionExpression,\n ExpressionAttributeNames: item.params.expressionAttributeNames,\n ExpressionAttributeValues: item.params.expressionAttributeValues,\n },\n };\n case \"Delete\":\n return {\n Delete: {\n TableName: item.params.tableName,\n Key: item.params.key,\n ConditionExpression: item.params.conditionExpression,\n ExpressionAttributeNames: item.params.expressionAttributeNames,\n ExpressionAttributeValues: item.params.expressionAttributeValues,\n },\n };\n case \"Update\":\n return {\n Update: {\n TableName: item.params.tableName,\n Key: item.params.key,\n UpdateExpression: item.params.updateExpression,\n ConditionExpression: item.params.conditionExpression,\n ExpressionAttributeNames: item.params.expressionAttributeNames,\n ExpressionAttributeValues: item.params.expressionAttributeValues,\n },\n };\n case \"ConditionCheck\":\n return {\n ConditionCheck: {\n TableName: item.params.tableName,\n Key: item.params.key,\n ConditionExpression: item.params.conditionExpression,\n ExpressionAttributeNames: item.params.expressionAttributeNames,\n ExpressionAttributeValues: item.params.expressionAttributeValues,\n },\n };\n default: {\n // This should never happen as we've covered all cases in the union type\n const exhaustiveCheck: never = item;\n throw new Error(`Unsupported transaction item type: ${String(exhaustiveCheck)}`);\n }\n }\n });\n\n const params: TransactWriteCommandInput = {\n TransactItems: transactItems,\n ClientRequestToken: this.options.clientRequestToken,\n ReturnConsumedCapacity: this.options.returnConsumedCapacity,\n ReturnItemCollectionMetrics: this.options.returnItemCollectionMetrics,\n };\n\n try {\n await this.executor(params);\n } catch (error) {\n console.log(this.debug());\n console.error(\"Error executing transaction:\", error);\n throw error;\n }\n }\n}\n","import type { Condition, ConditionOperator, PrimaryKeyWithoutExpression } from \"../conditions\";\nimport {\n and,\n attributeExists,\n attributeNotExists,\n beginsWith,\n between,\n contains,\n eq,\n gt,\n gte,\n inArray,\n lt,\n lte,\n ne,\n not,\n or,\n} from \"../conditions\";\nimport { buildExpression, generateAttributeName, generateValueName } from \"../expression\";\nimport type { DynamoItem } from \"../types\";\nimport { debugCommand } from \"../utils/debug-expression\";\nimport type { UpdateCommandParams } from \"./builder-types\";\nimport type { TransactionBuilder } from \"./transaction-builder\";\nimport type { Path, PathType } from \"./types\";\n\n/**\n * Configuration options for DynamoDB update operations.\n */\nexport interface UpdateOptions {\n /** Optional condition that must be satisfied for the update to succeed */\n condition?: Condition;\n /** Determines which item attributes to include in the response */\n returnValues?: \"ALL_NEW\" | \"UPDATED_NEW\" | \"ALL_OLD\" | \"UPDATED_OLD\" | \"NONE\";\n}\n\n/**\n * Function type for executing DynamoDB update operations.\n * @typeParam T - The type of the item being updated\n */\ntype UpdateExecutor<T extends DynamoItem> = (params: UpdateCommandParams) => Promise<{ item?: T }>;\n\n/**\n * Represents a single update action within an update operation.\n * Each action modifies the item in a specific way:\n * - SET: Modify or add attributes\n * - REMOVE: Delete attributes\n * - ADD: Update numbers and sets\n * - DELETE: Remove elements from a set\n */\nexport type UpdateAction = {\n /** The type of update action */\n type: \"SET\" | \"REMOVE\" | \"ADD\" | \"DELETE\";\n /** The attribute path to update */\n path: string;\n /** The value to use in the update (not used for REMOVE actions) */\n value?: unknown;\n};\n\n/**\n * Type utility to get the element type of a set.\n * Extracts the element type from either a Set or Array type.\n * @typeParam T - The set or array type\n */\ntype SetElementType<T> = T extends Set<infer U> ? U : T extends Array<infer U> ? U : never;\n\n/**\n * Type utility to get the element type from a path that points to a set.\n * Combines PathType and SetElementType to get the element type at a specific path.\n * @typeParam T - The type of the item\n * @typeParam K - The path within the item\n */\ntype PathSetElementType<T, K extends Path<T>> = SetElementType<PathType<T, K>>;\n\n/**\n * Builder for creating DynamoDB update operations.\n *\n * The builder supports all DynamoDB update operations:\n * - SET: Modify or add attributes\n * - REMOVE: Delete attributes\n * - ADD: Update numbers and sets\n * - DELETE: Remove elements from a set\n *\n * @example\n * ```typescript\n * // Simple update\n * const result = await new UpdateBuilder(executor, 'dinosaurs', { id: 'TREX-001' })\n * .set('status', 'HUNTING')\n * .set('lastFed', new Date().toISOString())\n * .execute();\n *\n * // Complex update with multiple operations\n * const result = await new UpdateBuilder(executor, 'habitats', { id: 'PADDOCK-A' })\n * .set({\n * status: 'OCCUPIED',\n * occupants: 3,\n * 'metadata.lastInspection': new Date().toISOString()\n * })\n * .add('securityBreaches', 1)\n * .deleteElementsFromSet('suitableDinosaurs', ['VELOCIRAPTOR'])\n * .condition(op => op.gt('securityLevel', 8))\n * .returnValues('ALL_NEW')\n * .execute();\n * ```\n *\n * @typeParam T - The type of item being updated\n */\nexport class UpdateBuilder<T extends DynamoItem> {\n protected updates: UpdateAction[] = [];\n protected options: UpdateOptions = {\n returnValues: \"ALL_NEW\",\n };\n protected readonly executor: UpdateExecutor<T>;\n protected readonly tableName: string;\n protected readonly key: PrimaryKeyWithoutExpression;\n\n constructor(executor: UpdateExecutor<T>, tableName: string, key: PrimaryKeyWithoutExpression) {\n this.executor = executor;\n this.tableName = tableName;\n this.key = key;\n }\n\n /**\n * Sets multiple attributes of an item using an object.\n *\n * @example\n * ```typescript\n * // Update multiple attributes\n * builder.set({\n * species: 'Tyrannosaurus Rex',\n * height: 20,\n * diet: 'CARNIVORE',\n * 'stats.threatLevel': 10\n * });\n * ```\n */\n set(values: Partial<T>): UpdateBuilder<T>;\n\n /**\n * Sets a single attribute to a specific value.\n *\n * @example\n * ```typescript\n * // Set simple attributes\n * builder\n * .set('status', 'SLEEPING')\n * .set('lastFeeding', new Date().toISOString());\n *\n * // Set nested attributes\n * builder\n * .set('location.zone', 'RESTRICTED')\n * .set('stats.health', 100);\n * ```\n */\n set<K extends Path<T>>(path: K, value: PathType<T, K>): UpdateBuilder<T>;\n set<K extends Path<T>>(valuesOrPath: K | Partial<T>, value?: PathType<T, K>): this {\n if (typeof valuesOrPath === \"object\") {\n for (const [key, value] of Object.entries(valuesOrPath)) {\n this.updates.push({\n type: \"SET\",\n path: key,\n value,\n });\n }\n } else {\n this.updates.push({\n type: \"SET\",\n path: valuesOrPath,\n value,\n });\n }\n\n return this;\n }\n\n /**\n * Removes an attribute from the item.\n *\n * @example\n * ```typescript\n * // Remove simple attributes\n * builder\n * .remove('temporaryTag')\n * .remove('previousLocation');\n *\n * // Remove nested attributes\n * builder\n * .remove('metadata.testData')\n * .remove('stats.experimentalMetrics');\n * ```\n *\n * @param path - The path to the attribute to remove\n * @returns The builder instance for method chaining\n */\n remove<K extends Path<T>>(path: K): this {\n this.updates.push({\n type: \"REMOVE\",\n path,\n });\n return this;\n }\n\n /**\n * Adds a value to a number attribute or adds elements to a set.\n *\n * @example\n * ```typescript\n * // Increment counters\n * builder\n * .add('escapeAttempts', 1)\n * .add('feedingCount', 1);\n *\n * // Add to sets\n * builder\n * .add('knownBehaviors', new Set(['PACK_HUNTING', 'AMBUSH_TACTICS']))\n * .add('visitedZones', new Set(['ZONE_A', 'ZONE_B']));\n * ```\n *\n * @param path - The path to the attribute to update\n * @param value - The value to add (number or set)\n * @returns The builder instance for method chaining\n */\n add<K extends Path<T>>(path: K, value: PathType<T, K>): this {\n this.updates.push({\n type: \"ADD\",\n path,\n value,\n });\n return this;\n }\n\n /**\n * Removes elements from a set attribute.\n *\n * @example\n * ```typescript\n * // Remove from sets using arrays\n * builder.deleteElementsFromSet(\n * 'allowedHabitats',\n * ['JUNGLE', 'COASTAL']\n * );\n *\n * // Remove from sets using Set DynamoItems\n * builder.deleteElementsFromSet(\n * 'knownBehaviors',\n * new Set(['NOCTURNAL', 'TERRITORIAL'])\n * );\n *\n * // Remove from nested sets\n * builder.deleteElementsFromSet(\n * 'stats.compatibleSpecies',\n * ['VELOCIRAPTOR', 'DILOPHOSAURUS']\n * );\n * ```\n *\n * @param path - The path to the set attribute\n * @param value - Elements to remove (array or Set)\n * @returns The builder instance for method chaining\n */\n deleteElementsFromSet<K extends Path<T>>(\n path: K,\n value: PathSetElementType<T, K>[] | Set<PathSetElementType<T, K>>,\n ): this {\n let valuesToDelete: Set<PathSetElementType<T, K>>;\n\n if (Array.isArray(value)) {\n valuesToDelete = new Set(value);\n } else {\n valuesToDelete = value;\n }\n\n this.updates.push({\n type: \"DELETE\",\n path,\n value: valuesToDelete,\n });\n return this;\n }\n\n /**\n * Adds a condition that must be satisfied for the update to succeed.\n *\n * @example\n * ```typescript\n * // Simple condition\n * builder.condition(op =>\n * op.eq('status', 'ACTIVE')\n * );\n *\n * // Health check condition\n * builder.condition(op =>\n * op.and([\n * op.gt('health', 50),\n * op.eq('status', 'HUNTING')\n * ])\n * );\n *\n * // Complex security condition\n * builder.condition(op =>\n * op.and([\n * op.attributeExists('securitySystem'),\n * op.eq('containmentStatus', 'SECURE'),\n * op.lt('aggressionLevel', 8)\n * ])\n * );\n *\n * // Version check (optimistic locking)\n * builder.condition(op =>\n * op.eq('version', currentVersion)\n * );\n * ```\n *\n * @param condition - Either a Condition DynamoItem or a callback function that builds the condition\n * @returns The builder instance for method chaining\n */\n condition(condition: Condition | ((op: ConditionOperator<T>) => Condition)): this {\n if (typeof condition === \"function\") {\n const conditionOperator: ConditionOperator<T> = {\n eq,\n ne,\n lt,\n lte,\n gt,\n gte,\n between,\n inArray,\n beginsWith,\n contains,\n attributeExists,\n attributeNotExists,\n and,\n or,\n not,\n };\n this.options.condition = condition(conditionOperator);\n } else {\n this.options.condition = condition;\n }\n return this;\n }\n\n /**\n * Sets which item attributes to include in the response.\n *\n * Available options:\n * - ALL_NEW: All attributes after the update (default)\n * - UPDATED_NEW: Only updated attributes, new values\n * - ALL_OLD: All attributes before the update\n * - UPDATED_OLD: Only updated attributes, old values\n * - NONE: No attributes returned\n *\n * @example\n * ```typescript\n * // Get complete updated dinosaur\n * const result = await builder\n * .set('status', 'SLEEPING')\n * .returnValues('ALL_NEW')\n * .execute();\n *\n * // Track specific attribute changes\n * const result = await builder\n * .set({\n * 'stats.health': 100,\n * 'stats.energy': 95\n * })\n * .returnValues('UPDATED_OLD')\n * .execute();\n *\n * if (result.item) {\n * console.log('Previous health:', result.item.stats?.health);\n * }\n * ```\n *\n * @param returnValues - Which attributes to return in the response\n * @returns The builder instance for method chaining\n */\n returnValues(returnValues: \"ALL_NEW\" | \"UPDATED_NEW\" | \"ALL_OLD\" | \"UPDATED_OLD\" | \"NONE\"): this {\n this.options.returnValues = returnValues;\n return this;\n }\n\n /**\n * Generate the DynamoDB command parameters\n */\n toDynamoCommand(): UpdateCommandParams {\n if (this.updates.length === 0) {\n throw new Error(\"No update actions specified\");\n }\n\n const expressionParams: {\n expressionAttributeNames: Record<string, string>;\n expressionAttributeValues: DynamoItem;\n valueCounter: { count: number };\n } = {\n expressionAttributeNames: {},\n expressionAttributeValues: {},\n valueCounter: { count: 0 },\n };\n\n // Build the update expression\n let updateExpression = \"\";\n\n // Group updates by type\n const setUpdates: UpdateAction[] = [];\n const removeUpdates: UpdateAction[] = [];\n const addUpdates: UpdateAction[] = [];\n const deleteUpdates: UpdateAction[] = [];\n\n for (const update of this.updates) {\n switch (update.type) {\n case \"SET\":\n setUpdates.push(update);\n break;\n case \"REMOVE\":\n removeUpdates.push(update);\n break;\n case \"ADD\":\n addUpdates.push(update);\n break;\n case \"DELETE\":\n deleteUpdates.push(update);\n break;\n }\n }\n\n // Build SET clause\n if (setUpdates.length > 0) {\n updateExpression += \"SET \";\n updateExpression += setUpdates\n .map((update) => {\n const attrName = generateAttributeName(expressionParams, update.path);\n const valueName = generateValueName(expressionParams, update.value);\n expressionParams.expressionAttributeValues[valueName] = update.value;\n return `${attrName} = ${valueName}`;\n })\n .join(\", \");\n }\n\n // Build REMOVE clause\n if (removeUpdates.length > 0) {\n if (updateExpression) {\n updateExpression += \" \";\n }\n updateExpression += \"REMOVE \";\n updateExpression += removeUpdates\n .map((update) => {\n return generateAttributeName(expressionParams, update.path);\n })\n .join(\", \");\n }\n\n // Build ADD clause\n if (addUpdates.length > 0) {\n if (updateExpression) {\n updateExpression += \" \";\n }\n updateExpression += \"ADD \";\n updateExpression += addUpdates\n .map((update) => {\n const attrName = generateAttributeName(expressionParams, update.path);\n const valueName = generateValueName(expressionParams, update.value);\n\n return `${attrName} ${valueName}`;\n })\n .join(\", \");\n }\n\n // Build DELETE clause\n if (deleteUpdates.length > 0) {\n if (updateExpression) {\n updateExpression += \" \";\n }\n\n updateExpression += \"DELETE \";\n updateExpression += deleteUpdates\n .map((update) => {\n const attrName = generateAttributeName(expressionParams, update.path);\n const valueName = generateValueName(expressionParams, update.value);\n\n return `${attrName} ${valueName}`;\n })\n .join(\", \");\n }\n\n // Build condition expression if provided\n let conditionExpression: string | undefined;\n if (this.options.condition) {\n conditionExpression = buildExpression(this.options.condition, expressionParams);\n }\n\n const { expressionAttributeNames, expressionAttributeValues } = expressionParams;\n\n return {\n tableName: this.tableName,\n key: this.key,\n updateExpression,\n conditionExpression,\n expressionAttributeNames: Object.keys(expressionAttributeNames).length > 0 ? expressionAttributeNames : undefined,\n expressionAttributeValues:\n Object.keys(expressionAttributeValues).length > 0 ? expressionAttributeValues : undefined,\n returnValues: this.options.returnValues,\n };\n }\n\n /**\n * Adds this update operation to a transaction.\n *\n * @example\n * ```typescript\n * const transaction = new TransactionBuilder(executor);\n *\n * // Update dinosaur status and habitat occupancy atomically\n * new UpdateBuilder(executor, 'dinosaurs', { id: 'TREX-001' })\n * .set('location', 'PADDOCK_A')\n * .set('status', 'CONTAINED')\n * .withTransaction(transaction);\n *\n * new UpdateBuilder(executor, 'habitats', { id: 'PADDOCK-A' })\n * .add('occupants', 1)\n * .set('lastOccupied', new Date().toISOString())\n * .withTransaction(transaction);\n *\n * // Execute all operations atomically\n * await transaction.execute();\n * ```\n *\n * @param transaction - The transaction builder to add this operation to\n * @returns The builder instance for method chaining\n */\n withTransaction(transaction: TransactionBuilder) {\n const command = this.toDynamoCommand();\n transaction.updateWithCommand(command);\n }\n\n /**\n * Gets a human-readable representation of the update command.\n *\n * @example\n * ```typescript\n * // Create complex update\n * const builder = new UpdateBuilder(executor, 'dinosaurs', { id: 'RAPTOR-001' })\n * .set({\n * status: 'HUNTING',\n * 'stats.health': 95,\n * 'behavior.lastObserved': new Date().toISOString()\n * })\n * .add('huntingSuccesses', 1)\n * .condition(op => op.gt('health', 50));\n *\n * // Debug the update\n * const debugInfo = builder.debug();\n * console.log('Update operation:', debugInfo);\n * ```\n *\n * @returns A readable representation of the update command with resolved expressions\n */\n debug() {\n const command = this.toDynamoCommand();\n return debugCommand(command);\n }\n\n /**\n * Executes the update operation against DynamoDB.\n *\n * @example\n * ```typescript\n * try {\n * // Update dinosaur status with conditions\n * const result = await new UpdateBuilder(executor, 'dinosaurs', { id: 'TREX-001' })\n * .set({\n * status: 'FEEDING',\n * lastMeal: new Date().toISOString(),\n * 'stats.hunger': 0\n * })\n * .add('feedingCount', 1)\n * .condition(op =>\n * op.and([\n * op.gt('stats.hunger', 80),\n * op.eq('status', 'HUNTING')\n * ])\n * )\n * .returnValues('ALL_NEW')\n * .execute();\n *\n * if (result.item) {\n * console.log('Updated dinosaur:', result.item);\n * }\n * } catch (error) {\n * // Handle condition check failure\n * console.error('Failed to update dinosaur:', error);\n * // Check if dinosaur wasn't hungry enough\n * if (error.name === 'ConditionalCheckFailedException') {\n * console.log('Dinosaur not ready for feeding');\n * }\n * }\n * ```\n *\n * @returns A promise that resolves to an DynamoItem containing the updated item (if returnValues is set)\n * @throws {ConditionalCheckFailedException} If the condition check fails\n * @throws {Error} If the update operation fails for other reasons\n */\n async execute(): Promise<{ item?: T }> {\n const params = this.toDynamoCommand();\n return this.executor(params);\n }\n}\n","import type { Condition, ConditionOperator } from \"../conditions\";\nimport type { IndexDefinition } from \"../entity/entity\";\nimport type { Table } from \"../table\";\nimport type { DynamoItem } from \"../types\";\nimport type { BatchBuilder } from \"./batch-builder\";\nimport type { UpdateCommandParams } from \"./builder-types\";\nimport type { DeleteBuilder } from \"./delete-builder\";\nimport type { GetBuilder } from \"./get-builder\";\nimport type { PutBuilder } from \"./put-builder\";\nimport type { TransactionBuilder } from \"./transaction-builder\";\nimport type { Path, PathType } from \"./types\";\nimport type { UpdateBuilder } from \"./update-builder\";\n\ntype SetElementType<T> = T extends Set<infer U> ? U : T extends Array<infer U> ? U : never;\ntype PathSetElementType<T, K extends Path<T>> = SetElementType<PathType<T, K>>;\n\n/**\n * Creates an entity-aware wrapper that automatically provides entity names to batch operations\n * while transparently delegating all other method calls to the underlying builder.\n */\nfunction createEntityAwareBuilder<T extends object>(\n builder: T,\n entityName: string,\n): T & { readonly entityName: string } {\n return new Proxy(builder, {\n get(target, prop, receiver) {\n // Expose the entity name as a readonly property\n if (prop === \"entityName\") {\n return entityName;\n }\n\n // Intercept withBatch method to provide automatic entity type inference\n if (prop === \"withBatch\" && typeof (target as Record<string, unknown>)[prop] === \"function\") {\n return <\n TEntities extends Record<string, DynamoItem> = Record<string, DynamoItem>,\n K extends keyof TEntities = keyof TEntities,\n >(\n batch: BatchBuilder<TEntities>,\n entityType?: K,\n ) => {\n // Use provided entityType or fall back to stored entityName\n const typeToUse = entityType ?? (entityName as K);\n const fn = (target as Record<string, unknown>)[prop] as (\n batch: BatchBuilder<TEntities>,\n entityType?: K,\n ) => unknown;\n // Call the function with the original target as 'this' context\n return fn.call(target, batch, typeToUse);\n };\n }\n\n // For all other properties/methods, delegate to the original builder\n return Reflect.get(target, prop, receiver);\n },\n }) as T & { readonly entityName: string };\n}\n\n/**\n * Entity-aware wrapper for PutBuilder that automatically provides entity name to batch operations\n */\nexport type EntityAwarePutBuilder<T extends DynamoItem> = PutBuilder<T> & {\n readonly entityName: string;\n};\n\n/**\n * Creates an entity-aware PutBuilder\n */\nexport function createEntityAwarePutBuilder<T extends DynamoItem>(\n builder: PutBuilder<T>,\n entityName: string,\n): EntityAwarePutBuilder<T> {\n return createEntityAwareBuilder(builder, entityName);\n}\n\n/**\n * Entity-aware wrapper for GetBuilder that automatically provides entity name to batch operations\n */\nexport type EntityAwareGetBuilder<T extends DynamoItem> = GetBuilder<T> & {\n readonly entityName: string;\n};\n\n/**\n * Creates an entity-aware GetBuilder\n */\nexport function createEntityAwareGetBuilder<T extends DynamoItem>(\n builder: GetBuilder<T>,\n entityName: string,\n): EntityAwareGetBuilder<T> {\n return createEntityAwareBuilder(builder, entityName);\n}\n\n/**\n * Entity-aware wrapper for DeleteBuilder that automatically provides entity name to batch operations\n */\nexport type EntityAwareDeleteBuilder = DeleteBuilder & {\n readonly entityName: string;\n};\n\n/**\n * Creates an entity-aware DeleteBuilder\n */\nexport function createEntityAwareDeleteBuilder(builder: DeleteBuilder, entityName: string): EntityAwareDeleteBuilder {\n return createEntityAwareBuilder(builder, entityName);\n}\n\n/**\n * Entity-aware wrapper for UpdateBuilder that adds forceIndexRebuild functionality\n * and automatically provides entity name to batch operations\n */\nexport class EntityAwareUpdateBuilder<T extends DynamoItem> {\n private forceRebuildIndexes: string[] = [];\n public readonly entityName: string;\n private builder: UpdateBuilder<T>;\n private entityConfig?: {\n data: Partial<T>;\n key: T;\n table: Table;\n indexes: Record<string, IndexDefinition<T>> | undefined;\n generateTimestamps: () => Record<string, string | number>;\n buildIndexUpdates: (\n currentData: T,\n updates: Partial<T>,\n table: Table,\n indexes: Record<string, IndexDefinition<T>> | undefined,\n forceRebuildIndexes?: string[],\n ) => Record<string, string>;\n };\n private updateDataApplied = false;\n\n constructor(builder: UpdateBuilder<T>, entityName: string) {\n this.builder = builder;\n this.entityName = entityName;\n }\n\n /**\n * Configure entity-specific logic for automatic timestamp generation and index updates\n */\n configureEntityLogic(config: {\n data: Partial<T>;\n key: T;\n table: Table;\n indexes: Record<string, IndexDefinition<T>> | undefined;\n generateTimestamps: () => Record<string, string | number>;\n buildIndexUpdates: (\n currentData: T,\n updates: Partial<T>,\n table: Table,\n indexes: Record<string, IndexDefinition<T>> | undefined,\n forceRebuildIndexes?: string[],\n ) => Record<string, string>;\n }): void {\n this.entityConfig = config;\n }\n\n /**\n * Forces a rebuild of one or more readonly indexes during the update operation.\n *\n * By default, readonly indexes are not updated during entity updates to prevent\n * errors when required index attributes are missing. This method allows you to\n * override that behavior and force specific indexes to be rebuilt.\n *\n * @example\n * ```typescript\n * // Force rebuild a single readonly index\n * const result = await repo.update({ id: 'TREX-001' }, { status: 'ACTIVE' })\n * .forceIndexRebuild('gsi1')\n * .execute();\n *\n * // Force rebuild multiple readonly indexes\n * const result = await repo.update({ id: 'TREX-001' }, { status: 'ACTIVE' })\n * .forceIndexRebuild(['gsi1', 'gsi2'])\n * .execute();\n *\n * // Chain with other update operations\n * const result = await repo.update({ id: 'TREX-001' }, { status: 'ACTIVE' })\n * .set('lastUpdated', new Date().toISOString())\n * .forceIndexRebuild('gsi1')\n * .condition(op => op.eq('status', 'INACTIVE'))\n * .execute();\n * ```\n *\n * @param indexes - A single index name or array of index names to force rebuild\n * @returns The builder instance for method chaining\n */\n forceIndexRebuild(indexes: string | string[]): this {\n if (Array.isArray(indexes)) {\n this.forceRebuildIndexes = [...this.forceRebuildIndexes, ...indexes];\n } else {\n this.forceRebuildIndexes.push(indexes);\n }\n return this;\n }\n\n /**\n * Gets the list of indexes that should be force rebuilt.\n * This is used internally by entity update logic.\n *\n * @returns Array of index names to force rebuild\n */\n getForceRebuildIndexes(): string[] {\n return [...this.forceRebuildIndexes];\n }\n\n /**\n * Apply entity-specific update data (timestamps and index updates)\n * This is called automatically when needed\n */\n private applyEntityUpdates(): void {\n if (!this.entityConfig || this.updateDataApplied) return;\n\n // Generate timestamps at the time this is called\n const timestamps = this.entityConfig.generateTimestamps();\n\n // Build index updates with force rebuild support\n const updatedItem = { ...this.entityConfig.key, ...this.entityConfig.data, ...timestamps } as T;\n const indexUpdates = this.entityConfig.buildIndexUpdates(\n this.entityConfig.key,\n updatedItem,\n this.entityConfig.table,\n this.entityConfig.indexes,\n this.forceRebuildIndexes,\n );\n\n // Apply all updates together: data, timestamps, and index updates\n this.builder.set({ ...this.entityConfig.data, ...timestamps, ...indexUpdates });\n this.updateDataApplied = true;\n }\n\n // Delegate all UpdateBuilder methods to the wrapped builder\n set(values: Partial<T>): this;\n set<K extends Path<T>>(path: K, value: PathType<T, K>): this;\n set<K extends Path<T>>(valuesOrPath: K | Partial<T>, value?: PathType<T, K>): this {\n if (typeof valuesOrPath === \"object\") {\n this.builder.set(valuesOrPath);\n } else {\n if (value === undefined) {\n throw new Error(\"Value is required when setting a single path\");\n }\n this.builder.set(valuesOrPath, value);\n }\n return this;\n }\n\n remove<K extends Path<T>>(path: K): this {\n this.builder.remove(path);\n return this;\n }\n\n add<K extends Path<T>>(path: K, value: PathType<T, K>): this {\n this.builder.add(path, value);\n return this;\n }\n\n deleteElementsFromSet<K extends Path<T>>(\n path: K,\n value: PathSetElementType<T, K>[] | Set<PathSetElementType<T, K>>,\n ): this {\n this.builder.deleteElementsFromSet(path, value);\n return this;\n }\n\n condition(condition: Condition | ((op: ConditionOperator<T>) => Condition)): this {\n this.builder.condition(condition);\n return this;\n }\n\n returnValues(returnValues: \"ALL_NEW\" | \"UPDATED_NEW\" | \"ALL_OLD\" | \"UPDATED_OLD\" | \"NONE\"): this {\n this.builder.returnValues(returnValues);\n return this;\n }\n\n toDynamoCommand(): UpdateCommandParams {\n return this.builder.toDynamoCommand();\n }\n\n withTransaction(transaction: TransactionBuilder): void {\n this.applyEntityUpdates();\n this.builder.withTransaction(transaction);\n }\n\n debug(): ReturnType<UpdateBuilder<T>[\"debug\"]> {\n return this.builder.debug();\n }\n\n async execute(): Promise<{ item?: T }> {\n // Reset the flag for each execution to ensure fresh timestamps\n this.updateDataApplied = false;\n this.applyEntityUpdates();\n return this.builder.execute();\n }\n}\n\n/**\n * Creates an entity-aware UpdateBuilder with force index rebuild functionality\n */\nexport function createEntityAwareUpdateBuilder<T extends DynamoItem>(\n builder: UpdateBuilder<T>,\n entityName: string,\n): EntityAwareUpdateBuilder<T> {\n return new EntityAwareUpdateBuilder(builder, entityName);\n}\n","import type { Table } from \"../table\";\nimport type { DynamoItem } from \"../types\";\nimport type { IndexDefinition } from \"./entity\";\n\n/**\n * Represents a generated key for a DynamoDB index\n */\ninterface IndexKey {\n /** The partition key value */\n pk: string;\n /** The sort key value (optional) */\n sk?: string;\n}\n\n/**\n * Helper class for building indexes for DynamoDB operations\n */\nexport class IndexBuilder<T extends DynamoItem> {\n /**\n * Creates a new IndexBuilder instance\n *\n * @param table - The DynamoDB table instance\n * @param indexes - The index definitions\n */\n constructor(\n private readonly table: Table,\n private readonly indexes: Record<string, IndexDefinition<T>> = {},\n ) {}\n\n /**\n * Build index attributes for item creation\n *\n * @param item - The item to generate indexes for\n * @param options - Options for building indexes\n * @returns Record of GSI attribute names to their values\n */\n buildForCreate(item: T, options: { excludeReadOnly?: boolean } = {}): Record<string, string> {\n const attributes: Record<string, string> = {};\n\n for (const [indexName, indexDef] of Object.entries(this.indexes)) {\n // Skip read-only indexes if requested\n if (options.excludeReadOnly && indexDef.isReadOnly) {\n continue;\n }\n\n const key = indexDef.generateKey(item);\n const gsiConfig = this.table.gsis[indexName];\n\n if (!gsiConfig) {\n throw new Error(`GSI configuration not found for index: ${indexName}`);\n }\n\n if (key.pk) {\n attributes[gsiConfig.partitionKey] = key.pk;\n }\n if (key.sk && gsiConfig.sortKey) {\n attributes[gsiConfig.sortKey] = key.sk;\n }\n }\n\n return attributes;\n }\n\n /**\n * Build index attributes for item updates\n *\n * @param currentData - The current data before update\n * @param updates - The update data\n * @param options - Options for building indexes\n * @returns Record of GSI attribute names to their updated values\n */\n buildForUpdate(\n currentData: T,\n updates: Partial<T>,\n options: { forceRebuildIndexes?: string[] } = {},\n ): Record<string, string> {\n const attributes: Record<string, string> = {};\n const updatedItem = { ...currentData, ...updates } as T;\n\n // Validate that all force rebuild indexes exist\n if (options.forceRebuildIndexes && options.forceRebuildIndexes.length > 0) {\n const invalidIndexes = options.forceRebuildIndexes.filter((indexName) => !this.indexes[indexName]);\n if (invalidIndexes.length > 0) {\n throw new Error(\n `Cannot force rebuild unknown indexes: ${invalidIndexes.join(\", \")}. ` +\n `Available indexes: ${Object.keys(this.indexes).join(\", \")}`,\n );\n }\n }\n\n for (const [indexName, indexDef] of Object.entries(this.indexes)) {\n const isForced = options.forceRebuildIndexes?.includes(indexName);\n\n // Skip read-only indexes if they are not being force-rebuilt\n if (indexDef.isReadOnly && !isForced) {\n continue;\n }\n\n // If the index is not being forcibly rebuilt, check if it needs to be updated\n if (!isForced) {\n let shouldUpdateIndex = false;\n try {\n const currentKey = indexDef.generateKey(currentData);\n const updatedKey = indexDef.generateKey(updatedItem);\n if (currentKey.pk !== updatedKey.pk || currentKey.sk !== updatedKey.sk) {\n shouldUpdateIndex = true;\n }\n } catch {\n shouldUpdateIndex = true;\n }\n\n if (!shouldUpdateIndex) {\n continue;\n }\n }\n\n // Now generate the full key and validate it\n let key: IndexKey;\n try {\n key = indexDef.generateKey(updatedItem);\n } catch (error) {\n if (error instanceof Error) {\n throw new Error(`Missing attributes: ${error.message}`);\n }\n throw error;\n }\n\n // Validate the generated keys\n if (this.hasUndefinedValues(key)) {\n throw new Error(\n `Missing attributes: Cannot update entity: insufficient data to regenerate index \"${indexName}\". All attributes required by the index must be provided in the update operation, or the index must be marked as readOnly.`,\n );\n }\n\n const gsiConfig = this.table.gsis[indexName];\n if (!gsiConfig) {\n throw new Error(`GSI configuration not found for index: ${indexName}`);\n }\n\n if (key.pk) {\n attributes[gsiConfig.partitionKey] = key.pk;\n }\n if (key.sk && gsiConfig.sortKey) {\n attributes[gsiConfig.sortKey] = key.sk;\n }\n }\n\n return attributes;\n }\n\n /**\n * Check if a key has undefined values\n *\n * @param key - The index key to check\n * @returns True if the key contains undefined values, false otherwise\n */\n private hasUndefinedValues(key: { pk: string; sk?: string }): boolean {\n return (key.pk?.includes(\"undefined\") ?? false) || (key.sk?.includes(\"undefined\") ?? false);\n }\n}\n","import type { Table } from \"../table\";\nimport type { DynamoItem } from \"../types\";\nimport { IndexBuilder } from \"./ddb-indexing\";\nimport type { IndexDefinition } from \"./entity\";\n\n/**\n * Builds secondary indexes for an item based on the configured indexes\n *\n * @param dataForKeyGeneration - The validated data to generate keys from\n * @param table - The DynamoDB table instance containing GSI configurations\n * @param indexes - The index definitions\n * @param excludeReadOnly - Whether to exclude read-only indexes\n * @returns Record of GSI attribute names to their values\n */\nexport function buildIndexes<T extends DynamoItem>(\n dataForKeyGeneration: T,\n table: Table,\n indexes: Record<string, IndexDefinition<T>> | undefined,\n excludeReadOnly = false,\n): Record<string, string> {\n if (!indexes) {\n return {};\n }\n\n const indexBuilder = new IndexBuilder(table, indexes);\n return indexBuilder.buildForCreate(dataForKeyGeneration, { excludeReadOnly });\n}\n\n/**\n * Builds index updates for an item based on the configured indexes\n *\n * @param currentData - The current data before update\n * @param updates - The update data\n * @param table - The DynamoDB table instance containing GSI configurations\n * @param indexes - The index definitions\n * @param forceRebuildIndexes - Array of index names to force rebuild even if readonly\n * @returns Record of GSI attribute names to their updated values\n */\nexport function buildIndexUpdates<T extends DynamoItem>(\n currentData: T,\n updates: Partial<T>,\n table: Table,\n indexes: Record<string, IndexDefinition<T>> | undefined,\n forceRebuildIndexes?: string[],\n): Record<string, string> {\n if (!indexes) {\n return {};\n }\n\n const indexBuilder = new IndexBuilder(table, indexes);\n return indexBuilder.buildForUpdate(currentData, updates, { forceRebuildIndexes });\n}\n","import type {\n EntityAwareDeleteBuilder,\n EntityAwareGetBuilder,\n EntityAwarePutBuilder,\n EntityAwareUpdateBuilder,\n} from \"../builders/entity-aware-builders\";\nimport {\n createEntityAwareDeleteBuilder,\n createEntityAwareGetBuilder,\n createEntityAwarePutBuilder,\n createEntityAwareUpdateBuilder,\n} from \"../builders/entity-aware-builders\";\nimport type { GetBuilder } from \"../builders/get-builder\";\nimport type { QueryBuilder } from \"../builders/query-builder\";\nimport type { ScanBuilder } from \"../builders/scan-builder\";\nimport { eq, type PrimaryKey, type PrimaryKeyWithoutExpression } from \"../conditions\";\nimport type { StandardSchemaV1, StandardSchemaV1 as StandardSchemaV1Namespace } from \"../standard-schema\";\nimport type { Table } from \"../table\";\nimport type { DynamoItem, Index, TableConfig } from \"../types\";\nimport { buildIndexes as buildEntityIndexes, buildIndexUpdates } from \"./index-utils\";\n\n// Define the QueryFunction type with a generic return type\nexport type QueryFunction<_T extends DynamoItem, I, R> = (input: I) => R;\n\n// Define a type for the query record that preserves the input type for each query function\nexport type QueryFunctionWithSchema<T extends DynamoItem, I, R> = QueryFunction<T, I, R> & {\n schema?: StandardSchemaV1<I>;\n};\n\nexport type QueryRecord<T extends DynamoItem> = {\n // biome-ignore lint/suspicious/noExplicitAny: This is for flexibility\n [K: string]: QueryFunctionWithSchema<T, any, ScanBuilder<T> | QueryBuilder<T, TableConfig> | GetBuilder<T>>;\n};\n\n// Define a type for entity with only scan, get and query methods\nexport type QueryEntity<T extends DynamoItem> = {\n scan: () => ScanBuilder<T>;\n get: (key: PrimaryKeyWithoutExpression) => EntityAwareGetBuilder<T>;\n query: (keyCondition: PrimaryKey) => QueryBuilder<T, TableConfig>;\n};\n\ninterface Settings {\n /**\n * Defaults to \"entityType\"\n */\n entityTypeAttributeName?: string;\n timestamps?: {\n createdAt?: {\n /**\n * ISO vs Unix trade-offs\n *\n * Both options support between, greater than and less than comparisons.\n *\n * ISO:\n * - Human readable, but requires more storage space\n * - Does not work with DynamoDBs TTL feature.\n *\n * UNIX:\n * - Less readable, but requires less storage space.\n * - Works with DynamoDBs TTL feature.\n */\n format: \"ISO\" | \"UNIX\";\n /**\n * Defaults to \"createdAt\"\n */\n attributeName?: string;\n };\n updatedAt?: {\n /**\n * ISO vs Unix trade-offs\n *\n * Both options support between, greater than and less than comparisons.\n *\n * ISO:\n * - Human readable, but requires more storage space\n * - Does not work with DynamoDBs TTL feature.\n *\n * UNIX:\n * - Less readable, but requires less storage space.\n * - Works with DynamoDBs TTL feature.\n */\n format: \"ISO\" | \"UNIX\";\n /**\n * Defaults to \"updatedAt\"\n */\n attributeName?: string;\n };\n };\n}\n\nexport interface EntityConfig<\n T extends DynamoItem,\n TInput extends DynamoItem = T,\n I extends DynamoItem = T,\n Q extends QueryRecord<T> = QueryRecord<T>,\n> {\n name: string;\n schema: StandardSchemaV1<TInput, T>;\n primaryKey: IndexDefinition<I>;\n indexes?: Record<string, IndexDefinition<T>>;\n queries: Q;\n settings?: Settings;\n}\n\nexport interface EntityRepository<\n /**\n * The Entity Type (output type)\n */\n T extends DynamoItem,\n /**\n * The Input Type (for create operations)\n */\n TInput extends DynamoItem = T,\n /**\n * The Primary Index (Partition index) Type\n */\n I extends DynamoItem = T,\n /**\n * The Queries object\n */\n Q extends QueryRecord<T> = QueryRecord<T>,\n> {\n create: (data: TInput) => EntityAwarePutBuilder<T>;\n upsert: (data: TInput & I) => EntityAwarePutBuilder<T>;\n get: (key: I) => EntityAwareGetBuilder<T>;\n update: (key: I, data: Partial<T>) => EntityAwareUpdateBuilder<T>;\n delete: (key: I) => EntityAwareDeleteBuilder;\n query: Q;\n scan: () => ScanBuilder<T>;\n}\n\n/**\n * Creates an entity definition with type-safe operations\n *\n * @example\n * ```typescript\n * interface User {\n * id: string;\n * name: string;\n * }\n *\n * const UserEntity = defineEntity<User>({\n * name: \"User\",\n * schema: userSchema,\n * primaryKey: primaryKey,\n * });\n * ```\n */\nexport function defineEntity<\n T extends DynamoItem,\n TInput extends DynamoItem = T,\n I extends DynamoItem = T,\n Q extends QueryRecord<T> = QueryRecord<T>,\n>(config: EntityConfig<T, TInput, I, Q>) {\n const entityTypeAttributeName = config.settings?.entityTypeAttributeName ?? \"entityType\";\n\n /**\n * Builds secondary indexes for an item based on the configured indexes\n *\n * @param dataForKeyGeneration The validated data to generate keys from\n * @param table The DynamoDB table instance containing GSI configurations\n * @returns Record of GSI attribute names to their values\n */\n const buildIndexes = <TData extends T>(\n dataForKeyGeneration: TData,\n table: Table,\n excludeReadOnly = false,\n ): Record<string, string> => {\n return buildEntityIndexes(dataForKeyGeneration, table, config.indexes, excludeReadOnly);\n };\n\n /**\n * Utility function to wrap a method with preparation logic while preserving all properties\n * for mock compatibility. This reduces boilerplate for withTransaction and withBatch wrappers.\n */\n // biome-ignore lint/suspicious/noExplicitAny: Required for flexible method wrapping\n const wrapMethodWithPreparation = <TMethod extends (...args: any[]) => any>(\n originalMethod: TMethod,\n prepareFn: () => void,\n // biome-ignore lint/suspicious/noExplicitAny: Required for flexible context binding\n context: any,\n ): TMethod => {\n // biome-ignore lint/suspicious/noExplicitAny: Required for flexible argument handling\n const wrappedMethod = (...args: any[]) => {\n prepareFn();\n return originalMethod.call(context, ...args);\n };\n\n // Copy all properties from the original function to preserve mock functionality\n Object.setPrototypeOf(wrappedMethod, originalMethod);\n const propertyNames = Object.getOwnPropertyNames(originalMethod);\n for (let i = 0; i < propertyNames.length; i++) {\n const prop = propertyNames[i] as string;\n if (prop !== \"length\" && prop !== \"name\" && prop !== \"prototype\") {\n // Check if the property is writable before attempting to assign it\n const descriptor = Object.getOwnPropertyDescriptor(originalMethod, prop);\n if (descriptor && descriptor.writable !== false && !descriptor.get) {\n // biome-ignore lint/suspicious/noExplicitAny: meh\n (wrappedMethod as any)[prop] = (originalMethod as any)[prop];\n }\n }\n }\n\n return wrappedMethod as TMethod;\n };\n\n /**\n * Generates an object containing timestamp attributes based on the given configuration settings.\n * The function determines the presence and format of \"createdAt\" and \"updatedAt\" timestamps dynamically.\n *\n * @param {Array<\"createdAt\" | \"updatedAt\">} timestampsToGenerate - Array of timestamp types to generate.\n * @param {Partial<T>} data - Data object to check for existing timestamps.\n * @returns {Record<string, string | number>} An object containing one or both of the \"createdAt\" and \"updatedAt\" timestamp attributes, depending on the configuration and requested types. Each timestamp can be formatted as either an ISO string or a UNIX timestamp.\n */\n const generateTimestamps = (\n timestampsToGenerate: Array<\"createdAt\" | \"updatedAt\">,\n data: Partial<T>,\n ): Record<string, string | number> => {\n if (!config.settings?.timestamps) return {};\n\n const timestamps: Record<string, string | number> = {};\n const now = new Date();\n const unixTime = Math.floor(Date.now() / 1000);\n\n const { createdAt, updatedAt } = config.settings.timestamps;\n\n /**\n * If the data object already has a createdAt value, skip generating it.\n */\n if (createdAt && timestampsToGenerate.includes(\"createdAt\") && !data.createdAt) {\n const name = createdAt.attributeName ?? \"createdAt\";\n timestamps[name] = createdAt.format === \"UNIX\" ? unixTime : now.toISOString();\n }\n\n /**\n * If the data object already has an updatedAt value, skip generating it.\n */\n if (updatedAt && timestampsToGenerate.includes(\"updatedAt\") && !data.updatedAt) {\n const name = updatedAt.attributeName ?? \"updatedAt\";\n timestamps[name] = updatedAt.format === \"UNIX\" ? unixTime : now.toISOString();\n }\n\n return timestamps;\n };\n\n return {\n name: config.name,\n createRepository: (table: Table): EntityRepository<T, TInput, I, Q> => {\n // Create a repository\n const repository = {\n create: (data: TInput) => {\n // Create a minimal builder without validation or key generation\n // We'll defer all processing until execute() or withTransaction() is called\n const builder = table.create<T>({} as T);\n\n // Core function that handles validation, key generation, and item preparation (async version)\n const prepareValidatedItemAsync = async () => {\n // Validate data to ensure defaults are applied before key generation\n const validatedData = await config.schema[\"~standard\"].validate(data);\n\n if (\"issues\" in validatedData && validatedData.issues) {\n throw new Error(`Validation failed: ${validatedData.issues.map((i) => i.message).join(\", \")}`);\n }\n\n const dataForKeyGeneration = {\n ...validatedData.value,\n ...generateTimestamps([\"createdAt\", \"updatedAt\"], validatedData.value),\n };\n\n // Generate the primary key using validated data (with defaults applied)\n const primaryKey = config.primaryKey.generateKey(dataForKeyGeneration as unknown as I);\n\n const indexes = buildEntityIndexes(dataForKeyGeneration, table, config.indexes, false);\n\n const validatedItem = {\n ...(dataForKeyGeneration as unknown as T),\n [entityTypeAttributeName]: config.name,\n [table.partitionKey]: primaryKey.pk,\n ...(table.sortKey ? { [table.sortKey]: primaryKey.sk } : {}),\n ...indexes,\n };\n\n Object.assign(builder, { item: validatedItem });\n return validatedItem;\n };\n\n // Core function that handles validation, key generation, and item preparation (sync version)\n const prepareValidatedItemSync = () => {\n const validationResult = config.schema[\"~standard\"].validate(data);\n\n // Handle Promise case - this shouldn't happen for most schemas, but we need to handle it\n if (validationResult instanceof Promise) {\n throw new Error(\n \"Async validation is not supported in withBatch or withTransaction. The schema must support synchronous validation for compatibility.\",\n );\n }\n\n if (\"issues\" in validationResult && validationResult.issues) {\n throw new Error(`Validation failed: ${validationResult.issues.map((i) => i.message).join(\", \")}`);\n }\n\n const dataForKeyGeneration = {\n ...validationResult.value,\n ...generateTimestamps([\"createdAt\", \"updatedAt\"], validationResult.value),\n };\n\n // Generate the primary key using validated data (with defaults applied)\n const primaryKey = config.primaryKey.generateKey(dataForKeyGeneration as unknown as I);\n\n const indexes = buildEntityIndexes(dataForKeyGeneration, table, config.indexes, false);\n\n const validatedItem = {\n ...(dataForKeyGeneration as unknown as T),\n [entityTypeAttributeName]: config.name,\n [table.partitionKey]: primaryKey.pk,\n ...(table.sortKey ? { [table.sortKey]: primaryKey.sk } : {}),\n ...indexes,\n };\n\n Object.assign(builder, { item: validatedItem });\n return validatedItem;\n };\n\n // Wrap the builder's execute method\n const originalExecute = builder.execute;\n builder.execute = async () => {\n await prepareValidatedItemAsync();\n return await originalExecute.call(builder);\n };\n\n // Wrap the builder's withTransaction method\n const originalWithTransaction = builder.withTransaction;\n if (originalWithTransaction) {\n builder.withTransaction = wrapMethodWithPreparation(\n originalWithTransaction,\n prepareValidatedItemSync,\n builder,\n );\n }\n\n // Wrap the builder's withBatch method\n const originalWithBatch = builder.withBatch;\n if (originalWithBatch) {\n builder.withBatch = wrapMethodWithPreparation(originalWithBatch, prepareValidatedItemSync, builder);\n }\n\n return createEntityAwarePutBuilder(builder, config.name);\n },\n\n upsert: (data: TInput & I) => {\n // Create a minimal builder without validation or key generation\n // We'll defer all processing until execute() or withTransaction() is called\n const builder = table.put<T>({} as T);\n\n // Core function that handles validation, key generation, and item preparation (async version)\n const prepareValidatedItemAsync = async () => {\n const validatedData = await config.schema[\"~standard\"].validate(data);\n\n if (\"issues\" in validatedData && validatedData.issues) {\n throw new Error(`Validation failed: ${validatedData.issues.map((i) => i.message).join(\", \")}`);\n }\n\n const dataForKeyGeneration = {\n ...validatedData.value,\n ...generateTimestamps([\"createdAt\", \"updatedAt\"], validatedData.value),\n };\n\n // Generate the primary key using validated data (with defaults applied)\n const primaryKey = config.primaryKey.generateKey(dataForKeyGeneration as unknown as TInput & I);\n\n const indexes = buildIndexes(dataForKeyGeneration, table, false);\n\n const validatedItem = {\n [table.partitionKey]: primaryKey.pk,\n ...(table.sortKey ? { [table.sortKey]: primaryKey.sk } : {}),\n ...dataForKeyGeneration,\n [entityTypeAttributeName]: config.name,\n ...indexes,\n };\n\n Object.assign(builder, { item: validatedItem });\n return validatedItem;\n };\n\n // Core function that handles validation, key generation, and item preparation (sync version)\n const prepareValidatedItemSync = () => {\n const validationResult = config.schema[\"~standard\"].validate(data);\n\n // Handle Promise case - this shouldn't happen in withTransaction but we need to handle it for type safety\n if (validationResult instanceof Promise) {\n throw new Error(\n \"Async validation is not supported in withTransaction or withBatch. Use execute() instead.\",\n );\n }\n\n if (\"issues\" in validationResult && validationResult.issues) {\n throw new Error(`Validation failed: ${validationResult.issues.map((i) => i.message).join(\", \")}`);\n }\n\n const dataForKeyGeneration = {\n ...validationResult.value,\n ...generateTimestamps([\"createdAt\", \"updatedAt\"], validationResult.value),\n };\n\n // Generate the primary key using validated data (with defaults applied)\n const primaryKey = config.primaryKey.generateKey(dataForKeyGeneration as unknown as TInput & I);\n\n const indexes = buildEntityIndexes(dataForKeyGeneration, table, config.indexes, false);\n\n const validatedItem = {\n [table.partitionKey]: primaryKey.pk,\n ...(table.sortKey ? { [table.sortKey]: primaryKey.sk } : {}),\n ...dataForKeyGeneration,\n [entityTypeAttributeName]: config.name,\n ...indexes,\n };\n\n Object.assign(builder, { item: validatedItem });\n return validatedItem;\n };\n\n // Wrap the builder's execute method\n const originalExecute = builder.execute;\n builder.execute = async () => {\n await prepareValidatedItemAsync();\n const result = await originalExecute.call(builder);\n if (!result) {\n throw new Error(\"Failed to upsert item\");\n }\n return result;\n };\n\n // Wrap the builder's withTransaction method\n const originalWithTransaction = builder.withTransaction;\n if (originalWithTransaction) {\n builder.withTransaction = wrapMethodWithPreparation(\n originalWithTransaction,\n prepareValidatedItemSync,\n builder,\n );\n }\n\n // Wrap the builder's withBatch method\n const originalWithBatch = builder.withBatch;\n if (originalWithBatch) {\n builder.withBatch = wrapMethodWithPreparation(originalWithBatch, prepareValidatedItemSync, builder);\n }\n\n return createEntityAwarePutBuilder(builder, config.name);\n },\n\n get: <K extends I>(key: K) => {\n return createEntityAwareGetBuilder(table.get<T>(config.primaryKey.generateKey(key)), config.name);\n },\n\n update: <K extends I>(key: K, data: Partial<T>) => {\n const primaryKeyObj = config.primaryKey.generateKey(key);\n const builder = table.update<T>(primaryKeyObj);\n\n builder.condition(eq(entityTypeAttributeName, config.name));\n\n // Create entity-aware builder with entity-specific functionality\n const entityAwareBuilder = createEntityAwareUpdateBuilder(builder, config.name);\n\n // Configure the entity-aware builder with entity-specific logic\n entityAwareBuilder.configureEntityLogic({\n data,\n key: key as unknown as T,\n table,\n indexes: config.indexes,\n generateTimestamps: () => generateTimestamps([\"updatedAt\"], data),\n buildIndexUpdates,\n });\n\n return entityAwareBuilder;\n },\n\n delete: <K extends I>(key: K) => {\n const builder = table.delete(config.primaryKey.generateKey(key));\n builder.condition(eq(entityTypeAttributeName, config.name));\n return createEntityAwareDeleteBuilder(builder, config.name);\n },\n\n query: Object.entries(config.queries || {}).reduce((acc, [key, inputCallback]) => {\n // @ts-expect-error - We need to cast the queryFn to a function that takes an unknown input\n acc[key] = (input: unknown) => {\n // Create a QueryEntity object with only the necessary methods\n const queryEntity: QueryEntity<T> = {\n scan: repository.scan,\n get: (key: PrimaryKeyWithoutExpression) => createEntityAwareGetBuilder(table.get<T>(key), config.name),\n query: (keyCondition: PrimaryKey) => {\n return table.query<T>(keyCondition);\n },\n };\n\n // Execute the query function to get the builder - This type is incorrect and needs to be fixed\n const queryBuilderCallback = inputCallback(input);\n\n // Run the inner handler which allows the user to apply their desired contraints\n // to the query builder of their choice\n // @ts-expect-error - We need to cast the queryBuilderCallback to a function that takes a QueryEntity\n const builder = queryBuilderCallback(queryEntity);\n\n // Add entity type filter if the builder has filter method\n if (builder && typeof builder === \"object\" && \"filter\" in builder && typeof builder.filter === \"function\") {\n builder.filter(eq(entityTypeAttributeName, config.name));\n }\n\n // Wrap the builder's execute method if it exists\n if (builder && typeof builder === \"object\" && \"execute\" in builder) {\n const originalExecute = builder.execute;\n builder.execute = async () => {\n // Validate the input before executing the query\n const queryFn = (\n config.queries as unknown as Record<string, QueryFunctionWithSchema<T, I, typeof builder>>\n )[key];\n\n if (queryFn && typeof queryFn === \"function\") {\n // Get the schema from the query function\n const schema = queryFn.schema;\n if (schema?.[\"~standard\"]?.validate && typeof schema[\"~standard\"].validate === \"function\") {\n const validationResult = schema[\"~standard\"].validate(input);\n if (\"issues\" in validationResult && validationResult.issues) {\n throw new Error(\n `Validation failed: ${validationResult.issues.map((issue) => issue.message).join(\", \")}`,\n );\n }\n }\n }\n\n // Execute the original builder\n const result = await originalExecute.call(builder);\n if (!result) {\n throw new Error(\"Failed to execute query\");\n }\n return result;\n };\n }\n\n return builder;\n };\n return acc;\n }, {} as Q),\n\n scan: () => {\n const builder = table.scan<T>();\n builder.filter(eq(entityTypeAttributeName, config.name));\n return builder;\n },\n };\n\n return repository;\n },\n };\n}\n\nexport function createQueries<T extends DynamoItem>() {\n return {\n input: <I>(schema: StandardSchemaV1<I>) => ({\n query: <\n Q extends QueryRecord<T> = QueryRecord<T>,\n R = ScanBuilder<T> | QueryBuilder<T, TableConfig> | GetBuilder<T>,\n >(\n handler: (params: { input: I; entity: QueryEntity<T> }) => R,\n ) => {\n const queryFn = (input: I) => (entity: QueryEntity<T>) => handler({ input, entity });\n queryFn.schema = schema;\n return queryFn as unknown as QueryFunctionWithSchema<T, I, R>;\n },\n }),\n };\n}\n/**\n * Defines a DynamoDB index configuration\n */\nexport interface IndexDefinition<T extends DynamoItem> extends Index<T> {\n /** The name of the index */\n name: string;\n /** Whether the index is read-only */\n isReadOnly: boolean;\n /** Function to generate the index key from an item */\n generateKey: (item: T) => { pk: string; sk?: string };\n}\n\ntype Result<T> = StandardSchemaV1Namespace.Result<T>;\n\nexport function createIndex() {\n return {\n input: <T extends DynamoItem>(schema: StandardSchemaV1<T>) => {\n const createIndexBuilder = (isReadOnly = false) => ({\n partitionKey: <P extends (item: T) => string>(pkFn: P) => ({\n sortKey: <S extends (item: T) => string>(skFn: S) => {\n const index = {\n name: \"custom\",\n partitionKey: \"pk\",\n sortKey: \"sk\",\n isReadOnly: isReadOnly,\n generateKey: (item: T) => {\n const data = schema[\"~standard\"].validate(item) as Result<T>;\n if (\"issues\" in data && data.issues) {\n throw new Error(`Index validation failed: ${data.issues.map((i) => i.message).join(\", \")}`);\n }\n const validData = \"value\" in data ? data.value : item;\n return { pk: pkFn(validData), sk: skFn(validData) };\n },\n } as IndexDefinition<T>;\n\n return Object.assign(index, {\n readOnly: (value = false) =>\n ({\n ...index,\n isReadOnly: value,\n }) as IndexDefinition<T>,\n });\n },\n\n withoutSortKey: () => {\n const index = {\n name: \"custom\",\n partitionKey: \"pk\",\n isReadOnly: isReadOnly,\n generateKey: (item: T) => {\n const data = schema[\"~standard\"].validate(item) as Result<T>;\n if (\"issues\" in data && data.issues) {\n throw new Error(`Index validation failed: ${data.issues.map((i) => i.message).join(\", \")}`);\n }\n const validData = \"value\" in data ? data.value : item;\n return { pk: pkFn(validData) };\n },\n } as IndexDefinition<T>;\n\n return Object.assign(index, {\n readOnly: (value = true) =>\n ({\n ...index,\n isReadOnly: value,\n }) as IndexDefinition<T>,\n });\n },\n }),\n\n readOnly: (value = true) => createIndexBuilder(value),\n });\n\n return createIndexBuilder(false);\n },\n };\n}\n","import type { Condition, ConditionOperator, PrimaryKeyWithoutExpression } from \"../conditions\";\nimport {\n and,\n attributeExists,\n attributeNotExists,\n beginsWith,\n between,\n contains,\n eq,\n gt,\n gte,\n inArray,\n lt,\n lte,\n ne,\n not,\n or,\n} from \"../conditions\";\nimport { prepareExpressionParams } from \"../expression\";\nimport type { DynamoItem } from \"../types\";\nimport { debugCommand } from \"../utils/debug-expression\";\nimport type { ConditionCheckCommandParams } from \"./builder-types\";\nimport type { TransactionBuilder } from \"./transaction-builder\";\n\n/**\n * Builder for creating DynamoDB condition check operations.\n * Use this builder when you need to:\n * - Verify item state without modifying it\n * - Ensure preconditions in transactions\n * - Implement optimistic locking patterns\n * - Validate business rules\n *\n * @example\n * ```typescript\n * // Check if dinosaur is ready for feeding\n * const check = new ConditionCheckBuilder('dinosaurs', { id: 'TREX-001' })\n * .condition(op =>\n * op.and([\n * op.eq('status', 'HUNTING'),\n * op.gt('stats.hunger', 80),\n * op.lt('stats.health', 100)\n * ])\n * )\n * .toDynamoCommand();\n *\n * // Check habitat security status\n * const securityCheck = new ConditionCheckBuilder('habitats', { id: 'PADDOCK-A' })\n * .condition(op =>\n * op.and([\n * op.eq('securityStatus', 'ACTIVE'),\n * op.attributeExists('lastInspection'),\n * op.lt('threatLevel', 5)\n * ])\n * )\n * .toDynamoCommand();\n * ```\n */\nexport class ConditionCheckBuilder {\n private readonly key: PrimaryKeyWithoutExpression;\n private readonly tableName: string;\n private conditionExpression?: Condition;\n\n constructor(tableName: string, key: PrimaryKeyWithoutExpression) {\n this.tableName = tableName;\n this.key = key;\n }\n\n /**\n * Adds a condition that must be satisfied for the check to succeed.\n *\n * @example\n * ```typescript\n * // Check dinosaur health and behavior\n * builder.condition(op =>\n * op.and([\n * op.gt('stats.health', 50),\n * op.not(op.eq('status', 'SEDATED')),\n * op.lt('aggressionLevel', 8)\n * ])\n * );\n *\n * // Verify habitat conditions\n * builder.condition(op =>\n * op.and([\n * op.eq('powerStatus', 'ONLINE'),\n * op.between('temperature', 20, 30),\n * op.attributeExists('lastMaintenance')\n * ])\n * );\n *\n * // Check breeding conditions\n * builder.condition(op =>\n * op.and([\n * op.eq('species', 'VELOCIRAPTOR'),\n * op.gte('age', 3),\n * op.eq('geneticPurity', 100)\n * ])\n * );\n * ```\n *\n * @param condition - Either a Condition DynamoItem or a callback function that builds the condition\n * @returns The builder instance for method chaining\n */\n condition<T extends DynamoItem>(condition: Condition | ((op: ConditionOperator<T>) => Condition)): this {\n if (typeof condition === \"function\") {\n const conditionOperator: ConditionOperator<T> = {\n eq,\n ne,\n lt,\n lte,\n gt,\n gte,\n between,\n inArray,\n beginsWith,\n contains,\n attributeExists,\n attributeNotExists,\n and,\n or,\n not,\n };\n this.conditionExpression = condition(conditionOperator);\n } else {\n this.conditionExpression = condition;\n }\n return this;\n }\n\n /**\n * Generates the DynamoDB command parameters for direct execution.\n * Use this method when you want to:\n * - Execute the condition check as a standalone operation\n * - Get the raw DynamoDB command for custom execution\n * - Inspect the generated command parameters\n *\n * @example\n * ```ts\n * const command = new ConditionCheckBuilder('myTable', { id: '123' })\n * .condition(op => op.attributeExists('status'))\n * .toDynamoCommand();\n * // Use command with DynamoDB client\n * ```\n *\n * @throws {Error} If no condition has been set\n * @returns The DynamoDB command parameters\n */\n private toDynamoCommand(): ConditionCheckCommandParams {\n if (!this.conditionExpression) {\n throw new Error(\"Condition is required for condition check operations\");\n }\n\n const { expression, names, values } = prepareExpressionParams(this.conditionExpression);\n\n if (!expression) {\n throw new Error(\"Failed to generate condition expression\");\n }\n\n return {\n tableName: this.tableName,\n key: this.key,\n conditionExpression: expression,\n expressionAttributeNames: names,\n expressionAttributeValues: values,\n };\n }\n\n /**\n * Adds this condition check operation to a transaction.\n *\n * @example\n * ```ts\n * const transaction = new TransactionBuilder();\n * new ConditionCheckBuilder('habitats', { id: 'PADDOCK-B' })\n * .condition(op => op.and([\n * op.eq('securityStatus', 'ACTIVE'),\n * op.lt('currentOccupants', 3),\n * op.eq('habitatType', 'CARNIVORE')\n * ]))\n * .withTransaction(transaction);\n * // Add dinosaur transfer operations\n * ```\n *\n * @param transaction - The transaction builder to add this operation to\n * @throws {Error} If no condition has been set\n * @returns The builder instance for method chaining\n */\n withTransaction(transaction: TransactionBuilder): this {\n if (!this.conditionExpression) {\n throw new Error(\"Condition is required for condition check operations\");\n }\n\n const command = this.toDynamoCommand();\n transaction.conditionCheckWithCommand(command);\n\n return this;\n }\n\n /**\n * Gets a human-readable representation of the condition check command\n * with all expression placeholders replaced by their actual values.\n *\n * @example\n * ```ts\n * const debugInfo = new ConditionCheckBuilder('dinosaurs', { id: 'TREX-001' })\n * .condition(op => op.and([\n * op.between('stats.health', 50, 100),\n * op.not(op.eq('status', 'SEDATED')),\n * op.attributeExists('lastFeedingTime')\n * op.eq('version', 1)\n * ]))\n * .debug();\n * console.log(debugInfo);\n * ```\n *\n * @returns A readable representation of the condition check command with resolved expressions\n */\n debug() {\n const command = this.toDynamoCommand();\n return debugCommand(command);\n }\n}\n","import type { ExpressionParams, PrimaryKeyWithoutExpression } from \"../conditions\";\nimport { generateAttributeName } from \"../expression\";\nimport type { DynamoItem } from \"../types\";\nimport type { BatchBuilder } from \"./batch-builder\";\nimport type { Path } from \"./types\";\n\n/**\n * Configuration options for DynamoDB get operations.\n */\nexport interface GetOptions {\n /** List of attributes to return in the result */\n projection?: string[];\n /** Whether to use strongly consistent reads */\n consistentRead?: boolean;\n}\n\n/**\n * Parameters for the DynamoDB get command.\n */\nexport interface GetCommandParams {\n /** The name of the DynamoDB table */\n tableName: string;\n /** The primary key of the item to get */\n key: PrimaryKeyWithoutExpression;\n /** Comma-separated list of attributes to return */\n projectionExpression?: string;\n /** Map of expression attribute name placeholders to actual names */\n expressionAttributeNames?: Record<string, string>;\n /** Whether to use strongly consistent reads */\n consistentRead?: boolean;\n}\n\n/**\n * Function type for executing DynamoDB get operations.\n * @typeParam T - The type of item being retrieved\n */\ntype GetExecutor<T extends DynamoItem> = (params: GetCommandParams) => Promise<{ item: T | undefined }>;\n\n/**\n * Builder for creating DynamoDB get operations.\n * Use this builder when you need to:\n * - Retrieve a single dinosaur by its primary key\n * - Project specific dinosaur attributes\n * - Use consistent reads for critical dinosaur data\n *\n * @example\n * ```typescript\n * // Simple get\n * const result = await new GetBuilder(executor, { pk: 'dinosaur#123', sk: 'profile' })\n * .execute();\n *\n * // Get with projection and consistent read\n * const result = await new GetBuilder(executor, { pk: 'dinosaur#123', sk: 'profile' })\n * .select(['species', 'name', 'diet'])\n * .consistentRead()\n * .execute();\n * ```\n *\n * @typeParam T - The type of item being retrieved\n */\nexport class GetBuilder<T extends DynamoItem> {\n private readonly params: GetCommandParams;\n private options: GetOptions = {};\n private selectedFields: Set<string> = new Set();\n\n /**\n * Creates a new GetBuilder instance.\n *\n * @param executor - Function that executes the get operation\n * @param key - Primary key of the item to retrieve\n * @param tableName - Name of the DynamoDB table\n */\n constructor(\n private readonly executor: GetExecutor<T>,\n key: PrimaryKeyWithoutExpression,\n tableName: string,\n ) {\n this.params = {\n tableName,\n key,\n };\n }\n\n /**\n * Specifies which attributes to return in the get results.\n *\n * @example\n * ```typescript\n * // Select single attribute\n * builder.select('species')\n *\n * // Select multiple attributes\n * builder.select(['id', 'species', 'diet'])\n *\n * // Chain multiple select calls\n * builder\n * .select('id')\n * .select(['species', 'diet'])\n * ```\n *\n * @param fields - A single field name or an array of field names to return\n * @returns The builder instance for method chaining\n */\n select<K extends Path<T>>(fields: K | K[]): GetBuilder<T> {\n if (typeof fields === \"string\") {\n this.selectedFields.add(fields);\n } else if (Array.isArray(fields)) {\n for (const field of fields) {\n this.selectedFields.add(field);\n }\n }\n\n this.options.projection = Array.from(this.selectedFields);\n return this;\n }\n\n /**\n * Sets whether to use strongly consistent reads for the get operation.\n * Use this method when you need:\n * - The most up-to-date dinosaur data\n * - To ensure you're reading the latest dinosaur status\n * - Critical safety information about dangerous species\n *\n * Note: Consistent reads consume twice the throughput\n *\n * @example\n * ```typescript\n * // Get the latest T-Rex data\n * const result = await new GetBuilder(executor, { pk: 'dinosaur#123', sk: 'profile' })\n * .consistentRead()\n * .execute();\n * ```\n *\n * @param consistentRead - Whether to use consistent reads (defaults to true)\n * @returns The builder instance for method chaining\n */\n consistentRead(consistentRead = true): GetBuilder<T> {\n this.params.consistentRead = consistentRead;\n return this;\n }\n\n /**\n * Adds this get operation to a batch with optional entity type information.\n *\n * @example Basic Usage\n * ```ts\n * const batch = table.batchBuilder();\n *\n * // Add multiple get operations to batch\n * dinosaurRepo.get({ id: 'dino-1' }).withBatch(batch);\n * dinosaurRepo.get({ id: 'dino-2' }).withBatch(batch);\n * dinosaurRepo.get({ id: 'dino-3' }).withBatch(batch);\n *\n * // Execute all gets efficiently\n * const results = await batch.execute();\n * ```\n *\n * @example Typed Usage\n * ```ts\n * const batch = table.batchBuilder<{\n * User: UserEntity;\n * Order: OrderEntity;\n * }>();\n *\n * // Add operations with type information\n * userRepo.get({ id: 'user-1' }).withBatch(batch, 'User');\n * orderRepo.get({ id: 'order-1' }).withBatch(batch, 'Order');\n *\n * // Execute and get typed results\n * const result = await batch.execute();\n * const users: UserEntity[] = result.reads.itemsByType.User;\n * const orders: OrderEntity[] = result.reads.itemsByType.Order;\n * ```\n *\n * @param batch - The batch builder to add this operation to\n * @param entityType - Optional entity type key for type tracking\n */\n public withBatch<\n TEntities extends Record<string, DynamoItem> = Record<string, DynamoItem>,\n K extends keyof TEntities = keyof TEntities,\n >(batch: BatchBuilder<TEntities>, entityType?: K) {\n const command = this.toDynamoCommand();\n batch.getWithCommand(command, entityType);\n }\n\n /**\n * Converts the builder configuration to a DynamoDB command\n */\n private toDynamoCommand(): GetCommandParams {\n const expressionParams: ExpressionParams = {\n expressionAttributeNames: {},\n expressionAttributeValues: {},\n valueCounter: { count: 0 },\n };\n\n const projectionExpression = Array.from(this.selectedFields)\n .map((p) => generateAttributeName(expressionParams, p))\n .join(\", \");\n\n const { expressionAttributeNames } = expressionParams;\n\n return {\n ...this.params,\n projectionExpression: projectionExpression.length > 0 ? projectionExpression : undefined,\n expressionAttributeNames: Object.keys(expressionAttributeNames).length > 0 ? expressionAttributeNames : undefined,\n };\n }\n\n /**\n * Executes the get operation against DynamoDB.\n *\n * @example\n * ```typescript\n * try {\n * const result = await new GetBuilder(executor, { pk: 'dinosaur#123', sk: 'profile' })\n * .select(['species', 'name', 'diet'])\n * .consistentRead()\n * .execute();\n *\n * if (result.item) {\n * console.log('Dinosaur found:', result.item);\n * } else {\n * console.log('Dinosaur not found');\n * }\n * } catch (error) {\n * console.error('Error getting dinosaur:', error);\n * }\n * ```\n *\n * @returns A promise that resolves to an object containing:\n * - item: The retrieved dinosaur or undefined if not found\n */\n async execute(): Promise<{ item: T | undefined }> {\n const command = this.toDynamoCommand();\n return this.executor(command);\n }\n}\n","import type { Condition } from \"../conditions\";\nimport type { DynamoItem, TableConfig } from \"../types\";\nimport type { ScanBuilderInterface } from \"./builder-types\";\nimport { FilterBuilder, type FilterOptions } from \"./filter-builder\";\nimport { ResultIterator } from \"./result-iterator\";\n\n/**\n * Configuration options for DynamoDB scan operations.\n * Extends the base FilterOptions.\n */\nexport type ScanOptions = FilterOptions;\n\n/**\n * Function type for executing DynamoDB filter operations.\n * @typeParam T - The type of items being filtered\n */\nexport type ScanExecutor<T extends DynamoItem> = (\n options: ScanOptions,\n) => Promise<{ items: T[]; lastEvaluatedKey?: DynamoItem }>;\n\n/**\n * Builder for creating DynamoDB scan operations.\n * Use this builder when you need to:\n * - Scan all items in a table\n * - Filter results based on non-key attributes\n * - Scan items on a Secondary Index (GSI)\n * - Implement pagination\n * - Project specific attributes\n *\n * The builder supports:\n * - Type-safe GSI selection\n * - Complex filter conditions\n * - Automatic pagination handling\n * - Consistent reads\n * - Attribute projection\n *\n * @example\n * ```typescript\n * // Simple scan with filtering\n * const result = await new ScanBuilder(executor)\n * .filter(op => op.eq('status', 'ACTIVE'))\n * .execute();\n *\n * // Scan with GSI and filtering\n * const result = await new ScanBuilder(executor)\n * .useIndex('status-index')\n * .filter(op => op.gt('securityLevel', 8))\n * .select(['id', 'capacity', 'currentOccupants'])\n * .limit(10)\n * .execute();\n *\n * // Scan with pagination\n * const paginator = new ScanBuilder(executor)\n * .filter(op => op.eq('type', 'INCIDENT'))\n * .paginate(25);\n *\n * while (paginator.hasNextPage()) {\n * const page = await paginator.getNextPage();\n * // Process page.items\n * }\n * ```\n *\n * @typeParam T - The type of items being scanned\n * @typeParam TConfig - The table configuration type for type-safe GSI selection\n */\nexport class ScanBuilder<T extends DynamoItem, TConfig extends TableConfig = TableConfig>\n extends FilterBuilder<T, TConfig>\n implements ScanBuilderInterface<T, TConfig>\n{\n protected readonly executor: ScanExecutor<T>;\n\n constructor(executor: ScanExecutor<T>) {\n super();\n this.executor = executor;\n }\n\n /**\n * Creates a deep clone of this ScanBuilder instance.\n *\n * @returns A new ScanBuilder instance with the same configuration\n */\n clone(): ScanBuilder<T, TConfig> {\n const clone = new ScanBuilder<T, TConfig>(this.executor);\n clone.options = {\n ...this.options,\n filter: this.deepCloneFilter(this.options.filter),\n };\n clone.selectedFields = new Set(this.selectedFields);\n return clone;\n }\n\n private deepCloneFilter(filter: Condition | undefined): Condition | undefined {\n if (!filter) return filter;\n if (filter.type === \"and\" || filter.type === \"or\") {\n return {\n ...filter,\n conditions: filter.conditions\n ?.map((condition) => this.deepCloneFilter(condition))\n .filter((c): c is Condition => c !== undefined),\n };\n }\n return { ...filter };\n }\n\n /**\n * Executes the scan against DynamoDB and returns a generator that behaves like an array.\n *\n * The generator automatically handles pagination and provides array-like methods\n * for processing results efficiently without loading everything into memory at once.\n *\n * @example\n * ```typescript\n * try {\n * // Find all dinosaurs with high aggression levels with automatic pagination\n * const results = await new ScanBuilder(executor)\n * .filter(op =>\n * op.and([\n * op.eq('status', 'ACTIVE'),\n * op.gt('aggressionLevel', 7)\n * ])\n * )\n * .execute();\n *\n * // Use like an array with automatic pagination\n * for await (const dinosaur of results) {\n * console.log(`Processing dangerous dinosaur: ${dinosaur.name}`);\n * }\n *\n * // Or convert to array and use array methods\n * const allItems = await results.toArray();\n * const criticalThreats = allItems.filter(dino => dino.aggressionLevel > 9);\n * const totalCount = allItems.length;\n * } catch (error) {\n * console.error('Security scan failed:', error);\n * }\n * ```\n *\n * @returns A promise that resolves to a ResultGenerator that behaves like an array\n */\n async execute(): Promise<ResultIterator<T, TConfig>> {\n const directExecutor = () => this.executor(this.options);\n return new ResultIterator(this, directExecutor);\n }\n}\n","/**\n * Generator function to create chunks of an array on-demand\n * This is more memory-efficient than creating all chunks at once\n *\n * @param array The array to chunk\n * @param size The size of each chunk\n * @returns A generator that yields chunks of the array\n */\nexport function* chunkArray<T>(array: T[], size: number): Generator<T[], void, unknown> {\n if (size <= 0) {\n throw new Error(\"Chunk size must be greater than 0\");\n }\n for (let i = 0; i < array.length; i += size) {\n yield array.slice(i, i + size);\n }\n}\n","import type {\n DynamoDBDocument,\n QueryCommandInput,\n ScanCommandInput,\n TransactWriteCommandInput,\n} from \"@aws-sdk/lib-dynamodb\";\nimport { BatchBuilder } from \"./builders/batch-builder\";\nimport type { DeleteCommandParams, PutCommandParams, UpdateCommandParams } from \"./builders/builder-types\";\nimport { ConditionCheckBuilder } from \"./builders/condition-check-builder\";\nimport { DeleteBuilder } from \"./builders/delete-builder\";\nimport { GetBuilder, type GetCommandParams } from \"./builders/get-builder\";\nimport { PutBuilder } from \"./builders/put-builder\";\nimport { QueryBuilder, type QueryOptions } from \"./builders/query-builder\";\nimport type { ScanOptions } from \"./builders/scan-builder\";\nimport { ScanBuilder } from \"./builders/scan-builder\";\nimport { TransactionBuilder, type TransactionOptions } from \"./builders/transaction-builder\";\nimport type { Path } from \"./builders/types\";\nimport { UpdateBuilder } from \"./builders/update-builder\";\nimport {\n and,\n beginsWith,\n between,\n type Condition,\n type ConditionOperator,\n type ExpressionParams,\n eq,\n gt,\n gte,\n type KeyConditionOperator,\n lt,\n lte,\n type PrimaryKey,\n type PrimaryKeyWithoutExpression,\n} from \"./conditions\";\nimport { buildExpression, generateAttributeName } from \"./expression\";\nimport type { BatchWriteOperation } from \"./operation-types\";\nimport type { DynamoItem, Index, TableConfig } from \"./types\";\nimport { chunkArray } from \"./utils/chunk-array\";\nimport { debugCommand } from \"./utils/debug-expression\";\n\nconst DDB_BATCH_WRITE_LIMIT = 25;\nconst DDB_BATCH_GET_LIMIT = 100;\nconst _DDB_TRANSACT_GET_LIMIT = 100;\nconst _DDB_TRANSACT_WRITE_LIMIT = 100;\n\nexport class Table<TConfig extends TableConfig = TableConfig> {\n private readonly dynamoClient: DynamoDBDocument;\n readonly tableName: string;\n /**\n * The column name of the partitionKey for the Table\n */\n readonly partitionKey: string;\n /**\n * The column name of the sortKey for the Table\n */\n readonly sortKey?: string;\n /**\n * The Global Secondary Indexes that are configured on this table\n */\n readonly gsis: Record<string, Index>;\n\n constructor(config: TConfig) {\n this.dynamoClient = config.client;\n\n this.tableName = config.tableName;\n this.partitionKey = config.indexes.partitionKey;\n this.sortKey = config.indexes.sortKey;\n\n this.gsis = config.indexes.gsis || {};\n }\n\n protected createKeyForPrimaryIndex(keyCondition: PrimaryKeyWithoutExpression): Record<string, unknown> {\n const primaryCondition = { [this.partitionKey]: keyCondition.pk };\n\n // If the table has a sort key, we need to add it to the condition\n if (this.sortKey) {\n if (!keyCondition.sk) {\n throw new Error(\"Sort key has not been provided but the Table has a sort key\");\n }\n // Apply the sort key condition\n primaryCondition[this.sortKey] = keyCondition.sk;\n }\n\n return primaryCondition;\n }\n\n /**\n * Creates a new item in the table, it will fail if the item already exists.\n *\n * By default, this method returns the input values passed to the create operation\n * upon successful creation.\n *\n * You can customise the return behaviour by chaining the `.returnValues()` method:\n *\n * @param item The item to create\n * @returns A PutBuilder instance for chaining additional conditions and executing the create operation\n *\n * @example\n * ```ts\n * // Create with default behavior (returns input values)\n * const result = await table.create({\n * id: 'user-123',\n * name: 'John Doe',\n * email: 'john@example.com'\n * }).execute();\n * console.log(result); // Returns the input object\n *\n * // Create with no return value for better performance\n * await table.create(userData).returnValues('NONE').execute();\n *\n * // Create and get fresh data from dynamodb using a strongly consistent read\n * const freshData = await table.create(userData).returnValues('CONSISTENT').execute();\n *\n * // Create and get previous values (if the item was overwritten)\n * const oldData = await table.create(userData).returnValues('ALL_OLD').execute();\n * ```\n */\n create<T extends DynamoItem>(item: T): PutBuilder<T> {\n return this.put(item)\n .condition((op: ConditionOperator<T>) => op.attributeNotExists(this.partitionKey as Path<T>))\n .returnValues(\"INPUT\");\n }\n\n get<T extends DynamoItem>(keyCondition: PrimaryKeyWithoutExpression): GetBuilder<T> {\n const executor = async (params: GetCommandParams): Promise<{ item: T | undefined }> => {\n try {\n const result = await this.dynamoClient.get({\n TableName: params.tableName,\n Key: this.createKeyForPrimaryIndex(keyCondition),\n ProjectionExpression: params.projectionExpression,\n ExpressionAttributeNames: params.expressionAttributeNames,\n ConsistentRead: params.consistentRead,\n });\n\n return {\n item: result.Item ? (result.Item as T) : undefined,\n };\n } catch (error) {\n console.error(\"Error getting item:\", error);\n throw error;\n }\n };\n\n return new GetBuilder<T>(executor, keyCondition, this.tableName);\n }\n\n /**\n * Updates an item in the table\n *\n * @param item The item to update\n * @returns A PutBuilder instance for chaining conditions and executing the put operation\n */\n put<T extends DynamoItem>(item: T): PutBuilder<T> {\n // Define the executor function that will be called when execute() is called on the builder\n const executor = async (params: PutCommandParams): Promise<T> => {\n try {\n const result = await this.dynamoClient.put({\n TableName: params.tableName,\n Item: params.item,\n ConditionExpression: params.conditionExpression,\n ExpressionAttributeNames: params.expressionAttributeNames,\n ExpressionAttributeValues: params.expressionAttributeValues,\n // CONSISTENT and INPUT are not valid ReturnValues for DDB, so we set NONE as we are not interested in its\n // response and will be handling these cases separately\n ReturnValues:\n params.returnValues === \"CONSISTENT\" || params.returnValues === \"INPUT\" ? \"NONE\" : params.returnValues,\n });\n\n // Handle different return value options\n if (params.returnValues === \"INPUT\") {\n // Return the input values that were passed to the operation\n // this is fairly common for create operations when using entities\n return params.item as T;\n }\n\n // Reload the item from the DB, so the user gets the most correct representation of the item from the DB\n if (params.returnValues === \"CONSISTENT\") {\n const getResult = await this.dynamoClient.get({\n TableName: params.tableName,\n Key: this.createKeyForPrimaryIndex({\n pk: params.item[this.partitionKey] as string,\n ...(this.sortKey && { sk: params.item[this.sortKey] as string }),\n }),\n ConsistentRead: true,\n });\n\n return getResult.Item as T;\n }\n\n return result.Attributes as T;\n } catch (error) {\n console.error(\"Error creating item:\", error);\n throw error;\n }\n };\n\n return new PutBuilder<T>(executor, item, this.tableName);\n }\n\n /**\n * Creates a query builder for complex queries\n * If useIndex is called on the returned QueryBuilder, it will use the GSI configuration\n */\n query<T extends DynamoItem>(keyCondition: PrimaryKey): QueryBuilder<T, TConfig> {\n // Default to main table's partition and sort keys\n const pkAttributeName = this.partitionKey;\n const skAttributeName = this.sortKey;\n\n // Create the key condition expression using the main table's keys\n let keyConditionExpression = eq(pkAttributeName, keyCondition.pk);\n\n if (keyCondition.sk) {\n if (!skAttributeName) {\n throw new Error(\"Sort key is not defined for Index\");\n }\n\n const keyConditionOperator: KeyConditionOperator = {\n eq: (value) => eq(skAttributeName, value),\n lt: (value) => lt(skAttributeName, value),\n lte: (value) => lte(skAttributeName, value),\n gt: (value) => gt(skAttributeName, value),\n gte: (value) => gte(skAttributeName, value),\n between: (lower, upper) => between(skAttributeName, lower, upper),\n beginsWith: (value) => beginsWith(skAttributeName, value),\n and: (...conditions) => and(...conditions),\n };\n\n const skCondition = keyCondition.sk(keyConditionOperator);\n\n // Create a key condition expression\n keyConditionExpression = and(eq(pkAttributeName, keyCondition.pk), skCondition);\n }\n\n const executor = async (originalKeyCondition: Condition, options: QueryOptions) => {\n // Start with the original key condition\n let finalKeyCondition = originalKeyCondition;\n\n // If an index is specified, we need to adjust the query based on the GSI configuration\n if (options.indexName) {\n const gsiName = String(options.indexName);\n const gsi = this.gsis[gsiName];\n\n if (!gsi) {\n throw new Error(`GSI with name \"${gsiName}\" does not exist on table \"${this.tableName}\"`);\n }\n\n // For GSI queries, we need to rebuild the key condition expression using the GSI's keys\n const gsiPkAttributeName = gsi.partitionKey;\n const gsiSkAttributeName = gsi.sortKey;\n\n // Extract the partition key value from the original condition\n // This is a simplification - in a real implementation, you might need more complex logic\n // to extract the correct values from the original condition\n let pkValue: unknown | undefined;\n let skValue: unknown | undefined;\n let extractedSkCondition: Condition | undefined;\n\n // Extract values from the original key condition\n if (originalKeyCondition.type === \"eq\") {\n pkValue = originalKeyCondition.value;\n } else if (originalKeyCondition.type === \"and\" && originalKeyCondition.conditions) {\n // Find the partition key condition\n const pkCondition = originalKeyCondition.conditions.find(\n (c) => c.type === \"eq\" && c.attr === pkAttributeName,\n );\n if (pkCondition && pkCondition.type === \"eq\") {\n pkValue = pkCondition.value;\n }\n\n // Find any sort key conditions\n const skConditions = originalKeyCondition.conditions.filter((c) => c.attr === skAttributeName);\n if (skConditions.length > 0) {\n if (skConditions.length === 1) {\n extractedSkCondition = skConditions[0];\n if (extractedSkCondition && extractedSkCondition.type === \"eq\") {\n skValue = extractedSkCondition.value;\n }\n } else if (skConditions.length > 1) {\n extractedSkCondition = and(...skConditions);\n }\n }\n }\n\n if (!pkValue) {\n throw new Error(\"Could not extract partition key value from key condition\");\n }\n\n // Build a new key condition expression for the GSI\n let gsiKeyCondition = eq(gsiPkAttributeName, pkValue);\n\n // Add sort key condition if applicable\n if (skValue && gsiSkAttributeName) {\n gsiKeyCondition = and(gsiKeyCondition, eq(gsiSkAttributeName, skValue));\n } else if (extractedSkCondition && gsiSkAttributeName) {\n // Replace the attribute name in the condition with the GSI sort key\n // We need to create a deep copy to avoid modifying the original condition\n // This is a simplified approach - a real implementation would need to handle all condition types\n if (extractedSkCondition.attr === skAttributeName) {\n const updatedSkCondition = {\n ...extractedSkCondition,\n attr: gsiSkAttributeName,\n };\n gsiKeyCondition = and(gsiKeyCondition, updatedSkCondition);\n } else {\n // If the attribute name doesn't match the table's sort key, use it as is\n gsiKeyCondition = and(gsiKeyCondition, extractedSkCondition);\n }\n }\n\n // Use the GSI-specific key condition\n finalKeyCondition = gsiKeyCondition;\n }\n\n // Implementation of the query execution logic\n const expressionParams: ExpressionParams = {\n expressionAttributeNames: {},\n expressionAttributeValues: {},\n valueCounter: { count: 0 },\n };\n\n const keyConditionExpression = buildExpression(finalKeyCondition, expressionParams);\n\n let filterExpression: string | undefined;\n if (options.filter) {\n filterExpression = buildExpression(options.filter, expressionParams);\n }\n\n const projectionExpression = options.projection\n ?.map((p) => generateAttributeName(expressionParams, p))\n .join(\", \");\n\n const { expressionAttributeNames, expressionAttributeValues } = expressionParams;\n const { indexName, limit, consistentRead, scanIndexForward, lastEvaluatedKey } = options;\n\n const params: QueryCommandInput = {\n TableName: this.tableName,\n KeyConditionExpression: keyConditionExpression,\n FilterExpression: filterExpression,\n ExpressionAttributeNames: expressionAttributeNames,\n ExpressionAttributeValues: expressionAttributeValues,\n IndexName: indexName,\n Limit: limit,\n ConsistentRead: consistentRead,\n ScanIndexForward: scanIndexForward,\n ProjectionExpression: projectionExpression,\n ExclusiveStartKey: lastEvaluatedKey,\n };\n\n try {\n const result = await this.dynamoClient.query(params);\n return {\n items: result.Items as T[],\n lastEvaluatedKey: result.LastEvaluatedKey,\n };\n } catch (error) {\n console.log(debugCommand(params));\n console.error(\"Error querying items:\", error);\n throw error;\n }\n };\n\n return new QueryBuilder<T, TConfig>(executor, keyConditionExpression);\n }\n\n /**\n * Creates a scan builder for scanning the entire table\n * Use this when you need to:\n * - Process all items in a table\n * - Apply filters to a large dataset\n * - Use a GSI for scanning\n *\n * @returns A ScanBuilder instance for chaining operations\n */\n scan<T extends DynamoItem>(): ScanBuilder<T, TConfig> {\n const executor = async (options: ScanOptions) => {\n // Implementation of the scan execution logic\n const expressionParams: ExpressionParams = {\n expressionAttributeNames: {},\n expressionAttributeValues: {},\n valueCounter: { count: 0 },\n };\n\n let filterExpression: string | undefined;\n if (options.filter) {\n filterExpression = buildExpression(options.filter, expressionParams);\n }\n\n const projectionExpression = options.projection\n ?.map((p) => generateAttributeName(expressionParams, p))\n .join(\", \");\n\n const { expressionAttributeNames, expressionAttributeValues } = expressionParams;\n const { indexName, limit, consistentRead, lastEvaluatedKey } = options;\n\n const params: ScanCommandInput = {\n TableName: this.tableName,\n FilterExpression: filterExpression,\n ExpressionAttributeNames:\n Object.keys(expressionAttributeNames).length > 0 ? expressionAttributeNames : undefined,\n ExpressionAttributeValues:\n Object.keys(expressionAttributeValues).length > 0 ? expressionAttributeValues : undefined,\n IndexName: indexName,\n Limit: limit,\n ConsistentRead: consistentRead,\n ProjectionExpression: projectionExpression,\n ExclusiveStartKey: lastEvaluatedKey,\n };\n\n try {\n const result = await this.dynamoClient.scan(params);\n return {\n items: result.Items as T[],\n lastEvaluatedKey: result.LastEvaluatedKey,\n };\n } catch (error) {\n console.log(debugCommand(params));\n console.error(\"Error scanning items:\", error);\n throw error;\n }\n };\n\n return new ScanBuilder<T, TConfig>(executor);\n }\n\n delete(keyCondition: PrimaryKeyWithoutExpression): DeleteBuilder {\n const executor = async (params: DeleteCommandParams) => {\n try {\n const result = await this.dynamoClient.delete({\n TableName: params.tableName,\n Key: this.createKeyForPrimaryIndex(keyCondition),\n ConditionExpression: params.conditionExpression,\n ExpressionAttributeNames: params.expressionAttributeNames,\n ExpressionAttributeValues: params.expressionAttributeValues,\n ReturnValues: params.returnValues,\n });\n return {\n item: result.Attributes as DynamoItem,\n };\n } catch (error) {\n console.error(\"Error deleting item:\", error);\n throw error;\n }\n };\n\n return new DeleteBuilder(executor, this.tableName, keyCondition);\n }\n\n /**\n * Updates an item in the table\n *\n * @param keyCondition The primary key of the item to update\n * @returns An UpdateBuilder instance for chaining update operations and conditions\n */\n update<T extends DynamoItem>(keyCondition: PrimaryKeyWithoutExpression): UpdateBuilder<T> {\n const executor = async (params: UpdateCommandParams) => {\n try {\n const result = await this.dynamoClient.update({\n TableName: params.tableName,\n Key: this.createKeyForPrimaryIndex(keyCondition),\n UpdateExpression: params.updateExpression,\n ConditionExpression: params.conditionExpression,\n ExpressionAttributeNames: params.expressionAttributeNames,\n ExpressionAttributeValues: params.expressionAttributeValues,\n ReturnValues: params.returnValues,\n });\n return {\n item: result.Attributes as T,\n };\n } catch (error) {\n console.error(\"Error updating item:\", error);\n throw error;\n }\n };\n\n return new UpdateBuilder<T>(executor, this.tableName, keyCondition);\n }\n\n /**\n * Creates a transaction builder for performing multiple operations atomically\n */\n transactionBuilder(): TransactionBuilder {\n // Create an executor function for the transaction\n const executor = async (params: TransactWriteCommandInput): Promise<void> => {\n await this.dynamoClient.transactWrite(params);\n };\n\n // Create a transaction builder with the executor and table's index configuration\n return new TransactionBuilder(executor, {\n partitionKey: this.partitionKey,\n sortKey: this.sortKey,\n });\n }\n\n /**\n * Creates a batch builder for performing multiple operations efficiently with optional type inference\n *\n * @example Basic Usage\n * ```typescript\n * const batch = table.batchBuilder();\n *\n * // Add operations\n * userRepo.create(newUser).withBatch(batch);\n * orderRepo.get({ id: 'order-1' }).withBatch(batch);\n *\n * // Execute operations\n * const result = await batch.execute();\n * ```\n *\n * @example Typed Usage\n * ```typescript\n * // Define entity types for the batch\n * const batch = table.batchBuilder<{\n * User: UserEntity;\n * Order: OrderEntity;\n * Product: ProductEntity;\n * }>();\n *\n * // Add operations with type information\n * userRepo.create(newUser).withBatch(batch, 'User');\n * orderRepo.get({ id: 'order-1' }).withBatch(batch, 'Order');\n * productRepo.delete({ id: 'old-product' }).withBatch(batch, 'Product');\n *\n * // Execute and get typed results\n * const result = await batch.execute();\n * const users: UserEntity[] = result.reads.itemsByType.User;\n * const orders: OrderEntity[] = result.reads.itemsByType.Order;\n * ```\n */\n batchBuilder<TEntities extends Record<string, DynamoItem> = Record<string, DynamoItem>>(): BatchBuilder<TEntities> {\n // Create executor functions for batch operations\n const batchWriteExecutor = async (operations: Array<BatchWriteOperation<DynamoItem>>) => {\n return this.batchWrite(operations);\n };\n\n const batchGetExecutor = async (keys: Array<PrimaryKeyWithoutExpression>) => {\n return this.batchGet(keys);\n };\n\n // Create a batch builder with the executors and table's index configuration\n return new BatchBuilder<TEntities>(batchWriteExecutor, batchGetExecutor, {\n partitionKey: this.partitionKey,\n sortKey: this.sortKey,\n });\n }\n\n /**\n * Executes a transaction using a callback function\n *\n * @param callback A function that receives a transaction context and performs operations on it\n * @param options Optional transaction options\n * @returns A promise that resolves when the transaction is complete\n */\n async transaction(\n callback: (tx: TransactionBuilder) => Promise<void> | void,\n options?: TransactionOptions,\n ): Promise<void> {\n // Create an executor function for the transaction\n const transactionExecutor = async (params: TransactWriteCommandInput): Promise<void> => {\n await this.dynamoClient.transactWrite(params);\n };\n\n // Create a transaction builder with the executor and table's index configuration\n const transaction = new TransactionBuilder(transactionExecutor, {\n partitionKey: this.partitionKey,\n sortKey: this.sortKey,\n });\n\n if (options) {\n transaction.withOptions(options);\n }\n\n const result = await callback(transaction);\n await transaction.execute();\n\n return result;\n }\n\n /**\n * Creates a condition check operation for use in transactions\n *\n * This is useful for when you require a transaction to succeed only when a specific condition is met on a\n * a record within the database that you are not directly updating.\n *\n * For example, you are updating a record and you want to ensure that another record exists and/or has a specific value before proceeding.\n */\n conditionCheck(keyCondition: PrimaryKeyWithoutExpression): ConditionCheckBuilder {\n return new ConditionCheckBuilder(this.tableName, keyCondition);\n }\n\n /**\n * Performs a batch get operation to retrieve multiple items at once\n *\n * @param keys Array of primary keys to retrieve\n * @returns A promise that resolves to the retrieved items\n */\n async batchGet<T extends DynamoItem>(\n keys: Array<PrimaryKeyWithoutExpression>,\n ): Promise<{ items: T[]; unprocessedKeys: PrimaryKeyWithoutExpression[] }> {\n const allItems: T[] = [];\n const allUnprocessedKeys: PrimaryKeyWithoutExpression[] = [];\n\n // Process each chunk from the generator\n for (const chunk of chunkArray(keys, DDB_BATCH_GET_LIMIT)) {\n const formattedKeys = chunk.map((key) => ({\n [this.partitionKey]: key.pk,\n ...(this.sortKey ? { [this.sortKey]: key.sk } : {}),\n }));\n\n const params = {\n RequestItems: {\n [this.tableName]: {\n Keys: formattedKeys,\n },\n },\n };\n\n try {\n const result = await this.dynamoClient.batchGet(params);\n\n // Add the retrieved items to our result\n if (result.Responses?.[this.tableName]) {\n allItems.push(...(result.Responses[this.tableName] as T[]));\n }\n\n // Track any unprocessed keys\n const unprocessedKeysArray = result.UnprocessedKeys?.[this.tableName]?.Keys || [];\n const unprocessedKeys = unprocessedKeysArray.map((key) => ({\n pk: key[this.partitionKey] as string,\n sk: this.sortKey ? (key[this.sortKey] as string) : undefined,\n }));\n\n if (unprocessedKeys.length > 0) {\n allUnprocessedKeys.push(...unprocessedKeys);\n }\n } catch (error) {\n console.error(\"Error in batch get operation:\", error);\n throw error;\n }\n }\n\n return {\n items: allItems,\n unprocessedKeys: allUnprocessedKeys,\n };\n }\n\n /**\n * Performs a batch write operation to put or delete multiple items at once\n *\n * @param operations Array of put or delete operations\n * @returns A promise that resolves to any unprocessed operations\n */\n async batchWrite<T extends DynamoItem>(\n operations: Array<BatchWriteOperation<T>>,\n ): Promise<{ unprocessedItems: Array<BatchWriteOperation<T>> }> {\n const allUnprocessedItems: Array<BatchWriteOperation<T>> = [];\n\n // Process each chunk from the generator\n for (const chunk of chunkArray(operations, DDB_BATCH_WRITE_LIMIT)) {\n const writeRequests = chunk.map((operation) => {\n if (operation.type === \"put\") {\n return {\n PutRequest: {\n Item: operation.item,\n },\n };\n }\n\n return {\n DeleteRequest: {\n Key: this.createKeyForPrimaryIndex(operation.key),\n },\n };\n });\n\n const params = {\n RequestItems: {\n [this.tableName]: writeRequests,\n },\n };\n\n try {\n const result = await this.dynamoClient.batchWrite(params);\n\n // Track any unprocessed items\n const unprocessedRequestsArray = result.UnprocessedItems?.[this.tableName] || [];\n\n if (unprocessedRequestsArray.length > 0) {\n const unprocessedItems = unprocessedRequestsArray.map((request) => {\n if (request?.PutRequest?.Item) {\n return {\n type: \"put\" as const,\n item: request.PutRequest.Item as T,\n };\n }\n\n if (request?.DeleteRequest?.Key) {\n return {\n type: \"delete\" as const,\n key: {\n pk: request.DeleteRequest.Key[this.partitionKey] as string,\n sk: this.sortKey ? (request.DeleteRequest.Key[this.sortKey] as string) : undefined,\n },\n };\n }\n\n // This should never happen, but TypeScript needs a fallback\n throw new Error(\"Invalid unprocessed item format returned from DynamoDB\");\n });\n\n allUnprocessedItems.push(...unprocessedItems);\n }\n } catch (error) {\n console.error(\"Error in batch write operation:\", error);\n throw error;\n }\n }\n\n return {\n unprocessedItems: allUnprocessedItems,\n };\n }\n}\n","export type StrictGenerateType<T extends readonly string[]> = {\n [K in T[number]]: string;\n};\n\n/**\n * Creates a template function for generating DynamoDB partition keys with dynamic values.\n * Use this function when you need to:\n * - Create consistent partition key patterns with variable parts\n * - Generate partition keys that follow a specific format\n * - Ensure type safety for partition key parameters\n * - Require all parameters to be provided\n *\n * @example\n * ```ts\n * // Define a partition key template\n * const pk = partitionKey`country#${\"country\"}#enclosure#${\"enclosure\"}`;\n *\n * // Generate a partition key (all parameters required)\n * const key = pk({ country: \"NZ\", enclosure: \"A1\" });\n * // Result: \"country#NZ#enclosure#A1\"\n *\n * // Type checking ensures all parameters are provided\n * const invalidKey = pk({ country: \"NZ\" }); // TypeScript error\n * ```\n *\n * @param strings - The static parts of the template string\n * @param keys - The dynamic parts of the template string that will be replaced with values\n *\n * @returns A function that accepts an object with the dynamic values and returns the formatted partition key\n */\nexport function partitionKey<T extends readonly string[]>(\n strings: TemplateStringsArray,\n ...keys: T\n): (params: StrictGenerateType<T>) => string {\n return (params) => {\n let result = strings[0] ?? \"\";\n\n for (let i = 0; i < keys.length; i++) {\n const key = keys[i];\n if (key) {\n result += params[key as T[number]] + (strings[i + 1] ?? \"\");\n }\n }\n\n return result;\n };\n}\n","export type GenerateType<T extends readonly string[], U extends string = never> = T extends [infer F, ...infer R]\n ? F extends string\n ? R extends string[]\n ? ({ [K in F | U]: string | number } & Partial<Record<Exclude<T[number], F | U>, never>>) | GenerateType<R, F | U>\n : never\n : never\n : never;\n\n/**\n * Creates a template function for generating DynamoDB sort keys with dynamic values.\n * Use this function when you need to:\n * - Create consistent sort key patterns with variable parts\n * - Generate sort keys that follow a specific format\n * - Ensure type safety for sort key parameters\n *\n * @example\n * ```ts\n * // Define a sort key template\n * const sk = sortKey`country#${\"country\"}#enclosure#${\"enclosure\"}#diet#${\"diet\"}`;\n *\n * // Generate a sort key with partial parameters\n * const templatedString = sk({ country: \"NZ\", enclosure: \"A1\" });\n * // Result: \"country#NZ#enclosure#A1#diet#\"\n *\n * // Generate a complete sort key\n * const fullKey = sk({ country: \"NZ\", enclosure: \"A1\", diet: \"carnivore\" });\n * // Result: \"country#NZ#enclosure#A1#diet#carnivore\"\n *\n * // Type checking ensures only valid parameters are used\n * const invalidKey = sk({ country: \"NZ\", invalid: \"value\" }); // TypeScript error\n * ```\n *\n * @param strings - The static parts of the template string\n * @param keys - The dynamic parts of the template string that will be replaced with values\n *\n * @returns A function that accepts an object with the dynamic values and returns the formatted sort key\n */\nexport function sortKey<T extends readonly string[]>(\n strings: TemplateStringsArray,\n ...keys: T\n): (params: GenerateType<T>) => string {\n return (params) => {\n let result = strings[0] ?? \"\";\n\n for (let i = 0; i < keys.length; i++) {\n const key = keys[i];\n\n if (key && params && key in params) {\n result += params[key] + (strings[i + 1] ?? \"\");\n }\n }\n\n return result;\n };\n}\n"]}