@steadybrew/postgresjs 4.2.0 → 4.4.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.
- package/README.md +70 -2
- package/cf/src/connection.js +63 -21
- package/cf/src/errors.js +8 -0
- package/cf/src/index.js +100 -33
- package/cf/src/subscribe.js +122 -47
- package/cjs/src/connection.js +63 -21
- package/cjs/src/errors.js +8 -0
- package/cjs/src/index.js +100 -33
- package/cjs/src/subscribe.js +122 -47
- package/package.json +1 -1
- package/src/connection.js +63 -21
- package/src/errors.js +8 -0
- package/src/index.js +100 -33
- package/src/subscribe.js +122 -47
- package/types/index.d.ts +41 -9
package/src/connection.js
CHANGED
|
@@ -5,7 +5,7 @@ import Stream from 'stream'
|
|
|
5
5
|
import { performance } from 'perf_hooks'
|
|
6
6
|
|
|
7
7
|
import { stringify, handleValue, addArrayType } from './types.js'
|
|
8
|
-
import { Errors } from './errors.js'
|
|
8
|
+
import { Errors, callback } from './errors.js'
|
|
9
9
|
import Result from './result.js'
|
|
10
10
|
import Queue from './queue.js'
|
|
11
11
|
import clampedTimeout from './timeout.js'
|
|
@@ -13,7 +13,7 @@ import { SSLRequest, tlsConfig, cancelRequest } from './transport.js'
|
|
|
13
13
|
import { Query, CLOSE } from './query.js'
|
|
14
14
|
import b from './bytes.js'
|
|
15
15
|
|
|
16
|
-
export
|
|
16
|
+
export { Connection }
|
|
17
17
|
|
|
18
18
|
let uid = 1
|
|
19
19
|
|
|
@@ -26,6 +26,8 @@ const Sync = b().S().end()
|
|
|
26
26
|
const Phase = { Closed: 0, Backoff: 1, Connecting: 2, Initializing: 3, Ready: 4, Draining: 5, Closing: 6 }
|
|
27
27
|
const phaseNames = Object.keys(Phase)
|
|
28
28
|
|
|
29
|
+
const endsAbortedState = /^\s*(rollback|abort)\b/i
|
|
30
|
+
|
|
29
31
|
const retryRoutines = new Set([
|
|
30
32
|
'FetchPreparedStatement',
|
|
31
33
|
'RevalidateCachedQuery',
|
|
@@ -110,6 +112,7 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
110
112
|
, chunk = null
|
|
111
113
|
, nonce = null
|
|
112
114
|
, query = null
|
|
115
|
+
, barrier = null
|
|
113
116
|
, final = null
|
|
114
117
|
|
|
115
118
|
const check = globalThis[Symbol.for('postgres.js:check')]
|
|
@@ -222,6 +225,11 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
222
225
|
},
|
|
223
226
|
expired: () => idleTimer.expired() || lifeTimer.expired(),
|
|
224
227
|
owner: null,
|
|
228
|
+
get active() { return query ? 1 : 0 },
|
|
229
|
+
get pipelined() { return sent.length },
|
|
230
|
+
get accepting() { return accepting() },
|
|
231
|
+
get copying() { return stream !== null },
|
|
232
|
+
get acquiring() { return acquisition && !acquisition.owner.cancelled ? 1 : 0 },
|
|
225
233
|
count: 0,
|
|
226
234
|
id
|
|
227
235
|
}
|
|
@@ -265,8 +273,12 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
265
273
|
return !query && sent.length === 0
|
|
266
274
|
}
|
|
267
275
|
|
|
276
|
+
function accepting() {
|
|
277
|
+
return !query || (!barrier && sent.length < max_pipeline)
|
|
278
|
+
}
|
|
279
|
+
|
|
268
280
|
function backoffMs() {
|
|
269
|
-
return (
|
|
281
|
+
return backoffSeconds(backoff, options.shared.retries) * 1000
|
|
270
282
|
}
|
|
271
283
|
|
|
272
284
|
function standbyPass() {
|
|
@@ -443,7 +455,7 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
443
455
|
queryError(pending, err)
|
|
444
456
|
pending.cancelled && pending.cancelled.resolve()
|
|
445
457
|
}
|
|
446
|
-
query = results = errorResponse = chunk = nextWriteTimer = null
|
|
458
|
+
query = results = errorResponse = chunk = nextWriteTimer = barrier = null
|
|
447
459
|
result = new Result()
|
|
448
460
|
rows = 0
|
|
449
461
|
nonce = serverSignature = null
|
|
@@ -507,8 +519,10 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
507
519
|
}
|
|
508
520
|
|
|
509
521
|
function submit(q) {
|
|
510
|
-
if (stream)
|
|
511
|
-
|
|
522
|
+
if (stream) {
|
|
523
|
+
queryError(q, Errors.generic('COPY_IN_PROGRESS', 'You cannot execute queries during copy'))
|
|
524
|
+
return true
|
|
525
|
+
}
|
|
512
526
|
|
|
513
527
|
if (q.cancelled)
|
|
514
528
|
return true
|
|
@@ -522,17 +536,21 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
522
536
|
: (query = q, query.active = true)
|
|
523
537
|
|
|
524
538
|
build(q)
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
539
|
+
const written = write(toBuffer(q))
|
|
540
|
+
if (q.describeFirst || q.cursorFn || mayCopy(q))
|
|
541
|
+
barrier = q
|
|
542
|
+
return written && accepting()
|
|
529
543
|
} catch (error) {
|
|
530
|
-
sent.
|
|
531
|
-
|
|
532
|
-
return
|
|
544
|
+
sent.remove(q) || write(Sync)
|
|
545
|
+
queryError(q, error)
|
|
546
|
+
return accepting()
|
|
533
547
|
}
|
|
534
548
|
}
|
|
535
549
|
|
|
550
|
+
function mayCopy(q) {
|
|
551
|
+
return q.options.simple && /\bcopy\b/i.test(q.string)
|
|
552
|
+
}
|
|
553
|
+
|
|
536
554
|
function toBuffer(q) {
|
|
537
555
|
if (q.parameters.length >= 65534)
|
|
538
556
|
throw Errors.generic('MAX_PARAMETERS_EXCEEDED', 'Max number of parameters (65534) exceeded')
|
|
@@ -591,7 +609,7 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
591
609
|
? statements[q.signature]
|
|
592
610
|
: { string, types, name: q.prepare ? statementId + statementCount++ : '' }
|
|
593
611
|
|
|
594
|
-
typeof options.debug === 'function' && options.debug
|
|
612
|
+
typeof options.debug === 'function' && callback(options.debug, id, string, parameters, types)
|
|
595
613
|
}
|
|
596
614
|
|
|
597
615
|
function write(x, fn) {
|
|
@@ -762,18 +780,21 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
762
780
|
backendParameters[k] = v
|
|
763
781
|
if (options.parameters[k] !== v) {
|
|
764
782
|
options.parameters[k] = v
|
|
765
|
-
onparameter
|
|
783
|
+
callback(onparameter, k, v)
|
|
766
784
|
}
|
|
767
785
|
}
|
|
768
786
|
|
|
769
|
-
function ReadyForQuery() {
|
|
787
|
+
function ReadyForQuery(x) {
|
|
788
|
+
query === barrier && (barrier = null)
|
|
770
789
|
if (query) {
|
|
771
790
|
if (errorResponse) {
|
|
772
791
|
if (query.initialization)
|
|
773
792
|
return dispatch('initFailed', errorResponse)
|
|
793
|
+
query.prepared && retryRoutines.has(errorResponse.routine) && delete statements[query.signature]
|
|
774
794
|
query.retried
|
|
775
795
|
? errored(query.retried)
|
|
776
|
-
: query.prepared && retryRoutines.has(errorResponse.routine) && query.owner === connection.owner
|
|
796
|
+
: query.prepared && retryRoutines.has(errorResponse.routine) && query.owner === connection.owner && !barrier
|
|
797
|
+
&& (x[5] !== 69 || endsAbortedState.test(query.string))
|
|
777
798
|
? retry(query, errorResponse)
|
|
778
799
|
: errored(errorResponse)
|
|
779
800
|
} else {
|
|
@@ -1056,7 +1077,6 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
1056
1077
|
}
|
|
1057
1078
|
|
|
1058
1079
|
function retry(q, error) {
|
|
1059
|
-
delete statements[q.signature]
|
|
1060
1080
|
q.retried = error
|
|
1061
1081
|
execute(q)
|
|
1062
1082
|
}
|
|
@@ -1067,7 +1087,8 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
1067
1087
|
|
|
1068
1088
|
let index = 9
|
|
1069
1089
|
while (x[index++] !== 0);
|
|
1070
|
-
|
|
1090
|
+
callback(
|
|
1091
|
+
onnotify,
|
|
1071
1092
|
x.toString('utf8', 9, index - 1),
|
|
1072
1093
|
x.toString('utf8', index, x.length - 1)
|
|
1073
1094
|
)
|
|
@@ -1113,6 +1134,7 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
1113
1134
|
}
|
|
1114
1135
|
})
|
|
1115
1136
|
query.resolve(stream)
|
|
1137
|
+
connection.owner && connection.owner.next()
|
|
1116
1138
|
}
|
|
1117
1139
|
|
|
1118
1140
|
function CopyOutResponse() {
|
|
@@ -1120,6 +1142,7 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
1120
1142
|
read() { socket.resume() }
|
|
1121
1143
|
})
|
|
1122
1144
|
query.resolve(stream)
|
|
1145
|
+
connection.owner && connection.owner.next()
|
|
1123
1146
|
}
|
|
1124
1147
|
|
|
1125
1148
|
/* c8 ignore next 3 */
|
|
@@ -1142,6 +1165,7 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
1142
1165
|
}
|
|
1143
1166
|
})
|
|
1144
1167
|
query.resolve(stream)
|
|
1168
|
+
connection.owner && connection.owner.next()
|
|
1145
1169
|
}
|
|
1146
1170
|
|
|
1147
1171
|
function CopyData(x) {
|
|
@@ -1154,10 +1178,12 @@ function Connection(options, queues = {}, { onopen = noop, onend = noop, onclose
|
|
|
1154
1178
|
}
|
|
1155
1179
|
|
|
1156
1180
|
function NoticeResponse(x) {
|
|
1181
|
+
if (onnotice === false)
|
|
1182
|
+
return
|
|
1183
|
+
|
|
1157
1184
|
onnotice
|
|
1158
|
-
? onnotice
|
|
1185
|
+
? callback(onnotice, parseError(x))
|
|
1159
1186
|
: console.log(parseError(x)) // eslint-disable-line
|
|
1160
|
-
|
|
1161
1187
|
}
|
|
1162
1188
|
|
|
1163
1189
|
/* c8 ignore next 3 */
|
|
@@ -1308,3 +1334,19 @@ function timer(fn, seconds) {
|
|
|
1308
1334
|
fn.apply(null, args)
|
|
1309
1335
|
}
|
|
1310
1336
|
}
|
|
1337
|
+
|
|
1338
|
+
export function defaultBackoff(retries) {
|
|
1339
|
+
return (0.5 + Math.random() / 2) * Math.min(3 ** retries / 100, 20)
|
|
1340
|
+
}
|
|
1341
|
+
|
|
1342
|
+
export function backoffSeconds(backoff, retries) {
|
|
1343
|
+
if (typeof backoff !== 'function')
|
|
1344
|
+
return backoff
|
|
1345
|
+
|
|
1346
|
+
try {
|
|
1347
|
+
return backoff(retries)
|
|
1348
|
+
} catch (e) {
|
|
1349
|
+
callback(() => { throw e })
|
|
1350
|
+
return defaultBackoff(retries)
|
|
1351
|
+
}
|
|
1352
|
+
}
|
package/src/errors.js
CHANGED
package/src/index.js
CHANGED
|
@@ -8,6 +8,7 @@ import {
|
|
|
8
8
|
Parameter,
|
|
9
9
|
Identifier,
|
|
10
10
|
Builder,
|
|
11
|
+
escapeIdentifier,
|
|
11
12
|
toPascal,
|
|
12
13
|
pascal,
|
|
13
14
|
toCamel,
|
|
@@ -19,12 +20,12 @@ import {
|
|
|
19
20
|
fromKebab
|
|
20
21
|
} from './types.js'
|
|
21
22
|
|
|
22
|
-
import Connection from './connection.js'
|
|
23
|
+
import { Connection, defaultBackoff } from './connection.js'
|
|
23
24
|
import { cancelRequest } from './transport.js'
|
|
24
25
|
import clampedTimeout from './timeout.js'
|
|
25
26
|
import { Query, CLOSE } from './query.js'
|
|
26
27
|
import Queue from './queue.js'
|
|
27
|
-
import { Errors, PostgresError } from './errors.js'
|
|
28
|
+
import { Errors, PostgresError, callback } from './errors.js'
|
|
28
29
|
import Subscribe from './subscribe.js'
|
|
29
30
|
import largeObject from './large.js'
|
|
30
31
|
|
|
@@ -81,6 +82,7 @@ function Postgres(a, b) {
|
|
|
81
82
|
PostgresError,
|
|
82
83
|
options,
|
|
83
84
|
reserve,
|
|
85
|
+
stats,
|
|
84
86
|
listen,
|
|
85
87
|
begin,
|
|
86
88
|
close,
|
|
@@ -150,6 +152,56 @@ function Postgres(a, b) {
|
|
|
150
152
|
}
|
|
151
153
|
}
|
|
152
154
|
|
|
155
|
+
function stats() {
|
|
156
|
+
let idleCount = 0
|
|
157
|
+
, busyCount = 0
|
|
158
|
+
, reservedCount = 0
|
|
159
|
+
, connectingCount = 0
|
|
160
|
+
, closingCount = 0
|
|
161
|
+
, executingCount = 0
|
|
162
|
+
, waitingCount = queries.length
|
|
163
|
+
|
|
164
|
+
for (const c of connections) {
|
|
165
|
+
executingCount += c.active
|
|
166
|
+
waitingCount += c.pipelined + c.acquiring + (c.owner ? c.owner.queue.length : 0)
|
|
167
|
+
c.queue === open
|
|
168
|
+
? idleCount++
|
|
169
|
+
: c.queue === connecting
|
|
170
|
+
? connectingCount++
|
|
171
|
+
: c.queue === ended
|
|
172
|
+
? closingCount++
|
|
173
|
+
: c.queue === reserved
|
|
174
|
+
? reservedCount++
|
|
175
|
+
: (c.queue === busy || c.queue === full) && (c.owner ? reservedCount++ : busyCount++)
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
const totalCount = idleCount + busyCount + reservedCount + connectingCount
|
|
179
|
+
|
|
180
|
+
return {
|
|
181
|
+
max: options.max,
|
|
182
|
+
totalCount,
|
|
183
|
+
idleCount,
|
|
184
|
+
waitingCount,
|
|
185
|
+
activeCount: busyCount + reservedCount,
|
|
186
|
+
availableCount: idleCount + options.max - totalCount - closingCount,
|
|
187
|
+
busyCount,
|
|
188
|
+
reservedCount,
|
|
189
|
+
connectingCount,
|
|
190
|
+
closingCount,
|
|
191
|
+
executingCount,
|
|
192
|
+
listenCount: pooled(listen.sql),
|
|
193
|
+
subscribeCount: pooled(subscribe.sql)
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
function pooled(sql) {
|
|
198
|
+
if (!sql)
|
|
199
|
+
return 0
|
|
200
|
+
|
|
201
|
+
const s = sql.stats()
|
|
202
|
+
return s.totalCount + s.closingCount
|
|
203
|
+
}
|
|
204
|
+
|
|
153
205
|
async function listen(name, fn, onlisten) {
|
|
154
206
|
const listener = { fn, onlisten }
|
|
155
207
|
|
|
@@ -167,7 +219,7 @@ function Postgres(a, b) {
|
|
|
167
219
|
})
|
|
168
220
|
},
|
|
169
221
|
onnotify(c, x) {
|
|
170
|
-
c in listen.channels && listen.channels[c].listeners.forEach(l => l.fn
|
|
222
|
+
c in listen.channels && listen.channels[c].listeners.forEach(l => callback(l.fn, x))
|
|
171
223
|
}
|
|
172
224
|
}))
|
|
173
225
|
|
|
@@ -177,7 +229,7 @@ function Postgres(a, b) {
|
|
|
177
229
|
if (exists) {
|
|
178
230
|
channels[name].listeners.push(listener)
|
|
179
231
|
const result = await channels[name].result
|
|
180
|
-
listener.onlisten
|
|
232
|
+
callback(listener.onlisten)
|
|
181
233
|
return { state: result.state, unlisten }
|
|
182
234
|
}
|
|
183
235
|
|
|
@@ -185,7 +237,7 @@ function Postgres(a, b) {
|
|
|
185
237
|
sql.unsafe('"' + name.replace(/"/g, '""') + '"')
|
|
186
238
|
}`, listeners: [listener] }
|
|
187
239
|
const result = await channels[name].result
|
|
188
|
-
listener.onlisten
|
|
240
|
+
callback(listener.onlisten)
|
|
189
241
|
return { state: result.state, unlisten }
|
|
190
242
|
|
|
191
243
|
async function unlisten() {
|
|
@@ -243,9 +295,9 @@ function Postgres(a, b) {
|
|
|
243
295
|
function send(l, q, expected = Lease.Active) {
|
|
244
296
|
const c = l.connection
|
|
245
297
|
l.state === expected
|
|
246
|
-
? c.queue
|
|
247
|
-
?
|
|
248
|
-
:
|
|
298
|
+
? c.copying || (c.queue !== full && c.accepting)
|
|
299
|
+
? c.execute(q) || move(c, full)
|
|
300
|
+
: (move(c, full), q.queue = l.queue, l.queue.push(q))
|
|
249
301
|
: q.reject(leaseError(l.state))
|
|
250
302
|
}
|
|
251
303
|
|
|
@@ -275,6 +327,7 @@ function Postgres(a, b) {
|
|
|
275
327
|
const l = await lease(false)
|
|
276
328
|
const sql = Sql(q => send(l, q))
|
|
277
329
|
sql.release = () => settle(l, Lease.Released)
|
|
330
|
+
sql.stats = stats
|
|
278
331
|
return sql
|
|
279
332
|
}
|
|
280
333
|
|
|
@@ -300,14 +353,16 @@ function Postgres(a, b) {
|
|
|
300
353
|
}
|
|
301
354
|
|
|
302
355
|
async function finish(statement) {
|
|
356
|
+
let result
|
|
303
357
|
l.state = Lease.Settling
|
|
304
358
|
try {
|
|
305
|
-
await statement(Sql(q => send(l, q, Lease.Settling)))
|
|
359
|
+
result = await statement(Sql(q => send(l, q, Lease.Settling)))
|
|
306
360
|
} catch (e) {
|
|
307
361
|
settle(l, Lease.Discarded)
|
|
308
362
|
throw e
|
|
309
363
|
}
|
|
310
364
|
settle(l, Lease.Released)
|
|
365
|
+
return result
|
|
311
366
|
}
|
|
312
367
|
|
|
313
368
|
async function scope(fn, name) {
|
|
@@ -322,7 +377,7 @@ function Postgres(a, b) {
|
|
|
322
377
|
let uncaughtError
|
|
323
378
|
, result
|
|
324
379
|
|
|
325
|
-
name && await sql
|
|
380
|
+
name && await sql.unsafe('savepoint ' + escapeIdentifier(name))
|
|
326
381
|
try {
|
|
327
382
|
result = await new Promise((resolve, reject) => {
|
|
328
383
|
const x = fn(sql)
|
|
@@ -333,8 +388,8 @@ function Postgres(a, b) {
|
|
|
333
388
|
throw uncaughtError
|
|
334
389
|
} catch (e) {
|
|
335
390
|
l.state === Lease.Active && await (name
|
|
336
|
-
? sql
|
|
337
|
-
: finish(final => final
|
|
391
|
+
? sql.unsafe('rollback to ' + escapeIdentifier(name))
|
|
392
|
+
: finish(final => final.unsafe('rollback'))
|
|
338
393
|
)
|
|
339
394
|
throw e instanceof PostgresError && e.code === '25P02' && uncaughtError || e
|
|
340
395
|
}
|
|
@@ -342,10 +397,18 @@ function Postgres(a, b) {
|
|
|
342
397
|
if (l.state !== Lease.Active)
|
|
343
398
|
throw l.error || leaseError(l.state)
|
|
344
399
|
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
400
|
+
if (!name) {
|
|
401
|
+
const done = await finish(final => prepare
|
|
402
|
+
? final.unsafe('prepare transaction ' + prepare)
|
|
403
|
+
: final.unsafe('commit')
|
|
404
|
+
)
|
|
405
|
+
if (done.command === 'ROLLBACK') {
|
|
406
|
+
throw Object.assign(
|
|
407
|
+
Errors.generic('TRANSACTION_ROLLED_BACK', 'The server rolled the transaction back instead of committing it'),
|
|
408
|
+
uncaughtError && { cause: uncaughtError }
|
|
409
|
+
)
|
|
410
|
+
}
|
|
411
|
+
}
|
|
349
412
|
|
|
350
413
|
return result
|
|
351
414
|
|
|
@@ -374,14 +437,6 @@ function Postgres(a, b) {
|
|
|
374
437
|
return c
|
|
375
438
|
}
|
|
376
439
|
|
|
377
|
-
function callback(fn, ...args) {
|
|
378
|
-
try {
|
|
379
|
-
fn && fn(...args)
|
|
380
|
-
} catch (e) {
|
|
381
|
-
queueMicrotask(() => { throw e })
|
|
382
|
-
}
|
|
383
|
-
}
|
|
384
|
-
|
|
385
440
|
function json(x) {
|
|
386
441
|
return new Parameter(x, 3802)
|
|
387
442
|
}
|
|
@@ -404,11 +459,24 @@ function Postgres(a, b) {
|
|
|
404
459
|
if (closed.length)
|
|
405
460
|
return connect(closed.shift(), query)
|
|
406
461
|
|
|
407
|
-
|
|
408
|
-
|
|
462
|
+
const c = takeBusy()
|
|
463
|
+
c
|
|
464
|
+
? go(c, query)
|
|
409
465
|
: queries.push(query)
|
|
410
466
|
}
|
|
411
467
|
|
|
468
|
+
function takeBusy() {
|
|
469
|
+
while (busy.length) {
|
|
470
|
+
const c = busy.shift()
|
|
471
|
+
if (c.accepting)
|
|
472
|
+
return c
|
|
473
|
+
|
|
474
|
+
move(c, full)
|
|
475
|
+
}
|
|
476
|
+
|
|
477
|
+
return null
|
|
478
|
+
}
|
|
479
|
+
|
|
412
480
|
function takeOpen() {
|
|
413
481
|
while (open.length) {
|
|
414
482
|
const c = open.shift()
|
|
@@ -435,7 +503,7 @@ function Postgres(a, b) {
|
|
|
435
503
|
if (query.state) {
|
|
436
504
|
query.cancelled = { resolve, reject }
|
|
437
505
|
} else {
|
|
438
|
-
queries.remove(query)
|
|
506
|
+
(query.queue || queries).remove(query)
|
|
439
507
|
query.cancelled = true
|
|
440
508
|
query.reject(Errors.generic('57014', 'canceling statement due to user request'))
|
|
441
509
|
resolve()
|
|
@@ -493,6 +561,9 @@ function Postgres(a, b) {
|
|
|
493
561
|
if (initial && initial.reserve)
|
|
494
562
|
return initial.reserve(c)
|
|
495
563
|
|
|
564
|
+
if (!initial && !c.accepting)
|
|
565
|
+
return move(c, full)
|
|
566
|
+
|
|
496
567
|
if (!initial && !queries.length)
|
|
497
568
|
return move(c, open)
|
|
498
569
|
|
|
@@ -531,7 +602,7 @@ function Postgres(a, b) {
|
|
|
531
602
|
function onclose(c, e) {
|
|
532
603
|
move(c, closed)
|
|
533
604
|
c.owner && settle(c.owner, Lease.Closed, e)
|
|
534
|
-
options.onclose
|
|
605
|
+
callback(options.onclose, c.id)
|
|
535
606
|
if (ending)
|
|
536
607
|
return closedWhileEnding(c, e)
|
|
537
608
|
|
|
@@ -586,7 +657,7 @@ function parseOptions(a, b) {
|
|
|
586
657
|
connect_timeout : 30,
|
|
587
658
|
max_lifetime : max_lifetime,
|
|
588
659
|
max_pipeline : 100,
|
|
589
|
-
backoff :
|
|
660
|
+
backoff : defaultBackoff,
|
|
590
661
|
keep_alive : 60,
|
|
591
662
|
prepare : true,
|
|
592
663
|
debug : false,
|
|
@@ -645,10 +716,6 @@ function tsa(o, url, env) {
|
|
|
645
716
|
throw new Error('target_session_attrs ' + x + ' is not supported')
|
|
646
717
|
}
|
|
647
718
|
|
|
648
|
-
function backoff(retries) {
|
|
649
|
-
return (0.5 + Math.random() / 2) * Math.min(3 ** retries / 100, 20)
|
|
650
|
-
}
|
|
651
|
-
|
|
652
719
|
function max_lifetime() {
|
|
653
720
|
return 60 * (30 + Math.random() * 30)
|
|
654
721
|
}
|