okmodel 0.1.1 → 0.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (228) hide show
  1. package/README.md +727 -37
  2. package/dist/adapters/capabilities.d.ts +34 -0
  3. package/dist/adapters/pg/bunsql-extra.d.ts +17 -0
  4. package/dist/adapters/pg/bunsql.d.ts +60 -0
  5. package/dist/adapters/pg/call.d.ts +2 -12
  6. package/dist/adapters/pg/nodepostgres-extra.d.ts +18 -0
  7. package/dist/adapters/pg/nodepostgres.d.ts +57 -0
  8. package/dist/adapters/pg/postgres-extra.d.ts +50 -1
  9. package/dist/adapters/pg/postgresjs.d.ts +0 -4
  10. package/dist/adapters/pg/session.d.ts +94 -0
  11. package/dist/adapters/pg/watch.d.ts +18 -0
  12. package/dist/contracts/catalog/enum.d.ts +31 -4
  13. package/dist/contracts/catalog/extension.d.ts +61 -0
  14. package/dist/contracts/catalog/object.d.ts +1 -0
  15. package/dist/contracts/catalog/privilege.d.ts +64 -0
  16. package/dist/contracts/catalog/routine.d.ts +56 -0
  17. package/dist/contracts/catalog/types.d.ts +179 -18
  18. package/dist/contracts/catalog/view.d.ts +73 -0
  19. package/dist/contracts/connection.d.ts +13 -0
  20. package/dist/contracts/driver.d.ts +18 -5
  21. package/dist/contracts/error.d.ts +17 -1
  22. package/dist/contracts/generator.d.ts +63 -0
  23. package/dist/contracts/index.d.ts +2 -2
  24. package/dist/contracts/index.js +1 -1
  25. package/dist/contracts/internal.js +11 -9
  26. package/dist/contracts/location.d.ts +24 -0
  27. package/dist/contracts/rows.d.ts +15 -0
  28. package/dist/dialects/pg/archive-bind.d.ts +22 -0
  29. package/dist/dialects/pg/column.d.ts +129 -10
  30. package/dist/dialects/pg/compile.d.ts +1 -0
  31. package/dist/dialects/pg/custom.d.ts +6 -0
  32. package/dist/dialects/pg/ddl.d.ts +65 -1
  33. package/dist/dialects/pg/enum.d.ts +10 -8
  34. package/dist/dialects/pg/ext/citext.d.ts +14 -0
  35. package/dist/dialects/pg/ext/citext.js +11 -0
  36. package/dist/dialects/pg/ext/index.d.ts +52 -0
  37. package/dist/dialects/pg/ext/index.js +6 -0
  38. package/dist/dialects/pg/ext/pg-trgm.d.ts +53 -0
  39. package/dist/dialects/pg/ext/pg-trgm.js +42 -0
  40. package/dist/dialects/pg/filter-parse.d.ts +19 -0
  41. package/dist/dialects/pg/filters.d.ts +19 -0
  42. package/dist/dialects/pg/fn/index.d.ts +107 -0
  43. package/dist/dialects/pg/fn/index.js +175 -0
  44. package/dist/dialects/pg/fn/touch.d.ts +14 -0
  45. package/dist/dialects/pg/index.d.ts +11 -2
  46. package/dist/dialects/pg/index.js +243 -1062
  47. package/dist/dialects/pg/introspect.d.ts +10 -1
  48. package/dist/dialects/pg/keys.d.ts +19 -3
  49. package/dist/dialects/pg/model.d.ts +223 -2
  50. package/dist/dialects/pg/operator-fit.d.ts +86 -0
  51. package/dist/dialects/pg/operators.d.ts +46 -1
  52. package/dist/dialects/pg/ops/arr-append.d.ts +9 -0
  53. package/dist/dialects/pg/ops/arr-ns.d.ts +7 -0
  54. package/dist/dialects/pg/ops/arr-remove.d.ts +9 -0
  55. package/dist/dialects/pg/ops/containedBy.d.ts +9 -0
  56. package/dist/dialects/pg/ops/contains.d.ts +8 -4
  57. package/dist/dialects/pg/ops/hasAnyKey.d.ts +8 -0
  58. package/dist/dialects/pg/ops/hasKey.d.ts +8 -0
  59. package/dist/dialects/pg/ops/json-ns.d.ts +6 -0
  60. package/dist/dialects/pg/ops/json-set.d.ts +12 -0
  61. package/dist/dialects/pg/ops/matches.d.ts +16 -0
  62. package/dist/dialects/pg/ops/overlaps.d.ts +9 -0
  63. package/dist/dialects/pg/ops/path.d.ts +13 -0
  64. package/dist/dialects/pg/preset.d.ts +76 -0
  65. package/dist/dialects/pg/relations.d.ts +59 -2
  66. package/dist/dialects/pg/role/check.d.ts +45 -0
  67. package/dist/dialects/pg/role/index.d.ts +50 -0
  68. package/dist/dialects/pg/role/sql.d.ts +44 -0
  69. package/dist/dialects/pg/schema.d.ts +109 -5
  70. package/dist/dialects/pg/table.d.ts +137 -11
  71. package/dist/dialects/pg/temporal.d.ts +9 -7
  72. package/dist/dialects/pg/tenancy.d.ts +103 -0
  73. package/dist/dialects/pg/through.d.ts +21 -0
  74. package/dist/dialects/pg/trait.d.ts +141 -0
  75. package/dist/dialects/pg/view/client.d.ts +30 -0
  76. package/dist/dialects/pg/view/depend.d.ts +35 -0
  77. package/dist/dialects/pg/view/index.d.ts +114 -0
  78. package/dist/dialects/pg/view/index.js +289 -0
  79. package/dist/dialects/pg/view/scratch.d.ts +21 -0
  80. package/dist/dialects/pg/where.d.ts +37 -0
  81. package/dist/runtime/aggregate.d.ts +25 -0
  82. package/dist/runtime/archive-handle.d.ts +18 -0
  83. package/dist/runtime/archive-rules.d.ts +12 -0
  84. package/dist/runtime/archive.d.ts +73 -0
  85. package/dist/runtime/batch.d.ts +20 -0
  86. package/dist/runtime/client.d.ts +114 -5
  87. package/dist/runtime/conflict.d.ts +2 -1
  88. package/dist/runtime/exposure.d.ts +27 -0
  89. package/dist/runtime/hookm.d.ts +39 -0
  90. package/dist/runtime/ids/index.d.ts +11 -0
  91. package/dist/runtime/ids/index.js +193 -0
  92. package/dist/runtime/ids/okid-extended.d.ts +19 -0
  93. package/dist/runtime/ids/okid-generator.d.ts +21 -0
  94. package/dist/runtime/ids/okid-shared.d.ts +89 -0
  95. package/dist/runtime/ids/okid.d.ts +24 -0
  96. package/dist/runtime/ids/uuid.d.ts +21 -0
  97. package/dist/runtime/lock.d.ts +22 -0
  98. package/dist/runtime/operator-sql.d.ts +8 -0
  99. package/dist/runtime/page.d.ts +25 -0
  100. package/dist/runtime/pg/bun.d.ts +30 -0
  101. package/dist/runtime/pg/bun.js +52 -0
  102. package/dist/runtime/pg/pg.d.ts +29 -0
  103. package/dist/runtime/pg/pg.js +52 -0
  104. package/dist/runtime/pg/pglite.js +16 -17
  105. package/dist/runtime/pg/postgresjs.js +14 -24
  106. package/dist/runtime/plan.d.ts +146 -7
  107. package/dist/runtime/preset-stack.d.ts +17 -0
  108. package/dist/runtime/presets.d.ts +48 -0
  109. package/dist/runtime/read-stream.d.ts +26 -0
  110. package/dist/runtime/safety/index.d.ts +159 -0
  111. package/dist/runtime/safety/index.js +294 -0
  112. package/dist/runtime/safety-hook.d.ts +42 -0
  113. package/dist/runtime/server-check.d.ts +34 -0
  114. package/dist/runtime/tenancy/index.d.ts +37 -0
  115. package/dist/runtime/tenancy/index.js +368 -0
  116. package/dist/runtime/trait-read.d.ts +30 -0
  117. package/dist/runtime/traits/index.d.ts +133 -0
  118. package/dist/runtime/traits/index.js +646 -0
  119. package/dist/runtime/transaction.d.ts +19 -0
  120. package/dist/runtime/tx.d.ts +22 -7
  121. package/dist/runtime/types.d.ts +376 -27
  122. package/dist/runtime/validate/bind.d.ts +11 -0
  123. package/dist/runtime/validate/closed.d.ts +16 -0
  124. package/dist/runtime/validate/engine.d.ts +41 -0
  125. package/dist/runtime/validate/hook.d.ts +17 -0
  126. package/dist/runtime/validate/index.d.ts +21 -0
  127. package/dist/runtime/validate/index.js +175 -0
  128. package/dist/runtime/validate/load.d.ts +13 -0
  129. package/dist/runtime/validate/places.d.ts +41 -0
  130. package/dist/runtime/validate/rules.d.ts +108 -0
  131. package/dist/runtime/validate/surface.d.ts +102 -0
  132. package/dist/runtime/write.d.ts +30 -5
  133. package/dist/shared/01yr20s5.js +149 -0
  134. package/dist/shared/0jc3ffzf.js +154 -0
  135. package/dist/shared/0v1g424p.js +26 -0
  136. package/dist/shared/1g0drakv.js +225 -0
  137. package/dist/shared/{kprcwaha.js → 1tfdfvhh.js} +5 -3
  138. package/dist/shared/{05w44d8g.js → 2ssqrv66.js} +767 -715
  139. package/dist/shared/3ekj9x92.js +210 -0
  140. package/dist/shared/49ypnfwt.js +1122 -0
  141. package/dist/shared/4e4c6vq2.js +62 -0
  142. package/dist/shared/4m9fn52z.js +70 -0
  143. package/dist/shared/{ycwz42az.js → 52szzakm.js} +6 -26
  144. package/dist/shared/5nmdenb6.js +1229 -0
  145. package/dist/shared/672t5vym.js +12 -0
  146. package/dist/shared/6bazvqwm.js +86 -0
  147. package/dist/shared/6w5j844a.js +201 -0
  148. package/dist/shared/{fgqgsb5z.js → 75xkjv0t.js} +2 -2
  149. package/dist/shared/7fvtrkwr.js +84 -0
  150. package/dist/shared/7m88x3e9.js +45 -0
  151. package/dist/shared/{mtkwv8wx.js → 7p2wbz7f.js} +1 -1
  152. package/dist/shared/83eaefwr.js +10 -0
  153. package/dist/shared/94ez8kzh.js +19 -0
  154. package/dist/shared/96ps4g1z.js +32 -0
  155. package/dist/shared/{xqbhg6cn.js → 999ade2q.js} +95 -10
  156. package/dist/shared/9m80mkac.js +158 -0
  157. package/dist/shared/9x25fxhc.js +150 -0
  158. package/dist/shared/a5sxz52y.js +13 -0
  159. package/dist/shared/axhk06q1.js +156 -0
  160. package/dist/shared/{dynq16vb.js → b066g80h.js} +8 -6
  161. package/dist/shared/bqha5cg6.js +229 -0
  162. package/dist/shared/bryqk9k9.js +31 -0
  163. package/dist/shared/c8aghh05.js +442 -0
  164. package/dist/shared/c9z5g0fm.js +309 -0
  165. package/dist/shared/{m3ypagh5.js → dbjej1tw.js} +124 -15
  166. package/dist/shared/dyj86cmj.js +69 -0
  167. package/dist/shared/e6wg00wd.js +164 -0
  168. package/dist/shared/{hadrfb9h.js → edwqqryd.js} +17 -14
  169. package/dist/shared/{qk3hxfja.js → fptpmvxp.js} +5 -5
  170. package/dist/shared/fs0ex00p.js +76 -0
  171. package/dist/shared/{jjb7yht9.js → g4f5kcx9.js} +3 -3
  172. package/dist/shared/gjthds9j.js +48 -0
  173. package/dist/shared/hcmdtwgh.js +102 -0
  174. package/dist/shared/{g5fhqmwe.js → jkc6ws1p.js} +6 -56
  175. package/dist/shared/{yd1kzwn2.js → jns2wx4t.js} +55 -12
  176. package/dist/shared/k34e0xf2.js +450 -0
  177. package/dist/shared/k3ted12y.js +33 -0
  178. package/dist/shared/k7dwkhvq.js +31 -0
  179. package/dist/shared/{8b04d28c.js → kgnc8grt.js} +2 -2
  180. package/dist/shared/{hd293j9g.js → kyxb62mc.js} +14 -2
  181. package/dist/shared/m78s7898.js +376 -0
  182. package/dist/shared/m9tv7xn7.js +404 -0
  183. package/dist/shared/meck53jv.js +99 -0
  184. package/dist/shared/mt5wswjz.js +90 -0
  185. package/dist/shared/n0dgs0pb.js +75 -0
  186. package/dist/shared/n442h54c.js +14 -0
  187. package/dist/shared/n4jqhpqz.js +27 -0
  188. package/dist/shared/n7mcc1gk.js +132 -0
  189. package/dist/shared/ne02ng5c.js +68 -0
  190. package/dist/shared/{mkjmqjv4.js → nfzc5z0w.js} +2 -104
  191. package/dist/shared/nsva2a6b.js +42 -0
  192. package/dist/shared/p24x2334.js +195 -0
  193. package/dist/shared/qbxzvwwc.js +88 -0
  194. package/dist/shared/{w8samvk1.js → qybh48nd.js} +1 -1
  195. package/dist/shared/r6nwkxnt.js +86 -0
  196. package/dist/shared/{xy79j5hq.js → rrstp3kb.js} +25 -36
  197. package/dist/shared/rwmrejjz.js +26 -0
  198. package/dist/shared/{zhc5vmgf.js → s6gqfn5j.js} +2 -2
  199. package/dist/shared/{523ft3e8.js → scwxrpx2.js} +7 -5
  200. package/dist/shared/{j5cn2963.js → t4tbsy9h.js} +13 -64
  201. package/dist/shared/{y9m15dfv.js → t616ynfn.js} +544 -32
  202. package/dist/shared/{ngk8gj61.js → tbszx8mz.js} +15 -1
  203. package/dist/shared/th14ygv2.js +69 -0
  204. package/dist/shared/tmbdywx0.js +178 -0
  205. package/dist/shared/ty3v3hfk.js +64 -0
  206. package/dist/shared/wekze34d.js +246 -0
  207. package/dist/shared/x6wysh83.js +1132 -0
  208. package/dist/shared/{rgs0st28.js → xrfnq5k8.js} +237 -434
  209. package/dist/shared/{x5x59srr.js → xva8v7qk.js} +416 -83
  210. package/dist/shared/{dkn3y60a.js → xw1d69vd.js} +76 -112
  211. package/dist/shared/y005b761.js +112 -0
  212. package/dist/shared/ydaz1sv3.js +55 -0
  213. package/dist/shared/{p0cbr3g2.js → zwmqxb0g.js} +1 -1
  214. package/dist/tooling/cli.js +40 -12
  215. package/dist/tooling/migrate/apply.d.ts +16 -0
  216. package/dist/tooling/migrate/commands.d.ts +12 -1
  217. package/dist/tooling/migrate/config.d.ts +8 -0
  218. package/dist/tooling/migrate/doctor.d.ts +25 -0
  219. package/dist/tooling/migrate/drift.d.ts +19 -0
  220. package/dist/tooling/migrate/engine.d.ts +36 -0
  221. package/dist/tooling/migrate/ext.d.ts +17 -0
  222. package/dist/tooling/migrate/extensions.d.ts +51 -0
  223. package/dist/tooling/migrate/managed.d.ts +17 -0
  224. package/dist/tooling/migrate/plan.d.ts +14 -1
  225. package/dist/tooling/migrate/project.d.ts +25 -1
  226. package/dist/tooling/migrate/type-name.d.ts +19 -0
  227. package/package.json +61 -4
  228. package/dist/shared/gk7cs7sp.js +0 -566
@@ -0,0 +1,158 @@
1
+ import {
2
+ ColumnBuilder2
3
+ } from "./c9z5g0fm.js";
4
+ import {
5
+ definition
6
+ } from "./tmbdywx0.js";
7
+ import {
8
+ OkmError2
9
+ } from "./52szzakm.js";
10
+
11
+ // src/runtime/validate/places.ts
12
+ function assertValidation(schema) {
13
+ const record = schema;
14
+ const tables = record.tables;
15
+ if (tables === undefined)
16
+ return;
17
+ for (const item of tables)
18
+ validationGate(record.validation, item);
19
+ }
20
+ function validationGate(schemaFlag, table) {
21
+ return buildGate(schemaFlag, table);
22
+ }
23
+ function writeWouldValidate(schemaFlag, table, options) {
24
+ if (options.validate === false)
25
+ return false;
26
+ const setting = tableSetting(readSetting(schemaFlag, "schema()"), table.options);
27
+ if (setting.enabled)
28
+ return true;
29
+ const section = table.options;
30
+ if (section?.validate !== undefined)
31
+ return true;
32
+ for (const builder of Object.values(table.columns)) {
33
+ if (builder instanceof ColumnBuilder2 && builder.state.validate !== undefined)
34
+ return true;
35
+ }
36
+ return false;
37
+ }
38
+ function buildGate(schemaFlag, table) {
39
+ const setting = tableSetting(readSetting(schemaFlag, "schema()"), table.options);
40
+ const section = readSection(table.name, table.options);
41
+ if (setting.style === "inline" && section.rowPresent)
42
+ conflict(table.name, "$row");
43
+ const fields = {};
44
+ const required = [];
45
+ const notNull = [];
46
+ const pick = {};
47
+ const names = new Set;
48
+ for (const [field, builder] of Object.entries(table.columns)) {
49
+ if (!(builder instanceof ColumnBuilder2))
50
+ continue;
51
+ names.add(field);
52
+ const inline = builder.state.validate?.rules;
53
+ const named = Object.hasOwn(section.fields, field) ? section.fields[field] : undefined;
54
+ const rules = takeRules(table.name, field, inline, named, setting.style);
55
+ if (rules !== undefined)
56
+ fields[field] = rules;
57
+ const state = builder.state;
58
+ const writable = state.guarded !== true && state.omitWrite !== true && state.generated === undefined;
59
+ if (setting.enabled && writable) {
60
+ if (!state.nullable && state.hasDefault !== true)
61
+ required.push(field);
62
+ if (!state.nullable)
63
+ notNull.push(field);
64
+ if (state.picklist !== undefined)
65
+ pick[field] = state.picklist.values;
66
+ }
67
+ }
68
+ for (const field of Object.keys(section.fields)) {
69
+ if (!names.has(field))
70
+ definition(`Table ${table.name} validate.${field} is not a column.`);
71
+ }
72
+ if (!setting.enabled)
73
+ return;
74
+ return { onRead: setting.onRead, row: section.row, fields, required, notNull, pick };
75
+ }
76
+ function readSetting(value, where) {
77
+ if (value === undefined || value === false)
78
+ return { enabled: false, onRead: false, style: undefined };
79
+ if (value === true)
80
+ return { enabled: true, onRead: false, style: undefined };
81
+ if (isPlain(value)) {
82
+ return {
83
+ enabled: value.enabled === undefined ? true : value.enabled === true,
84
+ onRead: value.onRead === true,
85
+ style: readStyle(value.style)
86
+ };
87
+ }
88
+ definition(`${where} validation must be a boolean or { enabled, onRead, style }.`);
89
+ }
90
+ function tableSetting(schemaSetting, options) {
91
+ const value = options === undefined ? undefined : options.validation;
92
+ if (value === undefined)
93
+ return schemaSetting;
94
+ if (value === true)
95
+ return { enabled: true, onRead: schemaSetting.onRead, style: schemaSetting.style };
96
+ if (value === false)
97
+ return { enabled: false, onRead: schemaSetting.onRead, style: schemaSetting.style };
98
+ if (isPlain(value)) {
99
+ return {
100
+ enabled: value.enabled === undefined ? true : value.enabled === true,
101
+ onRead: value.onRead === undefined ? schemaSetting.onRead : value.onRead === true,
102
+ style: value.style === undefined ? schemaSetting.style : readStyle(value.style)
103
+ };
104
+ }
105
+ definition("table() validation must be a boolean or { enabled, onRead, style }.");
106
+ }
107
+ function readStyle(value) {
108
+ if (value === undefined)
109
+ return;
110
+ if (value === "inline" || value === "section")
111
+ return value;
112
+ definition("validation.style must be inline or section.");
113
+ }
114
+ function readSection(table, options) {
115
+ const validate = options === undefined ? undefined : options.validate;
116
+ if (validate === undefined)
117
+ return { fields: {}, row: [], rowPresent: false };
118
+ if (!isPlain(validate)) {
119
+ definition(`Table ${table} option validate must be { field: rules, $row: rules }.`);
120
+ }
121
+ const fields = {};
122
+ let row = [];
123
+ let rowPresent = false;
124
+ for (const key of Object.keys(validate)) {
125
+ const item = validate[key];
126
+ if (!Array.isArray(item))
127
+ definition(`Table ${table} validate.${key} must be a list of rules.`);
128
+ if (key === "$row") {
129
+ row = item;
130
+ rowPresent = true;
131
+ } else
132
+ fields[key] = item;
133
+ }
134
+ return { fields, row, rowPresent };
135
+ }
136
+ function takeRules(table, field, inline, section, style) {
137
+ const hasInline = inline !== undefined;
138
+ const hasSection = section !== undefined;
139
+ if (hasInline && hasSection || style === "inline" && hasSection || style === "section" && hasInline) {
140
+ conflict(table, field);
141
+ }
142
+ if (hasInline && inline.length > 0)
143
+ return inline;
144
+ if (hasSection && section.length > 0)
145
+ return section;
146
+ return;
147
+ }
148
+ function conflict(table, field) {
149
+ throw new OkmError2("OKM1030", `Field ${table}.${field} is validated in two places. Keep the column rules or the validate section.`, {
150
+ ...field === "$row" ? {} : { columns: [field] },
151
+ fix: { summary: "Keep one validation for the field." }
152
+ });
153
+ }
154
+ function isPlain(value) {
155
+ return typeof value === "object" && value !== null && !Array.isArray(value);
156
+ }
157
+
158
+ export { assertValidation, validationGate, writeWouldValidate };
@@ -0,0 +1,150 @@
1
+ import {
2
+ staticNamespace2,
3
+ assertNamespace2,
4
+ normaliseEdges,
5
+ assertProvenance
6
+ } from "./t4tbsy9h.js";
7
+ import {
8
+ assertIdentifier2
9
+ } from "./nfzc5z0w.js";
10
+ import {
11
+ catalogError2
12
+ } from "./52szzakm.js";
13
+
14
+ // src/contracts/catalog/routine.ts
15
+ var VOLATILITY = new Set(["volatile", "stable", "immutable"]);
16
+ var SECURITY = new Set(["invoker", "definer"]);
17
+ var TIMING = new Set(["before", "after", "instead"]);
18
+ var LEVEL = new Set(["row", "statement"]);
19
+ var EVENT_ORDER = ["insert", "update", "delete", "truncate"];
20
+ var TYPE_TEXT = /^[A-Za-z][A-Za-z0-9_ ]*(\(\d+(,\s*\d+)?\))?(\[\])*$/;
21
+ function functionObject(input) {
22
+ assertIdentifier2(input.name, "function");
23
+ const namespace = input.namespace ?? staticNamespace2("public");
24
+ assertNamespace2(namespace);
25
+ assertProvenance(input.provenance);
26
+ if (input.language !== "sql" && input.language !== "plpgsql") {
27
+ catalogError2("OKM1020", `Function ${input.name} language must be sql or plpgsql.`);
28
+ }
29
+ const volatility = input.volatility ?? "volatile";
30
+ if (!VOLATILITY.has(volatility)) {
31
+ catalogError2("OKM1020", `Function ${input.name} volatility ${volatility} is not supported.`);
32
+ }
33
+ const security = input.security ?? "invoker";
34
+ if (!SECURITY.has(security)) {
35
+ catalogError2("OKM1020", `Function ${input.name} security ${security} is not supported.`);
36
+ }
37
+ assertTypeName(input.returns, `function ${input.name} return type`);
38
+ const args = (input.arguments ?? []).map((argument) => readArgument(input.name, argument));
39
+ if (input.body.length === 0) {
40
+ catalogError2("OKM1020", `Function ${input.name} needs a body.`);
41
+ }
42
+ const atomic = input.atomic === true;
43
+ if (atomic && input.language !== "sql") {
44
+ catalogError2("OKM1020", `Function ${input.name} BEGIN ATOMIC needs language sql.`);
45
+ }
46
+ if (input.searchPath !== undefined && input.searchPath.trim().length === 0) {
47
+ catalogError2("OKM1020", `Function ${input.name} search_path is empty.`);
48
+ }
49
+ const definition = {
50
+ arguments: args,
51
+ returns: input.returns,
52
+ language: input.language,
53
+ volatility,
54
+ security,
55
+ body: input.body,
56
+ ...input.searchPath !== undefined ? { searchPath: input.searchPath } : {},
57
+ ...atomic ? { atomic: true } : {}
58
+ };
59
+ return {
60
+ kind: "function",
61
+ identity: {
62
+ kind: "function",
63
+ namespace,
64
+ name: input.name,
65
+ argTypes: args.map((arg) => arg.type)
66
+ },
67
+ owner: input.owner ?? "managed",
68
+ definition,
69
+ dependencies: normaliseEdges(input.dependencies ?? []),
70
+ provenance: input.provenance
71
+ };
72
+ }
73
+ function triggerObject(input) {
74
+ assertIdentifier2(input.name, "trigger");
75
+ assertNamespace2(input.parent.namespace);
76
+ assertIdentifier2(input.parent.name, "trigger table");
77
+ assertProvenance(input.provenance);
78
+ if (!TIMING.has(input.timing)) {
79
+ catalogError2("OKM1020", `Trigger ${input.name} timing ${input.timing} is not supported.`);
80
+ }
81
+ if (!LEVEL.has(input.level)) {
82
+ catalogError2("OKM1020", `Trigger ${input.name} level ${input.level} is not supported.`);
83
+ }
84
+ const events = EVENT_ORDER.filter((event) => input.events.includes(event));
85
+ if (events.length === 0) {
86
+ catalogError2("OKM1020", `Trigger ${input.name} needs an event.`);
87
+ }
88
+ const updateOf = input.updateOf === undefined ? undefined : [...input.updateOf];
89
+ if (updateOf !== undefined) {
90
+ if (!events.includes("update")) {
91
+ catalogError2("OKM1020", `Trigger ${input.name} lists UPDATE OF columns without an update event.`);
92
+ }
93
+ if (input.level !== "row") {
94
+ catalogError2("OKM1020", `Trigger ${input.name} UPDATE OF columns need level row.`);
95
+ }
96
+ for (const column of updateOf)
97
+ assertIdentifier2(column, "trigger column");
98
+ }
99
+ assertIdentifier2(input.calls.name, "trigger function");
100
+ assertNamespace2(input.calls.namespace);
101
+ for (const typeName of input.calls.argTypes)
102
+ assertTypeName(typeName, `trigger ${input.name}`);
103
+ const edges = [
104
+ { kind: "table", namespace: input.parent.namespace, name: input.parent.name },
105
+ {
106
+ kind: "function",
107
+ namespace: input.calls.namespace,
108
+ name: input.calls.name,
109
+ argTypes: input.calls.argTypes
110
+ },
111
+ ...(updateOf ?? []).map((column) => ({
112
+ kind: "column",
113
+ parent: input.parent,
114
+ name: column
115
+ })),
116
+ ...input.dependencies ?? []
117
+ ];
118
+ const definition = {
119
+ timing: input.timing,
120
+ events,
121
+ level: input.level,
122
+ calls: {
123
+ namespace: input.calls.namespace,
124
+ name: input.calls.name,
125
+ argTypes: [...input.calls.argTypes]
126
+ },
127
+ ...updateOf !== undefined && updateOf.length > 0 ? { updateOf } : {},
128
+ ...input.when !== undefined && input.when.length > 0 ? { when: input.when } : {}
129
+ };
130
+ return {
131
+ kind: "trigger",
132
+ identity: { kind: "trigger", parent: input.parent, name: input.name },
133
+ owner: input.owner ?? "managed",
134
+ definition,
135
+ dependencies: normaliseEdges(edges),
136
+ provenance: input.provenance
137
+ };
138
+ }
139
+ function readArgument(fn, argument) {
140
+ assertIdentifier2(argument.name, `function ${fn} argument`);
141
+ assertTypeName(argument.type, `function ${fn} argument ${argument.name}`);
142
+ return { name: argument.name, type: argument.type };
143
+ }
144
+ function assertTypeName(typeName, role) {
145
+ if (!TYPE_TEXT.test(typeName)) {
146
+ catalogError2("OKM1020", `${role} ${typeName} is not a type name.`);
147
+ }
148
+ }
149
+
150
+ export { functionObject, triggerObject };
@@ -0,0 +1,13 @@
1
+ // src/runtime/safety-hook.ts
2
+ var hook;
3
+ function safetyInstalled() {
4
+ return hook !== undefined;
5
+ }
6
+ function installSafetyHook(next) {
7
+ hook = next;
8
+ }
9
+ function runSafety(contributions, hatches) {
10
+ hook?.(contributions, hatches);
11
+ }
12
+
13
+ export { safetyInstalled, installSafetyHook, runSafety };
@@ -0,0 +1,156 @@
1
+ import {
2
+ assertOperatorFits,
3
+ sqlType,
4
+ assertNoControl,
5
+ assertBoundText,
6
+ assertRegconfig,
7
+ textArray
8
+ } from "./n7mcc1gk.js";
9
+ import {
10
+ installOperatorSql,
11
+ quote,
12
+ isRecord,
13
+ fail
14
+ } from "./xrfnq5k8.js";
15
+ import {
16
+ isOperator,
17
+ operatorName,
18
+ operatorValue
19
+ } from "./cn0n68ft.js";
20
+
21
+ // src/runtime/operator-sql.ts
22
+ function emitStructured(column, ref, name, value, sink) {
23
+ if (name === "contains" || name === "containedBy" || name === "overlaps") {
24
+ emitContainment(column, ref, name, value, sink);
25
+ return;
26
+ }
27
+ if (name === "hasKey" || name === "hasAnyKey") {
28
+ emitJsonKey(column, ref, name, value, sink);
29
+ return;
30
+ }
31
+ if (name === "path") {
32
+ emitPath(column, ref, value, sink);
33
+ return;
34
+ }
35
+ if (name === "matches") {
36
+ emitMatches(column, ref, value, sink);
37
+ return;
38
+ }
39
+ if (name === "similar" || name === "wordSimilar") {
40
+ emitTrigram(column, ref, name, value, sink);
41
+ return;
42
+ }
43
+ assertOperatorFits(column, name);
44
+ fail("OKM1121", `${name} is not a value operator on ${column.field}. Use has, none, or every on a relation.`);
45
+ }
46
+ function emitContainment(column, ref, name, value, sink) {
47
+ assertOperatorFits(column, name);
48
+ const op = name === "contains" ? " @> " : name === "containedBy" ? " <@ " : " && ";
49
+ sink.text(ref);
50
+ sink.text(op);
51
+ sink.param(column.encode(value));
52
+ sink.text("::");
53
+ sink.text(sqlType(column.dataType, column));
54
+ }
55
+ function emitJsonKey(column, ref, name, value, sink) {
56
+ assertOperatorFits(column, name);
57
+ if (name === "hasKey") {
58
+ if (typeof value !== "string")
59
+ fail("OKM1121", `hasKey on ${column.field} needs a key.`);
60
+ assertBoundText(value, `key on ${column.field}`);
61
+ sink.text("jsonb_exists(");
62
+ sink.text(ref);
63
+ sink.text(", ");
64
+ sink.param(value);
65
+ sink.text(")");
66
+ return;
67
+ }
68
+ if (!Array.isArray(value) || value.some((item) => typeof item !== "string")) {
69
+ fail("OKM1121", `hasAnyKey on ${column.field} needs a list of keys.`);
70
+ }
71
+ sink.text("jsonb_exists_any(");
72
+ sink.text(ref);
73
+ sink.text(", ");
74
+ sink.param(textArray(value, `key on ${column.field}`));
75
+ sink.text("::text[])");
76
+ }
77
+ function emitPath(column, ref, value, sink) {
78
+ assertOperatorFits(column, "path");
79
+ if (!isRecord(value) || !Array.isArray(value.segments) || !isOperator(value.op)) {
80
+ fail("OKM1121", `path on ${column.field} needs segments and a comparison.`);
81
+ }
82
+ const segments = value.segments;
83
+ if (segments.length === 0 || segments.some((item) => typeof item !== "string")) {
84
+ fail("OKM1121", `path on ${column.field} needs a list of segments.`);
85
+ }
86
+ const opName = operatorName(value.op);
87
+ if (opName !== "eq" && opName !== "lt" && opName !== "lte" && opName !== "gt" && opName !== "gte") {
88
+ fail("OKM1121", `path on ${column.field} compares with eq, lt, lte, gt, or gte.`);
89
+ }
90
+ const operand = operatorValue(value.op);
91
+ const cast = pathCast(column, operand);
92
+ const sql = opName === "eq" ? " = " : opName === "lt" ? " < " : opName === "lte" ? " <= " : opName === "gt" ? " > " : " >= ";
93
+ sink.text("(");
94
+ sink.text(ref);
95
+ sink.text(" #>> ");
96
+ sink.param(textArray(segments, `path on ${column.field}`));
97
+ sink.text("::text[])::");
98
+ sink.text(cast);
99
+ sink.text(sql);
100
+ sink.param(pathParam(operand));
101
+ }
102
+ function pathCast(column, operand) {
103
+ if (typeof operand === "number")
104
+ return "numeric";
105
+ if (typeof operand === "boolean")
106
+ return "boolean";
107
+ if (typeof operand === "string")
108
+ return "text";
109
+ fail("OKM1121", `path on ${column.field} compares a string, number, or boolean.`);
110
+ }
111
+ function pathParam(operand) {
112
+ if (typeof operand === "number")
113
+ return String(operand);
114
+ if (typeof operand === "boolean")
115
+ return operand ? "true" : "false";
116
+ if (typeof operand === "string")
117
+ return operand;
118
+ return "";
119
+ }
120
+ function emitMatches(column, ref, value, sink) {
121
+ assertOperatorFits(column, "matches");
122
+ if (!isRecord(value) || typeof value.query !== "string") {
123
+ fail("OKM1121", `matches on ${column.field} needs search text.`);
124
+ }
125
+ assertNoControl(value.query, `matches on ${column.field}`);
126
+ const mode = value.mode ?? "websearch";
127
+ const fn = mode === "websearch" ? "websearch_to_tsquery" : mode === "plain" ? "plainto_tsquery" : mode === "phrase" ? "phraseto_tsquery" : undefined;
128
+ if (fn === undefined) {
129
+ fail("OKM1121", `matches on ${column.field} mode must be websearch, plain, or phrase.`);
130
+ }
131
+ sink.text(ref);
132
+ sink.text(" @@ ");
133
+ sink.text(fn);
134
+ sink.text("(");
135
+ if (typeof value.config === "string") {
136
+ assertRegconfig(value.config);
137
+ sink.param(value.config);
138
+ sink.text("::regconfig, ");
139
+ }
140
+ sink.param(value.query);
141
+ sink.text(")");
142
+ }
143
+ function emitTrigram(column, ref, name, value, sink) {
144
+ if (!isRecord(value) || typeof value.query !== "string" || typeof value.schema !== "string") {
145
+ fail("OKM1121", `${name} on ${column.field} needs query text.`);
146
+ }
147
+ if (!/^[A-Za-z_][A-Za-z0-9_]*$/.test(value.schema)) {
148
+ fail("OKM1121", `${name} on ${column.field} needs an extension schema name.`);
149
+ }
150
+ sink.text(ref);
151
+ sink.text(" operator(");
152
+ sink.text(quote(value.schema));
153
+ sink.text(name === "similar" ? ".%) " : ".<%) ");
154
+ sink.param(value.query);
155
+ }
156
+ installOperatorSql(emitStructured);
@@ -2,10 +2,10 @@ import {
2
2
  DriverError2,
3
3
  outcomeUnknown2,
4
4
  mapDriverError2
5
- } from "./hd293j9g.js";
5
+ } from "./kyxb62mc.js";
6
6
  import {
7
- isConnectionFailure
8
- } from "./ngk8gj61.js";
7
+ isConnectionLost
8
+ } from "./tbszx8mz.js";
9
9
 
10
10
  // src/adapters/pg/batch.ts
11
11
  var savepointIds = 0;
@@ -21,13 +21,14 @@ async function transaction(session, statements, watch) {
21
21
  try {
22
22
  await control(session, "COMMIT", watch);
23
23
  } catch (error) {
24
- if (isConnectionFailure(error))
24
+ if (isConnectionLost(error))
25
25
  throw outcomeUnknown2(error);
26
26
  throw stamp(error, null);
27
27
  }
28
28
  return results;
29
29
  } catch (error) {
30
- await rollback(session);
30
+ if (!isConnectionLost(error))
31
+ await rollback(session);
31
32
  throw error;
32
33
  }
33
34
  }
@@ -40,7 +41,8 @@ async function savepoint(session, statements, watch) {
40
41
  await control(session, `RELEASE SAVEPOINT ${name}`, watch);
41
42
  return results;
42
43
  } catch (error) {
43
- await rollback(session, `ROLLBACK TO SAVEPOINT ${name}`);
44
+ if (!isConnectionLost(error))
45
+ await rollback(session, `ROLLBACK TO SAVEPOINT ${name}`);
44
46
  throw error;
45
47
  }
46
48
  }