@intentius/chant-lexicon-sql 0.0.0-stage → 0.112.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (936) hide show
  1. package/README.md +39 -2
  2. package/dist/clickhouse/apply/apply.d.ts +82 -0
  3. package/dist/clickhouse/apply/apply.d.ts.map +1 -0
  4. package/dist/clickhouse/apply/mutations.d.ts +46 -0
  5. package/dist/clickhouse/apply/mutations.d.ts.map +1 -0
  6. package/dist/clickhouse/apply/statements.d.ts +99 -0
  7. package/dist/clickhouse/apply/statements.d.ts.map +1 -0
  8. package/dist/clickhouse/catalog-types.d.ts +76 -0
  9. package/dist/clickhouse/catalog-types.d.ts.map +1 -0
  10. package/dist/clickhouse/container.d.ts +63 -0
  11. package/dist/clickhouse/container.d.ts.map +1 -0
  12. package/dist/clickhouse/engine-syntax.d.ts +43 -0
  13. package/dist/clickhouse/engine-syntax.d.ts.map +1 -0
  14. package/dist/clickhouse/entities.d.ts +183 -0
  15. package/dist/clickhouse/entities.d.ts.map +1 -0
  16. package/dist/clickhouse/http.d.ts +40 -0
  17. package/dist/clickhouse/http.d.ts.map +1 -0
  18. package/dist/clickhouse/import/generator.d.ts +16 -0
  19. package/dist/clickhouse/import/generator.d.ts.map +1 -0
  20. package/dist/clickhouse/import/ir.d.ts +52 -0
  21. package/dist/clickhouse/import/ir.d.ts.map +1 -0
  22. package/dist/clickhouse/import/live-export.d.ts +28 -0
  23. package/dist/clickhouse/import/live-export.d.ts.map +1 -0
  24. package/dist/clickhouse/import/parser.d.ts +10 -0
  25. package/dist/clickhouse/import/parser.d.ts.map +1 -0
  26. package/dist/clickhouse/live/bind.d.ts +56 -0
  27. package/dist/clickhouse/live/bind.d.ts.map +1 -0
  28. package/dist/clickhouse/live/catalog.d.ts +39 -0
  29. package/dist/clickhouse/live/catalog.d.ts.map +1 -0
  30. package/dist/clickhouse/live/describe-resources.d.ts +34 -0
  31. package/dist/clickhouse/live/describe-resources.d.ts.map +1 -0
  32. package/dist/clickhouse/overlays/codecs.d.ts +28 -0
  33. package/dist/clickhouse/overlays/codecs.d.ts.map +1 -0
  34. package/dist/clickhouse/overlays/engines.d.ts +20 -0
  35. package/dist/clickhouse/overlays/engines.d.ts.map +1 -0
  36. package/dist/clickhouse/overlays/kinds.d.ts +38 -0
  37. package/dist/clickhouse/overlays/kinds.d.ts.map +1 -0
  38. package/dist/clickhouse/overlays/projections.d.ts +27 -0
  39. package/dist/clickhouse/overlays/projections.d.ts.map +1 -0
  40. package/dist/clickhouse/overlays/skip-indexes.d.ts +10 -0
  41. package/dist/clickhouse/overlays/skip-indexes.d.ts.map +1 -0
  42. package/dist/clickhouse/overlays/ttl.d.ts +35 -0
  43. package/dist/clickhouse/overlays/ttl.d.ts.map +1 -0
  44. package/dist/clickhouse/overlays/types.d.ts +21 -0
  45. package/dist/clickhouse/overlays/types.d.ts.map +1 -0
  46. package/dist/clickhouse/ownership.d.ts +71 -0
  47. package/dist/clickhouse/ownership.d.ts.map +1 -0
  48. package/dist/clickhouse/parser.d.ts +130 -0
  49. package/dist/clickhouse/parser.d.ts.map +1 -0
  50. package/dist/clickhouse/plan/commands.d.ts +26 -0
  51. package/dist/clickhouse/plan/commands.d.ts.map +1 -0
  52. package/dist/clickhouse/plan/deep.d.ts +32 -0
  53. package/dist/clickhouse/plan/deep.d.ts.map +1 -0
  54. package/dist/clickhouse/plan/diff.d.ts +37 -0
  55. package/dist/clickhouse/plan/diff.d.ts.map +1 -0
  56. package/dist/clickhouse/plan/disruption.d.ts +17 -0
  57. package/dist/clickhouse/plan/disruption.d.ts.map +1 -0
  58. package/dist/clickhouse/plan/normalize.d.ts +97 -0
  59. package/dist/clickhouse/plan/normalize.d.ts.map +1 -0
  60. package/dist/clickhouse/plan/rebuild-handoff.d.ts +38 -0
  61. package/dist/clickhouse/plan/rebuild-handoff.d.ts.map +1 -0
  62. package/dist/clickhouse/plan/report.d.ts +6 -0
  63. package/dist/clickhouse/plan/report.d.ts.map +1 -0
  64. package/dist/clickhouse/plan/rules.d.ts +60 -0
  65. package/dist/clickhouse/plan/rules.d.ts.map +1 -0
  66. package/dist/clickhouse/plan/schema.d.ts +23 -0
  67. package/dist/clickhouse/plan/schema.d.ts.map +1 -0
  68. package/dist/clickhouse/plan/server-format.d.ts +12 -0
  69. package/dist/clickhouse/plan/server-format.d.ts.map +1 -0
  70. package/dist/clickhouse/rebuild/backfill.d.ts +70 -0
  71. package/dist/clickhouse/rebuild/backfill.d.ts.map +1 -0
  72. package/dist/clickhouse/rebuild/observe.d.ts +157 -0
  73. package/dist/clickhouse/rebuild/observe.d.ts.map +1 -0
  74. package/dist/clickhouse/rebuild/op.d.ts +108 -0
  75. package/dist/clickhouse/rebuild/op.d.ts.map +1 -0
  76. package/dist/clickhouse/rebuild/partitions.d.ts +24 -0
  77. package/dist/clickhouse/rebuild/partitions.d.ts.map +1 -0
  78. package/dist/clickhouse/rebuild/receipts.d.ts +76 -0
  79. package/dist/clickhouse/rebuild/receipts.d.ts.map +1 -0
  80. package/dist/clickhouse/rebuild/replicas.d.ts +78 -0
  81. package/dist/clickhouse/rebuild/replicas.d.ts.map +1 -0
  82. package/dist/clickhouse/rebuild/steps.d.ts +151 -0
  83. package/dist/clickhouse/rebuild/steps.d.ts.map +1 -0
  84. package/dist/clickhouse/rebuild/verify.d.ts +51 -0
  85. package/dist/clickhouse/rebuild/verify.d.ts.map +1 -0
  86. package/dist/clickhouse/testing/fake-server.d.ts +27 -0
  87. package/dist/clickhouse/testing/fake-server.d.ts.map +1 -0
  88. package/dist/clickhouse/testing/roundtrip-schema.d.ts +3 -0
  89. package/dist/clickhouse/testing/roundtrip-schema.d.ts.map +1 -0
  90. package/dist/clickhouse/testing/writable-server.d.ts +35 -0
  91. package/dist/clickhouse/testing/writable-server.d.ts.map +1 -0
  92. package/dist/clickhouse/tokens.d.ts +15 -0
  93. package/dist/clickhouse/tokens.d.ts.map +1 -0
  94. package/dist/clickhouse.d.ts +24 -0
  95. package/dist/clickhouse.d.ts.map +1 -0
  96. package/dist/codegen/classifier-page.d.ts +6 -0
  97. package/dist/codegen/classifier-page.d.ts.map +1 -0
  98. package/dist/codegen/clickhouse-module.d.ts +23 -0
  99. package/dist/codegen/clickhouse-module.d.ts.map +1 -0
  100. package/dist/codegen/docs-cli.d.ts +3 -0
  101. package/dist/codegen/docs-cli.d.ts.map +1 -0
  102. package/dist/codegen/docs.d.ts +8 -0
  103. package/dist/codegen/docs.d.ts.map +1 -0
  104. package/dist/codegen/generate-cli.d.ts +3 -0
  105. package/dist/codegen/generate-cli.d.ts.map +1 -0
  106. package/dist/codegen/generate.d.ts +40 -0
  107. package/dist/codegen/generate.d.ts.map +1 -0
  108. package/dist/codegen/package.d.ts +7 -0
  109. package/dist/codegen/package.d.ts.map +1 -0
  110. package/dist/codegen/postgres-classifier-page.d.ts +7 -0
  111. package/dist/codegen/postgres-classifier-page.d.ts.map +1 -0
  112. package/dist/codegen/postgres-module.d.ts +30 -0
  113. package/dist/codegen/postgres-module.d.ts.map +1 -0
  114. package/dist/codegen/registry.d.ts +12 -0
  115. package/dist/codegen/registry.d.ts.map +1 -0
  116. package/dist/composites/audit-log-table.d.ts +31 -0
  117. package/dist/composites/audit-log-table.d.ts.map +1 -0
  118. package/dist/composites/catalog.d.ts +3 -0
  119. package/dist/composites/catalog.d.ts.map +1 -0
  120. package/dist/composites/cdc-mirror.d.ts +32 -0
  121. package/dist/composites/cdc-mirror.d.ts.map +1 -0
  122. package/dist/composites/clickhouse.d.ts +7 -0
  123. package/dist/composites/clickhouse.d.ts.map +1 -0
  124. package/dist/composites/events-table.d.ts +32 -0
  125. package/dist/composites/events-table.d.ts.map +1 -0
  126. package/dist/composites/index.d.ts +9 -0
  127. package/dist/composites/index.d.ts.map +1 -0
  128. package/dist/composites/join-table.d.ts +41 -0
  129. package/dist/composites/join-table.d.ts.map +1 -0
  130. package/dist/composites/postgres.d.ts +7 -0
  131. package/dist/composites/postgres.d.ts.map +1 -0
  132. package/dist/composites/refreshed-view.d.ts +32 -0
  133. package/dist/composites/refreshed-view.d.ts.map +1 -0
  134. package/dist/composites/replacing-table.d.ts +34 -0
  135. package/dist/composites/replacing-table.d.ts.map +1 -0
  136. package/dist/composites/rollup-view.d.ts +39 -0
  137. package/dist/composites/rollup-view.d.ts.map +1 -0
  138. package/dist/composites/sharded-table.d.ts +35 -0
  139. package/dist/composites/sharded-table.d.ts.map +1 -0
  140. package/dist/composites/soft-delete-table.d.ts +40 -0
  141. package/dist/composites/soft-delete-table.d.ts.map +1 -0
  142. package/dist/composites/tenant-table.d.ts +34 -0
  143. package/dist/composites/tenant-table.d.ts.map +1 -0
  144. package/dist/config.d.ts +213 -0
  145. package/dist/config.d.ts.map +1 -0
  146. package/dist/core/apply.d.ts +89 -0
  147. package/dist/core/apply.d.ts.map +1 -0
  148. package/dist/core/classifier.d.ts +88 -0
  149. package/dist/core/classifier.d.ts.map +1 -0
  150. package/dist/core/container.d.ts +45 -0
  151. package/dist/core/container.d.ts.map +1 -0
  152. package/dist/core/cursor.d.ts +67 -0
  153. package/dist/core/cursor.d.ts.map +1 -0
  154. package/dist/core/diff.d.ts +49 -0
  155. package/dist/core/diff.d.ts.map +1 -0
  156. package/dist/core/entity.d.ts +41 -0
  157. package/dist/core/entity.d.ts.map +1 -0
  158. package/dist/core/find-templates.d.ts +69 -0
  159. package/dist/core/find-templates.d.ts.map +1 -0
  160. package/dist/core/handoff.d.ts +36 -0
  161. package/dist/core/handoff.d.ts.map +1 -0
  162. package/dist/core/index.d.ts +61 -0
  163. package/dist/core/index.d.ts.map +1 -0
  164. package/dist/core/interpolation.d.ts +88 -0
  165. package/dist/core/interpolation.d.ts.map +1 -0
  166. package/dist/core/normalize.d.ts +18 -0
  167. package/dist/core/normalize.d.ts.map +1 -0
  168. package/dist/core/ownership.d.ts +60 -0
  169. package/dist/core/ownership.d.ts.map +1 -0
  170. package/dist/core/receipts.d.ts +28 -0
  171. package/dist/core/receipts.d.ts.map +1 -0
  172. package/dist/core/references.d.ts +37 -0
  173. package/dist/core/references.d.ts.map +1 -0
  174. package/dist/core/template.d.ts +41 -0
  175. package/dist/core/template.d.ts.map +1 -0
  176. package/dist/core/testing/http-stub.d.ts +17 -0
  177. package/dist/core/testing/http-stub.d.ts.map +1 -0
  178. package/dist/core/tokens.d.ts +102 -0
  179. package/dist/core/tokens.d.ts.map +1 -0
  180. package/dist/coverage.d.ts +25 -0
  181. package/dist/coverage.d.ts.map +1 -0
  182. package/dist/detect.d.ts +15 -0
  183. package/dist/detect.d.ts.map +1 -0
  184. package/dist/dialects.d.ts +20 -0
  185. package/dist/dialects.d.ts.map +1 -0
  186. package/dist/generated/clickhouse-types.d.ts +4380 -0
  187. package/dist/generated/clickhouse-types.d.ts.map +1 -0
  188. package/dist/generated/clickhouse.d.ts +11 -0
  189. package/dist/generated/clickhouse.d.ts.map +1 -0
  190. package/dist/generated/postgres-types.d.ts +1579 -0
  191. package/dist/generated/postgres-types.d.ts.map +1 -0
  192. package/dist/generated/postgres.d.ts +9 -0
  193. package/dist/generated/postgres.d.ts.map +1 -0
  194. package/dist/import-generator.d.ts +8 -0
  195. package/dist/import-generator.d.ts.map +1 -0
  196. package/dist/index.d.ts +7 -0
  197. package/dist/index.d.ts.map +1 -0
  198. package/dist/init-templates.d.ts +20 -0
  199. package/dist/init-templates.d.ts.map +1 -0
  200. package/dist/integrity.json +61 -0
  201. package/dist/lint/audit-catalog.d.ts +10 -0
  202. package/dist/lint/audit-catalog.d.ts.map +1 -0
  203. package/dist/lint/audit-lineage.d.ts +25 -0
  204. package/dist/lint/audit-lineage.d.ts.map +1 -0
  205. package/dist/lint/post-synth/audit-entries.d.ts +8 -0
  206. package/dist/lint/post-synth/audit-entries.d.ts.map +1 -0
  207. package/dist/lint/post-synth/clickhouse-helpers.d.ts +85 -0
  208. package/dist/lint/post-synth/clickhouse-helpers.d.ts.map +1 -0
  209. package/dist/lint/post-synth/index.d.ts +3 -0
  210. package/dist/lint/post-synth/index.d.ts.map +1 -0
  211. package/dist/lint/post-synth/postgres-audit-entries.d.ts +9 -0
  212. package/dist/lint/post-synth/postgres-audit-entries.d.ts.map +1 -0
  213. package/dist/lint/post-synth/postgres-helpers.d.ts +89 -0
  214. package/dist/lint/post-synth/postgres-helpers.d.ts.map +1 -0
  215. package/dist/lint/post-synth/sql-helpers.d.ts +27 -0
  216. package/dist/lint/post-synth/sql-helpers.d.ts.map +1 -0
  217. package/dist/lint/post-synth/sqlch101.d.ts +12 -0
  218. package/dist/lint/post-synth/sqlch101.d.ts.map +1 -0
  219. package/dist/lint/post-synth/sqlch102.d.ts +9 -0
  220. package/dist/lint/post-synth/sqlch102.d.ts.map +1 -0
  221. package/dist/lint/post-synth/sqlch103.d.ts +10 -0
  222. package/dist/lint/post-synth/sqlch103.d.ts.map +1 -0
  223. package/dist/lint/post-synth/sqlch104.d.ts +9 -0
  224. package/dist/lint/post-synth/sqlch104.d.ts.map +1 -0
  225. package/dist/lint/post-synth/sqlch105.d.ts +10 -0
  226. package/dist/lint/post-synth/sqlch105.d.ts.map +1 -0
  227. package/dist/lint/post-synth/sqlch106.d.ts +11 -0
  228. package/dist/lint/post-synth/sqlch106.d.ts.map +1 -0
  229. package/dist/lint/post-synth/sqlch107.d.ts +10 -0
  230. package/dist/lint/post-synth/sqlch107.d.ts.map +1 -0
  231. package/dist/lint/post-synth/sqlch108.d.ts +11 -0
  232. package/dist/lint/post-synth/sqlch108.d.ts.map +1 -0
  233. package/dist/lint/post-synth/sqlch109.d.ts +10 -0
  234. package/dist/lint/post-synth/sqlch109.d.ts.map +1 -0
  235. package/dist/lint/post-synth/sqlch110.d.ts +12 -0
  236. package/dist/lint/post-synth/sqlch110.d.ts.map +1 -0
  237. package/dist/lint/post-synth/sqlch111.d.ts +11 -0
  238. package/dist/lint/post-synth/sqlch111.d.ts.map +1 -0
  239. package/dist/lint/post-synth/sqlch112.d.ts +12 -0
  240. package/dist/lint/post-synth/sqlch112.d.ts.map +1 -0
  241. package/dist/lint/post-synth/sqlch113.d.ts +9 -0
  242. package/dist/lint/post-synth/sqlch113.d.ts.map +1 -0
  243. package/dist/lint/post-synth/sqlch114.d.ts +8 -0
  244. package/dist/lint/post-synth/sqlch114.d.ts.map +1 -0
  245. package/dist/lint/post-synth/sqlch115.d.ts +13 -0
  246. package/dist/lint/post-synth/sqlch115.d.ts.map +1 -0
  247. package/dist/lint/post-synth/sqlch116.d.ts +10 -0
  248. package/dist/lint/post-synth/sqlch116.d.ts.map +1 -0
  249. package/dist/lint/post-synth/sqlch117.d.ts +9 -0
  250. package/dist/lint/post-synth/sqlch117.d.ts.map +1 -0
  251. package/dist/lint/post-synth/sqlch118.d.ts +10 -0
  252. package/dist/lint/post-synth/sqlch118.d.ts.map +1 -0
  253. package/dist/lint/post-synth/sqlch119.d.ts +11 -0
  254. package/dist/lint/post-synth/sqlch119.d.ts.map +1 -0
  255. package/dist/lint/post-synth/sqlch120.d.ts +10 -0
  256. package/dist/lint/post-synth/sqlch120.d.ts.map +1 -0
  257. package/dist/lint/post-synth/sqlpg101.d.ts +12 -0
  258. package/dist/lint/post-synth/sqlpg101.d.ts.map +1 -0
  259. package/dist/lint/post-synth/sqlpg102.d.ts +11 -0
  260. package/dist/lint/post-synth/sqlpg102.d.ts.map +1 -0
  261. package/dist/lint/post-synth/sqlpg103.d.ts +11 -0
  262. package/dist/lint/post-synth/sqlpg103.d.ts.map +1 -0
  263. package/dist/lint/post-synth/sqlpg104.d.ts +10 -0
  264. package/dist/lint/post-synth/sqlpg104.d.ts.map +1 -0
  265. package/dist/lint/post-synth/sqlpg105.d.ts +10 -0
  266. package/dist/lint/post-synth/sqlpg105.d.ts.map +1 -0
  267. package/dist/lint/post-synth/sqlpg106.d.ts +9 -0
  268. package/dist/lint/post-synth/sqlpg106.d.ts.map +1 -0
  269. package/dist/lint/post-synth/sqlpg107.d.ts +10 -0
  270. package/dist/lint/post-synth/sqlpg107.d.ts.map +1 -0
  271. package/dist/lint/post-synth/sqlpg108.d.ts +11 -0
  272. package/dist/lint/post-synth/sqlpg108.d.ts.map +1 -0
  273. package/dist/lint/post-synth/sqlpg109.d.ts +11 -0
  274. package/dist/lint/post-synth/sqlpg109.d.ts.map +1 -0
  275. package/dist/lint/post-synth/sqlpg110.d.ts +12 -0
  276. package/dist/lint/post-synth/sqlpg110.d.ts.map +1 -0
  277. package/dist/lint/post-synth/sqlpg111.d.ts +10 -0
  278. package/dist/lint/post-synth/sqlpg111.d.ts.map +1 -0
  279. package/dist/lint/post-synth/sqlpg112.d.ts +10 -0
  280. package/dist/lint/post-synth/sqlpg112.d.ts.map +1 -0
  281. package/dist/lint/post-synth/sqlpg113.d.ts +11 -0
  282. package/dist/lint/post-synth/sqlpg113.d.ts.map +1 -0
  283. package/dist/lint/post-synth/sqlpg114.d.ts +13 -0
  284. package/dist/lint/post-synth/sqlpg114.d.ts.map +1 -0
  285. package/dist/lint/post-synth/sqlpg115.d.ts +13 -0
  286. package/dist/lint/post-synth/sqlpg115.d.ts.map +1 -0
  287. package/dist/lint/post-synth/sqlpg116.d.ts +11 -0
  288. package/dist/lint/post-synth/sqlpg116.d.ts.map +1 -0
  289. package/dist/lint/post-synth/sqlpg117.d.ts +12 -0
  290. package/dist/lint/post-synth/sqlpg117.d.ts.map +1 -0
  291. package/dist/lint/post-synth/sqlpg118.d.ts +12 -0
  292. package/dist/lint/post-synth/sqlpg118.d.ts.map +1 -0
  293. package/dist/lint/rules/index.d.ts +12 -0
  294. package/dist/lint/rules/index.d.ts.map +1 -0
  295. package/dist/lint/rules/postgres-templates.d.ts +18 -0
  296. package/dist/lint/rules/postgres-templates.d.ts.map +1 -0
  297. package/dist/lint/rules/sqlch001.d.ts +12 -0
  298. package/dist/lint/rules/sqlch001.d.ts.map +1 -0
  299. package/dist/lint/rules/sqlch002.d.ts +11 -0
  300. package/dist/lint/rules/sqlch002.d.ts.map +1 -0
  301. package/dist/lint/rules/sqlch003.d.ts +12 -0
  302. package/dist/lint/rules/sqlch003.d.ts.map +1 -0
  303. package/dist/lint/rules/sqlpg001.d.ts +16 -0
  304. package/dist/lint/rules/sqlpg001.d.ts.map +1 -0
  305. package/dist/lint/rules/sqlpg002.d.ts +12 -0
  306. package/dist/lint/rules/sqlpg002.d.ts.map +1 -0
  307. package/dist/lint/rules/sqlpg003.d.ts +16 -0
  308. package/dist/lint/rules/sqlpg003.d.ts.map +1 -0
  309. package/dist/lint/rules/sqlpg004.d.ts +21 -0
  310. package/dist/lint/rules/sqlpg004.d.ts.map +1 -0
  311. package/dist/lint/rules/templates.d.ts +23 -0
  312. package/dist/lint/rules/templates.d.ts.map +1 -0
  313. package/dist/live-dialect.d.ts +25 -0
  314. package/dist/live-dialect.d.ts.map +1 -0
  315. package/dist/lsp/catalog.d.ts +22 -0
  316. package/dist/lsp/catalog.d.ts.map +1 -0
  317. package/dist/lsp/completions.d.ts +13 -0
  318. package/dist/lsp/completions.d.ts.map +1 -0
  319. package/dist/lsp/hover.d.ts +12 -0
  320. package/dist/lsp/hover.d.ts.map +1 -0
  321. package/dist/lsp/postgres-catalog.d.ts +85 -0
  322. package/dist/lsp/postgres-catalog.d.ts.map +1 -0
  323. package/dist/lsp/postgres-template.d.ts +35 -0
  324. package/dist/lsp/postgres-template.d.ts.map +1 -0
  325. package/dist/lsp/postgres.d.ts +20 -0
  326. package/dist/lsp/postgres.d.ts.map +1 -0
  327. package/dist/lsp/refs.d.ts +8 -0
  328. package/dist/lsp/refs.d.ts.map +1 -0
  329. package/dist/lsp/registry.d.ts +4 -0
  330. package/dist/lsp/registry.d.ts.map +1 -0
  331. package/dist/lsp/template.d.ts +34 -0
  332. package/dist/lsp/template.d.ts.map +1 -0
  333. package/dist/manifest.json +8 -0
  334. package/dist/mcp/index.d.ts +13 -0
  335. package/dist/mcp/index.d.ts.map +1 -0
  336. package/dist/mcp/postgres.d.ts +32 -0
  337. package/dist/mcp/postgres.d.ts.map +1 -0
  338. package/dist/meta.json +67 -0
  339. package/dist/okf/index.md +67 -0
  340. package/dist/okf/rules/SQLCH001.md +11 -0
  341. package/dist/okf/rules/SQLCH002.md +11 -0
  342. package/dist/okf/rules/SQLCH003.md +11 -0
  343. package/dist/okf/rules/SQLCH101.md +15 -0
  344. package/dist/okf/rules/SQLCH102.md +11 -0
  345. package/dist/okf/rules/SQLCH103.md +11 -0
  346. package/dist/okf/rules/SQLCH104.md +11 -0
  347. package/dist/okf/rules/SQLCH105.md +11 -0
  348. package/dist/okf/rules/SQLCH106.md +11 -0
  349. package/dist/okf/rules/SQLCH107.md +11 -0
  350. package/dist/okf/rules/SQLCH108.md +15 -0
  351. package/dist/okf/rules/SQLCH109.md +11 -0
  352. package/dist/okf/rules/SQLCH110.md +11 -0
  353. package/dist/okf/rules/SQLCH111.md +11 -0
  354. package/dist/okf/rules/SQLCH112.md +11 -0
  355. package/dist/okf/rules/SQLCH113.md +11 -0
  356. package/dist/okf/rules/SQLCH114.md +11 -0
  357. package/dist/okf/rules/SQLCH115.md +11 -0
  358. package/dist/okf/rules/SQLCH116.md +11 -0
  359. package/dist/okf/rules/SQLCH117.md +15 -0
  360. package/dist/okf/rules/SQLCH118.md +15 -0
  361. package/dist/okf/rules/SQLCH119.md +15 -0
  362. package/dist/okf/rules/SQLCH120.md +15 -0
  363. package/dist/okf/rules/SQLPG001.md +11 -0
  364. package/dist/okf/rules/SQLPG002.md +11 -0
  365. package/dist/okf/rules/SQLPG003.md +11 -0
  366. package/dist/okf/rules/SQLPG004.md +11 -0
  367. package/dist/okf/rules/SQLPG101.md +11 -0
  368. package/dist/okf/rules/SQLPG102.md +11 -0
  369. package/dist/okf/rules/SQLPG103.md +11 -0
  370. package/dist/okf/rules/SQLPG104.md +11 -0
  371. package/dist/okf/rules/SQLPG105.md +11 -0
  372. package/dist/okf/rules/SQLPG106.md +11 -0
  373. package/dist/okf/rules/SQLPG107.md +11 -0
  374. package/dist/okf/rules/SQLPG108.md +11 -0
  375. package/dist/okf/rules/SQLPG109.md +11 -0
  376. package/dist/okf/rules/SQLPG110.md +11 -0
  377. package/dist/okf/rules/SQLPG111.md +11 -0
  378. package/dist/okf/rules/SQLPG112.md +11 -0
  379. package/dist/okf/rules/SQLPG113.md +24 -0
  380. package/dist/okf/rules/SQLPG114.md +11 -0
  381. package/dist/okf/rules/SQLPG115.md +11 -0
  382. package/dist/okf/rules/SQLPG116.md +15 -0
  383. package/dist/okf/rules/SQLPG117.md +11 -0
  384. package/dist/okf/rules/SQLPG118.md +11 -0
  385. package/dist/okf/types/Database.md +15 -0
  386. package/dist/okf/types/MaterializedView.md +14 -0
  387. package/dist/okf/types/PostgresDomain.md +13 -0
  388. package/dist/okf/types/PostgresEnum.md +13 -0
  389. package/dist/okf/types/PostgresExtension.md +13 -0
  390. package/dist/okf/types/PostgresIndex.md +9 -0
  391. package/dist/okf/types/PostgresMaterializedView.md +13 -0
  392. package/dist/okf/types/PostgresSchema.md +13 -0
  393. package/dist/okf/types/PostgresSequence.md +13 -0
  394. package/dist/okf/types/PostgresTable.md +13 -0
  395. package/dist/okf/types/PostgresView.md +13 -0
  396. package/dist/okf/types/Table.md +15 -0
  397. package/dist/okf/types/View.md +13 -0
  398. package/dist/op/activities/clickhouse-apply.d.ts +56 -0
  399. package/dist/op/activities/clickhouse-apply.d.ts.map +1 -0
  400. package/dist/op/activities/clickhouse-emulator.d.ts +26 -0
  401. package/dist/op/activities/clickhouse-emulator.d.ts.map +1 -0
  402. package/dist/op/activities/clickhouse-rebuild.d.ts +43 -0
  403. package/dist/op/activities/clickhouse-rebuild.d.ts.map +1 -0
  404. package/dist/op/activities/index.d.ts +19 -0
  405. package/dist/op/activities/index.d.ts.map +1 -0
  406. package/dist/op/activities/postgres-apply.d.ts +69 -0
  407. package/dist/op/activities/postgres-apply.d.ts.map +1 -0
  408. package/dist/op/activities/postgres-emulator.d.ts +33 -0
  409. package/dist/op/activities/postgres-emulator.d.ts.map +1 -0
  410. package/dist/op/activities/postgres-migration.d.ts +48 -0
  411. package/dist/op/activities/postgres-migration.d.ts.map +1 -0
  412. package/dist/op/activity-contracts.d.ts +464 -0
  413. package/dist/op/activity-contracts.d.ts.map +1 -0
  414. package/dist/package-cli.d.ts +3 -0
  415. package/dist/package-cli.d.ts.map +1 -0
  416. package/dist/plugin.d.ts +12 -0
  417. package/dist/plugin.d.ts.map +1 -0
  418. package/dist/postgres/apply/apply.d.ts +163 -0
  419. package/dist/postgres/apply/apply.d.ts.map +1 -0
  420. package/dist/postgres/apply/statements.d.ts +138 -0
  421. package/dist/postgres/apply/statements.d.ts.map +1 -0
  422. package/dist/postgres/catalog-types.d.ts +50 -0
  423. package/dist/postgres/catalog-types.d.ts.map +1 -0
  424. package/dist/postgres/container.d.ts +23 -0
  425. package/dist/postgres/container.d.ts.map +1 -0
  426. package/dist/postgres/entities.d.ts +322 -0
  427. package/dist/postgres/entities.d.ts.map +1 -0
  428. package/dist/postgres/entity-types.d.ts +17 -0
  429. package/dist/postgres/entity-types.d.ts.map +1 -0
  430. package/dist/postgres/import/generator.d.ts +28 -0
  431. package/dist/postgres/import/generator.d.ts.map +1 -0
  432. package/dist/postgres/import/ir.d.ts +24 -0
  433. package/dist/postgres/import/ir.d.ts.map +1 -0
  434. package/dist/postgres/import/live-export.d.ts +26 -0
  435. package/dist/postgres/import/live-export.d.ts.map +1 -0
  436. package/dist/postgres/keywords.d.ts +22 -0
  437. package/dist/postgres/keywords.d.ts.map +1 -0
  438. package/dist/postgres/live/bind.d.ts +76 -0
  439. package/dist/postgres/live/bind.d.ts.map +1 -0
  440. package/dist/postgres/live/catalog.d.ts +98 -0
  441. package/dist/postgres/live/catalog.d.ts.map +1 -0
  442. package/dist/postgres/live/client.d.ts +32 -0
  443. package/dist/postgres/live/client.d.ts.map +1 -0
  444. package/dist/postgres/live/describe-resources.d.ts +41 -0
  445. package/dist/postgres/live/describe-resources.d.ts.map +1 -0
  446. package/dist/postgres/migrate/backfill.d.ts +103 -0
  447. package/dist/postgres/migrate/backfill.d.ts.map +1 -0
  448. package/dist/postgres/migrate/batches.d.ts +90 -0
  449. package/dist/postgres/migrate/batches.d.ts.map +1 -0
  450. package/dist/postgres/migrate/carry.d.ts +196 -0
  451. package/dist/postgres/migrate/carry.d.ts.map +1 -0
  452. package/dist/postgres/migrate/handoff.d.ts +46 -0
  453. package/dist/postgres/migrate/handoff.d.ts.map +1 -0
  454. package/dist/postgres/migrate/names.d.ts +55 -0
  455. package/dist/postgres/migrate/names.d.ts.map +1 -0
  456. package/dist/postgres/migrate/observe.d.ts +139 -0
  457. package/dist/postgres/migrate/observe.d.ts.map +1 -0
  458. package/dist/postgres/migrate/op.d.ts +128 -0
  459. package/dist/postgres/migrate/op.d.ts.map +1 -0
  460. package/dist/postgres/migrate/receipts.d.ts +63 -0
  461. package/dist/postgres/migrate/receipts.d.ts.map +1 -0
  462. package/dist/postgres/migrate/replication.d.ts +80 -0
  463. package/dist/postgres/migrate/replication.d.ts.map +1 -0
  464. package/dist/postgres/migrate/steps.d.ts +225 -0
  465. package/dist/postgres/migrate/steps.d.ts.map +1 -0
  466. package/dist/postgres/overlays/columns.d.ts +6 -0
  467. package/dist/postgres/overlays/columns.d.ts.map +1 -0
  468. package/dist/postgres/overlays/constraints.d.ts +8 -0
  469. package/dist/postgres/overlays/constraints.d.ts.map +1 -0
  470. package/dist/postgres/overlays/indexes.d.ts +8 -0
  471. package/dist/postgres/overlays/indexes.d.ts.map +1 -0
  472. package/dist/postgres/overlays/kinds.d.ts +48 -0
  473. package/dist/postgres/overlays/kinds.d.ts.map +1 -0
  474. package/dist/postgres/overlays/partitioning.d.ts +5 -0
  475. package/dist/postgres/overlays/partitioning.d.ts.map +1 -0
  476. package/dist/postgres/overlays/relations.d.ts +6 -0
  477. package/dist/postgres/overlays/relations.d.ts.map +1 -0
  478. package/dist/postgres/overlays/storage.d.ts +28 -0
  479. package/dist/postgres/overlays/storage.d.ts.map +1 -0
  480. package/dist/postgres/overlays/type-ddl.d.ts +7 -0
  481. package/dist/postgres/overlays/type-ddl.d.ts.map +1 -0
  482. package/dist/postgres/overlays/types.d.ts +24 -0
  483. package/dist/postgres/overlays/types.d.ts.map +1 -0
  484. package/dist/postgres/parser.d.ts +216 -0
  485. package/dist/postgres/parser.d.ts.map +1 -0
  486. package/dist/postgres/plan/commands.d.ts +61 -0
  487. package/dist/postgres/plan/commands.d.ts.map +1 -0
  488. package/dist/postgres/plan/deep.d.ts +33 -0
  489. package/dist/postgres/plan/deep.d.ts.map +1 -0
  490. package/dist/postgres/plan/diff.d.ts +45 -0
  491. package/dist/postgres/plan/diff.d.ts.map +1 -0
  492. package/dist/postgres/plan/disruption.d.ts +14 -0
  493. package/dist/postgres/plan/disruption.d.ts.map +1 -0
  494. package/dist/postgres/plan/normalize.d.ts +108 -0
  495. package/dist/postgres/plan/normalize.d.ts.map +1 -0
  496. package/dist/postgres/plan/report.d.ts +6 -0
  497. package/dist/postgres/plan/report.d.ts.map +1 -0
  498. package/dist/postgres/plan/rules.d.ts +84 -0
  499. package/dist/postgres/plan/rules.d.ts.map +1 -0
  500. package/dist/postgres/plan/schema.d.ts +50 -0
  501. package/dist/postgres/plan/schema.d.ts.map +1 -0
  502. package/dist/postgres/plan/server-normalize.d.ts +26 -0
  503. package/dist/postgres/plan/server-normalize.d.ts.map +1 -0
  504. package/dist/postgres/providers/aurora.d.ts +12 -0
  505. package/dist/postgres/providers/aurora.d.ts.map +1 -0
  506. package/dist/postgres/providers/azure.d.ts +14 -0
  507. package/dist/postgres/providers/azure.d.ts.map +1 -0
  508. package/dist/postgres/providers/cloud-sql.d.ts +11 -0
  509. package/dist/postgres/providers/cloud-sql.d.ts.map +1 -0
  510. package/dist/postgres/providers/index.d.ts +35 -0
  511. package/dist/postgres/providers/index.d.ts.map +1 -0
  512. package/dist/postgres/providers/neon.d.ts +13 -0
  513. package/dist/postgres/providers/neon.d.ts.map +1 -0
  514. package/dist/postgres/providers/rds.d.ts +10 -0
  515. package/dist/postgres/providers/rds.d.ts.map +1 -0
  516. package/dist/postgres/providers/supabase.d.ts +12 -0
  517. package/dist/postgres/providers/supabase.d.ts.map +1 -0
  518. package/dist/postgres/providers/types.d.ts +59 -0
  519. package/dist/postgres/providers/types.d.ts.map +1 -0
  520. package/dist/postgres/testing/fake-client.d.ts +38 -0
  521. package/dist/postgres/testing/fake-client.d.ts.map +1 -0
  522. package/dist/postgres/testing/migration.d.ts +25 -0
  523. package/dist/postgres/testing/migration.d.ts.map +1 -0
  524. package/dist/postgres/testing/roundtrip-schema.d.ts +11 -0
  525. package/dist/postgres/testing/roundtrip-schema.d.ts.map +1 -0
  526. package/dist/postgres/testing/server.d.ts +17 -0
  527. package/dist/postgres/testing/server.d.ts.map +1 -0
  528. package/dist/postgres/testing/writable-server.d.ts +45 -0
  529. package/dist/postgres/testing/writable-server.d.ts.map +1 -0
  530. package/dist/postgres/tokens.d.ts +26 -0
  531. package/dist/postgres/tokens.d.ts.map +1 -0
  532. package/dist/postgres.d.ts +13 -0
  533. package/dist/postgres.d.ts.map +1 -0
  534. package/dist/rules/audit-entries.ts +29 -0
  535. package/dist/rules/clickhouse-helpers.ts +206 -0
  536. package/dist/rules/postgres-audit-entries.ts +29 -0
  537. package/dist/rules/postgres-helpers.ts +126 -0
  538. package/dist/rules/postgres-templates.ts +36 -0
  539. package/dist/rules/sql-helpers.ts +53 -0
  540. package/dist/rules/sqlch001.ts +53 -0
  541. package/dist/rules/sqlch002.ts +115 -0
  542. package/dist/rules/sqlch003.ts +68 -0
  543. package/dist/rules/sqlch101.ts +35 -0
  544. package/dist/rules/sqlch102.ts +23 -0
  545. package/dist/rules/sqlch103.ts +45 -0
  546. package/dist/rules/sqlch104.ts +42 -0
  547. package/dist/rules/sqlch105.ts +35 -0
  548. package/dist/rules/sqlch106.ts +27 -0
  549. package/dist/rules/sqlch107.ts +35 -0
  550. package/dist/rules/sqlch108.ts +27 -0
  551. package/dist/rules/sqlch109.ts +21 -0
  552. package/dist/rules/sqlch110.ts +29 -0
  553. package/dist/rules/sqlch111.ts +40 -0
  554. package/dist/rules/sqlch112.ts +30 -0
  555. package/dist/rules/sqlch113.ts +20 -0
  556. package/dist/rules/sqlch114.ts +26 -0
  557. package/dist/rules/sqlch115.ts +31 -0
  558. package/dist/rules/sqlch116.ts +22 -0
  559. package/dist/rules/sqlch117.ts +25 -0
  560. package/dist/rules/sqlch118.ts +26 -0
  561. package/dist/rules/sqlch119.ts +31 -0
  562. package/dist/rules/sqlch120.ts +21 -0
  563. package/dist/rules/sqlpg001.ts +88 -0
  564. package/dist/rules/sqlpg002.ts +68 -0
  565. package/dist/rules/sqlpg003.ts +59 -0
  566. package/dist/rules/sqlpg004.ts +73 -0
  567. package/dist/rules/sqlpg101.ts +24 -0
  568. package/dist/rules/sqlpg102.ts +30 -0
  569. package/dist/rules/sqlpg103.ts +23 -0
  570. package/dist/rules/sqlpg104.ts +23 -0
  571. package/dist/rules/sqlpg105.ts +22 -0
  572. package/dist/rules/sqlpg106.ts +22 -0
  573. package/dist/rules/sqlpg107.ts +22 -0
  574. package/dist/rules/sqlpg108.ts +27 -0
  575. package/dist/rules/sqlpg109.ts +37 -0
  576. package/dist/rules/sqlpg110.ts +33 -0
  577. package/dist/rules/sqlpg111.ts +23 -0
  578. package/dist/rules/sqlpg112.ts +25 -0
  579. package/dist/rules/sqlpg113.ts +28 -0
  580. package/dist/rules/sqlpg114.ts +37 -0
  581. package/dist/rules/sqlpg115.ts +38 -0
  582. package/dist/rules/sqlpg116.ts +25 -0
  583. package/dist/rules/sqlpg117.ts +24 -0
  584. package/dist/rules/sqlpg118.ts +22 -0
  585. package/dist/rules/templates.ts +35 -0
  586. package/dist/serializer.d.ts +37 -0
  587. package/dist/serializer.d.ts.map +1 -0
  588. package/dist/skill-defs.d.ts +3 -0
  589. package/dist/skill-defs.d.ts.map +1 -0
  590. package/dist/spec/catalog.d.ts +125 -0
  591. package/dist/spec/catalog.d.ts.map +1 -0
  592. package/dist/spec/fetch.d.ts +43 -0
  593. package/dist/spec/fetch.d.ts.map +1 -0
  594. package/dist/spec/pin.d.ts +39 -0
  595. package/dist/spec/pin.d.ts.map +1 -0
  596. package/dist/spec/postgres-catalog.d.ts +108 -0
  597. package/dist/spec/postgres-catalog.d.ts.map +1 -0
  598. package/dist/spec/postgres-fetch.d.ts +46 -0
  599. package/dist/spec/postgres-fetch.d.ts.map +1 -0
  600. package/dist/spec/postgres-pin.d.ts +67 -0
  601. package/dist/spec/postgres-pin.d.ts.map +1 -0
  602. package/dist/types/index.d.ts +4386 -0
  603. package/dist/validate-cli.d.ts +3 -0
  604. package/dist/validate-cli.d.ts.map +1 -0
  605. package/dist/validate.d.ts +15 -0
  606. package/dist/validate.d.ts.map +1 -0
  607. package/package.json +74 -4
  608. package/src/clickhouse/apply/apply.ts +288 -0
  609. package/src/clickhouse/apply/mutations.ts +90 -0
  610. package/src/clickhouse/apply/statements.ts +393 -0
  611. package/src/clickhouse/catalog-types.ts +84 -0
  612. package/src/clickhouse/container.ts +176 -0
  613. package/src/clickhouse/engine-syntax.test.ts +53 -0
  614. package/src/clickhouse/engine-syntax.ts +173 -0
  615. package/src/clickhouse/entities.test.ts +188 -0
  616. package/src/clickhouse/entities.ts +425 -0
  617. package/src/clickhouse/http.ts +76 -0
  618. package/src/clickhouse/import/generator.ts +153 -0
  619. package/src/clickhouse/import/import.test.ts +157 -0
  620. package/src/clickhouse/import/ir.ts +171 -0
  621. package/src/clickhouse/import/live-export.ts +53 -0
  622. package/src/clickhouse/import/parser.ts +27 -0
  623. package/src/clickhouse/import/roundtrip.test.ts +90 -0
  624. package/src/clickhouse/live/bind.ts +126 -0
  625. package/src/clickhouse/live/catalog.ts +96 -0
  626. package/src/clickhouse/live/describe-resources.ts +98 -0
  627. package/src/clickhouse/live/live.test.ts +143 -0
  628. package/src/clickhouse/live/roundtrip.e2e.test.ts +93 -0
  629. package/src/clickhouse/overlays/codecs.ts +68 -0
  630. package/src/clickhouse/overlays/engines.ts +108 -0
  631. package/src/clickhouse/overlays/kinds.ts +38 -0
  632. package/src/clickhouse/overlays/projections.ts +36 -0
  633. package/src/clickhouse/overlays/skip-indexes.ts +44 -0
  634. package/src/clickhouse/overlays/ttl.ts +55 -0
  635. package/src/clickhouse/overlays/types.ts +58 -0
  636. package/src/clickhouse/ownership.test.ts +20 -0
  637. package/src/clickhouse/ownership.ts +103 -0
  638. package/src/clickhouse/parser.test.ts +166 -0
  639. package/src/clickhouse/parser.ts +459 -0
  640. package/src/clickhouse/plan/commands.ts +101 -0
  641. package/src/clickhouse/plan/deep.ts +124 -0
  642. package/src/clickhouse/plan/diff.ts +203 -0
  643. package/src/clickhouse/plan/disruption.ts +61 -0
  644. package/src/clickhouse/plan/normalize.ts +352 -0
  645. package/src/clickhouse/plan/plan-wiring.test.ts +77 -0
  646. package/src/clickhouse/plan/plan.e2e.test.ts +77 -0
  647. package/src/clickhouse/plan/plan.test.ts +201 -0
  648. package/src/clickhouse/plan/rebuild-handoff.ts +59 -0
  649. package/src/clickhouse/plan/report.ts +19 -0
  650. package/src/clickhouse/plan/rules.ts +241 -0
  651. package/src/clickhouse/plan/schema.ts +56 -0
  652. package/src/clickhouse/plan/server-format.ts +39 -0
  653. package/src/clickhouse/rebuild/backfill.ts +186 -0
  654. package/src/clickhouse/rebuild/observe.ts +380 -0
  655. package/src/clickhouse/rebuild/op.ts +206 -0
  656. package/src/clickhouse/rebuild/partitions.ts +62 -0
  657. package/src/clickhouse/rebuild/rebuild-replicated.e2e.test.ts +513 -0
  658. package/src/clickhouse/rebuild/rebuild.e2e.test.ts +351 -0
  659. package/src/clickhouse/rebuild/rebuild.test.ts +190 -0
  660. package/src/clickhouse/rebuild/receipts.ts +143 -0
  661. package/src/clickhouse/rebuild/replicas.test.ts +70 -0
  662. package/src/clickhouse/rebuild/replicas.ts +148 -0
  663. package/src/clickhouse/rebuild/steps.ts +382 -0
  664. package/src/clickhouse/rebuild/verify.ts +124 -0
  665. package/src/clickhouse/testdata/NOTICE +5 -0
  666. package/src/clickhouse/testdata/clickhouse-tests-corpus.json +302 -0
  667. package/src/clickhouse/testing/fake-server.ts +65 -0
  668. package/src/clickhouse/testing/roundtrip-schema.ts +25 -0
  669. package/src/clickhouse/testing/writable-server.ts +141 -0
  670. package/src/clickhouse/tokens.ts +28 -0
  671. package/src/clickhouse.ts +63 -0
  672. package/src/codegen/classifier-page.test.ts +16 -0
  673. package/src/codegen/classifier-page.ts +76 -0
  674. package/src/codegen/clickhouse-module.test.ts +63 -0
  675. package/src/codegen/clickhouse-module.ts +269 -0
  676. package/src/codegen/docs-cli.ts +4 -0
  677. package/src/codegen/docs.ts +225 -0
  678. package/src/codegen/generate-cli.ts +13 -0
  679. package/src/codegen/generate.ts +126 -0
  680. package/src/codegen/package.ts +36 -0
  681. package/src/codegen/postgres-classifier-page.ts +81 -0
  682. package/src/codegen/postgres-module.test.ts +77 -0
  683. package/src/codegen/postgres-module.ts +434 -0
  684. package/src/codegen/registry.ts +36 -0
  685. package/src/composites/audit-log-table.ts +54 -0
  686. package/src/composites/catalog.test.ts +61 -0
  687. package/src/composites/catalog.ts +529 -0
  688. package/src/composites/cdc-mirror.ts +54 -0
  689. package/src/composites/clickhouse.ts +7 -0
  690. package/src/composites/composites.test.ts +758 -0
  691. package/src/composites/events-table.ts +49 -0
  692. package/src/composites/index.ts +9 -0
  693. package/src/composites/join-table.ts +57 -0
  694. package/src/composites/postgres.ts +7 -0
  695. package/src/composites/refreshed-view.ts +46 -0
  696. package/src/composites/replacing-table.ts +49 -0
  697. package/src/composites/rollup-view.ts +55 -0
  698. package/src/composites/sharded-table.ts +49 -0
  699. package/src/composites/soft-delete-table.ts +61 -0
  700. package/src/composites/tenant-table.ts +50 -0
  701. package/src/config.ts +157 -0
  702. package/src/core/apply.ts +153 -0
  703. package/src/core/classifier.ts +186 -0
  704. package/src/core/container.ts +93 -0
  705. package/src/core/core.test.ts +254 -0
  706. package/src/core/cursor.ts +189 -0
  707. package/src/core/diff.ts +72 -0
  708. package/src/core/entity.ts +85 -0
  709. package/src/core/find-templates.ts +158 -0
  710. package/src/core/handoff.ts +44 -0
  711. package/src/core/index.ts +61 -0
  712. package/src/core/interpolation.ts +225 -0
  713. package/src/core/normalize.ts +39 -0
  714. package/src/core/ownership.test.ts +36 -0
  715. package/src/core/ownership.ts +133 -0
  716. package/src/core/receipts.ts +29 -0
  717. package/src/core/references.ts +74 -0
  718. package/src/core/template.ts +83 -0
  719. package/src/core/testing/http-stub.ts +33 -0
  720. package/src/core/tokens.ts +252 -0
  721. package/src/coverage.ts +64 -0
  722. package/src/detect.ts +32 -0
  723. package/src/dialects.ts +21 -0
  724. package/src/generated/clickhouse-types.ts +4386 -0
  725. package/src/generated/clickhouse.ts +2476 -0
  726. package/src/generated/index.d.ts +4386 -0
  727. package/src/generated/lexicon-sql.json +67 -0
  728. package/src/generated/postgres-types.ts +1190 -0
  729. package/src/generated/postgres.ts +1039 -0
  730. package/src/import-generator.ts +18 -0
  731. package/src/index.ts +21 -0
  732. package/src/init-templates.test.ts +108 -0
  733. package/src/init-templates.ts +327 -0
  734. package/src/lint/audit-catalog.ts +73 -0
  735. package/src/lint/audit-lineage.ts +47 -0
  736. package/src/lint/post-synth/audit-entries.ts +29 -0
  737. package/src/lint/post-synth/clickhouse-checks.test.ts +278 -0
  738. package/src/lint/post-synth/clickhouse-helpers.ts +206 -0
  739. package/src/lint/post-synth/index.ts +81 -0
  740. package/src/lint/post-synth/post-synth.test.ts +33 -0
  741. package/src/lint/post-synth/postgres-audit-entries.ts +29 -0
  742. package/src/lint/post-synth/postgres-checks.test.ts +257 -0
  743. package/src/lint/post-synth/postgres-helpers.ts +126 -0
  744. package/src/lint/post-synth/sql-helpers.ts +53 -0
  745. package/src/lint/post-synth/sqlch101.ts +35 -0
  746. package/src/lint/post-synth/sqlch102.ts +23 -0
  747. package/src/lint/post-synth/sqlch103.ts +45 -0
  748. package/src/lint/post-synth/sqlch104.ts +42 -0
  749. package/src/lint/post-synth/sqlch105.ts +35 -0
  750. package/src/lint/post-synth/sqlch106.ts +27 -0
  751. package/src/lint/post-synth/sqlch107.ts +35 -0
  752. package/src/lint/post-synth/sqlch108.ts +27 -0
  753. package/src/lint/post-synth/sqlch109.ts +21 -0
  754. package/src/lint/post-synth/sqlch110.ts +29 -0
  755. package/src/lint/post-synth/sqlch111.ts +40 -0
  756. package/src/lint/post-synth/sqlch112.ts +30 -0
  757. package/src/lint/post-synth/sqlch113.ts +20 -0
  758. package/src/lint/post-synth/sqlch114.ts +26 -0
  759. package/src/lint/post-synth/sqlch115.ts +31 -0
  760. package/src/lint/post-synth/sqlch116.ts +22 -0
  761. package/src/lint/post-synth/sqlch117.ts +25 -0
  762. package/src/lint/post-synth/sqlch118.ts +26 -0
  763. package/src/lint/post-synth/sqlch119.ts +31 -0
  764. package/src/lint/post-synth/sqlch120.ts +21 -0
  765. package/src/lint/post-synth/sqlpg101.ts +24 -0
  766. package/src/lint/post-synth/sqlpg102.ts +30 -0
  767. package/src/lint/post-synth/sqlpg103.ts +23 -0
  768. package/src/lint/post-synth/sqlpg104.ts +23 -0
  769. package/src/lint/post-synth/sqlpg105.ts +22 -0
  770. package/src/lint/post-synth/sqlpg106.ts +22 -0
  771. package/src/lint/post-synth/sqlpg107.ts +22 -0
  772. package/src/lint/post-synth/sqlpg108.ts +27 -0
  773. package/src/lint/post-synth/sqlpg109.ts +37 -0
  774. package/src/lint/post-synth/sqlpg110.ts +33 -0
  775. package/src/lint/post-synth/sqlpg111.ts +23 -0
  776. package/src/lint/post-synth/sqlpg112.ts +25 -0
  777. package/src/lint/post-synth/sqlpg113.ts +28 -0
  778. package/src/lint/post-synth/sqlpg114.ts +37 -0
  779. package/src/lint/post-synth/sqlpg115.ts +38 -0
  780. package/src/lint/post-synth/sqlpg116.ts +25 -0
  781. package/src/lint/post-synth/sqlpg117.ts +24 -0
  782. package/src/lint/post-synth/sqlpg118.ts +22 -0
  783. package/src/lint/rules/index.ts +13 -0
  784. package/src/lint/rules/postgres-templates.ts +36 -0
  785. package/src/lint/rules/rules.test.ts +228 -0
  786. package/src/lint/rules/sqlch001.ts +53 -0
  787. package/src/lint/rules/sqlch002.ts +115 -0
  788. package/src/lint/rules/sqlch003.ts +68 -0
  789. package/src/lint/rules/sqlpg001.ts +88 -0
  790. package/src/lint/rules/sqlpg002.ts +68 -0
  791. package/src/lint/rules/sqlpg003.ts +59 -0
  792. package/src/lint/rules/sqlpg004.ts +73 -0
  793. package/src/lint/rules/templates.ts +35 -0
  794. package/src/live-dialect.ts +37 -0
  795. package/src/lsp/catalog.ts +60 -0
  796. package/src/lsp/completions.test.ts +111 -0
  797. package/src/lsp/completions.ts +128 -0
  798. package/src/lsp/diagnostics.test.ts +26 -0
  799. package/src/lsp/hover.test.ts +90 -0
  800. package/src/lsp/hover.ts +113 -0
  801. package/src/lsp/postgres-catalog.ts +234 -0
  802. package/src/lsp/postgres-template.ts +161 -0
  803. package/src/lsp/postgres.test.ts +150 -0
  804. package/src/lsp/postgres.ts +270 -0
  805. package/src/lsp/refs.ts +53 -0
  806. package/src/lsp/registry.ts +19 -0
  807. package/src/lsp/template.ts +166 -0
  808. package/src/mcp/index.ts +304 -0
  809. package/src/mcp/mcp.test.ts +184 -0
  810. package/src/mcp/postgres.ts +125 -0
  811. package/src/op/activities/clickhouse-apply.e2e.test.ts +150 -0
  812. package/src/op/activities/clickhouse-apply.test.ts +265 -0
  813. package/src/op/activities/clickhouse-apply.ts +113 -0
  814. package/src/op/activities/clickhouse-emulator.test.ts +23 -0
  815. package/src/op/activities/clickhouse-emulator.ts +37 -0
  816. package/src/op/activities/clickhouse-rebuild.ts +136 -0
  817. package/src/op/activities/index.ts +50 -0
  818. package/src/op/activities/postgres-apply.e2e.test.ts +184 -0
  819. package/src/op/activities/postgres-apply.test.ts +304 -0
  820. package/src/op/activities/postgres-apply.ts +170 -0
  821. package/src/op/activities/postgres-emulator.test.ts +26 -0
  822. package/src/op/activities/postgres-emulator.ts +44 -0
  823. package/src/op/activities/postgres-migration.ts +182 -0
  824. package/src/op/activity-contracts.ts +210 -0
  825. package/src/package-cli.ts +17 -0
  826. package/src/plugin.test.ts +74 -0
  827. package/src/plugin.ts +242 -0
  828. package/src/postgres/apply/apply.ts +582 -0
  829. package/src/postgres/apply/statements.test.ts +155 -0
  830. package/src/postgres/apply/statements.ts +603 -0
  831. package/src/postgres/catalog-types.ts +59 -0
  832. package/src/postgres/container.ts +72 -0
  833. package/src/postgres/entities.test.ts +170 -0
  834. package/src/postgres/entities.ts +1016 -0
  835. package/src/postgres/entity-types.ts +18 -0
  836. package/src/postgres/import/generator.ts +176 -0
  837. package/src/postgres/import/import.test.ts +71 -0
  838. package/src/postgres/import/ir.ts +67 -0
  839. package/src/postgres/import/live-export.ts +53 -0
  840. package/src/postgres/import/live-warnings.test.ts +45 -0
  841. package/src/postgres/keywords.ts +40 -0
  842. package/src/postgres/live/bind.ts +146 -0
  843. package/src/postgres/live/catalog.ts +581 -0
  844. package/src/postgres/live/client.ts +84 -0
  845. package/src/postgres/live/describe-resources.ts +111 -0
  846. package/src/postgres/live/live.test.ts +198 -0
  847. package/src/postgres/live/roundtrip.e2e.test.ts +111 -0
  848. package/src/postgres/migrate/backfill.ts +233 -0
  849. package/src/postgres/migrate/batches.e2e.test.ts +163 -0
  850. package/src/postgres/migrate/batches.test.ts +36 -0
  851. package/src/postgres/migrate/batches.ts +159 -0
  852. package/src/postgres/migrate/carry.e2e.test.ts +335 -0
  853. package/src/postgres/migrate/carry.test.ts +103 -0
  854. package/src/postgres/migrate/carry.ts +653 -0
  855. package/src/postgres/migrate/handoff.ts +73 -0
  856. package/src/postgres/migrate/kinds.e2e.test.ts +204 -0
  857. package/src/postgres/migrate/migrate.e2e.test.ts +362 -0
  858. package/src/postgres/migrate/migrate.test.ts +322 -0
  859. package/src/postgres/migrate/names.ts +93 -0
  860. package/src/postgres/migrate/observe.ts +521 -0
  861. package/src/postgres/migrate/op.ts +242 -0
  862. package/src/postgres/migrate/receipts.ts +135 -0
  863. package/src/postgres/migrate/replication.ts +151 -0
  864. package/src/postgres/migrate/steps.ts +657 -0
  865. package/src/postgres/overlays/columns.ts +34 -0
  866. package/src/postgres/overlays/constraints.ts +56 -0
  867. package/src/postgres/overlays/indexes.ts +27 -0
  868. package/src/postgres/overlays/kinds.ts +53 -0
  869. package/src/postgres/overlays/partitioning.ts +26 -0
  870. package/src/postgres/overlays/relations.ts +29 -0
  871. package/src/postgres/overlays/storage.ts +75 -0
  872. package/src/postgres/overlays/type-ddl.ts +38 -0
  873. package/src/postgres/overlays/types.ts +56 -0
  874. package/src/postgres/parser.test.ts +214 -0
  875. package/src/postgres/parser.ts +1062 -0
  876. package/src/postgres/plan/commands.ts +124 -0
  877. package/src/postgres/plan/deep.ts +177 -0
  878. package/src/postgres/plan/diff.ts +323 -0
  879. package/src/postgres/plan/disruption.ts +52 -0
  880. package/src/postgres/plan/normalize.test.ts +148 -0
  881. package/src/postgres/plan/normalize.ts +542 -0
  882. package/src/postgres/plan/plan.e2e.test.ts +117 -0
  883. package/src/postgres/plan/plan.test.ts +244 -0
  884. package/src/postgres/plan/report.ts +24 -0
  885. package/src/postgres/plan/rules.ts +276 -0
  886. package/src/postgres/plan/schema.ts +114 -0
  887. package/src/postgres/plan/server-normalize.ts +123 -0
  888. package/src/postgres/providers/aurora.ts +45 -0
  889. package/src/postgres/providers/azure.ts +54 -0
  890. package/src/postgres/providers/cloud-sql.ts +42 -0
  891. package/src/postgres/providers/index.ts +90 -0
  892. package/src/postgres/providers/neon.ts +45 -0
  893. package/src/postgres/providers/providers.test.ts +136 -0
  894. package/src/postgres/providers/rds.ts +48 -0
  895. package/src/postgres/providers/supabase.ts +46 -0
  896. package/src/postgres/providers/types.ts +70 -0
  897. package/src/postgres/testdata/NOTICE +31 -0
  898. package/src/postgres/testdata/postgres-regress-corpus.json +460 -0
  899. package/src/postgres/testing/fake-client.ts +42 -0
  900. package/src/postgres/testing/migration.ts +52 -0
  901. package/src/postgres/testing/roundtrip-schema.ts +46 -0
  902. package/src/postgres/testing/server.ts +58 -0
  903. package/src/postgres/testing/writable-server.ts +188 -0
  904. package/src/postgres/tokens.ts +46 -0
  905. package/src/postgres.ts +75 -0
  906. package/src/serializer.test.ts +128 -0
  907. package/src/serializer.ts +148 -0
  908. package/src/skill-defs.test.ts +81 -0
  909. package/src/skill-defs.ts +102 -0
  910. package/src/skills/chant-sql-plan.md +123 -0
  911. package/src/skills/chant-sql-postgres-migration.md +126 -0
  912. package/src/skills/chant-sql-postgres-plan.md +194 -0
  913. package/src/skills/chant-sql-postgres.md +165 -0
  914. package/src/skills/chant-sql-rebuild.md +68 -0
  915. package/src/skills/chant-sql.md +123 -0
  916. package/src/spec/catalog.e2e.test.ts +29 -0
  917. package/src/spec/catalog.test.ts +56 -0
  918. package/src/spec/catalog.ts +311 -0
  919. package/src/spec/clickhouse-catalog.snapshot.json +5246 -0
  920. package/src/spec/fetch.test.ts +77 -0
  921. package/src/spec/fetch.ts +112 -0
  922. package/src/spec/pin.ts +47 -0
  923. package/src/spec/postgres-catalog-14.snapshot.json +3494 -0
  924. package/src/spec/postgres-catalog-15.snapshot.json +3529 -0
  925. package/src/spec/postgres-catalog-16.snapshot.json +3597 -0
  926. package/src/spec/postgres-catalog-17.snapshot.json +3656 -0
  927. package/src/spec/postgres-catalog-18.snapshot.json +3747 -0
  928. package/src/spec/postgres-catalog.test.ts +43 -0
  929. package/src/spec/postgres-catalog.ts +301 -0
  930. package/src/spec/postgres-fetch.test.ts +75 -0
  931. package/src/spec/postgres-fetch.ts +112 -0
  932. package/src/spec/postgres-pin.test.ts +64 -0
  933. package/src/spec/postgres-pin.ts +101 -0
  934. package/src/typecheck.test.ts +104 -0
  935. package/src/validate-cli.ts +6 -0
  936. package/src/validate.ts +149 -0
@@ -0,0 +1,1062 @@
1
+ /**
2
+ * A hand-written, lossless parser for the Postgres statements the dialect
3
+ * declares (chant #3278, #3279): `CREATE SCHEMA`, `TABLE`, `INDEX`, `VIEW`,
4
+ * `MATERIALIZED VIEW`, `SEQUENCE`, `TYPE ... AS ENUM`, `DOMAIN`, `EXTENSION`,
5
+ * and `COMMENT ON` for those objects.
6
+ *
7
+ * As for ClickHouse (#3196), statement structure is parsed and expressions are
8
+ * not: a default, a check, a generated expression, an index element, a
9
+ * partition bound and a view's query are token spans, verbatim, with the
10
+ * interpolations inside them recorded. Postgres itself is the backstop.
11
+ *
12
+ * What the spike measured as missing is closed here: a column default is a
13
+ * `b_expr`, so a top-level `IN`, `AND`, `LIKE` or `IS NULL` in it is an error
14
+ * at that token; `LIKE ... INCLUDING` and `ON COMMIT` take only their own
15
+ * option words; a storage parameter list (`WITH (fillfactor = 70)`) is parsed
16
+ * as `name [= value]` items; a type cannot be a reserved word (`a ARRAY[4]`
17
+ * fails at `ARRAY`); and a range partition bound cannot be empty.
18
+ *
19
+ * An interpolation (`ref` token) is accepted wherever a name, a type or an
20
+ * expression goes. Lint parses with every interpolation still a `ref`.
21
+ *
22
+ * Grammar source: the Postgres 18 reference pages for each statement
23
+ * (sql-createtable, sql-createindex, sql-createview,
24
+ * sql-creatematerializedview, sql-createsequence, sql-createtype,
25
+ * sql-createdomain, sql-createextension, sql-createschema, sql-comment) and
26
+ * `src/backend/parser/gram.y` at `REL_18_6` where a page is silent.
27
+ */
28
+
29
+ import { kw, SqlCursor, type Span } from "../core/cursor";
30
+ import { SqlSyntaxError, type Token } from "../core/tokens";
31
+ import { keywordCategory } from "./keywords";
32
+
33
+ export type { Span } from "../core/cursor";
34
+ export { SqlSyntaxError };
35
+
36
+ /** An identifier as Postgres reads it: an unquoted name folds to lower case, a quoted one is exact. */
37
+ export function identValue(t: Token | string): string {
38
+ const text = typeof t === "string" ? t : t.text;
39
+ const quoted = typeof t === "string" ? /^(U&)?"/i.test(text) : t.kind === "qident";
40
+ if (quoted) {
41
+ if (/^[Uu]&/.test(text)) return text.slice(3, -1).replace(/""/g, '"');
42
+ return text.slice(1, -1).replace(/""/g, '"');
43
+ }
44
+ return text.toLowerCase();
45
+ }
46
+
47
+ const isKeywordToken = (t: Token): boolean => t.kind === "ident" && keywordCategory(t.text) !== undefined;
48
+
49
+ export interface NameNode {
50
+ /** The name's pieces, folded. An empty string where a piece is an interpolation. */
51
+ pieces: string[];
52
+ span: Span;
53
+ }
54
+
55
+ export interface ReferencesNode {
56
+ table: NameNode;
57
+ columns: Array<{ name: string; span: Span }>;
58
+ match?: string;
59
+ onDelete?: Span;
60
+ onUpdate?: Span;
61
+ }
62
+
63
+ export type ConstraintKind = "PRIMARY KEY" | "UNIQUE" | "CHECK" | "FOREIGN KEY" | "EXCLUDE" | "NOT NULL";
64
+
65
+ export interface ConstraintNode {
66
+ name?: string;
67
+ kind: ConstraintKind;
68
+ /** The columns a table constraint is on, by name. */
69
+ columns: Array<{ name: string; span: Span }>;
70
+ /** A check's expression, or an exclusion's element list. */
71
+ expr?: Span;
72
+ /** An exclusion constraint's access method. */
73
+ using?: string;
74
+ /** An exclusion constraint's predicate. */
75
+ where?: Span;
76
+ references?: ReferencesNode;
77
+ nullsNotDistinct?: boolean;
78
+ /** `INCLUDE (...)`, as written, parentheses excluded. */
79
+ include?: Span;
80
+ /** `WITH (...)` storage parameters, as written, parentheses excluded. */
81
+ with?: Span;
82
+ deferrable?: boolean;
83
+ initiallyDeferred?: boolean;
84
+ notValid?: boolean;
85
+ noInherit?: boolean;
86
+ /** `NOT ENFORCED` (Postgres 18). */
87
+ notEnforced?: boolean;
88
+ span: Span;
89
+ }
90
+
91
+ export interface ColumnNode {
92
+ name: string;
93
+ nameSpan: Span;
94
+ type?: Span;
95
+ collate?: Span;
96
+ compression?: Span;
97
+ storage?: Span;
98
+ /** `NOT NULL` (true) or `NULL` (false), when written. */
99
+ notNull?: boolean;
100
+ /** A name given to the column's NOT NULL constraint (`CONSTRAINT x NOT NULL`). */
101
+ notNullName?: string;
102
+ default?: Span;
103
+ generated?: { kind: "stored" | "virtual" | "identity"; expr?: Span; always: boolean; options?: Span };
104
+ /** Column constraints other than NOT NULL, NULL, DEFAULT and GENERATED. */
105
+ constraints: ConstraintNode[];
106
+ }
107
+
108
+ export interface TableNode {
109
+ statement: "table";
110
+ persistence?: "temporary" | "unlogged";
111
+ ifNotExists: boolean;
112
+ name: NameNode;
113
+ ofType?: NameNode;
114
+ partitionOf?: NameNode;
115
+ partitionBound?: Span;
116
+ columns: ColumnNode[];
117
+ constraints: ConstraintNode[];
118
+ like: Span[];
119
+ inherits?: NameNode[];
120
+ partitionBy?: Span;
121
+ using?: Span;
122
+ with?: Span;
123
+ onCommit?: Span;
124
+ tablespace?: Span;
125
+ }
126
+
127
+ export interface IndexElement {
128
+ span: Span;
129
+ /** When the element is a plain column (a name, then only opclass, collation and ordering words), its name. */
130
+ column?: string;
131
+ }
132
+
133
+ export interface IndexNode {
134
+ statement: "index";
135
+ unique: boolean;
136
+ concurrently: boolean;
137
+ ifNotExists: boolean;
138
+ name?: NameNode;
139
+ only: boolean;
140
+ table: NameNode;
141
+ using?: string;
142
+ elements: IndexElement[];
143
+ include?: Span;
144
+ nullsNotDistinct?: boolean;
145
+ with?: Span;
146
+ tablespace?: Span;
147
+ where?: Span;
148
+ }
149
+
150
+ export interface ViewNode {
151
+ statement: "view";
152
+ materialized: boolean;
153
+ orReplace: boolean;
154
+ temporary: boolean;
155
+ recursive: boolean;
156
+ ifNotExists: boolean;
157
+ name: NameNode;
158
+ columnNames: Array<{ name: string; span: Span }>;
159
+ using?: Span;
160
+ with?: Span;
161
+ tablespace?: Span;
162
+ query: Span;
163
+ checkOption?: Span;
164
+ /** `WITH DATA` (true) or `WITH NO DATA` (false), for a materialized view. */
165
+ withData?: boolean;
166
+ }
167
+
168
+ export interface SequenceNode {
169
+ statement: "sequence";
170
+ persistence?: "temporary" | "unlogged";
171
+ ifNotExists: boolean;
172
+ name: NameNode;
173
+ options: Array<{ option: string; value?: Span }>;
174
+ }
175
+
176
+ export interface SchemaNode {
177
+ statement: "schema";
178
+ ifNotExists: boolean;
179
+ name?: NameNode;
180
+ authorization?: Span;
181
+ }
182
+
183
+ export interface EnumNode {
184
+ statement: "enum";
185
+ name: NameNode;
186
+ labels: Span[];
187
+ }
188
+
189
+ export interface DomainNode {
190
+ statement: "domain";
191
+ name: NameNode;
192
+ type: Span;
193
+ collate?: Span;
194
+ default?: Span;
195
+ notNull?: boolean;
196
+ checks: Array<{ name?: string; expr: Span; notValid?: boolean }>;
197
+ }
198
+
199
+ export interface ExtensionNode {
200
+ statement: "extension";
201
+ ifNotExists: boolean;
202
+ name: NameNode;
203
+ schema?: Span;
204
+ version?: Span;
205
+ cascade: boolean;
206
+ }
207
+
208
+ export interface CommentNode {
209
+ statement: "comment";
210
+ /** TABLE, COLUMN, INDEX, VIEW, MATERIALIZED VIEW, SEQUENCE, TYPE, DOMAIN, SCHEMA, EXTENSION, CONSTRAINT, DOMAIN CONSTRAINT. */
211
+ objectType: string;
212
+ target: NameNode;
213
+ /** For `COMMENT ON CONSTRAINT c ON [DOMAIN] t`: the table or domain. */
214
+ on?: NameNode;
215
+ /** The comment, a string, or undefined for `IS NULL`. */
216
+ text?: Span;
217
+ }
218
+
219
+ export type StatementNode =
220
+ | TableNode
221
+ | IndexNode
222
+ | ViewNode
223
+ | SequenceNode
224
+ | SchemaNode
225
+ | EnumNode
226
+ | DomainNode
227
+ | ExtensionNode
228
+ | CommentNode;
229
+
230
+ const isNameToken = (t: Token | undefined): boolean =>
231
+ t !== undefined && (t.kind === "ident" || t.kind === "qident" || t.kind === "ref");
232
+
233
+ /** Words that end a column's type or a column clause: a column constraint, or a clause after the type. */
234
+ const COLUMN_CLAUSE = [
235
+ "CONSTRAINT",
236
+ "NOT",
237
+ "NULL",
238
+ "DEFAULT",
239
+ "GENERATED",
240
+ "UNIQUE",
241
+ "PRIMARY",
242
+ "CHECK",
243
+ "REFERENCES",
244
+ "COLLATE",
245
+ "DEFERRABLE",
246
+ "INITIALLY",
247
+ "COMPRESSION",
248
+ "STORAGE",
249
+ "ENFORCED",
250
+ ];
251
+
252
+ /** `LIKE source_table [ like_option ... ]`'s option words. */
253
+ const LIKE_OPTIONS = ["COMMENTS", "COMPRESSION", "CONSTRAINTS", "DEFAULTS", "GENERATED", "IDENTITY", "INDEXES", "STATISTICS", "STORAGE", "ALL"];
254
+
255
+ /**
256
+ * Words a `b_expr` cannot hold at its top level (gram.y): a column default and
257
+ * a domain default are `b_expr`, which has no `IN`, boolean operators, pattern
258
+ * matching, `BETWEEN`, `IS NULL`-style tests or `AT TIME ZONE`.
259
+ */
260
+ const NOT_IN_B_EXPR = ["IN", "AND", "OR", "LIKE", "ILIKE", "SIMILAR", "BETWEEN", "ISNULL", "NOTNULL", "AT", "COLLATE", "OVERLAPS"];
261
+
262
+ /** What may follow `IS` inside a `b_expr`. */
263
+ const B_EXPR_IS = [["DISTINCT", "FROM"], ["NOT", "DISTINCT", "FROM"], ["DOCUMENT"], ["NOT", "DOCUMENT"]];
264
+
265
+ class PgParser extends SqlCursor {
266
+ /** A multi-word stop is written with spaces: `"WITH CHECK OPTION"`. A stop never ends an expression at its first token. */
267
+ protected override stopsAt(stop: readonly string[]): boolean {
268
+ return stop.some((s) => this.is(...s.split(" ")));
269
+ }
270
+
271
+ /** `[` opens and `]` closes, as `(` and `)` do. */
272
+ protected override depthChange(t: Token): number {
273
+ if (t.kind === "punct" && (t.text === "(" || t.text === "[")) return 1;
274
+ if (t.kind === "punct" && (t.text === ")" || t.text === "]")) return -1;
275
+ return 0;
276
+ }
277
+
278
+ /**
279
+ * An expression span, up to a top-level `,` (unless `stopAtComma` is
280
+ * false), `)`, `]` or `;`, or a stop that is not its first token.
281
+ */
282
+ protected override expr(stop: readonly string[] = [], stopAtComma = true): Span {
283
+ const from = this.idx();
284
+ const refs: number[] = [];
285
+ let depth = 0;
286
+ const startP = this.p;
287
+ for (;;) {
288
+ const t = this.peek();
289
+ if (t === undefined) break;
290
+ if (depth === 0) {
291
+ if (t.kind === "punct" && (t.text === ")" || t.text === "]" || t.text === ";" || (stopAtComma && t.text === ","))) break;
292
+ if (this.p > startP && this.stopsAt(stop)) break;
293
+ }
294
+ depth += this.depthChange(t);
295
+ if (t.kind === "ref") refs.push(t.part);
296
+ this.p++;
297
+ }
298
+ if (this.p === startP) this.fail("expected an expression");
299
+ return this.span(from, refs);
300
+ }
301
+
302
+ private isOp(text: string, n = 0): boolean {
303
+ const t = this.peek(n);
304
+ return t !== undefined && t.kind === "op" && t.text === text;
305
+ }
306
+
307
+ /** A ColId: an identifier, or a key word that is neither reserved nor a type/function name word. */
308
+ private colId(t: Token, what: string): void {
309
+ if (!isNameToken(t)) this.fail(`expected ${what}`, t);
310
+ const k = t.kind === "ident" ? keywordCategory(t.text) : undefined;
311
+ if (k === "R" || k === "T") this.fail(`expected ${what} ('${t.text}' is a reserved key word; quote it to use it as a name)`, t);
312
+ }
313
+
314
+ private nameTok(what: string): { text: string; span: Span } {
315
+ const t = this.next();
316
+ this.colId(t, what);
317
+ const i = this.idx(-1);
318
+ return { text: t.kind === "ref" ? "" : identValue(t), span: { from: i, to: i + 1, refs: t.kind === "ref" ? [t.part] : [] } };
319
+ }
320
+
321
+ /** `name`, `schema.name`, `db.schema.name`. The first piece is a ColId; a piece after a dot may be any word. */
322
+ private qualifiedName(what = "a name"): NameNode {
323
+ const from = this.idx();
324
+ const refs: number[] = [];
325
+ const pieces: string[] = [];
326
+ const one = () => {
327
+ const t = this.next();
328
+ if (pieces.length === 0) this.colId(t, what);
329
+ else if (!isNameToken(t)) this.fail(`expected ${what}`, t);
330
+ if (t.kind === "ref") refs.push(t.part);
331
+ pieces.push(t.kind === "ref" ? "" : identValue(t));
332
+ };
333
+ one();
334
+ while (this.isPunct(".") && isNameToken(this.peek(1))) {
335
+ this.p++;
336
+ one();
337
+ }
338
+ if (this.isPunct(".")) this.fail(`expected ${what}`, this.peek(1));
339
+ return { pieces, span: this.span(from, refs) };
340
+ }
341
+
342
+ private ifNotExists(): boolean {
343
+ return this.acceptSeq("IF", "NOT", "EXISTS");
344
+ }
345
+
346
+ private checkedParens(): Span {
347
+ const span = this.parenthesized();
348
+ this.checkSpan(span);
349
+ return span;
350
+ }
351
+
352
+ /** `(a, b, c)`: a list of names. */
353
+ private nameList(what = "a column name"): Array<{ name: string; span: Span }> {
354
+ this.expectPunct("(");
355
+ const out: Array<{ name: string; span: Span }> = [];
356
+ for (;;) {
357
+ out.push((({ text, span }) => ({ name: text, span }))(this.nameTok(what)));
358
+ if (this.acceptPunct(",")) continue;
359
+ this.expectPunct(")");
360
+ return out;
361
+ }
362
+ }
363
+
364
+ /** A comma-separated list of expression spans inside parentheses. */
365
+ private parenList(): Span[] {
366
+ this.expectPunct("(");
367
+ const out: Span[] = [];
368
+ if (this.acceptPunct(")")) return out;
369
+ for (;;) {
370
+ out.push(this.expr());
371
+ if (this.acceptPunct(",")) continue;
372
+ this.expectPunct(")");
373
+ return out;
374
+ }
375
+ }
376
+
377
+ /**
378
+ * `( name [= value] [, ...] )`: storage parameters (`WITH (fillfactor = 70)`)
379
+ * or index parameters. A name may be qualified (`toast.autovacuum_enabled`);
380
+ * a value is a number, a string, a word or a signed number.
381
+ */
382
+ private reloptions(): Span {
383
+ const from = this.idx();
384
+ this.expectPunct("(");
385
+ const refs: number[] = [];
386
+ for (;;) {
387
+ const t = this.next();
388
+ if (t.kind === "ref") refs.push(t.part);
389
+ else if (t.kind !== "ident" && t.kind !== "qident") this.fail("expected a storage parameter name", t);
390
+ if (this.acceptPunct(".")) {
391
+ const u = this.next();
392
+ if (u.kind !== "ident" && u.kind !== "qident") this.fail("expected a storage parameter name", u);
393
+ }
394
+ if (this.isOp("=")) {
395
+ this.p++;
396
+ if (this.isOp("-") || this.isOp("+")) this.p++;
397
+ const v = this.next();
398
+ if (v.kind === "ref") refs.push(v.part);
399
+ else if (!["number", "string", "ident", "qident"].includes(v.kind)) this.fail("expected a storage parameter value", v);
400
+ }
401
+ if (this.acceptPunct(",")) continue;
402
+ this.expectPunct(")");
403
+ break;
404
+ }
405
+ // The span keeps the parentheses: `(fillfactor = 70)`.
406
+ return this.span(from, refs);
407
+ }
408
+
409
+ /** Constraint attributes after a constraint, recorded on it. */
410
+ private constraintAttributes(node: ConstraintNode): void {
411
+ for (;;) {
412
+ if (this.acceptSeq("NOT", "DEFERRABLE")) node.deferrable = false;
413
+ else if (this.accept("DEFERRABLE")) node.deferrable = true;
414
+ else if (this.acceptSeq("INITIALLY", "DEFERRED")) node.initiallyDeferred = true;
415
+ else if (this.acceptSeq("INITIALLY", "IMMEDIATE")) node.initiallyDeferred = false;
416
+ else if (this.acceptSeq("NOT", "VALID")) node.notValid = true;
417
+ else if (this.acceptSeq("NO", "INHERIT")) node.noInherit = true;
418
+ else if (this.acceptSeq("NOT", "ENFORCED")) node.notEnforced = true;
419
+ else if (this.accept("ENFORCED")) node.notEnforced = false;
420
+ else if (this.accept("INCLUDE")) node.include = this.parenthesized();
421
+ else if (kw(this.peek(), "WITH") && this.isPunct("(", 1)) {
422
+ this.p++;
423
+ node.with = this.reloptions();
424
+ } else if (this.acceptSeq("USING", "INDEX", "TABLESPACE")) this.nameTok("a tablespace");
425
+ else break;
426
+ }
427
+ }
428
+
429
+ private references(): ReferencesNode {
430
+ const table = this.qualifiedName("a referenced table");
431
+ const node: ReferencesNode = { table, columns: [] };
432
+ if (this.isPunct("(")) {
433
+ this.expectPunct("(");
434
+ for (;;) {
435
+ this.accept("PERIOD");
436
+ const { text, span } = this.nameTok("a referenced column");
437
+ node.columns.push({ name: text, span });
438
+ if (this.acceptPunct(",")) continue;
439
+ this.expectPunct(")");
440
+ break;
441
+ }
442
+ }
443
+ if (this.accept("MATCH")) {
444
+ if (!this.accept("FULL", "PARTIAL", "SIMPLE")) this.fail("expected FULL, PARTIAL or SIMPLE");
445
+ node.match = this.tokens[this.idx(-1)]!.text.toUpperCase();
446
+ }
447
+ for (;;) {
448
+ if (this.acceptSeq("ON", "DELETE")) node.onDelete = this.fkAction();
449
+ else if (this.acceptSeq("ON", "UPDATE")) node.onUpdate = this.fkAction();
450
+ else break;
451
+ }
452
+ return node;
453
+ }
454
+
455
+ private fkAction(): Span {
456
+ const from = this.idx();
457
+ if (this.acceptSeq("NO", "ACTION") || this.accept("RESTRICT") || this.accept("CASCADE")) return this.span(from, []);
458
+ if (this.acceptSeq("SET", "NULL") || this.acceptSeq("SET", "DEFAULT")) {
459
+ if (this.isPunct("(")) this.nameList();
460
+ return this.span(from, []);
461
+ }
462
+ return this.fail("expected NO ACTION, RESTRICT, CASCADE, SET NULL or SET DEFAULT");
463
+ }
464
+
465
+ /** `(a, b [, c WITHOUT OVERLAPS | PERIOD c])` for a key. */
466
+ private keyColumns(): Array<{ name: string; span: Span }> {
467
+ this.expectPunct("(");
468
+ const out: Array<{ name: string; span: Span }> = [];
469
+ for (;;) {
470
+ this.accept("PERIOD");
471
+ const { text, span } = this.nameTok("a column name");
472
+ out.push({ name: text, span });
473
+ this.acceptSeq("WITHOUT", "OVERLAPS");
474
+ if (this.acceptPunct(",")) continue;
475
+ this.expectPunct(")");
476
+ return out;
477
+ }
478
+ }
479
+
480
+ /** A table constraint, after an optional `CONSTRAINT name`. Undefined when the element is not one. */
481
+ private tableConstraint(): ConstraintNode | undefined {
482
+ const from = this.idx();
483
+ let name: string | undefined;
484
+ if (kw(this.peek(), "CONSTRAINT")) {
485
+ this.p++;
486
+ name = this.nameTok("a constraint name").text;
487
+ }
488
+ const at = (kind: ConstraintKind, extra: Partial<ConstraintNode> = {}): ConstraintNode => ({
489
+ name,
490
+ kind,
491
+ columns: [],
492
+ ...extra,
493
+ span: { from, to: from, refs: [] },
494
+ });
495
+ let node: ConstraintNode;
496
+ if (this.accept("CHECK")) node = at("CHECK", { expr: this.checkedParens() });
497
+ else if (this.acceptSeq("PRIMARY", "KEY")) node = at("PRIMARY KEY", { columns: this.keyColumns() });
498
+ else if (this.accept("UNIQUE")) {
499
+ // NULLS [NOT] DISTINCT comes before the column list.
500
+ const nnd = this.acceptSeq("NULLS", "NOT", "DISTINCT") ? true : this.acceptSeq("NULLS", "DISTINCT") ? false : undefined;
501
+ node = at("UNIQUE", { columns: this.keyColumns(), nullsNotDistinct: nnd });
502
+ } else if (this.acceptSeq("FOREIGN", "KEY")) {
503
+ const columns = this.keyColumns();
504
+ this.expect("REFERENCES");
505
+ node = at("FOREIGN KEY", { columns, references: this.references() });
506
+ } else if (kw(this.peek(), "EXCLUDE") && (this.isPunct("(", 1) || kw(this.peek(1), "USING"))) {
507
+ this.p++;
508
+ const using = this.accept("USING") ? this.nameTok("an access method").text : undefined;
509
+ if (this.isPunct("(") && this.isPunct(")", 1)) this.fail("expected an exclusion element", this.peek(1));
510
+ node = at("EXCLUDE", { expr: this.parenthesized(), using });
511
+ } else if (this.acceptSeq("NOT", "NULL")) {
512
+ const { text, span } = this.nameTok("a column name");
513
+ node = at("NOT NULL", { columns: [{ name: text, span }] });
514
+ } else {
515
+ if (name !== undefined) this.fail("expected CHECK, PRIMARY KEY, UNIQUE, FOREIGN KEY, EXCLUDE or NOT NULL");
516
+ return undefined;
517
+ }
518
+ this.constraintAttributes(node);
519
+ if (node.kind === "EXCLUDE" && this.accept("WHERE")) {
520
+ node.where = this.checkedParens();
521
+ this.constraintAttributes(node);
522
+ }
523
+ node.span = this.span(from, []);
524
+ return node;
525
+ }
526
+
527
+ private column(typed: boolean): ColumnNode {
528
+ const { text, span } = this.nameTok("a column name");
529
+ const col: ColumnNode = { name: text, nameSpan: span, constraints: [] };
530
+ if (!typed) this.acceptSeq("WITH", "OPTIONS");
531
+ const at = this.peek();
532
+ const bare = at === undefined || (at.kind === "punct" && (at.text === "," || at.text === ")"));
533
+ if (typed && !bare && !this.stopsAt(COLUMN_CLAUSE)) col.type = this.typeName();
534
+ else if (typed) this.fail("expected a column type");
535
+ for (;;) {
536
+ if (this.accept("COMPRESSION")) col.compression = this.expr(COLUMN_CLAUSE);
537
+ else if (this.accept("STORAGE")) col.storage = this.expr(COLUMN_CLAUSE);
538
+ else if (this.accept("COLLATE")) col.collate = this.expr(COLUMN_CLAUSE);
539
+ else if (!this.columnConstraint(col)) break;
540
+ }
541
+ const after = this.peek();
542
+ if (after && !(after.kind === "punct" && (after.text === "," || after.text === ")"))) this.fail("expected a column constraint, ',' or ')'");
543
+ return col;
544
+ }
545
+
546
+ /**
547
+ * A type name: `[schema.]name [(modifiers)]`, the SQL multi-word forms
548
+ * (`double precision`, `character varying`, `timestamp with time zone`,
549
+ * `interval day to second`, `bit varying`), `SETOF`-free, and array bounds
550
+ * (`int[]`, `int[3]`, `int ARRAY[3]`). An interpolated type is one token.
551
+ * A reserved word is never a type.
552
+ */
553
+ private typeName(): Span {
554
+ const from = this.idx();
555
+ const refs: number[] = [];
556
+ const t = this.next();
557
+ if (t.kind === "ref") refs.push(t.part);
558
+ else if (t.kind !== "ident" && t.kind !== "qident") this.fail("expected a type", t);
559
+ else if (t.kind === "ident" && keywordCategory(t.text) === "R") this.fail("expected a type", t);
560
+ const first = t.kind === "ident" ? t.text.toUpperCase() : "";
561
+ if (t.kind !== "ref") while (this.isPunct(".") && isNameToken(this.peek(1))) this.p += 2;
562
+ const precision = () => {
563
+ if (this.isPunct("(") && this.isPunct(")", 1)) this.fail("expected a type modifier", this.peek(1));
564
+ if (this.isPunct("(")) refs.push(...this.parenthesized().refs);
565
+ };
566
+ if (first === "DOUBLE") this.expect("PRECISION");
567
+ else if (["CHARACTER", "CHAR", "NCHAR", "NATIONAL", "BIT", "VARCHAR"].includes(first)) {
568
+ if (first === "NATIONAL") this.expect("CHARACTER", "CHAR");
569
+ this.accept("VARYING");
570
+ precision();
571
+ } else if (first === "TIME" || first === "TIMESTAMP") {
572
+ precision();
573
+ if (!this.acceptSeq("WITH", "TIME", "ZONE")) this.acceptSeq("WITHOUT", "TIME", "ZONE");
574
+ } else if (first === "INTERVAL") {
575
+ const FIELDS = ["YEAR", "MONTH", "DAY", "HOUR", "MINUTE", "SECOND"];
576
+ if (this.accept(...FIELDS) && this.accept("TO")) this.expect(...FIELDS);
577
+ precision();
578
+ } else precision();
579
+ for (;;) {
580
+ if (this.isPunct("[")) {
581
+ this.p++;
582
+ if (this.peek()?.kind === "number") this.p++;
583
+ this.expectPunct("]");
584
+ } else if (this.accept("ARRAY")) {
585
+ if (this.isPunct("[")) {
586
+ this.p++;
587
+ if (this.peek()?.kind === "number") this.p++;
588
+ this.expectPunct("]");
589
+ }
590
+ } else break;
591
+ }
592
+ return this.span(from, refs);
593
+ }
594
+
595
+ /** An expression span with the operand check {@link checkSpan} makes. */
596
+ private checkedExpr(stop: readonly string[] = [], stopAtComma = true): Span {
597
+ const span = this.expr(stop, stopAtComma);
598
+ this.checkSpan(span);
599
+ return span;
600
+ }
601
+
602
+ /** A `b_expr` (a column or domain default): an expression with none of {@link NOT_IN_B_EXPR} at its top level. */
603
+ private bExpr(stop: readonly string[]): Span {
604
+ const span = this.checkedExpr(stop);
605
+ let depth = 0;
606
+ const sig: Token[] = [];
607
+ for (let i = span.from; i < span.to; i++) {
608
+ const t = this.tokens[i]!;
609
+ if (t.kind !== "ws" && t.kind !== "comment") sig.push(t);
610
+ }
611
+ for (let k = 0; k < sig.length; k++) {
612
+ const t = sig[k]!;
613
+ depth += this.depthChange(t);
614
+ if (depth !== 0 || t.kind !== "ident") continue;
615
+ const word = t.text.toUpperCase();
616
+ if (NOT_IN_B_EXPR.includes(word)) this.fail("expected the end of the default (a default cannot hold this operator unparenthesized)", t);
617
+ if (word === "IS") {
618
+ const ok = B_EXPR_IS.some((seq) => seq.every((w, n) => kw(sig[k + 1 + n], w)));
619
+ if (!ok) this.fail("expected the end of the default (a default cannot hold IS unparenthesized)", t);
620
+ }
621
+ }
622
+ return span;
623
+ }
624
+
625
+ /**
626
+ * Since Postgres 14 removed postfix operators, an operand is never followed
627
+ * directly by a name that is not a key word, nor by another literal. That
628
+ * catches a misspelt key word after an expression (`DEFAULT 'x' CHEK (...)`)
629
+ * at its token, which a plain span would accept.
630
+ */
631
+ private checkSpan(span: Span): void {
632
+ let prev: Token | undefined;
633
+ const operandEnd = (x: Token) =>
634
+ x.kind === "string" ||
635
+ x.kind === "number" ||
636
+ x.kind === "qident" ||
637
+ x.kind === "param" ||
638
+ x.kind === "ref" ||
639
+ (x.kind === "punct" && (x.text === ")" || x.text === "]")) ||
640
+ (x.kind === "ident" && !isKeywordToken(x));
641
+ for (let i = span.from; i < span.to; i++) {
642
+ const t = this.tokens[i]!;
643
+ if (t.kind === "ws" || t.kind === "comment") continue;
644
+ if (prev && prev.kind === "punct" && prev.text === "," && t.kind === "punct" && t.text === ")") this.fail("expected an expression", t);
645
+ // Two operands in a row: `z 0`, `(a) 'x'`. A name before a string is a typed literal (`date '2020-01-01'`).
646
+ if (prev && operandEnd(prev) && (t.kind === "number" || t.kind === "qident" || t.kind === "param" || (t.kind === "string" && prev.kind !== "ident"))) {
647
+ this.fail("expected an operator, a key word or the end of the expression", t);
648
+ }
649
+ if (prev && t.kind === "ident" && !isKeywordToken(t) && operandEnd(prev)) {
650
+ this.fail("expected an operator, a key word or the end of the expression", t);
651
+ }
652
+ prev = t;
653
+ }
654
+ }
655
+
656
+ /** One column constraint; false when there is none here. */
657
+ private columnConstraint(col: ColumnNode): boolean {
658
+ const from = this.idx();
659
+ let name: string | undefined;
660
+ if (kw(this.peek(), "CONSTRAINT")) {
661
+ this.p++;
662
+ name = this.nameTok("a constraint name").text;
663
+ }
664
+ const push = (kind: ConstraintKind, extra: Partial<ConstraintNode> = {}) => {
665
+ const node: ConstraintNode = { name, kind, columns: [], ...extra, span: { from, to: from, refs: [] } };
666
+ this.constraintAttributes(node);
667
+ node.span = this.span(from, []);
668
+ col.constraints.push(node);
669
+ };
670
+ if (this.acceptSeq("NOT", "NULL")) {
671
+ col.notNull = true;
672
+ if (name !== undefined) col.notNullName = name;
673
+ this.acceptSeq("NO", "INHERIT");
674
+ } else if (this.accept("NULL")) col.notNull = false;
675
+ else if (this.accept("DEFAULT")) col.default = this.bExpr(COLUMN_CLAUSE);
676
+ else if (kw(this.peek(), "GENERATED")) {
677
+ this.p++;
678
+ let always: boolean;
679
+ if (this.accept("ALWAYS")) always = true;
680
+ else {
681
+ this.expect("BY");
682
+ this.expect("DEFAULT");
683
+ always = false;
684
+ }
685
+ this.expect("AS");
686
+ if (this.accept("IDENTITY")) {
687
+ col.generated = { kind: "identity", always, options: this.isPunct("(") ? this.parenthesized() : undefined };
688
+ } else {
689
+ if (!always) this.fail("expected IDENTITY (a generated column is GENERATED ALWAYS AS)");
690
+ const expr = this.checkedParens();
691
+ // Neither word is VIRTUAL, the default from 18 (the pinned major); 14 to 17 require STORED.
692
+ const kind = this.accept("STORED") ? "stored" : (this.accept("VIRTUAL"), "virtual");
693
+ col.generated = { kind, expr, always };
694
+ }
695
+ } else if (this.accept("CHECK")) push("CHECK", { expr: this.checkedParens() });
696
+ else if (this.accept("UNIQUE")) {
697
+ const nnd = this.acceptSeq("NULLS", "NOT", "DISTINCT") ? true : this.acceptSeq("NULLS", "DISTINCT") ? false : undefined;
698
+ push("UNIQUE", { nullsNotDistinct: nnd });
699
+ } else if (this.acceptSeq("PRIMARY", "KEY")) push("PRIMARY KEY");
700
+ else if (this.accept("REFERENCES")) push("FOREIGN KEY", { references: this.references() });
701
+ else if (name === undefined && col.constraints.length > 0 && kw(this.peek(), "DEFERRABLE", "INITIALLY", "NOT")) {
702
+ // `DEFERRABLE` / `INITIALLY ...` written after the constraint it qualifies.
703
+ const last = col.constraints[col.constraints.length - 1]!;
704
+ const before = this.p;
705
+ this.constraintAttributes(last);
706
+ if (this.p === before) return false;
707
+ } else {
708
+ if (name !== undefined) this.fail("expected a column constraint");
709
+ return false;
710
+ }
711
+ return true;
712
+ }
713
+
714
+ private tableElements(node: TableNode, typed: boolean): void {
715
+ this.expectPunct("(");
716
+ if (this.acceptPunct(")")) return;
717
+ for (;;) {
718
+ if (this.accept("LIKE")) node.like.push(this.likeClause());
719
+ else {
720
+ const c = this.tableConstraint();
721
+ if (c) node.constraints.push(c);
722
+ else node.columns.push(this.column(typed));
723
+ }
724
+ if (this.acceptPunct(",")) continue;
725
+ this.expectPunct(")");
726
+ return;
727
+ }
728
+ }
729
+
730
+ /** `LIKE source [ { INCLUDING | EXCLUDING } option ... ]`, as written after `LIKE`. */
731
+ private likeClause(): Span {
732
+ const from = this.idx();
733
+ const source = this.qualifiedName("a table name");
734
+ while (this.accept("INCLUDING", "EXCLUDING")) {
735
+ if (!this.accept(...LIKE_OPTIONS)) this.fail(`expected ${LIKE_OPTIONS.join(", ")}`);
736
+ }
737
+ return this.span(from, source.span.refs);
738
+ }
739
+
740
+ private persistence(): "temporary" | "unlogged" | undefined {
741
+ this.accept("GLOBAL", "LOCAL");
742
+ if (this.accept("TEMPORARY", "TEMP")) return "temporary";
743
+ if (this.accept("UNLOGGED")) return "unlogged";
744
+ return undefined;
745
+ }
746
+
747
+ parse(): StatementNode {
748
+ if (this.accept("COMMENT")) return this.comment();
749
+ this.expect("CREATE");
750
+ const orReplace = this.acceptSeq("OR", "REPLACE");
751
+ if (!orReplace) {
752
+ if (this.accept("SCHEMA")) return this.schema();
753
+ if (this.accept("EXTENSION")) return this.extension();
754
+ if (this.accept("DOMAIN")) return this.domain();
755
+ if (this.accept("TYPE")) return this.enumType();
756
+ if (kw(this.peek(), "UNIQUE", "INDEX")) return this.index();
757
+ }
758
+ const persistence = this.persistence();
759
+ if (!orReplace && this.accept("TABLE")) return this.table(persistence);
760
+ if (!orReplace && this.accept("SEQUENCE")) return this.sequence(persistence);
761
+ if (persistence === "unlogged") return this.fail("expected TABLE or SEQUENCE");
762
+ const recursive = this.accept("RECURSIVE");
763
+ if (!orReplace && !recursive && persistence === undefined && this.acceptSeq("MATERIALIZED", "VIEW")) return this.view(true, false, false, false);
764
+ if (this.accept("VIEW")) return this.view(false, orReplace, persistence === "temporary", recursive);
765
+ return this.fail("expected SCHEMA, TABLE, INDEX, VIEW, MATERIALIZED VIEW, SEQUENCE, TYPE, DOMAIN or EXTENSION");
766
+ }
767
+
768
+ private schema(): SchemaNode {
769
+ const node: SchemaNode = { statement: "schema", ifNotExists: this.ifNotExists() };
770
+ if (!kw(this.peek(), "AUTHORIZATION")) node.name = this.qualifiedName("a schema name");
771
+ if (this.accept("AUTHORIZATION")) {
772
+ const from = this.idx();
773
+ const t = this.next();
774
+ if (!isNameToken(t)) this.fail("expected a role name", t);
775
+ node.authorization = this.span(from, t.kind === "ref" ? [t.part] : []);
776
+ }
777
+ if (kw(this.peek(), "CREATE", "GRANT")) this.fail("schema elements inside CREATE SCHEMA are not declared here; declare each object on its own");
778
+ return node;
779
+ }
780
+
781
+ private extension(): ExtensionNode {
782
+ const node: ExtensionNode = { statement: "extension", ifNotExists: this.ifNotExists(), name: this.qualifiedName("an extension name"), cascade: false };
783
+ this.accept("WITH");
784
+ for (;;) {
785
+ if (this.accept("SCHEMA")) node.schema = this.nameTok("a schema name").span;
786
+ else if (this.accept("VERSION")) {
787
+ const from = this.idx();
788
+ const t = this.next();
789
+ if (!["ident", "qident", "string", "ref"].includes(t.kind)) this.fail("expected a version", t);
790
+ node.version = this.span(from, t.kind === "ref" ? [t.part] : []);
791
+ } else if (this.accept("CASCADE")) node.cascade = true;
792
+ else return node;
793
+ }
794
+ }
795
+
796
+ private domain(): DomainNode {
797
+ const name = this.qualifiedName("a domain name");
798
+ this.accept("AS");
799
+ const STOP = ["COLLATE", "DEFAULT", "CONSTRAINT", "NOT", "NULL", "CHECK"];
800
+ const node: DomainNode = { statement: "domain", name, type: this.typeName(), checks: [] };
801
+ for (;;) {
802
+ if (this.accept("COLLATE")) node.collate = this.expr(STOP);
803
+ else if (this.accept("DEFAULT")) node.default = this.bExpr(STOP);
804
+ else {
805
+ let cname: string | undefined;
806
+ if (this.accept("CONSTRAINT")) cname = this.nameTok("a constraint name").text;
807
+ if (this.acceptSeq("NOT", "NULL")) node.notNull = true;
808
+ else if (this.accept("NULL")) node.notNull = false;
809
+ else if (this.accept("CHECK")) {
810
+ const expr = this.checkedParens();
811
+ node.checks.push({ name: cname, expr, ...(this.acceptSeq("NOT", "VALID") ? { notValid: true } : {}) });
812
+ } else if (cname !== undefined) this.fail("expected NOT NULL, NULL or CHECK");
813
+ else return node;
814
+ }
815
+ }
816
+ }
817
+
818
+ private enumType(): EnumNode {
819
+ const name = this.qualifiedName("a type name");
820
+ this.expect("AS");
821
+ if (!this.accept("ENUM")) this.fail("expected ENUM (the type tag declares enum types; a domain has its own tag)");
822
+ const labels = this.parenList();
823
+ for (const l of labels) {
824
+ const sig = this.tokens.slice(l.from, l.to).filter((t) => t.kind !== "ws" && t.kind !== "comment");
825
+ if (sig.length !== 1 || (sig[0]!.kind !== "string" && sig[0]!.kind !== "ref")) this.fail("expected a string label", sig[0]);
826
+ }
827
+ return { statement: "enum", name, labels };
828
+ }
829
+
830
+ private table(persistence: TableNode["persistence"]): TableNode {
831
+ const ifNotExists = this.ifNotExists();
832
+ const node: TableNode = { statement: "table", persistence, ifNotExists, name: this.qualifiedName("a table name"), columns: [], constraints: [], like: [] };
833
+ if (this.accept("OF")) {
834
+ node.ofType = this.qualifiedName("a type name");
835
+ if (this.isPunct("(")) this.tableElements(node, false);
836
+ } else if (this.acceptSeq("PARTITION", "OF")) {
837
+ node.partitionOf = this.qualifiedName("a partitioned table");
838
+ if (this.isPunct("(")) this.tableElements(node, false);
839
+ node.partitionBound = this.partitionBound();
840
+ } else {
841
+ if (!this.isPunct("(")) this.fail("expected the column list (CREATE TABLE ... AS is not declared here)");
842
+ this.tableElements(node, true);
843
+ }
844
+ for (;;) {
845
+ if (this.accept("INHERITS")) {
846
+ this.expectPunct("(");
847
+ node.inherits = [];
848
+ do node.inherits.push(this.qualifiedName("a parent table"));
849
+ while (this.acceptPunct(","));
850
+ this.expectPunct(")");
851
+ } else if (this.acceptSeq("PARTITION", "BY")) {
852
+ const from = this.idx();
853
+ this.expect("RANGE", "LIST", "HASH");
854
+ if (this.isPunct(")", 1)) this.fail("expected a partition key", this.peek(1));
855
+ node.partitionBy = this.span(from, this.parenthesized().refs);
856
+ } else if (this.accept("USING")) node.using = this.nameTok("an access method").span;
857
+ else if (kw(this.peek(), "WITH") && this.isPunct("(", 1)) {
858
+ this.p++;
859
+ node.with = this.reloptions();
860
+ } else if (this.acceptSeq("WITHOUT", "OIDS")) continue;
861
+ else if (this.acceptSeq("ON", "COMMIT")) {
862
+ const from = this.idx();
863
+ if (!(this.acceptSeq("PRESERVE", "ROWS") || this.acceptSeq("DELETE", "ROWS") || this.accept("DROP"))) this.fail("expected PRESERVE ROWS, DELETE ROWS or DROP");
864
+ node.onCommit = this.span(from, []);
865
+ } else if (this.accept("TABLESPACE")) node.tablespace = this.nameTok("a tablespace").span;
866
+ else break;
867
+ }
868
+ return node;
869
+ }
870
+
871
+ /** `DEFAULT`, or `FOR VALUES IN (...)`, `FROM (...) TO (...)` or `WITH (MODULUS n, REMAINDER m)`. */
872
+ private partitionBound(): Span {
873
+ const from = this.idx();
874
+ if (this.accept("DEFAULT")) return this.span(from, []);
875
+ this.expect("FOR");
876
+ this.expect("VALUES");
877
+ const refs: number[] = [];
878
+ const values = () => {
879
+ if (this.isPunct("(") && this.isPunct(")", 1)) this.fail("expected a partition bound value", this.peek(1));
880
+ refs.push(...this.checkedParens().refs);
881
+ };
882
+ if (this.accept("IN")) values();
883
+ else if (this.accept("FROM")) {
884
+ values();
885
+ this.expect("TO");
886
+ values();
887
+ } else if (this.accept("WITH")) {
888
+ this.expectPunct("(");
889
+ for (const w of ["MODULUS", "REMAINDER"]) {
890
+ if (!this.accept(w)) this.fail(`expected ${w}`);
891
+ const t = this.next();
892
+ if (t.kind !== "number" && t.kind !== "ref") this.fail("expected a number", t);
893
+ if (w === "MODULUS") this.expectPunct(",");
894
+ }
895
+ this.expectPunct(")");
896
+ } else this.fail("expected IN, FROM or WITH");
897
+ return this.span(from, refs);
898
+ }
899
+
900
+ private index(): IndexNode {
901
+ const unique = this.accept("UNIQUE");
902
+ this.expect("INDEX");
903
+ const concurrently = this.accept("CONCURRENTLY");
904
+ const ifNotExists = this.ifNotExists();
905
+ let name: NameNode | undefined;
906
+ if (!(kw(this.peek(), "ON") && !ifNotExists)) {
907
+ // An index lives in its table's schema: CREATE INDEX takes an unqualified name.
908
+ const { text, span } = this.nameTok("an index name");
909
+ if (this.isPunct(".")) this.fail("expected ON (an index name is not schema-qualified; the index is created in its table's schema)");
910
+ name = { pieces: [text], span };
911
+ }
912
+ this.expect("ON");
913
+ const only = this.accept("ONLY");
914
+ const node: IndexNode = { statement: "index", unique, concurrently, ifNotExists, name, only, table: this.qualifiedName("a table name"), elements: [] };
915
+ if (this.accept("USING")) node.using = this.nameTok("an access method").text;
916
+ if (this.isPunct("(") && this.isPunct(")", 1)) this.fail("expected an index column or expression", this.peek(1));
917
+ for (const span of this.parenList()) {
918
+ const sig = this.tokens.slice(span.from, span.to).filter((t) => t.kind !== "ws" && t.kind !== "comment");
919
+ const first = sig[0];
920
+ // A column element is a bare name, then only opclass, collation and ordering words.
921
+ const column =
922
+ first && (first.kind === "ident" || first.kind === "qident") && sig.slice(1).every((t) => t.kind === "ident" || t.kind === "qident")
923
+ ? identValue(first)
924
+ : undefined;
925
+ node.elements.push({ span, ...(column !== undefined ? { column } : {}) });
926
+ }
927
+ for (;;) {
928
+ if (this.accept("INCLUDE")) node.include = this.parenthesized();
929
+ else if (this.acceptSeq("NULLS", "NOT", "DISTINCT")) node.nullsNotDistinct = true;
930
+ else if (this.acceptSeq("NULLS", "DISTINCT")) node.nullsNotDistinct = false;
931
+ else if (kw(this.peek(), "WITH") && this.isPunct("(", 1)) {
932
+ this.p++;
933
+ node.with = this.reloptions();
934
+ } else if (this.accept("TABLESPACE")) node.tablespace = this.nameTok("a tablespace").span;
935
+ else if (this.accept("WHERE")) node.where = this.checkedExpr([], false);
936
+ else return node;
937
+ }
938
+ }
939
+
940
+ private view(materialized: boolean, orReplace: boolean, temporary: boolean, recursive: boolean): ViewNode {
941
+ const ifNotExists = materialized ? this.ifNotExists() : false;
942
+ const node: ViewNode = {
943
+ statement: "view",
944
+ materialized,
945
+ orReplace,
946
+ temporary,
947
+ recursive,
948
+ ifNotExists,
949
+ name: this.qualifiedName("a view name"),
950
+ columnNames: [],
951
+ query: { from: 0, to: 0, refs: [] },
952
+ };
953
+ if (this.isPunct("(")) node.columnNames = this.nameList();
954
+ for (;;) {
955
+ if (materialized && this.accept("USING")) node.using = this.nameTok("an access method").span;
956
+ else if (kw(this.peek(), "WITH") && this.isPunct("(", 1)) {
957
+ this.p++;
958
+ node.with = this.reloptions();
959
+ } else if (materialized && this.accept("TABLESPACE")) node.tablespace = this.nameTok("a tablespace").span;
960
+ else break;
961
+ }
962
+ this.expect("AS");
963
+ const tail = materialized
964
+ ? ["WITH DATA", "WITH NO DATA"]
965
+ : ["WITH CHECK OPTION", "WITH CASCADED CHECK OPTION", "WITH LOCAL CHECK OPTION"];
966
+ node.query = this.expr(tail, false);
967
+ if (materialized) {
968
+ if (this.acceptSeq("WITH", "DATA")) node.withData = true;
969
+ else if (this.acceptSeq("WITH", "NO", "DATA")) node.withData = false;
970
+ } else if (kw(this.peek(), "WITH")) {
971
+ const from = this.idx();
972
+ this.p++;
973
+ this.accept("CASCADED", "LOCAL");
974
+ this.expect("CHECK");
975
+ this.expect("OPTION");
976
+ node.checkOption = this.span(from, []);
977
+ }
978
+ return node;
979
+ }
980
+
981
+ private sequence(persistence: SequenceNode["persistence"]): SequenceNode {
982
+ const node: SequenceNode = { statement: "sequence", persistence, ifNotExists: this.ifNotExists(), name: this.qualifiedName("a sequence name"), options: [] };
983
+ const STOP = ["AS", "INCREMENT", "MINVALUE", "MAXVALUE", "NO", "START", "RESTART", "CACHE", "CYCLE", "OWNED", "SEQUENCE", "LOGGED", "UNLOGGED"];
984
+ const value = () => {
985
+ const span = this.expr(STOP);
986
+ this.checkSpan(span);
987
+ return span;
988
+ };
989
+ for (;;) {
990
+ if (this.atEnd()) return node;
991
+ if (this.accept("AS")) node.options.push({ option: "AS", value: this.typeName() });
992
+ else if (this.accept("INCREMENT")) {
993
+ this.accept("BY");
994
+ node.options.push({ option: "INCREMENT", value: value() });
995
+ } else if (this.acceptSeq("NO", "MINVALUE") || this.acceptSeq("NO", "MAXVALUE") || this.acceptSeq("NO", "CYCLE")) {
996
+ node.options.push({ option: `NO ${this.tokens[this.idx(-1)]!.text.toUpperCase()}` });
997
+ } else if (this.accept("MINVALUE", "MAXVALUE", "CACHE")) {
998
+ node.options.push({ option: this.tokens[this.idx(-1)]!.text.toUpperCase(), value: value() });
999
+ } else if (this.accept("START")) {
1000
+ this.accept("WITH");
1001
+ node.options.push({ option: "START", value: value() });
1002
+ } else if (this.accept("CYCLE")) node.options.push({ option: "CYCLE" });
1003
+ else if (this.acceptSeq("OWNED", "BY")) {
1004
+ if (this.accept("NONE")) node.options.push({ option: "OWNED BY", value: this.span(this.idx(-1), []) });
1005
+ else node.options.push({ option: "OWNED BY", value: this.qualifiedName("a column").span });
1006
+ } else return node;
1007
+ }
1008
+ }
1009
+
1010
+ private comment(): CommentNode {
1011
+ this.expect("ON");
1012
+ let objectType: string;
1013
+ let on: NameNode | undefined;
1014
+ let target: NameNode;
1015
+ if (this.accept("CONSTRAINT")) {
1016
+ objectType = "CONSTRAINT";
1017
+ target = this.qualifiedName("a constraint name");
1018
+ this.expect("ON");
1019
+ if (this.accept("DOMAIN")) objectType = "DOMAIN CONSTRAINT";
1020
+ on = this.qualifiedName("a table name");
1021
+ } else {
1022
+ if (this.acceptSeq("MATERIALIZED", "VIEW")) objectType = "MATERIALIZED VIEW";
1023
+ else if (this.accept("TABLE", "COLUMN", "INDEX", "VIEW", "SEQUENCE", "TYPE", "DOMAIN", "SCHEMA", "EXTENSION")) {
1024
+ objectType = this.tokens[this.idx(-1)]!.text.toUpperCase();
1025
+ } else return this.fail("expected TABLE, COLUMN, INDEX, VIEW, MATERIALIZED VIEW, SEQUENCE, TYPE, DOMAIN, SCHEMA, EXTENSION or CONSTRAINT");
1026
+ target = this.qualifiedName("an object name");
1027
+ }
1028
+ this.expect("IS");
1029
+ const node: CommentNode = { statement: "comment", objectType, target, on };
1030
+ if (!this.accept("NULL")) {
1031
+ const t = this.peek();
1032
+ if (t?.kind !== "string" && t?.kind !== "ref") this.fail("expected a string or NULL");
1033
+ const from = this.idx();
1034
+ this.p++;
1035
+ node.text = this.span(from, t.kind === "ref" ? [t.part] : []);
1036
+ }
1037
+ return node;
1038
+ }
1039
+
1040
+ /** Statements separated by `;`, to the end. */
1041
+ parseMany(): StatementNode[] {
1042
+ const out: StatementNode[] = [];
1043
+ while (this.peek() !== undefined) {
1044
+ if (this.acceptPunct(";")) continue;
1045
+ out.push(this.parse());
1046
+ if (this.peek() !== undefined && !this.isPunct(";")) this.fail(`unexpected token after the ${describe(out[out.length - 1]!)}`);
1047
+ }
1048
+ if (out.length === 0) this.fail("expected a statement");
1049
+ return out;
1050
+ }
1051
+ }
1052
+
1053
+ const describe = (n: StatementNode): string =>
1054
+ n.statement === "comment" ? "COMMENT ON" : n.statement === "enum" ? "type definition" : `${n.statement} definition`;
1055
+
1056
+ /**
1057
+ * Parse a template: one CREATE, optionally followed by COMMENT ON statements,
1058
+ * separated by `;`. Throws {@link SqlSyntaxError} located in the template.
1059
+ */
1060
+ export function parseStatements(tokens: Token[]): StatementNode[] {
1061
+ return new PgParser(tokens).parseMany();
1062
+ }