@tdengine/websocket 3.2.2 → 3.3.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/lib/package.json +64 -0
- package/lib/src/client/retryConfig.d.ts +10 -0
- package/lib/src/client/retryConfig.d.ts.map +1 -0
- package/lib/src/client/retryConfig.js +46 -0
- package/lib/src/client/wsClient.d.ts +24 -7
- package/lib/src/client/wsClient.d.ts.map +1 -1
- package/lib/src/client/wsClient.js +164 -137
- package/lib/src/client/wsConnector.d.ts +55 -9
- package/lib/src/client/wsConnector.d.ts.map +1 -1
- package/lib/src/client/wsConnector.js +522 -102
- package/lib/src/client/wsConnectorPool.d.ts +5 -1
- package/lib/src/client/wsConnectorPool.d.ts.map +1 -1
- package/lib/src/client/wsConnectorPool.js +67 -52
- package/lib/src/client/wsEventCallback.d.ts +3 -0
- package/lib/src/client/wsEventCallback.d.ts.map +1 -1
- package/lib/src/client/wsEventCallback.js +67 -8
- package/lib/src/client/wsResponse.d.ts +0 -3
- package/lib/src/client/wsResponse.d.ts.map +1 -1
- package/lib/src/client/wsResponse.js +0 -3
- package/lib/src/common/addressConnectionTracker.d.ts +11 -0
- package/lib/src/common/addressConnectionTracker.d.ts.map +1 -0
- package/lib/src/common/addressConnectionTracker.js +53 -0
- package/lib/src/common/config.d.ts +3 -0
- package/lib/src/common/config.d.ts.map +1 -1
- package/lib/src/common/config.js +6 -0
- package/lib/src/common/constant.d.ts +1 -0
- package/lib/src/common/constant.d.ts.map +1 -1
- package/lib/src/common/constant.js +6 -1
- package/lib/src/common/dsn.d.ts +30 -0
- package/lib/src/common/dsn.d.ts.map +1 -0
- package/lib/src/common/dsn.js +221 -0
- package/lib/src/common/taosResult.d.ts.map +1 -1
- package/lib/src/common/taosResult.js +0 -5
- package/lib/src/common/urlParser.d.ts +32 -0
- package/lib/src/common/urlParser.d.ts.map +1 -0
- package/lib/src/common/urlParser.js +201 -0
- package/lib/src/common/utils.d.ts +6 -1
- package/lib/src/common/utils.d.ts.map +1 -1
- package/lib/src/common/utils.js +74 -22
- package/lib/src/index.d.ts.map +1 -1
- package/lib/src/sql/wsSql.d.ts.map +1 -1
- package/lib/src/sql/wsSql.js +2 -2
- package/lib/src/stmt/FieldBindParams.d.ts.map +1 -1
- package/lib/src/stmt/wsColumnInfo.d.ts.map +1 -1
- package/lib/src/stmt/wsParams1.d.ts.map +1 -1
- package/lib/src/stmt/wsParams1.js +26 -26
- package/lib/src/stmt/wsParams2.d.ts.map +1 -1
- package/lib/src/stmt/wsParams2.js +0 -3
- package/lib/src/stmt/wsParamsBase.d.ts.map +1 -1
- package/lib/src/stmt/wsProto.d.ts.map +1 -1
- package/lib/src/stmt/wsProto.js +16 -16
- package/lib/src/stmt/wsStmt1.d.ts.map +1 -1
- package/lib/src/stmt/wsStmt2.d.ts +12 -4
- package/lib/src/stmt/wsStmt2.d.ts.map +1 -1
- package/lib/src/stmt/wsStmt2.js +182 -64
- package/lib/src/stmt/wsTableInfo.d.ts.map +1 -1
- package/lib/src/tmq/config.d.ts +4 -2
- package/lib/src/tmq/config.d.ts.map +1 -1
- package/lib/src/tmq/config.js +30 -13
- package/lib/src/tmq/constant.d.ts +4 -0
- package/lib/src/tmq/constant.d.ts.map +1 -1
- package/lib/src/tmq/constant.js +4 -0
- package/lib/src/tmq/tmqResponse.d.ts.map +1 -1
- package/lib/src/tmq/tmqResponse.js +1 -4
- package/lib/src/tmq/wsTmq.d.ts +4 -1
- package/lib/src/tmq/wsTmq.d.ts.map +1 -1
- package/lib/src/tmq/wsTmq.js +55 -27
- package/lib/test/bulkPulling/a.test.d.ts +2 -0
- package/lib/test/bulkPulling/a.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/a.test.js +166 -0
- package/lib/test/bulkPulling/cloud.tmq.test.js +3 -2
- package/lib/test/bulkPulling/decimal.test.js +8 -8
- package/lib/test/bulkPulling/dsn.test.d.ts +2 -0
- package/lib/test/bulkPulling/dsn.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/dsn.test.js +397 -0
- package/lib/test/bulkPulling/queryTables.test.js +1 -1
- package/lib/test/bulkPulling/retryConfig.test.d.ts +2 -0
- package/lib/test/bulkPulling/retryConfig.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/retryConfig.test.js +34 -0
- package/lib/test/bulkPulling/schemaless.test.js +15 -14
- package/lib/test/bulkPulling/sql.failover.test.d.ts +2 -0
- package/lib/test/bulkPulling/sql.failover.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/sql.failover.test.js +338 -0
- package/lib/test/bulkPulling/sql.test.js +116 -44
- package/lib/test/bulkPulling/stmt1.func.test.js +31 -30
- package/lib/test/bulkPulling/stmt1.type.test.js +1 -1
- package/lib/test/bulkPulling/stmt2.failover.test.d.ts +2 -0
- package/lib/test/bulkPulling/stmt2.failover.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/stmt2.failover.test.js +313 -0
- package/lib/test/bulkPulling/stmt2.func.test.js +37 -36
- package/lib/test/bulkPulling/stmt2.init.failover.test.d.ts +2 -0
- package/lib/test/bulkPulling/stmt2.init.failover.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/stmt2.init.failover.test.js +50 -0
- package/lib/test/bulkPulling/stmt2.type.test.js +1 -1
- package/lib/test/bulkPulling/tmq.config.test.d.ts +2 -0
- package/lib/test/bulkPulling/tmq.config.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/tmq.config.test.js +77 -0
- package/lib/test/bulkPulling/tmq.failover.test.d.ts +2 -0
- package/lib/test/bulkPulling/tmq.failover.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/tmq.failover.test.js +404 -0
- package/lib/test/bulkPulling/tmq.test.js +135 -14
- package/lib/test/bulkPulling/urlParser.test.d.ts +2 -0
- package/lib/test/bulkPulling/urlParser.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/urlParser.test.js +452 -0
- package/lib/test/bulkPulling/wsClient.reconnect.integration.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsClient.reconnect.integration.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsClient.reconnect.integration.test.js +184 -0
- package/lib/test/bulkPulling/wsClient.recovery.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsClient.recovery.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsClient.recovery.test.js +104 -0
- package/lib/test/bulkPulling/wsConfig.dsn.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsConfig.dsn.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsConfig.dsn.test.js +39 -0
- package/lib/test/bulkPulling/wsConnectPool.test.js +7 -7
- package/lib/test/bulkPulling/wsConnector.failover.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsConnector.failover.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsConnector.failover.test.js +497 -0
- package/lib/test/bulkPulling/wsConnectorPool.key.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsConnectorPool.key.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsConnectorPool.key.test.js +52 -0
- package/lib/test/bulkPulling/wsConnectorPool.keyAuth.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsConnectorPool.keyAuth.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsConnectorPool.keyAuth.test.js +28 -0
- package/lib/test/bulkPulling/wsEventCallback.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsEventCallback.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsEventCallback.test.js +54 -0
- package/lib/test/bulkPulling/wsProxy.failover.integration.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsProxy.failover.integration.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsProxy.failover.integration.test.js +120 -0
- package/lib/test/bulkPulling/wsProxy.failover.test.d.ts +2 -0
- package/lib/test/bulkPulling/wsProxy.failover.test.d.ts.map +1 -0
- package/lib/test/bulkPulling/wsProxy.failover.test.js +465 -0
- package/lib/test/client/wsClient.recovery.test.d.ts +2 -0
- package/lib/test/client/wsClient.recovery.test.d.ts.map +1 -0
- package/lib/test/client/wsClient.recovery.test.js +122 -0
- package/lib/test/client/wsConnectPool.test.d.ts +2 -0
- package/lib/test/client/wsConnectPool.test.d.ts.map +1 -0
- package/lib/test/client/wsConnectPool.test.js +147 -0
- package/lib/test/client/wsConnector.failover.test.d.ts +2 -0
- package/lib/test/client/wsConnector.failover.test.d.ts.map +1 -0
- package/lib/test/client/wsConnector.failover.test.js +681 -0
- package/lib/test/client/wsConnector.leastConnections.test.d.ts +2 -0
- package/lib/test/client/wsConnector.leastConnections.test.d.ts.map +1 -0
- package/lib/test/client/wsConnector.leastConnections.test.js +71 -0
- package/lib/test/client/wsConnectorPool.key.test.d.ts +2 -0
- package/lib/test/client/wsConnectorPool.key.test.d.ts.map +1 -0
- package/lib/test/client/wsConnectorPool.key.test.js +127 -0
- package/lib/test/client/wsEventCallback.test.d.ts +2 -0
- package/lib/test/client/wsEventCallback.test.d.ts.map +1 -0
- package/lib/test/client/wsEventCallback.test.js +98 -0
- package/lib/test/common/addressConnectionTracker.test.d.ts +2 -0
- package/lib/test/common/addressConnectionTracker.test.d.ts.map +1 -0
- package/lib/test/common/addressConnectionTracker.test.js +74 -0
- package/lib/test/common/dsn.test.d.ts +2 -0
- package/lib/test/common/dsn.test.d.ts.map +1 -0
- package/lib/test/common/dsn.test.js +406 -0
- package/lib/test/common/log.test.d.ts +2 -0
- package/lib/test/common/log.test.d.ts.map +1 -0
- package/lib/test/common/log.test.js +54 -0
- package/lib/test/common/utils.test.d.ts +2 -0
- package/lib/test/common/utils.test.d.ts.map +1 -0
- package/lib/test/common/utils.test.js +13 -0
- package/lib/test/common/wsConfig.dsn.test.d.ts +2 -0
- package/lib/test/common/wsConfig.dsn.test.d.ts.map +1 -0
- package/lib/test/common/wsConfig.dsn.test.js +39 -0
- package/lib/test/helpers/utils.d.ts +27 -0
- package/lib/test/helpers/utils.d.ts.map +1 -0
- package/lib/test/helpers/utils.js +341 -0
- package/lib/test/helpers/wsFailoverProxy.d.ts +109 -0
- package/lib/test/helpers/wsFailoverProxy.d.ts.map +1 -0
- package/lib/test/helpers/wsFailoverProxy.js +420 -0
- package/lib/test/helpers/wsProxy.d.ts +110 -0
- package/lib/test/helpers/wsProxy.d.ts.map +1 -0
- package/lib/test/helpers/wsProxy.js +429 -0
- package/lib/test/sql/core/decimal.test.d.ts +2 -0
- package/lib/test/sql/core/decimal.test.d.ts.map +1 -0
- package/lib/test/sql/core/decimal.test.js +153 -0
- package/lib/test/sql/core/queryTables.test.d.ts +2 -0
- package/lib/test/sql/core/queryTables.test.d.ts.map +1 -0
- package/lib/test/sql/core/queryTables.test.js +506 -0
- package/lib/test/sql/core/schemaless.test.d.ts +2 -0
- package/lib/test/sql/core/schemaless.test.d.ts.map +1 -0
- package/lib/test/sql/core/schemaless.test.js +102 -0
- package/lib/test/sql/core/sql.test.d.ts +2 -0
- package/lib/test/sql/core/sql.test.d.ts.map +1 -0
- package/lib/test/sql/core/sql.test.js +324 -0
- package/lib/test/sql/decimal.test.d.ts +2 -0
- package/lib/test/sql/decimal.test.d.ts.map +1 -0
- package/lib/test/sql/decimal.test.js +153 -0
- package/lib/test/sql/failover/sql.failover.test.d.ts +2 -0
- package/lib/test/sql/failover/sql.failover.test.d.ts.map +1 -0
- package/lib/test/sql/failover/sql.failover.test.js +341 -0
- package/lib/test/sql/queryTables.test.d.ts +2 -0
- package/lib/test/sql/queryTables.test.d.ts.map +1 -0
- package/lib/test/sql/queryTables.test.js +506 -0
- package/lib/test/sql/schemaless.test.d.ts +2 -0
- package/lib/test/sql/schemaless.test.d.ts.map +1 -0
- package/lib/test/sql/schemaless.test.js +102 -0
- package/lib/test/sql/sql.failover.test.d.ts +2 -0
- package/lib/test/sql/sql.failover.test.d.ts.map +1 -0
- package/lib/test/sql/sql.failover.test.js +341 -0
- package/lib/test/sql/sql.test.d.ts +2 -0
- package/lib/test/sql/sql.test.d.ts.map +1 -0
- package/lib/test/sql/sql.test.js +324 -0
- package/lib/test/stmt/failover/stmt2.failover.mock.test.d.ts +2 -0
- package/lib/test/stmt/failover/stmt2.failover.mock.test.d.ts.map +1 -0
- package/lib/test/stmt/failover/stmt2.failover.mock.test.js +341 -0
- package/lib/test/stmt/failover/stmt2.failover.test.d.ts +2 -0
- package/lib/test/stmt/failover/stmt2.failover.test.d.ts.map +1 -0
- package/lib/test/stmt/failover/stmt2.failover.test.js +384 -0
- package/lib/test/stmt/stmt1.func.test.d.ts +2 -0
- package/lib/test/stmt/stmt1.func.test.d.ts.map +1 -0
- package/lib/test/stmt/stmt1.func.test.js +418 -0
- package/lib/test/stmt/stmt1.type.test.d.ts +2 -0
- package/lib/test/stmt/stmt1.type.test.d.ts.map +1 -0
- package/lib/test/stmt/stmt1.type.test.js +399 -0
- package/lib/test/stmt/stmt2.failover.mock.test.d.ts +2 -0
- package/lib/test/stmt/stmt2.failover.mock.test.d.ts.map +1 -0
- package/lib/test/stmt/stmt2.failover.mock.test.js +341 -0
- package/lib/test/stmt/stmt2.failover.test.d.ts +2 -0
- package/lib/test/stmt/stmt2.failover.test.d.ts.map +1 -0
- package/lib/test/stmt/stmt2.failover.test.js +384 -0
- package/lib/test/stmt/stmt2.func.test.d.ts +2 -0
- package/lib/test/stmt/stmt2.func.test.d.ts.map +1 -0
- package/lib/test/stmt/stmt2.func.test.js +537 -0
- package/lib/test/stmt/stmt2.type.test.d.ts +2 -0
- package/lib/test/stmt/stmt2.type.test.d.ts.map +1 -0
- package/lib/test/stmt/stmt2.type.test.js +401 -0
- package/lib/test/stmt/v1/stmt1.func.test.d.ts +2 -0
- package/lib/test/stmt/v1/stmt1.func.test.d.ts.map +1 -0
- package/lib/test/stmt/v1/stmt1.func.test.js +418 -0
- package/lib/test/stmt/v1/stmt1.type.test.d.ts +2 -0
- package/lib/test/stmt/v1/stmt1.type.test.d.ts.map +1 -0
- package/lib/test/stmt/v1/stmt1.type.test.js +399 -0
- package/lib/test/stmt/v2/stmt2.func.test.d.ts +2 -0
- package/lib/test/stmt/v2/stmt2.func.test.d.ts.map +1 -0
- package/lib/test/stmt/v2/stmt2.func.test.js +537 -0
- package/lib/test/stmt/v2/stmt2.type.test.d.ts +2 -0
- package/lib/test/stmt/v2/stmt2.type.test.d.ts.map +1 -0
- package/lib/test/stmt/v2/stmt2.type.test.js +401 -0
- package/lib/test/tmq/cloud/cloud.tmq.test.d.ts +2 -0
- package/lib/test/tmq/cloud/cloud.tmq.test.d.ts.map +1 -0
- package/lib/test/tmq/cloud/cloud.tmq.test.js +84 -0
- package/lib/test/tmq/cloud/tmq.cloud.test.d.ts +2 -0
- package/lib/test/tmq/cloud/tmq.cloud.test.d.ts.map +1 -0
- package/lib/test/tmq/cloud/tmq.cloud.test.js +82 -0
- package/lib/test/tmq/core/tmq.config.test.d.ts +2 -0
- package/lib/test/tmq/core/tmq.config.test.d.ts.map +1 -0
- package/lib/test/tmq/core/tmq.config.test.js +83 -0
- package/lib/test/tmq/core/tmq.test.d.ts +2 -0
- package/lib/test/tmq/core/tmq.test.d.ts.map +1 -0
- package/lib/test/tmq/core/tmq.test.js +513 -0
- package/lib/test/tmq/failover/tmq.failover.test.d.ts +2 -0
- package/lib/test/tmq/failover/tmq.failover.test.d.ts.map +1 -0
- package/lib/test/tmq/failover/tmq.failover.test.js +404 -0
- package/lib/test/tmq/tmq.cloud.test.d.ts +2 -0
- package/lib/test/tmq/tmq.cloud.test.d.ts.map +1 -0
- package/lib/test/tmq/tmq.cloud.test.js +82 -0
- package/lib/test/tmq/tmq.config.test.d.ts +2 -0
- package/lib/test/tmq/tmq.config.test.d.ts.map +1 -0
- package/lib/test/tmq/tmq.config.test.js +94 -0
- package/lib/test/tmq/tmq.failover.test.d.ts +2 -0
- package/lib/test/tmq/tmq.failover.test.d.ts.map +1 -0
- package/lib/test/tmq/tmq.failover.test.js +404 -0
- package/lib/test/tmq/tmq.test.d.ts +2 -0
- package/lib/test/tmq/tmq.test.d.ts.map +1 -0
- package/lib/test/tmq/tmq.test.js +513 -0
- package/lib/test/unit/connectionManager.test.d.ts +2 -0
- package/lib/test/unit/connectionManager.test.d.ts.map +1 -0
- package/lib/test/unit/connectionManager.test.js +91 -0
- package/lib/test/utils.d.ts +4 -0
- package/lib/test/utils.d.ts.map +1 -1
- package/lib/test/utils.js +11 -17
- package/package.json +1 -1
- package/readme.md +2 -2
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const wsConnector_1 = require("@src/client/wsConnector");
|
|
4
|
+
const addressConnectionTracker_1 = require("@src/common/addressConnectionTracker");
|
|
5
|
+
const dsn_1 = require("@src/common/dsn");
|
|
6
|
+
function resetAddressTracker() {
|
|
7
|
+
const tracker = addressConnectionTracker_1.AddressConnectionTracker.instance();
|
|
8
|
+
tracker._counts.clear();
|
|
9
|
+
}
|
|
10
|
+
function installWebSocketMock(autoOpen) {
|
|
11
|
+
const websocketModule = require("websocket");
|
|
12
|
+
const openState = websocketModule.w3cwebsocket.OPEN ?? 1;
|
|
13
|
+
const connectingState = websocketModule.w3cwebsocket.CONNECTING ?? 0;
|
|
14
|
+
const sockets = [];
|
|
15
|
+
jest
|
|
16
|
+
.spyOn(websocketModule, "w3cwebsocket")
|
|
17
|
+
.mockImplementation(function (...args) {
|
|
18
|
+
const url = args[0];
|
|
19
|
+
const socket = {
|
|
20
|
+
url,
|
|
21
|
+
readyState: connectingState,
|
|
22
|
+
send: jest.fn(),
|
|
23
|
+
close: jest.fn(),
|
|
24
|
+
};
|
|
25
|
+
sockets.push(socket);
|
|
26
|
+
if (autoOpen) {
|
|
27
|
+
setTimeout(() => {
|
|
28
|
+
socket.readyState = openState;
|
|
29
|
+
socket.onopen?.();
|
|
30
|
+
}, 0);
|
|
31
|
+
}
|
|
32
|
+
return socket;
|
|
33
|
+
});
|
|
34
|
+
websocketModule.w3cwebsocket.OPEN = openState;
|
|
35
|
+
return { sockets };
|
|
36
|
+
}
|
|
37
|
+
describe("WebSocketConnector least-connections selection", () => {
|
|
38
|
+
beforeEach(() => {
|
|
39
|
+
resetAddressTracker();
|
|
40
|
+
});
|
|
41
|
+
afterEach(() => {
|
|
42
|
+
jest.restoreAllMocks();
|
|
43
|
+
resetAddressTracker();
|
|
44
|
+
});
|
|
45
|
+
test("constructor chooses least-connected address for initial connection", async () => {
|
|
46
|
+
const tracker = addressConnectionTracker_1.AddressConnectionTracker.instance();
|
|
47
|
+
tracker.increment("host1:6041");
|
|
48
|
+
tracker.increment("host1:6041");
|
|
49
|
+
tracker.increment("host1:6041");
|
|
50
|
+
jest.spyOn(Math, "random").mockReturnValue(0);
|
|
51
|
+
const { sockets } = installWebSocketMock(true);
|
|
52
|
+
const connector = new wsConnector_1.WebSocketConnector((0, dsn_1.parse)("ws://root:taosdata@host1:6041,host2:6042"), "pool-key-test", 3000);
|
|
53
|
+
await connector.ready();
|
|
54
|
+
expect(sockets).toHaveLength(1);
|
|
55
|
+
expect(sockets[0].url).toContain("host2:6042");
|
|
56
|
+
expect(tracker.getCount("host2:6042")).toBe(1);
|
|
57
|
+
connector.close();
|
|
58
|
+
});
|
|
59
|
+
test("increments address count when socket onopen fires", async () => {
|
|
60
|
+
const tracker = addressConnectionTracker_1.AddressConnectionTracker.instance();
|
|
61
|
+
const { sockets } = installWebSocketMock(false);
|
|
62
|
+
const connector = new wsConnector_1.WebSocketConnector((0, dsn_1.parse)("ws://root:taosdata@host1:6041"), "pool-key-onopen", 3000);
|
|
63
|
+
expect(tracker.getCount("host1:6041")).toBe(0);
|
|
64
|
+
expect(sockets).toHaveLength(1);
|
|
65
|
+
sockets[0].readyState = 1;
|
|
66
|
+
sockets[0].onopen?.();
|
|
67
|
+
await connector.ready();
|
|
68
|
+
expect(tracker.getCount("host1:6041")).toBe(1);
|
|
69
|
+
connector.close();
|
|
70
|
+
});
|
|
71
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wsConnectorPool.key.test.d.ts","sourceRoot":"","sources":["../../../test/client/wsConnectorPool.key.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,127 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const wsConnectorPool_1 = require("@src/client/wsConnectorPool");
|
|
4
|
+
const wsConnector_1 = require("@src/client/wsConnector");
|
|
5
|
+
const config_1 = require("@src/common/config");
|
|
6
|
+
const dsn_1 = require("@src/common/dsn");
|
|
7
|
+
const wsSql_1 = require("@src/sql/wsSql");
|
|
8
|
+
const utils_1 = require("@test-helpers/utils");
|
|
9
|
+
const websocket_1 = require("websocket");
|
|
10
|
+
function resetPoolSingleton() {
|
|
11
|
+
const PoolClass = wsConnectorPool_1.WebSocketConnectionPool;
|
|
12
|
+
if (PoolClass._instance) {
|
|
13
|
+
PoolClass._instance.destroyed();
|
|
14
|
+
PoolClass._instance = undefined;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
describe("WebSocketConnectionPool key generation", () => {
|
|
18
|
+
beforeEach(() => {
|
|
19
|
+
resetPoolSingleton();
|
|
20
|
+
});
|
|
21
|
+
afterEach(() => {
|
|
22
|
+
resetPoolSingleton();
|
|
23
|
+
});
|
|
24
|
+
test("normalizes address order when generating pool key", () => {
|
|
25
|
+
const pool = wsConnectorPool_1.WebSocketConnectionPool.instance();
|
|
26
|
+
const dsnA = (0, dsn_1.parse)("ws://root:taosdata@host2:6042,host1:6041/mydb?timezone=UTC&token=abc");
|
|
27
|
+
const dsnB = (0, dsn_1.parse)("ws://root:taosdata@host1:6041,host2:6042/mydb?token=abc&timezone=UTC");
|
|
28
|
+
const keyA = pool.getPoolKey(dsnA);
|
|
29
|
+
const keyB = pool.getPoolKey(dsnB);
|
|
30
|
+
expect(keyA).toBe(keyB);
|
|
31
|
+
});
|
|
32
|
+
test("isolates connections for different auth identities", () => {
|
|
33
|
+
const pool = wsConnectorPool_1.WebSocketConnectionPool.instance();
|
|
34
|
+
const dsnUserA = (0, dsn_1.parse)("ws://root:taosdata@host1:6041/mydb");
|
|
35
|
+
const dsnUserB = (0, dsn_1.parse)("ws://admin:taosdata@host1:6041/mydb");
|
|
36
|
+
const keyA = pool.getPoolKey(dsnUserA);
|
|
37
|
+
const keyB = pool.getPoolKey(dsnUserB);
|
|
38
|
+
expect(keyA).not.toBe(keyB);
|
|
39
|
+
});
|
|
40
|
+
test("isolates connections for different token values", () => {
|
|
41
|
+
const pool = wsConnectorPool_1.WebSocketConnectionPool.instance();
|
|
42
|
+
const dsnA = (0, dsn_1.parse)("ws://host1:6041/mydb?token=token-a");
|
|
43
|
+
const dsnB = (0, dsn_1.parse)("ws://host1:6041/mydb?token=token-b");
|
|
44
|
+
const keyA = pool.getPoolKey(dsnA);
|
|
45
|
+
const keyB = pool.getPoolKey(dsnB);
|
|
46
|
+
expect(keyA).not.toBe(keyB);
|
|
47
|
+
});
|
|
48
|
+
test("does not collide auth scope when credentials contain colon", () => {
|
|
49
|
+
const pool = wsConnectorPool_1.WebSocketConnectionPool.instance();
|
|
50
|
+
const dsnA = (0, dsn_1.parse)("ws://host1:6041/mydb");
|
|
51
|
+
dsnA.username = "a:b";
|
|
52
|
+
dsnA.password = "c";
|
|
53
|
+
const dsnB = (0, dsn_1.parse)("ws://host1:6041/mydb");
|
|
54
|
+
dsnB.username = "a";
|
|
55
|
+
dsnB.password = "b:c";
|
|
56
|
+
const keyA = pool.getPoolKey(dsnA);
|
|
57
|
+
const keyB = pool.getPoolKey(dsnB);
|
|
58
|
+
expect(keyA).not.toBe(keyB);
|
|
59
|
+
});
|
|
60
|
+
test("does not split pool key by reconnect policy", () => {
|
|
61
|
+
const pool = wsConnectorPool_1.WebSocketConnectionPool.instance();
|
|
62
|
+
const lowRetryDsn = (0, dsn_1.parse)("ws://root:taosdata@host1:6041/mydb?retries=1&retry_backoff_ms=10&retry_backoff_max_ms=20");
|
|
63
|
+
const highRetryDsn = (0, dsn_1.parse)("ws://root:taosdata@host1:6041/mydb?retries=60&retry_backoff_ms=100&retry_backoff_max_ms=500");
|
|
64
|
+
const lowRetryKey = pool.getPoolKey(lowRetryDsn);
|
|
65
|
+
const highRetryKey = pool.getPoolKey(highRetryDsn);
|
|
66
|
+
expect(lowRetryKey).toBe(highRetryKey);
|
|
67
|
+
});
|
|
68
|
+
test("updates connector retry policy when reusing pooled connector", async () => {
|
|
69
|
+
const pool = wsConnectorPool_1.WebSocketConnectionPool.instance();
|
|
70
|
+
const lowRetryDsn = (0, dsn_1.parse)("ws://root:taosdata@host1:6041/mydb?retries=1&retry_backoff_ms=10&retry_backoff_max_ms=20");
|
|
71
|
+
const highRetryDsn = (0, dsn_1.parse)("ws://root:taosdata@host1:6041/mydb?retries=60&retry_backoff_ms=100&retry_backoff_max_ms=500");
|
|
72
|
+
const poolKey = pool.getPoolKey(lowRetryDsn);
|
|
73
|
+
let retries = 1;
|
|
74
|
+
const connector = {
|
|
75
|
+
readyState: jest.fn(() => websocket_1.w3cwebsocket.OPEN),
|
|
76
|
+
close: jest.fn(),
|
|
77
|
+
refreshRetryConfig: jest.fn((dsn) => {
|
|
78
|
+
retries = wsConnector_1.RetryConfig.fromDsn(dsn).retries;
|
|
79
|
+
}),
|
|
80
|
+
getReconnectRetries: jest.fn(() => retries),
|
|
81
|
+
getPoolKey: jest.fn(() => poolKey),
|
|
82
|
+
};
|
|
83
|
+
pool.pool.set(poolKey, [connector]);
|
|
84
|
+
const reused = await pool.getConnection(highRetryDsn, 3000);
|
|
85
|
+
expect(reused).toBe(connector);
|
|
86
|
+
expect(connector.refreshRetryConfig).toHaveBeenCalledWith(highRetryDsn);
|
|
87
|
+
expect(reused.getReconnectRetries()).toBe(60);
|
|
88
|
+
});
|
|
89
|
+
test("includes endpoint-derived websocket path in the pool key scope", () => {
|
|
90
|
+
const pool = wsConnectorPool_1.WebSocketConnectionPool.instance();
|
|
91
|
+
const sqlDsn = (0, dsn_1.parse)("ws://root:taosdata@host1:6041/mydb");
|
|
92
|
+
const tmqDsn = (0, dsn_1.parse)("ws://root:taosdata@host1:6041/mydb");
|
|
93
|
+
tmqDsn.endpoint = dsn_1.WS_TMQ_ENDPOINT;
|
|
94
|
+
const sqlKey = pool.getPoolKey(sqlDsn);
|
|
95
|
+
const tmqKey = pool.getPoolKey(tmqDsn);
|
|
96
|
+
expect(sqlKey).not.toBe(tmqKey);
|
|
97
|
+
});
|
|
98
|
+
});
|
|
99
|
+
describe("Security: pool key must include auth identity", () => {
|
|
100
|
+
beforeEach(() => {
|
|
101
|
+
resetPoolSingleton();
|
|
102
|
+
});
|
|
103
|
+
afterEach(() => {
|
|
104
|
+
resetPoolSingleton();
|
|
105
|
+
});
|
|
106
|
+
test("username/password: different credentials must not share a pool entry", async () => {
|
|
107
|
+
const validDsn = `ws://${(0, utils_1.testUsername)()}:${(0, utils_1.testPassword)()}@localhost:6041`;
|
|
108
|
+
const wrongPasswordDsn = `ws://${(0, utils_1.testUsername)()}:WRONG_PASSWORD_SENTINEL@localhost:6041`;
|
|
109
|
+
const validConn = await wsSql_1.WsSql.open(new config_1.WSConfig(validDsn));
|
|
110
|
+
expect(validConn.state()).toBeGreaterThan(0);
|
|
111
|
+
await validConn.close();
|
|
112
|
+
await expect(wsSql_1.WsSql.open(new config_1.WSConfig(wrongPasswordDsn))).rejects.toThrow();
|
|
113
|
+
});
|
|
114
|
+
test("same credentials should share a pool entry (sanity check)", async () => {
|
|
115
|
+
const dsn = `ws://${(0, utils_1.testUsername)()}:${(0, utils_1.testPassword)()}@localhost:6041`;
|
|
116
|
+
const conn1 = await wsSql_1.WsSql.open(new config_1.WSConfig(dsn));
|
|
117
|
+
expect(conn1.state()).toBeGreaterThan(0);
|
|
118
|
+
const connector1 = conn1._wsClient._wsConnector;
|
|
119
|
+
expect(connector1).toBeDefined();
|
|
120
|
+
await conn1.close();
|
|
121
|
+
const conn2 = await wsSql_1.WsSql.open(new config_1.WSConfig(dsn));
|
|
122
|
+
expect(conn2.state()).toBeGreaterThan(0);
|
|
123
|
+
const connector2 = conn2._wsClient._wsConnector;
|
|
124
|
+
expect(connector2).toBe(connector1);
|
|
125
|
+
await conn2.close();
|
|
126
|
+
});
|
|
127
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wsEventCallback.test.d.ts","sourceRoot":"","sources":["../../../test/client/wsEventCallback.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const wsEventCallback_1 = require("@src/client/wsEventCallback");
|
|
4
|
+
function resetCallbackRegistry() {
|
|
5
|
+
const CallbackClass = wsEventCallback_1.WsEventCallback;
|
|
6
|
+
CallbackClass._msgActionRegister = new Map();
|
|
7
|
+
}
|
|
8
|
+
describe("WsEventCallback lifecycle", () => {
|
|
9
|
+
beforeEach(() => {
|
|
10
|
+
resetCallbackRegistry();
|
|
11
|
+
});
|
|
12
|
+
afterEach(() => {
|
|
13
|
+
resetCallbackRegistry();
|
|
14
|
+
jest.restoreAllMocks();
|
|
15
|
+
});
|
|
16
|
+
test("clears timeout when callback is matched", async () => {
|
|
17
|
+
const callback = wsEventCallback_1.WsEventCallback.instance();
|
|
18
|
+
const resolve = jest.fn();
|
|
19
|
+
const reject = jest.fn();
|
|
20
|
+
const clearSpy = jest.spyOn(global, "clearTimeout");
|
|
21
|
+
await callback.registerCallback({
|
|
22
|
+
action: "insert",
|
|
23
|
+
req_id: 11n,
|
|
24
|
+
timeout: 2000,
|
|
25
|
+
}, resolve, reject);
|
|
26
|
+
await callback.handleEventCallback({
|
|
27
|
+
action: "insert",
|
|
28
|
+
req_id: 11n,
|
|
29
|
+
}, wsEventCallback_1.OnMessageType.MESSAGE_TYPE_STRING, {
|
|
30
|
+
action: "insert",
|
|
31
|
+
req_id: 11n,
|
|
32
|
+
code: 0,
|
|
33
|
+
});
|
|
34
|
+
expect(resolve).toHaveBeenCalledTimes(1);
|
|
35
|
+
expect(reject).not.toHaveBeenCalled();
|
|
36
|
+
expect(clearSpy).toHaveBeenCalled();
|
|
37
|
+
expect(wsEventCallback_1.WsEventCallback._msgActionRegister.size).toBe(0);
|
|
38
|
+
});
|
|
39
|
+
test("unregisterCallback removes entry and clears its timeout", async () => {
|
|
40
|
+
const callback = wsEventCallback_1.WsEventCallback.instance();
|
|
41
|
+
const resolve = jest.fn();
|
|
42
|
+
const reject = jest.fn();
|
|
43
|
+
const clearSpy = jest.spyOn(global, "clearTimeout");
|
|
44
|
+
await callback.registerCallback({
|
|
45
|
+
action: "options_connection",
|
|
46
|
+
req_id: 22n,
|
|
47
|
+
timeout: 2000,
|
|
48
|
+
id: 22n,
|
|
49
|
+
}, resolve, reject);
|
|
50
|
+
await callback.unregisterCallback(22n);
|
|
51
|
+
expect(clearSpy).toHaveBeenCalled();
|
|
52
|
+
expect(wsEventCallback_1.WsEventCallback._msgActionRegister.size).toBe(0);
|
|
53
|
+
});
|
|
54
|
+
test("timeout callback does not reject if response already handled", async () => {
|
|
55
|
+
const callback = wsEventCallback_1.WsEventCallback.instance();
|
|
56
|
+
const resolve = jest.fn();
|
|
57
|
+
const reject = jest.fn();
|
|
58
|
+
let capturedTimeoutHandler = null;
|
|
59
|
+
jest.spyOn(global, "setTimeout").mockImplementation(((handler) => {
|
|
60
|
+
capturedTimeoutHandler = handler;
|
|
61
|
+
return 1;
|
|
62
|
+
}));
|
|
63
|
+
await callback.registerCallback({
|
|
64
|
+
action: "insert",
|
|
65
|
+
req_id: 33n,
|
|
66
|
+
timeout: 2000,
|
|
67
|
+
}, resolve, reject);
|
|
68
|
+
await callback.handleEventCallback({
|
|
69
|
+
action: "insert",
|
|
70
|
+
req_id: 33n,
|
|
71
|
+
}, wsEventCallback_1.OnMessageType.MESSAGE_TYPE_STRING, {
|
|
72
|
+
action: "insert",
|
|
73
|
+
req_id: 33n,
|
|
74
|
+
code: 0,
|
|
75
|
+
});
|
|
76
|
+
expect(resolve).toHaveBeenCalledTimes(1);
|
|
77
|
+
expect(reject).not.toHaveBeenCalled();
|
|
78
|
+
expect(capturedTimeoutHandler).toBeTruthy();
|
|
79
|
+
await capturedTimeoutHandler();
|
|
80
|
+
expect(reject).not.toHaveBeenCalled();
|
|
81
|
+
});
|
|
82
|
+
test("timeout handler removes callback entry when timer fires", async () => {
|
|
83
|
+
jest.useFakeTimers();
|
|
84
|
+
const callback = wsEventCallback_1.WsEventCallback.instance();
|
|
85
|
+
const resolve = jest.fn();
|
|
86
|
+
const reject = jest.fn();
|
|
87
|
+
await callback.registerCallback({
|
|
88
|
+
action: "insert",
|
|
89
|
+
req_id: 44n,
|
|
90
|
+
timeout: 20,
|
|
91
|
+
}, resolve, reject);
|
|
92
|
+
expect(wsEventCallback_1.WsEventCallback._msgActionRegister.size).toBe(1);
|
|
93
|
+
await jest.advanceTimersByTimeAsync(20);
|
|
94
|
+
expect(wsEventCallback_1.WsEventCallback._msgActionRegister.size).toBe(0);
|
|
95
|
+
expect(resolve).not.toHaveBeenCalled();
|
|
96
|
+
expect(reject).toHaveBeenCalledTimes(1);
|
|
97
|
+
});
|
|
98
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"addressConnectionTracker.test.d.ts","sourceRoot":"","sources":["../../../test/common/addressConnectionTracker.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const addressConnectionTracker_1 = require("@src/common/addressConnectionTracker");
|
|
4
|
+
const dsn_1 = require("@src/common/dsn");
|
|
5
|
+
function resetTracker() {
|
|
6
|
+
const tracker = addressConnectionTracker_1.AddressConnectionTracker.instance();
|
|
7
|
+
tracker._counts.clear();
|
|
8
|
+
return tracker;
|
|
9
|
+
}
|
|
10
|
+
describe("AddressConnectionTracker", () => {
|
|
11
|
+
beforeEach(() => {
|
|
12
|
+
resetTracker();
|
|
13
|
+
});
|
|
14
|
+
afterEach(() => {
|
|
15
|
+
jest.restoreAllMocks();
|
|
16
|
+
resetTracker();
|
|
17
|
+
});
|
|
18
|
+
test("increment/decrement updates counts correctly", () => {
|
|
19
|
+
const tracker = resetTracker();
|
|
20
|
+
tracker.increment("host1:6041");
|
|
21
|
+
tracker.increment("host1:6041");
|
|
22
|
+
tracker.increment("host2:6042");
|
|
23
|
+
expect(tracker.getCount("host1:6041")).toBe(2);
|
|
24
|
+
expect(tracker.getCount("host2:6042")).toBe(1);
|
|
25
|
+
tracker.decrement("host1:6041");
|
|
26
|
+
expect(tracker.getCount("host1:6041")).toBe(1);
|
|
27
|
+
});
|
|
28
|
+
test("decrement never makes count negative", () => {
|
|
29
|
+
const tracker = resetTracker();
|
|
30
|
+
tracker.decrement("host1:6041");
|
|
31
|
+
tracker.increment("host1:6041");
|
|
32
|
+
tracker.decrement("host1:6041");
|
|
33
|
+
tracker.decrement("host1:6041");
|
|
34
|
+
expect(tracker.getCount("host1:6041")).toBe(0);
|
|
35
|
+
});
|
|
36
|
+
test("selectLeastConnected returns index with minimum count", () => {
|
|
37
|
+
const tracker = resetTracker();
|
|
38
|
+
const addresses = [
|
|
39
|
+
new dsn_1.Address("host1", 6041),
|
|
40
|
+
new dsn_1.Address("host2", 6042),
|
|
41
|
+
new dsn_1.Address("host3", 6043),
|
|
42
|
+
];
|
|
43
|
+
tracker.increment("host1:6041");
|
|
44
|
+
tracker.increment("host1:6041");
|
|
45
|
+
tracker.increment("host3:6043");
|
|
46
|
+
const index = tracker.selectLeastConnected(addresses);
|
|
47
|
+
expect(index).toBe(1);
|
|
48
|
+
});
|
|
49
|
+
test("selectLeastConnected uses random tie-break among least-connected addresses", () => {
|
|
50
|
+
const tracker = resetTracker();
|
|
51
|
+
const addresses = [
|
|
52
|
+
new dsn_1.Address("host1", 6041),
|
|
53
|
+
new dsn_1.Address("host2", 6042),
|
|
54
|
+
new dsn_1.Address("host3", 6043),
|
|
55
|
+
];
|
|
56
|
+
tracker.increment("host3:6043");
|
|
57
|
+
tracker.increment("host3:6043");
|
|
58
|
+
const rounds = 400;
|
|
59
|
+
let host1Count = 0;
|
|
60
|
+
let host2Count = 0;
|
|
61
|
+
for (let i = 0; i < rounds; i++) {
|
|
62
|
+
const selected = tracker.selectLeastConnected(addresses);
|
|
63
|
+
if (selected === 0) {
|
|
64
|
+
host1Count += 1;
|
|
65
|
+
}
|
|
66
|
+
if (selected === 1) {
|
|
67
|
+
host2Count += 1;
|
|
68
|
+
}
|
|
69
|
+
expect(selected).not.toBe(2);
|
|
70
|
+
}
|
|
71
|
+
expect(host1Count).toBeGreaterThan(80);
|
|
72
|
+
expect(host2Count).toBeGreaterThan(80);
|
|
73
|
+
});
|
|
74
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dsn.test.d.ts","sourceRoot":"","sources":["../../../test/common/dsn.test.ts"],"names":[],"mappings":""}
|