oracledb 6.2.0 → 6.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/LICENSE.txt +1 -1
- package/NOTICE.txt +1 -1
- package/README.md +3 -3
- package/build/Release/oracledb-6.4.0-darwin-x64.node +0 -0
- package/build/Release/oracledb-6.4.0-darwin-x64.node-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.4.0-js-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.4.0-linux-arm64.node +0 -0
- package/build/Release/oracledb-6.4.0-linux-arm64.node-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.4.0-linux-x64.node +0 -0
- package/build/Release/oracledb-6.4.0-linux-x64.node-buildinfo.txt +1 -0
- package/build/Release/oracledb-6.4.0-win32-x64.node +0 -0
- package/build/Release/oracledb-6.4.0-win32-x64.node-buildinfo.txt +1 -0
- package/examples/README.md +29 -8
- package/examples/dbconfig.js +50 -26
- package/examples/example.js +6 -4
- package/lib/aqQueue.js +8 -8
- package/lib/connection.js +121 -9
- package/lib/constants.js +7 -1
- package/lib/dbObject.js +72 -1
- package/lib/errors.js +45 -8
- package/lib/future.js +53 -0
- package/lib/impl/connection.js +56 -0
- package/lib/{thin/protocol → impl/datahandlers}/buffer.js +51 -39
- package/lib/impl/datahandlers/constants.js +105 -0
- package/lib/{thin/protocol → impl/datahandlers}/oson.js +19 -1
- package/lib/impl/datahandlers/vector.js +156 -0
- package/lib/impl/pool.js +14 -3
- package/lib/impl/resultset.js +65 -11
- package/lib/lob.js +22 -6
- package/lib/oracledb.js +47 -8
- package/lib/pool.js +20 -1
- package/lib/poolStatistics.js +3 -1
- package/lib/settings.js +30 -6
- package/lib/sodaDocCursor.js +14 -1
- package/lib/thin/connection.js +146 -146
- package/lib/thin/dbObject.js +49 -3
- package/lib/thin/index.js +1 -1
- package/lib/thin/lob.js +6 -6
- package/lib/thin/pool.js +25 -6
- package/lib/thin/protocol/capabilities.js +6 -2
- package/lib/thin/protocol/constants.js +50 -65
- package/lib/thin/protocol/messages/auth.js +6 -2
- package/lib/thin/protocol/messages/base.js +50 -32
- package/lib/thin/protocol/messages/dataType.js +10 -6
- package/lib/thin/protocol/messages/lobOp.js +7 -8
- package/lib/thin/protocol/messages/withData.js +91 -24
- package/lib/thin/protocol/packet.js +58 -4
- package/lib/thin/protocol/utils.js +1 -1
- package/lib/thin/sqlnet/connStrategy.js +8 -4
- package/lib/thin/sqlnet/constants.js +138 -138
- package/lib/thin/sqlnet/navNodes.js +5 -5
- package/lib/thin/sqlnet/networkSession.js +22 -3
- package/lib/thin/sqlnet/ntTcp.js +7 -7
- package/lib/thin/statement.js +8 -8
- package/lib/thin/statementCache.js +167 -0
- package/lib/thin/util.js +15 -4
- package/lib/transformer.js +13 -4
- package/lib/types.js +17 -2
- package/lib/util.js +37 -0
- package/lib/version.js +2 -2
- package/package.json +1 -1
- package/build/Release/oracledb-6.2.0-darwin-x64.node +0 -0
- package/build/Release/oracledb-6.2.0-darwin-x64.node-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.2.0-js-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.2.0-linux-arm64.node +0 -0
- package/build/Release/oracledb-6.2.0-linux-arm64.node-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.2.0-linux-x64.node +0 -0
- package/build/Release/oracledb-6.2.0-linux-x64.node-buildinfo.txt +0 -1
- package/build/Release/oracledb-6.2.0-win32-x64.node +0 -0
- package/build/Release/oracledb-6.2.0-win32-x64.node-buildinfo.txt +0 -1
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
// Copyright (c) 2024, Oracle and/or its affiliates.
|
|
2
|
+
|
|
3
|
+
//-----------------------------------------------------------------------------
|
|
4
|
+
//
|
|
5
|
+
// This software is dual-licensed to you under the Universal Permissive License
|
|
6
|
+
// (UPL) 1.0 as shown at https://oss.oracle.com/licenses/upl and Apache License
|
|
7
|
+
// 2.0 as shown at http://www.apache.org/licenses/LICENSE-2.0. You may choose
|
|
8
|
+
// either license.
|
|
9
|
+
//
|
|
10
|
+
// If you elect to accept the software under the Apache License, Version 2.0,
|
|
11
|
+
// the following applies:
|
|
12
|
+
//
|
|
13
|
+
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
14
|
+
// you may not use this file except in compliance with the License.
|
|
15
|
+
// You may obtain a copy of the License at
|
|
16
|
+
//
|
|
17
|
+
// https://www.apache.org/licenses/LICENSE-2.0
|
|
18
|
+
//
|
|
19
|
+
// Unless required by applicable law or agreed to in writing, software
|
|
20
|
+
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
21
|
+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
22
|
+
// See the License for the specific language governing permissions and
|
|
23
|
+
// limitations under the License.
|
|
24
|
+
//
|
|
25
|
+
//-----------------------------------------------------------------------------
|
|
26
|
+
|
|
27
|
+
'use strict';
|
|
28
|
+
|
|
29
|
+
const { BaseBuffer, GrowableBuffer } = require('./buffer.js');
|
|
30
|
+
const { Buffer } = require('buffer');
|
|
31
|
+
const constants = require("./constants.js");
|
|
32
|
+
const errors = require("../../errors.js");
|
|
33
|
+
|
|
34
|
+
/**
|
|
35
|
+
* Class used for decoding
|
|
36
|
+
*/
|
|
37
|
+
class VectorDecoder extends BaseBuffer {
|
|
38
|
+
|
|
39
|
+
//---------------------------------------------------------------------------
|
|
40
|
+
// decode()
|
|
41
|
+
//
|
|
42
|
+
// Decodes the VECTOR image and returns a JavaScript array corresponding to
|
|
43
|
+
// its contents.
|
|
44
|
+
//---------------------------------------------------------------------------
|
|
45
|
+
decode() {
|
|
46
|
+
|
|
47
|
+
// parse header
|
|
48
|
+
const magicByte = this.readUInt8();
|
|
49
|
+
if (magicByte != constants.TNS_VECTOR_MAGIC_BYTE)
|
|
50
|
+
errors.throwErr(errors.ERR_UNEXPECTED_DATA,
|
|
51
|
+
Buffer.from([magicByte]).toString('hex'));
|
|
52
|
+
const version = this.readUInt8();
|
|
53
|
+
if (version != constants.TNS_VECTOR_VERSION)
|
|
54
|
+
errors.throwErr(errors.ERR_VECTOR_VERSION_NOT_SUPPORTED, version);
|
|
55
|
+
const flags = this.readUInt16BE();
|
|
56
|
+
const vectorFormat = this.readUInt8();
|
|
57
|
+
let numElements;
|
|
58
|
+
if (flags & constants.TNS_VECTOR_FLAG_DIM_UINT8) {
|
|
59
|
+
numElements = this.readUInt8();
|
|
60
|
+
} else if (flags & constants.TNS_VECTOR_FLAG_DIM_UINT32) {
|
|
61
|
+
numElements = this.readUInt32BE();
|
|
62
|
+
} else {
|
|
63
|
+
numElements = this.readUInt16BE();
|
|
64
|
+
}
|
|
65
|
+
let elementSize, result;
|
|
66
|
+
if (vectorFormat === constants.VECTOR_FORMAT_FLOAT32) {
|
|
67
|
+
elementSize = 4;
|
|
68
|
+
result = new Float32Array(numElements);
|
|
69
|
+
} else if (vectorFormat === constants.VECTOR_FORMAT_FLOAT64) {
|
|
70
|
+
elementSize = 8;
|
|
71
|
+
result = new Float64Array(numElements);
|
|
72
|
+
} else if (vectorFormat === constants.VECTOR_FORMAT_INT8) {
|
|
73
|
+
elementSize = 1;
|
|
74
|
+
result = new Int8Array(numElements);
|
|
75
|
+
} else {
|
|
76
|
+
errors.throwErr(errors.ERR_VECTOR_FORMAT_NOT_SUPPORTED, vectorFormat);
|
|
77
|
+
}
|
|
78
|
+
if (flags & constants.TNS_VECTOR_FLAG_NORM)
|
|
79
|
+
this.skipBytes(8);
|
|
80
|
+
|
|
81
|
+
// parse data
|
|
82
|
+
for (let i = 0; i < numElements; i++) {
|
|
83
|
+
const buf = this.readBytes(elementSize);
|
|
84
|
+
if (vectorFormat === constants.VECTOR_FORMAT_FLOAT32) {
|
|
85
|
+
result[i] = this.parseBinaryFloat(buf);
|
|
86
|
+
} else if (vectorFormat === constants.VECTOR_FORMAT_FLOAT64) {
|
|
87
|
+
result[i] = this.parseBinaryDouble(buf);
|
|
88
|
+
} else {
|
|
89
|
+
result[i] = buf[0];
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
return result;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
class VectorEncoder extends GrowableBuffer {
|
|
99
|
+
|
|
100
|
+
//---------------------------------------------------------------------------
|
|
101
|
+
// encode()
|
|
102
|
+
//
|
|
103
|
+
// Encodes the value as OSON and returns a buffer containing the OSON bytes.
|
|
104
|
+
//---------------------------------------------------------------------------
|
|
105
|
+
encode(value) {
|
|
106
|
+
|
|
107
|
+
// determine some basic information about the vector
|
|
108
|
+
let vectorFormat = constants.VECTOR_FORMAT_FLOAT32;
|
|
109
|
+
let writeFn = this.writeBinaryFloat.bind(this);
|
|
110
|
+
|
|
111
|
+
if (Array.isArray(value) || value instanceof Float64Array) {
|
|
112
|
+
vectorFormat = constants.VECTOR_FORMAT_FLOAT64;
|
|
113
|
+
writeFn = this.writeBinaryDouble.bind(this);
|
|
114
|
+
} else if (value instanceof Int8Array) {
|
|
115
|
+
vectorFormat = constants.VECTOR_FORMAT_INT8;
|
|
116
|
+
writeFn = this.writeSB1.bind(this);
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
// Let server generate the norm (TNS_VECTOR_FLAG_NORMSRC)
|
|
120
|
+
let flags = constants.TNS_VECTOR_FLAG_NORM
|
|
121
|
+
| constants.TNS_VECTOR_FLAG_NORMSRC;
|
|
122
|
+
const numElements = value.length;
|
|
123
|
+
if (numElements < 256) {
|
|
124
|
+
flags |= constants.TNS_VECTOR_FLAG_DIM_UINT8;
|
|
125
|
+
} else if (numElements > 65535) {
|
|
126
|
+
flags |= constants.TNS_VECTOR_FLAG_DIM_UINT32;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
// write header
|
|
130
|
+
this.writeUInt8(constants.TNS_VECTOR_MAGIC_BYTE);
|
|
131
|
+
this.writeUInt8(constants.TNS_VECTOR_VERSION);
|
|
132
|
+
this.writeUInt16BE(flags);
|
|
133
|
+
this.writeUInt8(vectorFormat);
|
|
134
|
+
if (numElements < 256) {
|
|
135
|
+
this.writeUInt8(numElements);
|
|
136
|
+
} else if (numElements < 65536) {
|
|
137
|
+
this.writeUInt16BE(numElements);
|
|
138
|
+
} else {
|
|
139
|
+
this.writeUInt32BE(numElements);
|
|
140
|
+
}
|
|
141
|
+
this.reserveBytes(8);
|
|
142
|
+
|
|
143
|
+
// write data
|
|
144
|
+
value.forEach((element) => {
|
|
145
|
+
writeFn(element);
|
|
146
|
+
});
|
|
147
|
+
|
|
148
|
+
return this.buf.subarray(0, this.pos);
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
module.exports = {
|
|
154
|
+
VectorDecoder,
|
|
155
|
+
VectorEncoder
|
|
156
|
+
};
|
package/lib/impl/pool.js
CHANGED
|
@@ -37,10 +37,10 @@ class PoolImpl {
|
|
|
37
37
|
// Access token handler callback function which wraps the user callback and
|
|
38
38
|
// returns the token to the implementation.
|
|
39
39
|
//---------------------------------------------------------------------------
|
|
40
|
-
async _accessTokenHandler(userFn, externalObj, refresh) {
|
|
40
|
+
async _accessTokenHandler(userFn, externalObj, refresh, accessTokenConfig) {
|
|
41
41
|
let accessToken;
|
|
42
42
|
try {
|
|
43
|
-
let result = userFn(refresh);
|
|
43
|
+
let result = userFn(refresh, accessTokenConfig);
|
|
44
44
|
if (result instanceof Promise) {
|
|
45
45
|
result = await result;
|
|
46
46
|
}
|
|
@@ -48,7 +48,9 @@ class PoolImpl {
|
|
|
48
48
|
if (!nodbUtil.isTokenValid(result)) {
|
|
49
49
|
errors.throwErr(errors.ERR_TOKEN_HAS_EXPIRED);
|
|
50
50
|
}
|
|
51
|
-
|
|
51
|
+
if (typeof result === 'object' && result.privateKey !== undefined) {
|
|
52
|
+
result.privateKey = nodbUtil.denormalizePrivateKey(result.privateKey);
|
|
53
|
+
}
|
|
52
54
|
accessToken = result;
|
|
53
55
|
} finally {
|
|
54
56
|
this.returnAccessToken(externalObj, accessToken);
|
|
@@ -145,6 +147,15 @@ class PoolImpl {
|
|
|
145
147
|
errors.throwNotImplemented("getting the pool ping interval");
|
|
146
148
|
}
|
|
147
149
|
|
|
150
|
+
//---------------------------------------------------------------------------
|
|
151
|
+
// getPoolPingTimeout()
|
|
152
|
+
//
|
|
153
|
+
// Returns the pool ping Timeout (milliseconds).
|
|
154
|
+
//---------------------------------------------------------------------------
|
|
155
|
+
getPoolPingTimeout() {
|
|
156
|
+
errors.throwNotImplemented("getting the pool ping Timeout");
|
|
157
|
+
}
|
|
158
|
+
|
|
148
159
|
//---------------------------------------------------------------------------
|
|
149
160
|
// getPoolTimeout()
|
|
150
161
|
//
|
package/lib/impl/resultset.js
CHANGED
|
@@ -30,7 +30,10 @@ const constants = require('../constants.js');
|
|
|
30
30
|
const errors = require('../errors.js');
|
|
31
31
|
const nodbUtil = require('../util.js');
|
|
32
32
|
const settings = require('../settings.js');
|
|
33
|
+
const future = require('../future.js');
|
|
33
34
|
const types = require('../types.js');
|
|
35
|
+
const Lob = require('../lob.js');
|
|
36
|
+
const oson = require('./datahandlers/oson.js');
|
|
34
37
|
|
|
35
38
|
// define implementation class
|
|
36
39
|
class ResultSetImpl {
|
|
@@ -100,36 +103,87 @@ class ResultSetImpl {
|
|
|
100
103
|
metadata.fetchType = actualFetchType;
|
|
101
104
|
}
|
|
102
105
|
|
|
106
|
+
let converter;
|
|
107
|
+
const userConverter = metadata.converter;
|
|
108
|
+
|
|
109
|
+
// If IsJson or IsOson is set, convert to JSON objects unless
|
|
110
|
+
// user defined output type handler overwrites it.
|
|
111
|
+
if (metadata.dbType !== types.DB_TYPE_JSON && future.oldJsonColumnAsObj
|
|
112
|
+
&& userConverter === undefined) {
|
|
113
|
+
let outConverter;
|
|
114
|
+
if (metadata.isOson) {
|
|
115
|
+
outConverter = async function(val) {
|
|
116
|
+
if (!val) {
|
|
117
|
+
return val;
|
|
118
|
+
}
|
|
119
|
+
let result = val;
|
|
120
|
+
if (val instanceof Lob) {
|
|
121
|
+
result = await val.getData();
|
|
122
|
+
}
|
|
123
|
+
const decoder = new oson.OsonDecoder(result);
|
|
124
|
+
return decoder.decode();
|
|
125
|
+
};
|
|
126
|
+
converter = outConverter;
|
|
127
|
+
} else if (metadata.isJson) {
|
|
128
|
+
outConverter = async function(val) {
|
|
129
|
+
if (!val) {
|
|
130
|
+
return val;
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
let result = val;
|
|
134
|
+
if (val instanceof Lob) {
|
|
135
|
+
result = await val.getData();
|
|
136
|
+
}
|
|
137
|
+
if (result instanceof Buffer) {
|
|
138
|
+
result = result.toString();
|
|
139
|
+
}
|
|
140
|
+
result = JSON.parse(result);
|
|
141
|
+
return result;
|
|
142
|
+
};
|
|
143
|
+
converter = outConverter;
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
|
|
103
147
|
// in thin mode, Oracle NUMBER values are internally fetched as string in
|
|
104
148
|
// order to preserve precision so must be converted to JavaScript Number
|
|
105
149
|
// when needed; other numeric and date types are fetched natively as
|
|
106
150
|
// JavaScript Number and Date values and are converted to string using
|
|
107
151
|
// toString() when desired
|
|
108
152
|
if (settings.thin) {
|
|
109
|
-
let converter;
|
|
110
|
-
const userConverter = metadata.converter;
|
|
111
153
|
if (metadata.dbType === types.DB_TYPE_NUMBER &&
|
|
112
|
-
|
|
154
|
+
metadata.fetchType === types.DB_TYPE_NUMBER) {
|
|
113
155
|
converter = (v) => (v === null) ? null : parseFloat(v);
|
|
114
156
|
} else if (metadata.fetchType === types.DB_TYPE_VARCHAR) {
|
|
115
157
|
if (metadata.dbType === types.DB_TYPE_BINARY_DOUBLE ||
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
158
|
+
metadata.dbType === types.DB_TYPE_BINARY_FLOAT ||
|
|
159
|
+
metadata.dbType === types.DB_TYPE_DATE ||
|
|
160
|
+
metadata.dbType === types.DB_TYPE_TIMESTAMP ||
|
|
161
|
+
metadata.dbType === types.DB_TYPE_TIMESTAMP_LTZ ||
|
|
162
|
+
metadata.dbType === types.DB_TYPE_TIMESTAMP_TZ) {
|
|
121
163
|
converter = (v) => (v === null) ? null : v.toString();
|
|
122
164
|
} else if (metadata.dbType === types.DB_TYPE_RAW) {
|
|
123
165
|
converter = (v) => (v === null) ? null : v.toString('hex').toUpperCase();
|
|
124
166
|
}
|
|
167
|
+
} else if (metadata.dbType === types.DB_TYPE_XMLTYPE) {
|
|
168
|
+
const xmlConverter = async function(val) {
|
|
169
|
+
if (!val) {
|
|
170
|
+
return val;
|
|
171
|
+
}
|
|
172
|
+
if (typeof val === 'string') {
|
|
173
|
+
return val;
|
|
174
|
+
}
|
|
175
|
+
return await val.getData();
|
|
176
|
+
};
|
|
177
|
+
converter = xmlConverter;
|
|
125
178
|
}
|
|
126
179
|
if (userConverter && converter) {
|
|
127
180
|
const internalConverter = converter;
|
|
128
181
|
converter = (v) => userConverter(internalConverter(v));
|
|
129
182
|
}
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
if (converter) {
|
|
186
|
+
metadata.converter = converter;
|
|
133
187
|
}
|
|
134
188
|
|
|
135
189
|
}
|
package/lib/lob.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// Copyright (c) 2016,
|
|
1
|
+
// Copyright (c) 2016, 2024, Oracle and/or its affiliates.
|
|
2
2
|
|
|
3
3
|
//-----------------------------------------------------------------------------
|
|
4
4
|
//
|
|
@@ -50,7 +50,7 @@ class Lob extends Duplex {
|
|
|
50
50
|
// not already been closed (never called directly)
|
|
51
51
|
async _destroy(err, cb) {
|
|
52
52
|
// if LOB was already closed, nothing to do!
|
|
53
|
-
if (err && err.message.startsWith("NJS-
|
|
53
|
+
if (err && err.message.startsWith("NJS-003:"))
|
|
54
54
|
delete this._impl;
|
|
55
55
|
if (this._impl) {
|
|
56
56
|
const lobImpl = this._impl;
|
|
@@ -185,12 +185,28 @@ class Lob extends Duplex {
|
|
|
185
185
|
//---------------------------------------------------------------------------
|
|
186
186
|
// getData()
|
|
187
187
|
//
|
|
188
|
-
//
|
|
188
|
+
// Return a portion (or all) of the data in the LOB. Note that the amount
|
|
189
|
+
// and offset are in bytes for BLOB and BFILE type LOBs and in UCS - 2 code
|
|
190
|
+
// points for CLOB and NCLOB type LOBs.UCS-2 code points are equivalent
|
|
191
|
+
// to characters for all but supplemental characters.If supplemental
|
|
192
|
+
// characters are in the LOB, the offset and amount will have to be chosen
|
|
193
|
+
// carefully to avoid splitting a character.
|
|
194
|
+
// Returns data in the LOB as a single string or buffer.
|
|
189
195
|
//---------------------------------------------------------------------------
|
|
190
|
-
async getData() {
|
|
191
|
-
errors.assertArgCount(arguments, 0,
|
|
196
|
+
async getData(offset, amount) {
|
|
197
|
+
errors.assertArgCount(arguments, 0, 2);
|
|
198
|
+
if (offset === undefined) {
|
|
199
|
+
offset = 1;
|
|
200
|
+
} else {
|
|
201
|
+
errors.assertParamValue(Number.isInteger(offset) && offset > 0, 1);
|
|
202
|
+
}
|
|
203
|
+
if (amount === undefined) {
|
|
204
|
+
amount = 0;
|
|
205
|
+
} else {
|
|
206
|
+
errors.assertParamValue(Number.isInteger(amount) && amount > 0, 2);
|
|
207
|
+
}
|
|
192
208
|
errors.assert(this._impl, errors.ERR_INVALID_LOB);
|
|
193
|
-
return await this._impl.getData();
|
|
209
|
+
return await this._impl.getData(offset, amount);
|
|
194
210
|
}
|
|
195
211
|
|
|
196
212
|
//---------------------------------------------------------------------------
|
package/lib/oracledb.js
CHANGED
|
@@ -48,6 +48,7 @@ const AqDeqOptions = require('./aqDeqOptions.js');
|
|
|
48
48
|
const AqEnqOptions = require('./aqEnqOptions.js');
|
|
49
49
|
const AqMessage = require('./aqMessage.js');
|
|
50
50
|
const AqQueue = require('./aqQueue.js');
|
|
51
|
+
const future = require('./future.js');
|
|
51
52
|
const BaseDbObject = require('./dbObject.js');
|
|
52
53
|
const Connection = require('./connection.js');
|
|
53
54
|
const Lob = require('./lob.js');
|
|
@@ -367,6 +368,13 @@ async function _verifyOptions(options, inCreatePool) {
|
|
|
367
368
|
outOptions.poolPingInterval = options.poolPingInterval;
|
|
368
369
|
}
|
|
369
370
|
|
|
371
|
+
// poolPingTimeout must be an integer (>= 0)
|
|
372
|
+
if (options.poolPingTimeout !== undefined) {
|
|
373
|
+
errors.assertParamPropValue(Number.isInteger(options.poolPingTimeout) &&
|
|
374
|
+
options.poolPingTimeout >= 0, 1, "poolPingTimeout");
|
|
375
|
+
outOptions.poolPingTimeout = options.poolPingTimeout;
|
|
376
|
+
}
|
|
377
|
+
|
|
370
378
|
// homogeneous must be a boolean (and defaults to True)
|
|
371
379
|
outOptions.homogeneous = true;
|
|
372
380
|
if (options.homogeneous !== undefined) {
|
|
@@ -471,9 +479,10 @@ async function _verifyOptions(options, inCreatePool) {
|
|
|
471
479
|
let accessToken;
|
|
472
480
|
if (typeof options.accessToken === 'function') {
|
|
473
481
|
outOptions.accessTokenFn = options.accessToken;
|
|
474
|
-
|
|
482
|
+
outOptions.accessTokenConfig = options.accessTokenConfig;
|
|
483
|
+
accessToken = await options.accessToken(false, options.accessTokenConfig);
|
|
475
484
|
if (!nodbUtil.isTokenValid(accessToken)) {
|
|
476
|
-
accessToken = await options.accessToken(true);
|
|
485
|
+
accessToken = await options.accessToken(true, options.accessTokenConfig);
|
|
477
486
|
}
|
|
478
487
|
} else {
|
|
479
488
|
accessToken = options.accessToken;
|
|
@@ -482,9 +491,7 @@ async function _verifyOptions(options, inCreatePool) {
|
|
|
482
491
|
errors.ERR_TOKEN_HAS_EXPIRED);
|
|
483
492
|
if (accessToken.privateKey !== undefined) {
|
|
484
493
|
errors.assert(typeof accessToken.privateKey === 'string', errors.ERR_TOKEN_BASED_AUTH);
|
|
485
|
-
accessToken.privateKey = accessToken.privateKey
|
|
486
|
-
accessToken.privateKey = accessToken.privateKey.replace('-----BEGIN PRIVATE KEY-----', '');
|
|
487
|
-
accessToken.privateKey = accessToken.privateKey.replace('-----END PRIVATE KEY-----', '');
|
|
494
|
+
accessToken.privateKey = nodbUtil.denormalizePrivateKey(accessToken.privateKey);
|
|
488
495
|
}
|
|
489
496
|
|
|
490
497
|
// store token and privatekey
|
|
@@ -497,9 +504,20 @@ async function _verifyOptions(options, inCreatePool) {
|
|
|
497
504
|
|
|
498
505
|
}
|
|
499
506
|
|
|
500
|
-
// Check external Auth config
|
|
501
|
-
|
|
502
|
-
|
|
507
|
+
// Check external Auth config.
|
|
508
|
+
// Allow Session User enclosed in [] for proxy authentication.
|
|
509
|
+
if (outOptions.token === undefined && outOptions.externalAuth) {
|
|
510
|
+
if (outOptions.password) {
|
|
511
|
+
errors.throwErr(errors.ERR_WRONG_CRED_FOR_EXTAUTH);
|
|
512
|
+
}
|
|
513
|
+
if (outOptions.user) {
|
|
514
|
+
if (inCreatePool) {
|
|
515
|
+
errors.throwErr(errors.ERR_WRONG_CRED_FOR_EXTAUTH);
|
|
516
|
+
} else if (outOptions.user[0] !== '[' || outOptions.user.slice(-1) !== ']') {
|
|
517
|
+
// username is not enclosed in [].
|
|
518
|
+
errors.throwErr(errors.ERR_WRONG_USER_FORMAT_EXTAUTH_PROXY);
|
|
519
|
+
}
|
|
520
|
+
}
|
|
503
521
|
}
|
|
504
522
|
|
|
505
523
|
return outOptions;
|
|
@@ -547,6 +565,7 @@ async function createPool(options) {
|
|
|
547
565
|
"poolIncrement",
|
|
548
566
|
"poolTimeout",
|
|
549
567
|
"poolPingInterval",
|
|
568
|
+
"poolPingTimeout",
|
|
550
569
|
"queueMax",
|
|
551
570
|
"queueTimeout");
|
|
552
571
|
|
|
@@ -868,6 +887,8 @@ module.exports = {
|
|
|
868
887
|
DB_TYPE_TIMESTAMP_LTZ: types.DB_TYPE_TIMESTAMP_LTZ,
|
|
869
888
|
DB_TYPE_TIMESTAMP_TZ: types.DB_TYPE_TIMESTAMP_TZ,
|
|
870
889
|
DB_TYPE_VARCHAR: types.DB_TYPE_VARCHAR,
|
|
890
|
+
DB_TYPE_XMLTYPE: types.DB_TYPE_XMLTYPE,
|
|
891
|
+
DB_TYPE_VECTOR: types.DB_TYPE_VECTOR,
|
|
871
892
|
|
|
872
893
|
// fetchInfo type defaulting
|
|
873
894
|
DEFAULT: constants.DEFAULT,
|
|
@@ -999,6 +1020,11 @@ module.exports = {
|
|
|
999
1020
|
TPC_END_NORMAL: constants.TPC_END_NORMAL,
|
|
1000
1021
|
TPC_END_SUSPEND: constants.TPC_END_SUSPEND,
|
|
1001
1022
|
|
|
1023
|
+
// vector types
|
|
1024
|
+
VECTOR_FORMAT_FLOAT32: constants.VECTOR_FORMAT_FLOAT32,
|
|
1025
|
+
VECTOR_FORMAT_FLOAT64: constants.VECTOR_FORMAT_FLOAT64,
|
|
1026
|
+
VECTOR_FORMAT_INT8: constants.VECTOR_FORMAT_INT8,
|
|
1027
|
+
|
|
1002
1028
|
// database type aliases
|
|
1003
1029
|
BLOB: types.DB_TYPE_BLOB,
|
|
1004
1030
|
BUFFER: types.DB_TYPE_RAW,
|
|
@@ -1013,6 +1039,9 @@ module.exports = {
|
|
|
1013
1039
|
ARRAY: constants.OUT_FORMAT_ARRAY,
|
|
1014
1040
|
OBJECT: constants.OUT_FORMAT_OBJECT,
|
|
1015
1041
|
|
|
1042
|
+
// Instances
|
|
1043
|
+
future,
|
|
1044
|
+
|
|
1016
1045
|
// property getters
|
|
1017
1046
|
get autoCommit() {
|
|
1018
1047
|
return settings.autoCommit;
|
|
@@ -1098,6 +1127,10 @@ module.exports = {
|
|
|
1098
1127
|
return settings.poolPingInterval;
|
|
1099
1128
|
},
|
|
1100
1129
|
|
|
1130
|
+
get poolPingTimeout() {
|
|
1131
|
+
return settings.poolPingTimeout;
|
|
1132
|
+
},
|
|
1133
|
+
|
|
1101
1134
|
get poolTimeout() {
|
|
1102
1135
|
return settings.poolTimeout;
|
|
1103
1136
|
},
|
|
@@ -1236,6 +1269,12 @@ module.exports = {
|
|
|
1236
1269
|
settings.poolPingInterval = value;
|
|
1237
1270
|
},
|
|
1238
1271
|
|
|
1272
|
+
set poolPingTimeout(value) {
|
|
1273
|
+
errors.assertPropValue(Number.isInteger(value) && value >= 0,
|
|
1274
|
+
"poolPingTimeout");
|
|
1275
|
+
settings.poolPingTimeout = value;
|
|
1276
|
+
},
|
|
1277
|
+
|
|
1239
1278
|
set poolTimeout(value) {
|
|
1240
1279
|
errors.assertPropValue(Number.isInteger(value) && value >= 0,
|
|
1241
1280
|
"poolTimeout");
|
package/lib/pool.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// Copyright (c) 2016,
|
|
1
|
+
// Copyright (c) 2016, 2024, Oracle and/or its affiliates.
|
|
2
2
|
|
|
3
3
|
//-----------------------------------------------------------------------------
|
|
4
4
|
//
|
|
@@ -192,10 +192,20 @@ class Pool extends EventEmitter {
|
|
|
192
192
|
outOptions.user = options.username;
|
|
193
193
|
}
|
|
194
194
|
|
|
195
|
+
if (this.externalAuth &&
|
|
196
|
+
outOptions.user && (outOptions.user[0] !== '['
|
|
197
|
+
|| outOptions.user.slice(-1) !== ']')) {
|
|
198
|
+
// username is not enclosed in [].
|
|
199
|
+
errors.throwErr(errors.ERR_WRONG_USER_FORMAT_EXTAUTH_PROXY);
|
|
200
|
+
}
|
|
201
|
+
|
|
195
202
|
// password must be a string
|
|
196
203
|
if (options.password !== undefined) {
|
|
197
204
|
errors.assertParamPropValue(typeof options.password === 'string', 1,
|
|
198
205
|
"password");
|
|
206
|
+
if (this.externalAuth) {
|
|
207
|
+
errors.throwErr(errors.ERR_WRONG_CRED_FOR_EXTAUTH);
|
|
208
|
+
}
|
|
199
209
|
outOptions.password = options.password;
|
|
200
210
|
}
|
|
201
211
|
|
|
@@ -618,6 +628,15 @@ class Pool extends EventEmitter {
|
|
|
618
628
|
return this._impl.getPoolPingInterval();
|
|
619
629
|
}
|
|
620
630
|
|
|
631
|
+
//---------------------------------------------------------------------------
|
|
632
|
+
// poolPingTimeout
|
|
633
|
+
//
|
|
634
|
+
// Property for the ping timeout associated with the pool.
|
|
635
|
+
//---------------------------------------------------------------------------
|
|
636
|
+
get poolPingTimeout() {
|
|
637
|
+
return this._impl.getPoolPingTimeout();
|
|
638
|
+
}
|
|
639
|
+
|
|
621
640
|
//---------------------------------------------------------------------------
|
|
622
641
|
// poolTimeout
|
|
623
642
|
//
|
package/lib/poolStatistics.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// Copyright (c) 2021,
|
|
1
|
+
// Copyright (c) 2021, 2024, Oracle and/or its affiliates.
|
|
2
2
|
|
|
3
3
|
//-----------------------------------------------------------------------------
|
|
4
4
|
//
|
|
@@ -72,6 +72,7 @@ class PoolStatistics {
|
|
|
72
72
|
this.poolMaxPerShard = pool.poolMaxPerShard;
|
|
73
73
|
this.poolMin = pool.poolMin;
|
|
74
74
|
this.poolPingInterval = pool.poolPingInterval;
|
|
75
|
+
this.poolPingTimeout = pool.poolPingTimeout;
|
|
75
76
|
this.poolTimeout = pool.poolTimeout;
|
|
76
77
|
this.queueMax = pool.queueMax;
|
|
77
78
|
this.queueTimeout = pool.queueTimeout;
|
|
@@ -124,6 +125,7 @@ class PoolStatistics {
|
|
|
124
125
|
console.log('...poolMaxPerShard:', this.poolMaxPerShard);
|
|
125
126
|
console.log('...poolMin:', this.poolMin);
|
|
126
127
|
console.log('...poolPingInterval (seconds):', this.poolPingInterval);
|
|
128
|
+
console.log('...poolPingTimeout (milliseconds):', this.poolPingTimeout);
|
|
127
129
|
console.log('...poolTimeout (seconds):', this.poolTimeout);
|
|
128
130
|
console.log('...queueMax:', this.queueMax);
|
|
129
131
|
console.log('...queueTimeout (milliseconds):', this.queueTimeout);
|
package/lib/settings.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
|
//
|
|
@@ -29,6 +29,8 @@
|
|
|
29
29
|
const constants = require('./constants.js');
|
|
30
30
|
const errors = require('./errors.js');
|
|
31
31
|
const types = require('./types.js');
|
|
32
|
+
const nodbUtil = require("./util.js");
|
|
33
|
+
const vector = require('./impl/datahandlers/vector.js');
|
|
32
34
|
|
|
33
35
|
class Settings {
|
|
34
36
|
|
|
@@ -51,6 +53,7 @@ class Settings {
|
|
|
51
53
|
this.poolMaxPerShard = 0;
|
|
52
54
|
this.poolMin = 0;
|
|
53
55
|
this.poolPingInterval = 60;
|
|
56
|
+
this.poolPingTimeout = 5000;
|
|
54
57
|
this.poolTimeout = 60;
|
|
55
58
|
this.prefetchRows = 2;
|
|
56
59
|
this.queueTimeout = 60000;
|
|
@@ -105,11 +108,29 @@ class Settings {
|
|
|
105
108
|
// information).
|
|
106
109
|
//---------------------------------------------------------------------------
|
|
107
110
|
_makeDate(useLocal, year, month, day, hour, minute, second, fseconds, offset) {
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
111
|
+
return nodbUtil.makeDate(useLocal, year, month, day, hour, minute, second, fseconds, offset);
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
//---------------------------------------------------------------------------
|
|
115
|
+
// _decodeVector()
|
|
116
|
+
//
|
|
117
|
+
// Returns a typed array by decoding buffer.
|
|
118
|
+
//
|
|
119
|
+
//---------------------------------------------------------------------------
|
|
120
|
+
_decodeVector(buffer) {
|
|
121
|
+
const decoder = new vector.VectorDecoder(buffer);
|
|
122
|
+
return decoder.decode();
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
//---------------------------------------------------------------------------
|
|
126
|
+
// _encodeVector()
|
|
127
|
+
//
|
|
128
|
+
// Create a Vector image from typedarray
|
|
129
|
+
//
|
|
130
|
+
//---------------------------------------------------------------------------
|
|
131
|
+
_encodeVector(value) {
|
|
132
|
+
const encoder = new vector.VectorEncoder();
|
|
133
|
+
return encoder.encode(value);
|
|
113
134
|
}
|
|
114
135
|
|
|
115
136
|
//---------------------------------------------------------------------------
|
|
@@ -159,6 +180,9 @@ class Settings {
|
|
|
159
180
|
map.set(types.DB_TYPE_CLOB, types.DB_TYPE_LONG);
|
|
160
181
|
map.set(types.DB_TYPE_NCLOB, types.DB_TYPE_LONG_NVARCHAR);
|
|
161
182
|
break;
|
|
183
|
+
case types.DB_TYPE_VECTOR:
|
|
184
|
+
map.set(types.DB_TYPE_VECTOR, types.DB_TYPE_LONG);
|
|
185
|
+
break;
|
|
162
186
|
case types.DB_TYPE_RAW:
|
|
163
187
|
map.set(types.DB_TYPE_RAW, types.DB_TYPE_VARCHAR);
|
|
164
188
|
break;
|
package/lib/sodaDocCursor.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// Copyright (c) 2018,
|
|
1
|
+
// Copyright (c) 2018, 2024, Oracle and/or its affiliates.
|
|
2
2
|
|
|
3
3
|
//-----------------------------------------------------------------------------
|
|
4
4
|
//
|
|
@@ -60,6 +60,19 @@ class SodaDocCursor {
|
|
|
60
60
|
}
|
|
61
61
|
}
|
|
62
62
|
|
|
63
|
+
[Symbol.asyncIterator]() {
|
|
64
|
+
const cursor = this;
|
|
65
|
+
return {
|
|
66
|
+
async next() {
|
|
67
|
+
const doc = await cursor.getNext();
|
|
68
|
+
return {value: doc, done: doc === undefined};
|
|
69
|
+
},
|
|
70
|
+
return() {
|
|
71
|
+
return {done: true};
|
|
72
|
+
}
|
|
73
|
+
};
|
|
74
|
+
}
|
|
75
|
+
|
|
63
76
|
}
|
|
64
77
|
|
|
65
78
|
nodbUtil.wrapFns(SodaDocCursor.prototype,
|