@tstdl/base 0.93.182 → 0.93.183

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 (353) hide show
  1. package/api/server/api-request-token.provider.js +1 -1
  2. package/api/server/gateway.js +6 -1
  3. package/authentication/authentication.api.d.ts +13 -40
  4. package/authentication/authentication.api.js +5 -14
  5. package/authentication/client/authentication.service.d.ts +6 -14
  6. package/authentication/client/authentication.service.js +22 -4
  7. package/authentication/client/module.d.ts +1 -1
  8. package/authentication/client/module.js +4 -4
  9. package/authentication/models/index.d.ts +1 -0
  10. package/authentication/models/index.js +1 -0
  11. package/authentication/models/totp-results.model.d.ts +11 -0
  12. package/authentication/models/totp-results.model.js +37 -0
  13. package/authentication/server/authentication.api-controller.d.ts +3 -3
  14. package/authentication/server/authentication.api-controller.js +31 -4
  15. package/authentication/server/authentication.service.d.ts +5 -14
  16. package/authentication/server/authentication.service.js +6 -4
  17. package/core.d.ts +0 -5
  18. package/core.js +0 -8
  19. package/document-management/api/document-management.api.d.ts +2 -2
  20. package/document-management/service-models/document.service-model.d.ts +1 -1
  21. package/examples/config.d.ts +25 -0
  22. package/examples/config.js +26 -0
  23. package/notification/server/module.d.ts +1 -1
  24. package/notification/server/module.js +1 -1
  25. package/package.json +5 -5
  26. package/signals/api.d.ts +5 -1
  27. package/signals/api.js +3 -1
  28. package/signals/implementation/api.d.ts +13 -5
  29. package/signals/implementation/api.js +7 -1
  30. package/signals/implementation/asserts.d.ts +2 -2
  31. package/signals/implementation/asserts.js +3 -3
  32. package/signals/implementation/computed.d.ts +7 -34
  33. package/signals/implementation/computed.js +14 -83
  34. package/signals/implementation/configure.js +6 -2
  35. package/signals/implementation/effect.d.ts +65 -46
  36. package/signals/implementation/effect.js +97 -62
  37. package/signals/implementation/index.d.ts +2 -4
  38. package/signals/implementation/index.js +2 -4
  39. package/signals/implementation/linked_signal.d.ts +36 -0
  40. package/signals/implementation/linked_signal.js +34 -0
  41. package/signals/implementation/primitive/computed.d.ts +55 -0
  42. package/signals/implementation/primitive/computed.js +107 -0
  43. package/signals/implementation/primitive/effect.d.ts +26 -0
  44. package/signals/implementation/primitive/effect.js +31 -0
  45. package/signals/implementation/{equality.d.ts → primitive/equality.d.ts} +1 -1
  46. package/signals/implementation/{equality.js → primitive/equality.js} +1 -1
  47. package/signals/implementation/primitive/errors.d.ts +10 -0
  48. package/signals/implementation/{errors.js → primitive/errors.js} +3 -4
  49. package/signals/implementation/primitive/formatter.d.ts +19 -0
  50. package/signals/implementation/primitive/formatter.js +136 -0
  51. package/signals/implementation/{graph.d.ts → primitive/graph.d.ts} +68 -36
  52. package/signals/implementation/primitive/graph.js +386 -0
  53. package/signals/implementation/primitive/linked_signal.d.ts +46 -0
  54. package/signals/implementation/primitive/linked_signal.js +110 -0
  55. package/signals/implementation/primitive/signal.d.ts +31 -0
  56. package/signals/implementation/primitive/signal.js +80 -0
  57. package/signals/implementation/primitive/untracked.d.ts +12 -0
  58. package/signals/implementation/primitive/untracked.js +23 -0
  59. package/signals/implementation/{watch.d.ts → primitive/watch.d.ts} +1 -2
  60. package/signals/implementation/{watch.js → primitive/watch.js} +22 -16
  61. package/signals/implementation/resource/api.d.ts +275 -0
  62. package/signals/implementation/resource/api.js +26 -0
  63. package/signals/implementation/resource/debounce.d.ts +13 -0
  64. package/signals/implementation/resource/debounce.js +113 -0
  65. package/signals/implementation/resource/from_snapshots.d.ts +16 -0
  66. package/signals/implementation/resource/from_snapshots.js +44 -0
  67. package/signals/implementation/resource/index.d.ts +11 -0
  68. package/signals/implementation/resource/index.js +11 -0
  69. package/signals/implementation/resource/resource.d.ts +110 -0
  70. package/signals/implementation/resource/resource.js +402 -0
  71. package/signals/implementation/root_effect_scheduler.d.ts +50 -0
  72. package/signals/implementation/root_effect_scheduler.js +66 -0
  73. package/signals/implementation/signal.d.ts +42 -18
  74. package/signals/implementation/signal.js +29 -49
  75. package/signals/implementation/to-observable.d.ts +12 -5
  76. package/signals/implementation/to-observable.js +12 -2
  77. package/signals/implementation/to-signal.d.ts +9 -18
  78. package/signals/implementation/to-signal.js +46 -13
  79. package/signals/implementation/untracked.d.ts +1 -1
  80. package/signals/implementation/untracked.js +3 -11
  81. package/signals/operators/debounce.d.ts +8 -0
  82. package/signals/operators/debounce.js +19 -0
  83. package/signals/operators/derive-async.js +43 -15
  84. package/signals/operators/index.d.ts +2 -0
  85. package/signals/operators/index.js +2 -0
  86. package/signals/operators/throttle.d.ts +8 -0
  87. package/signals/operators/throttle.js +31 -0
  88. package/ai/genkit/tests/multi-region.test.d.ts +0 -2
  89. package/ai/genkit/tests/multi-region.test.js +0 -179
  90. package/ai/genkit/tests/token-limit-fallback.test.d.ts +0 -2
  91. package/ai/genkit/tests/token-limit-fallback.test.js +0 -209
  92. package/ai/prompts/tests/prompt-builder.test.d.ts +0 -1
  93. package/ai/prompts/tests/prompt-builder.test.js +0 -22
  94. package/ai/tests/instructions-formatter.test.d.ts +0 -1
  95. package/ai/tests/instructions-formatter.test.js +0 -116
  96. package/ai/tests/steering.test.d.ts +0 -1
  97. package/ai/tests/steering.test.js +0 -37
  98. package/api/client/tests/api-client.test.d.ts +0 -1
  99. package/api/client/tests/api-client.test.js +0 -194
  100. package/api/server/tests/csrf.middleware.test.d.ts +0 -1
  101. package/api/server/tests/csrf.middleware.test.js +0 -91
  102. package/authentication/tests/authentication-password-requirements.validator.test.d.ts +0 -1
  103. package/authentication/tests/authentication-password-requirements.validator.test.js +0 -29
  104. package/authentication/tests/authentication.api-controller.test.d.ts +0 -1
  105. package/authentication/tests/authentication.api-controller.test.js +0 -156
  106. package/authentication/tests/authentication.api-request-token.provider.test.d.ts +0 -1
  107. package/authentication/tests/authentication.api-request-token.provider.test.js +0 -48
  108. package/authentication/tests/authentication.client-error-handling.test.d.ts +0 -1
  109. package/authentication/tests/authentication.client-error-handling.test.js +0 -123
  110. package/authentication/tests/authentication.client-middleware.test.d.ts +0 -1
  111. package/authentication/tests/authentication.client-middleware.test.js +0 -118
  112. package/authentication/tests/authentication.client-service-methods.test.d.ts +0 -1
  113. package/authentication/tests/authentication.client-service-methods.test.js +0 -177
  114. package/authentication/tests/authentication.client-service-refresh.test.d.ts +0 -1
  115. package/authentication/tests/authentication.client-service-refresh.test.js +0 -153
  116. package/authentication/tests/authentication.client-service.test.d.ts +0 -1
  117. package/authentication/tests/authentication.client-service.test.js +0 -76
  118. package/authentication/tests/authentication.refresh-busy-loop.test.d.ts +0 -1
  119. package/authentication/tests/authentication.refresh-busy-loop.test.js +0 -84
  120. package/authentication/tests/authentication.service.test.d.ts +0 -1
  121. package/authentication/tests/authentication.service.test.js +0 -167
  122. package/authentication/tests/authentication.test-ancillary-service.d.ts +0 -9
  123. package/authentication/tests/authentication.test-ancillary-service.js +0 -27
  124. package/authentication/tests/brute-force-protection.test.d.ts +0 -1
  125. package/authentication/tests/brute-force-protection.test.js +0 -211
  126. package/authentication/tests/helper.test.d.ts +0 -1
  127. package/authentication/tests/helper.test.js +0 -122
  128. package/authentication/tests/password-requirements.error.test.d.ts +0 -1
  129. package/authentication/tests/password-requirements.error.test.js +0 -14
  130. package/authentication/tests/remember.api.test.d.ts +0 -1
  131. package/authentication/tests/remember.api.test.js +0 -117
  132. package/authentication/tests/remember.service.test.d.ts +0 -1
  133. package/authentication/tests/remember.service.test.js +0 -83
  134. package/authentication/tests/subject.service.test.d.ts +0 -1
  135. package/authentication/tests/subject.service.test.js +0 -140
  136. package/authentication/tests/suspended-subject.test.d.ts +0 -1
  137. package/authentication/tests/suspended-subject.test.js +0 -120
  138. package/authentication/tests/totp.enrollment.test.d.ts +0 -1
  139. package/authentication/tests/totp.enrollment.test.js +0 -123
  140. package/authentication/tests/totp.login.test.d.ts +0 -1
  141. package/authentication/tests/totp.login.test.js +0 -213
  142. package/authentication/tests/totp.recovery-codes.test.d.ts +0 -1
  143. package/authentication/tests/totp.recovery-codes.test.js +0 -97
  144. package/authentication/tests/totp.status.test.d.ts +0 -1
  145. package/authentication/tests/totp.status.test.js +0 -72
  146. package/cancellation/tests/coverage.test.d.ts +0 -1
  147. package/cancellation/tests/coverage.test.js +0 -49
  148. package/cancellation/tests/leak.test.d.ts +0 -1
  149. package/cancellation/tests/leak.test.js +0 -35
  150. package/cancellation/tests/token.test.d.ts +0 -1
  151. package/cancellation/tests/token.test.js +0 -136
  152. package/circuit-breaker/tests/circuit-breaker.test.d.ts +0 -1
  153. package/circuit-breaker/tests/circuit-breaker.test.js +0 -116
  154. package/cryptography/tests/cryptography.test.d.ts +0 -1
  155. package/cryptography/tests/cryptography.test.js +0 -175
  156. package/cryptography/tests/jwt.test.d.ts +0 -1
  157. package/cryptography/tests/jwt.test.js +0 -54
  158. package/cryptography/tests/modern.test.d.ts +0 -1
  159. package/cryptography/tests/modern.test.js +0 -105
  160. package/cryptography/tests/module.test.d.ts +0 -1
  161. package/cryptography/tests/module.test.js +0 -100
  162. package/cryptography/tests/totp.test.d.ts +0 -1
  163. package/cryptography/tests/totp.test.js +0 -108
  164. package/document-management/tests/ai-config-hierarchy.test.d.ts +0 -1
  165. package/document-management/tests/ai-config-hierarchy.test.js +0 -59
  166. package/document-management/tests/ai-config-integration.test.d.ts +0 -1
  167. package/document-management/tests/ai-config-integration.test.js +0 -125
  168. package/document-management/tests/ai-config-merge.test.d.ts +0 -1
  169. package/document-management/tests/ai-config-merge.test.js +0 -46
  170. package/document-management/tests/document-management-ai-overrides.test.d.ts +0 -1
  171. package/document-management/tests/document-management-ai-overrides.test.js +0 -63
  172. package/document-management/tests/document-management-core.test.d.ts +0 -1
  173. package/document-management/tests/document-management-core.test.js +0 -157
  174. package/document-management/tests/document-management.api.test.d.ts +0 -1
  175. package/document-management/tests/document-management.api.test.js +0 -101
  176. package/document-management/tests/document-statistics.service.test.d.ts +0 -1
  177. package/document-management/tests/document-statistics.service.test.js +0 -498
  178. package/document-management/tests/document-validation-ai-overrides.test.d.ts +0 -1
  179. package/document-management/tests/document-validation-ai-overrides.test.js +0 -87
  180. package/document-management/tests/document.service.test.d.ts +0 -1
  181. package/document-management/tests/document.service.test.js +0 -143
  182. package/document-management/tests/enum-helpers.test.d.ts +0 -1
  183. package/document-management/tests/enum-helpers.test.js +0 -452
  184. package/document-management/tests/helper.d.ts +0 -24
  185. package/document-management/tests/helper.js +0 -39
  186. package/errors/tests/format.test.d.ts +0 -1
  187. package/errors/tests/format.test.js +0 -84
  188. package/http/tests/server-timing.test.d.ts +0 -1
  189. package/http/tests/server-timing.test.js +0 -42
  190. package/injector/tests/advanced.test.d.ts +0 -1
  191. package/injector/tests/advanced.test.js +0 -116
  192. package/injector/tests/async-init.test.d.ts +0 -1
  193. package/injector/tests/async-init.test.js +0 -77
  194. package/injector/tests/basic.test.d.ts +0 -1
  195. package/injector/tests/basic.test.js +0 -114
  196. package/injector/tests/hierarchical.test.d.ts +0 -1
  197. package/injector/tests/hierarchical.test.js +0 -59
  198. package/injector/tests/leak.test.d.ts +0 -1
  199. package/injector/tests/leak.test.js +0 -45
  200. package/injector/tests/lifecycles.test.d.ts +0 -1
  201. package/injector/tests/lifecycles.test.js +0 -109
  202. package/logger/tests/pretty-print.test.d.ts +0 -1
  203. package/logger/tests/pretty-print.test.js +0 -60
  204. package/notification/tests/notification-api.test.d.ts +0 -1
  205. package/notification/tests/notification-api.test.js +0 -124
  206. package/notification/tests/notification-client.test.d.ts +0 -1
  207. package/notification/tests/notification-client.test.js +0 -101
  208. package/notification/tests/notification-flow.test.d.ts +0 -1
  209. package/notification/tests/notification-flow.test.js +0 -296
  210. package/notification/tests/notification-sse.service.test.d.ts +0 -1
  211. package/notification/tests/notification-sse.service.test.js +0 -43
  212. package/notification/tests/notification-type.service.test.d.ts +0 -1
  213. package/notification/tests/notification-type.service.test.js +0 -41
  214. package/object-storage/s3/tests/s3.object-storage.integration.test.d.ts +0 -1
  215. package/object-storage/s3/tests/s3.object-storage.integration.test.js +0 -303
  216. package/orm/tests/build-jsonb.test.d.ts +0 -1
  217. package/orm/tests/build-jsonb.test.js +0 -39
  218. package/orm/tests/data-types.test.d.ts +0 -1
  219. package/orm/tests/data-types.test.js +0 -39
  220. package/orm/tests/database-extension.test.d.ts +0 -1
  221. package/orm/tests/database-extension.test.js +0 -63
  222. package/orm/tests/database-migration.test.d.ts +0 -1
  223. package/orm/tests/database-migration.test.js +0 -83
  224. package/orm/tests/decorators.test.d.ts +0 -1
  225. package/orm/tests/decorators.test.js +0 -77
  226. package/orm/tests/encryption.test.d.ts +0 -1
  227. package/orm/tests/encryption.test.js +0 -31
  228. package/orm/tests/query-complex.test.d.ts +0 -1
  229. package/orm/tests/query-complex.test.js +0 -172
  230. package/orm/tests/query-converter-complex.test.d.ts +0 -1
  231. package/orm/tests/query-converter-complex.test.js +0 -131
  232. package/orm/tests/query-converter.test.d.ts +0 -1
  233. package/orm/tests/query-converter.test.js +0 -123
  234. package/orm/tests/repository-advanced.test.d.ts +0 -1
  235. package/orm/tests/repository-advanced.test.js +0 -189
  236. package/orm/tests/repository-attributes.test.d.ts +0 -1
  237. package/orm/tests/repository-attributes.test.js +0 -83
  238. package/orm/tests/repository-compound-primary-key.test.d.ts +0 -2
  239. package/orm/tests/repository-compound-primary-key.test.js +0 -226
  240. package/orm/tests/repository-comprehensive.test.d.ts +0 -1
  241. package/orm/tests/repository-comprehensive.test.js +0 -162
  242. package/orm/tests/repository-coverage.test.d.ts +0 -2
  243. package/orm/tests/repository-coverage.test.js +0 -242
  244. package/orm/tests/repository-cti-complex.test.d.ts +0 -1
  245. package/orm/tests/repository-cti-complex.test.js +0 -151
  246. package/orm/tests/repository-cti-embedded.test.d.ts +0 -1
  247. package/orm/tests/repository-cti-embedded.test.js +0 -178
  248. package/orm/tests/repository-cti-extensive.test.d.ts +0 -2
  249. package/orm/tests/repository-cti-extensive.test.js +0 -279
  250. package/orm/tests/repository-cti-mapping.test.d.ts +0 -2
  251. package/orm/tests/repository-cti-mapping.test.js +0 -108
  252. package/orm/tests/repository-cti-search.test.d.ts +0 -1
  253. package/orm/tests/repository-cti-search.test.js +0 -141
  254. package/orm/tests/repository-cti-soft-delete.test.d.ts +0 -2
  255. package/orm/tests/repository-cti-soft-delete.test.js +0 -103
  256. package/orm/tests/repository-cti-transactions.test.d.ts +0 -1
  257. package/orm/tests/repository-cti-transactions.test.js +0 -112
  258. package/orm/tests/repository-cti-upsert-many.test.d.ts +0 -2
  259. package/orm/tests/repository-cti-upsert-many.test.js +0 -115
  260. package/orm/tests/repository-cti.test.d.ts +0 -2
  261. package/orm/tests/repository-cti.test.js +0 -390
  262. package/orm/tests/repository-edge-cases.test.d.ts +0 -1
  263. package/orm/tests/repository-edge-cases.test.js +0 -178
  264. package/orm/tests/repository-expiration.test.d.ts +0 -2
  265. package/orm/tests/repository-expiration.test.js +0 -140
  266. package/orm/tests/repository-extra-coverage.test.d.ts +0 -2
  267. package/orm/tests/repository-extra-coverage.test.js +0 -402
  268. package/orm/tests/repository-mapping.test.d.ts +0 -2
  269. package/orm/tests/repository-mapping.test.js +0 -65
  270. package/orm/tests/repository-regression.test.d.ts +0 -1
  271. package/orm/tests/repository-regression.test.js +0 -288
  272. package/orm/tests/repository-search-coverage.test.d.ts +0 -1
  273. package/orm/tests/repository-search-coverage.test.js +0 -107
  274. package/orm/tests/repository-search.test.d.ts +0 -1
  275. package/orm/tests/repository-search.test.js +0 -105
  276. package/orm/tests/repository-soft-delete.test.d.ts +0 -1
  277. package/orm/tests/repository-soft-delete.test.js +0 -118
  278. package/orm/tests/repository-transactions-nested.test.d.ts +0 -1
  279. package/orm/tests/repository-transactions-nested.test.js +0 -178
  280. package/orm/tests/repository-types.test.d.ts +0 -1
  281. package/orm/tests/repository-types.test.js +0 -184
  282. package/orm/tests/repository-undelete.test.d.ts +0 -2
  283. package/orm/tests/repository-undelete.test.js +0 -201
  284. package/orm/tests/schema-converter.test.d.ts +0 -1
  285. package/orm/tests/schema-converter.test.js +0 -82
  286. package/orm/tests/schema-generation.test.d.ts +0 -2
  287. package/orm/tests/schema-generation.test.js +0 -174
  288. package/orm/tests/sql-helpers.test.d.ts +0 -1
  289. package/orm/tests/sql-helpers.test.js +0 -67
  290. package/orm/tests/transaction-safety.test.d.ts +0 -1
  291. package/orm/tests/transaction-safety.test.js +0 -81
  292. package/orm/tests/transactional.test.d.ts +0 -1
  293. package/orm/tests/transactional.test.js +0 -215
  294. package/orm/tests/utils.test.d.ts +0 -1
  295. package/orm/tests/utils.test.js +0 -70
  296. package/pdf/tests/utils.test.d.ts +0 -1
  297. package/pdf/tests/utils.test.js +0 -187
  298. package/process/tests/spawn.test.d.ts +0 -1
  299. package/process/tests/spawn.test.js +0 -182
  300. package/rate-limit/tests/postgres-rate-limiter.test.d.ts +0 -1
  301. package/rate-limit/tests/postgres-rate-limiter.test.js +0 -84
  302. package/renderer/tests/renderer.test.d.ts +0 -1
  303. package/renderer/tests/renderer.test.js +0 -88
  304. package/rpc/tests/rpc.integration.test.d.ts +0 -1
  305. package/rpc/tests/rpc.integration.test.js +0 -615
  306. package/signals/implementation/errors.d.ts +0 -2
  307. package/signals/implementation/graph.js +0 -312
  308. package/signals/implementation/writable-signal.d.ts +0 -48
  309. package/signals/implementation/writable-signal.js +0 -32
  310. package/task-queue/tests/coverage-branch.test.d.ts +0 -1
  311. package/task-queue/tests/coverage-branch.test.js +0 -395
  312. package/task-queue/tests/coverage-enhancement.test.d.ts +0 -1
  313. package/task-queue/tests/coverage-enhancement.test.js +0 -150
  314. package/task-queue/tests/dag.test.d.ts +0 -1
  315. package/task-queue/tests/dag.test.js +0 -188
  316. package/task-queue/tests/dependencies.test.d.ts +0 -1
  317. package/task-queue/tests/dependencies.test.js +0 -296
  318. package/task-queue/tests/enqueue-batch.test.d.ts +0 -1
  319. package/task-queue/tests/enqueue-batch.test.js +0 -125
  320. package/task-queue/tests/enqueue-item.test.d.ts +0 -1
  321. package/task-queue/tests/enqueue-item.test.js +0 -12
  322. package/task-queue/tests/fan-out-spawning.test.d.ts +0 -1
  323. package/task-queue/tests/fan-out-spawning.test.js +0 -94
  324. package/task-queue/tests/idempotent-replacement.test.d.ts +0 -1
  325. package/task-queue/tests/idempotent-replacement.test.js +0 -114
  326. package/task-queue/tests/missing-idempotent-tasks.test.d.ts +0 -1
  327. package/task-queue/tests/missing-idempotent-tasks.test.js +0 -39
  328. package/task-queue/tests/optimization-edge-cases.test.d.ts +0 -1
  329. package/task-queue/tests/optimization-edge-cases.test.js +0 -124
  330. package/task-queue/tests/queue-generic.test.d.ts +0 -1
  331. package/task-queue/tests/queue-generic.test.js +0 -8
  332. package/task-queue/tests/queue.test.d.ts +0 -1
  333. package/task-queue/tests/queue.test.js +0 -756
  334. package/task-queue/tests/shutdown.test.d.ts +0 -1
  335. package/task-queue/tests/shutdown.test.js +0 -41
  336. package/task-queue/tests/task-context.test.d.ts +0 -1
  337. package/task-queue/tests/task-context.test.js +0 -7
  338. package/task-queue/tests/task-union.test.d.ts +0 -1
  339. package/task-queue/tests/task-union.test.js +0 -18
  340. package/task-queue/tests/transactions.test.d.ts +0 -1
  341. package/task-queue/tests/transactions.test.js +0 -47
  342. package/task-queue/tests/typing.test.d.ts +0 -1
  343. package/task-queue/tests/typing.test.js +0 -9
  344. package/task-queue/tests/worker.test.d.ts +0 -1
  345. package/task-queue/tests/worker.test.js +0 -258
  346. package/task-queue/tests/zombie-parent.test.d.ts +0 -1
  347. package/task-queue/tests/zombie-parent.test.js +0 -45
  348. package/task-queue/tests/zombie-recovery.test.d.ts +0 -1
  349. package/task-queue/tests/zombie-recovery.test.js +0 -51
  350. package/utils/tests/backoff.test.d.ts +0 -1
  351. package/utils/tests/backoff.test.js +0 -41
  352. package/utils/tests/retry-with-backoff.test.d.ts +0 -1
  353. package/utils/tests/retry-with-backoff.test.js +0 -49
@@ -1,172 +0,0 @@
1
- var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
- else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
- return c > 3 && r && Object.defineProperty(target, key, r), r;
6
- };
7
- var __metadata = (this && this.__metadata) || function (k, v) {
8
- if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
9
- };
10
- import { sql } from 'drizzle-orm';
11
- import { beforeAll, describe, expect, test } from 'vitest';
12
- import { Integer, StringProperty } from '../../schema/index.js';
13
- import { setupIntegrationTest } from '../../testing/index.js';
14
- import { Table } from '../decorators.js';
15
- import { Entity } from '../entity.js';
16
- import { getRepository } from '../server/index.js';
17
- describe('ORM Query Complex (Integration)', () => {
18
- let injector;
19
- let db;
20
- let repo;
21
- const schema = 'test_orm_query_complex';
22
- let QueryEntity = class QueryEntity extends Entity {
23
- tag;
24
- score;
25
- status;
26
- };
27
- __decorate([
28
- StringProperty(),
29
- __metadata("design:type", String)
30
- ], QueryEntity.prototype, "tag", void 0);
31
- __decorate([
32
- Integer(),
33
- __metadata("design:type", Number)
34
- ], QueryEntity.prototype, "score", void 0);
35
- __decorate([
36
- StringProperty(),
37
- __metadata("design:type", String)
38
- ], QueryEntity.prototype, "status", void 0);
39
- QueryEntity = __decorate([
40
- Table('query_entities', { schema })
41
- ], QueryEntity);
42
- beforeAll(async () => {
43
- ({ injector, database: db } = await setupIntegrationTest({
44
- orm: { schema },
45
- }));
46
- repo = injector.resolve(getRepository(QueryEntity));
47
- await db.execute(sql `CREATE SCHEMA IF NOT EXISTS ${sql.identifier(schema)}`);
48
- await db.execute(sql `DROP TABLE IF EXISTS ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
49
- await db.execute(sql `
50
- CREATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} (
51
- id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
52
- tag TEXT NOT NULL,
53
- score INTEGER NOT NULL,
54
- status TEXT NOT NULL,
55
- revision INTEGER NOT NULL,
56
- revision_timestamp TIMESTAMP WITH TIME ZONE NOT NULL,
57
- create_timestamp TIMESTAMP WITH TIME ZONE NOT NULL,
58
- delete_timestamp TIMESTAMP WITH TIME ZONE,
59
- attributes JSONB NOT NULL DEFAULT '{}'
60
- )
61
- `);
62
- });
63
- test('should support nested AND/OR logic', async () => {
64
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
65
- await repo.insertMany([
66
- Object.assign(new QueryEntity(), { tag: 'A', score: 10, status: 'active' }),
67
- Object.assign(new QueryEntity(), { tag: 'A', score: 20, status: 'inactive' }),
68
- Object.assign(new QueryEntity(), { tag: 'B', score: 10, status: 'active' }),
69
- Object.assign(new QueryEntity(), { tag: 'B', score: 20, status: 'inactive' }),
70
- ]);
71
- // (Tag A AND Active) OR (Tag B AND Inactive)
72
- const results = await repo.loadManyByQuery({
73
- $or: [
74
- { $and: [{ tag: 'A' }, { status: 'active' }] },
75
- { $and: [{ tag: 'B' }, { status: 'inactive' }] },
76
- ],
77
- });
78
- expect(results).toHaveLength(2);
79
- expect(results.some((r) => r.tag === 'A' && r.status === 'active')).toBe(true);
80
- expect(results.some((r) => r.tag === 'B' && r.status === 'inactive')).toBe(true);
81
- });
82
- test('should support implicit AND', async () => {
83
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
84
- await repo.insert(Object.assign(new QueryEntity(), { tag: 'A', score: 10, status: 'active' }));
85
- const results = await repo.loadManyByQuery({
86
- tag: 'A',
87
- score: 10,
88
- status: 'active',
89
- });
90
- expect(results).toHaveLength(1);
91
- });
92
- test('should support NOT operator', async () => {
93
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
94
- await repo.insertMany([
95
- Object.assign(new QueryEntity(), { tag: 'A', score: 10, status: 'active' }),
96
- Object.assign(new QueryEntity(), { tag: 'B', score: 20, status: 'inactive' }),
97
- ]);
98
- const results = await repo.loadManyByQuery({
99
- tag: { $not: { $eq: 'A' } },
100
- });
101
- expect(results).toHaveLength(1);
102
- expect(results[0].tag).toBe('B');
103
- });
104
- test('should support IN operator with empty array (should match nothing)', async () => {
105
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
106
- await repo.insert(Object.assign(new QueryEntity(), { tag: 'A', score: 10, status: 'active' }));
107
- const results = await repo.loadManyByQuery({
108
- tag: { $in: [] },
109
- });
110
- expect(results).toHaveLength(0);
111
- });
112
- test('should support NOT IN operator with empty array (should match everything)', async () => {
113
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
114
- await repo.insert(Object.assign(new QueryEntity(), { tag: 'A', score: 10, status: 'active' }));
115
- const results = await repo.loadManyByQuery({
116
- tag: { $nin: [] },
117
- });
118
- expect(results).toHaveLength(1);
119
- });
120
- test('should support REGEX operator', async () => {
121
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
122
- await repo.insertMany([
123
- Object.assign(new QueryEntity(), { tag: 'apple', score: 10, status: '' }),
124
- Object.assign(new QueryEntity(), { tag: 'banana', score: 10, status: '' }),
125
- Object.assign(new QueryEntity(), { tag: 'apricot', score: 10, status: '' }),
126
- ]);
127
- const results = await repo.loadManyByQuery({
128
- tag: { $regex: '^ap' },
129
- });
130
- expect(results).toHaveLength(2); // apple, apricot
131
- });
132
- test('should support complex combination of logic and comparison', async () => {
133
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
134
- await repo.insertMany([
135
- Object.assign(new QueryEntity(), { tag: 'A', score: 5, status: 'ok' }),
136
- Object.assign(new QueryEntity(), { tag: 'A', score: 15, status: 'ok' }),
137
- Object.assign(new QueryEntity(), { tag: 'A', score: 25, status: 'fail' }),
138
- Object.assign(new QueryEntity(), { tag: 'B', score: 5, status: 'ok' }),
139
- ]);
140
- // Tag A AND (Score > 10 AND Score < 20) AND Status != fail
141
- const results = await repo.loadManyByQuery({
142
- tag: 'A',
143
- $and: [{ score: { $gt: 10 } }, { score: { $lt: 20 } }],
144
- status: { $neq: 'fail' },
145
- });
146
- expect(results).toHaveLength(1);
147
- expect(results[0].score).toBe(15);
148
- });
149
- test('should support NULL check', async () => {
150
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
151
- // Manually insert null status (violates NOT NULL usually, but let's assume nullable if we could change schema,
152
- // but Entity defines it as string. We can query for null even if no rows can be null (result 0) OR if we use a nullable column).
153
- // 'attributes' is JSONB and can be queried.
154
- // But query-converter maps properties.
155
- // Let's use a non-existent value for $eq which is different from null.
156
- // But checking $eq: null generates IS NULL.
157
- // Since our columns are NOT NULL, it should return empty.
158
- await repo.insert(Object.assign(new QueryEntity(), { tag: 'A', score: 10, status: 'active' }));
159
- const results = await repo.loadManyByQuery({
160
- status: { $eq: null },
161
- });
162
- expect(results).toHaveLength(0);
163
- });
164
- test('should support NOT NULL check', async () => {
165
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('query_entities')} CASCADE`);
166
- await repo.insert(Object.assign(new QueryEntity(), { tag: 'A', score: 10, status: 'active' }));
167
- const results = await repo.loadManyByQuery({
168
- status: { $neq: null },
169
- });
170
- expect(results).toHaveLength(1);
171
- });
172
- });
@@ -1 +0,0 @@
1
- export {};
@@ -1,131 +0,0 @@
1
- var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
- else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
- return c > 3 && r && Object.defineProperty(target, key, r), r;
6
- };
7
- var __metadata = (this && this.__metadata) || function (k, v) {
8
- if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
9
- };
10
- import { PgDialect } from 'drizzle-orm/pg-core';
11
- import { Integer, StringProperty } from '../../schema/index.js';
12
- import { describe, expect, test } from 'vitest';
13
- import { Table } from '../decorators.js';
14
- import { Entity } from '../entity.js';
15
- import { getColumnDefinitionsMap, getDrizzleTableFromType } from '../server/drizzle/schema-converter.js';
16
- import { convertQuery } from '../server/query-converter.js';
17
- describe('ORM Query Converter Complex', () => {
18
- const dialect = new PgDialect();
19
- let ComplexItem = class ComplexItem extends Entity {
20
- name;
21
- description;
22
- value;
23
- };
24
- __decorate([
25
- StringProperty(),
26
- __metadata("design:type", String)
27
- ], ComplexItem.prototype, "name", void 0);
28
- __decorate([
29
- StringProperty(),
30
- __metadata("design:type", String)
31
- ], ComplexItem.prototype, "description", void 0);
32
- __decorate([
33
- Integer(),
34
- __metadata("design:type", Number)
35
- ], ComplexItem.prototype, "value", void 0);
36
- ComplexItem = __decorate([
37
- Table('complex_items', { schema: 'test' })
38
- ], ComplexItem);
39
- const table = getDrizzleTableFromType(ComplexItem);
40
- const colMap = getColumnDefinitionsMap(table);
41
- test('should handle $tsvector with explicit weights', () => {
42
- const q = {
43
- $tsvector: {
44
- fields: [['name', 'A'], ['description', 'B']],
45
- query: 'search term',
46
- language: 'english',
47
- parser: 'websearch',
48
- },
49
- };
50
- const condition = convertQuery(q, table, colMap);
51
- const { sql, params } = dialect.sqlToQuery(condition);
52
- expect(sql).toContain('setweight(to_tsvector($1, "test"."complex_items"."name"), \'A\')');
53
- expect(sql).toContain('setweight(to_tsvector($2, "test"."complex_items"."description"), \'B\')');
54
- expect(sql).toContain('websearch_to_tsquery($3, $4)');
55
- expect(params).toEqual(['english', 'english', 'english', 'search term']);
56
- });
57
- test('should handle ParadeDB $parade match with tokenizer', () => {
58
- const q = {
59
- name: {
60
- $parade: {
61
- match: {
62
- value: 'test',
63
- tokenizer: { type: 'ngram', min_gram: 3, max_gram: 3 },
64
- },
65
- },
66
- },
67
- };
68
- const condition = convertQuery(q, table, colMap);
69
- const { sql, params } = dialect.sqlToQuery(condition);
70
- // Tokenizer is supported via JSON object syntax
71
- expect(sql).toContain('"test"."complex_items"."name" @@@ jsonb_build_object($1::text, jsonb_build_object($2::text, to_jsonb($3::text), $4::text, jsonb_build_object($5::text, to_jsonb($6::text), $7::text, to_jsonb($8::numeric), $9::text, to_jsonb($10::numeric))))::pdb.query');
72
- expect(params).toEqual(['match', 'value', 'test', 'tokenizer', 'type', 'ngram', 'min_gram', 3, 'max_gram', 3]);
73
- });
74
- test('should handle ParadeDB $parade range', () => {
75
- const q = {
76
- value: {
77
- $parade: {
78
- range: {
79
- lowerBound: { included: 10 },
80
- upperBound: { excluded: 20 },
81
- },
82
- },
83
- },
84
- };
85
- const condition = convertQuery(q, table, colMap);
86
- const { sql, params } = dialect.sqlToQuery(condition);
87
- // This should fall back to convertParadeComparisonQuery with recursive jsonb build
88
- expect(sql).toContain('"test"."complex_items"."value" @@@ jsonb_build_object($1::text, jsonb_build_object($2::text, jsonb_build_object($3::text, to_jsonb($4::numeric)), $5::text, jsonb_build_object($6::text, to_jsonb($7::numeric))))::pdb.query');
89
- expect(params).toEqual(['range', 'lower_bound', 'included', 10, 'upper_bound', 'excluded', 20]);
90
- });
91
- test('should handle ParadeDB $parade phrasePrefix', () => {
92
- const q = {
93
- name: {
94
- $parade: {
95
- phrasePrefix: { phrases: ['hello', 'wor'], maxExpansions: 10 },
96
- },
97
- },
98
- };
99
- const condition = convertQuery(q, table, colMap);
100
- const { sql, params } = dialect.sqlToQuery(condition);
101
- expect(sql).toContain('"test"."complex_items"."name" @@@ jsonb_build_object($1::text, jsonb_build_object($2::text, jsonb_build_array(to_jsonb($3::text), to_jsonb($4::text)), $5::text, to_jsonb($6::numeric)))::pdb.query');
102
- expect(params).toEqual(['phrase_prefix', 'phrases', 'hello', 'wor', 'max_expansions', 10]);
103
- });
104
- test('should handle ParadeDB $parade regexPhrase', () => {
105
- const q = {
106
- name: {
107
- $parade: {
108
- regexPhrase: { regexes: ['he.*', 'wo.*'], slop: 1 },
109
- },
110
- },
111
- };
112
- const condition = convertQuery(q, table, colMap);
113
- const { sql, params } = dialect.sqlToQuery(condition);
114
- expect(sql).toContain('"test"."complex_items"."name" @@@ jsonb_build_object($1::text, jsonb_build_object($2::text, jsonb_build_array(to_jsonb($3::text), to_jsonb($4::text)), $5::text, to_jsonb($6::numeric)))::pdb.query');
115
- expect(params).toEqual(['regex_phrase', 'regexes', 'he.*', 'wo.*', 'slop', 1]);
116
- });
117
- test('should handle ParadeDB top-level moreLikeThis', () => {
118
- const q = {
119
- $parade: {
120
- moreLikeThis: {
121
- keyValue: '123',
122
- fields: ['name', 'description'],
123
- },
124
- },
125
- };
126
- const condition = convertQuery(q, table, colMap);
127
- const { sql, params } = dialect.sqlToQuery(condition);
128
- expect(sql).toContain('"test"."complex_items"."id" @@@ jsonb_build_object($1::text, jsonb_build_object($2::text, to_jsonb($3::text), $4::text, to_jsonb(ARRAY[$5, $6])))::pdb.query');
129
- expect(params).toEqual(['more_like_this', 'key_value', '123', 'fields', 'name', 'description']);
130
- });
131
- });
@@ -1 +0,0 @@
1
- export {};
@@ -1,123 +0,0 @@
1
- var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
- else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
- return c > 3 && r && Object.defineProperty(target, key, r), r;
6
- };
7
- var __metadata = (this && this.__metadata) || function (k, v) {
8
- if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
9
- };
10
- import { describe, expect, test } from 'vitest';
11
- import { eq, sql } from 'drizzle-orm';
12
- import { getTableConfig, PgDialect } from 'drizzle-orm/pg-core';
13
- import { StringProperty } from '../../schema/index.js';
14
- import { Entity } from '../entity.js';
15
- import { Column, Inheritance, ChildEntity, Table } from '../decorators.js';
16
- import { getDrizzleTableFromType, getColumnDefinitionsMap } from '../server/drizzle/schema-converter.js';
17
- import { convertQuery } from '../server/query-converter.js';
18
- describe('ORM Query Converter (CTI)', () => {
19
- test('should resolve columns to correct table in joined query', () => {
20
- let BaseUser = class BaseUser extends Entity {
21
- type;
22
- name;
23
- };
24
- __decorate([
25
- StringProperty(),
26
- Column({ name: 'type' }),
27
- __metadata("design:type", String)
28
- ], BaseUser.prototype, "type", void 0);
29
- __decorate([
30
- StringProperty(),
31
- Column({ name: 'name' }),
32
- __metadata("design:type", String)
33
- ], BaseUser.prototype, "name", void 0);
34
- BaseUser = __decorate([
35
- Table('users', { schema: 'test' }),
36
- Inheritance({ strategy: 'joined', discriminatorColumn: 'type' })
37
- ], BaseUser);
38
- let Admin = class Admin extends BaseUser {
39
- role;
40
- };
41
- __decorate([
42
- StringProperty(),
43
- Column({ name: 'role' }),
44
- __metadata("design:type", String)
45
- ], Admin.prototype, "role", void 0);
46
- Admin = __decorate([
47
- Table('admins', { schema: 'test' }),
48
- ChildEntity('admin')
49
- ], Admin);
50
- const parentTable = getDrizzleTableFromType(BaseUser);
51
- const childTable = getDrizzleTableFromType(Admin);
52
- const columnDefinitionsMap = getColumnDefinitionsMap(childTable);
53
- const dialect = new PgDialect();
54
- // Query on child property
55
- const query1 = { role: 'super' };
56
- const sql1 = convertQuery(query1, childTable, columnDefinitionsMap);
57
- const sqlString1 = dialect.sqlToQuery(sql1).sql;
58
- expect(sqlString1).toContain('"admins"."role" = $1');
59
- // Query on parent property
60
- const query2 = { name: 'admin' };
61
- const sql2 = convertQuery(query2, childTable, columnDefinitionsMap);
62
- const sqlString2 = dialect.sqlToQuery(sql2).sql;
63
- expect(sqlString2).toContain('"users"."name" = $1');
64
- expect(sqlString2).not.toContain('"admins"."name"');
65
- });
66
- test('should handle $regex with flags', () => {
67
- let Item = class Item extends Entity {
68
- name;
69
- };
70
- __decorate([
71
- StringProperty(),
72
- __metadata("design:type", String)
73
- ], Item.prototype, "name", void 0);
74
- Item = __decorate([
75
- Table('items', { schema: 'test' })
76
- ], Item);
77
- const table = getDrizzleTableFromType(Item);
78
- const colMap = getColumnDefinitionsMap(table);
79
- const dialect = new PgDialect();
80
- const q = convertQuery({ name: { $regex: { pattern: '^test', flags: 'i' } } }, table, colMap);
81
- const sqlStr = dialect.sqlToQuery(q).sql;
82
- expect(sqlStr).toContain('"items"."name" ~* $1');
83
- });
84
- test('should handle $nin (not in)', () => {
85
- let Item = class Item extends Entity {
86
- name;
87
- };
88
- __decorate([
89
- StringProperty(),
90
- __metadata("design:type", String)
91
- ], Item.prototype, "name", void 0);
92
- Item = __decorate([
93
- Table('items', { schema: 'test' })
94
- ], Item);
95
- const table = getDrizzleTableFromType(Item);
96
- const colMap = getColumnDefinitionsMap(table);
97
- const dialect = new PgDialect();
98
- const q = convertQuery({ name: { $nin: ['a', 'b'] } }, table, colMap);
99
- const sqlStr = dialect.sqlToQuery(q).sql;
100
- expect(sqlStr.toLowerCase()).toContain('"items"."name" not in ($1, $2)');
101
- });
102
- test('should handle logical $nor', () => {
103
- let Item = class Item extends Entity {
104
- name;
105
- };
106
- __decorate([
107
- StringProperty(),
108
- __metadata("design:type", String)
109
- ], Item.prototype, "name", void 0);
110
- Item = __decorate([
111
- Table('items', { schema: 'test' })
112
- ], Item);
113
- const table = getDrizzleTableFromType(Item);
114
- const colMap = getColumnDefinitionsMap(table);
115
- const dialect = new PgDialect();
116
- const q = convertQuery({ $nor: [{ name: 'a' }, { name: 'b' }] }, table, colMap);
117
- const sqlStr = dialect.sqlToQuery(q).sql.toLowerCase();
118
- expect(sqlStr).toContain('not');
119
- expect(sqlStr).toContain('"items"."name" = $1');
120
- expect(sqlStr).toContain('"items"."name" = $2');
121
- expect(sqlStr).toContain('or');
122
- });
123
- });
@@ -1 +0,0 @@
1
- export {};
@@ -1,189 +0,0 @@
1
- var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
- else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
- return c > 3 && r && Object.defineProperty(target, key, r), r;
6
- };
7
- var __metadata = (this && this.__metadata) || function (k, v) {
8
- if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
9
- };
10
- import { sql } from 'drizzle-orm';
11
- import { beforeAll, describe, expect, test } from 'vitest';
12
- import { Integer, StringProperty } from '../../schema/index.js';
13
- import { setupIntegrationTest } from '../../testing/index.js';
14
- import { toArrayAsync } from '../../utils/async-iterable-helpers/to-array.js';
15
- import { Table } from '../decorators.js';
16
- import { Entity } from '../entity.js';
17
- import { getRepository } from '../server/index.js';
18
- describe('ORM Repository Advanced (Integration)', () => {
19
- let injector;
20
- let db;
21
- let repository;
22
- const schema = 'test_orm_advanced';
23
- let AdvancedEntity = class AdvancedEntity extends Entity {
24
- name;
25
- value;
26
- };
27
- __decorate([
28
- StringProperty(),
29
- __metadata("design:type", String)
30
- ], AdvancedEntity.prototype, "name", void 0);
31
- __decorate([
32
- Integer(),
33
- __metadata("design:type", Number)
34
- ], AdvancedEntity.prototype, "value", void 0);
35
- AdvancedEntity = __decorate([
36
- Table('advanced_entities', { schema })
37
- ], AdvancedEntity);
38
- beforeAll(async () => {
39
- ({ injector, database: db } = await setupIntegrationTest({
40
- orm: { schema },
41
- }));
42
- repository = injector.resolve(getRepository(AdvancedEntity));
43
- await db.execute(sql `CREATE SCHEMA IF NOT EXISTS ${sql.identifier(schema)}`);
44
- await db.execute(sql `DROP TABLE IF EXISTS ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
45
- await db.execute(sql `
46
- CREATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} (
47
- id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
48
- name TEXT NOT NULL,
49
- value INTEGER NOT NULL,
50
- revision INTEGER NOT NULL,
51
- revision_timestamp TIMESTAMP WITH TIME ZONE NOT NULL,
52
- create_timestamp TIMESTAMP WITH TIME ZONE NOT NULL,
53
- delete_timestamp TIMESTAMP WITH TIME ZONE,
54
- attributes JSONB NOT NULL DEFAULT '{}'
55
- )
56
- `);
57
- });
58
- test('should support loadManyCursor', async () => {
59
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
60
- const e1 = await repository.insert(Object.assign(new AdvancedEntity(), { name: 'E1', value: 1 }));
61
- const e2 = await repository.insert(Object.assign(new AdvancedEntity(), { name: 'E2', value: 2 }));
62
- const cursor = repository.loadManyCursor([e1.id, e2.id]);
63
- const results = await toArrayAsync(cursor);
64
- expect(results).toHaveLength(2);
65
- expect(results.map((r) => r.name).sort()).toEqual(['E1', 'E2']);
66
- });
67
- test('should support loadAllCursor', async () => {
68
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
69
- await repository.insertMany([
70
- Object.assign(new AdvancedEntity(), { name: 'E1', value: 1 }),
71
- Object.assign(new AdvancedEntity(), { name: 'E2', value: 2 }),
72
- ]);
73
- const cursor = repository.loadAllCursor();
74
- const results = await toArrayAsync(cursor);
75
- expect(results).toHaveLength(2);
76
- });
77
- test('should support countByQuery with various filters', async () => {
78
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
79
- await repository.insertMany([
80
- Object.assign(new AdvancedEntity(), { name: 'A', value: 10 }),
81
- Object.assign(new AdvancedEntity(), { name: 'B', value: 20 }),
82
- Object.assign(new AdvancedEntity(), { name: 'C', value: 30 }),
83
- ]);
84
- expect(await repository.countByQuery({ value: { $gt: 15 } })).toBe(2);
85
- expect(await repository.countByQuery({ value: { $lt: 25 } })).toBe(2);
86
- expect(await repository.countByQuery({ name: 'A' })).toBe(1);
87
- });
88
- test('should support has and hasByQuery', async () => {
89
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
90
- const e1 = await repository.insert(Object.assign(new AdvancedEntity(), { name: 'E1', value: 1 }));
91
- expect(await repository.has(e1.id)).toBe(true);
92
- expect(await repository.has('00000000-0000-0000-0000-000000000000')).toBe(false);
93
- expect(await repository.hasByQuery({ name: 'E1' })).toBe(true);
94
- expect(await repository.hasByQuery({ name: 'E2' })).toBe(false);
95
- });
96
- test('should support tryUpdate', async () => {
97
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
98
- const e1 = await repository.insert(Object.assign(new AdvancedEntity(), { name: 'E1', value: 1 }));
99
- const updated = await repository.tryUpdate(e1.id, { name: 'E1-Updated' });
100
- expect(updated.name).toBe('E1-Updated');
101
- const missing = await repository.tryUpdate('00000000-0000-0000-0000-000000000000', { name: 'X' });
102
- expect(missing).toBeUndefined();
103
- });
104
- test('should support tryUpdateByQuery', async () => {
105
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
106
- await repository.insert(Object.assign(new AdvancedEntity(), { name: 'E1', value: 1 }));
107
- const updated = await repository.tryUpdateByQuery({ name: 'E1' }, { value: 100 });
108
- expect(updated.value).toBe(100);
109
- const missing = await repository.tryUpdateByQuery({ name: 'Missing' }, { value: 0 });
110
- expect(missing).toBeUndefined();
111
- });
112
- test('should support insertIfNotExists', async () => {
113
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
114
- const e1 = await repository.insert(Object.assign(new AdvancedEntity(), { name: 'E1', value: 1 }));
115
- // Conflict on ID
116
- const conflict = await repository.insertIfNotExists('id', Object.assign(new AdvancedEntity(), { id: e1.id, name: 'Conflict', value: 2 }));
117
- expect(conflict).toBeUndefined();
118
- // No conflict
119
- const success = await repository.insertIfNotExists('id', Object.assign(new AdvancedEntity(), { name: 'E2', value: 2 }));
120
- expect(success).toBeDefined();
121
- expect(success.name).toBe('E2');
122
- });
123
- test('should support pagination (limit/offset)', async () => {
124
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
125
- await repository.insertMany([
126
- Object.assign(new AdvancedEntity(), { name: 'E1', value: 1 }),
127
- Object.assign(new AdvancedEntity(), { name: 'E2', value: 2 }),
128
- Object.assign(new AdvancedEntity(), { name: 'E3', value: 3 }),
129
- ]);
130
- const p1 = await repository.loadAll({ limit: 2, order: { value: 'asc' } });
131
- expect(p1).toHaveLength(2);
132
- expect(p1[0].name).toBe('E1');
133
- expect(p1[1].name).toBe('E2');
134
- const p2 = await repository.loadAll({ limit: 2, offset: 2, order: { value: 'asc' } });
135
- expect(p2).toHaveLength(1);
136
- expect(p2[0].name).toBe('E3');
137
- });
138
- test('should support complex ordering', async () => {
139
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
140
- await repository.insertMany([
141
- Object.assign(new AdvancedEntity(), { name: 'B', value: 10 }),
142
- Object.assign(new AdvancedEntity(), { name: 'A', value: 20 }),
143
- Object.assign(new AdvancedEntity(), { name: 'A', value: 10 }),
144
- ]);
145
- const results = await repository.loadAll({
146
- order: [
147
- ['name', 'asc'],
148
- ['value', 'desc'],
149
- ],
150
- });
151
- expect(results[0].name).toBe('A');
152
- expect(results[0].value).toBe(20);
153
- expect(results[1].name).toBe('A');
154
- expect(results[1].value).toBe(10);
155
- expect(results[2].name).toBe('B');
156
- });
157
- test('should return empty array for empty loadMany', async () => {
158
- const results = await repository.loadMany([]);
159
- expect(results).toEqual([]);
160
- });
161
- test('should fail on duplicate ID insert', async () => {
162
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
163
- const id = '00000000-0000-0000-0000-000000000001';
164
- await repository.insert(Object.assign(new AdvancedEntity(), { id, name: 'E1', value: 1 }));
165
- await expect(repository.insert(Object.assign(new AdvancedEntity(), { id, name: 'E2', value: 2 }))).rejects.toThrow();
166
- });
167
- test('should support explicit transaction usage', async () => {
168
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
169
- await repository.transaction(async (tx) => {
170
- const txRepo = repository.withTransaction(tx);
171
- await txRepo.insert(Object.assign(new AdvancedEntity(), { name: 'TxEntity', value: 100 }));
172
- // Should be visible in tx
173
- expect(await txRepo.count()).toBe(1);
174
- });
175
- // Should be committed
176
- expect(await repository.count()).toBe(1);
177
- });
178
- test('should exclude soft-deleted entities by default', async () => {
179
- await db.execute(sql `TRUNCATE TABLE ${sql.identifier(schema)}.${sql.identifier('advanced_entities')} CASCADE`);
180
- const e1 = await repository.insert(Object.assign(new AdvancedEntity(), { name: 'E1', value: 1 }));
181
- await repository.insert(Object.assign(new AdvancedEntity(), { name: 'E2', value: 2 }));
182
- await repository.delete(e1.id);
183
- const all = await repository.loadAll();
184
- expect(all).toHaveLength(1);
185
- expect(all[0].name).toBe('E2');
186
- const withDeleted = await repository.loadManyByQuery({}, { withDeleted: true });
187
- expect(withDeleted).toHaveLength(2);
188
- });
189
- });
@@ -1 +0,0 @@
1
- export {};