@reventlessdev/reventless-postgres 3.0.0-alpha.15 → 3.0.0-alpha.151
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.
- package/CHANGELOG.md +1093 -0
- package/README.md +83 -0
- package/lib/bs/.compiler.log +2 -2
- package/lib/bs/ReventlessPostgres.cmt +0 -0
- package/lib/bs/ReventlessPostgres.mlmap +0 -2
- package/lib/bs/compiler-info.json +4 -4
- package/lib/bs/src/DcbEventLogStorage_Postgres-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/DcbEventLogStorage_Postgres-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/DcbEventLogStorage_Postgres.ast +0 -0
- package/lib/bs/src/DcbEventLogStorage_Postgres.res +1 -1
- package/lib/bs/src/DcbEventLogStorage_Postgres_Ops-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/DcbEventLogStorage_Postgres_Ops-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/DcbEventLogStorage_Postgres_Ops.ast +0 -0
- package/lib/bs/src/DcbEventLogStorage_Postgres_Ops.res +43 -42
- package/lib/bs/src/DcbEventLogStorage_Postgres_Ops.res.mjs +4 -4
- package/lib/bs/src/EventLogChangeFeed-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/EventLogChangeFeed-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/EventLogChangeFeed.ast +0 -0
- package/lib/bs/src/EventLogChangeFeed.res +15 -6
- package/lib/bs/src/EventLogChangeFeed.res.mjs +3 -3
- package/lib/bs/src/EventLogStorage_Postgres-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/EventLogStorage_Postgres-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/EventLogStorage_Postgres.ast +0 -0
- package/lib/bs/src/EventLogStorage_Postgres.res +1 -1
- package/lib/bs/src/EventLogStorage_Postgres_Ops-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/EventLogStorage_Postgres_Ops-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/EventLogStorage_Postgres_Ops.ast +0 -0
- package/lib/bs/src/EventLogStorage_Postgres_Ops.res +24 -14
- package/lib/bs/src/PgChangeFeed-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/PgChangeFeed-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/PgChangeFeed.ast +0 -0
- package/lib/bs/src/PgChangeFeed.res +21 -9
- package/lib/bs/src/PgChangeFeed.res.mjs +6 -6
- package/lib/bs/src/PgDriver-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/PgDriver-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/PgDriver-ReventlessPostgres.cmti +0 -0
- package/lib/bs/src/PgDriver.ast +0 -0
- package/lib/bs/src/PgDriver.iast +0 -0
- package/lib/bs/src/PgDriver.res +1 -2
- package/lib/bs/src/PgSchema-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/PgSchema-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/PgSchema.ast +0 -0
- package/lib/bs/src/QueryDbStorage_Postgres-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/QueryDbStorage_Postgres-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/QueryDbStorage_Postgres.ast +0 -0
- package/lib/bs/src/QueryDbStorage_Postgres.res +7 -2
- package/lib/bs/src/QueryDbStorage_Postgres.res.mjs +1 -1
- package/lib/bs/src/QueryDbStorage_Postgres_Ops-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/QueryDbStorage_Postgres_Ops-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/QueryDbStorage_Postgres_Ops.ast +0 -0
- package/lib/bs/src/QueryDbStorage_Postgres_Ops.res +14 -14
- package/lib/bs/src/QueryEnginePostgres-ReventlessPostgres.cmi +0 -0
- package/lib/bs/src/QueryEnginePostgres-ReventlessPostgres.cmt +0 -0
- package/lib/bs/src/QueryEnginePostgres.ast +0 -0
- package/lib/bs/src/QueryEnginePostgres.res +141 -42
- package/lib/bs/src/QueryEnginePostgres.res.mjs +53 -30
- package/lib/bs/tests/PostgresIntegrationTest-ReventlessPostgres.cmi +0 -0
- package/lib/bs/tests/PostgresIntegrationTest-ReventlessPostgres.cmt +0 -0
- package/lib/bs/tests/PostgresIntegrationTest.ast +0 -0
- package/lib/bs/tests/PostgresIntegrationTest.res +157 -104
- package/lib/bs/tests/QueryEnginePostgresListPageTest-ReventlessPostgres.cmi +0 -0
- package/lib/bs/tests/QueryEnginePostgresListPageTest-ReventlessPostgres.cmt +0 -0
- package/lib/bs/tests/QueryEnginePostgresListPageTest.ast +0 -0
- package/lib/bs/tests/QueryEnginePostgresListPageTest.res +29 -6
- package/lib/bs/tests/QueryEnginePostgresListPageTest.res.mjs +4 -4
- package/lib/ocaml/.compiler.log +2 -2
- package/lib/ocaml/DcbEventLogStorage_Postgres-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/DcbEventLogStorage_Postgres-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/DcbEventLogStorage_Postgres.ast +0 -0
- package/lib/ocaml/DcbEventLogStorage_Postgres.res +1 -1
- package/lib/ocaml/DcbEventLogStorage_Postgres_Ops-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/DcbEventLogStorage_Postgres_Ops-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/DcbEventLogStorage_Postgres_Ops.ast +0 -0
- package/lib/ocaml/DcbEventLogStorage_Postgres_Ops.res +43 -42
- package/lib/ocaml/EventLogChangeFeed-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/EventLogChangeFeed-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/EventLogChangeFeed.ast +0 -0
- package/lib/ocaml/EventLogChangeFeed.res +15 -6
- package/lib/ocaml/EventLogStorage_Postgres-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/EventLogStorage_Postgres-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/EventLogStorage_Postgres.ast +0 -0
- package/lib/ocaml/EventLogStorage_Postgres.res +1 -1
- package/lib/ocaml/EventLogStorage_Postgres_Ops-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/EventLogStorage_Postgres_Ops-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/EventLogStorage_Postgres_Ops.ast +0 -0
- package/lib/ocaml/EventLogStorage_Postgres_Ops.res +24 -14
- package/lib/ocaml/PgChangeFeed-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/PgChangeFeed-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/PgChangeFeed.ast +0 -0
- package/lib/ocaml/PgChangeFeed.res +21 -9
- package/lib/ocaml/PgDriver-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/PgDriver-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/PgDriver-ReventlessPostgres.cmti +0 -0
- package/lib/ocaml/PgDriver.ast +0 -0
- package/lib/ocaml/PgDriver.iast +0 -0
- package/lib/ocaml/PgDriver.res +1 -2
- package/lib/ocaml/PgSchema-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/PgSchema-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/PgSchema.ast +0 -0
- package/lib/ocaml/PostgresIntegrationTest.res +157 -104
- package/lib/ocaml/QueryDbStorage_Postgres-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/QueryDbStorage_Postgres-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/QueryDbStorage_Postgres.ast +0 -0
- package/lib/ocaml/QueryDbStorage_Postgres.res +7 -2
- package/lib/ocaml/QueryDbStorage_Postgres_Ops-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/QueryDbStorage_Postgres_Ops-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/QueryDbStorage_Postgres_Ops.ast +0 -0
- package/lib/ocaml/QueryDbStorage_Postgres_Ops.res +14 -14
- package/lib/ocaml/QueryEnginePostgres-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/QueryEnginePostgres-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/QueryEnginePostgres.ast +0 -0
- package/lib/ocaml/QueryEnginePostgres.res +141 -42
- package/lib/ocaml/QueryEnginePostgresListPageTest.res +29 -6
- package/lib/ocaml/ReventlessPostgres.cmt +0 -0
- package/package.json +13 -13
- package/rescript.json +2 -1
- package/src/DcbEventLogStorage_Postgres.res +1 -1
- package/src/DcbEventLogStorage_Postgres_Ops.res +43 -42
- package/src/DcbEventLogStorage_Postgres_Ops.res.mjs +4 -4
- package/src/EventLogChangeFeed.res +15 -6
- package/src/EventLogChangeFeed.res.mjs +3 -3
- package/src/EventLogStorage_Postgres.res +1 -1
- package/src/EventLogStorage_Postgres_Ops.res +24 -14
- package/src/PgChangeFeed.res +21 -9
- package/src/PgChangeFeed.res.mjs +6 -6
- package/src/PgDriver.res +1 -2
- package/src/QueryDbStorage_Postgres.res +7 -2
- package/src/QueryDbStorage_Postgres.res.mjs +1 -1
- package/src/QueryDbStorage_Postgres_Ops.res +14 -14
- package/src/QueryEnginePostgres.res +141 -42
- package/src/QueryEnginePostgres.res.mjs +53 -30
- package/tests/PostgresIntegrationTest.res +157 -104
- package/tests/QueryEnginePostgresListPageTest.res +29 -6
- package/lib/ocaml/PostgresIntegrationTest-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/PostgresIntegrationTest-ReventlessPostgres.cmj +0 -0
- package/lib/ocaml/PostgresIntegrationTest-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/PostgresIntegrationTest.ast +0 -0
- package/lib/ocaml/QueryEnginePostgresListPageTest-ReventlessPostgres.cmi +0 -0
- package/lib/ocaml/QueryEnginePostgresListPageTest-ReventlessPostgres.cmj +0 -0
- package/lib/ocaml/QueryEnginePostgresListPageTest-ReventlessPostgres.cmt +0 -0
- package/lib/ocaml/QueryEnginePostgresListPageTest.ast +0 -0
- package/tests/PostgresIntegrationTest.res.mjs +0 -377
- package/tests/QueryEnginePostgresListPageTest.res.mjs +0 -461
|
@@ -28,7 +28,12 @@ let param = (b: paramBuilder, v: JSON.t): string => {
|
|
|
28
28
|
let col = (field: string): string => `(item->>'${field->String.replaceAll("'", "''")}')`
|
|
29
29
|
|
|
30
30
|
// One Filter.config → SQL predicate, appending any bound params.
|
|
31
|
-
let filterSql = (
|
|
31
|
+
let filterSql = (
|
|
32
|
+
b: paramBuilder,
|
|
33
|
+
field: string,
|
|
34
|
+
cmp: QueryEngine.Filter.comparator,
|
|
35
|
+
v: QueryEngine.value,
|
|
36
|
+
): string => {
|
|
32
37
|
let c = col(field)
|
|
33
38
|
let bind = () => b->param(JSON.Encode.string(valueToText(v)))
|
|
34
39
|
let cmpSql = op =>
|
|
@@ -48,10 +53,16 @@ let filterSql = (b: paramBuilder, field: string, cmp: QueryEngine.Filter.compara
|
|
|
48
53
|
}
|
|
49
54
|
}
|
|
50
55
|
|
|
51
|
-
let subIdSql = (
|
|
56
|
+
let subIdSql = (
|
|
57
|
+
b: paramBuilder,
|
|
58
|
+
field: string,
|
|
59
|
+
cmp: QueryEngine.SubId.comparator,
|
|
60
|
+
v: QueryEngine.value,
|
|
61
|
+
): string => {
|
|
52
62
|
let c = col(field)
|
|
53
63
|
let bind = () => b->param(JSON.Encode.string(valueToText(v)))
|
|
54
|
-
let cmpSql = op =>
|
|
64
|
+
let cmpSql = op =>
|
|
65
|
+
isNumeric(v) ? `${c}::numeric ${op} ${bind()}::numeric` : `${c} ${op} ${bind()}`
|
|
55
66
|
switch cmp {
|
|
56
67
|
| QueryEngine.SubId.Equal => cmpSql("=")
|
|
57
68
|
| Unequal => cmpSql("<>")
|
|
@@ -63,24 +74,28 @@ let subIdSql = (b: paramBuilder, field: string, cmp: QueryEngine.SubId.comparato
|
|
|
63
74
|
}
|
|
64
75
|
}
|
|
65
76
|
|
|
66
|
-
let notExpired =
|
|
77
|
+
let notExpired = QueryDbStorage_Postgres_Ops.notExpiredClause
|
|
67
78
|
|
|
68
79
|
// Add `id` (from partition_key) when absent — matches allRows/scan in the SQLite
|
|
69
80
|
// engine; partition-key queries return items as stored.
|
|
70
81
|
let decodeRow = (~withId, row: dict<JSON.t>): JSON.t => {
|
|
71
|
-
let item =
|
|
82
|
+
let item = QueryDbStorage_Postgres_Ops.decodeItem(row)
|
|
72
83
|
if withId {
|
|
73
84
|
let pk = switch row->Dict.get("partition_key") {
|
|
74
85
|
| Some(JSON.String(s)) => s
|
|
75
86
|
| _ => ""
|
|
76
87
|
}
|
|
77
|
-
|
|
88
|
+
QueryDbStorage_Postgres_Ops.withId(item, pk)
|
|
78
89
|
} else {
|
|
79
90
|
item
|
|
80
91
|
}
|
|
81
92
|
}
|
|
82
93
|
|
|
83
|
-
module Make = (
|
|
94
|
+
module Make = (
|
|
95
|
+
P: {
|
|
96
|
+
let pool: PgDriver.pool
|
|
97
|
+
},
|
|
98
|
+
) => {
|
|
84
99
|
let query = async (
|
|
85
100
|
~readModelName,
|
|
86
101
|
~key=?,
|
|
@@ -90,7 +105,7 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
90
105
|
~ascending=?,
|
|
91
106
|
~limit=?,
|
|
92
107
|
): array<JSON.t> => {
|
|
93
|
-
let table =
|
|
108
|
+
let table = QueryDbStorage_Postgres_Ops.tableName(readModelName)
|
|
94
109
|
let keyStr = switch key {
|
|
95
110
|
| Some(k) => k
|
|
96
111
|
| None => valueToText(id)
|
|
@@ -109,16 +124,22 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
109
124
|
| Some(n) => ` LIMIT ${b->param(JSON.Encode.int(n))}`
|
|
110
125
|
| None => ""
|
|
111
126
|
}
|
|
112
|
-
let sql = `SELECT partition_key, item FROM ${table} WHERE ${where->Array.join(
|
|
127
|
+
let sql = `SELECT partition_key, item FROM ${table} WHERE ${where->Array.join(
|
|
128
|
+
" AND ",
|
|
129
|
+
)} ORDER BY sub_key ${dir}${limitClause}`
|
|
113
130
|
(await P.pool->PgDriver.query(sql, b.params))->Array.map(decodeRow(~withId=false, ...))
|
|
114
131
|
}
|
|
115
132
|
|
|
116
133
|
let scan = async (~readModelName, ~filterConfigs, ~limit): array<JSON.t> => {
|
|
117
|
-
let table =
|
|
134
|
+
let table = QueryDbStorage_Postgres_Ops.tableName(readModelName)
|
|
118
135
|
let b = {params: []}
|
|
119
136
|
let where = [notExpired]
|
|
120
|
-
filterConfigs->Array.forEach(((field, cmp, v)) =>
|
|
121
|
-
|
|
137
|
+
filterConfigs->Array.forEach(((field, cmp, v)) =>
|
|
138
|
+
where->Array.push(filterSql(b, field, cmp, v))
|
|
139
|
+
)
|
|
140
|
+
let sql = `SELECT partition_key, item FROM ${table} WHERE ${where->Array.join(
|
|
141
|
+
" AND ",
|
|
142
|
+
)} ORDER BY partition_key, sub_key LIMIT ${b->param(JSON.Encode.int(limit))}`
|
|
122
143
|
(await P.pool->PgDriver.query(sql, b.params))->Array.map(decodeRow(~withId=true, ...))
|
|
123
144
|
}
|
|
124
145
|
|
|
@@ -138,7 +159,7 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
138
159
|
// (`ensureIndexes`) instead of scanning. String comparison mirrors the
|
|
139
160
|
// resolver's JS path (which only matched string-typed fields).
|
|
140
161
|
let indexLookup = async (~readModelName, field: string, value: string): array<JSON.t> => {
|
|
141
|
-
let table =
|
|
162
|
+
let table = QueryDbStorage_Postgres_Ops.tableName(readModelName)
|
|
142
163
|
let b = {params: []}
|
|
143
164
|
let sql = `SELECT partition_key, item FROM ${table} WHERE ${col(field)} = ${b->param(
|
|
144
165
|
JSON.Encode.string(value),
|
|
@@ -154,7 +175,7 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
154
175
|
if ids->Array.length == 0 {
|
|
155
176
|
[]
|
|
156
177
|
} else {
|
|
157
|
-
let table =
|
|
178
|
+
let table = QueryDbStorage_Postgres_Ops.tableName(readModelName)
|
|
158
179
|
let b = {params: []}
|
|
159
180
|
let idsJson = JSON.Encode.array(ids->Array.map(JSON.Encode.string))
|
|
160
181
|
let sql = `SELECT partition_key, item FROM ${table} WHERE partition_key = ANY(${b->param(
|
|
@@ -168,6 +189,39 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
168
189
|
let idExprC = `COALESCE(item->>'id', partition_key) COLLATE "C"`
|
|
169
190
|
let jsonTextC = (field: string): string => `${col(field)} COLLATE "C"`
|
|
170
191
|
|
|
192
|
+
// "not retired", as jsonb rather than text. `->` keeps the value typed, so a
|
|
193
|
+
// JSON boolean true is distinguishable from the JSON string "true"; `->>`
|
|
194
|
+
// would render both as 'true' and hide a row the shared spec keeps, since that
|
|
195
|
+
// spec decodes strictly and reads a non-boolean as "no flag". `IS DISTINCT
|
|
196
|
+
// FROM` rather than `<>` so an absent key — NULL — keeps the row instead of
|
|
197
|
+
// making the whole predicate NULL and dropping it.
|
|
198
|
+
//
|
|
199
|
+
// The state form compares against JSON strings instead of `true`, one
|
|
200
|
+
// `IS DISTINCT FROM` per state, ANDed. Not `NOT IN`: that is ordinary
|
|
201
|
+
// equality, so an absent key makes the predicate NULL and drops a row this
|
|
202
|
+
// spec keeps. Same shape and same index behaviour as the single-state form —
|
|
203
|
+
// a handful of equality predicates over an enum-valued attribute cost what one
|
|
204
|
+
// over a boolean does — so the `@index` guidance carries over unchanged.
|
|
205
|
+
//
|
|
206
|
+
// A set naming no states withdraws nothing, so the predicate is vacuously
|
|
207
|
+
// true, matching what `isRetiredValue` answers for it.
|
|
208
|
+
let notRetiredC = (scope: Reventless.OwnerScope.retiredScope): string => {
|
|
209
|
+
let key = scope.field->String.replaceAll("'", "''")
|
|
210
|
+
let distinctFrom = lit => `(item->'${key}') IS DISTINCT FROM ${lit}`
|
|
211
|
+
switch scope.values {
|
|
212
|
+
| None => distinctFrom("'true'::jsonb")
|
|
213
|
+
| Some([]) => "TRUE"
|
|
214
|
+
| Some(states) =>
|
|
215
|
+
// Parenthesised though every caller ANDs these together already: a clause
|
|
216
|
+
// that is safe only because of where it is spliced is a clause that breaks
|
|
217
|
+
// the first time it is spliced somewhere else.
|
|
218
|
+
"(" ++
|
|
219
|
+
states
|
|
220
|
+
->Array.map(state => distinctFrom(`'"${state->String.replaceAll("'", "''")}"'::jsonb`))
|
|
221
|
+
->Array.join(" AND ") ++ ")"
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
|
|
171
225
|
// Connection-list push-down. Builds `item->>'field'` predicates + keyset
|
|
172
226
|
// WHERE + `ORDER BY … LIMIT pageSize+1` so a page reads only what it returns
|
|
173
227
|
// rather than the whole read model. Reproduces `QueryDbListQuery` semantics
|
|
@@ -183,8 +237,10 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
183
237
|
~argsDict: dict<JSON.t>,
|
|
184
238
|
~capability: GraphQL_FragmentGenerator.serverCapability,
|
|
185
239
|
~labelField as _,
|
|
240
|
+
~ownerScope: option<(string, string)>=?,
|
|
241
|
+
~retiredScope: option<Reventless.OwnerScope.retiredScope>=?,
|
|
186
242
|
): option<JSON.t> => {
|
|
187
|
-
let table =
|
|
243
|
+
let table = QueryDbStorage_Postgres_Ops.tableName(readModelName)
|
|
188
244
|
let filterDict =
|
|
189
245
|
argsDict->Dict.get("filter")->Option.flatMap(JSON.Decode.object)->Option.getOr(Dict.make())
|
|
190
246
|
let strNonEmpty = k =>
|
|
@@ -210,6 +266,19 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
210
266
|
} else {
|
|
211
267
|
let b = {params: []}
|
|
212
268
|
let whereParts = [notExpired]
|
|
269
|
+
// Into the SQL, before the LIMIT — narrowing the returned page instead
|
|
270
|
+
// would hand back fewer rows than asked for while still claiming a next
|
|
271
|
+
// page. Mirrors the SQLite push-down; the parity harness holds the two
|
|
272
|
+
// and the shared spec to the same answer.
|
|
273
|
+
switch ownerScope {
|
|
274
|
+
| Some((field, required)) =>
|
|
275
|
+
whereParts->Array.push(`${jsonTextC(field)} = ${b->param(JSON.Encode.string(required))}`)
|
|
276
|
+
| None => ()
|
|
277
|
+
}
|
|
278
|
+
switch retiredScope {
|
|
279
|
+
| Some(scope) => whereParts->Array.push(notRetiredC(scope))
|
|
280
|
+
| None => ()
|
|
281
|
+
}
|
|
213
282
|
let valString = v =>
|
|
214
283
|
switch v->JSON.Decode.string {
|
|
215
284
|
| Some(s) => Some(s)
|
|
@@ -217,15 +286,17 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
217
286
|
}
|
|
218
287
|
capability.filterFields->Array.forEach(f => {
|
|
219
288
|
switch filterDict->Dict.get(f.name ++ "Eq") {
|
|
220
|
-
| Some(v)
|
|
289
|
+
| Some(v) if v != JSON.Encode.null =>
|
|
221
290
|
whereParts->Array.push(
|
|
222
|
-
`${jsonTextC(f.name)} = ${b->param(
|
|
291
|
+
`${jsonTextC(f.name)} = ${b->param(
|
|
292
|
+
JSON.Encode.string(valString(v)->Option.getOr("")),
|
|
293
|
+
)}`,
|
|
223
294
|
)
|
|
224
295
|
| _ => ()
|
|
225
296
|
}
|
|
226
297
|
if f.range {
|
|
227
298
|
switch filterDict->Dict.get(f.name ++ "From") {
|
|
228
|
-
| Some(v)
|
|
299
|
+
| Some(v) if v != JSON.Encode.null =>
|
|
229
300
|
whereParts->Array.push(
|
|
230
301
|
`${jsonTextC(f.name)} >= ${b->param(
|
|
231
302
|
JSON.Encode.string(valString(v)->Option.getOr("")),
|
|
@@ -234,7 +305,7 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
234
305
|
| _ => ()
|
|
235
306
|
}
|
|
236
307
|
switch filterDict->Dict.get(f.name ++ "To") {
|
|
237
|
-
| Some(v)
|
|
308
|
+
| Some(v) if v != JSON.Encode.null =>
|
|
238
309
|
whereParts->Array.push(
|
|
239
310
|
`${jsonTextC(f.name)} <= ${b->param(
|
|
240
311
|
JSON.Encode.string(valString(v)->Option.getOr("")),
|
|
@@ -256,7 +327,8 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
256
327
|
| Some(f) => jsonTextC(f)
|
|
257
328
|
| None => idExprC
|
|
258
329
|
}
|
|
259
|
-
|
|
330
|
+
let afterCursor = argsDict->Dict.get("after")->Option.flatMap(JSON.Decode.string)
|
|
331
|
+
switch afterCursor {
|
|
260
332
|
| Some(c) =>
|
|
261
333
|
whereParts->Array.push(
|
|
262
334
|
`${cursorExpr} ${isDesc ? "<" : ">"} ${b->param(
|
|
@@ -278,7 +350,8 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
278
350
|
let sql = `SELECT partition_key, item FROM ${table} WHERE ${whereParts->Array.join(
|
|
279
351
|
" AND ",
|
|
280
352
|
)} ORDER BY ${orderClause} LIMIT ${b->param(JSON.Encode.int(pageSize + 1))}`
|
|
281
|
-
let rows =
|
|
353
|
+
let rows =
|
|
354
|
+
(await P.pool->PgDriver.query(sql, b.params))->Array.map(decodeRow(~withId=true, ...))
|
|
282
355
|
let hasMore = rows->Array.length > pageSize
|
|
283
356
|
let pageItems = rows->Array.slice(~start=0, ~end=pageSize)
|
|
284
357
|
let cursorField = orderByField->Option.getOr("id")
|
|
@@ -290,7 +363,10 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
290
363
|
ReventlessCore.QueryDbListQuery.buildConnection(
|
|
291
364
|
~pageItems,
|
|
292
365
|
~hasNextPage=hasMore,
|
|
293
|
-
|
|
366
|
+
// Same rule the spec uses, because the parity suite compares them: a
|
|
367
|
+
// forward page reached by a cursor has one behind it. Hardcoding false
|
|
368
|
+
// made Prev disappear on exactly the pages that have a previous one.
|
|
369
|
+
~hasPreviousPage=afterCursor->Option.isSome,
|
|
294
370
|
~cursorValueOf,
|
|
295
371
|
),
|
|
296
372
|
)
|
|
@@ -309,14 +385,18 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
309
385
|
~subIdField as _: string,
|
|
310
386
|
~id: string,
|
|
311
387
|
~argsDict: dict<JSON.t>,
|
|
388
|
+
~ownerScope: option<(string, string)>=?,
|
|
389
|
+
~retiredScope: option<Reventless.OwnerScope.retiredScope>=?,
|
|
312
390
|
): JSON.t => {
|
|
313
|
-
let table =
|
|
391
|
+
let table = QueryDbStorage_Postgres_Ops.tableName(readModelName)
|
|
314
392
|
let filterDict =
|
|
315
393
|
argsDict->Dict.get("filter")->Option.flatMap(JSON.Decode.object)->Option.getOr(Dict.make())
|
|
316
394
|
let fstr = k => filterDict->Dict.get(k)->Option.flatMap(JSON.Decode.string)
|
|
317
395
|
let orderDesc = fstr("order")->Option.mapOr(false, o => o == "DESC")
|
|
318
|
-
let last =
|
|
319
|
-
|
|
396
|
+
let last =
|
|
397
|
+
argsDict->Dict.get("last")->Option.flatMap(JSON.Decode.float)->Option.map(Float.toInt)
|
|
398
|
+
let first =
|
|
399
|
+
argsDict->Dict.get("first")->Option.flatMap(JSON.Decode.float)->Option.map(Float.toInt)
|
|
320
400
|
let after = argsDict->Dict.get("after")->Option.flatMap(JSON.Decode.string)
|
|
321
401
|
let before = argsDict->Dict.get("before")->Option.flatMap(JSON.Decode.string)
|
|
322
402
|
let isBackward = last->Option.isSome
|
|
@@ -324,28 +404,49 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
324
404
|
let sk = `sub_key COLLATE "C"`
|
|
325
405
|
let b = {params: []}
|
|
326
406
|
let where = [`partition_key = ${b->param(JSON.Encode.string(id))}`, notExpired]
|
|
407
|
+
// Before the keyset window and the LIMIT, for the same reason as `listPage`.
|
|
408
|
+
switch ownerScope {
|
|
409
|
+
| Some((field, required)) =>
|
|
410
|
+
where->Array.push(`${jsonTextC(field)} = ${b->param(JSON.Encode.string(required))}`)
|
|
411
|
+
| None => ()
|
|
412
|
+
}
|
|
413
|
+
switch retiredScope {
|
|
414
|
+
| Some(scope) => where->Array.push(notRetiredC(scope))
|
|
415
|
+
| None => ()
|
|
416
|
+
}
|
|
327
417
|
fstr("prefix")->Option.forEach(p =>
|
|
328
418
|
where->Array.push(`starts_with(sub_key, ${b->param(JSON.Encode.string(p))})`)
|
|
329
419
|
)
|
|
330
|
-
fstr("from")->Option.forEach(f =>
|
|
331
|
-
|
|
420
|
+
fstr("from")->Option.forEach(f =>
|
|
421
|
+
where->Array.push(`${sk} >= ${b->param(JSON.Encode.string(f))}`)
|
|
422
|
+
)
|
|
423
|
+
fstr("to")->Option.forEach(t =>
|
|
424
|
+
where->Array.push(`${sk} <= ${b->param(JSON.Encode.string(t))}`)
|
|
425
|
+
)
|
|
332
426
|
fstr("eq")->Option.forEach(e => where->Array.push(`${sk} = ${b->param(JSON.Encode.string(e))}`))
|
|
333
427
|
// Keyset: forward excludes ≤ after; backward excludes ≥ before.
|
|
334
428
|
switch (isBackward, after, before) {
|
|
335
429
|
| (false, Some(c), _) =>
|
|
336
|
-
where->Array.push(
|
|
430
|
+
where->Array.push(
|
|
431
|
+
`${sk} > ${b->param(JSON.Encode.string(ReventlessCore.QueryDbListQuery.decodeCursor(c)))}`,
|
|
432
|
+
)
|
|
337
433
|
| (true, _, Some(c)) =>
|
|
338
|
-
where->Array.push(
|
|
434
|
+
where->Array.push(
|
|
435
|
+
`${sk} < ${b->param(JSON.Encode.string(ReventlessCore.QueryDbListQuery.decodeCursor(c)))}`,
|
|
436
|
+
)
|
|
339
437
|
| _ => ()
|
|
340
438
|
}
|
|
341
439
|
// Page-fetch direction is the LOGICAL order forward, and its OPPOSITE
|
|
342
440
|
// backward (take the N nearest `before`, then reverse to logical) — mirrors
|
|
343
441
|
// the resolver's `reverse = isBackward ? !orderDesc : orderDesc`.
|
|
344
442
|
let fetchDesc = isBackward ? !orderDesc : orderDesc
|
|
345
|
-
let pageSize =
|
|
443
|
+
let pageSize =
|
|
444
|
+
(isBackward ? last : first)->Option.getOr(ReventlessCore.QueryDbListQuery.defaultListPageSize)
|
|
346
445
|
let sql = `SELECT partition_key, sub_key, item FROM ${table} WHERE ${where->Array.join(
|
|
347
446
|
" AND ",
|
|
348
|
-
)} ORDER BY ${sk} ${fetchDesc ? "DESC" : "ASC"} LIMIT ${b->param(
|
|
447
|
+
)} ORDER BY ${sk} ${fetchDesc ? "DESC" : "ASC"} LIMIT ${b->param(
|
|
448
|
+
JSON.Encode.int(pageSize + 1),
|
|
449
|
+
)}`
|
|
349
450
|
let rows = await P.pool->PgDriver.query(sql, b.params)
|
|
350
451
|
let hasMore = rows->Array.length > pageSize
|
|
351
452
|
let taken = rows->Array.slice(~start=0, ~end=pageSize)
|
|
@@ -359,17 +460,18 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
359
460
|
| _ => ""
|
|
360
461
|
}
|
|
361
462
|
let cursors = logical->Array.map(subKeyOf)
|
|
362
|
-
let edges =
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
)
|
|
463
|
+
let edges = pageItems->Array.mapWithIndex((item, i) =>
|
|
464
|
+
Obj.magic({
|
|
465
|
+
"node": item,
|
|
466
|
+
"cursor": ReventlessCore.QueryDbListQuery.encodeCursor(cursors->Array.getUnsafe(i)),
|
|
467
|
+
})
|
|
468
|
+
)
|
|
369
469
|
let startCursor =
|
|
370
470
|
cursors->Array.get(0)->Option.map(ReventlessCore.QueryDbListQuery.encodeCursor)
|
|
371
471
|
let endCursor =
|
|
372
|
-
cursors
|
|
472
|
+
cursors
|
|
473
|
+
->Array.get(cursors->Array.length - 1)
|
|
474
|
+
->Option.map(ReventlessCore.QueryDbListQuery.encodeCursor)
|
|
373
475
|
Obj.magic({
|
|
374
476
|
"edges": edges,
|
|
375
477
|
"pageInfo": {
|
|
@@ -380,7 +482,4 @@ module Make = (P: {let pool: PgDriver.pool}) => {
|
|
|
380
482
|
},
|
|
381
483
|
})
|
|
382
484
|
}
|
|
383
|
-
|
|
384
|
-
let make: QueryDb_Adapter.queryEngineMaker = _allQueryDbs =>
|
|
385
|
-
Pulumi.Output.make({QueryEngine.scan, query})
|
|
386
485
|
}
|
|
@@ -2,11 +2,10 @@
|
|
|
2
2
|
|
|
3
3
|
import * as Stdlib_JSON from "@rescript/runtime/lib/es6/Stdlib_JSON.js";
|
|
4
4
|
import * as Stdlib_Option from "@rescript/runtime/lib/es6/Stdlib_Option.js";
|
|
5
|
-
import * as Pulumi from "@pulumi/pulumi";
|
|
6
5
|
import * as Stdlib_Nullable from "@rescript/runtime/lib/es6/Stdlib_Nullable.js";
|
|
7
6
|
import * as PgDriver$ReventlessPostgres from "./PgDriver.res.mjs";
|
|
8
7
|
import * as QueryDbListQuery$ReventlessCore from "@reventlessdev/reventless-core/src/components/Api/QueryDbListQuery.res.mjs";
|
|
9
|
-
import * as
|
|
8
|
+
import * as QueryDbStorage_Postgres_Ops$ReventlessPostgres from "./QueryDbStorage_Postgres_Ops.res.mjs";
|
|
10
9
|
|
|
11
10
|
function valueToText(v) {
|
|
12
11
|
switch (v.TAG) {
|
|
@@ -105,25 +104,25 @@ function subIdSql(b, field, cmp, v) {
|
|
|
105
104
|
}
|
|
106
105
|
|
|
107
106
|
function decodeRow(withId, row) {
|
|
108
|
-
let item =
|
|
107
|
+
let item = QueryDbStorage_Postgres_Ops$ReventlessPostgres.decodeItem(row);
|
|
109
108
|
if (!withId) {
|
|
110
109
|
return item;
|
|
111
110
|
}
|
|
112
111
|
let match = row["partition_key"];
|
|
113
112
|
let pk = typeof match === "string" ? match : "";
|
|
114
|
-
return
|
|
113
|
+
return QueryDbStorage_Postgres_Ops$ReventlessPostgres.withId(item, pk);
|
|
115
114
|
}
|
|
116
115
|
|
|
117
116
|
function Make(P) {
|
|
118
117
|
let query = async (readModelName, key, id, subIdConfig, filterConfigs, ascending, limit) => {
|
|
119
|
-
let table =
|
|
118
|
+
let table = QueryDbStorage_Postgres_Ops$ReventlessPostgres.tableName(readModelName);
|
|
120
119
|
let keyStr = key !== undefined ? key : valueToText(id);
|
|
121
120
|
let b = {
|
|
122
121
|
params: []
|
|
123
122
|
};
|
|
124
123
|
let where = [
|
|
125
124
|
`partition_key = ` + param(b, keyStr),
|
|
126
|
-
|
|
125
|
+
QueryDbStorage_Postgres_Ops$ReventlessPostgres.notExpiredClause
|
|
127
126
|
];
|
|
128
127
|
if (subIdConfig !== undefined) {
|
|
129
128
|
where.push(subIdSql(b, subIdConfig[0], subIdConfig[1], subIdConfig[2]));
|
|
@@ -137,11 +136,11 @@ function Make(P) {
|
|
|
137
136
|
return (await PgDriver$ReventlessPostgres.query(P.pool, sql, b.params)).map(extra => decodeRow(false, extra));
|
|
138
137
|
};
|
|
139
138
|
let scan = async (readModelName, filterConfigs, limit) => {
|
|
140
|
-
let table =
|
|
139
|
+
let table = QueryDbStorage_Postgres_Ops$ReventlessPostgres.tableName(readModelName);
|
|
141
140
|
let b = {
|
|
142
141
|
params: []
|
|
143
142
|
};
|
|
144
|
-
let where = [
|
|
143
|
+
let where = [QueryDbStorage_Postgres_Ops$ReventlessPostgres.notExpiredClause];
|
|
145
144
|
filterConfigs.forEach(param => {
|
|
146
145
|
where.push(filterSql(b, param[0], param[1], param[2]));
|
|
147
146
|
});
|
|
@@ -149,29 +148,45 @@ function Make(P) {
|
|
|
149
148
|
return (await PgDriver$ReventlessPostgres.query(P.pool, sql, b.params)).map(extra => decodeRow(true, extra));
|
|
150
149
|
};
|
|
151
150
|
let indexLookup = async (readModelName, field, value) => {
|
|
152
|
-
let table =
|
|
151
|
+
let table = QueryDbStorage_Postgres_Ops$ReventlessPostgres.tableName(readModelName);
|
|
153
152
|
let b = {
|
|
154
153
|
params: []
|
|
155
154
|
};
|
|
156
|
-
let sql = `SELECT partition_key, item FROM ` + table + ` WHERE ` + col(field) + ` = ` + param(b, value) + ` AND ` +
|
|
155
|
+
let sql = `SELECT partition_key, item FROM ` + table + ` WHERE ` + col(field) + ` = ` + param(b, value) + ` AND ` + QueryDbStorage_Postgres_Ops$ReventlessPostgres.notExpiredClause;
|
|
157
156
|
return (await PgDriver$ReventlessPostgres.query(P.pool, sql, b.params)).map(extra => decodeRow(true, extra));
|
|
158
157
|
};
|
|
159
158
|
let byIds = async (readModelName, ids) => {
|
|
160
159
|
if (ids.length === 0) {
|
|
161
160
|
return [];
|
|
162
161
|
}
|
|
163
|
-
let table =
|
|
162
|
+
let table = QueryDbStorage_Postgres_Ops$ReventlessPostgres.tableName(readModelName);
|
|
164
163
|
let b = {
|
|
165
164
|
params: []
|
|
166
165
|
};
|
|
167
166
|
let idsJson = ids.map(prim => prim);
|
|
168
|
-
let sql = `SELECT partition_key, item FROM ` + table + ` WHERE partition_key = ANY(` + param(b, idsJson) + `::text[]) AND ` +
|
|
167
|
+
let sql = `SELECT partition_key, item FROM ` + table + ` WHERE partition_key = ANY(` + param(b, idsJson) + `::text[]) AND ` + QueryDbStorage_Postgres_Ops$ReventlessPostgres.notExpiredClause;
|
|
169
168
|
return (await PgDriver$ReventlessPostgres.query(P.pool, sql, b.params)).map(extra => decodeRow(true, extra));
|
|
170
169
|
};
|
|
171
170
|
let idExprC = `COALESCE(item->>'id', partition_key) COLLATE "C"`;
|
|
172
171
|
let jsonTextC = field => col(field) + ` COLLATE "C"`;
|
|
173
|
-
let
|
|
174
|
-
let
|
|
172
|
+
let notRetiredC = scope => {
|
|
173
|
+
let key = scope.field.replaceAll("'", "''");
|
|
174
|
+
let states = scope.values;
|
|
175
|
+
if (states !== undefined) {
|
|
176
|
+
if (states.length !== 0) {
|
|
177
|
+
return "(" + states.map(state => {
|
|
178
|
+
let lit = `'"` + state.replaceAll("'", "''") + `"'::jsonb`;
|
|
179
|
+
return `(item->'` + key + `') IS DISTINCT FROM ` + lit;
|
|
180
|
+
}).join(" AND ") + ")";
|
|
181
|
+
} else {
|
|
182
|
+
return "TRUE";
|
|
183
|
+
}
|
|
184
|
+
} else {
|
|
185
|
+
return `(item->'` + key + `') IS DISTINCT FROM ` + "'true'::jsonb";
|
|
186
|
+
}
|
|
187
|
+
};
|
|
188
|
+
let listPage = async (readModelName, argsDict, capability, param$1, ownerScope, retiredScope) => {
|
|
189
|
+
let table = QueryDbStorage_Postgres_Ops$ReventlessPostgres.tableName(readModelName);
|
|
175
190
|
let filterDict = Stdlib_Option.getOr(Stdlib_Option.flatMap(argsDict["filter"], Stdlib_JSON.Decode.object), {});
|
|
176
191
|
let strNonEmpty = k => Stdlib_Option.mapOr(Stdlib_Option.flatMap(filterDict[k], Stdlib_JSON.Decode.string), false, s => s.length > 0);
|
|
177
192
|
let hasIds = Stdlib_Option.mapOr(Stdlib_Option.flatMap(filterDict["ids"], Stdlib_JSON.Decode.array), false, a => a.length !== 0);
|
|
@@ -183,7 +198,13 @@ function Make(P) {
|
|
|
183
198
|
let b = {
|
|
184
199
|
params: []
|
|
185
200
|
};
|
|
186
|
-
let whereParts = [
|
|
201
|
+
let whereParts = [QueryDbStorage_Postgres_Ops$ReventlessPostgres.notExpiredClause];
|
|
202
|
+
if (ownerScope !== undefined) {
|
|
203
|
+
whereParts.push(jsonTextC(ownerScope[0]) + ` = ` + param(b, ownerScope[1]));
|
|
204
|
+
}
|
|
205
|
+
if (retiredScope !== undefined) {
|
|
206
|
+
whereParts.push(notRetiredC(retiredScope));
|
|
207
|
+
}
|
|
187
208
|
let valString = v => {
|
|
188
209
|
let s = Stdlib_JSON.Decode.string(v);
|
|
189
210
|
if (s !== undefined) {
|
|
@@ -214,11 +235,11 @@ function Make(P) {
|
|
|
214
235
|
let orderByField = Stdlib_Option.flatMap(Stdlib_Option.flatMap(orderByDict, ob => ob["field"]), Stdlib_JSON.Decode.string);
|
|
215
236
|
let isDesc = Stdlib_Option.getOr(Stdlib_Option.flatMap(Stdlib_Option.flatMap(orderByDict, ob => ob["direction"]), Stdlib_JSON.Decode.string), "ASC") === "DESC";
|
|
216
237
|
let cursorExpr = orderByField !== undefined ? jsonTextC(orderByField) : idExprC;
|
|
217
|
-
let
|
|
218
|
-
if (
|
|
238
|
+
let afterCursor = Stdlib_Option.flatMap(argsDict["after"], Stdlib_JSON.Decode.string);
|
|
239
|
+
if (afterCursor !== undefined) {
|
|
219
240
|
whereParts.push(cursorExpr + ` ` + (
|
|
220
241
|
isDesc ? "<" : ">"
|
|
221
|
-
) + ` ` + param(b, QueryDbListQuery$ReventlessCore.decodeCursor(
|
|
242
|
+
) + ` ` + param(b, QueryDbListQuery$ReventlessCore.decodeCursor(afterCursor)));
|
|
222
243
|
}
|
|
223
244
|
let orderClause = orderByField !== undefined ? jsonTextC(orderByField) + ` ` + (
|
|
224
245
|
isDesc ? "DESC" : "ASC"
|
|
@@ -230,10 +251,10 @@ function Make(P) {
|
|
|
230
251
|
let pageItems = rows.slice(0, pageSize);
|
|
231
252
|
let cursorField = Stdlib_Option.getOr(orderByField, "id");
|
|
232
253
|
let cursorValueOf = item => Stdlib_Option.getOr(QueryDbListQuery$ReventlessCore.getFieldString(item, cursorField), QueryDbListQuery$ReventlessCore.getId(item));
|
|
233
|
-
return QueryDbListQuery$ReventlessCore.buildConnection(pageItems, hasMore,
|
|
254
|
+
return QueryDbListQuery$ReventlessCore.buildConnection(pageItems, hasMore, Stdlib_Option.isSome(afterCursor), cursorValueOf);
|
|
234
255
|
};
|
|
235
|
-
let itemsPage = async (readModelName, param$1, id, argsDict) => {
|
|
236
|
-
let table =
|
|
256
|
+
let itemsPage = async (readModelName, param$1, id, argsDict, ownerScope, retiredScope) => {
|
|
257
|
+
let table = QueryDbStorage_Postgres_Ops$ReventlessPostgres.tableName(readModelName);
|
|
237
258
|
let filterDict = Stdlib_Option.getOr(Stdlib_Option.flatMap(argsDict["filter"], Stdlib_JSON.Decode.object), {});
|
|
238
259
|
let fstr = k => Stdlib_Option.flatMap(filterDict[k], Stdlib_JSON.Decode.string);
|
|
239
260
|
let orderDesc = Stdlib_Option.mapOr(fstr("order"), false, o => o === "DESC");
|
|
@@ -248,8 +269,14 @@ function Make(P) {
|
|
|
248
269
|
};
|
|
249
270
|
let where = [
|
|
250
271
|
`partition_key = ` + param(b, id),
|
|
251
|
-
|
|
272
|
+
QueryDbStorage_Postgres_Ops$ReventlessPostgres.notExpiredClause
|
|
252
273
|
];
|
|
274
|
+
if (ownerScope !== undefined) {
|
|
275
|
+
where.push(jsonTextC(ownerScope[0]) + ` = ` + param(b, ownerScope[1]));
|
|
276
|
+
}
|
|
277
|
+
if (retiredScope !== undefined) {
|
|
278
|
+
where.push(notRetiredC(retiredScope));
|
|
279
|
+
}
|
|
253
280
|
Stdlib_Option.forEach(fstr("prefix"), p => {
|
|
254
281
|
where.push(`starts_with(sub_key, ` + param(b, p) + `)`);
|
|
255
282
|
});
|
|
@@ -304,10 +331,6 @@ function Make(P) {
|
|
|
304
331
|
}
|
|
305
332
|
};
|
|
306
333
|
};
|
|
307
|
-
let make = _allQueryDbs => Pulumi.output({
|
|
308
|
-
scan: scan,
|
|
309
|
-
query: query
|
|
310
|
-
});
|
|
311
334
|
return {
|
|
312
335
|
query: query,
|
|
313
336
|
scan: scan,
|
|
@@ -315,13 +338,13 @@ function Make(P) {
|
|
|
315
338
|
byIds: byIds,
|
|
316
339
|
idExprC: idExprC,
|
|
317
340
|
jsonTextC: jsonTextC,
|
|
341
|
+
notRetiredC: notRetiredC,
|
|
318
342
|
listPage: listPage,
|
|
319
|
-
itemsPage: itemsPage
|
|
320
|
-
make: make
|
|
343
|
+
itemsPage: itemsPage
|
|
321
344
|
};
|
|
322
345
|
}
|
|
323
346
|
|
|
324
|
-
let notExpired =
|
|
347
|
+
let notExpired = QueryDbStorage_Postgres_Ops$ReventlessPostgres.notExpiredClause;
|
|
325
348
|
|
|
326
349
|
export {
|
|
327
350
|
valueToText,
|
|
@@ -334,4 +357,4 @@ export {
|
|
|
334
357
|
decodeRow,
|
|
335
358
|
Make,
|
|
336
359
|
}
|
|
337
|
-
/*
|
|
360
|
+
/* PgDriver-ReventlessPostgres Not a pure module */
|