uql-orm 0.9.3 → 0.9.5

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 (657) hide show
  1. package/CHANGELOG.md +20 -1
  2. package/README.md +62 -683
  3. package/dist/browser/uql-browser.min.js +4791 -2940
  4. package/dist/browser/uql-browser.min.js.map +1 -1
  5. package/package.json +4 -4
  6. package/dist/browser/http/bus.d.ts +0 -4
  7. package/dist/browser/http/bus.d.ts.map +0 -1
  8. package/dist/browser/http/bus.js +0 -14
  9. package/dist/browser/http/bus.js.map +0 -1
  10. package/dist/browser/http/http.d.ts +0 -7
  11. package/dist/browser/http/http.d.ts.map +0 -1
  12. package/dist/browser/http/http.js +0 -45
  13. package/dist/browser/http/http.js.map +0 -1
  14. package/dist/browser/http/index.d.ts +0 -3
  15. package/dist/browser/http/index.d.ts.map +0 -1
  16. package/dist/browser/http/index.js +0 -3
  17. package/dist/browser/http/index.js.map +0 -1
  18. package/dist/browser/index.d.ts +0 -5
  19. package/dist/browser/index.d.ts.map +0 -1
  20. package/dist/browser/index.js +0 -5
  21. package/dist/browser/index.js.map +0 -1
  22. package/dist/browser/options.d.ts +0 -5
  23. package/dist/browser/options.d.ts.map +0 -1
  24. package/dist/browser/options.js +0 -14
  25. package/dist/browser/options.js.map +0 -1
  26. package/dist/browser/querier/httpQuerier.d.ts +0 -20
  27. package/dist/browser/querier/httpQuerier.d.ts.map +0 -1
  28. package/dist/browser/querier/httpQuerier.js +0 -68
  29. package/dist/browser/querier/httpQuerier.js.map +0 -1
  30. package/dist/browser/querier/index.d.ts +0 -3
  31. package/dist/browser/querier/index.d.ts.map +0 -1
  32. package/dist/browser/querier/index.js +0 -3
  33. package/dist/browser/querier/index.js.map +0 -1
  34. package/dist/browser/querier/querier.util.d.ts +0 -3
  35. package/dist/browser/querier/querier.util.d.ts.map +0 -1
  36. package/dist/browser/querier/querier.util.js +0 -17
  37. package/dist/browser/querier/querier.util.js.map +0 -1
  38. package/dist/browser/type/clientQuerier.d.ts +0 -24
  39. package/dist/browser/type/clientQuerier.d.ts.map +0 -1
  40. package/dist/browser/type/clientQuerier.js +0 -2
  41. package/dist/browser/type/clientQuerier.js.map +0 -1
  42. package/dist/browser/type/clientQuerierPool.d.ts +0 -5
  43. package/dist/browser/type/clientQuerierPool.d.ts.map +0 -1
  44. package/dist/browser/type/clientQuerierPool.js +0 -2
  45. package/dist/browser/type/clientQuerierPool.js.map +0 -1
  46. package/dist/browser/type/index.d.ts +0 -4
  47. package/dist/browser/type/index.d.ts.map +0 -1
  48. package/dist/browser/type/index.js +0 -4
  49. package/dist/browser/type/index.js.map +0 -1
  50. package/dist/browser/type/request.d.ts +0 -29
  51. package/dist/browser/type/request.d.ts.map +0 -1
  52. package/dist/browser/type/request.js +0 -2
  53. package/dist/browser/type/request.js.map +0 -1
  54. package/dist/bunSql/bunSql.util.d.ts +0 -30
  55. package/dist/bunSql/bunSql.util.d.ts.map +0 -1
  56. package/dist/bunSql/bunSql.util.js +0 -101
  57. package/dist/bunSql/bunSql.util.js.map +0 -1
  58. package/dist/bunSql/bunSqlPostgresDialect.d.ts +0 -12
  59. package/dist/bunSql/bunSqlPostgresDialect.d.ts.map +0 -1
  60. package/dist/bunSql/bunSqlPostgresDialect.js +0 -21
  61. package/dist/bunSql/bunSqlPostgresDialect.js.map +0 -1
  62. package/dist/bunSql/bunSqlQuerier.d.ts +0 -14
  63. package/dist/bunSql/bunSqlQuerier.d.ts.map +0 -1
  64. package/dist/bunSql/bunSqlQuerier.js +0 -37
  65. package/dist/bunSql/bunSqlQuerier.js.map +0 -1
  66. package/dist/bunSql/bunSqlQuerierPool.d.ts +0 -19
  67. package/dist/bunSql/bunSqlQuerierPool.d.ts.map +0 -1
  68. package/dist/bunSql/bunSqlQuerierPool.js +0 -58
  69. package/dist/bunSql/bunSqlQuerierPool.js.map +0 -1
  70. package/dist/bunSql/bunSqliteDialect.d.ts +0 -7
  71. package/dist/bunSql/bunSqliteDialect.d.ts.map +0 -1
  72. package/dist/bunSql/bunSqliteDialect.js +0 -7
  73. package/dist/bunSql/bunSqliteDialect.js.map +0 -1
  74. package/dist/bunSql/index.d.ts +0 -5
  75. package/dist/bunSql/index.d.ts.map +0 -1
  76. package/dist/bunSql/index.js +0 -5
  77. package/dist/bunSql/index.js.map +0 -1
  78. package/dist/cockroachdb/cockroachDialect.d.ts +0 -15
  79. package/dist/cockroachdb/cockroachDialect.d.ts.map +0 -1
  80. package/dist/cockroachdb/cockroachDialect.js +0 -14
  81. package/dist/cockroachdb/cockroachDialect.js.map +0 -1
  82. package/dist/cockroachdb/crdbQuerier.d.ts +0 -9
  83. package/dist/cockroachdb/crdbQuerier.d.ts.map +0 -1
  84. package/dist/cockroachdb/crdbQuerier.js +0 -7
  85. package/dist/cockroachdb/crdbQuerier.js.map +0 -1
  86. package/dist/cockroachdb/crdbQuerierPool.d.ts +0 -14
  87. package/dist/cockroachdb/crdbQuerierPool.d.ts.map +0 -1
  88. package/dist/cockroachdb/crdbQuerierPool.js +0 -18
  89. package/dist/cockroachdb/crdbQuerierPool.js.map +0 -1
  90. package/dist/cockroachdb/index.d.ts +0 -4
  91. package/dist/cockroachdb/index.d.ts.map +0 -1
  92. package/dist/cockroachdb/index.js +0 -4
  93. package/dist/cockroachdb/index.js.map +0 -1
  94. package/dist/d1/d1Querier.d.ts +0 -46
  95. package/dist/d1/d1Querier.d.ts.map +0 -1
  96. package/dist/d1/d1Querier.js +0 -30
  97. package/dist/d1/d1Querier.js.map +0 -1
  98. package/dist/d1/d1QuerierPool.d.ts +0 -11
  99. package/dist/d1/d1QuerierPool.d.ts.map +0 -1
  100. package/dist/d1/d1QuerierPool.js +0 -17
  101. package/dist/d1/d1QuerierPool.js.map +0 -1
  102. package/dist/d1/d1SqliteDialect.d.ts +0 -10
  103. package/dist/d1/d1SqliteDialect.d.ts.map +0 -1
  104. package/dist/d1/d1SqliteDialect.js +0 -10
  105. package/dist/d1/d1SqliteDialect.js.map +0 -1
  106. package/dist/d1/index.d.ts +0 -4
  107. package/dist/d1/index.d.ts.map +0 -1
  108. package/dist/d1/index.js +0 -4
  109. package/dist/d1/index.js.map +0 -1
  110. package/dist/dialect/abstractDialect.d.ts +0 -32
  111. package/dist/dialect/abstractDialect.d.ts.map +0 -1
  112. package/dist/dialect/abstractDialect.js +0 -39
  113. package/dist/dialect/abstractDialect.js.map +0 -1
  114. package/dist/dialect/abstractSqlDialect.d.ts +0 -233
  115. package/dist/dialect/abstractSqlDialect.d.ts.map +0 -1
  116. package/dist/dialect/abstractSqlDialect.js +0 -1332
  117. package/dist/dialect/abstractSqlDialect.js.map +0 -1
  118. package/dist/dialect/index.d.ts +0 -9
  119. package/dist/dialect/index.d.ts.map +0 -1
  120. package/dist/dialect/index.js +0 -9
  121. package/dist/dialect/index.js.map +0 -1
  122. package/dist/dialect/jsonArrayElemMatchUtils.d.ts +0 -10
  123. package/dist/dialect/jsonArrayElemMatchUtils.d.ts.map +0 -1
  124. package/dist/dialect/jsonArrayElemMatchUtils.js +0 -24
  125. package/dist/dialect/jsonArrayElemMatchUtils.js.map +0 -1
  126. package/dist/dialect/mysqlLikeSqlDialect.d.ts +0 -36
  127. package/dist/dialect/mysqlLikeSqlDialect.d.ts.map +0 -1
  128. package/dist/dialect/mysqlLikeSqlDialect.js +0 -84
  129. package/dist/dialect/mysqlLikeSqlDialect.js.map +0 -1
  130. package/dist/dialect/queryContext.d.ts +0 -49
  131. package/dist/dialect/queryContext.d.ts.map +0 -1
  132. package/dist/dialect/queryContext.js +0 -65
  133. package/dist/dialect/queryContext.js.map +0 -1
  134. package/dist/entity/decorator/entity.d.ts +0 -3
  135. package/dist/entity/decorator/entity.d.ts.map +0 -1
  136. package/dist/entity/decorator/entity.js +0 -7
  137. package/dist/entity/decorator/entity.js.map +0 -1
  138. package/dist/entity/decorator/field.d.ts +0 -3
  139. package/dist/entity/decorator/field.d.ts.map +0 -1
  140. package/dist/entity/decorator/field.js +0 -8
  141. package/dist/entity/decorator/field.js.map +0 -1
  142. package/dist/entity/decorator/hook.d.ts +0 -8
  143. package/dist/entity/decorator/hook.d.ts.map +0 -1
  144. package/dist/entity/decorator/hook.js +0 -15
  145. package/dist/entity/decorator/hook.js.map +0 -1
  146. package/dist/entity/decorator/id.d.ts +0 -3
  147. package/dist/entity/decorator/id.d.ts.map +0 -1
  148. package/dist/entity/decorator/id.js +0 -8
  149. package/dist/entity/decorator/id.js.map +0 -1
  150. package/dist/entity/decorator/index-decorator.d.ts +0 -37
  151. package/dist/entity/decorator/index-decorator.d.ts.map +0 -1
  152. package/dist/entity/decorator/index-decorator.js +0 -27
  153. package/dist/entity/decorator/index-decorator.js.map +0 -1
  154. package/dist/entity/decorator/index.d.ts +0 -8
  155. package/dist/entity/decorator/index.d.ts.map +0 -1
  156. package/dist/entity/decorator/index.js +0 -8
  157. package/dist/entity/decorator/index.js.map +0 -1
  158. package/dist/entity/decorator/relation.d.ts +0 -9
  159. package/dist/entity/decorator/relation.d.ts.map +0 -1
  160. package/dist/entity/decorator/relation.js +0 -20
  161. package/dist/entity/decorator/relation.js.map +0 -1
  162. package/dist/entity/index.d.ts +0 -2
  163. package/dist/entity/index.d.ts.map +0 -1
  164. package/dist/entity/index.js +0 -2
  165. package/dist/entity/index.js.map +0 -1
  166. package/dist/entity/metadata/definition.d.ts +0 -16
  167. package/dist/entity/metadata/definition.d.ts.map +0 -1
  168. package/dist/entity/metadata/definition.js +0 -309
  169. package/dist/entity/metadata/definition.js.map +0 -1
  170. package/dist/entity/test-helpers.d.ts +0 -4
  171. package/dist/entity/test-helpers.d.ts.map +0 -1
  172. package/dist/entity/test-helpers.js +0 -15
  173. package/dist/entity/test-helpers.js.map +0 -1
  174. package/dist/express/index.d.ts +0 -3
  175. package/dist/express/index.d.ts.map +0 -1
  176. package/dist/express/index.js +0 -3
  177. package/dist/express/index.js.map +0 -1
  178. package/dist/express/querierMiddleware.d.ts +0 -26
  179. package/dist/express/querierMiddleware.d.ts.map +0 -1
  180. package/dist/express/querierMiddleware.js +0 -143
  181. package/dist/express/querierMiddleware.js.map +0 -1
  182. package/dist/express/query.util.d.ts +0 -7
  183. package/dist/express/query.util.d.ts.map +0 -1
  184. package/dist/express/query.util.js +0 -27
  185. package/dist/express/query.util.js.map +0 -1
  186. package/dist/index.d.ts +0 -8
  187. package/dist/index.d.ts.map +0 -1
  188. package/dist/index.js +0 -8
  189. package/dist/index.js.map +0 -1
  190. package/dist/libsql/index.d.ts +0 -4
  191. package/dist/libsql/index.d.ts.map +0 -1
  192. package/dist/libsql/index.js +0 -4
  193. package/dist/libsql/index.js.map +0 -1
  194. package/dist/libsql/libsqlDialect.d.ts +0 -10
  195. package/dist/libsql/libsqlDialect.d.ts.map +0 -1
  196. package/dist/libsql/libsqlDialect.js +0 -10
  197. package/dist/libsql/libsqlDialect.js.map +0 -1
  198. package/dist/libsql/libsqlQuerier.d.ts +0 -24
  199. package/dist/libsql/libsqlQuerier.d.ts.map +0 -1
  200. package/dist/libsql/libsqlQuerier.js +0 -76
  201. package/dist/libsql/libsqlQuerier.js.map +0 -1
  202. package/dist/libsql/libsqlQuerierPool.d.ts +0 -20
  203. package/dist/libsql/libsqlQuerierPool.d.ts.map +0 -1
  204. package/dist/libsql/libsqlQuerierPool.js +0 -40
  205. package/dist/libsql/libsqlQuerierPool.js.map +0 -1
  206. package/dist/maria/index.d.ts +0 -4
  207. package/dist/maria/index.d.ts.map +0 -1
  208. package/dist/maria/index.js +0 -4
  209. package/dist/maria/index.js.map +0 -1
  210. package/dist/maria/mariaDialect.d.ts +0 -16
  211. package/dist/maria/mariaDialect.d.ts.map +0 -1
  212. package/dist/maria/mariaDialect.js +0 -56
  213. package/dist/maria/mariaDialect.js.map +0 -1
  214. package/dist/maria/mariadbQuerier.d.ts +0 -12
  215. package/dist/maria/mariadbQuerier.d.ts.map +0 -1
  216. package/dist/maria/mariadbQuerier.js +0 -31
  217. package/dist/maria/mariadbQuerier.js.map +0 -1
  218. package/dist/maria/mariadbQuerierPool.d.ts +0 -14
  219. package/dist/maria/mariadbQuerierPool.d.ts.map +0 -1
  220. package/dist/maria/mariadbQuerierPool.js +0 -18
  221. package/dist/maria/mariadbQuerierPool.js.map +0 -1
  222. package/dist/migrate/acquireQuerierForMigrations.d.ts +0 -9
  223. package/dist/migrate/acquireQuerierForMigrations.d.ts.map +0 -1
  224. package/dist/migrate/acquireQuerierForMigrations.js +0 -10
  225. package/dist/migrate/acquireQuerierForMigrations.js.map +0 -1
  226. package/dist/migrate/assertCliConfig.d.ts +0 -6
  227. package/dist/migrate/assertCliConfig.d.ts.map +0 -1
  228. package/dist/migrate/assertCliConfig.js +0 -31
  229. package/dist/migrate/assertCliConfig.js.map +0 -1
  230. package/dist/migrate/bin.d.ts +0 -3
  231. package/dist/migrate/bin.d.ts.map +0 -1
  232. package/dist/migrate/bin.js +0 -7
  233. package/dist/migrate/bin.js.map +0 -1
  234. package/dist/migrate/builder/columnBuilder.d.ts +0 -79
  235. package/dist/migrate/builder/columnBuilder.d.ts.map +0 -1
  236. package/dist/migrate/builder/columnBuilder.js +0 -159
  237. package/dist/migrate/builder/columnBuilder.js.map +0 -1
  238. package/dist/migrate/builder/expressions.d.ts +0 -87
  239. package/dist/migrate/builder/expressions.d.ts.map +0 -1
  240. package/dist/migrate/builder/expressions.js +0 -150
  241. package/dist/migrate/builder/expressions.js.map +0 -1
  242. package/dist/migrate/builder/index.d.ts +0 -6
  243. package/dist/migrate/builder/index.d.ts.map +0 -1
  244. package/dist/migrate/builder/index.js +0 -6
  245. package/dist/migrate/builder/index.js.map +0 -1
  246. package/dist/migrate/builder/migrationBuilder.d.ts +0 -110
  247. package/dist/migrate/builder/migrationBuilder.d.ts.map +0 -1
  248. package/dist/migrate/builder/migrationBuilder.js +0 -470
  249. package/dist/migrate/builder/migrationBuilder.js.map +0 -1
  250. package/dist/migrate/builder/splitSqlStatements.d.ts +0 -18
  251. package/dist/migrate/builder/splitSqlStatements.d.ts.map +0 -1
  252. package/dist/migrate/builder/splitSqlStatements.js +0 -44
  253. package/dist/migrate/builder/splitSqlStatements.js.map +0 -1
  254. package/dist/migrate/builder/tableBuilder.d.ts +0 -51
  255. package/dist/migrate/builder/tableBuilder.d.ts.map +0 -1
  256. package/dist/migrate/builder/tableBuilder.js +0 -291
  257. package/dist/migrate/builder/tableBuilder.js.map +0 -1
  258. package/dist/migrate/builder/types.d.ts +0 -466
  259. package/dist/migrate/builder/types.d.ts.map +0 -1
  260. package/dist/migrate/builder/types.js +0 -8
  261. package/dist/migrate/builder/types.js.map +0 -1
  262. package/dist/migrate/cli-config.d.ts +0 -3
  263. package/dist/migrate/cli-config.d.ts.map +0 -1
  264. package/dist/migrate/cli-config.js +0 -35
  265. package/dist/migrate/cli-config.js.map +0 -1
  266. package/dist/migrate/cli.d.ts +0 -20
  267. package/dist/migrate/cli.d.ts.map +0 -1
  268. package/dist/migrate/cli.js +0 -398
  269. package/dist/migrate/cli.js.map +0 -1
  270. package/dist/migrate/codegen/entityCodeGenerator.d.ts +0 -137
  271. package/dist/migrate/codegen/entityCodeGenerator.d.ts.map +0 -1
  272. package/dist/migrate/codegen/entityCodeGenerator.js +0 -405
  273. package/dist/migrate/codegen/entityCodeGenerator.js.map +0 -1
  274. package/dist/migrate/codegen/entityMerger.d.ts +0 -115
  275. package/dist/migrate/codegen/entityMerger.d.ts.map +0 -1
  276. package/dist/migrate/codegen/entityMerger.js +0 -294
  277. package/dist/migrate/codegen/entityMerger.js.map +0 -1
  278. package/dist/migrate/codegen/index.d.ts +0 -11
  279. package/dist/migrate/codegen/index.d.ts.map +0 -1
  280. package/dist/migrate/codegen/index.js +0 -15
  281. package/dist/migrate/codegen/index.js.map +0 -1
  282. package/dist/migrate/codegen/migrationCodeGenerator.d.ts +0 -62
  283. package/dist/migrate/codegen/migrationCodeGenerator.d.ts.map +0 -1
  284. package/dist/migrate/codegen/migrationCodeGenerator.js +0 -356
  285. package/dist/migrate/codegen/migrationCodeGenerator.js.map +0 -1
  286. package/dist/migrate/codegen/migrationFile.d.ts +0 -29
  287. package/dist/migrate/codegen/migrationFile.d.ts.map +0 -1
  288. package/dist/migrate/codegen/migrationFile.js +0 -48
  289. package/dist/migrate/codegen/migrationFile.js.map +0 -1
  290. package/dist/migrate/codegen/smartRelationDetector.d.ts +0 -48
  291. package/dist/migrate/codegen/smartRelationDetector.d.ts.map +0 -1
  292. package/dist/migrate/codegen/smartRelationDetector.js +0 -135
  293. package/dist/migrate/codegen/smartRelationDetector.js.map +0 -1
  294. package/dist/migrate/drift/driftDetector.d.ts +0 -80
  295. package/dist/migrate/drift/driftDetector.d.ts.map +0 -1
  296. package/dist/migrate/drift/driftDetector.js +0 -247
  297. package/dist/migrate/drift/driftDetector.js.map +0 -1
  298. package/dist/migrate/drift/index.d.ts +0 -7
  299. package/dist/migrate/drift/index.d.ts.map +0 -1
  300. package/dist/migrate/drift/index.js +0 -7
  301. package/dist/migrate/drift/index.js.map +0 -1
  302. package/dist/migrate/generator/index.d.ts +0 -3
  303. package/dist/migrate/generator/index.d.ts.map +0 -1
  304. package/dist/migrate/generator/index.js +0 -3
  305. package/dist/migrate/generator/index.js.map +0 -1
  306. package/dist/migrate/generator/mongoSchemaGenerator.d.ts +0 -48
  307. package/dist/migrate/generator/mongoSchemaGenerator.d.ts.map +0 -1
  308. package/dist/migrate/generator/mongoSchemaGenerator.js +0 -188
  309. package/dist/migrate/generator/mongoSchemaGenerator.js.map +0 -1
  310. package/dist/migrate/index.d.ts +0 -16
  311. package/dist/migrate/index.d.ts.map +0 -1
  312. package/dist/migrate/index.js +0 -23
  313. package/dist/migrate/index.js.map +0 -1
  314. package/dist/migrate/introspection/abstractSqlSchemaIntrospector.d.ts +0 -77
  315. package/dist/migrate/introspection/abstractSqlSchemaIntrospector.d.ts.map +0 -1
  316. package/dist/migrate/introspection/abstractSqlSchemaIntrospector.js +0 -156
  317. package/dist/migrate/introspection/abstractSqlSchemaIntrospector.js.map +0 -1
  318. package/dist/migrate/introspection/baseSqlIntrospector.d.ts +0 -26
  319. package/dist/migrate/introspection/baseSqlIntrospector.d.ts.map +0 -1
  320. package/dist/migrate/introspection/baseSqlIntrospector.js +0 -132
  321. package/dist/migrate/introspection/baseSqlIntrospector.js.map +0 -1
  322. package/dist/migrate/introspection/index.d.ts +0 -6
  323. package/dist/migrate/introspection/index.d.ts.map +0 -1
  324. package/dist/migrate/introspection/index.js +0 -6
  325. package/dist/migrate/introspection/index.js.map +0 -1
  326. package/dist/migrate/introspection/mongoIntrospector.d.ts +0 -15
  327. package/dist/migrate/introspection/mongoIntrospector.d.ts.map +0 -1
  328. package/dist/migrate/introspection/mongoIntrospector.js +0 -100
  329. package/dist/migrate/introspection/mongoIntrospector.js.map +0 -1
  330. package/dist/migrate/introspection/mysqlIntrospector.d.ts +0 -59
  331. package/dist/migrate/introspection/mysqlIntrospector.d.ts.map +0 -1
  332. package/dist/migrate/introspection/mysqlIntrospector.js +0 -175
  333. package/dist/migrate/introspection/mysqlIntrospector.js.map +0 -1
  334. package/dist/migrate/introspection/postgresIntrospector.d.ts +0 -55
  335. package/dist/migrate/introspection/postgresIntrospector.d.ts.map +0 -1
  336. package/dist/migrate/introspection/postgresIntrospector.js +0 -226
  337. package/dist/migrate/introspection/postgresIntrospector.js.map +0 -1
  338. package/dist/migrate/introspection/sqliteIntrospector.d.ts +0 -60
  339. package/dist/migrate/introspection/sqliteIntrospector.d.ts.map +0 -1
  340. package/dist/migrate/introspection/sqliteIntrospector.js +0 -188
  341. package/dist/migrate/introspection/sqliteIntrospector.js.map +0 -1
  342. package/dist/migrate/migrator.d.ts +0 -168
  343. package/dist/migrate/migrator.d.ts.map +0 -1
  344. package/dist/migrate/migrator.js +0 -614
  345. package/dist/migrate/migrator.js.map +0 -1
  346. package/dist/migrate/schemaGenerator.d.ts +0 -142
  347. package/dist/migrate/schemaGenerator.d.ts.map +0 -1
  348. package/dist/migrate/schemaGenerator.js +0 -693
  349. package/dist/migrate/schemaGenerator.js.map +0 -1
  350. package/dist/migrate/schemaGeneratorAsync.d.ts +0 -9
  351. package/dist/migrate/schemaGeneratorAsync.d.ts.map +0 -1
  352. package/dist/migrate/schemaGeneratorAsync.js +0 -13
  353. package/dist/migrate/schemaGeneratorAsync.js.map +0 -1
  354. package/dist/migrate/storage/databaseStorage.d.ts +0 -25
  355. package/dist/migrate/storage/databaseStorage.d.ts.map +0 -1
  356. package/dist/migrate/storage/databaseStorage.js +0 -78
  357. package/dist/migrate/storage/databaseStorage.js.map +0 -1
  358. package/dist/migrate/storage/index.d.ts +0 -3
  359. package/dist/migrate/storage/index.d.ts.map +0 -1
  360. package/dist/migrate/storage/index.js +0 -3
  361. package/dist/migrate/storage/index.js.map +0 -1
  362. package/dist/migrate/storage/jsonStorage.d.ts +0 -16
  363. package/dist/migrate/storage/jsonStorage.d.ts.map +0 -1
  364. package/dist/migrate/storage/jsonStorage.js +0 -43
  365. package/dist/migrate/storage/jsonStorage.js.map +0 -1
  366. package/dist/migrate/sync/index.d.ts +0 -7
  367. package/dist/migrate/sync/index.d.ts.map +0 -1
  368. package/dist/migrate/sync/index.js +0 -7
  369. package/dist/migrate/sync/index.js.map +0 -1
  370. package/dist/migrate/sync/schemaSync.d.ts +0 -132
  371. package/dist/migrate/sync/schemaSync.d.ts.map +0 -1
  372. package/dist/migrate/sync/schemaSync.js +0 -260
  373. package/dist/migrate/sync/schemaSync.js.map +0 -1
  374. package/dist/mongo/index.d.ts +0 -6
  375. package/dist/mongo/index.d.ts.map +0 -1
  376. package/dist/mongo/index.js +0 -6
  377. package/dist/mongo/index.js.map +0 -1
  378. package/dist/mongo/mongoDialect.d.ts +0 -83
  379. package/dist/mongo/mongoDialect.d.ts.map +0 -1
  380. package/dist/mongo/mongoDialect.js +0 -418
  381. package/dist/mongo/mongoDialect.js.map +0 -1
  382. package/dist/mongo/mongodbNativeDialect.d.ts +0 -10
  383. package/dist/mongo/mongodbNativeDialect.d.ts.map +0 -1
  384. package/dist/mongo/mongodbNativeDialect.js +0 -10
  385. package/dist/mongo/mongodbNativeDialect.js.map +0 -1
  386. package/dist/mongo/mongodbQuerier.d.ts +0 -46
  387. package/dist/mongo/mongodbQuerier.d.ts.map +0 -1
  388. package/dist/mongo/mongodbQuerier.js +0 -344
  389. package/dist/mongo/mongodbQuerier.js.map +0 -1
  390. package/dist/mongo/mongodbQuerierPool.d.ts +0 -12
  391. package/dist/mongo/mongodbQuerierPool.d.ts.map +0 -1
  392. package/dist/mongo/mongodbQuerierPool.js +0 -19
  393. package/dist/mongo/mongodbQuerierPool.js.map +0 -1
  394. package/dist/mysql/index.d.ts +0 -5
  395. package/dist/mysql/index.d.ts.map +0 -1
  396. package/dist/mysql/index.js +0 -5
  397. package/dist/mysql/index.js.map +0 -1
  398. package/dist/mysql/mysql2Dialect.d.ts +0 -10
  399. package/dist/mysql/mysql2Dialect.d.ts.map +0 -1
  400. package/dist/mysql/mysql2Dialect.js +0 -10
  401. package/dist/mysql/mysql2Dialect.js.map +0 -1
  402. package/dist/mysql/mysql2Querier.d.ts +0 -12
  403. package/dist/mysql/mysql2Querier.d.ts.map +0 -1
  404. package/dist/mysql/mysql2Querier.js +0 -34
  405. package/dist/mysql/mysql2Querier.js.map +0 -1
  406. package/dist/mysql/mysql2QuerierPool.d.ts +0 -12
  407. package/dist/mysql/mysql2QuerierPool.d.ts.map +0 -1
  408. package/dist/mysql/mysql2QuerierPool.js +0 -18
  409. package/dist/mysql/mysql2QuerierPool.js.map +0 -1
  410. package/dist/mysql/mysqlDialect.d.ts +0 -6
  411. package/dist/mysql/mysqlDialect.d.ts.map +0 -1
  412. package/dist/mysql/mysqlDialect.js +0 -6
  413. package/dist/mysql/mysqlDialect.js.map +0 -1
  414. package/dist/namingStrategy/defaultNamingStrategy.d.ts +0 -10
  415. package/dist/namingStrategy/defaultNamingStrategy.d.ts.map +0 -1
  416. package/dist/namingStrategy/defaultNamingStrategy.js +0 -15
  417. package/dist/namingStrategy/defaultNamingStrategy.js.map +0 -1
  418. package/dist/namingStrategy/index.d.ts +0 -3
  419. package/dist/namingStrategy/index.d.ts.map +0 -1
  420. package/dist/namingStrategy/index.js +0 -3
  421. package/dist/namingStrategy/index.js.map +0 -1
  422. package/dist/namingStrategy/snakeCaseNamingStrategy.d.ts +0 -9
  423. package/dist/namingStrategy/snakeCaseNamingStrategy.d.ts.map +0 -1
  424. package/dist/namingStrategy/snakeCaseNamingStrategy.js +0 -14
  425. package/dist/namingStrategy/snakeCaseNamingStrategy.js.map +0 -1
  426. package/dist/neon/index.d.ts +0 -4
  427. package/dist/neon/index.d.ts.map +0 -1
  428. package/dist/neon/index.js +0 -4
  429. package/dist/neon/index.js.map +0 -1
  430. package/dist/neon/neonDialect.d.ts +0 -11
  431. package/dist/neon/neonDialect.d.ts.map +0 -1
  432. package/dist/neon/neonDialect.js +0 -11
  433. package/dist/neon/neonDialect.js.map +0 -1
  434. package/dist/neon/neonQuerier.d.ts +0 -6
  435. package/dist/neon/neonQuerier.d.ts.map +0 -1
  436. package/dist/neon/neonQuerier.js +0 -4
  437. package/dist/neon/neonQuerier.js.map +0 -1
  438. package/dist/neon/neonQuerierPool.d.ts +0 -11
  439. package/dist/neon/neonQuerierPool.d.ts.map +0 -1
  440. package/dist/neon/neonQuerierPool.js +0 -15
  441. package/dist/neon/neonQuerierPool.js.map +0 -1
  442. package/dist/options.d.ts +0 -5
  443. package/dist/options.d.ts.map +0 -1
  444. package/dist/options.js +0 -14
  445. package/dist/options.js.map +0 -1
  446. package/dist/postgres/abstractPgQuerier.d.ts +0 -24
  447. package/dist/postgres/abstractPgQuerier.d.ts.map +0 -1
  448. package/dist/postgres/abstractPgQuerier.js +0 -33
  449. package/dist/postgres/abstractPgQuerier.js.map +0 -1
  450. package/dist/postgres/abstractPgQuerierPool.d.ts +0 -15
  451. package/dist/postgres/abstractPgQuerierPool.d.ts.map +0 -1
  452. package/dist/postgres/abstractPgQuerierPool.js +0 -10
  453. package/dist/postgres/abstractPgQuerierPool.js.map +0 -1
  454. package/dist/postgres/index.d.ts +0 -6
  455. package/dist/postgres/index.d.ts.map +0 -1
  456. package/dist/postgres/index.js +0 -6
  457. package/dist/postgres/index.js.map +0 -1
  458. package/dist/postgres/pgDialect.d.ts +0 -13
  459. package/dist/postgres/pgDialect.d.ts.map +0 -1
  460. package/dist/postgres/pgDialect.js +0 -14
  461. package/dist/postgres/pgDialect.js.map +0 -1
  462. package/dist/postgres/pgQuerier.d.ts +0 -6
  463. package/dist/postgres/pgQuerier.d.ts.map +0 -1
  464. package/dist/postgres/pgQuerier.js +0 -4
  465. package/dist/postgres/pgQuerier.js.map +0 -1
  466. package/dist/postgres/pgQuerierPool.d.ts +0 -11
  467. package/dist/postgres/pgQuerierPool.d.ts.map +0 -1
  468. package/dist/postgres/pgQuerierPool.js +0 -15
  469. package/dist/postgres/pgQuerierPool.js.map +0 -1
  470. package/dist/postgres/postgresDialect.d.ts +0 -48
  471. package/dist/postgres/postgresDialect.d.ts.map +0 -1
  472. package/dist/postgres/postgresDialect.js +0 -222
  473. package/dist/postgres/postgresDialect.js.map +0 -1
  474. package/dist/postgres/postgresWireDriverCapabilities.d.ts +0 -15
  475. package/dist/postgres/postgresWireDriverCapabilities.d.ts.map +0 -1
  476. package/dist/postgres/postgresWireDriverCapabilities.js +0 -15
  477. package/dist/postgres/postgresWireDriverCapabilities.js.map +0 -1
  478. package/dist/querier/abstractPoolQuerier.d.ts +0 -14
  479. package/dist/querier/abstractPoolQuerier.d.ts.map +0 -1
  480. package/dist/querier/abstractPoolQuerier.js +0 -31
  481. package/dist/querier/abstractPoolQuerier.js.map +0 -1
  482. package/dist/querier/abstractQuerier.d.ts +0 -141
  483. package/dist/querier/abstractQuerier.d.ts.map +0 -1
  484. package/dist/querier/abstractQuerier.js +0 -431
  485. package/dist/querier/abstractQuerier.js.map +0 -1
  486. package/dist/querier/abstractQuerierPool.d.ts +0 -27
  487. package/dist/querier/abstractQuerierPool.d.ts.map +0 -1
  488. package/dist/querier/abstractQuerierPool.js +0 -31
  489. package/dist/querier/abstractQuerierPool.js.map +0 -1
  490. package/dist/querier/abstractSqlQuerier.d.ts +0 -53
  491. package/dist/querier/abstractSqlQuerier.d.ts.map +0 -1
  492. package/dist/querier/abstractSqlQuerier.js +0 -256
  493. package/dist/querier/abstractSqlQuerier.js.map +0 -1
  494. package/dist/querier/decorator/index.d.ts +0 -5
  495. package/dist/querier/decorator/index.d.ts.map +0 -1
  496. package/dist/querier/decorator/index.js +0 -5
  497. package/dist/querier/decorator/index.js.map +0 -1
  498. package/dist/querier/decorator/injectQuerier.d.ts +0 -4
  499. package/dist/querier/decorator/injectQuerier.d.ts.map +0 -1
  500. package/dist/querier/decorator/injectQuerier.js +0 -34
  501. package/dist/querier/decorator/injectQuerier.js.map +0 -1
  502. package/dist/querier/decorator/log.d.ts +0 -7
  503. package/dist/querier/decorator/log.d.ts.map +0 -1
  504. package/dist/querier/decorator/log.js +0 -27
  505. package/dist/querier/decorator/log.js.map +0 -1
  506. package/dist/querier/decorator/serialized.d.ts +0 -7
  507. package/dist/querier/decorator/serialized.d.ts.map +0 -1
  508. package/dist/querier/decorator/serialized.js +0 -14
  509. package/dist/querier/decorator/serialized.js.map +0 -1
  510. package/dist/querier/decorator/transactional.d.ts +0 -7
  511. package/dist/querier/decorator/transactional.d.ts.map +0 -1
  512. package/dist/querier/decorator/transactional.js +0 -49
  513. package/dist/querier/decorator/transactional.js.map +0 -1
  514. package/dist/querier/index.d.ts +0 -5
  515. package/dist/querier/index.d.ts.map +0 -1
  516. package/dist/querier/index.js +0 -5
  517. package/dist/querier/index.js.map +0 -1
  518. package/dist/schema/canonicalType.d.ts +0 -54
  519. package/dist/schema/canonicalType.d.ts.map +0 -1
  520. package/dist/schema/canonicalType.js +0 -571
  521. package/dist/schema/canonicalType.js.map +0 -1
  522. package/dist/schema/index.d.ts +0 -26
  523. package/dist/schema/index.d.ts.map +0 -1
  524. package/dist/schema/index.js +0 -27
  525. package/dist/schema/index.js.map +0 -1
  526. package/dist/schema/schemaAST.d.ts +0 -155
  527. package/dist/schema/schemaAST.d.ts.map +0 -1
  528. package/dist/schema/schemaAST.js +0 -496
  529. package/dist/schema/schemaAST.js.map +0 -1
  530. package/dist/schema/schemaASTBuilder.d.ts +0 -58
  531. package/dist/schema/schemaASTBuilder.d.ts.map +0 -1
  532. package/dist/schema/schemaASTBuilder.js +0 -228
  533. package/dist/schema/schemaASTBuilder.js.map +0 -1
  534. package/dist/schema/schemaASTDiffer.d.ts +0 -84
  535. package/dist/schema/schemaASTDiffer.d.ts.map +0 -1
  536. package/dist/schema/schemaASTDiffer.js +0 -431
  537. package/dist/schema/schemaASTDiffer.js.map +0 -1
  538. package/dist/schema/types.d.ts +0 -348
  539. package/dist/schema/types.d.ts.map +0 -1
  540. package/dist/schema/types.js +0 -11
  541. package/dist/schema/types.js.map +0 -1
  542. package/dist/sqlite/abstractSqliteQuerier.d.ts +0 -4
  543. package/dist/sqlite/abstractSqliteQuerier.d.ts.map +0 -1
  544. package/dist/sqlite/abstractSqliteQuerier.js +0 -4
  545. package/dist/sqlite/abstractSqliteQuerier.js.map +0 -1
  546. package/dist/sqlite/betterSqlite3Dialect.d.ts +0 -10
  547. package/dist/sqlite/betterSqlite3Dialect.d.ts.map +0 -1
  548. package/dist/sqlite/betterSqlite3Dialect.js +0 -10
  549. package/dist/sqlite/betterSqlite3Dialect.js.map +0 -1
  550. package/dist/sqlite/index.d.ts +0 -6
  551. package/dist/sqlite/index.d.ts.map +0 -1
  552. package/dist/sqlite/index.js +0 -6
  553. package/dist/sqlite/index.js.map +0 -1
  554. package/dist/sqlite/sqliteDialect.d.ts +0 -36
  555. package/dist/sqlite/sqliteDialect.d.ts.map +0 -1
  556. package/dist/sqlite/sqliteDialect.js +0 -155
  557. package/dist/sqlite/sqliteDialect.js.map +0 -1
  558. package/dist/sqlite/sqliteQuerier.d.ts +0 -14
  559. package/dist/sqlite/sqliteQuerier.d.ts.map +0 -1
  560. package/dist/sqlite/sqliteQuerier.js +0 -30
  561. package/dist/sqlite/sqliteQuerier.js.map +0 -1
  562. package/dist/sqlite/sqliteQuerierPool.d.ts +0 -14
  563. package/dist/sqlite/sqliteQuerierPool.d.ts.map +0 -1
  564. package/dist/sqlite/sqliteQuerierPool.js +0 -36
  565. package/dist/sqlite/sqliteQuerierPool.js.map +0 -1
  566. package/dist/type/config.d.ts +0 -43
  567. package/dist/type/config.d.ts.map +0 -1
  568. package/dist/type/config.js +0 -2
  569. package/dist/type/config.js.map +0 -1
  570. package/dist/type/entity.d.ts +0 -332
  571. package/dist/type/entity.d.ts.map +0 -1
  572. package/dist/type/entity.js +0 -5
  573. package/dist/type/entity.js.map +0 -1
  574. package/dist/type/index.d.ts +0 -12
  575. package/dist/type/index.d.ts.map +0 -1
  576. package/dist/type/index.js +0 -12
  577. package/dist/type/index.js.map +0 -1
  578. package/dist/type/logger.d.ts +0 -61
  579. package/dist/type/logger.d.ts.map +0 -1
  580. package/dist/type/logger.js +0 -2
  581. package/dist/type/logger.js.map +0 -1
  582. package/dist/type/migration.d.ts +0 -267
  583. package/dist/type/migration.d.ts.map +0 -1
  584. package/dist/type/migration.js +0 -2
  585. package/dist/type/migration.js.map +0 -1
  586. package/dist/type/migratorDialect.d.ts +0 -10
  587. package/dist/type/migratorDialect.d.ts.map +0 -1
  588. package/dist/type/migratorDialect.js +0 -16
  589. package/dist/type/migratorDialect.js.map +0 -1
  590. package/dist/type/namingStrategy.d.ts +0 -18
  591. package/dist/type/namingStrategy.d.ts.map +0 -1
  592. package/dist/type/namingStrategy.js +0 -2
  593. package/dist/type/namingStrategy.js.map +0 -1
  594. package/dist/type/querier.d.ts +0 -167
  595. package/dist/type/querier.d.ts.map +0 -1
  596. package/dist/type/querier.js +0 -11
  597. package/dist/type/querier.js.map +0 -1
  598. package/dist/type/querierPool.d.ts +0 -62
  599. package/dist/type/querierPool.d.ts.map +0 -1
  600. package/dist/type/querierPool.js +0 -2
  601. package/dist/type/querierPool.js.map +0 -1
  602. package/dist/type/query.d.ts +0 -703
  603. package/dist/type/query.d.ts.map +0 -1
  604. package/dist/type/query.js +0 -11
  605. package/dist/type/query.js.map +0 -1
  606. package/dist/type/universalQuerier.d.ts +0 -136
  607. package/dist/type/universalQuerier.d.ts.map +0 -1
  608. package/dist/type/universalQuerier.js +0 -2
  609. package/dist/type/universalQuerier.js.map +0 -1
  610. package/dist/type/utility.d.ts +0 -37
  611. package/dist/type/utility.d.ts.map +0 -1
  612. package/dist/type/utility.js +0 -2
  613. package/dist/type/utility.js.map +0 -1
  614. package/dist/util/ansiSqlLiteral.d.ts +0 -21
  615. package/dist/util/ansiSqlLiteral.d.ts.map +0 -1
  616. package/dist/util/ansiSqlLiteral.js +0 -101
  617. package/dist/util/ansiSqlLiteral.js.map +0 -1
  618. package/dist/util/dialect.util.d.ts +0 -31
  619. package/dist/util/dialect.util.d.ts.map +0 -1
  620. package/dist/util/dialect.util.js +0 -113
  621. package/dist/util/dialect.util.js.map +0 -1
  622. package/dist/util/field.util.d.ts +0 -14
  623. package/dist/util/field.util.d.ts.map +0 -1
  624. package/dist/util/field.util.js +0 -57
  625. package/dist/util/field.util.js.map +0 -1
  626. package/dist/util/hook.util.d.ts +0 -15
  627. package/dist/util/hook.util.d.ts.map +0 -1
  628. package/dist/util/hook.util.js +0 -20
  629. package/dist/util/hook.util.js.map +0 -1
  630. package/dist/util/index.d.ts +0 -10
  631. package/dist/util/index.d.ts.map +0 -1
  632. package/dist/util/index.js +0 -10
  633. package/dist/util/index.js.map +0 -1
  634. package/dist/util/logger.d.ts +0 -34
  635. package/dist/util/logger.d.ts.map +0 -1
  636. package/dist/util/logger.js +0 -129
  637. package/dist/util/logger.js.map +0 -1
  638. package/dist/util/object.util.d.ts +0 -10
  639. package/dist/util/object.util.d.ts.map +0 -1
  640. package/dist/util/object.util.js +0 -29
  641. package/dist/util/object.util.js.map +0 -1
  642. package/dist/util/raw.d.ts +0 -18
  643. package/dist/util/raw.d.ts.map +0 -1
  644. package/dist/util/raw.js +0 -20
  645. package/dist/util/raw.js.map +0 -1
  646. package/dist/util/relationQuery.util.d.ts +0 -25
  647. package/dist/util/relationQuery.util.d.ts.map +0 -1
  648. package/dist/util/relationQuery.util.js +0 -101
  649. package/dist/util/relationQuery.util.js.map +0 -1
  650. package/dist/util/sql.util.d.ts +0 -50
  651. package/dist/util/sql.util.d.ts.map +0 -1
  652. package/dist/util/sql.util.js +0 -141
  653. package/dist/util/sql.util.js.map +0 -1
  654. package/dist/util/string.util.d.ts +0 -29
  655. package/dist/util/string.util.d.ts.map +0 -1
  656. package/dist/util/string.util.js +0 -93
  657. package/dist/util/string.util.js.map +0 -1
@@ -1,1332 +0,0 @@
1
- import { getMeta } from '../entity/index.js';
2
- import { resolveVectorCast } from '../schema/canonicalType.js';
3
- import { QueryRaw, RAW_ALIAS, RAW_VALUE, } from '../type/index.js';
4
- import { buildQueryWhereAsMap, buildSortMap, escapeSqlId, fillOnFields, filterFieldKeys, flatObject, getFieldCallbackValue, getFieldKeys, getKeys, getRelationRequestSummary, hasKeys, isJsonType, isPopulatingRelations, isVectorSearch, normalizeScalarFieldSelection, parseGroupMap, parseRelationAtKey, raw, } from '../util/index.js';
5
- import { AbstractDialect } from './abstractDialect.js';
6
- import { SqlQueryContext } from './queryContext.js';
7
- export class AbstractSqlDialect extends AbstractDialect {
8
- constructor(engineDefaults, options = {}) {
9
- super(engineDefaults, options);
10
- }
11
- isolationLevelStrategy = 'inline';
12
- alterColumnStrategy = 'single-statement';
13
- alterColumnSyntax = 'ALTER COLUMN';
14
- dropForeignKeySyntax = 'DROP CONSTRAINT';
15
- dropIndexSyntax = 'standalone';
16
- renameTableSyntax = 'alter-table';
17
- booleanLiteral = 'native';
18
- vectorOpsClass = undefined;
19
- vectorExtension = undefined;
20
- get escapeIdChar() {
21
- return this.quoteChar;
22
- }
23
- getBeginTransactionStatements(isolationLevel) {
24
- const level = isolationLevel?.toUpperCase();
25
- const strategy = this.isolationLevelStrategy;
26
- if (!level || strategy === 'none') {
27
- return [this.beginTransactionCommand];
28
- }
29
- if (strategy === 'inline') {
30
- return [`${this.beginTransactionCommand} ISOLATION LEVEL ${level}`];
31
- }
32
- // 'set-before' — MySQL/MariaDB pattern
33
- return [`SET TRANSACTION ISOLATION LEVEL ${level}`, this.beginTransactionCommand];
34
- }
35
- createContext() {
36
- return new SqlQueryContext(this);
37
- }
38
- addValue(values, value) {
39
- values.push(this.normalizeValue(value));
40
- return this.placeholder(values.length);
41
- }
42
- /**
43
- * Normalizes a parameter value for the database driver.
44
- * Handles bigint, boolean, and serializes plain objects/arrays to JSON strings.
45
- * Date values are preserved so SQL drivers can apply native date/time binding.
46
- * Postgres overrides to pass objects through to its native JSONB driver.
47
- */
48
- normalizeValue(value) {
49
- if (value == null || value instanceof Date || value instanceof Uint8Array || value instanceof QueryRaw) {
50
- return value;
51
- }
52
- if (typeof value === 'bigint') {
53
- return Number(value);
54
- }
55
- if (typeof value === 'boolean') {
56
- return this.booleanLiteral === 'native' ? value : value ? 1 : 0;
57
- }
58
- return value;
59
- }
60
- /**
61
- * Normalizes a list of parameter values.
62
- */
63
- normalizeValues(values) {
64
- return values?.map((v) => this.normalizeValue(v));
65
- }
66
- placeholder(_index) {
67
- return '?';
68
- }
69
- returningId(entity) {
70
- const meta = getMeta(entity);
71
- const idKey = (meta.id ?? 'id');
72
- const idName = this.resolveColumnName(idKey, meta.fields[idKey]);
73
- return `RETURNING ${this.escapeId(idName)} ${this.escapeId('id')}`;
74
- }
75
- search(ctx, entity, q = {}, opts = {}) {
76
- const meta = getMeta(entity);
77
- const tableName = this.resolveTableName(entity, meta);
78
- const prefix = this.resolveRelationAwarePrefix(tableName, meta, opts, q.$select, q.$populate);
79
- opts = { ...opts, prefix };
80
- this.where(ctx, entity, q.$where, opts);
81
- this.sort(ctx, entity, q.$sort, opts);
82
- this.pager(ctx, q);
83
- }
84
- selectFields(ctx, entity, select, opts = {}, exclude) {
85
- const meta = getMeta(entity);
86
- const prefix = opts.prefix ? opts.prefix + '.' : '';
87
- const escapedPrefix = this.escapeId(opts.prefix, true, true);
88
- let selectArr;
89
- if (select) {
90
- if (Array.isArray(select)) {
91
- // Internal-only path: raw SQL expressions passed as QueryRaw[]
92
- selectArr = select;
93
- }
94
- else {
95
- selectArr = normalizeScalarFieldSelection(meta, select, exclude);
96
- }
97
- const id = meta.id;
98
- if (id && opts.prefix && !selectArr.includes(id)) {
99
- selectArr = [id, ...selectArr];
100
- }
101
- }
102
- else {
103
- selectArr = normalizeScalarFieldSelection(meta, undefined, exclude);
104
- }
105
- if (!selectArr.length) {
106
- ctx.append(escapedPrefix + '*');
107
- return;
108
- }
109
- selectArr.forEach((key, index) => {
110
- if (index > 0)
111
- ctx.append(', ');
112
- if (key instanceof QueryRaw) {
113
- this.getRawValue(ctx, {
114
- value: key,
115
- prefix: opts.prefix,
116
- escapedPrefix,
117
- autoPrefixAlias: opts.autoPrefixAlias,
118
- });
119
- }
120
- else {
121
- const field = meta.fields[key];
122
- if (!field)
123
- return;
124
- const columnName = this.resolveColumnName(key, field);
125
- if (field.virtual) {
126
- this.getRawValue(ctx, {
127
- value: raw(field.virtual[RAW_VALUE], key),
128
- prefix: opts.prefix,
129
- escapedPrefix,
130
- autoPrefixAlias: opts.autoPrefixAlias,
131
- });
132
- }
133
- else {
134
- ctx.append(escapedPrefix + this.escapeId(columnName));
135
- }
136
- if (!field.virtual && (columnName !== key || opts.autoPrefixAlias)) {
137
- const aliasStr = prefix + key;
138
- ctx.append(' ' + this.escapeId(aliasStr, true));
139
- }
140
- }
141
- });
142
- }
143
- select(ctx, entity, select, exclude, populate, opts = {}, distinct, sort) {
144
- const meta = getMeta(entity);
145
- const tableName = this.resolveTableName(entity, meta);
146
- const mapSelect = Array.isArray(select) ? undefined : select;
147
- const prefix = this.resolveRelationAwarePrefix(tableName, meta, opts, mapSelect, populate);
148
- ctx.append(distinct ? 'SELECT DISTINCT ' : 'SELECT ');
149
- this.selectFields(ctx, entity, select, { prefix }, exclude);
150
- // Add related fields BEFORE FROM clause
151
- this.selectRelationFields(ctx, entity, mapSelect, populate, { prefix });
152
- // Inject vector distance projections when $project is set
153
- if (sort) {
154
- const sortMap = buildSortMap(sort);
155
- for (const [key, val] of Object.entries(sortMap)) {
156
- if (isVectorSearch(val) && val.$project) {
157
- ctx.append(', ');
158
- this.appendVectorProjection(ctx, meta, key, val);
159
- }
160
- }
161
- }
162
- ctx.append(` FROM ${this.escapeId(tableName)}`);
163
- // Add JOINs AFTER FROM clause
164
- this.selectRelationJoins(ctx, entity, mapSelect, populate, { prefix });
165
- }
166
- resolveRelationAwarePrefix(tableName, meta, opts, select, populate) {
167
- return (opts.prefix ?? (opts.autoPrefix || isPopulatingRelations(meta, populate))) ? tableName : undefined;
168
- }
169
- selectRelationFields(ctx, entity, select, populate, opts = {}) {
170
- this.forEachJoinableRelation(entity, select, populate, opts, (relEntity, relQuery, joinRelAlias) => {
171
- ctx.append(', ');
172
- this.selectFields(ctx, relEntity, relQuery.$select, { prefix: joinRelAlias, autoPrefixAlias: true }, relQuery.$exclude);
173
- this.selectRelationFields(ctx, relEntity, relQuery.$select, relQuery.$populate, { prefix: joinRelAlias });
174
- });
175
- }
176
- selectRelationJoins(ctx, entity, select, populate, opts = {}) {
177
- this.forEachJoinableRelation(entity, select, populate, opts, (relEntity, relQuery, joinRelAlias, relOpts, meta, tableName, required) => {
178
- const relMeta = getMeta(relEntity);
179
- const relTableName = this.resolveTableName(relEntity, relMeta);
180
- const relEntityName = this.escapeId(relTableName);
181
- const relPath = opts.prefix ? this.escapeId(opts.prefix, true) : this.escapeId(tableName);
182
- const joinType = required ? 'INNER' : 'LEFT';
183
- const joinAlias = this.escapeId(joinRelAlias, true);
184
- ctx.append(` ${joinType} JOIN ${relEntityName} ${joinAlias} ON `);
185
- let refAppended = false;
186
- for (const it of relOpts.references ?? []) {
187
- if (refAppended)
188
- ctx.append(' AND ');
189
- const relField = relMeta.fields[it.foreign];
190
- const field = meta.fields[it.local];
191
- const foreignColumnName = this.resolveColumnName(it.foreign, relField);
192
- const localColumnName = this.resolveColumnName(it.local, field);
193
- ctx.append(`${joinAlias}.${this.escapeId(foreignColumnName)} = ${relPath}.${this.escapeId(localColumnName)}`);
194
- refAppended = true;
195
- }
196
- if (relQuery.$where) {
197
- ctx.append(' AND ');
198
- this.where(ctx, relEntity, relQuery.$where, { prefix: joinRelAlias, clause: false });
199
- }
200
- this.selectRelationJoins(ctx, relEntity, relQuery.$select, relQuery.$populate, { prefix: joinRelAlias });
201
- });
202
- }
203
- /**
204
- * Iterates over joinable (11/m1) relations for a given select, resolving shared metadata.
205
- * Used by both `selectRelationFields` and `selectRelationJoins` to avoid duplicated iteration logic.
206
- */
207
- forEachJoinableRelation(entity, select, populate, opts, callback) {
208
- if (!select && !populate)
209
- return;
210
- const meta = getMeta(entity);
211
- const tableName = this.resolveTableName(entity, meta);
212
- const relKeys = getRelationRequestSummary(meta, populate).joinableKeys;
213
- const prefix = opts.prefix;
214
- for (const relKey of relKeys) {
215
- const relOpts = meta.relations[relKey];
216
- if (!relOpts?.entity)
217
- continue;
218
- const isFirstLevel = prefix === tableName;
219
- const joinRelAlias = isFirstLevel ? relKey : prefix ? `${prefix}.${relKey}` : relKey;
220
- const relEntity = relOpts.entity();
221
- const { query: relQuery, required } = parseRelationAtKey(relKey, populate);
222
- callback(relEntity, relQuery, joinRelAlias, relOpts, meta, tableName, required);
223
- }
224
- }
225
- where(ctx, entity, where = {}, opts = {}) {
226
- const meta = getMeta(entity);
227
- const { usePrecedence, clause = 'WHERE', softDelete } = opts;
228
- where = buildQueryWhereAsMap(meta, where);
229
- if (meta.softDelete &&
230
- (softDelete || softDelete === undefined) &&
231
- !where[meta.softDelete]) {
232
- where[meta.softDelete] = null;
233
- }
234
- const entries = Object.entries(where);
235
- if (!entries.length) {
236
- return;
237
- }
238
- if (clause) {
239
- ctx.append(` ${clause} `);
240
- }
241
- if (usePrecedence) {
242
- ctx.append('(');
243
- }
244
- const whereKeys = getKeys(where);
245
- const hasMultipleKeys = whereKeys.length > 1;
246
- let appended = false;
247
- whereKeys.forEach((key) => {
248
- const val = where[key];
249
- if (val === undefined)
250
- return;
251
- if (appended) {
252
- ctx.append(' AND ');
253
- }
254
- this.compare(ctx, entity, key, val, {
255
- ...opts,
256
- usePrecedence: hasMultipleKeys,
257
- });
258
- appended = true;
259
- });
260
- if (usePrecedence) {
261
- ctx.append(')');
262
- }
263
- }
264
- compare(ctx, entity, key, val, opts = {}) {
265
- const meta = getMeta(entity);
266
- if (val instanceof QueryRaw) {
267
- if (key === '$exists' || key === '$nexists') {
268
- ctx.append(key === '$exists' ? 'EXISTS (' : 'NOT EXISTS (');
269
- const tableName = this.resolveTableName(entity, meta);
270
- this.getRawValue(ctx, {
271
- value: val,
272
- prefix: tableName,
273
- escapedPrefix: this.escapeId(tableName, false, true),
274
- });
275
- ctx.append(')');
276
- return;
277
- }
278
- this.getComparisonKey(ctx, entity, key, opts);
279
- ctx.append(' = ');
280
- this.getRawValue(ctx, { value: val });
281
- return;
282
- }
283
- if (key === '$text') {
284
- const search = val;
285
- const searchFields = search.$fields ?? getFieldKeys(meta.fields);
286
- const fields = searchFields.map((fKey) => {
287
- const field = meta.fields[fKey];
288
- const columnName = this.resolveColumnName(fKey, field);
289
- return this.escapeId(columnName);
290
- });
291
- ctx.append(`MATCH(${fields.join(', ')}) AGAINST(`);
292
- ctx.addValue(search.$value);
293
- ctx.append(')');
294
- return;
295
- }
296
- if (key === '$and' || key === '$or' || key === '$not' || key === '$nor') {
297
- this.compareLogicalOperator(ctx, entity, key, val, opts);
298
- return;
299
- }
300
- // Detect JSONB dot-notation: 'column.path' where column is a registered JSON/JSONB field
301
- const jsonDot = this.resolveJsonDotPath(meta, key, opts.prefix);
302
- if (jsonDot) {
303
- this.compareJsonPath(ctx, jsonDot, val);
304
- return;
305
- }
306
- if (key.includes('.')) {
307
- throw new TypeError(`path ${key} does not exist in ${meta.name}`);
308
- }
309
- // Detect relation filtering
310
- const rel = meta.relations[key];
311
- if (rel) {
312
- // Check if this is a $size query on a relation (count filtering)
313
- const valObj = val;
314
- if (valObj && typeof valObj === 'object' && '$size' in valObj && Object.keys(valObj).length === 1) {
315
- this.compareRelationSize(ctx, entity, key, valObj['$size'], rel, opts);
316
- return;
317
- }
318
- this.compareRelation(ctx, entity, key, val, rel, opts);
319
- return;
320
- }
321
- const value = this.normalizeWhereValue(val);
322
- const operators = getKeys(value);
323
- if (operators.length > 1) {
324
- ctx.append('(');
325
- }
326
- operators.forEach((op, index) => {
327
- if (index > 0) {
328
- ctx.append(' AND ');
329
- }
330
- this.compareFieldOperator(ctx, entity, key, op, value[op], opts);
331
- });
332
- if (operators.length > 1) {
333
- ctx.append(')');
334
- }
335
- }
336
- compareLogicalOperator(ctx, entity, key, val, opts) {
337
- const op = AbstractSqlDialect.NEGATE_OP_MAP[key] ?? key;
338
- const negate = key in AbstractSqlDialect.NEGATE_OP_MAP ? 'NOT' : '';
339
- const valArr = val ?? [];
340
- const hasManyItems = valArr.length > 1;
341
- if ((opts.usePrecedence || negate) && hasManyItems) {
342
- ctx.append((negate ? negate + ' ' : '') + '(');
343
- }
344
- else if (negate) {
345
- ctx.append(negate + ' ');
346
- }
347
- valArr.forEach((whereEntry, index) => {
348
- if (index > 0) {
349
- ctx.append(op === '$or' ? ' OR ' : ' AND ');
350
- }
351
- if (whereEntry instanceof QueryRaw) {
352
- this.getRawValue(ctx, {
353
- value: whereEntry,
354
- });
355
- }
356
- else if (whereEntry) {
357
- this.where(ctx, entity, whereEntry, {
358
- prefix: opts.prefix,
359
- usePrecedence: hasManyItems && !Array.isArray(whereEntry) && Object.keys(whereEntry).length > 1,
360
- clause: false,
361
- });
362
- }
363
- });
364
- if ((opts.usePrecedence || negate) && hasManyItems) {
365
- ctx.append(')');
366
- }
367
- }
368
- /** Simple comparison operators: `getComparisonKey → op → addValue`. */
369
- static NEGATE_OP_MAP = { $not: '$and', $nor: '$or' };
370
- static COMPARE_OP_MAP = {
371
- $gt: ' > ',
372
- $gte: ' >= ',
373
- $lt: ' < ',
374
- $lte: ' <= ',
375
- };
376
- static LIKE_OP_MAP = {
377
- $startsWith: (v) => `${v}%`,
378
- $istartsWith: (v) => `${v.toLowerCase()}%`,
379
- $endsWith: (v) => `%${v}`,
380
- $iendsWith: (v) => `%${v.toLowerCase()}`,
381
- $includes: (v) => `%${v}%`,
382
- $iincludes: (v) => `%${v.toLowerCase()}%`,
383
- $like: (v) => v,
384
- $ilike: (v) => v.toLowerCase(),
385
- };
386
- // biome-ignore lint/suspicious/noExplicitAny: method works with any entity type
387
- resolveColumnWithPrefix(entity, key, { prefix } = {}) {
388
- const meta = getMeta(entity);
389
- const field = meta.fields[key];
390
- const columnName = this.resolveColumnName(key, field);
391
- const escapedPrefix = this.escapeId(prefix, true, true);
392
- return escapedPrefix + this.escapeId(columnName);
393
- }
394
- /**
395
- * Resolves the SQL operand for a field comparison.
396
- * For QueryRaw virtuals, appends the raw expression to ctx and returns undefined.
397
- */
398
- resolveOperandField(ctx,
399
- // biome-ignore lint/suspicious/noExplicitAny: method works with any entity type
400
- entity, key, opts) {
401
- const col = getMeta(entity).fields[key];
402
- if (col?.virtual) {
403
- if (col.virtual instanceof QueryRaw) {
404
- // biome-ignore lint/suspicious/noExplicitAny: field key type erased at runtime
405
- this.getComparisonKey(ctx, entity, key, opts);
406
- return undefined;
407
- }
408
- return `(${col.virtual})`;
409
- }
410
- return this.resolveColumnWithPrefix(entity, key, opts);
411
- }
412
- appendFieldSql(ctx, field, sql) {
413
- ctx.append(field ? `${field}${sql}` : sql);
414
- }
415
- compareFieldOperator(ctx, entity, key, op, val, opts = {}) {
416
- const field = this.resolveOperandField(ctx, entity, key, opts);
417
- const simpleOp = AbstractSqlDialect.COMPARE_OP_MAP[op];
418
- if (simpleOp) {
419
- this.appendFieldSql(ctx, field, `${simpleOp}${this.addValue(ctx.values, val)}`);
420
- return;
421
- }
422
- const likeWrap = AbstractSqlDialect.LIKE_OP_MAP[op];
423
- if (likeWrap) {
424
- this.appendLikeOp(ctx, field, op, likeWrap(val));
425
- return;
426
- }
427
- switch (op) {
428
- case '$eq':
429
- case '$ne':
430
- this.appendEqNe(ctx, field, op, val);
431
- break;
432
- case '$regex':
433
- this.appendFieldSql(ctx, field, ` ${this.regexpOp} ${this.addValue(ctx.values, val)}`);
434
- break;
435
- case '$not':
436
- ctx.append('NOT (');
437
- this.compare(ctx, entity, key, val, opts);
438
- ctx.append(')');
439
- break;
440
- case '$in':
441
- case '$nin':
442
- this.appendInNin(ctx, field, op, val);
443
- break;
444
- case '$between': {
445
- const col = this.resolveColumnWithPrefix(entity, key, opts);
446
- const [min, max] = val;
447
- ctx.append(`${col} BETWEEN ${this.addValue(ctx.values, min)} AND ${this.addValue(ctx.values, max)}`);
448
- break;
449
- }
450
- case '$isNull':
451
- this.appendFieldSql(ctx, field, val ? ' IS NULL' : ' IS NOT NULL');
452
- break;
453
- case '$isNotNull':
454
- this.appendFieldSql(ctx, field, val ? ' IS NOT NULL' : ' IS NULL');
455
- break;
456
- case '$all':
457
- ctx.append(this.jsonAll(ctx, field ?? '', val));
458
- break;
459
- case '$size':
460
- ctx.append(this.jsonSize(ctx, field ?? '', val));
461
- break;
462
- case '$elemMatch':
463
- ctx.append(this.jsonElemMatch(ctx, field ?? '', val));
464
- break;
465
- default:
466
- throw TypeError(`unknown operator: ${op}`);
467
- }
468
- }
469
- appendLikeOp(ctx, field, op, wrappedVal) {
470
- const isIlike = op.startsWith('$i') || op === '$ilike';
471
- const ph = this.addValue(ctx.values, wrappedVal);
472
- if (isIlike && field) {
473
- ctx.append(this.ilikeExpr(field, ph));
474
- }
475
- else {
476
- this.appendFieldSql(ctx, field, ` ${this.likeFn} ${ph}`);
477
- }
478
- }
479
- appendEqNe(ctx, field, op, val) {
480
- if (val === null) {
481
- this.appendFieldSql(ctx, field, op === '$eq' ? ' IS NULL' : ' IS NOT NULL');
482
- return;
483
- }
484
- const ph = this.addValue(ctx.values, val);
485
- if (op === '$eq') {
486
- this.appendFieldSql(ctx, field, ` = ${ph}`);
487
- return;
488
- }
489
- if (field) {
490
- ctx.append(this.neExpr(field, ph));
491
- }
492
- else {
493
- this.appendFieldSql(ctx, field, ` ${this.neOp} ${ph}`);
494
- }
495
- }
496
- appendInNin(ctx, field, op, val) {
497
- this.appendFieldSql(ctx, field, this.formatIn(ctx, Array.isArray(val) ? val : [], op === '$nin'));
498
- }
499
- addValues(ctx, vals) {
500
- vals.forEach((val, index) => {
501
- if (index > 0) {
502
- ctx.append(', ');
503
- }
504
- ctx.addValue(val);
505
- });
506
- }
507
- /**
508
- * Build a comparison condition for a JSON field.
509
- * Used by both `$elemMatch` and dot-notation paths.
510
- * All dialect-specific behavior comes from overridable methods on `this`.
511
- */
512
- buildJsonFieldCondition(ctx, fieldAccessor, jsonPath, op, value) {
513
- const jsonField = fieldAccessor(jsonPath);
514
- switch (op) {
515
- case '$eq':
516
- return value === null ? `${jsonField} IS NULL` : `${jsonField} = ${this.addValue(ctx.values, value)}`;
517
- case '$ne':
518
- if (value === null)
519
- return `${jsonField} IS NOT NULL`;
520
- return this.neExpr(jsonField, this.addValue(ctx.values, value));
521
- case '$gt':
522
- return `${this.numericCast(jsonField)} > ${this.addValue(ctx.values, value)}`;
523
- case '$gte':
524
- return `${this.numericCast(jsonField)} >= ${this.addValue(ctx.values, value)}`;
525
- case '$lt':
526
- return `${this.numericCast(jsonField)} < ${this.addValue(ctx.values, value)}`;
527
- case '$lte':
528
- return `${this.numericCast(jsonField)} <= ${this.addValue(ctx.values, value)}`;
529
- case '$like':
530
- return `${jsonField} ${this.likeFn} ${this.addValue(ctx.values, value)}`;
531
- case '$ilike':
532
- return this.ilikeExpr(jsonField, this.addValue(ctx.values, value.toLowerCase()));
533
- case '$startsWith':
534
- return `${jsonField} ${this.likeFn} ${this.addValue(ctx.values, `${value}%`)}`;
535
- case '$istartsWith':
536
- return this.ilikeExpr(jsonField, this.addValue(ctx.values, `${value.toLowerCase()}%`));
537
- case '$endsWith':
538
- return `${jsonField} ${this.likeFn} ${this.addValue(ctx.values, `%${value}`)}`;
539
- case '$iendsWith':
540
- return this.ilikeExpr(jsonField, this.addValue(ctx.values, `%${value.toLowerCase()}`));
541
- case '$includes':
542
- return `${jsonField} ${this.likeFn} ${this.addValue(ctx.values, `%${value}%`)}`;
543
- case '$iincludes':
544
- return this.ilikeExpr(jsonField, this.addValue(ctx.values, `%${value.toLowerCase()}%`));
545
- case '$regex':
546
- return `${jsonField} ${this.regexpOp} ${this.addValue(ctx.values, value)}`;
547
- case '$in':
548
- case '$nin':
549
- return this.jsonInNin(ctx, jsonField, op, value);
550
- case '$all':
551
- return this.jsonAll(ctx, jsonField, value);
552
- case '$size':
553
- return this.jsonSize(ctx, jsonField, value);
554
- case '$elemMatch':
555
- return this.jsonElemMatch(ctx, jsonField, value);
556
- default:
557
- throw TypeError(`unknown operator: ${op}`);
558
- }
559
- }
560
- jsonInNin(ctx, jsonField, op, value) {
561
- return `${jsonField}${this.formatIn(ctx, Array.isArray(value) ? value : [], op === '$nin')}`;
562
- }
563
- jsonAll(ctx, jsonField, value) {
564
- throw TypeError(`$all is not supported in the base SQL dialect - override in dialect subclass`);
565
- }
566
- jsonSize(ctx, jsonField, value) {
567
- throw TypeError(`$size is not supported in the base SQL dialect - override in dialect subclass`);
568
- }
569
- jsonElemMatch(ctx, jsonField, value) {
570
- throw TypeError(`$elemMatch is not supported in the base SQL dialect - override in dialect subclass`);
571
- }
572
- isJsonbOp(op) {
573
- return op === '$all' || op === '$size' || op === '$elemMatch';
574
- }
575
- getComparisonKey(ctx, entity, key, { prefix } = {}) {
576
- const meta = getMeta(entity);
577
- const escapedPrefix = this.escapeId(prefix, true, true);
578
- const field = meta.fields[key];
579
- if (field?.virtual) {
580
- this.getRawValue(ctx, {
581
- value: field.virtual,
582
- prefix,
583
- escapedPrefix,
584
- });
585
- return;
586
- }
587
- const columnName = this.resolveColumnName(key, field);
588
- ctx.append(escapedPrefix + this.escapeId(columnName));
589
- }
590
- sort(ctx, entity, sort, { prefix }) {
591
- const sortMap = buildSortMap(sort);
592
- if (!hasKeys(sortMap)) {
593
- return;
594
- }
595
- const meta = getMeta(entity);
596
- // Separate vector search entries from direction entries before flattening,
597
- // because flatObject recursively destructures objects — it would break QueryVectorSearch.
598
- const vectorEntries = [];
599
- const directionEntries = {};
600
- for (const [key, val] of Object.entries(sortMap)) {
601
- if (isVectorSearch(val)) {
602
- vectorEntries.push([key, val]);
603
- }
604
- else {
605
- directionEntries[key] = val;
606
- }
607
- }
608
- const flattenedSort = flatObject(directionEntries, prefix);
609
- // Merge: vector entries first (primary ordering), then flattened direction entries.
610
- const allEntries = [...vectorEntries, ...Object.entries(flattenedSort)];
611
- if (!allEntries.length)
612
- return;
613
- ctx.append(' ORDER BY ');
614
- allEntries.forEach(([key, sort], index) => {
615
- if (index > 0) {
616
- ctx.append(', ');
617
- }
618
- if (isVectorSearch(sort)) {
619
- if (sort.$project) {
620
- // Distance already projected in SELECT — reference the alias to avoid recomputation
621
- ctx.append(this.escapeId(sort.$project));
622
- }
623
- else {
624
- this.appendVectorSort(ctx, meta, key, sort);
625
- }
626
- return;
627
- }
628
- const direction = AbstractSqlDialect.SORT_DIRECTION_MAP[sort];
629
- // Detect JSONB dot-notation: 'column.path'
630
- const jsonDot = this.resolveJsonDotPath(meta, key);
631
- if (jsonDot) {
632
- ctx.append(jsonDot.accessor() + direction);
633
- return;
634
- }
635
- const field = meta.fields[key];
636
- const name = this.resolveColumnName(key, field);
637
- ctx.append(this.escapeId(name) + direction);
638
- });
639
- }
640
- /**
641
- * Resolve common parameters for a vector similarity ORDER BY expression.
642
- * Shared by all dialect overrides of `appendVectorSort`.
643
- */
644
- resolveVectorSortParams(meta, key, search) {
645
- const field = meta.fields[key];
646
- const colName = this.resolveColumnName(key, field);
647
- const distance = search.$distance ?? field?.distance ?? 'cosine';
648
- const vectorCast = resolveVectorCast(field);
649
- return { colName, distance, field, vectorCast };
650
- }
651
- /**
652
- * Mapping of UQL vector distance metrics to native SQL functions.
653
- * Override in dialects that use function-call syntax (e.g. SQLite, MariaDB).
654
- * Dialects with operator-based syntax (e.g. Postgres) leave this empty and override `appendVectorSort` directly.
655
- */
656
- vectorDistanceFns = {};
657
- /**
658
- * Append a vector similarity function call: `fn(col, ?)`.
659
- * Used by dialects that express vector distance via SQL functions (SQLite, MariaDB).
660
- */
661
- appendFunctionVectorSort(ctx, meta, key, search, dialectName) {
662
- const { colName, distance, vectorCast } = this.resolveVectorSortParams(meta, key, search);
663
- const fn = this.vectorDistanceFns[distance];
664
- if (!fn) {
665
- throw Error(`${dialectName} does not support vector distance metric: ${distance}`);
666
- }
667
- ctx.append(`${fn}(${this.escapeId(colName)}, `);
668
- ctx.addValue(`[${search.$vector.join(',')}]`);
669
- if (vectorCast && dialectName === 'PostgreSQL') {
670
- ctx.append(`::${vectorCast}`);
671
- }
672
- ctx.append(')');
673
- }
674
- /**
675
- * Append a vector distance projection.
676
- */
677
- appendVectorProjection(ctx, meta, key, search) {
678
- this.appendVectorSort(ctx, meta, key, search);
679
- ctx.append(` AS ${this.escapeId(search.$project)}`);
680
- }
681
- /**
682
- * Append a vector similarity ORDER BY expression.
683
- * Default: auto-delegates to `appendFunctionVectorSort` when `vectorDistanceFns` has entries.
684
- * Override for operator-based syntax (e.g. PostgreSQL `<=>`, `<->` operators).
685
- */
686
- appendVectorSort(ctx, meta, key, search) {
687
- if (hasKeys(this.vectorDistanceFns)) {
688
- this.appendFunctionVectorSort(ctx, meta, key, search, this.dialectName);
689
- return;
690
- }
691
- throw new TypeError('Vector similarity sort is not supported by this dialect. Use raw() for vector queries.');
692
- }
693
- pager(ctx, opts) {
694
- if (opts.$limit) {
695
- ctx.append(` LIMIT ${Number(opts.$limit)}`);
696
- }
697
- if (opts.$skip !== undefined) {
698
- ctx.append(` OFFSET ${Number(opts.$skip)}`);
699
- }
700
- }
701
- count(ctx, entity, q, opts) {
702
- const search = { ...q };
703
- delete search.$sort;
704
- this.select(ctx, entity, [raw('COUNT(*)', 'count')]);
705
- this.search(ctx, entity, search, opts);
706
- }
707
- aggregate(ctx, entity, q, opts = {}) {
708
- const meta = getMeta(entity);
709
- const tableName = this.resolveTableName(entity, meta);
710
- const groupKeys = [];
711
- const selectParts = [];
712
- const aggregateExpressions = {};
713
- for (const entry of parseGroupMap(q.$group)) {
714
- if (entry.kind === 'key') {
715
- const field = meta.fields[entry.alias];
716
- const columnName = this.resolveColumnName(entry.alias, field);
717
- const escaped = this.escapeId(columnName);
718
- groupKeys.push(escaped);
719
- selectParts.push(columnName !== entry.alias ? `${escaped} ${this.escapeId(entry.alias)}` : escaped);
720
- }
721
- else {
722
- const sqlFn = entry.op.slice(1).toUpperCase();
723
- const sqlArg = entry.fieldRef === '*'
724
- ? '*'
725
- : this.escapeId(this.resolveColumnName(entry.fieldRef, meta.fields[entry.fieldRef]));
726
- const expr = `${sqlFn}(${sqlArg})`;
727
- aggregateExpressions[entry.alias] = expr;
728
- selectParts.push(`${expr} ${this.escapeId(entry.alias)}`);
729
- }
730
- }
731
- ctx.append(`SELECT ${selectParts.join(', ')} FROM ${this.escapeId(tableName)}`);
732
- this.where(ctx, entity, q.$where, opts);
733
- if (groupKeys.length) {
734
- ctx.append(` GROUP BY ${groupKeys.join(', ')}`);
735
- }
736
- if (q.$having) {
737
- this.having(ctx, q.$having, aggregateExpressions);
738
- }
739
- this.aggregateSort(ctx, q.$sort, aggregateExpressions);
740
- this.pager(ctx, q);
741
- }
742
- /**
743
- * ORDER BY for aggregate queries — handles both entity-field and alias references.
744
- */
745
- aggregateSort(ctx, sort, aggregateExpressions) {
746
- const sortMap = buildSortMap(sort);
747
- if (!hasKeys(sortMap))
748
- return;
749
- ctx.append(' ORDER BY ');
750
- Object.entries(sortMap).forEach(([key, dir], index) => {
751
- if (index > 0)
752
- ctx.append(', ');
753
- const direction = AbstractSqlDialect.SORT_DIRECTION_MAP[dir];
754
- const ref = aggregateExpressions[key] ?? this.escapeId(key);
755
- ctx.append(ref + direction);
756
- });
757
- }
758
- having(ctx, having, aggregateExpressions) {
759
- const entries = Object.entries(having).filter(([, v]) => v !== undefined);
760
- if (!entries.length)
761
- return;
762
- ctx.append(' HAVING ');
763
- entries.forEach(([alias, condition], index) => {
764
- if (index > 0)
765
- ctx.append(' AND ');
766
- const expr = aggregateExpressions[alias] ?? this.escapeId(alias);
767
- this.havingCondition(ctx, expr, condition);
768
- });
769
- }
770
- static SORT_DIRECTION_MAP = Object.assign({ 1: '', asc: '', desc: ' DESC', '-1': ' DESC' }, { [-1]: ' DESC' });
771
- static havingOpMap = {
772
- $eq: '=',
773
- $ne: '<>',
774
- $gt: '>',
775
- $gte: '>=',
776
- $lt: '<',
777
- $lte: '<=',
778
- };
779
- havingCondition(ctx, expr, condition) {
780
- if (typeof condition !== 'object' || condition === null) {
781
- ctx.append(`${expr} = `);
782
- ctx.addValue(condition);
783
- return;
784
- }
785
- const ops = condition;
786
- const keys = getKeys(ops);
787
- keys.forEach((op, i) => {
788
- if (i > 0)
789
- ctx.append(' AND ');
790
- const val = ops[op];
791
- if (op === '$between') {
792
- const [min, max] = val;
793
- ctx.append(`${expr} BETWEEN `);
794
- ctx.addValue(min);
795
- ctx.append(' AND ');
796
- ctx.addValue(max);
797
- }
798
- else if (op === '$in' || op === '$nin') {
799
- ctx.append(`${expr}${this.formatIn(ctx, Array.isArray(val) ? val : [], op === '$nin')}`);
800
- }
801
- else if (op === '$isNull') {
802
- ctx.append(`${expr}${val ? ' IS NULL' : ' IS NOT NULL'}`);
803
- }
804
- else if (op === '$isNotNull') {
805
- ctx.append(`${expr}${val ? ' IS NOT NULL' : ' IS NULL'}`);
806
- }
807
- else if (op === '$ne') {
808
- ctx.append(this.neExpr(expr, this.addValue(ctx.values, val)));
809
- }
810
- else {
811
- const sqlOp = AbstractSqlDialect.havingOpMap[op];
812
- if (!sqlOp)
813
- throw TypeError(`unsupported HAVING operator: ${op}`);
814
- ctx.append(`${expr} ${sqlOp} `);
815
- ctx.addValue(val);
816
- }
817
- });
818
- }
819
- find(ctx, entity, q = {}, opts) {
820
- this.select(ctx, entity, q.$select, q.$exclude, q.$populate, opts, q.$distinct, q.$sort);
821
- this.search(ctx, entity, q, opts);
822
- }
823
- insert(ctx, entity, payload, opts) {
824
- const meta = getMeta(entity);
825
- const payloads = fillOnFields(meta, payload, 'onInsert');
826
- const keys = filterFieldKeys(meta, payloads[0], 'onInsert');
827
- const columns = keys.map((key) => {
828
- const field = meta.fields[key];
829
- return this.escapeId(this.resolveColumnName(key, field));
830
- });
831
- const tableName = this.resolveTableName(entity, meta);
832
- ctx.append(`INSERT INTO ${this.escapeId(tableName)} (${columns.join(', ')}) VALUES (`);
833
- payloads.forEach((it, recordIndex) => {
834
- if (recordIndex > 0) {
835
- ctx.append('), (');
836
- }
837
- keys.forEach((key, keyIndex) => {
838
- if (keyIndex > 0) {
839
- ctx.append(', ');
840
- }
841
- const field = meta.fields[key];
842
- this.formatPersistableValue(ctx, field, it[key]);
843
- });
844
- });
845
- ctx.append(')');
846
- }
847
- update(ctx, entity, q, payload, opts) {
848
- const meta = getMeta(entity);
849
- const [filledPayload] = fillOnFields(meta, payload, 'onUpdate');
850
- const keys = filterFieldKeys(meta, filledPayload, 'onUpdate');
851
- const tableName = this.resolveTableName(entity, meta);
852
- ctx.append(`UPDATE ${this.escapeId(tableName)} SET `);
853
- keys.forEach((key, index) => {
854
- if (index > 0) {
855
- ctx.append(', ');
856
- }
857
- const field = meta.fields[key];
858
- const columnName = this.resolveColumnName(key, field);
859
- const escapedCol = this.escapeId(columnName);
860
- const value = filledPayload[key];
861
- if (this.isJsonUpdateOp(value)) {
862
- this.formatJsonUpdate(ctx, escapedCol, value);
863
- }
864
- else {
865
- ctx.append(`${escapedCol} = `);
866
- this.formatPersistableValue(ctx, field, value);
867
- }
868
- });
869
- this.search(ctx, entity, q, opts);
870
- }
871
- upsert(ctx, entity, conflictPaths, payload) {
872
- const meta = getMeta(entity);
873
- const updateCtx = this.createContext();
874
- const update = this.getUpsertUpdateAssignments(updateCtx, meta, conflictPaths, payload, (name) => `VALUES(${name})`);
875
- if (update) {
876
- this.insert(ctx, entity, payload);
877
- ctx.append(` ON DUPLICATE KEY UPDATE ${update}`);
878
- ctx.pushValue(...updateCtx.values);
879
- }
880
- else {
881
- const insertCtx = this.createContext();
882
- this.insert(insertCtx, entity, payload);
883
- ctx.append(insertCtx.sql.replace(/^INSERT/, 'INSERT IGNORE'));
884
- ctx.pushValue(...insertCtx.values);
885
- }
886
- }
887
- getUpsertUpdateAssignments(ctx, meta, conflictPaths, payload, callback) {
888
- const sample = Array.isArray(payload) ? payload[0] : payload;
889
- const cloned = { ...sample };
890
- const [filledPayload] = fillOnFields(meta, cloned, 'onUpdate');
891
- const fields = filterFieldKeys(meta, filledPayload, 'onUpdate');
892
- return fields
893
- .filter((col) => !conflictPaths[col])
894
- .map((col) => {
895
- const field = meta.fields[col];
896
- const columnName = this.resolveColumnName(col, field);
897
- if (callback && Object.hasOwn(sample, col)) {
898
- return `${this.escapeId(columnName)} = ${callback(this.escapeId(columnName))}`;
899
- }
900
- const valCtx = this.createContext();
901
- this.formatPersistableValue(valCtx, field, filledPayload[col]);
902
- ctx.pushValue(...valCtx.values);
903
- return `${this.escapeId(columnName)} = ${valCtx.sql}`;
904
- })
905
- .join(', ');
906
- }
907
- /**
908
- * Shared ON CONFLICT ... DO UPDATE / DO NOTHING logic for positional-placeholder dialects (SQLite).
909
- * Uses a deferred context for update params so they follow INSERT params.
910
- * PG uses its own implementation since `$N` numbered placeholders handle param ordering natively.
911
- */
912
- onConflictUpsert(ctx, entity, conflictPaths, payload, insertFn) {
913
- const meta = getMeta(entity);
914
- const updateCtx = this.createContext();
915
- const update = this.getUpsertUpdateAssignments(updateCtx, meta, conflictPaths, payload, (name) => `EXCLUDED.${name}`);
916
- const keysStr = this.getUpsertConflictPathsStr(meta, conflictPaths);
917
- const onConflict = update ? `DO UPDATE SET ${update}` : 'DO NOTHING';
918
- insertFn(ctx, entity, payload);
919
- ctx.append(` ON CONFLICT (${keysStr}) ${onConflict}`);
920
- ctx.pushValue(...updateCtx.values);
921
- }
922
- getUpsertConflictPathsStr(meta, conflictPaths) {
923
- return getKeys(conflictPaths)
924
- .map((key) => {
925
- const field = meta.fields[key];
926
- const columnName = this.resolveColumnName(key, field);
927
- return this.escapeId(columnName);
928
- })
929
- .join(', ');
930
- }
931
- delete(ctx, entity, q, opts = {}) {
932
- const meta = getMeta(entity);
933
- const tableName = this.resolveTableName(entity, meta);
934
- if (opts.softDelete || opts.softDelete === undefined) {
935
- if (meta.softDelete) {
936
- const field = meta.fields[meta.softDelete];
937
- if (!field?.onDelete)
938
- return;
939
- const value = getFieldCallbackValue(field.onDelete);
940
- const columnName = this.resolveColumnName(meta.softDelete, field);
941
- ctx.append(`UPDATE ${this.escapeId(tableName)} SET ${this.escapeId(columnName)} = `);
942
- ctx.addValue(value);
943
- this.search(ctx, entity, q, opts);
944
- return;
945
- }
946
- if (opts.softDelete) {
947
- throw TypeError(`'${tableName}' has not enabled 'softDelete'`);
948
- }
949
- }
950
- ctx.append(`DELETE FROM ${this.escapeId(tableName)}`);
951
- this.search(ctx, entity, q, opts);
952
- }
953
- escapeId(val, forbidQualified, addDot) {
954
- return escapeSqlId(val, this.escapeIdChar, forbidQualified, addDot);
955
- }
956
- getPersistables(ctx, meta, payload, callbackKey) {
957
- const payloads = fillOnFields(meta, payload, callbackKey);
958
- return payloads.map((it) => this.getPersistable(ctx, meta, it, callbackKey));
959
- }
960
- getPersistable(ctx, meta, payload, callbackKey) {
961
- const filledPayload = fillOnFields(meta, payload, callbackKey)[0];
962
- const keys = filterFieldKeys(meta, filledPayload, callbackKey);
963
- return keys.reduce((acc, key) => {
964
- const field = meta.fields[key];
965
- const valCtx = this.createContext();
966
- this.formatPersistableValue(valCtx, field, filledPayload[key]);
967
- ctx.pushValue(...valCtx.values);
968
- acc[key] = valCtx.sql;
969
- return acc;
970
- }, {});
971
- }
972
- formatPersistableValue(ctx, field, value) {
973
- if (value instanceof QueryRaw) {
974
- this.getRawValue(ctx, { value });
975
- return;
976
- }
977
- if (isJsonType(field?.type)) {
978
- ctx.addValue(value == null ? null : JSON.stringify(value));
979
- return;
980
- }
981
- if (field?.type === 'vector' && Array.isArray(value)) {
982
- ctx.addValue(`[${value.join(',')}]`);
983
- return;
984
- }
985
- ctx.addValue(value);
986
- }
987
- /**
988
- * Generate SQL for a JSONB merge and/or unset operation.
989
- * Called from `update()` when a field value has `$merge`, `$unset`, and/or `$push` operators.
990
- * Generates the full `"col" = <expression>` assignment.
991
- *
992
- * Base implementation uses MySQL-compatible syntax with *shallow* merge semantics
993
- * (RHS top-level keys replace LHS top-level keys, matching PostgreSQL's `jsonb || jsonb`).
994
- * Override in dialect subclasses when a dialect needs different JSON function semantics.
995
- */
996
- getJsonCastExpr() {
997
- return 'CAST(? AS JSON)';
998
- }
999
- formatJsonUpdate(ctx, escapedCol, value) {
1000
- let expr = escapedCol;
1001
- if (hasKeys(value.$merge)) {
1002
- const merge = value.$merge;
1003
- expr = `JSON_SET(COALESCE(${escapedCol}, '{}')`;
1004
- for (const [key, v] of Object.entries(merge)) {
1005
- expr += `, '$.${this.escapeJsonKey(key)}', ${this.getJsonCastExpr()}`;
1006
- ctx.pushValue(JSON.stringify(v));
1007
- }
1008
- expr += ')';
1009
- }
1010
- if (hasKeys(value.$push)) {
1011
- const push = value.$push;
1012
- expr = `JSON_ARRAY_APPEND(${expr}`;
1013
- for (const [key, v] of Object.entries(push)) {
1014
- expr += `, '$.${this.escapeJsonKey(key)}', ${this.getJsonCastExpr()}`;
1015
- ctx.pushValue(JSON.stringify(v));
1016
- }
1017
- expr += ')';
1018
- }
1019
- if (value.$unset?.length) {
1020
- for (const key of value.$unset) {
1021
- expr = `JSON_REMOVE(${expr}, '$.${this.escapeJsonKey(key)}')`;
1022
- }
1023
- }
1024
- ctx.append(`${escapedCol} = ${expr}`);
1025
- }
1026
- isJsonUpdateOp(value) {
1027
- return typeof value === 'object' && value !== null && ('$merge' in value || '$unset' in value || '$push' in value);
1028
- }
1029
- /** Escapes a JSON key for safe interpolation into SQL string literals. */
1030
- escapeJsonKey(key) {
1031
- return key.replace(/'/g, "''");
1032
- }
1033
- getRawValue(ctx, opts) {
1034
- const { value, prefix = '', escapedPrefix, autoPrefixAlias } = opts;
1035
- const rawValue = value[RAW_VALUE];
1036
- if (typeof rawValue === 'function') {
1037
- const res = rawValue({
1038
- ...opts,
1039
- ctx,
1040
- dialect: this,
1041
- prefix,
1042
- escapedPrefix: escapedPrefix ?? this.escapeId(prefix, true, true),
1043
- });
1044
- if (typeof res === 'string' || (typeof res === 'number' && !Number.isNaN(res))) {
1045
- ctx.append(String(res));
1046
- }
1047
- }
1048
- else {
1049
- ctx.append(prefix + String(rawValue));
1050
- }
1051
- const alias = value[RAW_ALIAS];
1052
- if (alias) {
1053
- const fullAlias = autoPrefixAlias && prefix ? `${prefix}.${alias}` : alias;
1054
- ctx.append(' ' + this.escapeId(fullAlias, true));
1055
- }
1056
- }
1057
- /**
1058
- * Resolves a dot-notation key to its JSON field metadata.
1059
- * Shared by `where()` and `sort()` to detect 'column.path' keys where 'column' is a JSON/JSONB field.
1060
- *
1061
- * @returns resolved metadata or `undefined` if the key is not a JSON dot-notation path
1062
- */
1063
- resolveJsonDotPath(meta, key, prefix) {
1064
- const dotIndex = key.indexOf('.');
1065
- if (dotIndex <= 0) {
1066
- return undefined;
1067
- }
1068
- const root = key.slice(0, dotIndex);
1069
- const field = meta.fields[root];
1070
- if (!field || !isJsonType(field.type)) {
1071
- return undefined;
1072
- }
1073
- const jsonPath = key.slice(dotIndex + 1);
1074
- const colName = this.resolveColumnName(root, field);
1075
- const escapedCol = (prefix ? this.escapeId(prefix, true, true) : '') + this.escapeId(colName);
1076
- return {
1077
- root,
1078
- jsonPath,
1079
- accessor: (asJsonb) => asJsonb ? this.getJsonPathJsonbExpr(escapedCol, jsonPath) : this.getJsonPathScalarExpr(escapedCol, jsonPath),
1080
- };
1081
- }
1082
- /**
1083
- * Compare a JSONB dot-notation path, e.g. `'settings.isArchived': { $ne: true }`.
1084
- * Receives a pre-resolved `resolveJsonDotPath` result to avoid redundant computation.
1085
- */
1086
- compareJsonPath(ctx, resolved, val) {
1087
- const { jsonPath, accessor } = resolved;
1088
- const value = this.normalizeWhereValue(val);
1089
- const operators = getKeys(value);
1090
- if (operators.length > 1) {
1091
- ctx.append('(');
1092
- }
1093
- operators.forEach((op, index) => {
1094
- if (index > 0)
1095
- ctx.append(' AND ');
1096
- const sql = this.buildJsonFieldCondition(ctx, (f) => accessor(this.isJsonbOp(op)), jsonPath, op, value[op]);
1097
- if (sql) {
1098
- ctx.append(sql);
1099
- }
1100
- });
1101
- if (operators.length > 1) {
1102
- ctx.append(')');
1103
- }
1104
- }
1105
- /**
1106
- * Returns SQL that extracts a scalar value from a JSON path.
1107
- * Dialects can override this to customize path access syntax while preserving
1108
- * the shared comparison/operator pipeline.
1109
- */
1110
- getJsonPathScalarExpr(escapedColumn, jsonPath) {
1111
- const segments = jsonPath.split('.');
1112
- let expr = escapedColumn;
1113
- for (let i = 0; i < segments.length; i++) {
1114
- const op = i === segments.length - 1 ? '->>' : '->';
1115
- expr = `(${expr}${op}'${this.escapeJsonKey(segments[i])}')`;
1116
- }
1117
- return expr;
1118
- }
1119
- getJsonPathJsonbExpr(escapedColumn, jsonPath) {
1120
- const segments = jsonPath.split('.');
1121
- let expr = escapedColumn;
1122
- for (const segment of segments) {
1123
- expr = `(${expr}->'${this.escapeJsonKey(segment)}')`;
1124
- }
1125
- return expr;
1126
- }
1127
- /**
1128
- * Normalizes a raw WHERE value into an operator map.
1129
- * Arrays become `$in`, scalars/null become `$eq`, objects pass through.
1130
- */
1131
- normalizeWhereValue(val) {
1132
- if (Array.isArray(val))
1133
- return { $in: val };
1134
- if (typeof val === 'object' && val !== null)
1135
- return val;
1136
- return { $eq: val };
1137
- }
1138
- /**
1139
- * Filter by relation using an EXISTS subquery.
1140
- * Supports all cardinalities: mm (via junction), 1m, m1, and 11.
1141
- */
1142
- compareRelation(ctx, entity, key, val, rel, opts) {
1143
- const meta = getMeta(entity);
1144
- const parentTable = this.resolveTableName(entity, meta);
1145
- const parentId = meta.id;
1146
- const escapedParentId = (opts.prefix ? this.escapeId(opts.prefix, true, true) : this.escapeId(parentTable, false, true)) +
1147
- this.escapeId(parentId);
1148
- if (!rel.references?.length) {
1149
- throw new TypeError(`Relation '${key}' on '${parentTable}' has no references defined`);
1150
- }
1151
- const relatedEntity = rel.entity();
1152
- const relatedMeta = getMeta(relatedEntity);
1153
- const relatedTable = this.resolveTableName(relatedEntity, relatedMeta);
1154
- ctx.append('EXISTS (SELECT 1 FROM ');
1155
- if (rel.cardinality === 'mm' && rel.through) {
1156
- // ManyToMany: EXISTS (SELECT 1 FROM JunctionTable WHERE junction.localFk = parent.id AND junction.foreignFk IN (SELECT related.id FROM Related WHERE ...))
1157
- const throughEntity = rel.through();
1158
- const throughMeta = getMeta(throughEntity);
1159
- const throughTable = this.resolveTableName(throughEntity, throughMeta);
1160
- const localFk = rel.references[0].local;
1161
- const foreignFk = rel.references[1].local;
1162
- const relatedId = relatedMeta.id;
1163
- ctx.append(this.escapeId(throughTable));
1164
- ctx.append(` WHERE ${this.escapeId(throughTable, false, true)}${this.escapeId(localFk)} = ${escapedParentId}`);
1165
- ctx.append(` AND ${this.escapeId(throughTable, false, true)}${this.escapeId(foreignFk)} IN (`);
1166
- ctx.append(`SELECT ${this.escapeId(relatedTable, false, true)}${this.escapeId(relatedId)} FROM ${this.escapeId(relatedTable)}`);
1167
- this.where(ctx, relatedEntity, val, {
1168
- prefix: relatedTable,
1169
- clause: 'WHERE',
1170
- softDelete: false,
1171
- });
1172
- ctx.append(')');
1173
- }
1174
- else {
1175
- // 1m / m1 / 11: EXISTS (SELECT 1 FROM Related WHERE related.fk_or_pk = parent.pk_or_fk AND ...)
1176
- // Left side is always relatedTable.references[0].foreign
1177
- // Right side is the parent's PK (1m) or the parent's FK (m1/11)
1178
- const joinLeft = `${this.escapeId(relatedTable, false, true)}${this.escapeId(rel.references[0].foreign)}`;
1179
- const joinRight = rel.cardinality === '1m'
1180
- ? escapedParentId
1181
- : (opts.prefix ? this.escapeId(opts.prefix, true, true) : this.escapeId(parentTable, false, true)) +
1182
- this.escapeId(rel.references[0].local);
1183
- ctx.append(this.escapeId(relatedTable));
1184
- ctx.append(` WHERE ${joinLeft} = ${joinRight}`);
1185
- this.where(ctx, relatedEntity, val, {
1186
- prefix: relatedTable,
1187
- clause: 'AND',
1188
- softDelete: false,
1189
- });
1190
- }
1191
- ctx.append(')');
1192
- }
1193
- /**
1194
- * Filter by relation size using a `COUNT(*)` subquery.
1195
- * Supports all cardinalities: mm (via junction), 1m.
1196
- */
1197
- compareRelationSize(ctx, entity, key, sizeVal, rel, opts) {
1198
- const meta = getMeta(entity);
1199
- const parentTable = this.resolveTableName(entity, meta);
1200
- const parentId = meta.id;
1201
- const escapedParentId = (opts.prefix ? this.escapeId(opts.prefix, true, true) : this.escapeId(parentTable, false, true)) +
1202
- this.escapeId(parentId);
1203
- if (!rel.references?.length) {
1204
- throw new TypeError(`Relation '${key}' on '${parentTable}' has no references defined`);
1205
- }
1206
- const appendSubquery = () => {
1207
- ctx.append('(SELECT COUNT(*) FROM ');
1208
- if (rel.cardinality === 'mm' && rel.through) {
1209
- const throughEntity = rel.through();
1210
- const throughMeta = getMeta(throughEntity);
1211
- const throughTable = this.resolveTableName(throughEntity, throughMeta);
1212
- const localFk = rel.references[0].local;
1213
- ctx.append(this.escapeId(throughTable));
1214
- ctx.append(` WHERE ${this.escapeId(throughTable, false, true)}${this.escapeId(localFk)} = ${escapedParentId}`);
1215
- }
1216
- else {
1217
- const relatedEntity = rel.entity();
1218
- const relatedMeta = getMeta(relatedEntity);
1219
- const relatedTable = this.resolveTableName(relatedEntity, relatedMeta);
1220
- const joinLeft = `${this.escapeId(relatedTable, false, true)}${this.escapeId(rel.references[0].foreign)}`;
1221
- ctx.append(this.escapeId(relatedTable));
1222
- ctx.append(` WHERE ${joinLeft} = ${escapedParentId}`);
1223
- }
1224
- ctx.append(')');
1225
- };
1226
- this.buildSizeComparison(ctx, appendSubquery, sizeVal);
1227
- }
1228
- /**
1229
- * Build a complete `$size` comparison expression.
1230
- * Handles both single and multiple comparison operators by repeating the size expression.
1231
- * @param sizeExprFn - function that appends the size expression to ctx (e.g. `jsonb_array_length("col")`)
1232
- */
1233
- buildSizeComparison(ctx, sizeExprFn, sizeVal) {
1234
- if (typeof sizeVal === 'number') {
1235
- sizeExprFn();
1236
- ctx.append(' = ');
1237
- ctx.addValue(sizeVal);
1238
- return;
1239
- }
1240
- const entries = Object.entries(sizeVal).filter(([, v]) => v !== undefined);
1241
- if (entries.length > 1) {
1242
- ctx.append('(');
1243
- }
1244
- entries.forEach(([op, val], index) => {
1245
- if (index > 0) {
1246
- ctx.append(' AND ');
1247
- }
1248
- sizeExprFn();
1249
- this.appendSizeOp(ctx, op, val);
1250
- });
1251
- if (entries.length > 1) {
1252
- ctx.append(')');
1253
- }
1254
- }
1255
- /**
1256
- * Append a single size comparison operator and value to the context.
1257
- */
1258
- appendSizeOp(ctx, op, val) {
1259
- switch (op) {
1260
- case '$eq':
1261
- ctx.append(' = ');
1262
- ctx.addValue(val);
1263
- break;
1264
- case '$ne':
1265
- ctx.append(' <> ');
1266
- ctx.addValue(val);
1267
- break;
1268
- case '$gt':
1269
- ctx.append(' > ');
1270
- ctx.addValue(val);
1271
- break;
1272
- case '$gte':
1273
- ctx.append(' >= ');
1274
- ctx.addValue(val);
1275
- break;
1276
- case '$lt':
1277
- ctx.append(' < ');
1278
- ctx.addValue(val);
1279
- break;
1280
- case '$lte':
1281
- ctx.append(' <= ');
1282
- ctx.addValue(val);
1283
- break;
1284
- case '$between': {
1285
- const [min, max] = val;
1286
- ctx.append(' BETWEEN ');
1287
- ctx.addValue(min);
1288
- ctx.append(' AND ');
1289
- ctx.addValue(max);
1290
- break;
1291
- }
1292
- default:
1293
- throw TypeError(`unsupported $size comparison operator: ${op}`);
1294
- }
1295
- }
1296
- get regexpOp() {
1297
- return 'REGEXP';
1298
- }
1299
- get likeFn() {
1300
- return 'LIKE';
1301
- }
1302
- /**
1303
- * Not-equal operator token for non-null comparisons.
1304
- * Postgres uses `IS DISTINCT FROM`; MySQL/Maria uses custom `neExpr`.
1305
- */
1306
- get neOp() {
1307
- return '<>';
1308
- }
1309
- neExpr(field, ph) {
1310
- return `${field} ${this.neOp} ${ph}`;
1311
- }
1312
- ilikeExpr(f, ph) {
1313
- return `LOWER(${f}) LIKE ${ph}`;
1314
- }
1315
- /**
1316
- * Formats an IN/NOT IN expression, binding each value individually.
1317
- * Postgres overrides to use `= ANY($1)` / `<> ALL($1)` with a single array parameter.
1318
- */
1319
- formatIn(ctx, values, negate) {
1320
- if (values.length === 0)
1321
- return negate ? ' NOT IN (NULL)' : ' IN (NULL)';
1322
- const phs = values.map((v) => this.addValue(ctx.values, v)).join(', ');
1323
- return ` ${negate ? 'NOT IN' : 'IN'} (${phs})`;
1324
- }
1325
- numericCast(expr) {
1326
- return expr;
1327
- }
1328
- toString() {
1329
- return this.dialectName;
1330
- }
1331
- }
1332
- //# sourceMappingURL=abstractSqlDialect.js.map