Skip to content

Commit 2b59209

Browse files
charmanderbrianc
authored andcommitted
Warn when functions intended as constructors are called without new (#2021)
* Warn when pg.Pool() isn’t called as a constructor in preparation for #1541. `eval` is a bit awkward, but it’s more accurate than an `instanceof` check and will work on platforms new enough to support pg 8 (i.e. only not Node 4). * Warn when Query() isn’t called as a constructor
1 parent c1f954b commit 2b59209

File tree

4 files changed

+49
-1
lines changed

4 files changed

+49
-1
lines changed

lib/compat/check-constructor.js

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
'use strict'
2+
3+
const warnDeprecation = require('./warn-deprecation')
4+
5+
// Node 4 doesn’t support new.target.
6+
let hasNewTarget
7+
8+
try {
9+
// eslint-disable-next-line no-eval
10+
eval('(function () { new.target })')
11+
hasNewTarget = true
12+
} catch (error) {
13+
hasNewTarget = false
14+
}
15+
16+
const checkConstructor = (name, code, getNewTarget) => {
17+
if (hasNewTarget && getNewTarget() === undefined) {
18+
warnDeprecation(`Constructing a ${name} without new is deprecated and will stop working in pg 8.`, code)
19+
}
20+
}
21+
22+
module.exports = checkConstructor

lib/compat/warn-deprecation.js

+19
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
'use strict'
2+
3+
const util = require('util')
4+
5+
const dummyFunctions = new Map()
6+
7+
// Node 4 doesn’t support process.emitWarning(message, 'DeprecationWarning', code).
8+
const emitDeprecationWarning = (message, code) => {
9+
let dummy = dummyFunctions.get(code)
10+
11+
if (dummy === undefined) {
12+
dummy = util.deprecate(() => {}, message)
13+
dummyFunctions.set(code, dummy)
14+
}
15+
16+
dummy()
17+
}
18+
19+
module.exports = emitDeprecationWarning

lib/index.js

+4
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,13 @@ var Client = require('./client')
1212
var defaults = require('./defaults')
1313
var Connection = require('./connection')
1414
var Pool = require('pg-pool')
15+
const checkConstructor = require('./compat/check-constructor')
1516

1617
const poolFactory = (Client) => {
1718
var BoundPool = function (options) {
19+
// eslint-disable-next-line no-eval
20+
checkConstructor('pg.Pool', 'PG-POOL-NEW', () => eval('new.target'))
21+
1822
var config = Object.assign({ Client: Client }, options)
1923
return new Pool(config)
2024
}

lib/query.js

+4-1
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,15 @@
99

1010
var EventEmitter = require('events').EventEmitter
1111
var util = require('util')
12+
const checkConstructor = require('./compat/check-constructor')
1213

1314
var Result = require('./result')
1415
var utils = require('./utils')
1516

1617
var Query = function (config, values, callback) {
17-
// use of "new" optional
18+
// use of "new" optional in pg 7
19+
// eslint-disable-next-line no-eval
20+
checkConstructor('Query', 'PG-QUERY-NEW', () => eval('new.target'))
1821
if (!(this instanceof Query)) { return new Query(config, values, callback) }
1922

2023
config = utils.normalizeQueryConfig(config, values, callback)

0 commit comments

Comments
 (0)