oracledb 6.6.0 → 6.7.1
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 +2 -2
- package/build/Release/Linux_cmds.txt +972 -0
- package/build/Release/oracledb-6.7.1-darwin-arm64.node +0 -0
- package/build/Release/oracledb-6.7.1-darwin-arm64.node-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.7.1-darwin-x64.node +0 -0
- package/build/Release/oracledb-6.7.1-darwin-x64.node-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.7.1-js-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.7.1-linux-arm64.node +0 -0
- package/build/Release/oracledb-6.7.1-linux-arm64.node-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.7.1-linux-x64.node +0 -0
- package/build/Release/oracledb-6.7.1-linux-x64.node-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.7.1-win32-x64.node +0 -0
- package/build/Release/oracledb-6.7.1-win32-x64.node-buildinfo.txt +1 -0
- package/examples/example.js +5 -5
- package/lib/configProviders/azure.js +26 -15
- package/lib/configProviders/base.js +23 -37
- package/lib/configProviders/ociobject.js +53 -45
- package/lib/connection.js +75 -3
- package/lib/errors.js +26 -14
- package/lib/impl/aqQueue.js +2 -1
- package/lib/impl/base.js +45 -0
- package/lib/impl/connection.js +53 -0
- package/lib/impl/lob.js +2 -1
- package/lib/impl/pool.js +15 -0
- package/lib/impl/resultset.js +2 -1
- package/lib/impl/sodaCollection.js +2 -1
- package/lib/impl/sodaDatabase.js +2 -1
- package/lib/impl/sodaDocCursor.js +2 -1
- package/lib/impl/sodaOperation.js +2 -1
- package/lib/lob.js +3 -2
- package/lib/oracledb.js +221 -36
- package/lib/pool.js +14 -5
- package/lib/settings.js +1 -0
- package/lib/thin/connection.js +150 -91
- package/lib/thin/dbObject.js +13 -4
- package/lib/thin/pool.js +3 -0
- package/lib/thin/protocol/constants.js +1 -1
- package/lib/thin/protocol/messages/auth.js +12 -6
- package/lib/thin/protocol/messages/base.js +3 -0
- package/lib/thin/protocol/messages/sessionRelease.js +1 -0
- package/lib/thin/protocol/messages/withData.js +6 -13
- package/lib/thin/protocol/protocol.js +23 -0
- package/lib/thin/sqlnet/connStrategy.js +12 -3
- package/lib/thin/sqlnet/constants.js +2 -0
- package/lib/thin/sqlnet/navNodes.js +30 -23
- package/lib/thin/sqlnet/networkSession.js +18 -14
- package/lib/thin/sqlnet/ntTcp.js +12 -6
- package/lib/thin/sqlnet/nvStrToNvPair.js +23 -26
- package/lib/thin/sqlnet/paramParser.js +42 -43
- package/lib/thin/sqlnet/sessionAtts.js +1 -1
- package/lib/thin/util.js +4 -3
- package/lib/traceHandler.js +133 -0
- package/lib/util.js +177 -33
- package/lib/version.js +2 -2
- package/package.json +1 -1
- package/build/Release/oracledb-6.6.0-darwin-arm64.node +0 -0
- package/build/Release/oracledb-6.6.0-darwin-arm64.node-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.6.0-darwin-x64.node +0 -0
- package/build/Release/oracledb-6.6.0-darwin-x64.node-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.6.0-js-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.6.0-linux-arm64.node +0 -0
- package/build/Release/oracledb-6.6.0-linux-arm64.node-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.6.0-linux-x64.node +0 -0
- package/build/Release/oracledb-6.6.0-linux-x64.node-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.6.0-win32-x64.node +0 -0
- package/build/Release/oracledb-6.6.0-win32-x64.node-buildinfo.txt +0 -1
- package/examples/README.md +0 -138
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// Copyright (c) 2022,
|
|
1
|
+
// Copyright (c) 2022, 2024, Oracle and/or its affiliates.
|
|
2
2
|
|
|
3
3
|
//-----------------------------------------------------------------------------
|
|
4
4
|
//
|
|
@@ -315,6 +315,7 @@ class Description {
|
|
|
315
315
|
}
|
|
316
316
|
}
|
|
317
317
|
}
|
|
318
|
+
|
|
318
319
|
toString() {
|
|
319
320
|
let s = new String(""), child ;
|
|
320
321
|
|
|
@@ -428,9 +429,6 @@ class DescriptionList {
|
|
|
428
429
|
}
|
|
429
430
|
|
|
430
431
|
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
432
|
/**
|
|
435
433
|
* Class that contains information about a possible connection.
|
|
436
434
|
*/
|
|
@@ -453,6 +451,7 @@ const NavSchemaObject = {
|
|
|
453
451
|
const options = {
|
|
454
452
|
all: true,
|
|
455
453
|
};
|
|
454
|
+
|
|
456
455
|
/**
|
|
457
456
|
* Class that navigates the address node in the tree.
|
|
458
457
|
*/
|
|
@@ -460,16 +459,17 @@ class NavAddress extends Address {
|
|
|
460
459
|
constructor() {
|
|
461
460
|
super();
|
|
462
461
|
}
|
|
462
|
+
|
|
463
463
|
/**
|
|
464
464
|
* Set the connection option to this address.
|
|
465
465
|
* @param {object} cs
|
|
466
466
|
*/
|
|
467
467
|
async navigate(cs) {
|
|
468
468
|
let addresses;
|
|
469
|
-
let nullHost =
|
|
469
|
+
let nullHost = false;
|
|
470
470
|
let needToCloseDescription = false;
|
|
471
471
|
if (!this.host) {
|
|
472
|
-
nullHost =
|
|
472
|
+
nullHost = true;
|
|
473
473
|
this.host = os.hostname();
|
|
474
474
|
try {
|
|
475
475
|
await dnsPromises.lookup(this.host, options);
|
|
@@ -495,7 +495,7 @@ class NavAddress extends Address {
|
|
|
495
495
|
co.httpsProxyPort = this.httpsProxyPort;
|
|
496
496
|
co.desc = cs.getcurrentDescription();
|
|
497
497
|
co.CNdata.push(cs.sBuf.join(""));
|
|
498
|
-
if (nullHost
|
|
498
|
+
if (nullHost)
|
|
499
499
|
co.CNdata.push('(address=(protocol=' + this.prot + ')(host=' + this.host + ')(port=' + this.port + '))');
|
|
500
500
|
else
|
|
501
501
|
co.CNdata.push(this.toString());
|
|
@@ -505,6 +505,8 @@ class NavAddress extends Address {
|
|
|
505
505
|
}
|
|
506
506
|
} catch {
|
|
507
507
|
// do nothing
|
|
508
|
+
// Any error in the try block is ignored, because we want to try
|
|
509
|
+
// the next address
|
|
508
510
|
}
|
|
509
511
|
} else {
|
|
510
512
|
const co = new ConnOption();
|
|
@@ -527,8 +529,6 @@ class NavAddress extends Address {
|
|
|
527
529
|
|
|
528
530
|
}
|
|
529
531
|
|
|
530
|
-
|
|
531
|
-
|
|
532
532
|
/**
|
|
533
533
|
* AddToString is used to construct a string representation of the TNS
|
|
534
534
|
* Address. Constructing a string is mainly needed when source route is ON.
|
|
@@ -557,10 +557,10 @@ class NavAddressList extends AddressList {
|
|
|
557
557
|
}
|
|
558
558
|
|
|
559
559
|
/**
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
560
|
+
* Method decides how to traverse and sets the active children based on
|
|
561
|
+
* the loadbalancing, failover values.
|
|
562
|
+
* @param {object} cs
|
|
563
|
+
*/
|
|
564
564
|
async navigate(cs) {
|
|
565
565
|
await this.navigate2(cs, 0);
|
|
566
566
|
}
|
|
@@ -592,6 +592,7 @@ class NavAddressList extends AddressList {
|
|
|
592
592
|
cs.sBuf.length = this.sBuflength;
|
|
593
593
|
|
|
594
594
|
}
|
|
595
|
+
|
|
595
596
|
addToString(cs) {
|
|
596
597
|
const NVString = this.toString();
|
|
597
598
|
let cOpts = new Array();
|
|
@@ -604,7 +605,6 @@ class NavAddressList extends AddressList {
|
|
|
604
605
|
}
|
|
605
606
|
}
|
|
606
607
|
|
|
607
|
-
|
|
608
608
|
getChildrenSize() {
|
|
609
609
|
let size = 0;
|
|
610
610
|
for (let i = 0; i < this.activeChildren.length; i++) {
|
|
@@ -762,7 +762,6 @@ class NavDescription extends Description {
|
|
|
762
762
|
}
|
|
763
763
|
|
|
764
764
|
closeNVPair(cs) {
|
|
765
|
-
|
|
766
765
|
if (cs.getcurrentDescription() == null)
|
|
767
766
|
return;
|
|
768
767
|
let cOpts = new Array();
|
|
@@ -777,8 +776,20 @@ class NavDescription extends Description {
|
|
|
777
776
|
if (this.connectData == null) {
|
|
778
777
|
this.connectData = "(SERVICE_NAME=)";
|
|
779
778
|
}
|
|
780
|
-
|
|
781
|
-
|
|
779
|
+
|
|
780
|
+
let pgmName = cInfo.program;
|
|
781
|
+
if (cs.program) {
|
|
782
|
+
pgmName = cs.program;
|
|
783
|
+
}
|
|
784
|
+
let hostName = cInfo.hostName;
|
|
785
|
+
if (cs.machine) {
|
|
786
|
+
hostName = cs.machine;
|
|
787
|
+
}
|
|
788
|
+
let userName = cInfo.userName;
|
|
789
|
+
if (cs.osUser) {
|
|
790
|
+
userName = cs.osUser;
|
|
791
|
+
}
|
|
792
|
+
const cid = `(CID=(PROGRAM=${pgmName})(HOST=${hostName})(USER=${userName}))`;
|
|
782
793
|
cOpts[i].CNdata.push(NavSchemaObject.CD);
|
|
783
794
|
cOpts[i].CNdata.push(this.connectData);
|
|
784
795
|
cOpts[i].CNdata.push(cid);
|
|
@@ -800,11 +811,9 @@ class NavDescription extends Description {
|
|
|
800
811
|
}
|
|
801
812
|
|
|
802
813
|
getIntValue(stringInt, defaultValue) {
|
|
803
|
-
|
|
814
|
+
if (/^\d+$/.test(stringInt))
|
|
804
815
|
return parseInt(stringInt);
|
|
805
|
-
|
|
806
|
-
return defaultValue;
|
|
807
|
-
}
|
|
816
|
+
return defaultValue;
|
|
808
817
|
}
|
|
809
818
|
|
|
810
819
|
}
|
|
@@ -872,7 +881,5 @@ class NavDescriptionList extends DescriptionList {
|
|
|
872
881
|
|
|
873
882
|
}
|
|
874
883
|
|
|
875
|
-
|
|
876
|
-
|
|
877
884
|
}
|
|
878
885
|
module.exports = {NavAddress, NavAddressList, NavDescription, NavDescriptionList};
|
|
@@ -46,7 +46,7 @@ const downHostInstance = require("./connStrategy.js").SOLE_INST_DHCACHE;
|
|
|
46
46
|
|
|
47
47
|
async function getConnectionInfo(userConfig) {
|
|
48
48
|
const connStr = await resolveConnectStr(userConfig.connectString, userConfig.configDir);
|
|
49
|
-
const addressNode = await createNode(connStr);
|
|
49
|
+
const addressNode = await createNode(connStr, userConfig);
|
|
50
50
|
let nvpair;
|
|
51
51
|
if (typeof connStr === 'string')
|
|
52
52
|
nvpair = createNVPair(connStr);
|
|
@@ -97,9 +97,9 @@ async function resolveConnectStr(connectString, configDir) {
|
|
|
97
97
|
|
|
98
98
|
}
|
|
99
99
|
|
|
100
|
-
async function resolveAddress(connStr,
|
|
101
|
-
const connstr = await resolveConnectStr(connStr, configDir);
|
|
102
|
-
return createNode(connstr);
|
|
100
|
+
async function resolveAddress(connStr, userConfig) {
|
|
101
|
+
const connstr = await resolveConnectStr(connStr, userConfig.configDir);
|
|
102
|
+
return createNode(connstr, userConfig);
|
|
103
103
|
}
|
|
104
104
|
|
|
105
105
|
/**
|
|
@@ -143,6 +143,7 @@ class NetworkSession {
|
|
|
143
143
|
async getAddress(addressNode, userConfig) {
|
|
144
144
|
/* Get the next address */
|
|
145
145
|
const address = await addressNode.execute(userConfig);
|
|
146
|
+
|
|
146
147
|
/* Prepare connection attributes */
|
|
147
148
|
const uuid = this.sAtts ? this.sAtts.uuid : null;
|
|
148
149
|
this.sAtts = new SessionAtts(uuid);
|
|
@@ -196,10 +197,12 @@ class NetworkSession {
|
|
|
196
197
|
}
|
|
197
198
|
|
|
198
199
|
/**
|
|
199
|
-
* Establish network session
|
|
200
|
-
*
|
|
200
|
+
* Establish network session. Make transport level connection, send
|
|
201
|
+
* NSPTCN(connect packet) and read the response. @returns NetError.
|
|
202
|
+
* (connection successfully established(NetError.CONNECTED)
|
|
203
|
+
* or reason for failure)
|
|
201
204
|
*/
|
|
202
|
-
async connect2(address) {
|
|
205
|
+
async connect2(address, userConfig) {
|
|
203
206
|
/* Sanitise SDU */
|
|
204
207
|
if (this.sAtts.sdu) {
|
|
205
208
|
if (this.sAtts.sdu > constants.NSPABSSDULN) {
|
|
@@ -269,7 +272,7 @@ class NetworkSession {
|
|
|
269
272
|
redirConnData = this.cData;
|
|
270
273
|
}
|
|
271
274
|
|
|
272
|
-
const redirAddressNode = await resolveAddress(adrStr);
|
|
275
|
+
const redirAddressNode = await resolveAddress(adrStr, userConfig);
|
|
273
276
|
const host = address.hostname;
|
|
274
277
|
address = await redirAddressNode.execute();
|
|
275
278
|
if (address.desc)
|
|
@@ -314,10 +317,10 @@ class NetworkSession {
|
|
|
314
317
|
do {
|
|
315
318
|
try {
|
|
316
319
|
if (this.sAtts.connectTimeout) {
|
|
317
|
-
const asyncPromise = this.connect2(address);
|
|
320
|
+
const asyncPromise = this.connect2(address, userConfig);
|
|
318
321
|
connected = await timeout(asyncPromise, this.sAtts.connectTimeout, "connectTimeout", address, this.sAtts.connectionId);
|
|
319
322
|
} else {
|
|
320
|
-
connected = await this.connect2(address);
|
|
323
|
+
connected = await this.connect2(address, userConfig);
|
|
321
324
|
}
|
|
322
325
|
} catch (err) {
|
|
323
326
|
if (err.message.startsWith('NJS-510') && !this.ntAdapter.connected) {
|
|
@@ -528,14 +531,14 @@ class NetworkSession {
|
|
|
528
531
|
addressNode = userConfig._connInfo[5];
|
|
529
532
|
addressNode.reset();
|
|
530
533
|
} else {
|
|
531
|
-
addressNode = await resolveAddress(connStr, userConfig
|
|
534
|
+
addressNode = await resolveAddress(connStr, userConfig);
|
|
532
535
|
}
|
|
533
536
|
let address;
|
|
534
537
|
try {
|
|
535
538
|
address = await this.getAddress(addressNode, userConfig);
|
|
536
539
|
} catch (err) {
|
|
537
|
-
if (err.message == "All options tried") /* Not even one valid
|
|
538
|
-
errors.throwErr(errors.
|
|
540
|
+
if (err.message == "All options tried") /* Not even one valid address */
|
|
541
|
+
errors.throwErr(errors.ERR_HOST_NOT_FOUND);
|
|
539
542
|
else
|
|
540
543
|
errors.throwErr(errors.ERR_INVALID_CONNECT_STRING_PARAMETERS, err.message);
|
|
541
544
|
}
|
|
@@ -617,7 +620,8 @@ class NetworkSession {
|
|
|
617
620
|
/**
|
|
618
621
|
* receive inband notification
|
|
619
622
|
* @param {Object} obj Return the notification into user provided object
|
|
620
|
-
* @returns Error number sent from server, or error on the connection.
|
|
623
|
+
* @returns Error number sent from server, or error on the connection.
|
|
624
|
+
* returns 0 if healthy connection
|
|
621
625
|
*/
|
|
622
626
|
recvInbandNotif() {
|
|
623
627
|
let error = 0;
|
package/lib/thin/sqlnet/ntTcp.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// Copyright (c) 2022,
|
|
1
|
+
// Copyright (c) 2022, 2024, Oracle and/or its affiliates.
|
|
2
2
|
|
|
3
3
|
//-----------------------------------------------------------------------------
|
|
4
4
|
//
|
|
@@ -72,7 +72,7 @@ class NTTCP {
|
|
|
72
72
|
}
|
|
73
73
|
|
|
74
74
|
/**
|
|
75
|
-
* DN matching
|
|
75
|
+
* DN matching function(used with TLS)
|
|
76
76
|
*/
|
|
77
77
|
dnMatch(serverName, cert) {
|
|
78
78
|
if (this.atts.sslServerDNMatch && this.doDNMatch) {
|
|
@@ -211,7 +211,7 @@ class NTTCP {
|
|
|
211
211
|
|
|
212
212
|
try {
|
|
213
213
|
await this.ntConnect(address);
|
|
214
|
-
if (this.atts.expireTime || this.atts.enableDCD) { /* Set
|
|
214
|
+
if (this.atts.expireTime || this.atts.enableDCD) { /* Set KeepAlives */
|
|
215
215
|
if (this.atts.expireTime) {
|
|
216
216
|
this.stream.setKeepAlive(true, this.atts.expireTime);
|
|
217
217
|
} else {
|
|
@@ -234,7 +234,7 @@ class NTTCP {
|
|
|
234
234
|
ca: this.atts.wallet,
|
|
235
235
|
});
|
|
236
236
|
} catch (err) {
|
|
237
|
-
errors.throwErr(errors.ERR_TLS_INIT_FAILURE);
|
|
237
|
+
errors.throwErr(errors.ERR_TLS_INIT_FAILURE, err.message);
|
|
238
238
|
}
|
|
239
239
|
await this.tlsConnect(secureContext, this.stream);
|
|
240
240
|
}
|
|
@@ -248,7 +248,7 @@ class NTTCP {
|
|
|
248
248
|
/**
|
|
249
249
|
* Disconnect Network Transoprt
|
|
250
250
|
* @param {int} type
|
|
251
|
-
* @returns
|
|
251
|
+
* @returns Promise
|
|
252
252
|
*/
|
|
253
253
|
disconnect(type) { /* Disconnect function for TCP sockets */
|
|
254
254
|
if (this.connected && !this.err) {
|
|
@@ -470,8 +470,9 @@ class NTTCP {
|
|
|
470
470
|
* @returns Promise
|
|
471
471
|
*/
|
|
472
472
|
async renegTLS() {
|
|
473
|
+
let initTLSDone = false;
|
|
474
|
+
this.checkErr();
|
|
473
475
|
try {
|
|
474
|
-
this.checkErr();
|
|
475
476
|
this.doDNMatch = true;
|
|
476
477
|
const secureContext = tls.createSecureContext({
|
|
477
478
|
cert: this.atts.wallet,
|
|
@@ -479,7 +480,12 @@ class NTTCP {
|
|
|
479
480
|
passphrase: this.atts.walletPassword,
|
|
480
481
|
ca: this.atts.wallet,
|
|
481
482
|
});
|
|
483
|
+
initTLSDone = true;
|
|
482
484
|
await this.tlsConnect(secureContext, this.connStream);
|
|
485
|
+
} catch (err) {
|
|
486
|
+
if (!initTLSDone)
|
|
487
|
+
errors.throwErr(errors.ERR_TLS_INIT_FAILURE, err.message);
|
|
488
|
+
else throw err;
|
|
483
489
|
} finally {
|
|
484
490
|
this.setupEventHandlers();
|
|
485
491
|
}
|
|
@@ -68,6 +68,9 @@ class NVPair {
|
|
|
68
68
|
this.listType = LIST_REGULAR;
|
|
69
69
|
this.rhsType = RHS_NONE;
|
|
70
70
|
}
|
|
71
|
+
/**
|
|
72
|
+
* @param {string} atom - input atom string literal
|
|
73
|
+
*/
|
|
71
74
|
set setAtom(atom) {
|
|
72
75
|
if (this._containsComment(atom)) {
|
|
73
76
|
errors.throwErr(errors.ERR_INVALID_CONNECT_STRING_SYNTAX);
|
|
@@ -122,7 +125,7 @@ class NVPair {
|
|
|
122
125
|
}
|
|
123
126
|
/**
|
|
124
127
|
* adds a nvpair to the existing one.
|
|
125
|
-
* @param {
|
|
128
|
+
* @param {NVPair} pair
|
|
126
129
|
*/
|
|
127
130
|
addListElement(pair) {
|
|
128
131
|
if (this.list == null) {
|
|
@@ -147,11 +150,11 @@ class NVPair {
|
|
|
147
150
|
}
|
|
148
151
|
}
|
|
149
152
|
/**
|
|
150
|
-
* Returns an empty string with the number specified in the argument. Used
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
153
|
+
* Returns an empty string with the number specified in the argument. Used
|
|
154
|
+
* for indentation of multi-level NVPairs as they are stored
|
|
155
|
+
*
|
|
156
|
+
* @param count
|
|
157
|
+
* Number of spaces required in the blank string.
|
|
155
158
|
*/
|
|
156
159
|
_space(count) {
|
|
157
160
|
var blank_str = "";
|
|
@@ -274,9 +277,9 @@ const TKN_LF_VALUE = '\n';
|
|
|
274
277
|
const TKN_CR_VALUE = '\r';
|
|
275
278
|
|
|
276
279
|
/**
|
|
277
|
-
* The NVTokens class is used to help break NVStrings apart into tokens, such
|
|
278
|
-
* TKN_LPAREN or TKN_LITERAL - this helps simplify the task of building
|
|
279
|
-
* from an NVString.
|
|
280
|
+
* The NVTokens class is used to help break NVStrings apart into tokens, such
|
|
281
|
+
* as TKN_LPAREN or TKN_LITERAL - this helps simplify the task of building
|
|
282
|
+
* NVPairs from an NVString.
|
|
280
283
|
*/
|
|
281
284
|
class NVTokens {
|
|
282
285
|
|
|
@@ -435,9 +438,8 @@ class NVTokens {
|
|
|
435
438
|
return true;
|
|
436
439
|
}
|
|
437
440
|
/**
|
|
438
|
-
* Returns current token. Throws Error if no string has
|
|
439
|
-
*
|
|
440
|
-
* the token position.
|
|
441
|
+
* Returns current token. Throws Error if no string has been parsed,
|
|
442
|
+
* or if there are no tokens left. Does NOT advance the token position.
|
|
441
443
|
*/
|
|
442
444
|
getToken() {
|
|
443
445
|
if (this.tkType == null) { // nothing parsed
|
|
@@ -451,9 +453,8 @@ class NVTokens {
|
|
|
451
453
|
}
|
|
452
454
|
|
|
453
455
|
/**
|
|
454
|
-
* Returns current token. Throws Error if no string has
|
|
455
|
-
*
|
|
456
|
-
* token position.
|
|
456
|
+
* Returns current token. Throws Error if no string has been parsed,
|
|
457
|
+
* or if there are no tokens left. DOES advance the token position.
|
|
457
458
|
*/
|
|
458
459
|
popToken() {
|
|
459
460
|
let token = TKN_NONE;
|
|
@@ -470,9 +471,8 @@ class NVTokens {
|
|
|
470
471
|
}
|
|
471
472
|
/**
|
|
472
473
|
* Returns literal for current token. If current token is NOT a TKN_LITERAL,
|
|
473
|
-
* it returns a string representation of the current token. Throws
|
|
474
|
-
*
|
|
475
|
-
* if there are no tokens left.
|
|
474
|
+
* it returns a string representation of the current token. Throws Error
|
|
475
|
+
* if no string has been parsed, or if there are no tokens left.
|
|
476
476
|
*
|
|
477
477
|
* DOES NOT advance the token position.
|
|
478
478
|
*/
|
|
@@ -492,9 +492,8 @@ class NVTokens {
|
|
|
492
492
|
|
|
493
493
|
/**
|
|
494
494
|
* Returns literal for current token. If current token is NOT a TKN_LITERAL,
|
|
495
|
-
* it returns a string representation of the current token. Throws
|
|
496
|
-
*
|
|
497
|
-
* if there are no tokens left.
|
|
495
|
+
* it returns a string representation of the current token. Throws Error
|
|
496
|
+
* if no string has been parsed, or if there are no tokens left.
|
|
498
497
|
*
|
|
499
498
|
* DOES advance the token position.
|
|
500
499
|
*/
|
|
@@ -547,8 +546,6 @@ class NVTokens {
|
|
|
547
546
|
}
|
|
548
547
|
|
|
549
548
|
|
|
550
|
-
|
|
551
|
-
|
|
552
549
|
/**
|
|
553
550
|
* The NVFactory class is used to help interpret the tokens generated by
|
|
554
551
|
* NVTokens from an NVString.
|
|
@@ -696,7 +693,7 @@ function readNVList(nvt, parent) {
|
|
|
696
693
|
|
|
697
694
|
/**
|
|
698
695
|
* Returns a NVPair whose name matches (ignoring case) the specified
|
|
699
|
-
* name. This function does search recursively through all
|
|
696
|
+
* name. This function does search recursively through all descendants
|
|
700
697
|
* of the specified NVPair.
|
|
701
698
|
* @param nvp NVPair to search through
|
|
702
699
|
* @param name name to match (ignoring case)
|
|
@@ -726,8 +723,8 @@ function findNVPairRecurse(nvp, name) {
|
|
|
726
723
|
}
|
|
727
724
|
|
|
728
725
|
/**
|
|
729
|
-
* Returns a NVPair whose name matches (ignoring case) the specified
|
|
730
|
-
*
|
|
726
|
+
* Returns a NVPair whose name matches (ignoring case) the specified name.
|
|
727
|
+
* This functions only searches the direct descendants of specified NVPair
|
|
731
728
|
* @param nvp NVPair to search through
|
|
732
729
|
* @param name name to match (ignoring case)
|
|
733
730
|
*/
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// Copyright (c) 2022,
|
|
1
|
+
// Copyright (c) 2022, 2024, Oracle and/or its affiliates.
|
|
2
2
|
|
|
3
3
|
//-----------------------------------------------------------------------------
|
|
4
4
|
//
|
|
@@ -26,7 +26,7 @@
|
|
|
26
26
|
|
|
27
27
|
'use strict';
|
|
28
28
|
|
|
29
|
-
const {createNVPair
|
|
29
|
+
const {createNVPair} = require("./nvStrToNvPair.js");
|
|
30
30
|
const fs = require('fs');
|
|
31
31
|
const process = require('process');
|
|
32
32
|
const readline = require('readline');
|
|
@@ -59,12 +59,21 @@ function tnsnamesFilePath(configDir) {
|
|
|
59
59
|
return filePathVal;
|
|
60
60
|
}
|
|
61
61
|
}
|
|
62
|
+
//Structure for each tnsnames.ora file
|
|
63
|
+
class tnsnamesElement {
|
|
62
64
|
|
|
65
|
+
constructor() {
|
|
66
|
+
this.readInProgress = false;
|
|
67
|
+
this.waiters = [];
|
|
68
|
+
this.aliasht = new Map(); // It will have key as alias and value as its aliases value
|
|
69
|
+
this.modTime = new Map(); // It will have tnsnames filename and also all its ifile and its modified time
|
|
70
|
+
}
|
|
71
|
+
}
|
|
63
72
|
class NLParamParser {
|
|
64
73
|
|
|
65
74
|
constructor() {
|
|
66
|
-
|
|
67
|
-
this.
|
|
75
|
+
// key as tnsnames.ora(file_name) and value will be tnsnamesStruct<ht(alias key and value), modTime>
|
|
76
|
+
this.tnsnamesHT = new Map();
|
|
68
77
|
}
|
|
69
78
|
/**
|
|
70
79
|
* Reads the given file line by line and stores the
|
|
@@ -73,29 +82,35 @@ class NLParamParser {
|
|
|
73
82
|
* @returns {Promise}
|
|
74
83
|
*/
|
|
75
84
|
async initializeNlpa(file_path) {
|
|
76
|
-
|
|
85
|
+
let tnsFileStruct;
|
|
86
|
+
if (this.tnsnamesHT.has(file_path))
|
|
87
|
+
tnsFileStruct = this.tnsnamesHT.get(file_path);
|
|
88
|
+
else
|
|
89
|
+
tnsFileStruct = new tnsnamesElement();
|
|
90
|
+
if (tnsFileStruct.readInProgress) {
|
|
77
91
|
await new Promise((resolve) => {
|
|
78
|
-
|
|
92
|
+
tnsFileStruct.waiters.push(resolve);
|
|
79
93
|
});
|
|
80
94
|
}
|
|
81
|
-
|
|
95
|
+
/* check modification time of all files in the cache
|
|
96
|
+
including the file_path */
|
|
97
|
+
if (!this.checkModfTime(tnsFileStruct)) {
|
|
82
98
|
/* No File has been modified */
|
|
83
|
-
return
|
|
99
|
+
return tnsFileStruct.aliasht;
|
|
84
100
|
}
|
|
85
|
-
|
|
86
|
-
this.
|
|
87
|
-
this.
|
|
88
|
-
|
|
89
|
-
return this.ht;
|
|
101
|
+
tnsFileStruct.readInProgress = true;
|
|
102
|
+
await this.start(file_path, 0, tnsFileStruct); //start with 0 depth (tnsnames.ora)
|
|
103
|
+
this.tnsnamesHT.set(file_path, tnsFileStruct);
|
|
104
|
+
return tnsFileStruct.aliasht;
|
|
90
105
|
}
|
|
91
106
|
|
|
92
|
-
async start(file_path, depth) {
|
|
107
|
+
async start(file_path, depth, tnsFileStruct) {
|
|
93
108
|
|
|
94
109
|
if (depth > MAX_IFILE_DEPTH)
|
|
95
110
|
return; //ignore after max depth
|
|
96
111
|
const stat = fs.statSync(file_path);
|
|
97
112
|
// store file path and its modified time.
|
|
98
|
-
|
|
113
|
+
tnsFileStruct.modTime.set(file_path, stat.mtime);
|
|
99
114
|
// Creating a readable stream from file
|
|
100
115
|
// readline module reads line by line
|
|
101
116
|
// but from a readable stream only.
|
|
@@ -129,7 +144,7 @@ class NLParamParser {
|
|
|
129
144
|
nvElem = nvElem + line;
|
|
130
145
|
|
|
131
146
|
} else if (nvElem.length != 0) {
|
|
132
|
-
await this.addNLPListElement(nvElem, depth); // Add Parameter to Hashtable
|
|
147
|
+
await this.addNLPListElement(nvElem, depth, tnsFileStruct); // Add Parameter to Hashtable
|
|
133
148
|
nvElem = ""; // Clear first, before storing current line
|
|
134
149
|
|
|
135
150
|
line = this.checkNLPforComments(line);
|
|
@@ -138,12 +153,12 @@ class NLParamParser {
|
|
|
138
153
|
}
|
|
139
154
|
}
|
|
140
155
|
if (nvElem.length != 0) { // at eof, still one more parameter to read
|
|
141
|
-
await this.addNLPListElement(nvElem, depth);
|
|
156
|
+
await this.addNLPListElement(nvElem, depth, tnsFileStruct);
|
|
142
157
|
nvElem = ""; // clear nvElem buffer after added
|
|
143
158
|
}
|
|
144
|
-
|
|
159
|
+
tnsFileStruct.readInProgress = false;
|
|
145
160
|
let waiter;
|
|
146
|
-
while ((waiter =
|
|
161
|
+
while ((waiter = tnsFileStruct.waiters.pop())) {
|
|
147
162
|
waiter();
|
|
148
163
|
}
|
|
149
164
|
}
|
|
@@ -173,9 +188,11 @@ class NLParamParser {
|
|
|
173
188
|
return str1.join('');
|
|
174
189
|
}
|
|
175
190
|
// check if any of the IFiles has been changed
|
|
176
|
-
checkModfTime() {
|
|
177
|
-
if
|
|
178
|
-
|
|
191
|
+
checkModfTime(tnsFileStruct) {
|
|
192
|
+
// There may be multiple tnsnames.ora files. So check if the tnsnames.ora
|
|
193
|
+
// in question is already cached
|
|
194
|
+
if (tnsFileStruct.modTime.size != 0) {
|
|
195
|
+
for (const [key, value] of tnsFileStruct.modTime) {
|
|
179
196
|
if (fs.existsSync(key)) {
|
|
180
197
|
const stat = fs.statSync(key);
|
|
181
198
|
if ((stat.mtime - value > 0)) {
|
|
@@ -193,7 +210,7 @@ class NLParamParser {
|
|
|
193
210
|
* adds name value pairs from the input buffer into the hash table.
|
|
194
211
|
* @param {string} ibuf
|
|
195
212
|
*/
|
|
196
|
-
async addNLPListElement(ibuf, depth) {
|
|
213
|
+
async addNLPListElement(ibuf, depth, tnsFileStruct) {
|
|
197
214
|
const res = ibuf.split(/\r?\n/).filter(element => element);
|
|
198
215
|
for (let i = 0; i < res.length; i++) {
|
|
199
216
|
if (res[i].charAt(0) != '(') {
|
|
@@ -205,33 +222,15 @@ class NLParamParser {
|
|
|
205
222
|
nvp.name = uname;
|
|
206
223
|
// support for ifile
|
|
207
224
|
if (uname == 'IFILE') {
|
|
208
|
-
await this.start(nvp.atom, depth + 1);
|
|
225
|
+
await this.start(nvp.atom, depth + 1, tnsFileStruct);
|
|
209
226
|
} else {
|
|
210
227
|
const unames = uname.split(","); //multiple aliases (alias1, alias2, alias3)
|
|
211
228
|
for (let i = 0; i < unames.length; i++) {
|
|
212
|
-
|
|
229
|
+
tnsFileStruct.aliasht.set(unames[i], nvp);
|
|
213
230
|
}
|
|
214
231
|
}
|
|
215
232
|
}
|
|
216
233
|
}
|
|
217
|
-
toString() {
|
|
218
|
-
let out = "";
|
|
219
|
-
this.ht.forEach((value) => {
|
|
220
|
-
out = out + value.toString() + "\n";
|
|
221
|
-
});
|
|
222
|
-
return out;
|
|
223
|
-
}
|
|
224
|
-
/**
|
|
225
|
-
* if key is address/port then it returns the port value from the
|
|
226
|
-
* address NVPAIR.
|
|
227
|
-
* @param {string} key
|
|
228
|
-
* @returns {string}
|
|
229
|
-
*/
|
|
230
|
-
findValueOf(key) {
|
|
231
|
-
const myarr = key.split('/');
|
|
232
|
-
return (findValue(this.ht.get(myarr[0].toUpperCase()), myarr));
|
|
233
|
-
}
|
|
234
|
-
|
|
235
234
|
}
|
|
236
235
|
|
|
237
236
|
module.exports = {
|
|
@@ -168,7 +168,7 @@ class SessionAtts {
|
|
|
168
168
|
}
|
|
169
169
|
|
|
170
170
|
if (!this.connectTimeout && !this.transportConnectTimeout)
|
|
171
|
-
this.transportConnectTimeout =
|
|
171
|
+
this.transportConnectTimeout = constants.DEFAULT_TRANSPORT_CONNECT_TIMEOUT; /* Default to 20 secs */
|
|
172
172
|
}
|
|
173
173
|
|
|
174
174
|
}
|
package/lib/thin/util.js
CHANGED
|
@@ -29,6 +29,7 @@
|
|
|
29
29
|
const constants = require('../constants');
|
|
30
30
|
const errors = require('../errors.js');
|
|
31
31
|
const os = require('os');
|
|
32
|
+
const nodbUtil = require('../util.js');
|
|
32
33
|
|
|
33
34
|
//---------------------------------------------------------------------------
|
|
34
35
|
// populateClientInfo()
|
|
@@ -36,15 +37,15 @@ const os = require('os');
|
|
|
36
37
|
// Populates client process information
|
|
37
38
|
//---------------------------------------------------------------------------
|
|
38
39
|
function populateClientInfo() {
|
|
39
|
-
this.program = process.argv0;
|
|
40
|
+
this.program = nodbUtil.sanitize(process.argv0);
|
|
40
41
|
this.terminal = "unknown";
|
|
41
42
|
this.pid = process.pid.toString();
|
|
42
43
|
try {
|
|
43
|
-
this.userName = os.userInfo().username;
|
|
44
|
+
this.userName = nodbUtil.sanitize(os.userInfo().username);
|
|
44
45
|
} catch {
|
|
45
46
|
this.userName = "unknown";
|
|
46
47
|
}
|
|
47
|
-
this.hostName = os.hostname();
|
|
48
|
+
this.hostName = nodbUtil.sanitize(os.hostname());
|
|
48
49
|
}
|
|
49
50
|
// Initialize client data on startup.
|
|
50
51
|
const CLIENT_INFO = new populateClientInfo();
|