@farukada/aws-langgraph-dynamodb-ts 1.0.0-rc.1 → 1.0.0-rc.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (324) hide show
  1. package/README.md +1621 -288
  2. package/dist/backfill/backfill.d.ts +168 -0
  3. package/dist/backfill/backfill.js +393 -0
  4. package/dist/checkpointer/actions/delete-thread.d.ts +44 -4
  5. package/dist/checkpointer/actions/delete-thread.js +56 -22
  6. package/dist/checkpointer/actions/get-tuple.d.ts +29 -5
  7. package/dist/checkpointer/actions/get-tuple.js +41 -13
  8. package/dist/checkpointer/actions/list.d.ts +42 -10
  9. package/dist/checkpointer/actions/list.js +86 -57
  10. package/dist/checkpointer/actions/put-writes.d.ts +41 -9
  11. package/dist/checkpointer/actions/put-writes.js +62 -48
  12. package/dist/checkpointer/actions/put.d.ts +82 -10
  13. package/dist/checkpointer/actions/put.js +166 -44
  14. package/dist/checkpointer/internal/delta-history.d.ts +112 -0
  15. package/dist/checkpointer/internal/delta-history.js +252 -0
  16. package/dist/checkpointer/internal/listing.d.ts +149 -0
  17. package/dist/checkpointer/internal/listing.js +245 -0
  18. package/dist/checkpointer/internal/parse.d.ts +262 -0
  19. package/dist/checkpointer/internal/parse.js +372 -0
  20. package/dist/checkpointer/internal/pending-writes.d.ts +275 -0
  21. package/dist/checkpointer/internal/pending-writes.js +588 -0
  22. package/dist/checkpointer/internal/read.d.ts +130 -0
  23. package/dist/checkpointer/internal/read.js +264 -0
  24. package/dist/checkpointer/internal/rows.d.ts +571 -0
  25. package/dist/checkpointer/internal/rows.js +834 -0
  26. package/dist/checkpointer/internal/setup.d.ts +42 -21
  27. package/dist/checkpointer/internal/setup.js +65 -31
  28. package/dist/checkpointer/saver.d.ts +242 -42
  29. package/dist/checkpointer/saver.js +257 -53
  30. package/dist/checkpointer/types.d.ts +37 -44
  31. package/dist/checkpointer/types.js +10 -0
  32. package/dist/factory/factory.d.ts +120 -11
  33. package/dist/factory/factory.js +195 -16
  34. package/dist/factory/types.d.ts +23 -4
  35. package/dist/factory/types.js +8 -0
  36. package/dist/history/actions/add-messages.d.ts +30 -2
  37. package/dist/history/actions/add-messages.js +37 -57
  38. package/dist/history/actions/clear.d.ts +46 -4
  39. package/dist/history/actions/clear.js +64 -15
  40. package/dist/history/actions/get-messages.d.ts +41 -0
  41. package/dist/history/actions/get-messages.js +94 -32
  42. package/dist/history/actions/list-sessions.d.ts +52 -10
  43. package/dist/history/actions/list-sessions.js +141 -38
  44. package/dist/history/actions/reconcile-count.d.ts +41 -8
  45. package/dist/history/actions/reconcile-count.js +44 -57
  46. package/dist/history/chat-message-history.d.ts +200 -38
  47. package/dist/history/chat-message-history.js +218 -51
  48. package/dist/history/internal/append.d.ts +212 -0
  49. package/dist/history/internal/append.js +500 -0
  50. package/dist/history/internal/message-read.d.ts +84 -0
  51. package/dist/history/internal/message-read.js +204 -0
  52. package/dist/history/internal/parse.d.ts +153 -0
  53. package/dist/history/internal/parse.js +252 -0
  54. package/dist/history/internal/rows.d.ts +195 -0
  55. package/dist/history/internal/rows.js +250 -0
  56. package/dist/history/internal/session.d.ts +331 -0
  57. package/dist/history/internal/session.js +628 -0
  58. package/dist/history/internal/setup.d.ts +52 -19
  59. package/dist/history/internal/setup.js +90 -27
  60. package/dist/history/session-adapter.d.ts +95 -6
  61. package/dist/history/session-adapter.js +99 -8
  62. package/dist/history/types.d.ts +61 -31
  63. package/dist/history/types.js +10 -0
  64. package/dist/index.d.ts +38 -14
  65. package/dist/index.js +31 -12
  66. package/dist/shared/adapter.d.ts +135 -0
  67. package/dist/shared/adapter.js +143 -0
  68. package/dist/shared/clock.d.ts +48 -4
  69. package/dist/shared/clock.js +51 -4
  70. package/dist/shared/codec/codec.d.ts +275 -9
  71. package/dist/shared/codec/codec.js +394 -19
  72. package/dist/shared/codec/compression.d.ts +43 -6
  73. package/dist/shared/codec/compression.js +52 -11
  74. package/dist/shared/codec/json-serde.d.ts +76 -3
  75. package/dist/shared/codec/json-serde.js +181 -7
  76. package/dist/shared/codec/s3/client-types.d.ts +20 -1
  77. package/dist/shared/codec/s3/client-types.js +20 -1
  78. package/dist/shared/codec/s3/client.d.ts +35 -8
  79. package/dist/shared/codec/s3/client.js +61 -10
  80. package/dist/shared/codec/s3/config.d.ts +226 -22
  81. package/dist/shared/codec/s3/config.js +274 -24
  82. package/dist/shared/codec/s3/lifecycle.d.ts +163 -11
  83. package/dist/shared/codec/s3/lifecycle.js +328 -36
  84. package/dist/shared/codec/s3/offloader.d.ts +390 -19
  85. package/dist/shared/codec/s3/offloader.js +590 -50
  86. package/dist/shared/concurrency.d.ts +40 -3
  87. package/dist/shared/concurrency.js +55 -7
  88. package/dist/shared/dynamodb/abort.d.ts +45 -7
  89. package/dist/shared/dynamodb/abort.js +46 -14
  90. package/dist/shared/dynamodb/batch-write.d.ts +77 -13
  91. package/dist/shared/dynamodb/batch-write.js +146 -26
  92. package/dist/shared/dynamodb/cancellation.d.ts +121 -3
  93. package/dist/shared/dynamodb/cancellation.js +147 -2
  94. package/dist/shared/dynamodb/client.d.ts +159 -12
  95. package/dist/shared/dynamodb/client.js +135 -10
  96. package/dist/shared/dynamodb/idempotent-write.d.ts +551 -0
  97. package/dist/shared/dynamodb/idempotent-write.js +593 -0
  98. package/dist/shared/dynamodb/paginate.d.ts +105 -8
  99. package/dist/shared/dynamodb/paginate.js +175 -6
  100. package/dist/shared/dynamodb/partition-delete.d.ts +181 -16
  101. package/dist/shared/dynamodb/partition-delete.js +312 -43
  102. package/dist/shared/dynamodb/recency-index.d.ts +231 -0
  103. package/dist/shared/dynamodb/recency-index.js +377 -0
  104. package/dist/shared/dynamodb/retry.d.ts +265 -10
  105. package/dist/shared/dynamodb/retry.js +426 -20
  106. package/dist/shared/dynamodb/table-schema.d.ts +190 -0
  107. package/dist/shared/dynamodb/table-schema.js +209 -0
  108. package/dist/shared/errors/base-error.d.ts +174 -8
  109. package/dist/shared/errors/base-error.js +154 -7
  110. package/dist/shared/errors/boundary.d.ts +63 -10
  111. package/dist/shared/errors/boundary.js +110 -13
  112. package/dist/shared/errors/classify.d.ts +97 -0
  113. package/dist/shared/errors/classify.js +257 -0
  114. package/dist/shared/errors/error-code.d.ts +76 -1
  115. package/dist/shared/errors/error-code.js +83 -1
  116. package/dist/shared/errors/errors.d.ts +157 -58
  117. package/dist/shared/errors/errors.js +218 -93
  118. package/dist/shared/logging/logger.d.ts +63 -1
  119. package/dist/shared/logging/logger.js +97 -2
  120. package/dist/shared/logging/redaction.d.ts +86 -6
  121. package/dist/shared/logging/redaction.js +265 -24
  122. package/dist/shared/logging/secret-patterns.d.ts +136 -24
  123. package/dist/shared/logging/secret-patterns.js +165 -30
  124. package/dist/shared/logging/truncate.d.ts +197 -0
  125. package/dist/shared/logging/truncate.js +231 -0
  126. package/dist/shared/options.d.ts +52 -5
  127. package/dist/shared/options.js +9 -0
  128. package/dist/shared/ulid.d.ts +71 -14
  129. package/dist/shared/ulid.js +77 -14
  130. package/dist/shared/validation/collaborators.d.ts +141 -0
  131. package/dist/shared/validation/collaborators.js +188 -0
  132. package/dist/shared/validation/option-shape.d.ts +89 -0
  133. package/dist/shared/validation/option-shape.js +113 -0
  134. package/dist/shared/validation/options.d.ts +142 -5
  135. package/dist/shared/validation/options.js +284 -46
  136. package/dist/shared/validation/primitives.d.ts +287 -24
  137. package/dist/shared/validation/primitives.js +347 -42
  138. package/dist/shared/validation/ttl.d.ts +61 -12
  139. package/dist/shared/validation/ttl.js +102 -22
  140. package/dist/store/actions/list-namespaces.d.ts +76 -5
  141. package/dist/store/actions/list-namespaces.js +160 -22
  142. package/dist/store/actions/put.d.ts +33 -7
  143. package/dist/store/actions/put.js +53 -71
  144. package/dist/store/actions/reconcile-vector-index.d.ts +28 -8
  145. package/dist/store/actions/reconcile-vector-index.js +33 -13
  146. package/dist/store/actions/search.d.ts +34 -5
  147. package/dist/store/actions/search.js +52 -20
  148. package/dist/store/internal/batch-plan.d.ts +24 -9
  149. package/dist/store/internal/batch-plan.js +91 -34
  150. package/dist/store/internal/filter.d.ts +36 -2
  151. package/dist/store/internal/filter.js +66 -14
  152. package/dist/store/internal/get-item.d.ts +45 -0
  153. package/dist/store/internal/get-item.js +115 -0
  154. package/dist/store/internal/item-write.d.ts +230 -0
  155. package/dist/store/internal/item-write.js +463 -0
  156. package/dist/store/internal/parse.d.ts +225 -0
  157. package/dist/store/internal/parse.js +350 -0
  158. package/dist/store/internal/rows.d.ts +355 -0
  159. package/dist/store/internal/rows.js +447 -0
  160. package/dist/store/internal/semantic-search.d.ts +146 -12
  161. package/dist/store/internal/semantic-search.js +317 -15
  162. package/dist/store/internal/setup.d.ts +86 -21
  163. package/dist/store/internal/setup.js +209 -26
  164. package/dist/store/internal/table-search.d.ts +100 -0
  165. package/dist/store/internal/table-search.js +213 -0
  166. package/dist/store/internal/vector-index.d.ts +247 -0
  167. package/dist/store/internal/vector-index.js +546 -0
  168. package/dist/store/store.d.ts +258 -33
  169. package/dist/store/store.js +309 -53
  170. package/dist/store/types.d.ts +74 -28
  171. package/dist/store/types.js +13 -0
  172. package/dist/store/vector-backend.d.ts +64 -3
  173. package/dist/store/vector-backend.js +15 -0
  174. package/package.json +41 -25
  175. package/dist/checkpointer/internal/assemble.d.ts +0 -17
  176. package/dist/checkpointer/internal/assemble.js +0 -38
  177. package/dist/checkpointer/internal/checkpoint-write-verify.d.ts +0 -24
  178. package/dist/checkpointer/internal/checkpoint-write-verify.js +0 -67
  179. package/dist/checkpointer/internal/configurable.d.ts +0 -12
  180. package/dist/checkpointer/internal/configurable.js +0 -24
  181. package/dist/checkpointer/internal/fetch.d.ts +0 -19
  182. package/dist/checkpointer/internal/fetch.js +0 -88
  183. package/dist/checkpointer/internal/filter-match.d.ts +0 -13
  184. package/dist/checkpointer/internal/filter-match.js +0 -15
  185. package/dist/checkpointer/internal/item-reader.d.ts +0 -66
  186. package/dist/checkpointer/internal/item-reader.js +0 -113
  187. package/dist/checkpointer/internal/item-writer.d.ts +0 -35
  188. package/dist/checkpointer/internal/item-writer.js +0 -107
  189. package/dist/checkpointer/internal/keys.d.ts +0 -41
  190. package/dist/checkpointer/internal/keys.js +0 -117
  191. package/dist/checkpointer/internal/list-scope.d.ts +0 -61
  192. package/dist/checkpointer/internal/list-scope.js +0 -108
  193. package/dist/checkpointer/internal/pending-sends.d.ts +0 -13
  194. package/dist/checkpointer/internal/pending-sends.js +0 -29
  195. package/dist/checkpointer/internal/query.d.ts +0 -21
  196. package/dist/checkpointer/internal/query.js +0 -42
  197. package/dist/checkpointer/internal/regular-write.d.ts +0 -28
  198. package/dist/checkpointer/internal/regular-write.js +0 -66
  199. package/dist/checkpointer/internal/special-write-cas.d.ts +0 -29
  200. package/dist/checkpointer/internal/special-write-cas.js +0 -104
  201. package/dist/checkpointer/internal/special-write-cleanup.d.ts +0 -23
  202. package/dist/checkpointer/internal/special-write-cleanup.js +0 -50
  203. package/dist/checkpointer/internal/special-write-verify.d.ts +0 -53
  204. package/dist/checkpointer/internal/special-write-verify.js +0 -80
  205. package/dist/checkpointer/internal/stored-channels.d.ts +0 -31
  206. package/dist/checkpointer/internal/stored-channels.js +0 -70
  207. package/dist/checkpointer/internal/validation.d.ts +0 -18
  208. package/dist/checkpointer/internal/validation.js +0 -40
  209. package/dist/checkpointer/internal/write-guard.d.ts +0 -20
  210. package/dist/checkpointer/internal/write-guard.js +0 -48
  211. package/dist/checkpointer/internal/write-index.d.ts +0 -36
  212. package/dist/checkpointer/internal/write-index.js +0 -41
  213. package/dist/history/internal/append-saga.d.ts +0 -25
  214. package/dist/history/internal/append-saga.js +0 -79
  215. package/dist/history/internal/compensation.d.ts +0 -25
  216. package/dist/history/internal/compensation.js +0 -92
  217. package/dist/history/internal/item-mapper.d.ts +0 -9
  218. package/dist/history/internal/item-mapper.js +0 -27
  219. package/dist/history/internal/keys.d.ts +0 -16
  220. package/dist/history/internal/keys.js +0 -48
  221. package/dist/history/internal/message-chunker.d.ts +0 -13
  222. package/dist/history/internal/message-chunker.js +0 -67
  223. package/dist/history/internal/message-transaction.d.ts +0 -25
  224. package/dist/history/internal/message-transaction.js +0 -61
  225. package/dist/history/internal/message-window.d.ts +0 -17
  226. package/dist/history/internal/message-window.js +0 -49
  227. package/dist/history/internal/query.d.ts +0 -23
  228. package/dist/history/internal/query.js +0 -39
  229. package/dist/history/internal/session-count.d.ts +0 -47
  230. package/dist/history/internal/session-count.js +0 -115
  231. package/dist/history/internal/session-title.d.ts +0 -19
  232. package/dist/history/internal/session-title.js +0 -43
  233. package/dist/history/internal/session-update.d.ts +0 -27
  234. package/dist/history/internal/session-update.js +0 -69
  235. package/dist/history/internal/title-generator.d.ts +0 -12
  236. package/dist/history/internal/title-generator.js +0 -41
  237. package/dist/history/internal/ttl-anchor.d.ts +0 -24
  238. package/dist/history/internal/ttl-anchor.js +0 -38
  239. package/dist/history/internal/validation.d.ts +0 -25
  240. package/dist/history/internal/validation.js +0 -53
  241. package/dist/shared/codec/descriptor-keys.d.ts +0 -12
  242. package/dist/shared/codec/descriptor-keys.js +0 -14
  243. package/dist/shared/codec/encode.d.ts +0 -13
  244. package/dist/shared/codec/encode.js +0 -43
  245. package/dist/shared/codec/payload-loss.d.ts +0 -12
  246. package/dist/shared/codec/payload-loss.js +0 -38
  247. package/dist/shared/codec/s3/adapter-config.d.ts +0 -13
  248. package/dist/shared/codec/s3/adapter-config.js +0 -22
  249. package/dist/shared/codec/s3/bounded-body.d.ts +0 -14
  250. package/dist/shared/codec/s3/bounded-body.js +0 -47
  251. package/dist/shared/codec/s3/delete.d.ts +0 -7
  252. package/dist/shared/codec/s3/delete.js +0 -28
  253. package/dist/shared/codec/s3/key-scope.d.ts +0 -23
  254. package/dist/shared/codec/s3/key-scope.js +0 -44
  255. package/dist/shared/codec/s3/orphans.d.ts +0 -23
  256. package/dist/shared/codec/s3/orphans.js +0 -71
  257. package/dist/shared/codec/s3/read-write.d.ts +0 -18
  258. package/dist/shared/codec/s3/read-write.js +0 -51
  259. package/dist/shared/codec/s3/retry.d.ts +0 -5
  260. package/dist/shared/codec/s3/retry.js +0 -22
  261. package/dist/shared/constants.d.ts +0 -112
  262. package/dist/shared/constants.js +0 -115
  263. package/dist/shared/dynamodb/backoff.d.ts +0 -15
  264. package/dist/shared/dynamodb/backoff.js +0 -48
  265. package/dist/shared/dynamodb/conditional-put.d.ts +0 -67
  266. package/dist/shared/dynamodb/conditional-put.js +0 -76
  267. package/dist/shared/dynamodb/drain-unprocessed.d.ts +0 -21
  268. package/dist/shared/dynamodb/drain-unprocessed.js +0 -43
  269. package/dist/shared/dynamodb/expiry.d.ts +0 -16
  270. package/dist/shared/dynamodb/expiry.js +0 -29
  271. package/dist/shared/dynamodb/paginate-core.d.ts +0 -24
  272. package/dist/shared/dynamodb/paginate-core.js +0 -82
  273. package/dist/shared/dynamodb/retry-classifier.d.ts +0 -17
  274. package/dist/shared/dynamodb/retry-classifier.js +0 -118
  275. package/dist/shared/dynamodb/retry-policy.d.ts +0 -26
  276. package/dist/shared/dynamodb/retry-policy.js +0 -22
  277. package/dist/shared/dynamodb/scan.d.ts +0 -14
  278. package/dist/shared/dynamodb/scan.js +0 -19
  279. package/dist/shared/dynamodb/types.d.ts +0 -23
  280. package/dist/shared/dynamodb/types.js +0 -2
  281. package/dist/shared/errors/upstream-error.d.ts +0 -16
  282. package/dist/shared/errors/upstream-error.js +0 -27
  283. package/dist/shared/errors/wrap-error.d.ts +0 -7
  284. package/dist/shared/errors/wrap-error.js +0 -15
  285. package/dist/shared/logging/redaction-walk.d.ts +0 -23
  286. package/dist/shared/logging/redaction-walk.js +0 -112
  287. package/dist/store/actions/get.d.ts +0 -13
  288. package/dist/store/actions/get.js +0 -73
  289. package/dist/store/internal/backend-search.d.ts +0 -4
  290. package/dist/store/internal/backend-search.js +0 -74
  291. package/dist/store/internal/candidates.d.ts +0 -23
  292. package/dist/store/internal/candidates.js +0 -94
  293. package/dist/store/internal/index-reconcile.d.ts +0 -21
  294. package/dist/store/internal/index-reconcile.js +0 -118
  295. package/dist/store/internal/index-sync.d.ts +0 -10
  296. package/dist/store/internal/index-sync.js +0 -25
  297. package/dist/store/internal/item-mapper.d.ts +0 -27
  298. package/dist/store/internal/item-mapper.js +0 -61
  299. package/dist/store/internal/keys.d.ts +0 -17
  300. package/dist/store/internal/keys.js +0 -41
  301. package/dist/store/internal/namespace-match.d.ts +0 -11
  302. package/dist/store/internal/namespace-match.js +0 -40
  303. package/dist/store/internal/option-validation.d.ts +0 -13
  304. package/dist/store/internal/option-validation.js +0 -77
  305. package/dist/store/internal/overwrite-swap.d.ts +0 -32
  306. package/dist/store/internal/overwrite-swap.js +0 -68
  307. package/dist/store/internal/persist.d.ts +0 -28
  308. package/dist/store/internal/persist.js +0 -64
  309. package/dist/store/internal/query.d.ts +0 -11
  310. package/dist/store/internal/query.js +0 -48
  311. package/dist/store/internal/ranker.d.ts +0 -18
  312. package/dist/store/internal/ranker.js +0 -39
  313. package/dist/store/internal/read-existing.d.ts +0 -23
  314. package/dist/store/internal/read-existing.js +0 -41
  315. package/dist/store/internal/score-direction.d.ts +0 -31
  316. package/dist/store/internal/score-direction.js +0 -38
  317. package/dist/store/internal/search-filter.d.ts +0 -3
  318. package/dist/store/internal/search-filter.js +0 -10
  319. package/dist/store/internal/text-path.d.ts +0 -17
  320. package/dist/store/internal/text-path.js +0 -147
  321. package/dist/store/internal/validation.d.ts +0 -18
  322. package/dist/store/internal/validation.js +0 -51
  323. package/dist/store/internal/write-verify.d.ts +0 -42
  324. package/dist/store/internal/write-verify.js +0 -71
@@ -1,90 +1,328 @@
1
1
  "use strict";
2
+ /**
3
+ * Hides which adapter-wide construction options are accepted.
4
+ *
5
+ * The table name, the client choice, the ttl, the retry policy, the recency
6
+ * index, the read concurrency, compression and S3 offload are checked here with
7
+ * their bounds, before an adapter builds anything, so a misconfiguration
8
+ * surfaces at construction rather than on the first call.
9
+ */
2
10
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.validateBaseAdapterOptions = validateBaseAdapterOptions;
11
+ exports.MAX_READ_CONCURRENCY = exports.MAX_RETRY_DELAY_MS = exports.MAX_RETRY_ATTEMPTS = exports.MAX_PAYLOAD_BUFFER_BYTES = void 0;
12
+ exports.assertTableName = assertTableName;
13
+ exports.assertClientChoice = assertClientChoice;
14
+ exports.assertRetryBounds = assertRetryBounds;
15
+ exports.assertRetryPolicy = assertRetryPolicy;
16
+ exports.assertBaseAdapterOptions = assertBaseAdapterOptions;
17
+ exports.assertCompression = assertCompression;
18
+ exports.assertS3 = assertS3;
19
+ const codec_1 = require("../codec/codec");
4
20
  const config_1 = require("../codec/s3/config");
5
- const constants_1 = require("../constants");
21
+ const recency_index_1 = require("../dynamodb/recency-index");
6
22
  const errors_1 = require("../errors/errors");
23
+ const option_shape_1 = require("./option-shape");
7
24
  const primitives_1 = require("./primitives");
8
25
  const ttl_1 = require("./ttl");
9
26
  /** DynamoDB's table-name rule: 3–255 characters from `[A-Za-z0-9_.-]`. */
10
27
  const TABLE_NAME_PATTERN = /^[A-Za-z0-9_.-]{3,255}$/;
11
- /** Server-side encryption algorithms S3 accepts for `PutObject`. */
12
- const SSE_ALGORITHMS = ['AES256', 'aws:kms', 'aws:kms:dsse'];
13
- function validateTableName(tableName) {
28
+ /**
29
+ * Largest `s3.maxDownloadBytes`/`compression.maxDecompressedBytes` an adapter
30
+ * accepts (512 MiB): both hold one buffer fully resident while it is read or
31
+ * inflated, and `BaseAdapterOptions.readConcurrency`'s doc multiplies the two
32
+ * together into the package's memory ceiling, so an unbounded value here is an
33
+ * unbounded process, not just an unbounded object.
34
+ */
35
+ exports.MAX_PAYLOAD_BUFFER_BYTES = 512 * 1024 * 1024;
36
+ /** Largest `retry.maxAttempts` an adapter accepts; beyond it a retry loop is a hang, not a policy. */
37
+ exports.MAX_RETRY_ATTEMPTS = 100;
38
+ /**
39
+ * Largest `retry.baseDelayMs`/`retry.maxDelayMs` an adapter accepts (one
40
+ * minute): combined with {@link MAX_RETRY_ATTEMPTS}, an unbounded per-attempt
41
+ * delay turns a bounded attempt count back into an effectively unbounded wait.
42
+ */
43
+ exports.MAX_RETRY_DELAY_MS = 60_000;
44
+ /**
45
+ * Largest `readConcurrency` an adapter accepts: it is a multiplier on the
46
+ * memory-ceiling formula (see the option's own doc) and on requests fired at
47
+ * once, so an unbounded value turns a typo into an out-of-memory crash or a
48
+ * request storm against the table/bucket.
49
+ */
50
+ exports.MAX_READ_CONCURRENCY = 128;
51
+ const RETRY_KEYS = (0, option_shape_1.allKeysOf)({
52
+ maxAttempts: 'maxAttempts',
53
+ baseDelayMs: 'baseDelayMs',
54
+ maxDelayMs: 'maxDelayMs',
55
+ });
56
+ /**
57
+ * Validate a table name against DynamoDB's own naming rule.
58
+ *
59
+ * Accepts: `tableName` — as the caller gave it.
60
+ *
61
+ * Returns: nothing: the value is kept under its declared type, and this
62
+ * checks it.
63
+ *
64
+ * Throws: `VALIDATION` naming `tableName`.
65
+ */
66
+ function assertTableName(tableName) {
14
67
  if (typeof tableName !== 'string' || !TABLE_NAME_PATTERN.test(tableName)) {
15
- throw new errors_1.ValidationError('tableName must be 3-255 characters from [A-Za-z0-9_.-], as DynamoDB requires', 'tableName');
68
+ throw (0, errors_1.validationError)('tableName must be 3-255 characters from [A-Za-z0-9_.-], as DynamoDB requires', 'tableName');
16
69
  }
17
70
  }
18
71
  /**
19
- * An injected `client` is used as-is, so a `clientConfig` or `createClient`
20
- * given alongside it would be silently ignored — including a `region` the
21
- * caller believes is in effect. Reject the combination instead.
72
+ * Reject a client choice that names two ways of getting one, or a
73
+ * `clientConfig` that is not an object.
74
+ *
75
+ * Accepts: the three client options, from an adapter or from the factory that
76
+ * defaults them. An injected `client` is used as-is, so a `clientConfig` or
77
+ * `createClient` given alongside it would be silently ignored — including a
78
+ * `region` the caller believes is in effect. `clientConfig`, when given, must
79
+ * be an object that is neither `null` nor an array; what it holds is the AWS
80
+ * SDK's to judge.
81
+ *
82
+ * Returns: nothing: the value is kept under its declared type, and this
83
+ * checks it.
84
+ *
85
+ * Throws: `VALIDATION` naming `client` for both ways at once, then
86
+ * `clientConfig` for one that is not an object.
22
87
  */
23
- function validateClientChoice(options) {
88
+ function assertClientChoice(options) {
24
89
  if (options.client &&
25
90
  (options.clientConfig !== undefined || options.createClient !== undefined)) {
26
- throw new errors_1.ValidationError('provide either `client` or `clientConfig`/`createClient`, not both: an injected client ' +
91
+ throw (0, errors_1.validationError)('provide either `client` or `clientConfig`/`createClient`, not both: an injected client ' +
27
92
  'is used as-is and the configuration would be silently ignored', 'client');
28
93
  }
94
+ // The shape only, never the keys, and on purpose: they are the AWS SDK's
95
+ // `DynamoDBClientConfig`, which gains keys between SDK releases, and an
96
+ // application may install a newer SDK than the one this package was
97
+ // compiled against, so a key list compiled in here would refuse valid
98
+ // configuration. The SDK reads each key itself.
99
+ if (options.clientConfig !== undefined)
100
+ (0, option_shape_1.assertObjectShape)(options.clientConfig, 'clientConfig');
29
101
  }
30
- function validateRetryPolicy(policy) {
102
+ /**
103
+ * The three numeric bounds every retry policy shares, regardless of which
104
+ * other keys the caller's own type allows beyond them. Split out so a caller
105
+ * with a wider surface than {@link RetryPolicy} (`backfillRecencyIndex`'s
106
+ * `RetryOptions`, which also exposes `onRetry`, `isRetryable` and friends)
107
+ * can reuse the identical bounds without going through {@link
108
+ * assertRetryPolicy}'s narrower `assertShape`, which would refuse those
109
+ * extra keys outright.
110
+ *
111
+ * Accepts: `policy` — its `maxAttempts`, `baseDelayMs` and `maxDelayMs`, each
112
+ * optional.
113
+ *
114
+ * Returns: nothing: the value is kept under its declared type, and this
115
+ * checks it.
116
+ *
117
+ * Throws: `VALIDATION` naming `retry.maxAttempts`, `retry.baseDelayMs` or
118
+ * `retry.maxDelayMs`.
119
+ */
120
+ function assertRetryBounds(policy) {
31
121
  if (policy.maxAttempts !== undefined) {
32
- (0, primitives_1.validateInteger)(policy.maxAttempts, 'retry.maxAttempts', { min: 1, max: constants_1.MAX_RETRY_ATTEMPTS });
122
+ (0, primitives_1.assertInteger)(policy.maxAttempts, 'retry.maxAttempts', { min: 1, max: exports.MAX_RETRY_ATTEMPTS });
33
123
  }
34
124
  if (policy.baseDelayMs !== undefined) {
35
- (0, primitives_1.validateInteger)(policy.baseDelayMs, 'retry.baseDelayMs', { min: 1 });
125
+ (0, primitives_1.assertInteger)(policy.baseDelayMs, 'retry.baseDelayMs', { min: 1, max: exports.MAX_RETRY_DELAY_MS });
36
126
  }
37
127
  if (policy.maxDelayMs !== undefined) {
38
- (0, primitives_1.validateInteger)(policy.maxDelayMs, 'retry.maxDelayMs', { min: policy.baseDelayMs ?? 1 });
128
+ (0, primitives_1.assertInteger)(policy.maxDelayMs, 'retry.maxDelayMs', {
129
+ min: policy.baseDelayMs ?? 1,
130
+ max: exports.MAX_RETRY_DELAY_MS,
131
+ });
132
+ }
133
+ }
134
+ /**
135
+ * Validate a retry policy: shape, then each bound.
136
+ *
137
+ * Accepts: `policy` — must be an object naming only `maxAttempts`,
138
+ * `baseDelayMs` and `maxDelayMs`; each, if given, is a bounded integer.
139
+ *
140
+ * Returns: nothing: the value is kept under its declared type, and this
141
+ * checks it.
142
+ *
143
+ * Throws: `VALIDATION` naming `retry` or `retry.<key>`.
144
+ */
145
+ function assertRetryPolicy(policy) {
146
+ (0, option_shape_1.assertShape)(policy, RETRY_KEYS, 'retry');
147
+ assertRetryBounds(policy);
148
+ }
149
+ /** The recency index: a named GSI, and the partition count rows are sharded across. */
150
+ function assertRecencyIndex(options) {
151
+ if (options.indexShards !== undefined) {
152
+ (0, primitives_1.assertInteger)(options.indexShards, 'indexShards', { min: 1, max: recency_index_1.MAX_INDEX_SHARDS });
153
+ }
154
+ if (options.indexName !== undefined)
155
+ (0, primitives_1.assertNonEmptyString)(options.indexName, 'indexName');
156
+ }
157
+ /**
158
+ * Validate the options every adapter shares, at construction.
159
+ *
160
+ * Accepts: `options` — must be an object. `tableName` is required; every other
161
+ * option is optional, and `undefined` means "not configured" for each. A
162
+ * nested `ttl`, `retry`, `compression` or `s3` must be an object whose keys
163
+ * this package reads: a misspelt key is rejected rather than ignored, because
164
+ * the caller would otherwise run on a default they believe they overrode.
165
+ * `clientConfig` and `s3.clientConfig` must be objects, but their keys belong
166
+ * to the AWS SDK and are not checked. Keys of `options` itself are not checked
167
+ * here — the adapter types differ and this validator sees only the shared ones.
168
+ *
169
+ * Returns: nothing: the value is kept under its declared type, and this
170
+ * checks it.
171
+ *
172
+ * Throws: `VALIDATION` whose `context.field` names the offending option,
173
+ * dotted for a nested one (`s3.bucketName`). The order is `tableName`, client
174
+ * choice, `ttl`, `retry`, `compression`, `s3`, `readConcurrency`, then the
175
+ * index options.
176
+ *
177
+ * Guarantees: a misconfiguration surfaces at construction, naming the option,
178
+ * rather than as a raw AWS error on the first request.
179
+ */
180
+ function assertBaseAdapterOptions(options) {
181
+ if (typeof options !== 'object' || options === null) {
182
+ throw (0, errors_1.validationError)('options must be an object naming at least a tableName', 'options');
183
+ }
184
+ assertTableName(options.tableName);
185
+ assertClientChoice(options);
186
+ if (options.ttl !== undefined)
187
+ (0, ttl_1.resolveTtlSeconds)(options.ttl);
188
+ if (options.retry !== undefined)
189
+ assertRetryPolicy(options.retry);
190
+ if (options.compression !== undefined)
191
+ assertCompression(options.compression);
192
+ if (options.s3 !== undefined)
193
+ assertS3(options.s3);
194
+ if (options.readConcurrency !== undefined) {
195
+ (0, primitives_1.assertInteger)(options.readConcurrency, 'readConcurrency', {
196
+ min: 1,
197
+ max: exports.MAX_READ_CONCURRENCY,
198
+ });
39
199
  }
200
+ assertRecencyIndex(options);
40
201
  }
41
- function validateCompression(config) {
202
+ /** Server-side encryption algorithms S3 accepts for `PutObject`. */
203
+ const SSE_ALGORITHMS = ['AES256', 'aws:kms', 'aws:kms:dsse'];
204
+ const COMPRESSION_KEYS = (0, option_shape_1.allKeysOf)({
205
+ enabled: 'enabled',
206
+ level: 'level',
207
+ minSizeBytes: 'minSizeBytes',
208
+ maxDecompressedBytes: 'maxDecompressedBytes',
209
+ });
210
+ const S3_KEYS = (0, option_shape_1.allKeysOf)({
211
+ bucketName: 'bucketName',
212
+ keyPrefix: 'keyPrefix',
213
+ thresholdBytes: 'thresholdBytes',
214
+ serverSideEncryption: 'serverSideEncryption',
215
+ sseKmsKeyId: 'sseKmsKeyId',
216
+ maxDownloadBytes: 'maxDownloadBytes',
217
+ clientConfig: 'clientConfig',
218
+ createS3Client: 'createS3Client',
219
+ });
220
+ /**
221
+ * Validate a `compression` config, honoring its allowed key set.
222
+ *
223
+ * Accepts: `config` — an object naming only {@link CompressionConfig}'s keys.
224
+ *
225
+ * Returns: nothing: the value is kept under its declared type, and this
226
+ * checks it.
227
+ *
228
+ * Throws: `VALIDATION` naming the offending field, dotted under
229
+ * `compression`.
230
+ */
231
+ function assertCompression(config) {
232
+ (0, option_shape_1.assertShape)(config, COMPRESSION_KEYS, 'compression');
42
233
  if (typeof config.enabled !== 'boolean') {
43
- throw new errors_1.ValidationError('compression.enabled must be a boolean', 'compression.enabled');
234
+ throw (0, errors_1.validationError)('compression.enabled must be a boolean', 'compression.enabled');
44
235
  }
45
236
  if (config.level !== undefined) {
46
- (0, primitives_1.validateInteger)(config.level, 'compression.level', { min: 0, max: 9 });
237
+ (0, primitives_1.assertInteger)(config.level, 'compression.level', { min: 0, max: 9 });
47
238
  }
48
239
  if (config.minSizeBytes !== undefined) {
49
- (0, primitives_1.validateInteger)(config.minSizeBytes, 'compression.minSizeBytes', { min: 0 });
240
+ // Bounded by MAX_PAYLOAD_BUFFER_BYTES, not by MAX_INLINE_PAYLOAD_BYTES as
241
+ // `s3.thresholdBytes` is, because the two differ in kind. `encodePayload`
242
+ // compresses first and only then decides inline versus offload, on the
243
+ // compressed size — so `minSizeBytes` above the inline limit, paired with
244
+ // `s3`, is a meaningful configuration: compress only what will be offloaded
245
+ // anyway. A `thresholdBytes` above the inline limit is not: a payload
246
+ // between the two is too large to store inline and too small to offload,
247
+ // so its write fails. `minSizeBytes` only decides whether gzip runs; the
248
+ // only value it can never act on is one larger than any payload this
249
+ // package can read back.
250
+ (0, primitives_1.assertInteger)(config.minSizeBytes, 'compression.minSizeBytes', {
251
+ min: 0,
252
+ max: exports.MAX_PAYLOAD_BUFFER_BYTES,
253
+ });
50
254
  }
51
255
  if (config.maxDecompressedBytes !== undefined) {
52
- (0, primitives_1.validateInteger)(config.maxDecompressedBytes, 'compression.maxDecompressedBytes', { min: 1 });
256
+ (0, primitives_1.assertInteger)(config.maxDecompressedBytes, 'compression.maxDecompressedBytes', {
257
+ min: 1,
258
+ max: exports.MAX_PAYLOAD_BUFFER_BYTES,
259
+ });
260
+ }
261
+ }
262
+ /**
263
+ * Validate the two `s3` options `PutObject` receives as they were given.
264
+ *
265
+ * Accepts: `config.serverSideEncryption` — absent, or an algorithm S3 accepts.
266
+ * `config.sseKmsKeyId` — absent, or a non-empty string. Only its type is
267
+ * checked; whether it names a real key, by id or by ARN, is for S3 to answer.
268
+ *
269
+ * Returns: nothing: the value is kept under its declared type, and this
270
+ * checks it.
271
+ *
272
+ * Throws: `VALIDATION` naming `s3.serverSideEncryption` or
273
+ * `s3.sseKmsKeyId`. Unchecked, a truthy key id that is not a string was
274
+ * handed to `PutObject` at the first offload, and a falsy one (`''`, `null`,
275
+ * `0`) was dropped, uploading without the key the caller named.
276
+ */
277
+ function assertS3Encryption(config) {
278
+ if (config.serverSideEncryption !== undefined &&
279
+ !SSE_ALGORITHMS.includes(config.serverSideEncryption)) {
280
+ throw (0, errors_1.validationError)(`s3.serverSideEncryption must be one of ${SSE_ALGORITHMS.join(', ')}`, 's3.serverSideEncryption');
281
+ }
282
+ if (config.sseKmsKeyId !== undefined) {
283
+ (0, primitives_1.assertNonEmptyString)(config.sseKmsKeyId, 's3.sseKmsKeyId');
53
284
  }
54
285
  }
55
- function validateS3(config) {
56
- (0, primitives_1.validateNonEmptyString)(config.bucketName, 's3.bucketName');
286
+ /**
287
+ * Validate an `s3` offload config, honoring its allowed key set.
288
+ *
289
+ * Accepts: `config` — an object naming only {@link S3OffloadConfig}'s keys.
290
+ * `config.clientConfig`, when given, must be an object that is neither `null`
291
+ * nor an array; its own keys are not checked. `config.createS3Client`, when
292
+ * given, must be a function.
293
+ *
294
+ * Returns: nothing: the value is kept under its declared type, and this
295
+ * checks it.
296
+ *
297
+ * Throws: `VALIDATION` naming the offending field, dotted under `s3`.
298
+ */
299
+ function assertS3(config) {
300
+ (0, option_shape_1.assertShape)(config, S3_KEYS, 's3');
301
+ (0, primitives_1.assertNonEmptyString)(config.bucketName, 's3.bucketName');
302
+ // The shape only, never the keys: they are the AWS SDK's `S3ClientConfig`,
303
+ // which gains keys between SDK releases, and an application may install a
304
+ // newer SDK than the one this package was compiled against, so a key list
305
+ // compiled in here would refuse valid configuration.
306
+ if (config.clientConfig !== undefined)
307
+ (0, option_shape_1.assertObjectShape)(config.clientConfig, 's3.clientConfig');
57
308
  if (config.thresholdBytes !== undefined) {
58
- (0, primitives_1.validateInteger)(config.thresholdBytes, 's3.thresholdBytes', {
309
+ (0, primitives_1.assertInteger)(config.thresholdBytes, 's3.thresholdBytes', {
59
310
  min: 1,
60
- max: constants_1.MAX_INLINE_PAYLOAD_BYTES,
311
+ max: codec_1.MAX_INLINE_PAYLOAD_BYTES,
61
312
  });
62
313
  }
63
314
  if (config.keyPrefix !== undefined)
64
315
  (0, config_1.assertScopedKeyPrefix)(config.keyPrefix);
65
316
  if (config.maxDownloadBytes !== undefined) {
66
- (0, primitives_1.validateInteger)(config.maxDownloadBytes, 's3.maxDownloadBytes', { min: 1 });
317
+ (0, primitives_1.assertInteger)(config.maxDownloadBytes, 's3.maxDownloadBytes', {
318
+ min: 1,
319
+ max: exports.MAX_PAYLOAD_BUFFER_BYTES,
320
+ });
67
321
  }
68
- if (config.serverSideEncryption !== undefined &&
69
- !SSE_ALGORITHMS.includes(config.serverSideEncryption)) {
70
- throw new errors_1.ValidationError(`s3.serverSideEncryption must be one of ${SSE_ALGORITHMS.join(', ')}`, 's3.serverSideEncryption');
322
+ assertS3Encryption(config);
323
+ // Called to build the S3 client at the first offload, where a value that is
324
+ // not a function threw a bare `TypeError`.
325
+ if (config.createS3Client !== undefined && typeof config.createS3Client !== 'function') {
326
+ throw (0, errors_1.validationError)('s3.createS3Client must be a function', 's3.createS3Client');
71
327
  }
72
328
  }
73
- /**
74
- * Validate the options every adapter shares, at construction. Each failure is
75
- * a {@link ValidationError} whose `context.field` names the offending option,
76
- * so a misconfiguration surfaces where it was written instead of as a raw AWS
77
- * error on the first request.
78
- */
79
- function validateBaseAdapterOptions(options) {
80
- validateTableName(options.tableName);
81
- validateClientChoice(options);
82
- if (options.ttl !== undefined)
83
- (0, ttl_1.resolveTtlSeconds)(options.ttl);
84
- if (options.retry !== undefined)
85
- validateRetryPolicy(options.retry);
86
- if (options.compression !== undefined)
87
- validateCompression(options.compression);
88
- if (options.s3 !== undefined)
89
- validateS3(options.s3);
90
- }