Skip to content

Commit b6c5c19

Browse files
committed
copy-from: fix interaction with pg optional timeout mechanism
1 parent 25a0d0d commit b6c5c19

File tree

3 files changed

+47
-2
lines changed

3 files changed

+47
-2
lines changed

README.md

+4
Original file line numberDiff line numberDiff line change
@@ -132,6 +132,10 @@ Since this isn't a module with tons of installs and dependent modules I hope we
132132

133133
## changelog
134134

135+
### version 6.0.2 - published 2021-09-13
136+
137+
- copy-from : fix interaction with `pg` optional timeout mechanism
138+
135139
### version 6.0.1 - published 2021-08-23
136140

137141
- Bugfix for node 14+. The order of _destroy / _final calls are different before and after node 14 which caused an issue with the COPY FROM _destroy implementation that appeared in version 6.0.0.

copy-from.js

+13
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,12 @@ class CopyStreamQuery extends Writable {
2525
connection.query(this.text)
2626
}
2727

28+
callback() {
29+
// this callback is empty but defining it allows
30+
// `pg` to discover it and overwrite it
31+
// with its timeout mechanism when query_timeout config is set
32+
}
33+
2834
_write(chunk, enc, cb) {
2935
this.chunks.push({ chunk: chunk, encoding: enc })
3036
if (this._gotCopyInResponse) {
@@ -104,6 +110,9 @@ class CopyStreamQuery extends Writable {
104110
}
105111

106112
handleError(e) {
113+
// clear `pg` timeout mechanism
114+
this.callback()
115+
107116
if (this.cb_destroy) {
108117
const cb = this.cb_destroy
109118
this.cb_destroy = null
@@ -142,6 +151,10 @@ class CopyStreamQuery extends Writable {
142151
// Note: `pg` currently does not call this callback when the backend
143152
// sends an ErrorResponse message during the query (for example during
144153
// a CopyFail)
154+
155+
// clear `pg` timeout mechanism
156+
this.callback()
157+
145158
this.cb_ReadyForQuery()
146159
this.connection = null
147160
}

test/copy-from.js

+30-2
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,8 @@ const { spawn } = require('child_process')
1111
const copy = require('../').from
1212

1313
describe('copy-from', () => {
14-
function getClient() {
15-
const client = new pg.Client()
14+
function getClient(config) {
15+
const client = new pg.Client(config)
1616
client.connect()
1717
return client
1818
}
@@ -159,6 +159,34 @@ describe('copy-from', () => {
159159
query.end()
160160
})
161161

162+
it('`pg` query_timeout should be properly canceled upon error - issue #125', (done) => {
163+
const fromClient = getClient({ query_timeout: 500 })
164+
fromClient.query('CREATE TEMP TABLE numbers(num int)')
165+
const txt = 'COPY numbers FROM STDIN'
166+
const query = copy(txt)
167+
query.on('error', function (err) {
168+
fromClient.end()
169+
done()
170+
})
171+
fromClient.query(query)
172+
query.write('A')
173+
query.end()
174+
})
175+
176+
it('`pg` query_timeout should be properly canceled upon success - issue #125', (done) => {
177+
const fromClient = getClient({ query_timeout: 1000 })
178+
fromClient.query('CREATE TEMP TABLE numbers(num int)')
179+
const txt = 'COPY numbers FROM STDIN'
180+
const query = copy(txt)
181+
query.on('finish', function (err) {
182+
fromClient.end()
183+
done()
184+
})
185+
fromClient.query(query)
186+
query.write('1')
187+
query.end()
188+
})
189+
162190
describe('stream compliance', () => {
163191
describe('successful stream', () => {
164192
it("emits 1 'finish' (writable stream)", (done) => {

0 commit comments

Comments
 (0)