-
Notifications
You must be signed in to change notification settings - Fork 1.1k
Closed
Labels
Description
-
Oracle Version: Oracle 11g Enterprise Edition Release 11.2.0.4.0 - 64bit Production
Platform: win32
Version: v12.13.1
Arch: x64
Version String: 5.0.0
Client Version String: 12.1.0.2.0 -
When I set database pool's queueTimeout 0, the queued connection requests are quickly terminated. The document API says when queueTimeout is 0, the queued connection requests are never terminated.
-
The input command like this:
In node-oracledb-5.0.0 root directory, and runnode_modules\.bin\mocha test\pool.js, only test use case test/pool.js2.8.2 generates NJS-040.
Output:
- pool.js
2.8 connection request queue
(node:20180) UnhandledPromiseRejectionWarning: AssertionError: expected null to exist
at F:\ideaworkspace\node-oracledb-5.0.0\test\pool.js:737:28
at F:\ideaworkspace\node-oracledb-5.0.0\lib\util.js:182:7
(node:20180) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
(node:20180) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.
- Code in here, node-oracledb-5.0.0/test/pool.js, modify the
queueTimeout :0:
describe('2.8 connection request queue', function(){
function getBlockingSql(secondsToBlock) {
var blockingSql = '' +
'declare \n' +
' \n' +
' l_start timestamp with local time zone := systimestamp; \n' +
' \n' +
'begin \n' +
' \n' +
' loop \n' +
' exit when l_start + interval \'' + (secondsToBlock || 3) + '\' second <= systimestamp; \n' +
' end loop; \n' +
' \n' +
'end;';
return blockingSql;
}
it('2.8.2 generates NJS-040 if request is queued and queueTimeout expires', function(done) {
oracledb.createPool(
{
user : dbConfig.user,
password : dbConfig.password,
connectString : dbConfig.connectString,
poolMin : 0,
poolMax : 1,
poolIncrement : 1,
poolTimeout : 1,
queueTimeout : 0 //0 seconds
},
function(err, pool){
should.not.exist(err);
async.parallel(
[
function(cb) {
pool.getConnection(function(err, conn) {
should.not.exist(err);
conn.execute(getBlockingSql(4), function(err) {
should.not.exist(err);
conn.release(function(err) {
should.not.exist(err);
cb();
});
});
});
},
function(cb) {
//using setTimeout to help ensure this gets to the db last
setTimeout(function() {
pool.getConnection(function(err, conn) {
should.exist(err);
(err.message.startsWith("NJS-040:")).should.be.true();
should.not.exist(conn);
cb();
});
}, 100);
}
],
function(err){
should.not.exist(err);
pool.terminate(function(err) {
should.not.exist(err);
done();
});
}
);
}
);
});
- My Thought, I see the node-oracledb-5.0.0/lib/pool.js file
async function getConnection(a1)method line:117this._queueTimeout !== 0is alwaystrue, becausethis._queueTimeoutisundefined.
if (this._connectionsOut >= poolMax) {
// when the queue is huge, throw error early without waiting for queue timeout
if (this._connRequestQueue.length >= this.queueMax && this.queueMax >= 0) {
if (this._enableStats) {
this._totalRequestsRejected += 1;
}
throw new Error(nodbUtil.getErrorMessage('NJS-076', this.queueMax));
}
// if too many connections are out, wait until room is made available or the
// queue timeout expires
await new Promise((resolve, reject) => {
// set up a payload which will be added to the queue for processing
const payload = { resolve: resolve, reject: reject };
// if using a queue timeout, establish the timeout so that when it
// expires the payload will be removed from the queue and an exception
// thrown
if (this._queueTimeout !== 0) {
payload.timeoutHandle = setTimeout(() => {
const ix = this._connRequestQueue.indexOf(payload);
if (ix >= 0) {
this._connRequestQueue.splice(ix, 1);
}
if (this._enableStats) {
this._totalRequestTimeouts += 1;
this._totalTimeInQueue += Date.now() - payload.enqueuedTime;
}
reject(new Error(nodbUtil.getErrorMessage('NJS-040',
this.queueTimeout)));
}, this.queueTimeout);
}
// add payload to the queue
this._connRequestQueue.push(payload);
if (this._enableStats) {
payload.enqueuedTime = Date.now();
this._totalRequestsEnqueued += 1;
this._maxQueueLength = Math.max(this._maxQueueLength,
this._connRequestQueue.length);
}
});
// check if pool is draining or closed after delay has completed and throw
// an appropriate error if so
this._checkPoolOpen();
}
matheuspl and caratilos